Jobs
Typed job definitions, the registry, state machine, retries, and backoff.
Jobs are the fundamental unit of work in Dispatch. A job definition is a typed Go function that processes a JSON payload.
Defining a job
import "github.com/xraph/dispatch/job"
type EmailInput struct {
To string `json:"to"`
Subject string `json:"subject"`
Body string `json:"body"`
}
var SendEmail = job.NewDefinition("send_email",
func(ctx context.Context, input EmailInput) error {
return mailer.Send(input.To, input.Subject, input.Body)
},
)The generic type parameter T must be JSON-serializable. NewDefinition returns a *Definition[T] that carries both the name and the handler.
Registering a job
Use engine.Register at startup:
engine.Register(eng, SendEmail)
engine.Register(eng, GenerateReport)
engine.Register(eng, ProcessPayment)Internally, Register calls job.RegisterDefinition on the engine's *job.Registry, converting the typed handler to a type-erased HandlerFunc.
Enqueueing a job
engine.Enqueue(ctx, eng, SendEmail, EmailInput{
To: "user@example.com",
Subject: "Welcome!",
})Additional enqueue options:
// Schedule for the future
engine.EnqueueAt(ctx, eng, SendEmail, input, time.Now().Add(10*time.Minute))
// Set priority (higher = dequeued first)
engine.EnqueueWithPriority(ctx, eng, SendEmail, input, 10)
// Target a specific queue
engine.EnqueueOnQueue(ctx, eng, SendEmail, input, "critical")State machine
A job progresses through these states:
pending → running → completed
pending → running → retrying → pending → running → ...
pending → running → failed
pending → running → failed → dlq
pending → cancelled| State | Meaning |
|---|---|
pending | Waiting to be picked up |
running | Currently executing |
completed | Finished successfully |
retrying | Failed but scheduled for retry |
failed | Failed terminally (no retries remain) |
cancelled | Explicitly cancelled |
Retries and backoff
Configure retries on the job definition:
var SendEmail = job.NewDefinition("send_email",
handler,
job.WithMaxRetries(5),
)Configure the backoff strategy on the engine:
eng := engine.Build(d,
engine.WithBackoff(backoff.Exponential(
backoff.WithBase(5*time.Second),
backoff.WithMax(2*time.Hour),
)),
)After MaxRetries is exhausted, the job is moved to the DLQ.
Job timeout
Set a per-job execution deadline:
var SendEmail = job.NewDefinition("send_email",
handler,
job.WithTimeout(30*time.Second),
)The middleware.Timeout() middleware enforces this via context cancellation.