Error codes

Errors Arkyc deliberately raises carry a stable, machine-readable error key alongside the HTTP status.

error envelope
{
  "status": "error",
  "code": 401,
  "error": "session_expired",
  "message": "Session expired"
}

This disambiguates cases that share an HTTP status: a 401 could be an expired session, a bad client token, or an invalid API key.

Catalog

errorHTTPMeaning
missing_client_token401No client token on a Client/Widget API request.
invalid_client_token401The client token doesn't resolve to a session.
session_expired401The session (and its client token) has expired.
missing_api_key401No secret key on a Public Project API request.
invalid_api_key401The secret key is unknown, revoked, or expired.
invalid_workflow422workflow_id is unknown for this organization.
invalid_webhook422The referenced webhook endpoint is unknown or invalid.

Responses without an error key are unexpected/unhandled; treat them generically by status. Only the keys above are part of this contract.

Reading the key from a client

Both typed clients surface the key, typed as the ApiErrorKey union so your editor autocompletes every case and flags a typo. The server SDK throws an ArkycApiError with err.error; the widget passes a WidgetApiError with err.error to onError. Both re-export the ApiErrorKey type.

branch on the key
import { ArkycApiError } from '@arkyc/sdk'

try {
  await arkyc.sessions.create({ userReference, workflowId })
} catch (err) {
  if (err instanceof ArkycApiError) {
    if (err.error === 'invalid_api_key') return rotateKey()
    if (err.error === 'invalid_workflow') return useDefaultWorkflow()
    // no `error` key → unexpected; handle by err.status
  }
}