FaceCard Docs

Errors

The error format and every error code the FaceCard API returns.

Every error response is JSON with a correct HTTP status:

{ "error": { "code": "snake_case_code", "message": "Human readable text." } }

Branch on code, not on message. The message can change. Some errors add fields next to code and message; those are listed below.

Codes

StatusCodeMeaningWhat to do
400invalid_requestThe request is malformed: a field is missing or has the wrong type, a descriptor does not have exactly 128 finite numbers, or a query value is out of range.Fix the request. The message names the field.
400invalid_jsonThe body is not valid JSON.Send valid JSON with Content-Type: application/json.
400consent_requiredEnrollment without consent.accepted: true.Show your privacy notice and get consent first.
400challenge_invalidThe challenge is missing, expired, already used or belongs to another app.Request a new challenge and retry.
400invalid_codeThe email change confirmation code is wrong or expired (15 minutes).Start the email change again.
401unauthorizedThe credential is missing, invalid, revoked or expired.Check the key or token. A user token lasts one hour.
401no_matchNo enrolled face matched clearly enough.Let the user retry in better light. The response carries no candidate data.
403forbiddenThis credential cannot call this route, for example a publishable key on /v1/users.Use the right credential for the route.
403origin_not_allowedThe request Origin is not on the app's allow list.Add the exact origin in the portal.
403plan_limit_reachedYou hit a plan count limit such as the number of apps or keys. Includes limit and used.Remove something or upgrade your plan.
404not_foundThe user or resource does not exist in this app.Check the id.
409email_takenThe email already exists in this app.Use a different email, or sign the user in instead.
409face_already_enrolledThe face matches an existing user in this app. The response never names that user.Sign in as the existing user.
413payload_too_largeThe body is over the limit (256 KB on /v1/enroll).Send fewer descriptors.
429plan_limit_reachedThe team used all its auths for the month. Includes limit, used and resets_at.Wait until resets_at or upgrade.
429rate_limitedToo many requests. A Retry-After header gives the seconds to wait.Back off and retry.
500internal_errorA fault on our side. The response contains no details.Retry. If it persists, contact support with the time of the call.
503noneGET /health reports db: "down".Retry later.

Rate limit and plan limit examples

{
  "error": {
    "code": "plan_limit_reached",
    "message": "Monthly auth limit reached.",
    "limit": 1000,
    "used": 1000,
    "resets_at": "2026-11-01T00:00:00.000Z"
  }
}

plan_limit_reached uses two statuses. An exhausted monthly auth allowance is 429. A count limit (number of apps or keys per plan) is 403. See Plans and limits.

In the SDK

SDK calls throw FaceCardError. It has the same code and the HTTP status. See FaceCardError.

On this page