import { Queue } from 'bullmq'; import { getReminderDate } from '../reminders/reminderDate.js'; import { redisConnection } from './redisConnection.js'; export const weightReminderQueueName = 'weight-reminders'; export const weightReminderQueue = new Queue(weightReminderQueueName, { connection: redisConnection, defaultJobOptions: { attempts: 3, backoff: { type: 'exponential', delay: 60_000 }, removeOnComplete: 100, removeOnFail: 1000, }, }); export const enqueueDailyWeightReminder = (now = new Date()) => { const runDate = getReminderDate(now); return weightReminderQueue.add('check-overdue-weights', { runDate }, { jobId: `weight-reminders-${runDate}`, }); }; export const startWeightReminderScheduler = async () => { // Remove the previous five-minute schedule during upgrades and when disabled. await weightReminderQueue.removeJobScheduler('weight-reminders'); if (process.env.WEIGHT_REMINDERS_ENABLED === 'false') return () => {}; await weightReminderQueue.setGlobalConcurrency(1); let lastRunDate = ''; const runIfNeeded = async () => { const now = new Date(); const runDate = getReminderDate(now); if (lastRunDate === runDate) return; await enqueueDailyWeightReminder(now); lastRunDate = runDate; }; const check = () => { void runIfNeeded().catch(error => console.error('Weight reminder scheduler failed', error)); }; const startup = setTimeout(check, 15_000); const interval = setInterval(check, 60 * 60_000); return () => { clearTimeout(startup); clearInterval(interval); }; };