@nightowlsdev/runner-background
RunnerThe durable runner for Night Owls, runs a swarm turn in Trigger.dev v4 or Vercel Workflow so an ask-suspended run can park for days and resume across process death.
What it does
`createBackgroundRunner({ engine, storage, backend })` returns the core `Runner` whose durable task body loops `engine.run`/`engine.resume`, opening a parkable waitpoint (keyed by `followupId`) on each `ask` suspend so a human-in-the-loop turn can park (default `askTimeout` 7d) and resume across process death; `run()` streams live progress over Supabase Realtime rather than an HTTP task stream. The whole vendor surface reduces to a 3-verb `DurableBackend` seam (enqueueRun / createWaitpoint / completeWaitpoint), with three implementations: `createTriggerBackend` (Trigger.dev v4 waitpoints, with `runDurableTask` + `registerBackgroundSwarm`/`getRegisteredSwarm` for the deployed task), `createVercelBackend` (Vercel Workflow hooks, host-injected callables), and an in-memory backend for hermetic tests. `@trigger.dev/sdk` and `workflow` are optional peers (wire exactly one). It asserts the backend is the single retry owner. It never imports `@mastra/*` and re-exports no Mastra types (the engine wall).
Install
pnpm add @nightowlsdev/runner-backgroundKey exports
- createBackgroundRunner
- registerBackgroundSwarm
- getRegisteredSwarm
- buildTaskBody
- createTriggerBackend
- runDurableTask
- createVercelBackend
- createInMemoryBackend
- InMemoryDurableBackend
- verifyDurableLifecycle
- nightOwlsPlugin
- DurableBackend
- Waitpoint
- DurableTaskBody
- BackgroundRunnerOpts
- BackgroundSwarm
- DurableVerifyResult
Usage
import { createBackgroundRunner, createTriggerBackend } from "@nightowlsdev/runner-background";
const backend = createTriggerBackend(/* Trigger.dev v4 wiring */);
const runner = createBackgroundRunner({ engine, storage, backend });
// Suspended HITL turns park on a waitpoint and resume across process death.
await runner.run(ctx, { message: "Draft the launch post." });