UNPKG

@mediarithmics/plugins-nodejs-sdk

Version:

This is the mediarithmics nodejs to help plugin developers bootstrapping their plugin without having to deal with most of the plugin boilerplate

112 lines 5.8 kB
"use strict"; var __importDefault = (this && this.__importDefault) || function (mod) { return (mod && mod.__esModule) ? mod : { "default": mod }; }; Object.defineProperty(exports, "__esModule", { value: true }); exports.ProductionPluginRunner = exports.MsgCmd = void 0; const cluster_1 = __importDefault(require("cluster")); const os_1 = require("os"); var MsgCmd; (function (MsgCmd) { MsgCmd[MsgCmd["LOG_LEVEL_UPDATE_FROM_WORKER"] = 0] = "LOG_LEVEL_UPDATE_FROM_WORKER"; MsgCmd[MsgCmd["LOG_LEVEL_UPDATE_FROM_MASTER"] = 1] = "LOG_LEVEL_UPDATE_FROM_MASTER"; MsgCmd[MsgCmd["GET_LOG_LEVEL_REQUEST"] = 2] = "GET_LOG_LEVEL_REQUEST"; })(MsgCmd || (exports.MsgCmd = MsgCmd = {})); class ProductionPluginRunner { constructor(plugin) { this.numCPUs = (0, os_1.cpus)().length; this.updatePluginLogLevel = (value) => { this.plugin.logger.level = value; }; this.broadcastLogLevelToWorkers = () => { const msg = { cmd: MsgCmd.LOG_LEVEL_UPDATE_FROM_MASTER, value: this.plugin.logger.level, }; for (const id in cluster_1.default.workers) { const worker = cluster_1.default.workers[id]; if (worker) { worker.send(msg); } } }; /** * Socker Listener for master process. It has 4 jobs: * 1 - If a new token is detected by a Worker, it receives a message and should send a message to each workers * 2 - If a worker is asking for a token update (ex: the worker was just created because one of his friends died), the master should send a message to each workers * 3 - If a log level change is detected by a worker, it receives a message and should send a message to each workers * 4 - If a worker is asking for a log level update (ex: the worker was just created because one of his friends died), the master should send a message to each workers * @param recMsg */ this.masterListener = (worker, recMsg) => { this.plugin.logger.debug(`Master ${process.pid} is being called with cmd: ${MsgCmd[recMsg.cmd]}, value: ${recMsg.value ? recMsg.value : 'undefined'}`); if (recMsg.cmd === MsgCmd.LOG_LEVEL_UPDATE_FROM_WORKER) { if (recMsg.value) { // If we receive a Log Level, we update the token this.updatePluginLogLevel(recMsg.value); // We send the log level to each of the workers this.broadcastLogLevelToWorkers(); } else { throw new Error('We received a LOG_LEVEL_UPDATE_FROM_WORKER msg without logLevel in the value field of the msg.'); } } }; /** * Socker Listener of the workers. It should listen for Token update from master and for Log Level changes * @param recMsg */ this.workerListener = (recMsg) => { this.plugin.logger.debug(`Worker ${process.pid} is being called with cmd: ${MsgCmd[recMsg.cmd]}, value: ${recMsg.value ? recMsg.value : 'undefined'}`); if (recMsg.cmd === MsgCmd.LOG_LEVEL_UPDATE_FROM_MASTER) { if (!recMsg.value) { throw new Error('We received a LOG_LEVEL_UPDATE_FROM_MASTER msg without logLevel in the value field of the msg.'); } const level = recMsg.value.toLocaleLowerCase(); this.plugin.onLogLevelUpdate(level); this.plugin.logger.debug(`${process.pid}: Updated log level with: ${JSON.stringify(this.plugin.logger.level)}`); } }; this.plugin = plugin; } /** * Multi threading launch of the App, with socket communicaton to propagate token updates * @param port */ start(port, multiProcessEnabled = false) { const pluginPort = process.env.PLUGIN_PORT; this.pluginPort = pluginPort ? parseInt(pluginPort) : 8080; const serverPort = port ? port : this.pluginPort; if (multiProcessEnabled) { if (cluster_1.default.isMaster) { this.plugin.logger.info(`Master ${process.pid} is running`); // Fork workers. for (let i = 0; i < this.numCPUs; i++) { cluster_1.default.fork(); } // Listener for when the Cluster is being called by a worker cluster_1.default.on('message', this.masterListener); // Sometimes, workers dies cluster_1.default.on('exit', (worker, code, signal) => { this.plugin.logger.info(`worker ${worker.process.pid} died`); // We add a new worker, with the proper socket listener cluster_1.default.fork(); }); } else { // We pass the Plugin into MT mode this.plugin.multiThread = true; // We attach a socket listener to get messages from master process.on('message', this.workerListener); const serverPort = port ? port : this.pluginPort; this.server = this.plugin.app.listen(serverPort, () => this.plugin.logger.info(`${process.pid} Plugin started, listening at ${serverPort}`)); this.plugin.logger.info(`Worker ${process.pid} started`); } } else { this.server = this.plugin.app.listen(serverPort, () => this.plugin.logger.info(`${process.pid} Plugin started, listening at ${serverPort}`)); } } } exports.ProductionPluginRunner = ProductionPluginRunner; //# sourceMappingURL=ProductionPluginRunner.js.map