UNPKG

@uisap/core

Version:

A modular Fastify-based framework inspired by Laravel

239 lines (209 loc) 6.24 kB
import { ToadScheduler, AsyncTask, CronJob } from "toad-scheduler"; import { QueueFacade as Queue } from "./facades.js"; export class Schedule { constructor(app) { this.app = app; this.scheduler = new ToadScheduler(); this.pendingTasks = []; this.tasks = []; this.timezone = this.app.config.schedule?.timezone || "Europe/Istanbul"; } addTask(type, options) { const task = { type, ...options }; this.pendingTasks.push(task); this.tasks.push(task); return this; } call(callback, cronExpression = "* * * * *") { return this.addTask("call", { callback, cronExpression }); } queue(queueName, data, cronExpression = "* * * * *") { return this.addTask("queue", { queueName, data, cronExpression }); } command(signature, cronExpression = "* * * * *", options = {}) { return this.addTask("command", { signature, cronExpression, options }); } everySecond() { const lastTask = this.pendingTasks.pop(); return this.addTask(lastTask.type, { ...lastTask, cronExpression: "* * * * * *", }); } everyTwoSeconds() { const lastTask = this.pendingTasks.pop(); return this.addTask(lastTask.type, { ...lastTask, cronExpression: "*/2 * * * * *", }); } everyFiveSeconds() { const lastTask = this.pendingTasks.pop(); return this.addTask(lastTask.type, { ...lastTask, cronExpression: "*/5 * * * * *", }); } everyTenSeconds() { const lastTask = this.pendingTasks.pop(); return this.addTask(lastTask.type, { ...lastTask, cronExpression: "*/10 * * * * *", }); } everyFifteenSeconds() { const lastTask = this.pendingTasks.pop(); return this.addTask(lastTask.type, { ...lastTask, cronExpression: "*/15 * * * * *", }); } everyThirtySeconds() { const lastTask = this.pendingTasks.pop(); return this.addTask(lastTask.type, { ...lastTask, cronExpression: "*/30 * * * * *", }); } everyMinute() { const lastTask = this.pendingTasks.pop(); return this.addTask(lastTask.type, { ...lastTask, cronExpression: "* * * * *", }); } everyTwoMinutes() { const lastTask = this.pendingTasks.pop(); return this.addTask(lastTask.type, { ...lastTask, cronExpression: "*/2 * * * *", }); } everyFiveMinutes() { const lastTask = this.pendingTasks.pop(); return this.addTask(lastTask.type, { ...lastTask, cronExpression: "*/5 * * * *", }); } everyTenMinutes() { const lastTask = this.pendingTasks.pop(); return this.addTask(lastTask.type, { ...lastTask, cronExpression: "*/10 * * * *", }); } everyFifteenMinutes() { const lastTask = this.pendingTasks.pop(); return this.addTask(lastTask.type, { ...lastTask, cronExpression: "*/15 * * * *", }); } hourly(minutes = 0) { const lastTask = this.pendingTasks.pop(); return this.addTask(lastTask.type, { ...lastTask, cronExpression: `${minutes} * * * *`, }); } daily(time = "0:00") { const lastTask = this.pendingTasks.pop(); const [hour, minute] = time.split(":"); return this.addTask(lastTask.type, { ...lastTask, cronExpression: `${minute} ${hour} * * *`, }); } twiceDaily(hour1, hour2, minute = 0) { const lastTask = this.pendingTasks.pop(); return this.addTask(lastTask.type, { ...lastTask, cronExpression: `${minute} ${hour1},${hour2} * * *`, }); } weekly(day = 0, time = "0:00") { const lastTask = this.pendingTasks.pop(); const [hour, minute] = time.split(":"); return this.addTask(lastTask.type, { ...lastTask, cronExpression: `${minute} ${hour} * * ${day}`, }); } monthly(day = 1, time = "0:00") { const lastTask = this.pendingTasks.pop(); const [hour, minute] = time.split(":"); return this.addTask(lastTask.type, { ...lastTask, cronExpression: `${minute} ${hour} ${day} * *`, }); } quarterly(day = 1, time = "0:00") { const lastTask = this.pendingTasks.pop(); const [hour, minute] = time.split(":"); return this.addTask(lastTask.type, { ...lastTask, cronExpression: `${minute} ${hour} ${day} */3 *`, }); } yearly(month = 1, day = 1, time = "0:00") { const lastTask = this.pendingTasks.pop(); const [hour, minute] = time.split(":"); return this.addTask(lastTask.type, { ...lastTask, cronExpression: `${minute} ${hour} ${day} ${month} *`, }); } setTimezone(timezone) { this.timezone = timezone; return this; } run() { this.pendingTasks.forEach((task) => { const taskFn = task.type === "call" ? async () => await task.callback(this.app) : task.type === "queue" ? async () => { await Queue.push(task.queueName, task.data); this.app.fastify.logger.info( `Kuyruk görevi eklendi: ${task.queueName}` ); } : async () => { const consoleKernel = this.app.container.make("consoleKernel"); await consoleKernel.run(task.signature, task.options); }; const errorHandler = (err) => this.app.fastify.logger.error(`${task.type} zamanlama hatası`, { error: err.message, }); const cronJob = new CronJob( { cronExpression: task.cronExpression || "* * * * *", timezone: this.timezone, }, new AsyncTask(`${task.type}-${Date.now()}`, taskFn, errorHandler) ); this.scheduler.addCronJob(cronJob); }); this.pendingTasks = []; this.app.fastify.logger.info("Zamanlayıcı başlatıldı"); } listTasks() { return this.tasks.map((task) => ({ type: task.type, cronExpression: task.cronExpression, details: task.type === "call" ? "Callback" : task.type === "queue" ? `${task.queueName}: ${JSON.stringify(task.data)}` : `${task.signature} ${JSON.stringify(task.options)}`, })); } stop() { this.scheduler.stop(); this.app.fastify.logger.info("Zamanlayıcı durduruldu"); } }