Lite IP tools
This lib is an alternative for the ip
package which resolves many upstream issues.
- Rewritten in TypeScript
- Provides both ESM and CJS entries
- Eliminates annoying vulnerability CVE-2024-29415
- Brings various fixes and improvements
npm i @webpod/ip
- const ip = require('ip')
+ const ip = require('@webpod/ip')
Temporary workaround to avoid refactoring is using overrides
/ resolutions
in your package.json
:
{
"overrides": {
"ip": "@webpod/ip"
}
}
Browser-compatible core build is available as @webpod/ip/core
: it omits node:os
dependency and polyfills the Buffer
API.
The API is fully compatible with the latest [email protected]
import ip from '@webpod/ip'
// -------------------------------------------------------
// Addresses & formats
// -------------------------------------------------------
ip.address() // '192.168.1.50' (example local address)
ip.isPrivate('127.0.0.1') // true
ip.isV4Format('127.0.0.1') // true
ip.isV6Format('::ffff:127.0.0.1') // true
ip.isEqual('::1', '::0:1') // true
// -------------------------------------------------------
// Conversions
// -------------------------------------------------------
ip.toBuffer('127.0.0.1') // <Buffer 7f 00 00 01>
ip.toString(Buffer.from([127, 0, 0, 1])) // '127.0.0.1'
ip.toLong('127.0.0.1') // 2130706433
ip.fromLong(2130706433) // '127.0.0.1'
ip.fromPrefixLen(24) // '255.255.255.0'
// in-place buffer usage
const buf = Buffer.alloc(128)
const offset = 64
ip.toBuffer('127.0.0.1', buf, offset) // writes [127, 0, 0, 1] at offset 64
ip.toString(buf, offset, 4) // '127.0.0.1'
// -------------------------------------------------------
// Masking, bitwise, and ranges
// -------------------------------------------------------
ip.mask('192.168.1.134', '255.255.255.0') // '192.168.1.0'
ip.cidr('192.168.1.134/26') // '192.168.1.128'
ip.not('255.255.255.0') // '0.0.0.255'
ip.or('192.168.1.134', '0.0.0.255') // '192.168.1.255'
// -------------------------------------------------------
// Subnets
// -------------------------------------------------------
ip.subnet('192.168.1.134', '255.255.255.192')
/*
{
networkAddress: '192.168.1.128',
firstAddress: '192.168.1.129',
lastAddress: '192.168.1.190',
broadcastAddress: '192.168.1.191',
subnetMask: '255.255.255.192',
subnetMaskLength: 26,
numHosts: 62,
length: 64,
contains: [Function: contains]
}
*/
ip.cidrSubnet('192.168.1.134/26').contains('192.168.1.190') // true
import { Address } from '@webpod/ip'
// -------------------------------------------------------
// Prototype methods
// -------------------------------------------------------
const addr4 = Address.from('192.168.1.134')
addr4.family // 4
addr4.big // 323223590n
addr4.toString() // '192.168.1.134'
addr4.toLong() // 323223590
addr4.toBuffer() // <Buffer c0 a8 01 86>
addr4.toArray() // [192, 168, 1, 134]
const addr6 = Address.from('::1')
addr6.family // 6
addr6.big // 1n
addr6.toString() // '::1'
addr6.toString(4) // '0.0.0.1'
// -------------------------------------------------------
// Specific ranges check
// -------------------------------------------------------
Address.isSpecial('127.0.0.1') // true
Address.isSpecial('127.0.0.1', 'loopback') // true
Address.isSpecial('127.0.0.1', 'documentation') // false
Address.isSpecial('1.2.3.4') // false
MIT