Skip to content

Run a headless agent worker

This how-to runs a headless, autonomous worker built on the native @nimbus/nimbus SDK. There is no UI: it takes a batch of jobs and runs each one to completion inside your own Nimbus deployment, driven by the same scheduler and document store as any other mutation.

The example lives at examples/nimbus/agent-worker. Run it in place from a checkout of the repository.

runWorker takes a batch of job ids and schedules one processJob hop per job through ctx.scheduler.runAfter, staggered by a fixed interval. Every job then transitions from pending to done entirely server-side — no client polling, no cron, no sandbox execution, just the database and the scheduler.

The reference driver, run.ts, shows the intended shape: it enqueues a batch of jobs, kicks the worker off with one call, and then only observes completion through a live subscription. It never asks the worker to do anything further.

Start the local development server:

Terminal window
nimbus dev

Then deploy the app:

Terminal window
nimbus deploy [TARGET]

TARGET is a URL or a configured target name; omit it to target your local server. To run the headless driver against a running server:

Terminal window
npm run nimbus:example:agent-worker

The driver exits once every job it enqueued reaches done.

ctx.scheduler.runAfter can only target a mutation that compiles to a single database operation — the scheduler replays a stored plan, and that plan has no “schedule another call” variant. So a scheduled target can never itself call ctx.scheduler.runAfter: there is no self-rescheduling worker loop against this surface, by construction. The public cron API (HTTP API) is bounded the same way — a cron job fires a single built-in mutation, not a user function — so it is no escape hatch for a self-rescheduling worker either.

This worker fits that boundary honestly. runWorker — which is never itself a scheduled target — schedules every processJob hop up front in one unrestricted call, staggered by an interval, rather than attempting an open-ended reschedule chain. Scheduling the whole batch at once is how you get unattended, multi-step, scheduler-driven work out of this surface today.