Skip to main content
All Bluum API errors follow a consistent format with structured error codes for programmatic handling.

Error response format

{
  "code": "BLUM-400-001",
  "message": "Invalid quantity. Must be a positive number."
}
FieldDescription
codeStructured error code: BLUM-{HTTP_STATUS}-{SEQUENCE}
messageHuman-readable description of the error

Error code categories

PrefixHTTP StatusCategory
BLUM-400-*400 Bad RequestValidation failures, malformed requests
BLUM-401-*401 UnauthorizedAuthentication errors
BLUM-403-*403 ForbiddenAuthorization/permission errors
BLUM-404-*404 Not FoundResource doesn’t exist or not accessible
BLUM-409-*409 ConflictDuplicate resource or state conflict
BLUM-422-*422 UnprocessableBusiness rule violation
BLUM-429-*429 Too Many RequestsRate limit exceeded
BLUM-500-*500 Internal ErrorServer-side error

Common errors

Authentication (401)

CodeMessageResolution
BLUM-401-001Missing authorizationInclude Authorization: Basic <credentials> header
BLUM-401-002Malformed credentialsVerify Base64 encoding of API_KEY:API_SECRET
BLUM-401-003Invalid credentialsCheck key and secret are correct and not revoked

Validation (400)

CodeMessageResolution
BLUM-400-001Generic validation errorCheck the message for specific field issues
BLUM-400-002Missing required fieldInclude all required fields in the request
BLUM-400-003Invalid field formatMatch expected types and formats (dates as ISO 8601, etc.)

Not Found (404)

CodeMessageResolution
BLUM-404-001Resource not foundVerify the ID exists and belongs to your tenant

Rate Limiting (429)

CodeMessageResolution
BLUM-429-001Rate limit exceededImplement backoff; check Retry-After header

Rate limits

EnvironmentLimit
Sandbox10 requests/second per key pair
Production25 requests/second per key pair

Retry strategy

Implement exponential backoff with jitter for retryable errors (429, 500, 502, 503, 504):
async function requestWithRetry(url, options, maxRetries = 3) {
  for (let attempt = 0; attempt < maxRetries; attempt++) {
    const response = await fetch(url, options);

    if (response.status === 429) {
      const retryAfter = parseInt(response.headers.get('Retry-After') || '1');
      const delay = retryAfter * 1000 * Math.pow(2, attempt) + Math.random() * 1000;
      await new Promise(resolve => setTimeout(resolve, delay));
      continue;
    }

    if (response.status >= 500 && attempt < maxRetries - 1) {
      const delay = Math.pow(2, attempt) * 1000 + Math.random() * 1000;
      await new Promise(resolve => setTimeout(resolve, delay));
      continue;
    }

    return response;
  }
  throw new Error('Max retries exceeded');
}
Do not retry 400, 401, 403, 404, or 422 errors — these indicate client-side issues that won’t resolve on retry.

HTTP status codes

CodeMeaningRetryable
200Success (GET, PUT, DELETE)N/A
201Created (POST)N/A
400Bad requestNo
401UnauthorizedNo (fix credentials)
403ForbiddenNo (check permissions)
404Not foundNo
409ConflictNo (resolve conflict)
422UnprocessableNo (fix business logic)
429Rate limitedYes (with backoff)
500Server errorYes (with backoff)
See Error Code Reference for the complete catalog.