Skip to content

Commit

Permalink
Require Node.js 14 and move to ESM
Browse files Browse the repository at this point in the history
  • Loading branch information
sindresorhus committed Jun 6, 2022
1 parent b9b5710 commit b0e3bd2
Show file tree
Hide file tree
Showing 10 changed files with 90 additions and 88 deletions.
1 change: 0 additions & 1 deletion .github/funding.yml

This file was deleted.

9 changes: 4 additions & 5 deletions .github/workflows/main.yml
Original file line number Diff line number Diff line change
Expand Up @@ -10,13 +10,12 @@ jobs:
fail-fast: false
matrix:
node-version:
- 18
- 16
- 14
- 12
- 10
- 8
steps:
- uses: actions/checkout@v2
- uses: actions/setup-node@v1
- uses: actions/checkout@v3
- uses: actions/setup-node@v3
with:
node-version: ${{ matrix.node-version }}
- run: npm install
Expand Down
15 changes: 6 additions & 9 deletions browser.js
Original file line number Diff line number Diff line change
@@ -1,15 +1,14 @@
/* eslint-env browser */
'use strict';
const publicIp = require('public-ip');
import publicIp from 'public-ip';

const isOnline = async options => {
export default async function isOnline(options) {
options = {
timeout: 5000,
ipVersion: 4,
...options
...options,
};

if (navigator && !navigator.onLine) {
if (!navigator?.onLine) {
return false;
}

Expand All @@ -18,9 +17,7 @@ const isOnline = async options => {
try {
await publicIp[publicIpFunctionName](options);
return true;
} catch (_) {
} catch {
return false;
}
};

module.exports = isOnline;
}
40 changes: 18 additions & 22 deletions index.d.ts
Original file line number Diff line number Diff line change
@@ -1,20 +1,20 @@
declare namespace isOnline {
interface Options {
/**
Milliseconds to wait for a server to respond.
export type Options = {
/**
Milliseconds to wait for a server to respond.
@default 5000
*/
readonly timeout?: number;
@default 5000
*/
readonly timeout?: number;

/**
Internet Protocol version to use. This is an advanced option that is usually not necessary to be set, but it can prove useful to specifically assert IPv6 connectivity.
/**
[Internet Protocol version](https://en.wikipedia.org/wiki/Internet_Protocol#Version_history) to use.
@default 4
*/
readonly ipVersion?: 4 | 6;
}
}
This is an advanced option that is usually not necessary to be set, but it can prove useful to specifically assert IPv6 connectivity.
@default 4
*/
readonly ipVersion?: 4 | 6;
};

/**
Check if the internet connection is up.
Expand All @@ -28,14 +28,10 @@ When any check succeeds, the returned Promise is resolved to `true`.
@example
```
import isOnline = require('is-online');
import isOnline from 'is-online';
(async () => {
console.log(await isOnline());
//=> true
})();
console.log(await isOnline());
//=> true
```
*/
declare function isOnline(options?: isOnline.Options): Promise<boolean>;

export = isOnline;
export default function isOnline(options?: Options): Promise<boolean>;
50 changes: 29 additions & 21 deletions index.js
Original file line number Diff line number Diff line change
@@ -1,20 +1,18 @@
'use strict';
const os = require('os');
const got = require('got');
const publicIp = require('public-ip');
const pAny = require('p-any');
const pTimeout = require('p-timeout');

// Use Array#flat when targeting Node.js 12
const flat = array => [].concat(...array);
import os from 'node:os';
import got, {CancelError} from 'got';
import publicIp from 'public-ip';
import pAny from 'p-any';
import pTimeout from 'p-timeout';

const appleCheck = options => {
const gotPromise = got('https://captive.apple.com/hotspot-detect.html', {
timeout: options.timeout,
dnsLookupIpVersion: options.ipVersion === 6 ? 'ipv6' : 'ipv4',
timeout: {
request: options.timeout,
},
dnsLookupIpVersion: options.ipVersion,
headers: {
'user-agent': 'CaptiveNetworkSupport/1.0 wispr'
}
'user-agent': 'CaptiveNetworkSupport/1.0 wispr',
},
});

const promise = (async () => {
Expand All @@ -24,7 +22,7 @@ const appleCheck = options => {
throw new Error('Apple check failed');
}
} catch (error) {
if (!(error instanceof got.CancelError)) {
if (!(error instanceof CancelError)) {
throw error;
}
}
Expand All @@ -35,15 +33,16 @@ const appleCheck = options => {
return promise;
};

const isOnline = options => {
// Note: It cannot be `async`` as then it looses the `.cancel()` method.
export default function isOnline(options) {
options = {
timeout: 5000,
ipVersion: 4,
...options
...options,
};

if (flat(Object.values(os.networkInterfaces())).every(({internal}) => internal)) {
return Promise.resolve(false);
if (Object.values(os.networkInterfaces()).flat().every(({internal}) => internal)) {
return false;
}

if (![4, 6].includes(options.ipVersion)) {
Expand Down Expand Up @@ -72,7 +71,7 @@ const isOnline = options => {
queries.push(query);
await query;
return true;
})()
})(),
]);

return pTimeout(promise, options.timeout).catch(() => {
Expand All @@ -82,6 +81,15 @@ const isOnline = options => {

return false;
});
};

module.exports = isOnline;
// TODO: Use this instead when supporting AbortController.
// try {
// return await pTimeout(promise, options.timeout);
// } catch {
// for (const query of queries) {
// query.cancel();
// }

// return false;
// }
}
2 changes: 1 addition & 1 deletion index.test-d.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import {expectType} from 'tsd';
import isOnline = require('.');
import isOnline from './index.js';

expectType<Promise<boolean>>(isOnline());
expectType<Promise<boolean>>(isOnline({timeout: 10}));
Expand Down
33 changes: 19 additions & 14 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -13,11 +13,17 @@
"contributors": [
"silverwind <me@silverwind.io> (github.com/silverwind)"
],
"type": "module",
"exports": {
"types": "./index.d.ts",
"node": "./index.js",
"default": "./browser.js"
},
"engines": {
"node": ">=10"
"node": ">=14.16"
},
"scripts": {
"test": "xo && ava test.js && tsd"
"test": "xo && ava && tsd"
},
"files": [
"index.js",
Expand Down Expand Up @@ -47,20 +53,19 @@
"disconnected"
],
"dependencies": {
"got": "^11.8.0",
"p-any": "^3.0.0",
"p-timeout": "^3.2.0",
"public-ip": "^4.0.4"
"got": "^12.1.0",
"p-any": "^4.0.0",
"p-timeout": "^5.1.0",
"public-ip": "^5.0.0"
},
"devDependencies": {
"ava": "^2.4.0",
"tsd": "^0.13.1",
"xo": "^0.34.1"
"ava": "^4.3.0",
"tsd": "^0.20.0",
"xo": "^0.49.0"
},
"browser": "browser.js",
"xo": {
"rules": {
"unicorn/prefer-optional-catch-binding": "off"
}
"ava": {
"files": [
"test.js"
]
}
}
18 changes: 9 additions & 9 deletions readme.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,23 +4,21 @@
Works in Node.js and the browser *(with a bundler)*.

In the browser you have [`navigator.onLine`](https://developer.mozilla.org/en-US/docs/Web/API/NavigatorOnLine.onLine), but it's useless as it only tells you if there's a local connection, and not whether the internet is accessible.
In the browser, there is already [`navigator.onLine`](https://developer.mozilla.org/en-US/docs/Web/API/NavigatorOnLine.onLine), but it's useless as it only tells you if there's a local connection, and not whether the internet is accessible.

## Install

```
$ npm install is-online
```sh
npm install is-online
```

## Usage

```js
const isOnline = require('is-online');
import isOnline from 'is-online';

(async () => {
console.log(await isOnline());
//=> true
})();
console.log(await isOnline());
//=> true
```

## API
Expand All @@ -44,7 +42,9 @@ Type: `number`\
Values: `4 | 6`\
Default: `4`

Internet Protocol version to use. This is an advanced option that is usually not necessary to be set, but it can prove useful to specifically assert IPv6 connectivity.
The [Internet Protocol version](https://en.wikipedia.org/wiki/Internet_Protocol#Version_history) to use.

This is an advanced option that is usually not necessary to be set, but it can prove useful to specifically assert IPv6 connectivity.

## How it works

Expand Down
7 changes: 2 additions & 5 deletions test-browser.js
Original file line number Diff line number Diff line change
@@ -1,8 +1,5 @@
// Need to test manually in DevTools
// $ browserify test-browser.js | pbcopy
'use strict';
const isOnline = require('./browser');
import isOnline from './browser.js';

(async () => {
console.log('is online:', await isOnline());
})();
console.log('is online:', await isOnline());
3 changes: 2 additions & 1 deletion test.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import process from 'node:process';
import test from 'ava';
import isOnline from '.';
import isOnline from './index.js';

test('v4', async t => {
t.true(await isOnline());
Expand Down

0 comments on commit b0e3bd2

Please sign in to comment.