UNPKG

@citrineos/util

Version:

The OCPP util module which supplies helpful utilities like cache and queue connectors, etc.

168 lines 7.05 kB
"use strict"; // Copyright (c) 2023 S44, LLC // Copyright Contributors to the CitrineOS Project // // SPDX-License-Identifier: Apache 2.0 var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) { if (k2 === undefined) k2 = k; var desc = Object.getOwnPropertyDescriptor(m, k); if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) { desc = { enumerable: true, get: function() { return m[k]; } }; } Object.defineProperty(o, k2, desc); }) : (function(o, m, k, k2) { if (k2 === undefined) k2 = k; o[k2] = m[k]; })); var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) { Object.defineProperty(o, "default", { enumerable: true, value: v }); }) : function(o, v) { o["default"] = v; }); var __importStar = (this && this.__importStar) || (function () { var ownKeys = function(o) { ownKeys = Object.getOwnPropertyNames || function (o) { var ar = []; for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k; return ar; }; return ownKeys(o); }; return function (mod) { if (mod && mod.__esModule) return mod; var result = {}; if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]); __setModuleDefault(result, mod); return result; }; })(); var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) { function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); } return new (P || (P = Promise))(function (resolve, reject) { function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } } function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } } function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); } step((generator = generator.apply(thisArg, _arguments || [])).next()); }); }; Object.defineProperty(exports, "__esModule", { value: true }); exports.RabbitMqSender = void 0; const base_1 = require("@citrineos/base"); const amqplib = __importStar(require("amqplib")); const class_transformer_1 = require("class-transformer"); /** * Implementation of a {@link IMessageSender} using RabbitMQ as the underlying transport. */ class RabbitMqSender extends base_1.AbstractMessageSender { /** * Constructor for the class. * * @param {SystemConfig} config - The system configuration. * @param {Logger<ILogObj>} [logger] - The logger object. */ constructor(config, logger) { super(config, logger); this._connect() .then((channel) => { this._channel = channel; }) .catch((error) => { this._logger.error('Failed to connect to RabbitMQ', error); }); } /** * Methods */ /** * Sends a request message with an optional payload and returns a promise that resolves to the confirmation message. * * @param {IMessage<OcppRequest>} message - The message to be sent. * @param {OcppRequest | undefined} payload - The optional payload to be sent with the message. * @return {Promise<IMessageConfirmation>} A promise that resolves to the confirmation message. */ sendRequest(message, payload) { return this.send(message, payload, base_1.MessageState.Request); } /** * Sends a response message and returns a promise of the message confirmation. * * @param {IMessage<OcppResponse | OcppError>} message - The message to send. * @param {OcppResponse | OcppError} payload - The payload to include in the response. * @return {Promise<IMessageConfirmation>} - A promise that resolves to the message confirmation. */ sendResponse(message, payload) { return this.send(message, payload, base_1.MessageState.Response); } /** * Sends a message and returns a promise that resolves to a message confirmation. * * @param {IMessage<OcppRequest | OcppResponse | OcppError>} message - The message to be sent. * @param {OcppRequest | OcppResponse | OcppError} [payload] - The payload to be included in the message. * @param {MessageState} [state] - The state of the message. * @return {Promise<IMessageConfirmation>} - A promise that resolves to a message confirmation. */ send(message, payload, state) { return __awaiter(this, void 0, void 0, function* () { var _a; if (payload) { message.payload = payload; } if (state) { message.state = state; } if (!message.state) { return { success: false, payload: 'Message state must be set' }; } if (!message.payload) { return { success: false, payload: 'Message payload must be set' }; } const exchange = (_a = this._config.util.messageBroker.amqp) === null || _a === void 0 ? void 0 : _a.exchange; const channel = this._channel || (yield this._connect()); this._channel = channel; this._logger.debug(`Publishing to ${exchange}:`, message); const success = channel.publish(exchange || '', '', Buffer.from(JSON.stringify((0, class_transformer_1.instanceToPlain)(message)), 'utf-8'), { contentEncoding: 'utf-8', contentType: 'application/json', headers: Object.assign({ origin: message.origin.toString(), eventGroup: message.eventGroup.toString(), action: message.action.toString(), state: message.state.toString() }, message.context), }); return { success }; }); } /** * Shuts down the sender by closing the client. * * @return {Promise<void>} A promise that resolves when the client is closed. */ shutdown() { return Promise.resolve(); } /** * Protected Methods */ /** * Connect to RabbitMQ */ _connect() { var _a; return amqplib .connect(((_a = this._config.util.messageBroker.amqp) === null || _a === void 0 ? void 0 : _a.url) || '') .then((connection) => __awaiter(this, void 0, void 0, function* () { this._connection = connection; return connection.createChannel(); })) .then((channel) => { // Add listener for channel errors channel.on('error', (err) => { this._logger.error('AMQP channel error', err); // TODO: add recovery logic }); return channel; }); } } exports.RabbitMqSender = RabbitMqSender; /** * Constants */ RabbitMqSender.QUEUE_PREFIX = 'amqp_queue_'; //# sourceMappingURL=sender.js.map