1

I am trying to listen to network changes using method registerDefaultNetworkCallback() of conenctivityManager Using the code below from this answer

     val connectivityManager = cotnext.getSystemService(Context.CONNECTIVITY_SERVICE) as ConnectivityManager
        connectivityManager?.let {
            it.registerDefaultNetworkCallback(object : ConnectivityManager.NetworkCallback() {
                override fun onAvailable(network: Network) {
                    //take action when network connection is gained
                }
                override fun onLost(network: Network) {
                    //take action when network connection is lost
                }
            })
        }

but I have a few questions about this method:

  1. what if the phone is connected to wifi but the wifi is not connected to Internet
  2. In the method documentation I read this which I don't understand, when exactly will the limit will hit? If the callback is called 100 times then an Exception will be thrown? And how to handle this?

To avoid performance issues due to apps leaking callbacks, the system will limit the number of outstanding requests to 100 per app (identified by their UID), shared with all variants of this method, of requestNetwork as well as ConnectivityDiagnosticsManager.registerConnectivityDiagnosticsCallback. Requesting a network with this method will count toward this limit. If this limit is exceeded, an exception will be thrown. To avoid hitting this issue and to conserve resources, make sure to unregister the callbacks with unregisterNetworkCallback(ConnectivityManager.NetworkCallback).

David Ibrahim
  • 748
  • 4
  • 16

2 Answers2

1
  1. what if the phone is connected to wifi but the wifi is not connected to Internet

The answer, this method will return false

  1. In the method documentation I read this which I don't understand, when exactly will the limit will hit? If the callback is called 100 times then an Exception will be thrown? And how to handle this?

I think it means if you cant register more than 100 callback

David Ibrahim
  • 748
  • 4
  • 16
  • I'm also not sure what "100 outstanding requests" means, they should make it more clear. But yea looking at the exception it throws it probably means 100 registrations – DennisVA Feb 22 '21 at 22:49
  • It's 100 registered listeners. If you count your listeners, you will get crash (TooManyRequestsException) when your registered listeners reach 100. – Atakan Yildirim May 09 '21 at 20:20
0

At first, add the ConnectivityReceiver class:

class ConnectivityReceiver : BroadcastReceiver() {
    override fun onReceive(context: Context, intent: Intent) {
        if (connectivityReceiverListener != null) {
            connectivityReceiverListener!!.onNetworkConnectionChanged(
                isConnectedOrConnecting(
                    context
                )
            )
        }
    }

    private fun isConnectedOrConnecting(context: Context): Boolean {
        val cm = context.getSystemService(Context.CONNECTIVITY_SERVICE) as ConnectivityManager

        if (cm != null) {
            if (Build.VERSION.SDK_INT < 23) {
                val ni = cm.activeNetworkInfo
                if (ni != null) {
                    return ni.isConnected && (ni.type == ConnectivityManager.TYPE_WIFI || ni.type == ConnectivityManager.TYPE_MOBILE)
                }
            } else {
                val n = cm.activeNetwork
                if (n != null) {
                    val nc = cm.getNetworkCapabilities(n)
                    return nc!!.hasTransport(NetworkCapabilities.TRANSPORT_CELLULAR) || nc!!.hasTransport(
                        NetworkCapabilities.TRANSPORT_WIFI
                    )
                }
            }
        }
        return false
    }

    interface ConnectivityReceiverListener {
        fun onNetworkConnectionChanged(isConnected: Boolean)
    }

    companion object {
        var connectivityReceiverListener: ConnectivityReceiverListener? = null
    }

}

Then In your BaseActivity or MainActivity add these lines:

 abstract class BaseActivity:AppCompatActivity(), 
      ConnectivityReceiver.ConnectivityReceiverListener {

var receiver: ConnectivityReceiver? = null

override fun onResume() {
        super.onResume()
        try {
            receiver = ConnectivityReceiver()
            registerReceiver(
                receiver!!,
                IntentFilter(ConnectivityManager.CONNECTIVITY_ACTION)
            )
            connectivityReceiverListener = this
        } catch (ex: Exception) {
            //Timber.d("Base ex ${ex.localizedMessage}")
        }

    }

    override fun onPause() {
        try {
            unregisterReceiver(receiver!!)
            receiver = null

        } catch (ex: Exception) {
        }
        super.onPause()

    }

 override fun onNetworkConnectionChanged(isConnected: Boolean) {
        showMessage(isConnected)
    }


private fun showMessage(isConnected: Boolean) {
    try {
        if (!isConnected) {
           Log.d("Connection state"," disconnected")
        } else {
            Log.d("Connection state"," connected")
        }
    } catch (ex: Exception) {
       
    }
} 
}

You should register the receiver in the OnResume method and unregister it in theOnPause method

mona baharlou
  • 621
  • 4
  • 14