Accounts

Create account-bootstrap session

Create an account-bootstrap session for agent-driven onboarding. Public endpoint (rate limited: 15/min per IP, plus a per-identity budget of 3/hour for the email and SMS channels that no amount of IP rotation avoids).

The session is ALWAYS tagged type="account_creation". It does NOT branch on whether the submitted identity already maps to a User — the response is uniform by design, because a differing shape or timing would answer "does this address have an account here?" to anyone who asks. Completing verification transparently creates a User when none exists or signs the existing one in; an agent that needs to tell those apart calls GET /auth/me afterwards and reads created_at.

THE EMAIL CHANNEL SENDS NOTHING HERE (email_sent: false, send_required: true). Delivering a message from our domain to an address nobody has proven is a separate, explicit act: POST /api/v1/accounts/{id}/send. The other channels are inbound — the user messages us (reverse OTP) — so nothing is dispatched to them at all.

No credential is required. A client that DOES present an API key (Authorization: Bearer pk_…) has it checked: a key the API no longer accepts is refused with 401 invalid_api_key before anything is stored, and a live one is recorded so the session issued on completion is BOUND to it — revoking the key by any path ends that session.

post/api/v1/accounts

Request

  • Base URL: https://api.proof.holdings
  • URL: https://api.proof.holdings/api/v1/accounts
  • Auth: none declared

Request body

channel'telegram' | 'whatsapp' | 'sms' | 'email' required

Authentication channel

phone_numberstring

Required for SMS channel to determine DID routing.

emailstring email

Required for email channel.

Example request

{
  "channel": "telegram",
  "phone_number": "+37069199199",
  "email": "alex@example.com"
}

Response

Account session created

idstring required
type'account_creation' | 'login' required

Outcome of an account-session creation. account_creation means a new User will be written on verification. login indicates the submitted identity matched an existing User and the session will log them in.

channel'telegram' | 'whatsapp' | 'sms' | 'email' required

Authentication channel

status'pending' | 'verified' | 'expired' required

Status of an auth session

deep_linkstring
qr_codestring

Base64-encoded PNG QR code for the deep link

qr_textstring

UTF-8 text QR for terminal/agent rendering

sms_codestring

Short code for SMS-channel reverse-OTP

sms_messagestring
emailstring
email_sentboolean
email_errorstring
expires_atstring date-time required
instructionsstring
verified_atstring date-time
user_idstring
created_atstring date-time

Example response

{
  "id": "auth_9c2f...",
  "type": "account_creation",
  "channel": "telegram",
  "status": "pending",
  "deep_link": "https://t.me/bot?start=auth_9c2f...",
  "expires_at": "2026-04-16T20:10:00Z"
}

Changes

No recorded changes to this operation across all 1 revision of this API.