Skip to content

Theseus field APIs and guard ​

Approved: 17 September 2026 (#154)

Theseus field HTTP is a write-scoped th_ token surface. It reads the same navigation snapshot, catalog, and floor map Ariadne reads, and it writes beacon pose confirm plus floor graph. It is not admin JWT, not X-Mobile-Api-Key, and not Keryx ntfy.

No Flutter in this item. Tokens already live on the customer SQLite — no operator-actions row.

Pairing mint and revoke stay in site pairing.

Auth ​

guard_theseus accepts only a live T3 field token:

  • Authorization: Bearer th_…
  • SHA-256 match in theseus_field_tokens
  • revoked_at is null

Anything else is 401, including missing auth, admin JWT, the Nav mobile key, Keryx ntfy auth, a revoked th_, and a Bearer that is not th_.

Cross-guard:

  • th_ still fails guard_admin / guard_auth (admin routes stay 403).
  • Mobile key still fails Theseus field routes (401).
  • Existing Ariadne /navigation/mobile/* guards stay unchanged.

GET /theseus/session uses the same guard_theseus function.

Routes ​

MethodPathAuth
GET/api/v1/theseus/navigation/snapshotguard_theseus
GET/api/v1/theseus/navigation/catalogguard_theseus
GET/api/v1/theseus/navigation/floor/:id/mapguard_theseus
POST/api/v1/theseus/beacons/:id/confirmguard_theseus
POST/api/v1/theseus/floor/:id/graphguard_theseus

Reads share navigation_bundle_build, the catalog SHA list, and the floor map file resolve with Ariadne. Paths and guard differ.

Beacon confirm is a narrow UPDATE (x, y, optional mac). It does not run replace-device or asset_uid mint. If mac is omitted, the current MAC stays. If mac is provided and another beacon already owns it, 400.

Graph save uses the same body (FloorGraphSaveRequestSchema) and SQL as admin POST /floor/:id/graph.

Flutter reads are map picker. Pose write from a phone is BLE confirm. Graph write from a phone is route authoring.

Non-goals ​

FCM, staff ntfy, safecall-ops, hospital rasters / mar.json.