【问题标题】:ConnectivityManager Networkcallback doesn't catch connection to wifi network with no internet connectionConnectivityManager Networkcallback 在没有互联网连接的情况下无法捕获到 wifi 网络的连接
【发布时间】:2019-01-07 22:06:26
【问题描述】:

我有一个设备,我的应用可以通过 WIFI 连接到该设备,但是该设备没有互联网。我实现了一个 NetworkCallback 来捕捉连接的变化:

public class ConnectivityNetworkCallback extends ConnectivityManager.NetworkCallback{

        @Override
        public void onAvailable(android.net.Network network) {
            super.onAvailable(network);

            if(Build.VERSION.SDK_INT >= Build.VERSION_CODES.M)
                mConnectivityManager.bindProcessToNetwork(network);
            else
                ConnectivityManager.setProcessDefaultNetwork(network);

            NetworkInfo networkInfo = mConnectivityManager.getActiveNetworkInfo();
            int connectionType = networkInfo.getType();
            Log.e("networkCallback", "connectionType: " + networkInfo.getTypeName());
            switch(connectionType){

                case ConnectivityManager.TYPE_WIFI:
                    String networkName = networkInfo.getExtraInfo().substring(1,networkInfo.getExtraInfo().length()-1);

                    Log.e("networkCallback","network type wifi, extra: " + networkName);

                    break;
                case ConnectivityManager.TYPE_MOBILE:
                    Log.e("networkCallback","network type mobile, extra:  " + networkInfo.getExtraInfo());
                    break;
            }
        }

        @Override
        public void onLost(android.net.Network network) {
            super.onLost(network);

            Log.e("networkCallback", "losing active connection");
        }
}

当我的 Wifi 和移动数据都打开并且我在具有 Internet 访问权限的不同 wifi 网络之间切换时,"onAvailable()" 会触发并打印以记录我已通过 wifi 连接。 一旦我尝试连接到没有互联网的 wifi 网络 "onAvailable()" 方法就会触发并打印我已通过移动设备连接,并且设备会在 wifi 图标旁边显示一个感叹号.

有没有办法让我仍然可以捕捉到我连接到没有互联网的 wifi 网络的情况?

【问题讨论】:

    标签: android android-connectivitymanager


    【解决方案1】:

    我一直在努力解决同样的问题。现在似乎对我有用的是首先获得网络功能:

    connectivityManager.getNetworkCapabilities(network)
    

    然后检查连接是否有互联网并已验证:

    private val NetworkCapabilities.hasInternet
        get() = hasCapability(NetworkCapabilities.NET_CAPABILITY_INTERNET) && when {
            Build.VERSION.SDK_INT >= Build.VERSION_CODES.M -> hasCapability(NetworkCapabilities.NET_CAPABILITY_VALIDATED)
            else -> true
        }
    

    不幸的是,NetworkCapabilities.NET_CAPABILITY_VALIDATED 标志仅在 API 23 中引入,这就是我在这种情况下忽略该标志的原因。

    【讨论】:

      【解决方案2】:

      创建实用程序

      public class CheckInternet extends AsyncTask<Void,Void,Boolean> {
      
      private Consumer mConsumer;
      public  interface Consumer { void accept(Boolean internet); }
      
      public  CheckInternet(Consumer consumer) { mConsumer = consumer; execute(); }
      
      @Override protected Boolean doInBackground(Void... voids) { try {
          Socket sock = new Socket();
          sock.connect(new InetSocketAddress("8.8.8.8", 53), 1500);
          sock.close();
          return true;
      } catch (IOException e) { return false; } }
      
      @Override protected void onPostExecute(Boolean internet) { mConsumer.accept(internet); }
      

      }

      使用此方法检查互联网连接

       new InternetCheck(internet -> {
          if (internet){
              check your condition
          }else {
              //error message
          }
      

      【讨论】:

        【解决方案3】:

        您必须使用 Connectivity Manager 注册网络回调。

        ConnectivityManager connMgr = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE);
        
        NetworkRequestBuilder.Builder builder = new NetworkRequest.Builder()
        //Use builder to set custom network parameter
        connMgr.requestNetwork(builder.build(),new ConnectivityNetworkCallback())
        

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 2016-12-30
          • 2015-05-24
          • 1970-01-01
          • 1970-01-01
          • 2015-10-24
          • 2015-12-14
          • 2011-10-27
          • 1970-01-01
          相关资源
          最近更新 更多