NodeJS/Web网络检测

navigator.onLine

注意

这种方式只支持Web环境

NetWork API:http://wicg.github.io/netinfo/

navigator.onLine只会在机器未连接到局域网或路由器时返回false,其他情况下均返回true。

也就是说,机器连接上路由器后,即使这个路由器没联通网络,navigator.onLine仍然返回true。

判断网络连接的网络状态

1
2
3
4
5
if (navigator.onLine) {
alert('online')
} else {
alert('offline');
}

想要监听浏览器的联网状态, 使用window.onOnlinewindow.onOffline事件:

1
2
window.addEventListener("offline", function(e) {alert("offline");})
window.addEventListener("online", function(e) {alert("online");})

更为安全的做法:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
var el = document.body;  
if (el.addEventListener) {
window.addEventListener("online", function () {
alert("online");}, true);
window.addEventListener("offline", function () {
alert("offline");}, true);
}
else if (el.attachEvent) {
window.attachEvent("ononline", function () {
alert("online");});
window.attachEvent("onoffline", function () {
alert("offline");});
}
else {
window.ononline = function () {
alert("online");};
window.onoffline = function () {
alert("offline");};
}

注意,检测ononline事件,要绑定在window对象上

attachEvent——兼容:IE7、IE8;不兼容firefox、chrome、IE9、IE10、IE11、safari、opera

addEventListener——兼容:firefox、chrome、IE、safari、opera;不兼容IE7、IE8

is-online(Web推荐)

注意

这种方式同时支持NodeJS和Web环境

安装依赖

1
npm install is-online --save

工具类

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
const isOnline = require('is-online');
let network_good = true;

function network_check_timer_fun() {
console.info("network check start")
setInterval(() => {
network_check();
}, 6000)
}

function network_check() {
isOnline({
timeout: 6000,
version: "v4" // v4 or v6
}).then(online => {
if (online) {
if (!network_good) {
network_good = true;
console.info("network good");
if (homeWin && !homeWin.isDestroyed()) {
homeWin.webContents.send('network_check', network_good);
}
}
} else {
console.info("network bad")
network_good = false;
if (homeWin && !homeWin.isDestroyed()) {
homeWin.webContents.send('network_check', network_good);
}
}
});
}

network_check_timer_fun();

internet-available(NodeJS推荐)

注意

这种方式只支持NodeJS环境

相比于is-online,这个可以自定义DNS服务器的地址,这样不会因为使用国外的地址而导致网络状态判断不正确。

这个库检测因特网连接状态原理,是检测dns连接状态。

这里大家肯定有个疑问,使用nodejs原生模块dns不是更简洁吗?

你说的没错,nodejs确实提供这样的方法,但是dns原生模块并没有提供超时检测。internet-available可以设置超时参数,默认是5000ms

安装依赖

1
npm install internet-available --save

示例代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
const internetAvailable = require("internet-available");
let network_good = true;

function network_check() {
internetAvailable({
domainName: "www.baidu.com",
port: 53,
host: '223.5.5.5',
retries: 10,
timeout: 8000,
}).then(() => {
if (!network_good) {
network_good = true;
console.info("network good");
if (homeWin && !homeWin.isDestroyed()) {
homeWin.webContents.send('network_check', network_good);
}
}
}).catch(() => {
console.info("network bad")
network_good = false;
if (homeWin && !homeWin.isDestroyed()) {
homeWin.webContents.send('network_check', network_good);
}
});
}

function network_check_timer_fun() {
console.info("network check start")
setInterval(() => {
network_check();
}, 10000)
}

network_check_timer_fun();

注意

端口53不是网址的端口是DNS服务的端口,DNS 协议运行在 UDP 协议之上,使用 端口号53 。

超时时间和重试次数

1
2
3
4
5
6
7
8
9
10
11
12
13
var internetAvailable = require("internet-available");

// Most easy way
internetAvailable({
// Provide maximum execution time for the verification
timeout: 5000,
// If it tries 5 times and it fails, then it will throw no internet
retries: 5
}).then(() => {
console.log("Internet available");
}).catch(() => {
console.log("No internet");
});

默认值在源码中可以看到

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
var socket = dns({
timeout: (settings.timeout || 5000),
retries: (settings.retries || 5)
});
// Run the dns lowlevel lookup
socket.query(
{
questions: [{
type: 'A',
name: (settings.domainName || "google.com")
}]
},
(settings.port || 53),
(settings.host || '8.8.8.8')
);

默认

  • 超时时间:5秒
  • 重试次数:5
  • 域名:google.com
  • 端口:53
  • DNS:8.8.8.8