Documentation

Build background jobs with JobOrc

Plain-language guides for integrating the platform — not internal engineering specs.

Writing workers

Workers are long-running processes that claim jobs, run your handlers, heartbeat leases, and complete or fail attempts.

Minimal worker

>_example.ts
TS
import { createJobOrc } from '@joborc/sdk';
const joborc = createJobOrc({
apiKey: process.env.JOBORC_API_KEY!,
projectId: process.env.JOBORC_PROJECT_ID!,
});
const worker = joborc.worker({
queues: ['default', 'emails'],
concurrency: 5,
handlers: {
'email.send': async (payload, ctx) => {
ctx.log('sending', { to: (payload as { to: string }).to });
},
'invoice.pdf': async (payload, ctx) => {
await generatePdf(payload);
await ctx.heartbeat();
},
},
});
await worker.start();
process.on('SIGTERM', async () => {
await worker.stop({ drainTimeoutMs: 30_000 });
process.exit(0);
});

Job context

  • ctx.jobId, queue, jobType, attemptNumber
  • ctx.heartbeat() — extend lease during long work
  • ctx.signal — AbortSignal for cancellation / drain
  • ctx.log(msg, fields?) — scoped logging

Handler contract

  • Resolve → attempt succeeds
  • Throw → attempt fails; server retry policy decides next attempt or DLQ

At-least-once

Handlers must tolerate duplicates. Use DB unique constraints and provider idempotency keys. Prefer enqueue-time idempotencyKey for producer retries.

Replay failed / DLQ jobs

>_example.ts
TS
await joborc.jobs.replay(jobId, { resetAttempts: true });

Related: Concepts · Quickstart