import { NestFactory, Reflector } from '@nestjs/core'; import { AppModule } from './app.module'; import { FastifyAdapter, NestFastifyApplication, } from '@nestjs/platform-fastify'; import { Logger, NotFoundException, ValidationPipe } from '@nestjs/common'; import { TransformHttpResponseInterceptor } from './common/interceptors/http-response.interceptor'; import { WsRedisIoAdapter } from './ws/adapter/ws-redis.adapter'; import { InternalLogFilter } from './common/logger/internal-log-filter'; import fastifyMultipart from '@fastify/multipart'; import fastifyCookie from '@fastify/cookie'; async function bootstrap() { const app = await NestFactory.create( AppModule, new FastifyAdapter({ ignoreTrailingSlash: true, ignoreDuplicateSlashes: true, maxParamLength: 1000, trustProxy: true, }), { rawBody: true, logger: new InternalLogFilter(), }, ); app.setGlobalPrefix('api', { exclude: ['robots.txt'] }); const reflector = app.get(Reflector); const redisIoAdapter = new WsRedisIoAdapter(app); await redisIoAdapter.connectToRedis(); app.useWebSocketAdapter(redisIoAdapter); await app.register(fastifyMultipart); await app.register(fastifyCookie); app .getHttpAdapter() .getInstance() .decorateReply('setHeader', function (name: string, value: unknown) { this.header(name, value); }) .decorateReply('end', function () { this.send(''); }) .addHook('preHandler', function (req, reply, done) { // don't require workspaceId for the following paths const excludedPaths = [ '/api/auth/setup', '/api/health', '/api/billing/stripe/webhook', '/api/workspace/check-hostname', '/api/sso/google', '/api/workspace/create', '/api/workspace/joined', ]; if ( req.originalUrl.startsWith('/api') && !excludedPaths.some((path) => req.originalUrl.startsWith(path)) ) { if (!req.raw?.['workspaceId'] && req.originalUrl !== '/api') { throw new NotFoundException('Workspace not found'); } done(); } else { done(); } }); app.useGlobalPipes( new ValidationPipe({ whitelist: true, stopAtFirstError: true, transform: true, }), ); app.enableCors(); app.useGlobalInterceptors(new TransformHttpResponseInterceptor(reflector)); app.enableShutdownHooks(); const logger = new Logger('NestApplication'); const port = process.env.PORT || 3000; await app.listen(port, '0.0.0.0', () => { logger.log( `Listening on http://127.0.0.1:${port} / ${process.env.APP_URL}`, ); }); } bootstrap();