1 | const Controllers = require("./controllers");
|
2 | const Factories = require("./factories");
|
3 | const Messages = require("./messages");
|
4 | const Router = require("./router");
|
5 | const OpenApi = require("./open-api");
|
6 | const Config = require("./../config");
|
7 |
|
8 |
|
9 | class Server {
|
10 |
|
11 | constructor() {
|
12 | this.componentsModules = {
|
13 | requestInterceptors: new Set(),
|
14 | responseInterceptors: new Set(),
|
15 | controllers: new Set(),
|
16 | factories: new Set(),
|
17 | bootstrap: new Set()
|
18 | };
|
19 | }
|
20 |
|
21 | start() {
|
22 | const environment = Object.entries(Config.env).find(([env, flag]) => flag)[0];
|
23 | const Http = Config.server.protocol === "http"? require("http") : require("https");
|
24 |
|
25 | componentsRegistration.call(this);
|
26 | this.server = Http.createServer(Config.server, Router.handle);
|
27 | this.server.once("error", error => {
|
28 | if (error.code === 'EADDRINUSE') {
|
29 | console.log('\x1b[31m%s\x1b[0m', `Server failed to start at ${Config.server.protocol}://${Config.server.host}:${Config.server.port}/. Port ${Config.server.port} is in use.`);
|
30 | } else {
|
31 | console.log(error);
|
32 | }
|
33 | });
|
34 | this.server.listen(Config.server, () => {
|
35 | componentsBootstrap.call(this);
|
36 | console.log('\x1b[32m%s\x1b[0m', `Server is running at ${Config.server.protocol}://${Config.server.host}:${Config.server.port}/ in ${environment} mode...`);
|
37 | });
|
38 | }
|
39 |
|
40 | stop() {
|
41 | this.server.close();
|
42 | }
|
43 |
|
44 | addComponent(componentInfo) {
|
45 | Object.keys(componentInfo).forEach(type => componentInfo[type].forEach(
|
46 | path => this.componentsModules[type].add(path)
|
47 | ));
|
48 | }
|
49 |
|
50 | openApiJSON() {
|
51 | const packageJson = require.main.require("./package.json");
|
52 | return OpenApi.generate({
|
53 | "title": packageJson.name,
|
54 | "description": packageJson.description,
|
55 | "version": packageJson.version,
|
56 | "contact": packageJson.author
|
57 | });
|
58 | }
|
59 |
|
60 | openApiToFile(path = "./openapi.json") {
|
61 | const fs = require("fs");
|
62 | fs.writeFileSync(path, JSON.stringify(this.openApiJSON(), null, 4));
|
63 | }
|
64 | }
|
65 |
|
66 |
|
67 | const componentsRegistration = function () {
|
68 | this.componentsModules.factories.forEach(model => {
|
69 | Factories.define(require(model));
|
70 | });
|
71 |
|
72 | this.componentsModules.requestInterceptors.forEach(interceptor => {
|
73 | Messages.request.addInterceptor(require(interceptor));
|
74 | });
|
75 |
|
76 | this.componentsModules.responseInterceptors.forEach(interceptor => {
|
77 | Messages.response.addInterceptor(require(interceptor));
|
78 | });
|
79 |
|
80 | this.componentsModules.controllers.forEach(controller => {
|
81 | Controllers.define(require(controller));
|
82 | });
|
83 |
|
84 | };
|
85 |
|
86 | const componentsBootstrap = function () {
|
87 | this.componentsModules.bootstrap.forEach(controller => {
|
88 | const bootstrapFn = require(controller);
|
89 | (typeof bootstrapFn === "function") && bootstrapFn(this);
|
90 | });
|
91 | };
|
92 |
|
93 |
|
94 | module.exports = Server;
|