function createAgendaReplan({ now = () => new Date(), update }) { let items = []; let index = 0; let pending = false; let active = false; const dayKey = date => [ date.getFullYear(), String(date.getMonth() + 1).padStart(2, '0'), String(date.getDate()).padStart(2, '0'), ].join('-'); const dueDay = value => { const match = String(value || '').match(/^(\d{4}-\d{2}-\d{2})(?:$|T)/); return match ? match[1] : ''; }; const current = () => active ? items[index] || null : null; const snapshot = () => ({ active, index, total: items.length, current: current()?.key || null, pending, }); const advance = () => { index += 1; if (index >= items.length) active = false; return { ok:true, done:!active }; }; const change = async dueDate => { const item = current(); if (!item) return { ok:false, error:'No overdue deadline selected.' }; if (pending) return { ok:false, error:'Deadline update already in progress.' }; pending = true; try { await update(item, dueDate); return advance(); } catch (error) { return { ok:false, error:error?.message || 'Deadline could not be updated.' }; } finally { pending = false; } }; return { start(overdue) { items = (overdue || []).slice().sort((left, right) => dueDay(left.due_date).localeCompare(dueDay(right.due_date)) || String(left.repository || '').localeCompare(String(right.repository || '')) || Number(left.number || 0) - Number(right.number || 0) ); index = 0; pending = false; active = items.length > 0; return snapshot(); }, snapshot, current, keep() { if (pending) return Promise.resolve({ ok:false, error:'Deadline update already in progress.' }); if (!current()) return Promise.resolve({ ok:false, error:'No overdue deadline selected.' }); return Promise.resolve(advance()); }, tomorrow() { const date = new Date(now()); date.setDate(date.getDate() + 1); return change(dayKey(date) + 'T23:59:59Z'); }, choose(value) { const chosen = String(value || ''); if (!/^\d{4}-\d{2}-\d{2}$/.test(chosen) || chosen <= dayKey(now())) { return Promise.resolve({ ok:false, error:'Choose a future date.' }); } return change(chosen + 'T23:59:59Z'); }, cancel() { active = false; pending = false; return snapshot(); }, }; } if (typeof module !== 'undefined' && module.exports) module.exports = createAgendaReplan;