Skip to content

Atlas 0.4.0

Released 2026-10-14 · v0.4.0 on GitHub · install with "atlas": "github:AndreyDAraya/atlas#v0.4.0"

Scale out: any number of instances share one database, each consumer (capability or edge subscriber) is delivered by one live instance at a time with automatic failover, and an instance can run API-only. No breaking change: 0.3.0 code keeps working unchanged.

  • Consumer leases. A worker loop delivers a consumer only while its instance holds that consumer’s lease; the others stand by and take it over when the owner stops (it releases its leases) or when its lease expires (a dead or unreachable instance), continuing from the cursor. Edge subscribers (push, email, webhooks) no longer run in every instance, so a fact’s side effect is no longer performed once per instance; capability consumers stop wasting work on cursor conflicts. start({ leaseMs, renewMs }) (defaults 30000 / 10000; renewMs must be shorter, start throws otherwise). (3347d0c)
  • createRuntime({ instance }) and runtime.instance: the lease owner id, a random UUID by default. (3347d0c)
  • start({ workers: false }): an API-only instance runs no consumer loop and no timer loop; dispatch, queries and await / Atlas-Await keep working against the instances that run workers (an await polls the cursors in the store). (3347d0c)
  • Store.lease?(consumer, owner, ttlMs) and Store.unlease?(consumer, owner), optional: the memory and Postgres stores implement them, the contract suite in test/store-contract.ts covers them. A custom store without them runs every consumer in every instance started with workers, as in 0.3.0. (3347d0c)
  • Postgres: table atlas_leases (consumer, owner, expires_at), created by migrate() (CREATE TABLE IF NOT EXISTS, nothing rewritten); a lease is acquired or renewed with one conditional upsert on the database clock. (3347d0c)
  • Trace: warning with code lease-lost when an instance loses a consumer, and a failed (lease) event when a renewal throws. (3347d0c)
  • An edge subscriber’s cursor advances only after its instance renews the lease following the handler; when the lease was lost meanwhile the cursor stays and the new owner delivers the fact again. The remaining at-least-once case is a handler that outlives its lease (a process frozen longer than leaseMs): dedupe by fact.id stays the contract. (3347d0c)
  • stop() releases the instance’s leases after its loops finish. (3347d0c)

Run migrate() on boot as before (it adds atlas_leases). Nothing else changes for one instance. For several: deploy N identical instances, or API instances with start({ workers: false }) plus one or more worker instances; do not call drain() next to running workers (it ignores leases).


From CHANGELOG.md. All versions: Releases.