nowinandroid icon indicating copy to clipboard operation
nowinandroid copied to clipboard

Missing implementation of NET_CAPABILITY_VALIDATED in ConnectivityManager

Open loke101 opened this issue 11 months ago • 3 comments

The current implementation of ConnectivityManager.isCurrentlyConnected() does not check for the NET_CAPABILITY_VALIDATED capability, leading to incorrect behavior when determining network connectivity status.

Steps to Reproduce:

  • Connect to a Wi-Fi network or cellular network that requires login/authentication but does not have internet access.
  • Observe that the app does not display a Snackbar or any indication of lack of internet access.
  • Expected Behavior:
  • The app should detect that the network does not have internet access and display a Snackbar or some form of notification to inform the user. I propose updating the isCurrentlyConnected() function in ConnectivityManager to include a check for the NET_CAPABILITY_VALIDATED capability. Here's the modified code:

private fun ConnectivityManager.isCurrentlyConnected() = when { Build.VERSION.SDK_INT >= Build.VERSION_CODES.M -> { activeNetwork ?.let { network -> getNetworkCapabilities(network)?.let { capabilities -> capabilities.hasCapability(NetworkCapabilities.NET_CAPABILITY_INTERNET) && capabilities.hasCapability(NetworkCapabilities.NET_CAPABILITY_VALIDATED) } } ?: false } else -> activeNetworkInfo?.isConnected ?: false }

val networkCapabilities = connectivityManager.getNetworkCapabilities(network) val hasInternetCapability = networkCapabilities?.hasCapability(NetworkCapabilities.NET_CAPABILITY_VALIDATED) if (hasInternetCapability == true) { networks += network channel.trySend(true) }

loke101 avatar Mar 16 '24 09:03 loke101

In Android OS, differentiating between NET_CAPABILITY_INTERNET and NET_CAPABILITY_VALIDATED is designed to give developers more granular control over network connections. : link

  • NET_CAPABILITY_INTERNET is used to check if the current network is capable of connecting to the internet.
  • NET_CAPABILITY_VALIDATED is used before actual data exchange through the network to ensure that data can be successfully sent and received.

It appears that the differentiation between each status value, as currently implemented, is intended for usage according to their respective purposes.

If you have a different opinion or further insights, please feel free to leave a comment!

yongsuk44 avatar Mar 18 '24 07:03 yongsuk44

Then how can we check if we are connected to WIFI but has internet connection or not ?? @yongsuk44

loke101 avatar Mar 18 '24 11:03 loke101

@loke101 If you're asking about how to check if Wi-Fi is connected but not actually connected to the internet, I think I would handle it like this:

NetworkRequest.Builder()
    .addCapability(NetworkCapabilities.NET_CAPABILITY_INTERNET)
    .addTransportType(NetworkCapabilities.TRANSPORT_WIFI)
    .build()

// ...

val networkCapabilities = getNetworkCapabilities(activeNetwork)

val hasActiveInternetConnection =
    networkCapabilities?.hasCapability(NetworkCapabilities.NET_CAPABILITY_INTERNET)
        && networkCapabilities?.hasTransport(NetworkCapabilities.TRANSPORT_WIFI)

By doing this, you should be able to determine cases where Wi-Fi is connected but there is no internet connection.

Link

yongsuk44 avatar Mar 18 '24 12:03 yongsuk44