Product and API guide

Errors

Errors come back as RFC 9457 problem+json. Every response carries a correlationId; quote it when you contact support.

Status Meaning What to do
401Key missing or invalidCheck the X-PDFgine-Key header and that the key has not been revoked.
402Quota exhaustedUpgrade the plan or wait for the period to renew.
404Template or document not foundVerify the template code and that it has a published revision.
429Rate limit exceededWait the number of seconds in the Retry-After header, then retry.

Rate limits come with the plan

The per-minute and hourly ceilings on the generation endpoints are per TENANT and come from your plan; the table below lists them. Because the ceiling counts per tenant rather than per key, adding a second API key does not raise it. A 429 response names the window you hit in the X-PDFgine-RateLimit-Scope header: tenant-api, tenant-render-minute or tenant-render-hour. For bulk work, send up to 100 documents in one /document-batches request instead of one document per request.

The response when the quota is exhausted
HTTP/1.1 402 Payment Required
X-PDFgine-Quota-Remaining: 0
X-PDFgine-Metering-Basis: pdf-equivalent

{
  "title": "Page quota exceeded",
  "status": 402,
  "detail": "Your plan has used up its available page quota.",
  "correlationId": "114249cb1dbc52a29026ab2eca5c4b72"
}

Retry-After and the window

Two ceilings apply, one after the other. The first protects the service and counts per credential: 30 requests per window without a key, 120 with one, over a 60 second window. The second comes from your plan and counts per tenant.

Plan Documents / minute Documents / hour
Free15150
Go30300
Pro60600
Max3003,000
HTTP 429
HTTP/1.1 429 Too Many Requests
Retry-After: 60
X-PDFgine-RateLimit-Scope: tenant-render-minute

{
  "title": "Too many requests",
  "status": 429,
  "detail": "The request limit was exceeded. Please try again later.",
  "correlationId": "505aac87e234a7b4669e6203ac7ffcd5"
}

The window is fixed, not sliding: it opens on the first request and every request inside it counts against the same allowance, then the count resets. Retry-After is the number of seconds left in that window - waiting exactly that long is enough, and retrying sooner only spends another refusal.

What usually goes wrong

  • A 4xx repeated unchanged fails again. These say the request is wrong, not that the service is busy; only 429 and 5xx are worth retrying.
  • On 429 the answer already carries Retry-After. Backing off by your own guess either wastes time or walks straight into the next refusal.
  • 402 is not a fault to page someone about at three in the morning. It means the month is spent; watch X-PDFgine-Quota-Remaining and raise the plan before it happens.
  • 410 on a download is not a lost file. Retention ended: the document was produced, counted and then removed on the schedule your plan sets.
  • Logging only the status code makes a support request a guessing game. Log correlationId with it; that one value finds the request.