Base URL (local dev): http://localhost:3000. All request/response bodies are JSON except where noted (image uploads use multipart/form-data).

Auth

Two independent subject types, never mixed sessions:
  • ConsumerPOST /auth/otp/request / POST /auth/otp/verify → JWT access token + opaque refresh token.
  • OperatorPOST /auth/operator/login (admin-issued credentials only, no self-registration) → same token shape, plus a mustResetPassword flag enforced server-side on every other operator endpoint until cleared via POST /auth/operator/set-password.
Every protected endpoint expects Authorization: Bearer <accessToken>.

Error shape

Every error response is { "error": "<stable_code>", "message": "<human text>" }, sometimes with a details object. Distinct-outcome endpoints (verify-face, /identify, /verify/self) also echo the code as outcome in the body, e.g.:

Modules