import 'source-map-support/register'; import 'dotenv/config'; import '../commons/utils/force-chalk-colors'; import express from 'express'; import cookieParser from 'cookie-parser'; import cors from 'cors'; import chalk from 'chalk'; import { json } from 'body-parser'; import morgan from 'morgan'; import passport from 'passport'; import { AppDb } from './db/db'; import { handleError } from '../commons/utils/handle-error'; import './socket/rooms'; import { authorizeReq } from './auth/auth'; import { setupDbIndexes } from './db/setup-db-indexes'; import { io } from './socket/socket'; import { Logger } from '../commons/logger/logger'; import { initRunnerManager } from './runners/init-runner-manager'; import { initCleanJobsTask } from './jobs/clean-jobs-task'; import { migrate } from './db/migrate/migrate'; import { env } from './env'; import { routes } from './routes/routes'; import { initRepoSyncTask } from './repos/repo-sync-task'; import { createServer } from 'http'; import { createServer as createSecureServer } from 'https'; import { promises } from 'fs'; import { initRefreshAuthTokensTask } from './auth/refresh-auth-tokens'; import { GITEA_WEBHOOK_SIGNATURE_HEADER } from './git-servers/gitea/gitea'; import { GITHUB_WEBHOOK_SIGNATURE_HEADER } from './git-servers/github/github'; const logger = new Logger('metroline.server:server'); logger.info(`Metroline Server ${BUILD_INFO.version} - ${BUILD_INFO.buildDate} - ${BUILD_INFO.commitHash}`); async function main(): Promise<any> { await AppDb.init(); await migrate(AppDb.client, AppDb.db); await setupDbIndexes(); initRunnerManager(); initCleanJobsTask(); initRepoSyncTask(); initRefreshAuthTokensTask(); const app = express(); app.use(morgan('tiny')); app.use(json({ verify: (req: any, res, buf) => { // store raw body for signature verification if ( Buffer.isBuffer(buf) && ( // https://developer.github.com/webhooks/event-payloads/#delivery-headers req.header(GITHUB_WEBHOOK_SIGNATURE_HEADER) // https://docs.gitea.io/en-us/webhooks/#example || req.header(GITEA_WEBHOOK_SIGNATURE_HEADER) ) ) { // import cloneBuffer from 'clone-buffer'; // req.rawBody = cloneBuffer(buf); req.rawBody = buf; } return true; }, })); app.use(cookieParser()); app.use(cors({ origin: env.METROLINE_UI_URL, credentials: true, })); app.use(passport.initialize()); app.use(authorizeReq); app.use(routes); app.use(handleError); const server = env.METROLINE_SSL_KEY && env.METROLINE_SSL_CERT ? createSecureServer({ key: await promises.readFile(env.METROLINE_SSL_KEY), cert: await promises.readFile(env.METROLINE_SSL_CERT), }, app) : createServer(app); server.listen(env.METROLINE_PORT, () => { logger.info(`Listening on port ${chalk.bold.green(env.METROLINE_PORT)}`); }); io.listen(server); } main().catch(err => logger.error(err));