android 网络连接 网络是否可用,Android 使用ping判断网络/WIFI连接是否可用

最近项目中有一个网络判断的需求,因为终端只能连接wifi,wifi即使连接上也可能会出现不能连接网络的问题,所以需要进行网络连接的判断。

ping的相关知识

使用ping检验网络是否可以连接

ping就是检测客户端是否可以上网。

那么我们就上代码

该段代码来自http://blankj.com

导入常用工具包compile 'com.blankj:utilcode:1.9.8'

这个里边有各种各样的常用的工具类,下边的代码是NetworkUtils的一个方法;

/**

* 判断网络是否可用

*

需添加权限 {@code }

*

需要异步ping,如果ping不通就说明网络不可用

*

* @param ip ip地址(自己服务器ip),如果为空,ip为阿里巴巴公共ip

* @return {@code true}: 可用
{@code false}: 不可用

*/

public static boolean isAvailableByPing(String ip) {

if (ip == null || ip.length() <= 0) {

ip = "223.5.5.5";// 阿里巴巴公共ip

}

ShellUtils.CommandResult result = ShellUtils.execCmd(String.format("ping -c 1 %s", ip), false);

boolean ret = result.result == 0;

if (result.errorMsg != null) {

Log.d("NetworkUtils", "isAvailableByPing() called" + result.errorMsg);

}

if (result.successMsg != null) {

Log.d("NetworkUtils", "isAvailableByPing() called" + result.successMsg);

}

return ret;

}

这段代码完全可以作为网络检测的使用,可是我在使用这段代码的时候偶尔会遇到anr的问题。出现anr就说明在主线程做了耗时操作,这是我没有将这段代码放到子线程造成的问题。其实ping也就相当于去请求网络,跟普通的接口请求差不多,当网络比较慢的时候就会消耗时间,放在主线程就会造成anr。

在修改bug的时候我对这段代码进行了一些修改:

* 判断网络是否可用

*

需添加权限 {@code }

*

需要异步ping,如果ping不通就说明网络不可用

*

* @param ip ip地址(自己服务器ip),如果为空,ip为阿里巴巴公共ip

* @return {@code true}: 可用
{@code false}: 不可用

*/

public static boolean isAvailableByPing(String ip) {

if (ip == null || ip.length() <= 0) {

ip = "223.5.5.5";// 阿里巴巴公共ip

}

Runtime runtime = Runtime.getRuntime();

Process ipProcess = null;

try {

//-c 后边跟随的是重复的次数,-w后边跟随的是超时的时间,单位是秒,不是毫秒,要不然也不会anr了

ipProcess = runtime.exec("ping -c 3 -w 3 "+ip);

int exitValue = ipProcess.waitFor();

Log.i("Avalible", "Process:" + exitValue);

return (exitValue == 0);

} catch (IOException | InterruptedException e) {

e.printStackTrace();

} finally {

//在结束的时候应该对资源进行回收

if (ipProcess != null) {

ipProcess.destroy();

}

runtime.gc();

}

return false;

}

只需要把这个方法引用到子线程中就行了,其实不引用也可以,因为在这里设定了超时时间为3秒。但是最好是放到子线程里边。

问题补充

上边的代码在Android 7.1.2中出现了问题,好好的WIFI连接上之后,ping不通,每次waitfor都返回1,返回一表示WiFi连接,但是没有网络。其实是有网络的,很奇怪。

解决方法:

这里我获取了ping时抓包的信息,判断是否丢包为100%。如果为100%,就说明网络有问题。不是100%说明网络连接没问题。

废话不多说,直接上代码!老铁双击666,,哈哈😄

public boolean isNetworkOnline() {

Runtime runtime = Runtime.getRuntime();

Process ipProcess = null;

try {

ipProcess = runtime.exec("ping -c 5 -w 4 223.5.5.5");

InputStream input = ipProcess.getInputStream();

BufferedReader in = new BufferedReader(new InputStreamReader(input));

StringBuffer stringBuffer = new StringBuffer();

String content = "";

while ((content = in.readLine()) != null) {

stringBuffer.append(content);

}

int exitValue = ipProcess.waitFor();

if (exitValue == 0) {

//WiFi连接,网络正常

return true;

} else {

if (stringBuffer.indexOf("100% packet loss") != -1) {

//网络丢包严重,判断为网络未连接

return false;

} else {

//网络未丢包,判断为网络连接

return true;

}

}

} catch (IOException | InterruptedException e) {

e.printStackTrace();

} finally {

if (ipProcess != null) {

ipProcess.destroy();

}

runtime.gc();

}

return false;

}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Android 应用中,可以通过 ConnectivityManager 类来获取当前网络连接的状态,进而判断当前连接网络是否可以上网。具体实现方法如下: ```java ConnectivityManager connectivityManager = (ConnectivityManager) getSystemService(Context.CONNECTIVITY_SERVICE); NetworkInfo networkInfo = connectivityManager.getActiveNetworkInfo(); if (networkInfo != null && networkInfo.isConnected()) { // 判断当前网络是否可以上网 if (networkInfo.getType() == ConnectivityManager.TYPE_WIFI) { // 当前连接的是 WiFi 网络 // 判断是否可以上网,可以使用 ping 命令测试网络连通性 // 可以使用 Runtime.getRuntime().exec() 方法执行 ping 命令 } else if (networkInfo.getType() == ConnectivityManager.TYPE_MOBILE) { // 当前连接的是移动网络(流量) // 判断是否可以上网,同样可以使用 ping 命令测试网络连通性 // 可以使用 Runtime.getRuntime().exec() 方法执行 ping 命令 } } else { // 当前未连接网络 } ``` 在上述代码中,先通过 ConnectivityManager 获取当前网络连接的状态,如果 networkInfo 不为 null 并且 isConnected() 方法返回 true,则说明当前连接网络,可以继续判断网络类型。对于 WiFi 和移动网络,可以使用 ping 命令测试网络连通性,从而判断当前连接网络是否可以上网。如果当前未连接网络,则无法判断当前连接网络是否可以上网。 需要注意的是,使用 ping 命令测试网络连通性可能会受到防火墙等因素的影响,因此测试结果并不一定准确。如果需要更加准确地判断当前连接网络是否可以上网,可以考虑通过访问特定的网址来测试网络连通性。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值