Background jobs
The eleven job types, the three queues, how retries and orphan recovery work, and what the jobs page shows.
Admin → Background jobs. Needs platform.view_jobs.
A database-backed queue in the API process. Claiming is an atomic conditional update, so more than one worker is safe; a job whose worker dies is requeued by a sweeper rather than lost.
Nothing long-running happens inside a request.
The eleven job types
| Type | Queue | Attempts | What it does |
|---|---|---|---|
repository.ingest |
ingestion | 3 | Fetch, classify and heuristically scan a repository. |
repository.analyse |
ai | 2 | Interpret an ingested repository into a summary and architecture map. |
ai.workflow |
ai | 2 | Run a registered AI workflow and persist its artifact. |
pullrequest.sync |
default | 3 | Mirror pull requests so provenance and change analysis have a local record. |
checks.sync |
default | 3 | Pull CI results and pull-request approvals for supervised pull requests, as observed evidence. |
workmanagement.sync |
default | 3 | Reconcile a work connection — Jira, ClickUp, Monday — into source items. |
brain.derive |
ai | 2 | Read a repository into the workspace's context. |
decisions.mine |
ai | 2 | Mine proposed decisions from the workspace record. |
workspace.provision |
ingestion | 2 | Set up a freshly created workspace from its repository. |
capsules.retrospective |
ingestion | 2 | Build review capsules for the last few merged pull requests. |
retention.purge |
default | 2 | Purge retained prompt and output bodies past their retention window. |
Three queues — default, ingestion and ai — so one kind of work cannot starve another. The queue comes from the registry, always. An earlier design let the caller name one, they disagreed, and jobs sat unclaimed forever.
What triggers a job
Most jobs are enqueued on demand: connecting a repository, pressing Re-index, creating a workspace, asking for a test plan or a capsule summary, pressing Sync now.
Two things run on a timer:
| Timer | Interval | What it does |
|---|---|---|
| Work-connection reconciliation | 15 minutes | Enqueues a sync for any active connection last synced longer ago than that, with nothing already queued for it. Webhooks are the fast path; this is the safety net. |
| Trial sweep | 1 hour | Emails organizations whose trial ends within 3 days. |
There is no scheduled repository re-index. It is manual, or driven by a push webhook.
Statuses and retries
A job is queued, running, succeeded, failed or cancelled.
Retries back off 30 seconds, 2 minutes, 8 minutes, capped at 30 minutes.
A running job heartbeats every 15 seconds. A job silent for 5 minutes is requeued by the reaper with the message "Requeued after a worker restart." — generously long, because an AI run legitimately goes quiet. If its retry budget is spent, it fails with "Worker died and the retry budget is exhausted."
On boot, everything still marked running is requeued regardless of heartbeat.
Cancelling only works on a queued job. A running one has to be waited out.
The page
Four tiles — queued, running, succeeded, failed — over the most recent jobs.
The table shows Type, Queue, Status, Progress (the percentage and the live message, or the error), Attempts as {n}/{max}, Took, and When.
It auto-refreshes every 3 seconds while anything is queued or running, and stops when nothing is.
A Retry button appears on failed jobs only:
Only a failed job can be retried.
Retrying resets the attempt count to zero — a deliberate full budget — clears the error, and marks the job "Requeued by an administrator."
Related
- Connecting a repository — what indexing does.
- Telemetry and retention
- The platform admin area