Connectivity Manager: What It Is, Methods, and Connection Monitoring

Author: IT Sectr Published: 2026-03-10 Reading time: 9 min

Connectivity Manager is an Android system service that provides applications with information about the device’s network connection status. It allows checking internet availability, determining the network type (Wi-Fi, mobile data, Ethernet), tracking connection changes, and managing network requests based on connection quality. According to Android Developers, 2025, ConnectivityManager is the main API for network monitoring and has been part of the Android Framework since API Level 1.

Key Takeaways

  • Connectivity Manager — an Android system service for monitoring the device’s network connection.
  • NetworkCallback — the primary mechanism for tracking network changes through callback registration.
  • NetworkCapabilities — a class providing detailed information about current network capabilities (Wi-Fi, mobile data, VPN, Ethernet).
  • NetworkRequest — a filter for subscribing to specific network types with defined characteristics.
  • getActiveNetworkInfo() — a deprecated method (deprecated since API 29), replaced by NetworkCallback and registerDefaultNetworkCallback.

What Is Connectivity Manager?

ConnectivityManager is a system service of the Android operating system, accessible via Context.getSystemService(Context.CONNECTIVITY_SERVICE). It provides an API for obtaining information about the device’s network connection, monitoring network changes, and managing the application’s network requests. Connectivity Manager has been part of the Android Framework since the first platform version (API Level 1) and has undergone significant changes over the decades: from the simple getActiveNetworkInfo() to the modern reactive model with NetworkCallback and NetworkRequest.

The main capabilities of Connectivity Manager include: checking for an active network connection, determining the network type (Wi-Fi, mobile data, Ethernet, Bluetooth, VPN), real-time monitoring of network state changes, obtaining bandwidth and latency information, and managing the application’s network requests. ConnectivityManager is used in conjunction with WorkManager and Repository to implement Offline-First architecture, adaptive content loading, and application optimization based on connection quality.

Starting with Android 10 (API 29), Google changed the approach to working with ConnectivityManager. The getActiveNetworkInfo() method is declared deprecated, and instead it is recommended to use registerDefaultNetworkCallback() or registerNetworkCallback() with NetworkRequest. The new API provides more detailed network information, including the ability to detect captive portals (Wi-Fi with authentication) and assess connection quality. ConnectivityManager is also integrated with the Jetpack family: the ConnectivityManager library was released in 2024 as part of Jetpack to simplify network monitoring in Compose applications.

The Role of Connectivity Manager in Application Architecture

In modern Android architecture, Connectivity Manager is used at the repository or UseCase level to make decisions about network requests. The Repository Layer checks the network state before calling the API: if the network is unavailable, data is returned from the local storage (Room). If the network is available, a request to the server is made, and the result is saved in Room. The ViewModel subscribes to a Flow from Room and does not know about the details of network interaction — this allows each layer to be tested independently.

How Connectivity Manager Works

Connectivity Manager obtains network state information from the connectivity system service, which interacts with the Linux kernel’s network interfaces. When the device connects to Wi-Fi or turns on mobile data, the kernel notifies the system service, which updates its internal state and notifies all registered callbacks. The architecture of ConnectivityManager is built on the Observer pattern: the application registers a NetworkCallback and receives notifications about any network changes — connection establishment, connection loss, network type change, or quality degradation.

The modern ConnectivityManager API uses NetworkRequest to filter network events. NetworkRequest allows specifying requirements for the network: transport (Transport.WIFI, Transport.CELLULAR, Transport.ETHERNET), internet capability (NetworkCapabilities.NET_CAPABILITY_INTERNET), and other criteria. If an application only needs Wi-Fi for downloading large files, it creates a NetworkRequest with Transport.WIFI and registers a callback. The system will notify the application only when the Wi-Fi connection changes, ignoring mobile network events.

An important feature of Connectivity Manager on Android 12+ is capabilities-based networking. The application does not just check “is there internet,” but can assess what type of traffic is available. For example, NET_CAPABILITY_NOT_METERED indicates an unmetered connection (Wi-Fi), NET_CAPABILITY_NOT_ROAMING indicates the device is not roaming. This allows making decisions: download video only on Wi-Fi, postpone synchronization while roaming, or use mobile data only for critical requests.

API LevelRecommended MethodStatus
1-22getActiveNetworkInfo()Deprecated
21+NetworkCallback + registerNetworkCallback()Recommended
24+registerDefaultNetworkCallback()Recommended
28+getActiveNetwork() + NetworkCapabilitiesAlternative
31+registerBestMatchingNetworkCallback()New API

Permissions for Connectivity Manager

Using Connectivity Manager in an Android application requires permissions. ACCESS_NETWORK_STATE is a mandatory permission for reading network information, declared in AndroidManifest.xml. Without this permission, ConnectivityManager will return null for getActiveNetwork() and will not invoke callbacks. For performing network operations, the INTERNET permission is also required. Starting with Android 10 (API 29), the application can check the network state without additional runtime permissions — ACCESS_NETWORK_STATE is a normal permission and is granted automatically upon installation.

Main Methods of Connectivity Manager

The modern Connectivity Manager provides several key methods for working with the network. getActiveNetwork() (API 23+) returns the Network object of the current active network or null if the device is not connected. This method does not require callbacks and is suitable for one-time checks. The Network object can be passed to NetworkCapabilities to obtain detailed information: transport type, metered status, roaming, internet capability, and other characteristics.

registerDefaultNetworkCallback() (API 24+) is the preferred way to monitor the network. The application registers a callback that is invoked upon any changes to the default network (the network through which the application sends traffic). The callback receives a Network object that can be used for binding sockets and HTTP clients. This method replaces the deprecated getActiveNetworkInfo() and provides reactive network monitoring without polling.

registerNetworkCallback() (API 21+) allows subscribing to changes of a specific network type via NetworkRequest. For example, an application can track only Wi-Fi networks using new NetworkRequest.Builder().addTransportType(NetworkCapabilities.TRANSPORT_WIFI).build(). The system will notify the application about Wi-Fi connection/disconnection without affecting mobile network events. NetworkCapabilities.getLinkDownstreamBandwidthKbps() returns an estimate of the downstream bandwidth in kbit/s, allowing content quality to be adapted to connection speed.

MethodMinimum APIPurpose
getActiveNetwork()23Get the current active network
getNetworkCapabilities()21Get network capabilities (type, metered, roaming)
registerDefaultNetworkCallback()24Monitor the default network
registerNetworkCallback()21Monitor networks by NetworkRequest filter
unregisterNetworkCallback()21Unregister a callback
getActiveNetworkInfo()1Deprecated, do not use

ConnectivityManager in Jetpack Compose

The Jetpack Connectivity library (androidx.core:core-ktx) provides convenient extensions for working with ConnectivityManager in Compose. The ConnectivityManager.observeAsState() function returns a State that updates when the network changes. The @Composable NetworkStatus() component displays the connection status and automatically redraws on changes. This saves the developer from manually managing callbacks and the Activity/Fragment lifecycle.

NetworkCallback and Handling Network Changes

ConnectivityManager.NetworkCallback is an abstract class with methods that are called by the system when the network state changes. onAvailable(Network) is called when a network becomes available. The application receives a Network object that can be used to bind sockets via Network.bindSocket(). onLost(Network) is called when a network becomes unavailable. The application should switch to local data or show a message about no connection. onCapabilitiesChanged(Network, NetworkCapabilities) is called when network characteristics change (for example, when switching from Wi-Fi to mobile data).

Proper handling of network changes requires considering the component lifecycle. The callback must be registered in onStart()/onResume() and unregistered in onStop()/onPause(). If the callback is not unregistered, it can continue running after the Activity is destroyed, causing memory leaks and potential NullPointerException when the callback tries to update the UI of a destroyed component. Use lifecycleScope or repeatOnLifecycle for automatic registration management. In Jetpack Compose, use DisposableEffect for callback registration and unregistration.

Captive portal handling is an important feature of ConnectivityManager starting from Android 10. A CAPTIVE_PORTAL is a scenario where a Wi-Fi network is available but requires authentication through a web page (airports, hotels, cafes). NetworkCapabilities.NET_CAPABILITY_VALIDATED indicates that the network has full internet access. If NET_CAPABILITY_VALIDATED is absent, the application can open a browser for captive portal authentication. The isCaptivePortal() method, added in Android 11 (API 30), is used to detect captive portals.

Network for Specific Purposes (NetworkRequest)

ConnectivityManager allows requesting a network for specific purposes through requestNetwork() and bindProcessToNetwork(). For example, an application for downloading large files can request a Wi-Fi network even if mobile data is active. To do this, a NetworkRequest is created with addTransportType(TRANSPORT_WIFI), and when Wi-Fi becomes available, the system calls onAvailable(). The application binds sockets to this network via network.bindSocket() or OkHttp with a configured Network object. This provides flexible control over the use of network interfaces.

Implementation Example in Kotlin

Let’s look at a complete example of using ConnectivityManager with the modern API (NetworkCallback) in Clean Architecture. NetworkMonitor is a wrapper class around ConnectivityManager that provides reactive network status via StateFlow. The ViewModel subscribes to this Flow and passes the state to the UI. The Repository uses NetworkMonitor to make decisions about network requests. This approach ensures testability and isolation of platform dependencies.

The example below shows how to correctly use ConnectivityManager with registerDefaultNetworkCallback. The NetworkMonitor class encapsulates work with the system service and provides a clean Kotlin Flow. It registers the callback on start and unregisters it on lifecycle end. Asynchronous operation is ensured through coroutines and callbackFlow — a bridge between the callback-style ConnectivityManager and the reactive Flow-style Kotlin.

kotlin
class NetworkMonitor(
    private val connectivityManager: ConnectivityManager
) {
    val isOnline: StateFlow<Boolean> = callbackFlow {
        val callback = object : ConnectivityManager.NetworkCallback() {
            override fun onAvailable(network: Network) {
                trySend(true)
            }
            override fun onLost(network: Network) {
                trySend(false)
            }
            override fun onCapabilitiesChanged(
                network: Network,
                caps: NetworkCapabilities
            ) {
                val connected = caps.hasCapability(
                    NetworkCapabilities.NET_CAPABILITY_INTERNET
                )
                trySend(connected)
            }
        }
        connectivityManager.registerDefaultNetworkCallback(callback)
        awaitClose {
            connectivityManager.unregisterNetworkCallback(callback)
        }
    }.stateIn(
        CoroutineScope(Dispatchers.Default),
        SharingStarted.WhileSubscribed(5000),
        initialValue = checkInitialState()
    )

    private fun checkInitialState(): Boolean {
        val network = connectivityManager.getActiveNetwork() ?: return false
        val caps = connectivityManager.getNetworkCapabilities(network) ?: return false
        return caps.hasCapability(
            NetworkCapabilities.NET_CAPABILITY_INTERNET
        )
    }
}

Using NetworkMonitor in ViewModel and Repository

The ViewModel subscribes to NetworkMonitor.isOnline via stateIn() and passes the state to Compose. The Repository checks the current isOnline.value before calling the API: if false — returns a Flow from Room. If true — calls the API, saves the result in Room, and returns a Flow from Room. WorkManager uses NetworkType.CONNECTED to constrain background tasks. Testing NetworkMonitor is done with a mock ConnectivityManager object and a fake NetworkCallback, allowing any network scenario to be emulated in unit tests.

Best Practices and Common Mistakes

The first rule of working with ConnectivityManager is not to use the deprecated API. getActiveNetworkInfo() has been deprecated since API 29 and may return incorrect data on newer Android versions. Instead, use getActiveNetwork() + getNetworkCapabilities() for one-time checks and registerDefaultNetworkCallback() for continuous monitoring. The old method also does not distinguish between networks with captive portals and full internet access, leading to false positives.

The second rule is to always unregister the callback. If an Activity registers a NetworkCallback in onStart() but does not unregister it in onStop(), the callback continues running after the Activity is destroyed. This causes memory leaks and potential NullPointerException when the callback tries to update the UI of a destroyed component. Use lifecycleScope or repeatOnLifecycle for automatic registration management. In Jetpack Compose, use DisposableEffect for callback registration and unregistration.

The third common mistake is checking only for network availability without considering its quality. A simple “is there internet” check is not sufficient for making decisions. The application should check NET_CAPABILITY_NOT_METERED for downloading large files, NET_CAPABILITY_NOT_ROAMING for background synchronization, and NET_CAPABILITY_VALIDATED to confirm internet access. Ignoring these flags leads to the application trying to download video while roaming or synchronizing data through a hotel’s captive portal.

The fourth rule is not to use ConnectivityManager to check the availability of a specific server. ConnectivityManager reports the network state on the device, but does not guarantee that the server is reachable. To check API availability, use an HTTP request with a short timeout or a Health Check. ConnectivityManager + HTTP ping is a reliable combination: first check for network availability, then perform a lightweight request to the server to confirm actual reachability.

Testing ConnectivityManager

For unit tests, use Robolectric with ShadowConnectivityManager, which allows emulating network states. For integration tests — Android Test Orchestrator with Airplane Mode toggling. In tests, verify scenarios: transitioning from online to offline, Wi-Fi appearing while mobile data is active, network loss during a request, captive portal, roaming. For mocking in unit tests, use a wrapper interface (e.g., NetworkMonitorInterface) that can be replaced with a mock object without platform dependencies.

Frequently Asked Questions

How do I check if the device is connected to the internet?

The modern way is to use registerDefaultNetworkCallback() with NET_CAPABILITY_INTERNET check in onCapabilitiesChanged(). For a one-time check: connectivityManager.getActiveNetwork()?.let { caps -> caps.hasCapability(NET_CAPABILITY_INTERNET) } ?: false. The deprecated getActiveNetworkInfo() method is not recommended from API 29+.

What permission is needed for ConnectivityManager?

To read network information, the android.permission.ACCESS_NETWORK_STATE permission is required. This is a normal permission — it is granted automatically when the application is installed and does not require a runtime request. For performing network operations (HTTP requests), the INTERNET permission is also required.

What is the difference between registerDefaultNetworkCallback and registerNetworkCallback?

registerDefaultNetworkCallback() monitors the default network — the one through which the application sends its main traffic. registerNetworkCallback(NetworkRequest) monitors networks matching a given filter (e.g., only Wi-Fi). The default callback is simpler and covers 90% of scenarios, while a custom request is for specific network type requirements.

How do I determine the network type: Wi-Fi or mobile data?

Use NetworkCapabilities: caps.hasTransport(NetworkCapabilities.TRANSPORT_WIFI) for Wi-Fi, hasTransport(TRANSPORT_CELLULAR) for mobile data. Do not use ConnectivityManager.getActiveNetworkInfo().getType() — this method is deprecated. NetworkCapabilities is available via connectivityManager.getNetworkCapabilities(network).

Why is getActiveNetworkInfo() deprecated?

getActiveNetworkInfo() is deprecated due to inaccuracy: it does not distinguish between networks with captive portals and full internet access, and does not provide bandwidth or roaming information. Starting with Android 10, this method may return null or incorrect data for multi-network connections. The replacement is getActiveNetwork() + NetworkCapabilities.

Summary

  • ConnectivityManager — an Android system service for monitoring network connectivity, accessible via getSystemService(CONNECTIVITY_SERVICE).
  • Modern API — registerDefaultNetworkCallback() + NetworkCapabilities, replacing the deprecated getActiveNetworkInfo() since API 29.
  • NetworkCapabilities — a class for checking network type (Wi-Fi, Cellular), metering, roaming, and internet connection validation.
  • NetworkCallback — a reactive monitoring mechanism with onAvailable, onLost, and onCapabilitiesChanged methods for tracking network changes.
  • NetworkRequest — a filter for subscribing to networks of a specific type, used with registerNetworkCallback() for precise control.
  • ACCESS_NETWORK_STATE permission — mandatory for working with ConnectivityManager, granted automatically upon application installation.
  • Best Practices — unregister callbacks in onStop(), check NET_CAPABILITY_NOT_METERED and NET_CAPABILITY_VALIDATED, do not rely solely on network presence without quality checking.

We will develop a mobile application turnkey

IT Sectr creates iOS and Android applications for startups and businesses since 2017. We will advise you and propose the best solution.

Discuss the project

Read also