在我的代码中,我需要跟踪internet连接并进行适当的更改.首先,我创建一个网络请求,然后使用ConnectivityManager注册一个网络回调.

    val networkCallback = createNetworkCallback()
    val networkRequest = NetworkRequest.Builder()
        .addCapability(NET_CAPABILITY_INTERNET)
        .addTransportType(TRANSPORT_CELLULAR)
        .addTransportType(TRANSPORT_WIFI)
        .addTransportType(TRANSPORT_ETHERNET)
        .build()
    connectivityManager.registerNetworkCallback(networkRequest, networkCallback)

让我们看看networkRequest.我请求的网络需要NET_CAPABILITY_INTERNET和一些我在代码中指定的传输类型.

表示,例如,我将打开/关闭WI-FI,仅当我在网络请求中指定了传输类型或相应功能时,才会触发网络回调.现在的问题是,当networkCallback触发时,我是否需要再次判断功能和传输类型?

override fun onAvailable(network: Network) {
        val networkCapabilities = cm.getNetworkCapabilities(network)
        val hasInternetCapabilities = networkCapabilities?.let {
            return@let it.hasCapability(NET_CAPABILITY_INTERNET) or
                it.hasTransport(TRANSPORT_WIFI) or
                it.hasTransport(TRANSPORT_CELLULAR) or
                it.hasTransport(TRANSPORT_ETHERNET)
        } ?: false
    }
}

据我所知,如果网络不能满足我的networkRequestonAvailable()内的判断就无关紧要了,因为它不会执行.非常感谢.

推荐答案

你说得对,onAvailable元的额外支票是不必要的.对于satisfy传入NetworkRequest的网络,平台只会发送onAvailable(否则,API将毫无意义).

以下是一些关于该主题的官方文件(link):

该应用程序构建一个NetworkRequest,通知ConnectionManager

NetworkRequest request = new NetworkRequest.Builder()
  .addCapability(NetworkCapabilities.NET_CAPABILITY_NOT_METERED)
  .addCapability(NET_CAPABILITY_INTERNET)
  .build();
connectivityManager.registerNetworkCallback(request, myNetworkCallback);

这将确保你的应用程序能够听到所有

Note the below is accurate at the time of writing this answer.

对于回调,在Android的连接堆栈中,它们被称为listen个请求,因此,如果您想了解它们与发送onAvailable的相互作用,那么processNewlySatisfiedListenRequests中应该是here个:

private void processNewlySatisfiedListenRequests(@NonNull final NetworkAgentInfo nai) {
        for (final NetworkRequestInfo nri : mNetworkRequests.values()) {
            if (nri.isMultilayerRequest()) {
                continue;
            }
            final NetworkRequest nr = nri.mRequests.get(0);
            if (!nr.isListen()) continue;
            if (nai.satisfies(nr) && !nai.isSatisfyingRequest(nr.requestId)) {
                nai.addRequest(nr);
                notifyNetworkAvailable(nai, nri);
            }
        }
    }

ConnectivityService控制了所有这些,这很难理解,但如果您遵循此处的代码路径,您将看到它来自方法computeNetworkReassignment here.

上面的重要代码行是:

bestNetwork = mNetworkRanker.getBestNetwork(req, nais, nri.getSatisfier());

深入到该方法中,您将看到它调用NetworkRankerNetworkRanker针对最初传入的NetworkRequest运行satisfies:

final ArrayList<NetworkAgentInfo> candidates = filter(nais, nai -> nai.satisfies(request));

综上所述,您可以看到,如果您收到NetworkRequestonAvailable分,那么它将满足最初传入的NetworkCapabilities分,因此无需再次判断以确认.

Android相关问答推荐

在Android中点击滑动时触发的手势

如何允许我的应用程序在Android 10上运行,同时目标是API 33

修改参数应该应用于哪些子元素?

Android Jetpack Compose Material3主题配色方案

原因平滑滚动的滞后懒惰列在android jetpack compose

译码BLE血糖仪特征值

对支持哪些数据存储区方法感到困惑

Android:微调:在代码中设置ArrayAdapter不希望调用On ItemSelected,仅当用户单击微调时调用

LocalContext.current的问题(@Composable调用只能从@Composable函数的上下文发生)

如何在Android Studio的LinearLayout中禁用阴影

Jetpack Compose:根据盒子中的最大视图固定宽度和高度

只能从同一个库组内调用成功(引用groupId=androidx.work from groupId=My Composable)

Compose 状态不是 recomposing

如何让这个三角形指示器在 android jetpack compose 中旋转和移动?

Jetpack 组合千位分隔符视觉转换,也适用于小数

compose 更改列表元素但lazyColumn不更改

协程是否在 if 条件下保持秩序?

在jetpack compose中看不到圆角

Xamarin 获取动态 ListView DataTemplate 中的按钮单击事件数据

dagger2 抛出错误:如果没有 @Provides-annotated 方法就无法提供.在我的 android 项目的构建中