Every example on this page is synthetic and runs against the sandbox environment only. Endpoints, headers, and payload shapes match the real API in this codebase (openapi.verify.v1.yaml and app/api/v1/verify/**) -- none of it is imaginary.
1. Sign up and create a sandbox project (Cloud dashboard). 2. Create a sandbox credential. 3. Create a verification session. 4. Complete it deterministically. 5. Read the result. No real document or face capture is required for any of this.
openapi.verify.v1.yaml documents a Bearer server-secret credential. The version running in this repository today is alpha/fixture tenant resolution -- it requires a bearer token to be present and four explicit fixture headers identifying the tenant. Verifying a real presented secret against a stored credential hash (rather than trusting caller-supplied headers) is a real, scoped, non-blocking follow-up, documented as a gap, not hidden.
Authorization: Bearer <your-sandbox-secret>
x-uv-fixture-organization-id: org_...
x-uv-fixture-project-id: proj_...
x-uv-fixture-environment-id: sandbox
x-uv-fixture-account-id: acct_...POST /api/v1/verify/verification-sessions
Idempotency-Key: <16-255 char unique key>
Content-Type: application/json
{
"subject_reference": "synthetic_user_001",
"template": "identity_basic",
"sandbox_scenario": "IDENTITY_PASS"
}
--> 201
{
"id": "vs_...",
"status": "CREATED",
"environment": "SANDBOX",
"synthetic": true,
"created_at": "2026-01-01T00:00:00.000Z",
"expires_at": null
}Issue a short-lived client token scoped to one session, then complete the session deterministically -- the sandbox has no real capture UI to redirect to, so completion is a direct API call.
POST /api/v1/verify/verification-sessions/{id}/client-token
Idempotency-Key: <key>
--> 201
{
"token": "uv_ct_...",
"verification_id": "vs_...",
"hosted_flow_url": "https://api.unitedvaluta.example/hosted/uv_ct_...",
"expires_at": "2026-01-01T00:15:00.000Z",
"environment": "SANDBOX",
"synthetic": true
}
POST /api/v1/verify/verification-sessions/{id}/complete
Idempotency-Key: <key>
--> 200 { "id": "vs_...", "status": "VERIFIED", ... }GET /api/v1/verify/verification-sessions/{id}/result
--> 200
{
"verification_id": "vs_...",
"status": "VERIFIED",
"subject_reference": "synthetic_user_001",
"checks": [{ "type": "IDENTITY_PASS", "status": "PASS", "reason_codes": [] }],
"review_state": "NOT_REQUIRED",
"completed_at": "2026-01-01T00:00:01.000Z",
"reason_codes": [],
"environment": "SANDBOX",
"synthetic": true
}
--> 503 if the session hasn't completed yet (PROVIDER_UNAVAILABLE, retryable: true)GET .../checks and GET .../attempts return the individual checks and capture attempts behind a result, for building a detailed review UI.
Register an endpoint; the response includes a signing secret exactly once. Verify the t={timestamp},v1={hex-hmac-sha256} header constant-time and reject anything outside a 300-second window.
POST /api/v1/verify/webhook-endpoints
Idempotency-Key: <key>
{ "url": "https://example.com/hooks/verify" }
--> 201
{ "id": "whep_...", "url": "https://example.com/hooks/verify",
"environment": "SANDBOX", "synthetic": true,
"signing_secret": "uv_whsec_..." } // shown exactly onceTwelve named, deterministic scenarios are available -- see Identity for the full list. Every sandbox event is metered but explicitly non-billable.
Session creation and completion both require an Idempotency-Key header (16-255 characters). A retried request with the same key and the same payload returns the original result; the same key with a different payload returns IDEMPOTENCY_CONFLICT.
{
"code": "PERMISSION_DENIED",
"message": "The requested resource does not belong to the authenticated tenant.",
"request_id": "req_...",
"correlation_id": "verify_...",
"retryable": false
}Codes: INVALID_REQUEST, AUTHENTICATION_REQUIRED, PERMISSION_DENIED, PROJECT_NOT_FOUND, CAPABILITY_NOT_CONFIGURED, SESSION_EXPIRED, PROVIDER_UNAVAILABLE, RATE_LIMITED, IDEMPOTENCY_CONFLICT, EVIDENCE_REJECTED, REVIEW_REQUIRED, REGION_UNAVAILABLE, INTERNAL_ERROR.
See Security for exactly what has and hasn't been tested. No formal review has passed yet.
Sandbox data is entirely synthetic -- no real document, face, or biometric data is ever accepted by anything documented here. Evidence access, retention, and deletion workflows for a real production flow are a design-stage gap, not yet built.
See Pricing. Sandbox usage is metered and free; production pricing is not decided.
2026-08-16 -- Sandbox verification-session lifecycle, webhooks, client tokens, and usage summary endpoints implemented and tested end-to-end for the first time.