PH0.3 — Worker skeleton: claim loop, task handler registry, jobs discovery, heartbeat #6
Labels
No labels
ready-for-agent
No milestone
No project
No assignees
1 participant
Notifications
Due date
No due date set.
Blocks
Depends on
#14 PH1.6 — Seed: sample FleetPulse feed, catalogue, three crews, week of shifts, dev persons
patrick/Polaris
#17 T-B — Ingest & projector: FleetPulse ingest, pure presence projector, P12, heatmap on P06
patrick/Polaris
#20 T-E — Plan orchestration: snapshot builder, result writer, solver_run/plan_version lifecycle, publish/supersede
patrick/Polaris
#22 T-G — Scorer & dashboard v1: reliability scorer, score handler, adjusted-confidence hook, dashboard P01
patrick/Polaris
#45 PH6.4 — Retention job per Q16
patrick/Polaris
Reference
patrick/Polaris#6
Loading…
Reference in a new issue
No description provided.
Delete branch "%!s()"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
Parent
Row PH0.3 in
docs/12-implementation-plan.md(branch, owned paths and doc section are defined there).What to build
The worker process claims rows from the
tasktable withFOR UPDATE SKIP LOCKED, dispatches them to handlers registered by decorator and found by package discovery, retries with backoff, runs discovered scheduled jobs, and logs a heartbeat. Domain code can enqueue work through a single helper.Acceptance criteria
Blocked by
Starting on branch
feature/worker-skeleton(fromdevelop@ PH0.2 merge). Owned paths:backend/src/polaris/worker/**,backend/tests/unit/worker/**, plusbackend/src/polaris/domain/tasks.py(creating thedomainpackage with only this file). Minimal, explicitly-scoped extension tobackend/src/polaris/db/repositories/task.pyfor theTaskRepositoryimplementation the import rules require (per the ticket brief). Also addingbackend/tests/unit/domain/**since that dir doesn't exist yet and pairs withdomain/tasks.py.Two notes:
CLAUDE.mdonmainwarns the Forgejo stopwatch is one clock per account, shared across parallel sessions on this token, and says only start it if no other session currently has one open — I can't confirm that from here, so I'm skipping stopwatch start/stop for this ticket rather than risk stomping another session's timer.polaris workerCLI command —backend/Dockerfile(PH0.2) already comments thatENTRYPOINT ["polaris"]/CMD ["api"]expects aworkersubcommand from this ticket, anddocs/07-architecture.md's compose table has theworkerservice runningpolaris worker. That's acli/worker.pyfile (~15 lines, same shape ascli/api.py), but my brief says not to touch anything underbackend/src/polaris/cli/**. I'm building the actual entrypoint aspolaris.worker.main:main()(also reachable viapython -m polaris.worker) so a futurecli/worker.pyis a trivial wrapper — flagging this as a seam request rather than widening this ticket to touchcli/.polaris workerCLI subcommand (cli/worker.py) #52Filed the CLI seam request as #52 (
cli/worker.pyneeded fordocker compose'sworkerservicecommand: ["polaris", "worker"]to actually start it). The Forgejo issue-dependency API returned 404 on this instance so I couldn't wire a formal blocked-by edge — noting the relationship here instead: #52 blocks acceptance criterion 1 of this ticket ("Worker starts against the compose stack...") being provable end-to-end; everything else in this ticket (claim loop, retry/backoff, handler/job discovery, heartbeat job, unit tests) is self-contained and does not depend on #52.PR opened: #53 (targets
main, per the corrected git model). 4/5 acceptance criteria checked above; AC1 ("Worker starts against the compose stack...") is blocked on seam request #52 (cli/worker.py) — everything it needs on the worker side (discovery, scheduler, heartbeat job) is done and tested, confirmed working inside the built Docker image viapython -m polaris.worker.Last AC ticked. While drafting the seam PR for #52 (cli/worker.py), I actually ran the worker against the real compose stack (not just unit tests) and found two more bugs blocking this: the compose worker service's
command:duplicated the Dockerfile'sENTRYPOINT, andPOLARIS_DB_URLisn't a realSettingsfield (silently ignored -- affectedapitoo). Fixing those surfaced a third, deeper bug:task.py'stask_statusenum column persisted the Python member name (QUEUED) instead of.value(queued), which the real Alembic-migrated schema uses -- masked byconftest.pybuilding its test schema from the same buggy column definition viacreate_all(). All three fixed and verified end-to-end (real image, real migration, real heartbeat) in #64.