# The APIs — four narrow doors, one layer that composes them

Each .dev door does one thing completely, and you can use it now without talking to anyone. visibility.cloud is the layer above them, where they compose into one record you can ask questions of, and it is the only surface in the family that carries a contract.

**Probed 2026-08-06.** Every status code below was read from a terminal on that date. Where a door does not answer, the row says so with the code it actually returned. No conformance attestation has ever been issued, and none is claimed.

## Why four doors and not one

A door that does one thing can be understood in an afternoon, priced on one page and called without a sales conversation. That is the design of the .dev layer: one developer service each, self-serve throughout.

What one narrow door cannot do is answer a question that crosses all four — which lot went out on which pallet under which purchase order, and who touched it. That needs the barcode read, the event, the paperwork and the task in one place. A rollup across sources exists at no other layer, and it is only possible because the four doors write one record instead of four.

## The four doors

### barcoding.dev — the barcode layer

It reads and writes identity on the symbol — GS1, VIN, ISBN, UDI, NDC, SSCC — and names the source and licence on every answer.

POST, JSON body {"payload":"…"}. No key, no account.

| Verb | Code | What it answers |
| --- | --- | --- |
| resolve | 200 | any identifier-bearing string → scheme, canonical form, parsed fields |
| verify | 200 | check digit, structure and prefix legitimacy, from pinned tables |
| generate | 200 | the write-side twin of resolve — id + AI map → element string, Digital Link URI, rendered symbol |
| serialize | 200 | one serial, derived from the request with no stored counter |
| pins | 200 | the pinned artifact and data-source digests |
| version | 200 | package, engine-core and pin-set versions |
| decode | 400 | a frame → what the barcode says; it takes an image, so an identifier string is refused in its own vocabulary |

label · enrich · bridge · hierarchy · party are designed and are not built: each returned 404 on 2026-08-06, and this page claims nothing else about them.

On your machine: npx barcoding.dev@0.1.0 (MIT). Its stdio MCP door served 4 tools when handshaked on 2026-08-06 — resolve, verify, generate, pins — every one annotated readOnlyHint.

### epcis.dev — the event engine

It is the spine: every event validated against GS1's pinned official schema, stamped at the door, hashed by the standard's own hash, append-only.

POST, on the apex, no key. The stateful half runs on api.epcis.dev and takes a capture key.

| Verb | Code | What it answers |
| --- | --- | --- |
| translate | 200 | EPCIS 1.1/1.2 XML → 2.0 JSON-LD with a per-job fidelity report |
| validate | 200 | a verdict against the sha256-pinned official GS1 EPCIS 2.0 schema |
| hash | 200 | the CBV 2.0 §8.9 event hash, as an ni:///sha-256 URI |
| events | 200 | the keyless demo collection — clearly-labeled seed records, not your data |
| capture | 401 | the write door on api.epcis.dev — the code is what a call with no key gets |
| events | 401 | the query door on api.epcis.dev — the code is what a call with no key gets |
| mcp | 401 | the agent door on api.epcis.dev — the code is what a call with no key gets |

On your machine: npx epcis.dev@0.2.0 (MIT). Its stdio MCP door served 6 tools when handshaked on 2026-08-06 — capture, query, get_event, trace, translate, seed — all but capture annotated readOnlyHint.

### transactions.dev — the paperwork layer

Purchase orders, ASNs and invoices — X12, EDIFACT or API-native — compiled onto the same event record in the standard's own vocabulary.

It runs where you run it: a CLI, an MCP server and an SDK in one MIT-licensed package. Over HTTP the origin serves the pages and answers 405 on the verbs.

| Verb | Code | What it answers |
| --- | --- | --- |
| join | 405 | the document and the events it covers, matched |
| reconcile | 405 | what was ordered against what actually moved |

On your machine: npx transactions.dev@0.2.0 (MIT). Its stdio MCP door served 6 tools when handshaked on 2026-08-06 — parse, validate, ack, intake, join, reconcile — every one annotated readOnlyHint.

### worklists.dev — the work layer

A task is the causal parent of the events that satisfy it, so the record reads this was scanned because this task said to — and complete takes an event hash rather than a boolean.

That origin serves static bytes. It publishes no OpenAPI description and no capability card, and says why in its own llms.txt: it answers no verb over HTTP, and a machine face describing a door that does not answer would be a fabricated one.

| Verb | Code | What it answers |
| --- | --- | --- |
| / | 200 | the door, and its markdown twin |
| /openapi.json | 404 | absent, deliberately — a description of a door that does not answer would be a fabricated one |
| /.well-known/agents.json | 404 | absent for the same reason, and probed rather than asserted |

There is no package on the registry for this door on 2026-08-06.


## This origin's own surface

| Address | Code | What it answers |
| --- | --- | --- |
| GET /limits | 200 | the rate and size limits, as a document an agent can plan against |
| POST /waitlist | 303 | the address door; it answers a redirect, by design |
| POST /flow | 303 | the interview, machine-callable |
| GET /.well-known/agents.json | 200 | the capability card |
| GET /openapi.json | 200 | the description |
| GET /pricing | 200 | what costs money, in what unit |
| GET /traces | 200 | the answer this surface sells, described |
| GET /family.json | 200 | the four doors as typed edges |

Everything this layer holds will be readable as Apache Iceberg, and it will federate the Iceberg tables you already have rather than asking you to copy them here. That write path is an open entry on /what-ships-today.

## For agents

/apis/index.md — this page as markdown. /family.json — the doors as typed edges. Two of them answer on an origin that is not the one the name suggests (api.epcis.dev, api.barcoding.dev), so each carries an “api” edge naming where it actually answers; the other two carry none, because neither answers a verb over HTTP. The doors' own machine faces are theirs to serve and are addressed, never restated: a capability card copied to a second origin goes stale silently.
