-
Notifications
You must be signed in to change notification settings - Fork 47
Expand file tree
/
Copy pathindex.ts
More file actions
90 lines (78 loc) · 3.14 KB
/
index.ts
File metadata and controls
90 lines (78 loc) · 3.14 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
// @TODO-ZM: remove the need for reflect-metadata
// Import these two first! in this order
import "reflect-metadata";
import "src/_utils/setup-sentry";
import * as Sentry from "@sentry/node";
import { RoutingControllersOptions, createExpressServer, useContainer } from "routing-controllers";
import { Application } from "express";
import { ConfigService } from "src/config/service";
import Container from "typedi";
import { ContributionController } from "src/contribution/controller";
import { ContributorController } from "src/contributor/controller";
import { DigestCron } from "src/digest/cron";
import { GithubController } from "src/github/controller";
import { LoggerMiddleware } from "./middlewares/logger";
import { LoggerService } from "src/logger/service";
import { PostgresService } from "src/postgres/service";
import { ProjectController } from "src/project/controller";
import { RobotsController } from "./middlewares/robots";
import { SearchController } from "src/search/controller";
import { SearchService } from "src/search/service";
import { SecurityMiddleware } from "./middlewares/security";
import { fsConfig } from "@dzcode.io/utils/dist/config";
// Use typedi container
useContainer(Container); // eslint-disable-line react-hooks/rules-of-hooks
(async () => {
// Initialize Database
const postgresService = Container.get(PostgresService);
await postgresService.migrate();
const { NODE_ENV, PORT } = Container.get(ConfigService).env();
// Initialize Search Service
const searchService = Container.get(SearchService);
await searchService.setupSearch();
// Add crons to DI container
const CronServices = [DigestCron];
CronServices.forEach((service) => Container.get(service));
// Create the app:
const routingControllersOptions: RoutingControllersOptions = {
controllers: [
ContributionController,
GithubController,
ProjectController,
ContributorController,
RobotsController,
SearchController,
],
middlewares: [SecurityMiddleware, LoggerMiddleware],
cors: Container.get(SecurityMiddleware).cors(),
};
const app: Application = createExpressServer(routingControllersOptions);
const loggerService = Container.get(LoggerService);
Sentry.setupExpressErrorHandler(app);
// Graceful shutdown handler for logger file streams
const shutdown = (signal: string, server?: ReturnType<Application["listen"]>) => {
loggerService.logger.info("Received signal, closing logger streams", "signal", signal);
if (server) {
server.close(() => {
loggerService.close();
process.exit(0);
});
// Force shutdown after timeout
setTimeout(() => {
loggerService.logger.error("Forced shutdown after timeout");
loggerService.close();
process.exit(1);
}, 10000);
} else {
loggerService.close();
process.exit(0);
}
};
// Start it
const server = app.listen(PORT, () => {
const commonConfig = fsConfig(NODE_ENV);
loggerService.logger.info("API Server started", "url", commonConfig.api.url);
});
process.on("SIGTERM", () => shutdown("SIGTERM", server));
process.on("SIGINT", () => shutdown("SIGINT", server));
})();