import cron from "node-cron";
import { logger } from "./logger"; // Assuming logger exists
// ============================================
// Job Definitions
// ============================================
const jobs = {
// Run every minute
heartbeat: {
schedule: "* * * * *",
task: async () => {
logger.info("Heartbeat: System is alive");
},
},
// Run every night at midnight
dailyCleanup: {
schedule: "0 0 * * *",
task: async () => {
logger.info("Starting daily cleanup...");
// Db cleanup logic here
await new Promise((resolve) => setTimeout(resolve, 1000));
logger.info("Daily cleanup completed");
},
},
// Run every Monday at 9am
weeklyReport: {
schedule: "0 9 * * 1",
task: async () => {
logger.info("Generating weekly report...");
// Report logic here
},
},
};
// ============================================
// Scheduler Service
// ============================================
type JobName = keyof typeof jobs;
export class Scheduler {
private tasks: Map<JobName, cron.ScheduledTask> = new Map();
init() {
logger.info("Initializing scheduler...");
Object.entries(jobs).forEach(([name, config]) => {
const task = cron.schedule(
config.schedule,
async () => {
logger.info(`Starting job: ${name}`);
try {
await config.task();
logger.info(`Job completed: ${name}`);
} catch (error) {
logger.error(`Job failed: ${name}`, error);
}
},
{
scheduled: false, // Don't start immediately
timezone: "UTC",
},
);
this.tasks.set(name as JobName, task);
});
this.startAll();
}
startAll() {
this.tasks.forEach((task) => task.start());
logger.info("All scheduled tasks started");
}
stopAll() {
this.tasks.forEach((task) => task.stop());
logger.info("All scheduled tasks stopped");
}
stop(name: JobName) {
const task = this.tasks.get(name);
if (task) {
task.stop();
logger.info(`Stopped job: ${name}`);
}
}
start(name: JobName) {
const task = this.tasks.get(name);
if (task) {
task.start();
logger.info(`Started job: ${name}`);
}
}
}
export const scheduler = new Scheduler();
// Start automatically if not imported as module
if (require.main === module) {
scheduler.init();
}