diff --git a/center.js b/center.js index 3e14e02..9fee37f 100644 --- a/center.js +++ b/center.js @@ -6,6 +6,7 @@ const { createBaseLogger, createSessionLogger } = require("./logger"); const { verifyDefaults, verifyExists } = require("./utils"); const { centerOptions } = require("./cliOptions"); const crypto = require("crypto"); +const { MetricManager } = require("./metrics/metricManager"); const logger = createBaseLogger(); const options = commandLineArgs(centerOptions); @@ -27,6 +28,8 @@ if (options.help) { process.exit(0); } +const metricManager = new MetricManager(); + verifyDefaults(options, centerOptions); verifyExists(options.port, "Port can not be undefined or empty! (--port)", logger); verifyExists(options.systemid, "SystemID can not be undefined or empty! (--systemid)", logger); @@ -41,7 +44,7 @@ const sendTimer = new NanoTimer(); // TODO: Fix issue where a client disconnecting does not stop this timer // TODO: Fix issue where only one session is being utilized because they all share the same timer // Instead just use the same timer but make a pool of connections; That way both problems will be solved -function startInterval(session, sessionLogger) { +function startInterval(session, sessionLogger, rxMetrics) { if (!options.messagecount > 0) { sessionLogger.info("No messages to send"); return; @@ -49,10 +52,10 @@ function startInterval(session, sessionLogger) { sendTimer.setInterval( async () => { if (sent >= options.messagecount) { - sessionLogger.info(`Finished sending messages success:${success}, failed:${failed}, idling...`); + // sessionLogger.info(`Finished sending messages success:${success}, failed:${failed}, idling...`); sendTimer.clearInterval(); } else if (inFlight < options.window) { - sessionLogger.info(`Sending message ${sent + 1}/${options.messagecount}`); + // sessionLogger.info(`Sending message ${sent + 1}/${options.messagecount}`); session.deliver_sm( { source_addr: options.source, @@ -62,7 +65,7 @@ function startInterval(session, sessionLogger) { function (pdu) { inFlight--; if (pdu.command_status === 0) { - sessionLogger.info(`Received response with id ${pdu.message_id}`); + // sessionLogger.info(`Received response with id ${pdu.message_id}`); success++; } else { sessionLogger.warn(`Message failed with id ${pdu.message_id}`); @@ -70,6 +73,7 @@ function startInterval(session, sessionLogger) { } } ); + rxMetrics.AddEvent(); sent++; inFlight++; } else { @@ -93,7 +97,10 @@ const server = smpp.createServer( debug: options.debug, }, function (session) { - const sessionLogger = createSessionLogger(sessionid++); + const id = sessionid++; + const sessionLogger = createSessionLogger(id); + const rxMetrics = metricManager.AddMetrics(`Session-${id}-RX`); + const txMetrics = metricManager.AddMetrics(`Session-${id}-TX`); session.on("bind_transceiver", function (pdu) { if (pdu.system_id === options.systemid && pdu.password === options.password) { @@ -115,7 +122,8 @@ const server = smpp.createServer( }); session.on("submit_sm", async function (pdu) { if (!options.dr) { - sessionLogger.info("Replying to incoming submit_sm"); + // sessionLogger.info("Replying to incoming submit_sm"); + rxMetrics.AddEvent(); session.send(pdu.response()); return; } @@ -157,6 +165,7 @@ const server = smpp.createServer( }; sessionLogger.info(`Generated DR as ${drMessage}`); session.deliver_sm(DRPdu); + txMetrics.AddEvent(); }); session.on("close", function () { diff --git a/client.js b/client.js index 7c5fc61..1cac220 100644 --- a/client.js +++ b/client.js @@ -39,14 +39,22 @@ let success = 0; let failed = 0; const sendTimer = new NanoTimer(); -function startInterval(session, sessionLogger) { +function startInterval(session, sessionLogger, metrics) { + if (!metrics.progress) { + metrics.progress = metricManager.AddMetrics("Send progress", false); + metrics.progress.bar.total = options.messagecount; + metrics.window = metricManager.AddMetrics("Send window", false); + metrics.window.bar.total = options.window; + } sendTimer.setInterval( async () => { if (sent >= options.messagecount) { - sessionLogger.info(`Finished sending messages success:${success}, failed:${failed}, idling...`); + // sessionLogger.info(`Finished sending messages success:${success}, failed:${failed}, idling...`); sendTimer.clearInterval(); } else if (inFlight < options.window) { - sessionLogger.info(`Sending message ${sent + 1}/${options.messagecount}`); + // sessionLogger.info(`Sending message ${sent + 1}/${options.messagecount}`); + metrics.progress.bar.increment(); + metrics.window.bar.increment(); session.submit_sm( { source_addr: options.source, @@ -54,9 +62,10 @@ function startInterval(session, sessionLogger) { short_message: options.message, }, function (pdu) { + metrics.window.bar.update(metrics.window.bar.value - 1); inFlight--; if (pdu.command_status === 0) { - sessionLogger.info(`Received response with id ${pdu.message_id}`); + // sessionLogger.info(`Received response with id ${pdu.message_id}`); success++; } else { sessionLogger.warn(`Message failed with id ${pdu.message_id}`); @@ -64,14 +73,15 @@ function startInterval(session, sessionLogger) { } } ); + metrics.txMetrics.AddEvent(); sent++; inFlight++; } else { - sessionLogger.warn( - `${inFlight}/${options.window} messages pending, waiting for a reply before sending more` - ); + // sessionLogger.warn( + // `${inFlight}/${options.window} messages pending, waiting for a reply before sending more` + // ); sendTimer.clearInterval(); - setTimeout(() => startInterval(session, sessionLogger), options.windowsleep); + setTimeout(() => startInterval(session, sessionLogger, metrics), options.windowsleep); } }, "", @@ -80,15 +90,6 @@ function startInterval(session, sessionLogger) { } const metricManager = new MetricManager(); -// async function main() { -// const test1 = metricManager.AddMetrics("test"); -// for (let i = 0; i < 1e5; i++) { -// test1.AddEvent(); -// test1.UpdateBar(); -// await setTimeout(() => {}, 200); -// } -// } -// main(); for (let i = 0; i < options.sessions; i++) { const sessionLogger = createSessionLogger(i); @@ -115,7 +116,10 @@ for (let i = 0; i < options.sessions; i++) { ); const rxMetrics = metricManager.AddMetrics(`Session-${i}-RX`); const txMetrics = metricManager.AddMetrics(`Session-${i}-TX`); - startInterval(session, sessionLogger); + startInterval(session, sessionLogger, { + rxMetrics, + txMetrics, + }); // TODO: Add error message for invalid systemid and password session.on("deliver_sm", function (pdu) { diff --git a/metrics/metricManager.js b/metrics/metricManager.js index c613364..63e5350 100644 --- a/metrics/metricManager.js +++ b/metrics/metricManager.js @@ -13,10 +13,11 @@ class MetricManager { }, cliProgress.Presets.shades_grey ); + setInterval(() => this.multibar.update(), 100); } - AddMetrics(name) { - const metric = new Metric(name, this.multibar, this.metricBufferSize); + AddMetrics(name, refresh = true) { + const metric = new Metric(name, this.multibar, this.metricBufferSize, refresh); return metric; } } diff --git a/metrics/metrics.js b/metrics/metrics.js index 85cf4f3..5b99b31 100644 --- a/metrics/metrics.js +++ b/metrics/metrics.js @@ -1,13 +1,15 @@ const { CircularBuffer } = require("./circularBuffer"); class Metric { - constructor(barName, multibar, bufferSize) { + constructor(barName, multibar, bufferSize, refresh = true) { this.multibar = multibar; - this.pbar = multibar.create(0, 0); - this.pbar.update(0, { name: barName }); + this.bar = multibar.create(0, 0); + this.bar.update(0, { name: barName }); this.buffer = new CircularBuffer(bufferSize); this.maxRate = 0; - setInterval(this.UpdateBar.bind(this), 100); + if (refresh) { + setInterval(this.UpdateBar.bind(this), 100); + } } AddEvent() { @@ -28,11 +30,10 @@ class Metric { UpdateBar() { const eps = this.GetRate(); if (eps > this.maxRate) { - this.pbar.total = eps; + this.bar.total = eps; this.maxRate = eps; } - this.pbar.update(eps); - this.multibar.update(); + this.bar.update(eps); } }