import express from 'express'; import cors from 'cors'; import helmet from 'helmet'; import path from 'path'; import http from 'http'; import passport from 'passport'; import { config } from './config'; import { getDatabase, closeDatabase } from './database'; import { apiLimiter } from './middleware/rateLimiter'; import { initRealtime } from './services/realtime'; import authRoutes from './routes/auth'; import settingsRoutes from './routes/settings'; const app = express(); app.set('trust proxy', 1); app.use(helmet({ contentSecurityPolicy: false, crossOriginEmbedderPolicy: false, })); app.use(cors({ origin: config.corsOrigin, credentials: true, methods: ['GET', 'POST', 'PUT', 'DELETE', 'OPTIONS'], allowedHeaders: ['Content-Type', 'Authorization'], })); app.use(express.json({ limit: '50mb' })); app.use(apiLimiter); app.use(passport.initialize()); app.use('/api/auth', authRoutes); app.use('/api/settings', settingsRoutes); const uploadsPath = path.resolve(__dirname, '../../uploads'); app.use('/uploads', express.static(uploadsPath)); const clientDist = path.resolve(__dirname, '../../client/dist'); app.use(express.static(clientDist)); app.get('*', (_req, res) => { res.sendFile(path.join(clientDist, 'index.html')); }); app.use((err: any, _req: express.Request, res: express.Response, _next: express.NextFunction) => { console.error('Unhandled error:', err); res.status(500).json({ error: 'Internal server error' }); }); getDatabase(); const httpServer = http.createServer(app); initRealtime(httpServer); const server = httpServer.listen(config.port, () => { console.log(`RealBlocks server running on port ${config.port}`); console.log(`Environment: ${config.nodeEnv}`); }); process.on('SIGTERM', () => { console.log('SIGTERM received. Shutting down...'); closeDatabase(); server.close(() => process.exit(0)); }); process.on('SIGINT', () => { console.log('SIGINT received. Shutting down...'); closeDatabase(); server.close(() => process.exit(0)); }); export default app;