Example: Inventory Tracker

Items, locations, movements, and low-stock alerts. A complete warehouse tracker where the ledger is always right.

Inventory is a ledger problem: current stock is a sum of movements, and every movement must be recorded once, in order. This example builds that ledger with alerts on top.

Data Model

  • items: sku, name, unit, reorder_level.
  • locations, warehouse/zone/bin.
  • movements. One append-only document per change:
Movement Document
{
  "_meta": {
    "cms": 1782166695055,
    "created": 1782166695,
    "entity": 1,
    "expiry": -1,
    "guid": "08193b4a5d6e7f8091a2b3c4d5e6f708192a3b4c5d6e7f8091a2b3c4d5e6f708",
    "removed": 0,
    "ums": 1782166695092,
    "update_hash": "5e0d38c7a1f294b6037ce8a51d9f27b046a3c81e",
    "updated": 1782166695
  },
  "actor_guid": "b9ee6a631b24e78d1aa48aef0dc067fff7bfbacd24a56ef4ed1f08e537d48b6bd02",
  "item_name": "essential cotton t-shirt",
  "location": "wh-1/zone-a/bin-04",
  "note": "po-10482",
  "quantity": 24,
  "sku": "TSHIRT-BLK-M",
  "type": "receive"
}

Movement types: receive, ship, adjust, transfer (two linked movements: out + in). Never update movements: corrections are new adjust movements (the activity-log principle from Storage Examples).

Current Stock, Two Ways

  1. Ledger sum (exact): aggregate movements per sku+location when you need the precise figure.
  2. Counter document (fast). A stock storage with one doc per sku+location; every movement flow also applies mutations_increment_by_field to it via function_update_document (sequential, race-free. See mutations). Lists and alerts read only counters.

Audit job: a daily schedule_repeating_event recomputes the ledger sum against the counter and logs drift. You will catch a missed movement within a day, not at year-end.

The Flows

  • Receive: form or API → create movement → increment counter. Idempotent via a source reference (po-10482): re-receiving the same reference is skipped.
  • Ship: same, negative increment, with a guard when the counter would drop below zero (hold as backorder movement instead of going negative).
  • Transfer. One flow writes the out-movement and in-movement as two linked documents sharing a transfer guid; the counters move in the same flow.
  • Count check. An adjust movement with the counted quantity difference; the counter follows the same path as everything else.

Low-Stock Alerts

  1. After every counter change, compare against the item's reorder_level.
  2. Crossing the threshold (and only then: track previous state on the counter to avoid alert spam) creates an alert document and emails the buyer via the email pattern.
  3. Alert page: open alerts sorted by severity, closed with a status mutation once the receive lands.
  4. Next Steps

    E-Commerce Catalog Sell through this stock. Storage Examples The ledger and counter models in full. Repeating Events The daily drift-check scheduler.