Prashikshak / API /src /server.ts
Abhisingh-18's picture
Initial commit: Prashikshak - disaster management training platform
9a92a42
Raw
History Blame Contribute Delete
4.26 kB
import express, { Request, Response } from "express";
import cookieParser from "cookie-parser";
import cors from "cors";
import connectDB from "./util/database.util";
import userRoutes from "./router/user.router";
import locationRoutes from "./router/locationHistory.router";
import analyticsRoutes from './router/analytics.router';
import activityRoutes from './router/activity.router';
import eventRoutes from './router/event.router';
import eventDayRoutes from './router/eventDay.router';
import formRoutes from './router/form.router';
import sachetRoutes from './router/sachet.router';
import { API_PREFIX, PORT } from "./config/env.config";
import { initializeRedis } from './util/redis.util';
import cluster from 'cluster';
import os from 'os';
const app = express();
// ============================================================================
// MIDDLEWARE
// ============================================================================
app.use(express.json());
app.use(express.urlencoded({ extended: true }));
app.use(cookieParser());
const allowedOrigins = [
"http://localhost:5173",
"https://jpglj93t-3000.inc1.devtunnels.ms",
"https://jpglj93t-5173.inc1.devtunnels.ms"
];
app.use(
cors({
origin: function (origin, callback) {
if (!origin || allowedOrigins.includes(origin)) {
callback(null, origin);
} else {
callback(new Error("Not allowed by CORS"));
}
},
credentials: true,
})
);
// Trust proxy for load balancers
app.set('trust proxy', 1);
// ============================================================================
// HEALTH CHECK - Required for load balancers
// ============================================================================
app.get(`${API_PREFIX}/health`, (req: Request, res: Response): Response => {
return res.status(200).json({
message: "I eat apple everyday :)",
success: true,
instance: process.pid,
uptime: process.uptime()
});
});
// Readiness check for K8s/load balancers
app.get(`${API_PREFIX}/ready`, async (req: Request, res: Response) => {
try {
// Check database connection
const mongoose = await import('mongoose');
if (mongoose.connection.readyState !== 1) {
return res.status(503).json({ ready: false, reason: 'Database not ready' });
}
// Check Redis connection
const redis = await import('./util/redis.util');
const redisClient = await redis.getRedisClient();
if (!redisClient.isReady) {
return res.status(503).json({ ready: false, reason: 'Redis not ready' });
}
return res.status(200).json({ ready: true, instance: process.pid });
} catch (error) {
return res.status(503).json({ ready: false, error: String(error) });
}
});
// ============================================================================
// API ROUTES
// ============================================================================
app.use(`${API_PREFIX}/users`, userRoutes);
app.use(`${API_PREFIX}/location`, locationRoutes);
app.use(`${API_PREFIX}/events`, eventRoutes);
app.use(`${API_PREFIX}/event-days`, eventDayRoutes);
app.use(`${API_PREFIX}/analytics`, analyticsRoutes);
app.use(`${API_PREFIX}/activity`, activityRoutes);
app.use(`${API_PREFIX}/forms`, formRoutes);
app.use(`${API_PREFIX}/sachet`, sachetRoutes);
// ============================================================================
// CLUSTERING FOR MULTI-CORE USAGE
// ============================================================================
if (cluster.isPrimary && process.env.NODE_ENV === 'production') {
const numCPUs = os.cpus().length;
console.log(`Primary ${process.pid} is running`);
console.log(`Forking ${numCPUs} workers...`);
for (let i = 0; i < numCPUs; i++) {
cluster.fork();
}
cluster.on('exit', (worker, code, signal) => {
console.log(`Worker ${worker.process.pid} died. Forking new worker...`);
cluster.fork();
});
} else {
// Worker processes
startServer();
}
async function startServer() {
try {
await connectDB();
await initializeRedis();
app.listen(PORT, () => {
console.log(`Worker ${process.pid} running on port ${PORT}`);
});
} catch (error) {
console.error('Failed to start server:', error);
process.exit(1);
}
}