Add IAX Ping for all servers for healthcheck

This commit is contained in:
Christopher Cookman 2026-06-24 04:39:17 -06:00
parent f850288796
commit 409a12ea89
3 changed files with 73 additions and 2 deletions

View file

@ -23,6 +23,7 @@ const crypto = require("crypto")
const dns = require("dns"); const dns = require("dns");
const app = express(); const app = express();
const port = process.env.SERVER_PORT || 3000; const port = process.env.SERVER_PORT || 3000;
const iaxping = require("iaxping");
const invalidBlocks = [ const invalidBlocks = [
// Emergency number prefixes (112, 911, 999, 110, 117, 119, 113, 191, 111) // Emergency number prefixes (112, 911, 999, 110, 117, 119, 113, 191, 111)
@ -1050,8 +1051,71 @@ app.get("/api/healthcheck", (req, res) => {
}); });
}); });
// Periodic healthcheck on routes (iax ping every server every 5 minutes)
let persistentHealthCheckData;
function healthCheck() {
return new Promise((resolve, reject) => {
let healthCheckData = {};
pool.getConnection().then(conn => {
conn.query('SELECT * FROM routes').then((rows) => {
let count = 0;
for (const row of rows) {
const host = row.server;
const port = row.port;
const block = row.block_start;
iaxping({ host, port }).then((pingResult) => {
// Good ping
healthCheckData[block] = { online: true, ping: pingResult.rttMs, timestamp: Date.now() };
}).catch((pingErr) => {
switch (pingErr.code) {
case "ERR_POKE_TIMEOUT":
healthCheckData[block] = { online: false, ping: null, timestamp: Date.now(), error: "Timeout" };
break;
case "ENOTFOUND":
healthCheckData[block] = { online: false, ping: null, timestamp: Date.now(), error: "Host not found (DNS)" };
break;
default:
healthCheckData[block] = { online: false, ping: null, timestamp: Date.now(), error: pingErr.message };
break;
}
}).finally(() => {
count++;
if (count === rows.length) {
conn.release();
persistentHealthCheckData = healthCheckData;
resolve(healthCheckData);
}
});
}
}).catch(err => {
console.error('Error getting routes for health check:', err);
conn.release();
reject(err);
});
}).catch(err => {
console.error('Error getting connection for health check:', err);
reject(err);
});
});
};
setInterval(healthCheck, 300000); // Run every 5 minutes
app.get("/api/servers", (req, res) => {
if (!persistentHealthCheckData) {
healthCheck().then((data) => {
res.json(data);
}).catch(err => {
console.error('Error running health check:', err);
res.status(500).json({ error: 'Internal server error' });
});
} else {
res.json(persistentHealthCheckData);
}
});
// logCall function (caller, callee) // logCall function (caller, callee)
const logCall = (caller, callee, srcIp="none_given", success, reason="none_given") => { const logCall = (caller, callee, srcIp = "none_given", success, reason = "none_given") => {
pool.getConnection().then(conn => { pool.getConnection().then(conn => {
conn.query('INSERT INTO callLogs (caller, callee, timestamp, srcIp, success, reason) VALUES (?, ?, ?, ?, ?, ?)', conn.query('INSERT INTO callLogs (caller, callee, timestamp, srcIp, success, reason) VALUES (?, ?, ?, ?, ?, ?)',
[caller, callee, Math.floor(Date.now()), srcIp, success, reason]).catch(err => { [caller, callee, Math.floor(Date.now()), srcIp, success, reason]).catch(err => {

6
package-lock.json generated
View file

@ -15,6 +15,7 @@
"escape-html": "^1.0.3", "escape-html": "^1.0.3",
"express": "^4.21.2", "express": "^4.21.2",
"express-session": "^1.18.1", "express-session": "^1.18.1",
"iaxping": "github:ChrisChrome/IAXPing.js",
"mariadb": "^3.4.0", "mariadb": "^3.4.0",
"session-file-store": "^1.5.0" "session-file-store": "^1.5.0"
} }
@ -868,6 +869,11 @@
"integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==", "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==",
"license": "MIT" "license": "MIT"
}, },
"node_modules/iaxping": {
"version": "1.0.0",
"resolved": "git+ssh://git@github.com/ChrisChrome/IAXPing.js.git#105e669e5916cecc30273c9e4aa1f7bc47440f52",
"license": "GPL-3.0-only"
},
"node_modules/iconv-lite": { "node_modules/iconv-lite": {
"version": "0.4.24", "version": "0.4.24",
"resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.24.tgz", "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.24.tgz",

View file

@ -16,6 +16,7 @@
"escape-html": "^1.0.3", "escape-html": "^1.0.3",
"express": "^4.21.2", "express": "^4.21.2",
"express-session": "^1.18.1", "express-session": "^1.18.1",
"iaxping": "github:ChrisChrome/IAXPing.js",
"mariadb": "^3.4.0", "mariadb": "^3.4.0",
"session-file-store": "^1.5.0" "session-file-store": "^1.5.0"
} }