# Product

**Nothing on this door is built and nothing is hosted.** Every capability below is stated in the
future tense. The one present-tense fact is the contract the surface renders against:
`@mdxld/frame@0.1.0` is merged on `main` in `github.com/dot-org-ai/mdx.org.ai` and its 157 tests
pass (run 2026-08-05). Everything else here ships later, and this file says so rather than implying
otherwise.

The implementation is specified in
[`docs/specs/surfaces/worklists.app.md`](../../specs/surfaces/worklists.app.md) — six Views, twelve
Roles, the verbs, the states, the refusals, the build order — and that document is authoritative;
this page restates it for a buyer. The verb set and its free/paid derivation are
[`docs/specs/verbs/worklists.dev.md`](../../specs/verbs/worklists.dev.md). Everything under
[the shared surface](../../specs/shared-surface.md) is inherited and not restated.

## Register

product

## Users

**The operator who is going to put their own name on a frontline app.** A DC or plant leader, a
3PL's ops director, a retailer's store-ops lead, a food or pharma operations VP under a dated
compliance clock. They already have a floor, a scanner fleet or a phone in every hand, and a WMS
that records that a button was pressed. What they do not have is an app they can hand a picker on
Monday that produces evidence an auditor, a customer or a chargeback panel accepts — and every
vendor who offers them one wants their brand on the worker's screen.

**A second operator, and the design owes as much to them as to the first.** A union, a trade
school, an apprenticeship program, a trade association — an organization the worker already
believes, running an instance for its own members. That deployment's record belongs to the worker,
counts toward no employer's metric, and is visible to no employer. It is not a charity case bolted
on; it is the second of two deliberately non-fungible identity regimes, and the app is what makes
which one you are in legible to the person holding the device.

**The buying agent is a first-class reader.** It arrives with a job and a budget, reads the Offer
below, and needs the unit of purchase to be unambiguous without a call.

**⚠ The frontline worker is the subject of this product and is not its audience.** They never meet
this brand. Every shipped instance is their employer's app or their own organization's app, and
*nothing upstream is named at all* [RULED 2026-08-03, owner]. Copy that addresses the worker does
not belong on this surface; copy that addresses the operator *about* the worker is what this
surface is. **worklists.app has a public face and it is operator-facing** [RULED 2026-08-04, owner:
*"that page might be for managers as well as employees — but that's the name of the generic
whitelabeable app (that we expect customers to white label and publish on their app store
account)"*].

## Product Purpose

worklists.app is the frontline app of the visibility family, operated by Visibility Cloud, Inc. It
is **the generic app an operator white-labels, brands, and ships to their own floor** — the human
and agent face of [worklists.dev](../worklists.dev/PRODUCT.md), which is the API door and a
different product.

**The whole app is one motion, and everything else in it is support for that motion:**

```
   SCAN  ──▶  ATTEST  ──▶  EMIT  ──▶  COMPLETE(eventHash)
   the person      barcoding.dev    id.org.ai     epcis.dev      worklists.dev
   points a        detect/decode/   attest        capture        complete
   camera at       parse
   a mark
```

One of those four steps is performed by a human, and it is the one that requires no reading.
`complete` takes an event hash, not a boolean, so closing a task means presenting an attested
capture — a real `who`, at a real place, inside the window. **The record of the work is the same
object as the evidence it happened.** An operator gets task completion that cannot be faked without
building anything, because it falls out of the spine rather than sitting on top of it.

**The scan emits whether or not a queue agrees with it.** The capture goes to the spine first; the
app then matches it against the worklist it already holds. Exactly one match closes the task. More
than one fails closed and presents the candidates rather than guessing. No match leaves the event
standing — **a scan that closed no task is not an error.** A worker's record of what they did does
not depend on a dispatcher having predicted it.

**White-label runs in both directions, and that is the product rather than a feature of it**
[RULED 2026-08-03, owner]. The employer's deployment is their brand, their controller, their app
store account. The worker-held deployment is their organization's. One implementation, many branded
fronts — the estate's brand-projection thesis, instantiated. **We take no reputational risk from an
app workers are required to use, because our name is not on it, and neither does the operator
inherit ours.**

**The regime is compiled into a deployment, not configured in it.** A build is bound at compile
time to one of two identity paths — employer-directed attestation, which counts toward
who-completeness and which the worker knows they are under; or worker-held record, which counts
toward nothing and is visible to no employer. It is not a prop, not a config row, not a response
field, and not reachable from any authenticated session. *An app that could be re-pointed from one
regime to the other by configuration would convert a structural guarantee back into a promise.*

**Agents are performers here, not spectators.** An agent has no camera, so three of the four steps
are identical and the fourth is whatever produced its payload — and the provenance on those values
says which. An agent that cannot present a hash has not completed anything either.

The runtime is **Expo (React Native)** and the transport is **capnweb over a Cloudflare Durable
Object WebSocket on the Hibernation API** — the same session the console and an agent speak
[RULED 2026-08-04, owner]. Distribution — store-published from the operator's own developer
account, an Expo dev-client build, or a PWA — is not yet ruled, and this file does not pretend it is.

## Brand Personality

Plain, operational, unfussy — the register of a good shift lead talking to the person who runs the
building. Short nouns for real things: task, scan, block, evidence, done. **The voice on the public
face is addressed to an operator; the voice inside a deployment is the operator's own, not ours.**

**This is the one door in the family whose design serves someone else's brand**, which is why the
Register is `product` and not `brand`. Every string, glyph, color and asset a performer can see is
projectable. A hard-coded product name anywhere in the shared code is a defect, not a style
question.

Present tense only for what is live and tested; explicit future tense for everything else. Proof is
an artifact — a computed hash, a passing parity assertion, a rendered face — never an adjective.

## Anti-references

- No leaderboard, no ranking, no streak, no badge, no level, no target. **Gamification of a rate is
  still a rate**, and the `*.ing.games` name is a brand family, never a scoreboard.
- No "workforce optimization," no productivity score, no utilization, no attainment, no
  "employee engagement" vocabulary anywhere on this surface.
- No mission-control grid: this is a phone held in one gloved hand, not a wall display.
- No swipe-only affordance on the critical path. Swipe-to-complete is precisely the pattern
  WCAG 2.2's Dragging Movements criterion exists to refuse, and it is the first pattern a frontline
  app reaches for.
- No dark-mode-only and no light-mode-only aesthetic — this is read in a freezer at 05:00 and in a
  yard at noon, and the deployment honours the device.
- No stock photography of smiling warehouse workers, no conveyor belts, no "digital transformation"
  headline over what is a list of work.
- No "powered by," no family footer, no upstream link, in any shipped instance.
- No "Contact us." Banned on every surface, including Enterprise.

## Design Principles

1. **The close path requires no reading.** The confirm *is* the scan — a confirmation dialog
   reintroduces reading on the critical path. Success is conveyed non-textually and redundantly:
   haptic **and** a shape change **and** a sound. Never color, never color plus text.
2. **The regime is compiled in, not passed in.** Build-time constant, grep-able build assertion,
   and it is rendered to the performer because *the app you are holding tells you which regime you
   are in* is a claim the surface should make out loud.
3. **It carries no name but the operator's.** No shared chrome, no shared analytics tag, no shared
   error-reporting hostname, no shared push certificate. *The link graph is the association graph a
   model learns*, and it is not made only of anchors.
4. **Every rendered value carries its provenance and its presence.** Observed, computed and
   model-inferred are marked as what they are, in every face. **`absent` ≠ `withheld` ≠
   `unconfirmed` ≠ `present(0)`** — genuinely unknown, license-gated, in-flight, and a real zero are
   four different facts, and collapsing them is a quiet lie about the record.
5. **The record survives the queue.** The scan emits first and unconditionally. Nothing on the
   critical path requires a round trip to render: the worklist is held, the block causes are in the
   build, the regime is a constant. A dead network does not stop a camera.
6. **The human face and the agent face cannot disagree.** Both are derivations of one typed frame
   built once, held to the same canonical glyph by an assertion that runs in CI — not two
   implementations kept in sync by discipline.

## Accessibility & Inclusion

WCAG 2.2 AA, and on this surface it is a product requirement rather than a compliance one: the
reader may be gloved, in a freezer, in a yard, unable to read the deployment's language, or unable
to read at all. Full function without color. `prefers-reduced-motion` and `prefers-color-scheme`
honored. Keyboard-reachable throughout.

The 2.2 criteria this surface lives or dies on are Target Size (Minimum), Dragging Movements,
Accessible Authentication (Minimum), Focus Not Obscured (Minimum), and Redundant Entry — a gloved
hand needs a target floor, the critical path needs no drag, login must not be a memory puzzle, a
viewfinder overlay is the canonical way to obscure a focused control, and a performer never
re-enters what the scan already produced. *(Criterion numbers and levels are enumerated in
[`surfaces/worklists.app.md`](../../specs/surfaces/worklists.app.md) §6.1 and are marked there as
stated-from-knowledge and unverified against the published W3C Recommendation. Verify before any
conformance claim is written on a public surface.)*

**Provenance is never conveyed by styling alone.** The markdown face has no styling, so the text
glyph *is* the accessible rendering. A colored chip alone fails. A tooltip alone fails — there is
no hover on a touch device. An icon alone fails without a text alternative that names the class. A
model-inferred value rendered at the same weight as an observed one fails at the pixel and at the
token.

Agent readers are first-class: every View serves a token-efficient markdown face alongside the data
face, and both are held to the same values as the app face.

## Offer

Entry is self-serve. The CTA everywhere is **Get started**.

**The unit is a deployment, not a seat, and that is a decision rather than a default.** Three
reasons, and none is aesthetic:

1. **Per-seat pricing would re-paywall the thing worklists.dev gives away.** `complete`, `block`,
   `escalate`, `query` and `trace` are free permanently, because *you always can record what you
   did*. A worker with no seat cannot open the app and therefore cannot record — the promise would
   be true at the API and false in the hand.
2. **It would make the operator ration coverage.** A DC with 400 pickers and 60 seats deploys to
   the 60 whose work is billable, and a partial deployment produces a partial record. The product
   is that the record is complete; the pricing must not push against it.
3. **It would tax the shelter's best case.** The union, trade school or apprenticeship operator has
   the most members and the least money, and per-seat is exactly the shape that makes the
   worker-held regime unaffordable at the scale where it is the answer to *why isn't this the whip*.

A per-seat meter also requires us to hold a per-person commercial roster, which sits closer to the
no-roster boundary below than anything in this product should.

**The line is the same one barcoding.dev draws around `label`: the meter is the artifact, not the
call.** There, the built-in templates keep the loop free and the curated library is what is bought.
Here, the verbs stay free at worklists.dev — any operator may build their own app against them and
pay nothing — and **the branded, regime-bound, store-shippable app is the artifact.**

- **Free to evaluate, self-serve, no card** — an unbranded evaluation deployment against the demo
  tenant, whose events carry write-class `simulated`. It is the real app on real devices; it is not
  a slide deck and not a sandbox mock. *(Demo-is-the-product: the demo world is tenant #1 on the
  production spine.)*
- **Paid — one price per production deployment, annual, unlimited performers. $TBD.** A deployment
  is one branded build, bound to one operator, one tenant and one regime. Adding a person, a
  station, a site or a device does not change the price; adding a *brand* or a *regime* is a second
  deployment.
- **Consumption bills at the door that serves it, never marked up and never bundled** — event
  volume and retention at epcis.dev, and `barcoding.dev.interpret`, which is the one metered call
  the app can make on the critical path and which it makes only when `decode` did not yield the
  field the task needs. That is the same posted-price rule that governs every other property pair
  in the estate, and it is why a flat deployment price does not have to pretend volume is free.
- **Enterprise — bought through visibility.cloud**, whose Enterprise tier is the only unpublished
  price in the family. Many deployments under one agreement, MDM distribution, signing from the
  operator's own developer account, and the contract ceremony.

**Who pays: the operator, always.** The `*.ing.games` instances are no exception — Longtail
Holdings, LLC consumes this door at posted prices like any other operator, and a union or trade
school running an instance pays for it the same way. **The performer never pays and is never the
billable unit.**

**The model above is a ruling; the number is an experiment.** `$TBD` never publishes as-is, and the
gate on publishing is *a v0 number we are willing to change*, not the right number. Until the
pricing pass lands there is no pricing island here, because an island with no number is one a
buying agent cannot validate and would be worse than prose.

## Boundaries

The four below are **inherited verbatim from [worklists.dev](../worklists.dev/PRODUCT.md)** and
bind this app as UI invariants, not only as data rules.

- **Never computes a rate.** No duration, no per-unit-time figure, no utilization, no attainment —
  not to the worker, not to any customer, not in any export. Not "time in queue," not "picks per
  hour," not a shift progress bar, not "ahead of / behind," not a streak. **Allowed:** a count, a
  step indicator within one task, and a timestamp. Whether a per-task deadline is rendered at all
  is undecided and **v1 renders none** — a countdown is a whip in timestamp clothing, and the SLA
  clock runs server-side against the worklist and escalates on non-action.
- **No employer-facing per-person surface.** No roster, no ranking, no query returning two
  performers side by side. There is no assignee column, because every row is already the reader's
  own. Escalation targets a **role, never a person**. There is no "online now," no connected count,
  and no presence surface — a transport that can enumerate who is on shift is a roster arriving as
  an implementation detail.
- **The block is author-owned and never editable by a supervisor** — timestamped, located, private
  by default. This app goes one step further than read-only: **a non-author never receives the
  block at all.** Not greyed out, not `withheld` — absent from the frame, because for a mechanism
  whose whole value is *that wasn't me / here's what I was handed*, the existence of the block is
  part of what is private.
- **Holds no authority.** `escalate` compiles to id.org.ai's ceremony. **No surface in this family
  is permitted to be an authority-authoring UI**, and this one is not the exception.

And four that are this door's own:

- **There is no supervisor face in this app, and none will be added.** The frontline manager's
  surface is the visibility.cloud console. A supervisor who opens a deployment is a performer in it
  or is nothing in it.
- **The regime is never switchable at runtime.** No API returns it as authoritative; the field the
  performer sees displays it and is not the source of it.
- **Never our name.** No shared footer, chrome, "powered by," upstream link, analytics tag, error
  DSN or push certificate resolving to a family hostname, in any shared module or any shipped
  instance.
- **Not a spine, not a resolver, not a work API.** The events are epcis.dev's, the identity is
  id.org.ai's, the tasks are worklists.dev's. This is the face, and it invents no verb and no
  second write path.

## Stack

- [worklists.dev](../worklists.dev/PRODUCT.md): the API door this is the face of — the task, the
  verbs, and the free/paid line the critical path inherits
- [epcis.dev](../epcis.dev/PRODUCT.md): the spine the scan lands on, and the hash that closes a task
- [barcoding.dev](../barcoding.dev/PRODUCT.md): the read — detect, decode, parse, and the one
  metered call, `interpret`
- [transactions.dev](../transactions.dev/PRODUCT.md): the documents that dispatch work, and an
  agent performer's payload
- [visibility.cloud](../visibility.cloud/PRODUCT.md): the console the supervisor uses instead of
  this app, and the Enterprise rung this door does not sell
- id.org.ai: the performer's attested identity, the ceremony `escalate` compiles to — **login-only
  here, and therefore invisible to the person holding the device**
- primitives.org.ai: Task, Action, Worklist, human-in-the-loop — upstream, not rebuilt
- `@mdxld/frame`: the unstyled contract every rendered value passes through — Field, Frame, View,
  Rendering, and the face-parity assertion
- `*.ing.games`: brand projections over this implementation, operated under Longtail Holdings, LLC
  or a third-party operator — consumers at posted prices, and they point nowhere upstream
- product.md: the specification this file conforms to (Layer 1)
