feat(scheduler): persist recurring daily starts

Add a local-calendar daily start scheduler with pending receipts, per-day deduplication, DST-safe target calculation, missed-day recovery, and retryable account/start failure outcomes.

Persist and validate the daily rule, expose its next target to the renderer, preserve legacy one-time schedules until a daily rule is saved, and gate boot auto-resume on recorded active-run evidence.

Wire boot, settings, account, suspend, resume, interval, and shutdown lifecycle handling with focused RED/GREEN coverage for calendar, persistence, renderer, and controller boundaries.
This commit is contained in:
Sucukdeluxe
2026-08-22 09:36:45 +02:00
parent d7384c34d1
commit 4eb95c92b9
14 changed files with 843 additions and 71 deletions
+14 -2
View File
@@ -122,7 +122,18 @@ export interface DebridAccountStatus {
export type NotifyPackageSuccessMode = "digest" | "individual";
export interface AppSettings {
export type DailyStartOutcome = "" | "started" | "already_active" | "empty_queue" | "missing_account" | "start_failed" | "missed";
export interface DailyStartSettings {
dailyStartEnabled: boolean;
dailyStartMinuteOfDay: number;
dailyStartFirstLocalDate: string;
dailyStartLastHandledLocalDate: string;
dailyStartPendingLocalDate: string;
dailyStartLastOutcome: DailyStartOutcome;
}
export interface AppSettings extends DailyStartSettings {
language: AppLanguage;
token: string;
realDebridUseWebLogin: boolean;
@@ -271,7 +282,7 @@ export interface RendererAccount {
status: DebridAccountStatus | null;
}
export interface RendererSettings {
export interface RendererSettings extends DailyStartSettings {
language: AppLanguage;
realDebridUseWebLogin: boolean;
realDebridDisabledAccountIds: string[];
@@ -373,6 +384,7 @@ export interface RendererSettings {
debridAccountStatuses: Record<string, DebridAccountStatus>;
providerDailyUsageDay: string;
scheduledStartEpochMs: number;
nextDailyStartEpochMs: number;
}
export type RendererSettingsUpdate = Partial<RendererSettings> & {