Errors
How the Quotometry APIs report problems: one problem document shape, stable codes, and the difference between a failed request and an unpriceable part.
This page explains how the buyer API and the merchant API report problems, and how your integration should respond to each kind. Read it before you write error handling: a line that needs review is a normal answer, not an error, and the two must be handled differently.
The problem document
Every non-2xx response is an RFC 9457 problem document with the media type application/problem+json:
{
"type": "https://docs.quotometry.app/errors#invalid_request",
"title": "Request is not valid",
"status": 422,
"code": "invalid_request",
"issues": [
{ "path": "machines[0].params.travel_factor", "code": "out_of_range", "severity": "error",
"message": "must be between 0 and 1" }
]
}
| Field | Type | Always present | Description |
|---|---|---|---|
type | string | Yes | A stable identifier for the code, not the address of this page. |
title | string | Yes | A short, human-readable summary. Prose: do not match on it. |
status | integer | Yes | The HTTP status, repeated. |
code | string | Yes | The stable wire name. Match on this. It never changes. |
detail | string | No | More about this occurrence, for example which plan feature was refused. Prose. |
issues | array | No | Field-level problems, each with path, code, severity and message. path uses the same syntax as the console. |
incident_id | string | No | Present on a 500. Quote it when you contact support. |
A 500 response carries an incident_id and nothing else about the failure. The detail is in our logs, not in a
response a stranger can read.
Three kinds of “no”
It matters which one you are looking at.
A failed request is a 4xx or 5xx response with a problem document: you sent something the API cannot act
on, you are not allowed to do it, or you asked too often.
An unpriceable line is a 200 response. The call succeeded, but the line has a state of review or
blocked, and its reasons explain why: oversize, no_compatible_machine, over_review_qty, a DFM code and so
on. This is the normal way a shop says “we need to look at this one”.
A DFM verdict is advice attached to a part: a thin wall, an unsupported overhang, a tiny hole. Depending on the shop’s rules it may only inform the buyer, add a charge, block the line or send it to review.
Common codes
The codes you will meet most often while integrating:
| Code | Status | Meaning | What to do |
|---|---|---|---|
unauthorized | 401 | The key or session is missing or not valid. | Check the key you send. |
forbidden | 403 | The credential is valid but not for this. detail says why, for example origin not allowed for this widget. | For an origin, add the page’s origin to the widget’s allowed origins. |
plan_forbids | 403 | Your plan does not include this (merchant API). detail names what. | Change plan, or remove what goes over it. |
not_found | 404 | The id is wrong, or belongs to another shop. | Check the id. |
invalid_request | 422 | The request failed validation. | Read issues; each has a path. |
rate_limited | 429 | A rate limit refused the call. | Wait Retry-After seconds. See rate limits. |
stale_etag | 412 | Someone else saved the draft first (merchant API). | Read the draft again and re-apply your change. |
quote_expired | 409 | The quote’s validity period has ended. | Price again and save a new quote. |
price_changed | 409 | The configuration was republished between the quote and the order. | Show the new price and ask the buyer to confirm. |
file_not_ready | 409 | The file’s upload has not completed (merchant API file download). | Try again once the upload has completed. |
file_purged | 409 | Retention has removed the file. | The buyer must upload it again. |
too_large | 413 | The body or file is larger than the endpoint accepts. | Send a smaller file. |
Why price_changed exists
When an order is placed, Quotometry checks that the quote’s price still stands. If the shop republished its configuration in between, the API refuses the order rather than quietly charging a different amount from the one the buyer agreed to.
The full registry
Every issue code, line-state reason, DFM code, breakdown line id, problem code and event type is kept in one file
in the repository, because these names are a contract and a contract needs one home:
docs/agent-docs/api/errors.md.
Next steps
- Rate limits: what to do with a
429. - Versioning and changelog: why codes never change.
- DFM rules: what each DFM check looks for.
- Cart recipes: handling
price_changedat checkout.