Skip to content

Error Handling

All API errors return a consistent JSON structure with a machine-readable code and human-readable message.

Error format

{
  "error": {
    "code": "auth.unauthorized",
    "message": "Invalid or missing API key"
  }
}

Error codes

StatusCodeMeaning
401auth.unauthorizedMissing or invalid API key
403auth.forbiddenKey is valid but lacks the scope, the IP is not allowlisted, or a plan limit or quota was hit
404not_foundResource does not exist
409conflictDuplicate or conflicting resource
422validation.failedRequest body failed schema validation
429rate_limit.exceededToo many requests
500internalServer error

SDK error handling

import { HelmdeskError } from '@helmdesk/sdk'

try {
  await client.tickets.get('invalid-id')
} catch (err) {
  if (err instanceof HelmdeskError) {
    console.log(err.status) // 404
    console.log(err.code)   // "not_found"
    console.log(err.message) // "Ticket not found"
  }
}

Validation errors

A 422 adds a details object keyed by field name. Each value is an array — one field can fail more than one rule:

{
  "error": {
    "code": "validation.failed",
    "message": "Validation failed",
    "details": {
      "subject": ["Required"],
      "customerEmail": ["Invalid email address"]
    }
  }
}

details is only present on 422 responses. Other errors carry just code and message.

Rate limits and quotas

Two different limits produce two different codes, and they need different handling:

LimitResponseWhat to do
100 requests/min per key429 rate_limit.exceededBack off and retry — it clears within the minute.
Plan quota (emails, log events, storage)403 auth.forbiddenRetrying will not help. The message names the limit; upgrade or wait for the monthly reset.

Warnings are not errors

A few endpoints return 200 with a warnings array — the operation succeeded, but something is worth knowing. Template import is the main one: an unresolved layout or partial warns rather than failing, so an email can send unbranded while the request looks entirely healthy. Check warnings when it is present.