Skip to main content

Error Response Format

All errors follow a consistent format with an optional hint field that provides actionable guidance:
{
  "error": {
    "code": "NOT_FOUND",
    "message": "Event not found: abc-123",
    "hint": "Check that the event ID is correct and belongs to your organization.",
    "details": []
  },
  "requestId": "req_a1b2c3d4e5f6"
}
The requestId is unique per request — include it in support tickets for faster debugging.

Error Codes

CodeHTTP StatusDescriptionCommon Cause
VALIDATION_ERROR400Input failed validationMissing required fields, invalid format
UNAUTHORIZED401Authentication failedMissing/invalid/expired API key
FORBIDDEN403Not allowedMissing scope, IP not in allowlist
SCOPE_REQUIRED403Specific scope neededKey lacks the required scope
NOT_FOUND404Resource not foundWrong ID, or resource belongs to another org
RATE_LIMITED429Too many requestsExceeded rate limit for your tier
INTERNAL_ERROR500Server errorTransient failure — retry with backoff

The Hint System

Error responses include a hint field with a human-readable suggestion for how to resolve the issue. Hints are tailored to the specific error context.
{
  "error": {
    "code": "VALIDATION_ERROR",
    "message": "Validation failed",
    "hint": "The 'dateTime' field must be a valid ISO 8601 date string (e.g., '2025-06-15T18:00:00.000Z').",
    "details": [
      { "field": "name", "message": "name should not be empty" },
      { "field": "dateTime", "message": "dateTime must be a valid ISO 8601 date string" }
    ]
  },
  "requestId": "req_x1y2z3"
}
{
  "error": {
    "code": "SCOPE_REQUIRED",
    "message": "This endpoint requires the 'events:write' scope.",
    "hint": "Update your API key's scopes in the Organizer Dashboard under Settings > API Keys, or create a new key with 'events:write' enabled."
  },
  "requestId": "req_a1b2c3"
}
{
  "error": {
    "code": "NOT_FOUND",
    "message": "Event not found: abc-123",
    "hint": "Check that the event ID is correct and belongs to your organization. Use tn.events.list() to see your events."
  },
  "requestId": "req_d4e5f6"
}
{
  "error": {
    "code": "RATE_LIMITED",
    "message": "Rate limit exceeded",
    "hint": "You have exceeded 60 requests per minute. Wait until the X-RateLimit-Reset timestamp before retrying. Consider upgrading to a higher tier for increased limits."
  },
  "requestId": "req_g7h8i9"
}

Validation Errors

When the code is VALIDATION_ERROR, the details array contains field-level information:
{
  "error": {
    "code": "VALIDATION_ERROR",
    "message": "Validation failed",
    "hint": "Fix the fields listed in 'details' and retry your request.",
    "details": [
      { "field": "name", "message": "name should not be empty" },
      { "field": "dateTime", "message": "dateTime must be a valid ISO 8601 date string" }
    ]
  },
  "requestId": "req_x1y2z3"
}

SDK Error Handling

The SDK throws typed TicketnationError instances with all fields including hint:
import { TicketnationError } from 'ticketnation-sdk';

try {
  await tn.events.create({ name: '' });
} catch (error) {
  if (error instanceof TicketnationError) {
    console.log(`Code: ${error.code}`);         // 'VALIDATION_ERROR'
    console.log(`Status: ${error.status}`);     // 400
    console.log(`Message: ${error.message}`);   // 'Validation failed'
    console.log(`Hint: ${error.hint}`);         // 'Fix the fields listed in...'
    console.log(`Request ID: ${error.requestId}`);
    console.log(`Details:`, error.details);     // [{ field: 'name', message: '...' }]
  }
}

Complete Error Handler Example

import { TicketnationError } from 'ticketnation-sdk';

async function safeCreateEvent(params: CreateEventParams) {
  try {
    return await tn.events.createAndPublish(params);
  } catch (error) {
    if (!(error instanceof TicketnationError)) {
      throw error; // Not a Ticketnation error
    }

    switch (error.code) {
      case 'VALIDATION_ERROR':
        console.error('Fix these fields:', error.details);
        if (error.hint) console.error('Hint:', error.hint);
        break;

      case 'UNAUTHORIZED':
        console.error('Check your API key');
        if (error.hint) console.error('Hint:', error.hint);
        break;

      case 'SCOPE_REQUIRED':
        console.error('Missing scope:', error.message);
        if (error.hint) console.error('Hint:', error.hint);
        break;

      case 'RATE_LIMITED':
        console.error('Slow down — retry after a pause');
        if (error.hint) console.error('Hint:', error.hint);
        break;

      case 'NOT_FOUND':
        console.error('Resource not found:', error.message);
        if (error.hint) console.error('Hint:', error.hint);
        break;

      case 'TIMEOUT':
        console.error('Request timed out — retry');
        break;

      case 'NETWORK_ERROR':
        console.error('Check your internet connection');
        break;

      default:
        console.error(`${error.code}: ${error.message}`);
        if (error.hint) console.error('Hint:', error.hint);
    }

    return null;
  }
}

TicketnationError Properties

PropertyTypeDescription
codestringError code (e.g., VALIDATION_ERROR, NOT_FOUND)
statusnumberHTTP status code (0 for client-side errors like TIMEOUT)
messagestringHuman-readable error message
requestIdstringUnique request identifier for support
detailsarrayField-level errors (for VALIDATION_ERROR)
hintstringActionable suggestion for resolving the error

SDK-Only Error Codes

These codes are generated by the SDK itself, not the API:
CodeStatusDescriptionFix
TIMEOUT0Request exceeded the configured timeoutIncrease timeout in config, or check network
NETWORK_ERROR0DNS/connection failureVerify baseUrl is reachable
HTTP_ERRORvariesServer returned error with no parseable bodyTransient — retry

Automatic Retries

The SDK automatically retries on 5xx server errors with exponential backoff:
  • Attempt 1: immediate
  • Attempt 2: after 1 second
  • Attempt 3: after 2 seconds
Not retried: 4xx errors (400, 401, 403, 404, 429) — these are client errors that need to be fixed. Configure retries:
const tn = new Ticketnation({
  apiKey: '...',
  retries: 3,   // max retry attempts (default: 2)
});

Rate Limit Headers

Every response includes rate limit information:
HeaderDescription
X-RateLimit-LimitMax requests for your tier
X-RateLimit-RemainingRequests remaining in current window
X-RateLimit-ResetUnix timestamp when the window resets
When you hit the limit, the response is 429 with a RATE_LIMITED error. Wait until X-RateLimit-Reset before retrying.

Troubleshooting

  • Verify your API key is correct and not expired
  • Check the api-key header name (not Authorization)
  • Ensure the key has not been deleted from the dashboard
  • Check which scope the endpoint needs (see API Reference)
  • Performers, schedules, and brands require events:write
  • Update your API key’s scopes in the dashboard, or create a new key with the required scopes
  • Check the error.hint for specific guidance
  • Events/tickets are scoped to your organization — you can only access resources owned by the org associated with your API key
  • Double-check the UUID format
  • Use tn.events.list() to list your events and verify the ID
  • Default timeout is 30 seconds — increase it if needed
  • Check if baseUrl is correct (no trailing slash)
  • For local development, use http://localhost:4000
  • These resources require the events:write scope
  • Create a new API key with events:write enabled if your current key does not have it