UNPKG

@ssb-graphql/stats

Version:

Statistics GraphQL types and resolvers for the machine

131 lines (125 loc) 3.5 kB
const si = require('systeminformation') const publicIp = require('public-ip') const stoppable = require('stoppable') const net = require('net') const PORT_FORWARDING_TEST_PORT = 3063 // PROBLEM this can be called multiple times so you sometimes get collisions on port 3063. // // TODO - change so that it doesn't start multiple at once // track state something like: // let checkingPortForwarding = false // let portForwardingState = null function portOpen (externalHost, externalPort) { return new Promise(resolve => { const server = stoppable( net.createServer(socket => { socket.end() }) ) // var server = net.createServer() server.on('error', e => { console.log('error', e) resolve(false) server.stop() }) server.on('listening', () => { const socket = net.connect(externalPort, externalHost, () => { // console.log('connected') resolve(true) socket.destroy() server.stop() }) socket.setTimeout(3000) socket.on('timeout', () => { resolve(false) socket.destroy() server.stop() }) socket.on('error', e => { console.log('connect error', e) resolve(false) socket.destroy() server.stop() }) }) server.listen(PORT_FORWARDING_TEST_PORT) }) } module.exports = function stats (ssb) { return { Query: { cpuLoad: async () => { const load = await si.currentLoad() return load.currentLoad.toFixed(2) }, memoryLoad: async () => { const mem = await si.mem() const memLoad = (mem.used * 100) / mem.total return memLoad.toFixed(2) }, diskUsage: async () => { const disk = await si.fsSize() disk.forEach(diskVal => Object.keys(diskVal).forEach(i => { if (isNaN(disk[i])) { disk[i] = 0 } }) ) return disk }, network: async () => { const defaultInterface = await si.networkInterfaceDefault() const interfaces = await si.networkInterfaces() const interfaceInUse = interfaces.filter( i => i.iface === defaultInterface )[0] const ipv4 = interfaceInUse.ip4 const ip4subnet = interfaceInUse.ip4subnet const ipv6 = interfaceInUse.ip6 const ip6subnet = interfaceInUse.ip6subnet const type = interfaceInUse.type const macAddress = interfaceInUse.mac return { ipv4, ip4subnet, ipv6, ip6subnet, type, macAddress } } }, NetworkInfo: { defaultGateway: async () => await si.networkGatewayDefault(), internetLatency: async () => si.inetLatency(), publicIpv4: async () => { try { return await publicIp.v4({ timeout: 3000, fallbackUrls: ['https://ifconfig.co/ip'] }) } catch (err) { return null } }, publicIpv6: async () => { try { return await publicIp.v6({ timeout: 3000, fallbackUrls: ['https://ifconfig.co/ip'] }) } catch (err) { return null } }, portForwarding: async () => { const ip = await publicIp.v4({ timeout: 3000, fallbackUrls: ['https://ifconfig.co/ip'] }) return portOpen(ip, ssb.config.port) } } } }