import ip from 'ipaddr.js'; import { networkInterfaces, platform, type } from 'os'; /** * Copy from https://github.com/sindresorhus/internal-ip, to fix silverwind/default-gateway 's bug * @returns */ function findIp(gateway: string): string | undefined { const gatewayIp = ip.parse(gateway); // Look for the matching interface in all local interfaces. for (const addresses of Object.values(networkInterfaces())) { if (addresses !== undefined) { for (const { cidr } of addresses) { if (cidr) { const net = ip.parseCIDR(cidr); if (net[0] && net[0].kind() === gatewayIp.kind() && gatewayIp.match(net)) { return net[0].toString(); } } } } } } export async function internalIpV4(): Promise { try { const defaultGatewayResult = await defaultGatewayV4(); if (defaultGatewayResult?.gateway) { return findIp(defaultGatewayResult.gateway); } } catch (_error) { // noop: best-effort to get default gateway, ignore errors void _error; } return 'localhost'; } const supportedPlatforms = new Set(['aix', 'android', 'darwin', 'freebsd', 'linux', 'openbsd', 'sunos', 'win32']); /** * Copy from https://github.com/silverwind/default-gateway 's index.js, to fix its weird behavior on windows. Its require statement will always require sunos * @returns */ async function defaultGatewayV4(): Promise { const plat = platform(); if (supportedPlatforms.has(plat)) { let gatewayQueryFileName: NodeJS.Platform | 'ibmi' = plat; if (plat === 'aix') { gatewayQueryFileName = type() === 'OS400' ? 'ibmi' : 'sunos'; // AIX `netstat` output is compatible with Solaris } switch (gatewayQueryFileName) { case 'ibmi': { const defaultGateway = await import('default-gateway/ibmi'); return await defaultGateway.v4(); } case 'android': { const defaultGateway = await import('default-gateway/android'); return await defaultGateway.v4(); } case 'darwin': { const defaultGateway = await import('default-gateway/darwin'); return await defaultGateway.v4(); } case 'freebsd': { const defaultGateway = await import('default-gateway/freebsd'); return await defaultGateway.v4(); } case 'linux': { const defaultGateway = await import('default-gateway/linux'); return await defaultGateway.v4(); } case 'openbsd': { const defaultGateway = await import('default-gateway/openbsd'); return await defaultGateway.v4(); } case 'sunos': { const defaultGateway = await import('default-gateway/sunos'); return await defaultGateway.v4(); } case 'win32': { const defaultGateway = await import('default-gateway/win32'); return await defaultGateway.v4(); } } } }