UNPKG

neura-express-app

Version:

Basic express application starter with some common utilities.

125 lines (124 loc) 4.91 kB
"use strict"; var __importDefault = (this && this.__importDefault) || function (mod) { return (mod && mod.__esModule) ? mod : { "default": mod }; }; Object.defineProperty(exports, "__esModule", { value: true }); exports.NeuraApp = void 0; const http_1 = __importDefault(require("http")); const express_1 = __importDefault(require("express")); const http_terminator_1 = require("http-terminator"); const app_error_1 = require("./errors/app.error"); const api_error_1 = require("./errors/api.error"); const express_2 = __importDefault(require("express")); const cookie_parser_1 = __importDefault(require("cookie-parser")); class NeuraApp { constructor(config, container) { this.config = config; this.container = container; this.started = false; this.middlewaresInitialized = false; this.app = (0, express_1.default)(); this.httpServer = new http_1.default.Server(this.app); const logger = container.get("logger"); if (!logger) { throw new app_error_1.NeuraAppError("logger-not-defined", "Can't find logger in container!", false); } this.logger = logger; this.httpTerminator = (0, http_terminator_1.createHttpTerminator)({ server: this.httpServer, }); } get HttpServer() { return this.httpServer; } get ExpressApp() { return this.app; } addController(instance) { if (!this.middlewaresInitialized) { if (this.config.bodyParserEnabled) { this.addMiddleware((0, cookie_parser_1.default)()); this.addMiddleware(express_2.default.json()); this.addMiddleware(express_2.default.urlencoded({ extended: false })); } if (this.config.logHttpRequests) { this.app.use((req, _res, next) => { this.logger.info(`[App]: New request`, { method: req.method, url: req.url, body: req.body, query: req.query, }); next(); }); } this.middlewaresInitialized = true; } const routePrefix = instance.getRouterPrefix(); const router = instance.getRouter(); const constructorName = instance?.constructor?.name; if (routePrefix) { this.app.use(routePrefix, router); this.logger.debug(`[App]: Controller added: ${constructorName} on base url: ${routePrefix}`); return; } this.logger.debug(`[App]: Controller added: ${constructorName}`); this.app.use(router); } addMiddleware(handler) { this.logger.debug(`[App]: Middleware added: ${handler.name}`); this.app.use(handler); } listen() { // Make sure application was not already started if (this.started) { throw new app_error_1.NeuraAppError("app-started-multiple-times", "Application was already started", false); } // If route was not found, handle it this.app.use((req, _res) => { throw new api_error_1.NotFoundError(`HTTP Not found: ${req.method} on ${req.url}`); }); // If error was thrown, handle it this.app.use((error, req, res, _next) => { this.logger.warn("ErrorMiddleware: API error occurs", error); // Handle validation errors if (error instanceof api_error_1.ValidationRequestError) { return res.status(error.status).send({ code: error.status, error: error.message, data: error.data, }); } // Handle other API errors if (error instanceof api_error_1.NeuraAPIError) { return res.status(error.status).send({ code: error.status, error: error.message, }); } // Unknown error, return 500 return res.status(500).send({ code: 500, message: "Something went wrong!", }); }); return new Promise((res, _rej) => { this.httpServer.listen(this.config.port, () => { this.started = true; this.httpServer.on("close", () => { this.logger.info(`[HttpServer]: Closed`); }); this.logger.info(`[HttpServer]: Listening at http://localhost:${this.config.port}`); res(); }); }); } async close() { if (this.started) { // HttpTerminator will terminate all pending connections await this.httpTerminator.terminate(); } this.logger.info("[Application]: Closed"); } } exports.NeuraApp = NeuraApp;