From 704ffd3f4b2da668157dc8053df65068ea5010c4 Mon Sep 17 00:00:00 2001 From: Matt Visnovsky Date: Tue, 30 Apr 2024 15:18:25 -0600 Subject: [PATCH] Finalized SNMP monitor --- server/monitor-types/snmp.js | 69 +++++++++++++++++++++--------------- 1 file changed, 41 insertions(+), 28 deletions(-) diff --git a/server/monitor-types/snmp.js b/server/monitor-types/snmp.js index 1752ab717..2fa397161 100644 --- a/server/monitor-types/snmp.js +++ b/server/monitor-types/snmp.js @@ -1,5 +1,5 @@ const { MonitorType } = require("./monitor-type"); -const { UP, DOWN } = require("../../src/util"); +const { UP, DOWN, log } = require("../../src/util"); const snmp = require("net-snmp"); class SNMPMonitorType extends MonitorType { @@ -13,18 +13,17 @@ class SNMPMonitorType extends MonitorType { */ async check(monitor, heartbeat, _server) { - console.log("IP Address:", monitor._hostname); - console.log("SNMP Community String:", monitor._snmpCommunityString); - console.log("SNMP OID:", monitor._snmpOid); - console.log("SNMP Version:", monitor._snmpVersion); - console.log("SNMP Condition:", monitor._snmpCondition); - console.log("SNMP Control Value:", monitor._snmpControlValue); + log.debug("monitor", `SNMP: Community String: ${monitor.snmpCommunityString}`); + log.debug("monitor", `SNMP: OID: ${monitor.snmpOid}`); + log.debug("monitor", `SNMP: Version: ${monitor.snmpVersion}`); + log.debug("monitor", `SNMP: Condition: ${monitor.snmpCondition}`); + log.debug("monitor", `SNMP: Control Value: ${monitor.snmpControlValue}`); const options = { - port: monitor._port || 161, - retries: 1, + port: monitor.port || '161', + retries: monitor.maxretries, timeout: 1000, - version: getKey(snmp.Version, monitor._snmpVersion) || snmp.Version2c, + version: getKey(snmp.Version, monitor.snmpVersion) || snmp.Version2c, }; function getKey(obj, value) { @@ -34,56 +33,70 @@ class SNMPMonitorType extends MonitorType { try { const session = snmp.createSession(monitor.hostname, monitor.snmpCommunityString, options); + // Handle errors during session creation + session.on('error', (error) => { + heartbeat.status = DOWN; + heartbeat.msg = `SNMP: Error creating SNMP session: ${error.message}`; + log.debug("monitor", `SNMP: ${heartbeat.msg}`); + }); + const varbinds = await new Promise((resolve, reject) => { - session.get([monitor._snmpOid], (error, varbinds) => { + session.get([monitor.snmpOid], (error, varbinds) => { if (error) { reject(error); } else { + log.debug("monitor", `SNMP: Received varbinds: Type: ${getKey(snmp.ObjectType, varbinds[0].type)}, Value: ${varbinds[0].value}`); // Log the received varbinds for debugging resolve(varbinds); } }); }); - console.log("Received varbinds:", varbinds); // Log the received varbinds for debugging - - if (varbinds && varbinds.length > 0) { + if (varbinds.length === 0 || getKey(snmp.ObjectType, varbinds[0].type) === 'NoSuchInstance') { + throw new Error(`No varbinds returned from SNMP session (OID: ${monitor.snmpOid})`); + } else { const value = varbinds[0].value; const numericValue = parseInt(value); - const stringValue = value.toString(); + const stringValue = value.toString('ascii'); switch (monitor.snmpCondition) { case '>': - heartbeat.status = numericValue > monitor._snmpControlValue ? UP : DOWN; + heartbeat.status = numericValue > monitor.snmpControlValue ? UP : DOWN; break; case '>=': - heartbeat.status = numericValue >= monitor._snmpControlValue ? UP : DOWN; + heartbeat.status = numericValue >= monitor.snmpControlValue ? UP : DOWN; break; case '<': - heartbeat.status = numericValue < monitor._snmpControlValue ? UP : DOWN; + heartbeat.status = numericValue < monitor.snmpControlValue ? UP : DOWN; break; case '<=': - heartbeat.status = numericValue <= monitor._snmpControlValue ? UP : DOWN; + heartbeat.status = numericValue <= monitor.snmpControlValue ? UP : DOWN; break; case '==': - heartbeat.status = value === monitor._snmpControlValue ? UP : DOWN; + if (!isNaN(value) && !isNaN(monitor.snmpControlValue)) { + // Both values are numeric, parse them as numbers + heartbeat.status = parseFloat(value) === parseFloat(monitor.snmpControlValue) ? UP : DOWN; + } else { + // At least one of the values is not numeric, compare them as strings + heartbeat.status = value.toString() === monitor.snmpControlValue.toString() ? UP : DOWN; + } break; case 'contains': - heartbeat.status = stringValue.includes(monitor._snmpControlValue) ? UP : DOWN; + heartbeat.status = stringValue.includes(monitor.snmpControlValue) ? UP : DOWN; break; default: heartbeat.status = DOWN; - heartbeat.msg = `Invalid condition: ${monitor._snmpCondition}`; + heartbeat.msg = `Invalid condition: ${monitor.snmpCondition}`; + break; } - } else { - heartbeat.status = DOWN; - heartbeat.msg = 'No varbinds returned from SNMP session'; - } + heartbeat.msg = `SNMP value ` + (heartbeat.status ? `passes` : `does not pass`) + ` comparison: ${value.toString('ascii')} ${monitor.snmpCondition} ${monitor.snmpControlValue}`; + } session.close(); // Close the session after use + } catch (err) { - console.error("Error in SNMP check:", err); // Log any errors heartbeat.status = DOWN; - heartbeat.msg = `Error: ${err.message}`; + heartbeat.msg = `SNMP Error: ${err.message}`; + log.debug("monitor", `SNMP: ${heartbeat.msg}`); } }