PgQue · Design Brief
Within one queue, events that share a partition key are consumed in order by a single worker at a time; events with different keys are consumed in parallel. Order within a key, parallelism across keys — Kafka's partition model, achieved by routing, with no per-event locks or mutable state.
PgQue is an ordered, immutable log, not a job queue. The motivating
workload (a multi-tenant storage service evaluating PgQue to replace pg-boss) emits
millions of file-lifecycle events — FileCreated,
FileDeleted, FileOverwritten. They must be processed
in order per tenant, but order across tenants does not matter.
A single in-order consumer can't keep up; naive multi-worker consumption breaks per-tenant order. PgQue has cooperative consumers, but they distribute events without key affinity — so a key's order is not preserved. This brief closes that gap.
In · v0.1
hash(key) % N assignmentOut · later
| ID | Decision | Choice (v0.1) |
|---|---|---|
| D1 | Where the key lives | ev_extra1 — no schema change |
| D2 | Failure policy (head-of-line) | Pause the partition (default); skip opt-in |
| D3 | Elasticity | Fixed N in v0.1 |
| D4 | Assignment function | hashtext(key) % N, stable |
| D5 | Per-event state | None — routing only, no lease, no lock |
D2 is the contract-shaping choice: PgQ retry re-inserts a failed event with a later ev_id, which would reorder a key — so strict order must block the key until the failure resolves.
Biggest open risk: a crash-safe pause-on-failure that holds a key "blocked" with no mutable table — likely re-derived at slot start from the presence of an unacked/retrying event for the key. Next concrete step is confirming where assignment hooks into cooperative consumers without touching the engine.