API errors
Esta página aún no está disponible en español. Se muestra la versión en inglés.
When a call to the Querri API fails, the response says why with an error code. Most of the errors below also carry a doc_url that links straight to the code on this page.
The error envelope
Section titled “The error envelope”Errors come back wrapped in detail:
{ "detail": { "error": { "type": "invalid_request_error", "code": "missing_tenant_id", "message": "X-Tenant-ID header is required for API key authentication.", "doc_url": "https://docs.querri.com/api/errors#missing_tenant_id" } }}| Field | What it is |
|---|---|
type | The broad category, such as authentication_error, permission_error or rate_limit_error |
code | The specific error. Check this in your code rather than the message, which can change |
message | A readable explanation |
doc_url | A link to the code on this page. Not every error has one |
access_denied and insufficient_permission also include resource_type and resource_id. Every response carries an X-Request-Id header, so quote it when you contact support.
This page covers the codes that link here. Errors about a specific item, such as source_not_found, are listed under Error codes in the Data API guide.
Authentication
Section titled “Authentication”missing_api_key
Section titled “missing_api_key”HTTP 401, authentication_error
The request had no credentials the API recognizes. It looks for an X-Embed-Session: es_... header, then an Authorization: Bearer qk_... API key, then a user’s token in Authorization: Bearer ey... or the access_token cookie. A Bearer value that starts with anything else ends up here too.
What to do: send your API key as Authorization: Bearer qk_..., with your organization ID in X-Tenant-ID. See Authentication.
missing_tenant_id
Section titled “missing_tenant_id”HTTP 400, invalid_request_error
An API key was sent without the X-Tenant-ID header.
What to do: add X-Tenant-ID with your organization ID. It’s shown as Org ID on Settings → My Account.
invalid_api_key
Section titled “invalid_api_key”HTTP 401, authentication_error
No key with that secret exists in the organization named in X-Tenant-ID. The key is mistyped, expired or revoked, or it belongs to a different organization.
What to do: check that the key and the organization ID belong together. If the key has expired or been revoked, an admin creates a new one in Settings → API Keys.
invalid_jwt
Section titled “invalid_jwt”HTTP 401, authentication_error
Your bearer token didn’t validate. It has expired, it’s malformed or from the wrong issuer, or it’s missing the user (sub) or organization (org_id) claim.
What to do: sign in again for a fresh token (for the CLI, querri auth login). For jobs that run without a person, use an API key.
invalid_embed_session
Section titled “invalid_embed_session”HTTP 401, authentication_error
The X-Embed-Session token doesn’t match a live session: it expired, was revoked or never existed. You also get this when Querri couldn’t renew the session’s sign-in, and in that case the session is revoked.
What to do: create a new session with POST /embed/sessions. POST /embed/sessions/refresh works only while the old session still exists. See Embed sessions.
csrf_token_invalid
Section titled “csrf_token_invalid”HTTP 403, permission_error
Code running in a browser signed in to Querri tried to change something (POST, PUT, PATCH or DELETE) using the access_token cookie, and the X-CSRF-Token header was missing or didn’t match the csrf_token cookie.
What to do: set X-CSRF-Token to the value of the csrf_token cookie. See Cookie and CSRF. An integration that doesn’t run inside a Querri browser session should use an API key.
csrf_token_missing
Section titled “csrf_token_missing”HTTP 403, permission_error
It’s the same check, from Querri servers that only look for the header: X-CSRF-Token wasn’t sent with a change made using the access_token cookie.
What to do: send X-CSRF-Token, set to the value of the csrf_token cookie, with every change.
Permissions
Section titled “Permissions”ip_not_allowed
Section titled “ip_not_allowed”HTTP 403, permission_error
This key only accepts requests from the addresses on its IP allowlist, and this one came from somewhere else.
What to do: call from an address on the list. The API can create and revoke keys but can’t change one, so to allow a new address, create a key that includes it and revoke the old key.
insufficient_scope
Section titled “insufficient_scope”HTTP 403, permission_error
Your key doesn’t have the scope this endpoint needs. The message names the scope, or the scopes that would do.
What to do: use a key that has the scope, which usually means creating one. See Scopes. A user’s token gets its scopes from the user’s role, and an embed session has a fixed set. See JWT bearer tokens and Embed sessions.
access_denied
Section titled “access_denied”HTTP 403, permission_error
The identity behind the request has no access to this item. For an API key, that’s the user the key is bound to, or the person who created the key if it isn’t bound. An ID that doesn’t exist gets this error too.
What to do: check the ID first. Then share the item with that person, or use a key tied to someone who can see it. If you’re sure the access is there, retry once, because a temporary fault while checking access also comes back as this error.
insufficient_permission
Section titled “insufficient_permission”HTTP 403, permission_error
That identity can see the item but needs more access. The message names the level: editor for changes such as updating a project or adding rows to a source, and owner for deleting an item or changing who it’s shared with.
What to do: have the item shared with that person at the level the message names, or use a key tied to someone who already has it.
authorization_unavailable
Section titled “authorization_unavailable”HTTP 503, service_unavailable_error
Querri couldn’t check your access at that moment. It’s a temporary problem on Querri’s side, not a change to your permissions. The response has a Retry-After: 5 header.
What to do: wait five seconds, then retry.
Limits
Section titled “Limits”rate_limit_exceeded
Section titled “rate_limit_exceeded”HTTP 429, rate_limit_error
Too many requests in the current minute. An API key’s limit is set when the key is created, 60 a minute by default. A user’s token allows 600 a minute per user, and an embed session 600 a minute per session.
What to do: wait for the Retry-After time (60 seconds), then spread your requests out. X-RateLimit-Limit, X-RateLimit-Remaining and X-RateLimit-Reset show where you stand. The Python SDK and PHP SDK retry 429 for you. For a higher limit, create a key with a larger Rate Limit (per min).
Not available yet
Section titled “Not available yet”not_implemented
Section titled “not_implemented”HTTP 501, api_error
This endpoint exists but doesn’t work yet. These return it:
POST /dashboardsDELETE /dashboards/{dashboard_id}POST /sources/{source_id}/syncPOST /dashboards/from-templateandPOST /dashboards/{dashboard_id}/export-template, without adoc_url
What to do: nothing in the request will fix it, so leave these calls out for now. The CLI’s dashboard new, dashboard delete and source sync call these endpoints and fail the same way, as do the matching SDK methods.