diff --git a/cron/jobs.py b/cron/jobs.py index 2f572c6acb..5e493ae3f7 100644 --- a/cron/jobs.py +++ b/cron/jobs.py @@ -797,19 +797,36 @@ def get_due_jobs() -> List[Dict[str, Any]]: next_run = job.get("next_run_at") if not next_run: + schedule = job.get("schedule", {}) + kind = schedule.get("kind") + + # One-shot jobs use a small grace window via the dedicated helper. recovered_next = _recoverable_oneshot_run_at( - job.get("schedule", {}), + schedule, now, last_run_at=job.get("last_run_at"), ) + recovery_kind = "one-shot" if recovered_next else None + + # Recurring jobs reach here only when something — typically a + # direct jobs.json edit that bypassed add_job() — left + # next_run_at unset. Without this branch, such jobs are + # silently skipped forever; recompute next_run_at from the + # schedule so they pick up at their next scheduled tick. + if not recovered_next and kind in ("cron", "interval"): + recovered_next = compute_next_run(schedule, now.isoformat()) + if recovered_next: + recovery_kind = kind + if not recovered_next: continue job["next_run_at"] = recovered_next next_run = recovered_next logger.info( - "Job '%s' had no next_run_at; recovering one-shot run at %s", + "Job '%s' had no next_run_at; recovering %s run at %s", job.get("name", job["id"]), + recovery_kind, recovered_next, ) for rj in raw_jobs: diff --git a/cron/scheduler.py b/cron/scheduler.py index f8aaf6e3ca..0be6d36239 100644 --- a/cron/scheduler.py +++ b/cron/scheduler.py @@ -417,7 +417,7 @@ def _deliver_result(job: dict, content: str, adapters=None, loop=None) -> Option thread_id = target.get("thread_id") # Diagnostic: log thread_id for topic-aware delivery debugging - origin = job.get("origin") or {} + origin = _resolve_origin(job) or {} origin_thread = origin.get("thread_id") if origin_thread and not thread_id: logger.warning( diff --git a/scripts/release.py b/scripts/release.py index d7fab88b03..17a48e8cff 100755 --- a/scripts/release.py +++ b/scripts/release.py @@ -635,6 +635,7 @@ AUTHOR_MAP = { "nftpoetrist@gmail.com": "nftpoetrist", "dodofun@126.com": "colorcross", "1615063567@qq.com": "zhao0112", + "ethanguo.2003@gmail.com": "EthanGuo-coder", "leozeli@qq.com": "leozeli", "linlehao@cuhk.edu.cn": "LehaoLin", "liutong@isacas.ac.cn": "I3eg1nner",