Skip to content

fix(scheduler): reject past one-time 'at' cron schedules - #1526

Closed
lifelmy wants to merge 73 commits into
TokenRhythm:mainfrom
lifelmy:agent-tasks/1516
Closed

lifelmy wants to merge 73 commits into
TokenRhythm:mainfrom
lifelmy:agent-tasks/1516

Conversation

@lifelmy

@lifelmy lifelmy commented Aug 31, 2026

Copy link
Copy Markdown
Contributor

Scope

Integrated into main through #1684, retaining the original contribution and maintainer follow-up commits. This PR is closed as superseded by that merged integration.

Past one-time schedules previously executed immediately and disappeared after their run. New or rescheduled at jobs now reject past timestamps before persistence, with an actionable field-named error.

Scope boundary: scheduler creation/update validation, idempotent creation, the cron update RPC, and regression tests. An update containing both an enabled toggle and an invalid schedule leaves the entire stored job unchanged. Valid combined updates persist once. Idempotent retries return an existing job even after its scheduled time; only a genuinely new job is checked for expiry, after acquiring the creation lock with a fresh clock.

Recurring schedules and metadata-only changes to existing overdue jobs retain their behavior.

Branch

Base branch: main.

Target exception: none.

Integrated mainline fixes: #1674 (SQLite fallback connection compatibility) and #1677 (atomic initial generated publication receipts) resolve existing main-branch failures exposed by CI. Both fixes are included and tested with this change. #1674 and #1677 both merged separately after their own review and required CI checks.

Issue

Linked issue: Refs #1516. The closing reference is carried by the stable integration in #1684.

Release Note

Release note: Reject expired one-time reminders without partially updating tasks or breaking idempotent creation retries. No standalone changelog entry added.

Tests

  • Original PR preflight: 57 passed.
  • Supplemental regressions reproduced 12 failures before the fixes.
  • Scheduler, cron RPC, admin-tool, and CLI focused verification: 347 passed.
  • Integrated verification with fix(sqlite): expose change counts on the fallback connection #1674 and fix(artifacts): record initial publication receipts atomically #1677: 376 scheduler, cron update RPC, SQLite compatibility, ArtifactSession, generated source, and workbench tests passed.
  • Coverage includes timezone offsets, no-write rejection, combined enable/schedule updates, concurrent idempotent retries after the due time, expiry while waiting for the creation lock, and metadata-only edits to overdue jobs.
  • Ruff on changed files, targeted mypy on changed source modules, and git diff --check passed.
  • Platform-neutral Python/SQLite logic, locally verified on macOS; remote CI verifies the final PR and queue revision.

Maintainer Live Check

Maintainer live check: no.

Surface: gateway.

Safety

Offline, deterministic, credential-free tests use synthetic jobs and isolated temporary databases. No secrets, runtime transcripts, or local artifacts are included.

Third-Party Origin

Third-party origin: original OpenSquilla contribution by @lifelmy, retained with its commit history in #1684. Maintainer follow-ups make updates atomic and preserve idempotent retries. No external vendored implementation.

A one-time 'at' schedule with a timestamp already in the past is accepted,
fires on the next scheduler tick, and the one-shot job is then deleted — so
the payload runs immediately with no future occurrence and disappears. That
is almost never what a caller scheduling a one-time reminder intends.

Validate the 'at' timestamp against the current time in SchedulerOps.add and
SchedulerOps.update (the two structured-schedule entry points) and raise a
field-named ValueError before persisting, matching the existing timezone and
interval validation style. Recurring cron/every schedules are unaffected.

Fixes TokenRhythm#1516
@lifelmy
lifelmy marked this pull request as ready for review September 2, 2026 11:17
@lifelmy

lifelmy commented Sep 4, 2026

Copy link
Copy Markdown
Contributor Author

Refreshed this PR onto the latest upstream/main (3f92428e); current head is a1762a25. The merge completed without manual conflict edits and preserved the strict past-schedule rejection.

Verification on the refreshed head:

  • .venv/bin/pytest -q tests/test_scheduler/test_ops_strict_schedule.py -> 17 passed
  • focused ruff check -> passed
  • git diff --check upstream/main...HEAD -> passed

GitHub reports the branch as mergeable; the newly triggered CI jobs are still running.

@lifelmy

lifelmy commented Sep 4, 2026

Copy link
Copy Markdown
Contributor Author

Refreshed this PR onto the latest upstream/main (4535029); new head is 9558a1e. The branch was 1 commit behind and merged cleanly without manual conflict edits. Verification: 17 strict-schedule tests passed; focused ruff passed; git diff --check passed.

@lifelmy

lifelmy commented Sep 5, 2026

Copy link
Copy Markdown
Contributor Author

Task A refresh (2026-09-05): fetched latest upstream/main at 770ff387c6, merged it without conflicts, and pushed head e3faf53a9a. The two new base commits touch provider ensemble/runtime and WebUI toast-host paths; the scheduler fix remains unchanged.

Verification on the refreshed head:

  • uv run pytest -q tests/test_scheduler/test_ops_strict_schedule.py -> 17 passed
  • focused uv run ruff check -> passed
  • git diff --check upstream/main...HEAD -> passed

No new comments/reviews or unresolved review threads.

@lifelmy

lifelmy commented Sep 5, 2026

Copy link
Copy Markdown
Contributor Author

Refreshed this branch onto latest upstream/main (1663b1a); new head is 37231ee. The one-commit base update merged without conflicts, and the strict one-time schedule diff remains limited to scheduler ops plus its regression tests. Verification: 17 strict-schedule tests passed, focused Ruff passed, and git diff --check passed.

@lifelmy

lifelmy commented Sep 5, 2026

Copy link
Copy Markdown
Contributor Author

Task A refresh: merged latest upstream/main (846bbc6b) without conflicts; new head is 7af664e42. The strict one-time schedule behavior remains covered. Verification: scheduler/parser/RPC strict-schedule suites passed (44 tests), focused Ruff passed, and git diff --check upstream/main...HEAD passed.

@lifelmy

lifelmy commented Sep 6, 2026

Copy link
Copy Markdown
Contributor Author

Task A refresh: merged latest upstream/main (085bfed00d) without conflicts; new head is 735b225602. The upstream change consolidates settings and durable turn admission, while this PR’s strict rejection of past one-time schedules remains intact. Verification: PYENV_VERSION=3.11.11 uv run pytest -q tests/test_scheduler/test_ops_strict_schedule.py (17 passed), focused Ruff passed, and git diff --check upstream/main...HEAD passed.

@lifelmy

lifelmy commented Sep 7, 2026

Copy link
Copy Markdown
Contributor Author

Refreshed onto current upstream/main (cfa8e4b); merge completed without conflicts and preserved the scheduler change. New head: 172d5c4. Verification: .venv/bin/pytest -q tests/test_scheduler/test_ops_strict_schedule.py (17 passed); git diff --check refs/task-a/upstream/main...HEAD (clean). Fresh CI is running.

@lifelmy

lifelmy commented Sep 7, 2026

Copy link
Copy Markdown
Contributor Author

Task A refresh: merged latest upstream/main (bf7fa0e1e) without conflicts; new head is 4ae1088e5. The upstream progressive-tool-disclosure change does not overlap the scheduler fix. Verification: .venv/bin/pytest -q tests/test_scheduler/test_ops_strict_schedule.py (17 passed), focused Ruff passed, and git diff --check upstream/main...HEAD passed.

@lifelmy

lifelmy commented Sep 7, 2026

Copy link
Copy Markdown
Contributor Author

Task A refresh: merged latest upstream/main (05a6b8619) into the branch without conflicts; new head is a2d0ee1622a59b1bcb32fbcced1b1fbd60c4e5ef. The branch was 1 commit behind; the merge preserved the strict one-time at schedule rejection change.

Verification: .venv/bin/pytest -q tests/test_scheduler/test_ops_strict_schedule.py → 17 passed; git diff --check upstream/main clean. No new review feedback; unresolved threads = 0.

@lifelmy

lifelmy commented Sep 8, 2026

Copy link
Copy Markdown
Contributor Author

Task A refresh: merged latest upstream/main (f7dd1b6f6) into the branch without conflicts; new head is 433b93a21. Re-ran pytest tests/test_scheduler/test_ops_strict_schedule.py = 17 passed. PR remains MERGEABLE/CLEAN.

@lifelmy

lifelmy commented Sep 16, 2026

Copy link
Copy Markdown
Contributor Author

Task A base refresh: merged current upstream/main (a25b696) without conflicts and pushed ec50f84. The incoming base change only updates the Windows desktop icon/verification script and does not overlap this scheduler fix. Verification: PYENV_VERSION=3.11.11 uv run pytest -q tests/test_scheduler/test_ops_strict_schedule.py -> 17 passed; focused Ruff check/format and git diff --check passed.

@lifelmy

lifelmy commented Sep 16, 2026

Copy link
Copy Markdown
Contributor Author

Task A base refresh: fast-forwarded to the maintainer follow-up commit (4073b8d1b), then merged current upstream/main (14087d9ce) without conflicts and pushed 8b74a4644 (0 behind). The upstream skill-streaming/CI changes do not overlap the scheduler fix. Verification: PYENV_VERSION=3.11.11 uv run pytest -q tests/test_scheduler/test_ops_strict_schedule.py tests/test_gateway/test_rpc_cron_update_enabled.py -> 37 passed; focused Ruff and git diff --check refs/remotes/upstream/main...HEAD passed. Fresh CI is running.

@lifelmy

lifelmy commented Sep 16, 2026

Copy link
Copy Markdown
Contributor Author

Task A update: fast-forwarded the local branch to include the maintainer commits through 0af192ab9, then merged the current live upstream/main (9799db657) without conflicts and pushed 3efb407f5 (0 behind).

Fresh verification on the updated head:

  • uv run pytest -q tests/test_scheduler/test_ops_strict_schedule.py tests/test_gateway/test_rpc_cron_update_enabled.py tests/test_compat/test_aiosqlite.py tests/test_gateway/test_generated_source_continuity.py — 80 passed
  • focused uv run ruff check ... — passed
  • git diff --check refs/remotes/upstream/main...HEAD — passed

The previous CI run had two failures while still running; the new head has started a fresh CI evaluation.

@lifelmy

lifelmy commented Sep 16, 2026

Copy link
Copy Markdown
Contributor Author

Refreshed this branch onto the latest main (4d1811616) in 473e268a5; the merge was conflict-free. Revalidated the scheduler/RPC/source-continuity paths plus the new upstream SQLite compatibility coverage: 80 passed, focused Ruff clean, and git diff --check clean. Fresh CI is now running on the updated head.

@lifelmy

lifelmy commented Sep 16, 2026

Copy link
Copy Markdown
Contributor Author

Task A base refresh: merged current upstream/main (44ca500d7, compaction/history fix) into this branch without conflicts and pushed a3c1257e9 (0 behind). The incoming commit overlaps scheduler files only through upstream cleanup/removal of older tests; this PR's past one-time at rejection remains covered. Verification: focused scheduler/RPC/source-continuity/persistence pytest passed (82 tests), focused Ruff passed, and git diff --check upstream/main...HEAD passed.

@lifelmy

lifelmy commented Sep 16, 2026

Copy link
Copy Markdown
Contributor Author

Task A base refresh: merged latest upstream/main (7ac8b37) without conflicts and pushed 49cda42 (0 behind / 73 ahead). The incoming skill-install work touched scheduler files, but Git reconciled it cleanly while preserving this PR’s past one-time schedule rejection. Verification: .venv/bin/pytest -q tests/test_scheduler/test_ops_strict_schedule.py tests/test_gateway/test_rpc_cron_update_enabled.py → 37 passed; focused Ruff and git diff --check passed.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants