Skip to content
Documentation sections

Keys and environments

Every request carries your key in the X-Api-Key header. The key identifies your account and its environment: a sandbox key only works in the sandbox and a production key only in production.

Where your key is

  1. Log in to the account of the environment you'll use: sandbox-app.facturadigital.com.mx for tests or app.facturadigital.com.mx for production.
  2. Go to Configuración › API y desarrolladores.
  3. Copy the Llave vigente (current key) as shown. It's already in the format the header expects.

That screen also shows the Llave anterior (previous key), the format older integrations used. It works until June 30, 2027; while you use it, every response carries the X-FD-ApiKey-Deprecation header with the cutoff date. Move your integration to the current key before then.

How to send it

In the X-Api-Key header of every request. There's nothing to sign and no token to request first. POST requests send their body as a form (application/x-www-form-urlencoded), except stampxmlfile, which sends a file.

curl -sS "https://sandbox-app.facturadigital.com.mx/api/v5/account/balance" \
  -H "X-Api-Key: $FD_API_KEY"

Sandbox and production

SandboxProduction
Base URLhttps://sandbox-app.facturadigital.com.mx/api/v5https://app.facturadigital.com.mx/api/v5
AccountSign up in the sandboxSign up in production
StampingWith a test provider; CFDIs have no tax validity and never reach the SAT.Valid with the SAT.
CostFree.Each stamped CFDI uses 1 folio. Cancelling uses no folio.

They're two separate accounts, each with its own data, folios and keys. Nothing you do in the sandbox touches your production CFDIs. To go live you change the base URL and the key; the code stays the same.

If the key doesn't work

All of these respond HTTP 400 with code 501. The end of the message names the environment that answered, for example [Environment: SANDBOX].

messageWhat's going on
Invalid X-API-Key. Please make sure you're passing the X-API-Key in the Header…The header is missing, the key is incomplete or it doesn't exist in that environment. The usual cause is a production key against the sandbox or the other way around: compare the environment at the end of the message with your key's.
This API Key belongs to PRODUCTION and you are calling SANDBOX…Your current key belongs to the other environment. Use the key of the account in the environment you're calling.
Your legacy API Key expired on 2027-07-01…You're using the previous key after its cutoff. Switch to the current key.

Your folio balance

GET/account/balance

Returns the available folios of the key's account. It's the simplest request to confirm the key and the URL belong to the same environment.

200
{
  "message": "10 credits available.",
  "balance": 10,
  "code": 200
}

Get the key through the API

GET/account/authorize

If your system needs to read the key without opening the screen, account/authorize returns it in exchange for the platform username and password, in the API-USUARIO and API-PASSWORD headers. Call it only from your server and over HTTPS: the password travels with it.

200 response

x_api_key_v2string
The current key. This is the one to use.
x_api_keystring
The previous key until its cutoff; after the cutoff it returns the current key too.
accountobject
Account details: company, rfc, username, contact, email, active and last_seen.

With a wrong username or password it responds HTTP 401 with code 502. After several failed attempts from the same IP it responds HTTP 403 with code 503 until the block wears off.

Checked against the production API v5 on 2026-11-03.