Catálogos

Clientes

Alta, búsqueda y actualización de los receptores de tus CFDI.

Un CFDI de ingreso necesita un receptor registrado. En Facty ese receptor es un cliente, y el clientId que devuelve esta API es lo que mandas al timbrar.

Listar y buscar

GET /api/authenticated/{org}/clients

Scope: clients.read

ParámetroTipoDescripción
qstringBusca en RFC y razón social, sin distinguir mayúsculas. Máx. 100 caracteres.
limitnúmero1–500. Default 50.
cursorcuidId del último elemento de la página anterior.
curl -s "$FACTY_HOST/api/authenticated/$FACTY_ORG/clients?q=acme&limit=20" \
  -H "X-API-Key: $FACTY_KEY" | jq
{
  "items": [
    {
      "id": "clx9aa3k80000abcd1234efgh",
      "rfc": "ACM980101ABC",
      "legalName": "ACME SA DE CV",
      "email": "facturas@acme.mx",
      "cp": "06600",
      "regimenFiscal": "601",
      "usoCfdiDefault": "G03",
      "createdAt": "2026-03-11T15:22:04.000Z"
    }
  ],
  "nextCursor": null
}

Para resolver un RFC exacto antes de timbrar, ?q= con el RFC completo es suficiente; verifica de todos modos el rfc de la fila que uses.

Crear

POST /api/authenticated/{org}/clients

Scope: clients.create

CampoRequeridoReglas
rfc12 (moral) o 13 (física) caracteres. Se normaliza a mayúsculas.
legalNameRazón social como está en la Constancia de Situación Fiscal: sin el régimen de capital, sin puntos. 2–255 caracteres.
cprecomendado5 dígitos. Es el domicilio fiscal del receptor; el SAT lo valida contra su padrón.
regimenFiscalrecomendadoClave de 3 dígitos de c_RegimenFiscal.
usoCfdiDefaultnoClave de c_UsoCFDI que se usará si el timbrado no manda usoCfdi.
emailnoPara el envío del CFDI por correo.
upsertnoVer abajo.
curl -s -X POST "$FACTY_HOST/api/authenticated/$FACTY_ORG/clients" \
  -H "X-API-Key: $FACTY_KEY" -H "Content-Type: application/json" \
  -d '{
    "rfc": "ACM980101ABC",
    "legalName": "ACME SA DE CV",
    "cp": "06600",
    "regimenFiscal": "601",
    "usoCfdiDefault": "G03",
    "email": "facturas@acme.mx"
  }' | jq

Respuesta 201:

{ "id": "clx9aa3k80000abcd1234efgh", "rfc": "ACM980101ABC", "created": true }

upsert — para sincronizadores

Por default, un RFC que ya existe devuelve 409: la app web usa ese conflicto para decirle a una persona "ya tienes un cliente con ese RFC".

Un sincronizador quiere lo contrario. Con "upsert": true, un RFC existente es el caso de éxito:

ResultadoHTTPcreated
Se creó un cliente nuevo201true
Ya existía ese RFC200false

Así, una corrida interrumpida converge al reintentarse en vez de fallar.

Actualizar

PATCH /api/authenticated/{org}/clients/{clientId}

Scope: clients.update. Acepta los mismos campos que el alta; manda solo los que cambian.

curl -s -X PATCH "$FACTY_HOST/api/authenticated/$FACTY_ORG/clients/clx9aa…" \
  -H "X-API-Key: $FACTY_KEY" -H "Content-Type: application/json" \
  -d '{ "email": "cuentas.por.pagar@acme.mx" }' | jq

Facturar al público en general

Para el CFDI global o una venta al mostrador, el receptor es el genérico del SAT:

CampoValor
rfcXAXX010101000
legalNamePUBLICO EN GENERAL
regimenFiscal616 (Sin obligaciones fiscales)
usoCfdiDefaultS01 (Sin efectos fiscales)
cpEl CP de tu propio domicilio fiscal

Ver factura global para el nodo informacionGlobal.

Clientes en el extranjero

Si vas a exportar, el cliente admite además los datos de comercio exterior: numRegIdTrib (tax id extranjero), residenciaFiscalPais (clave de 3 letras) y el domicilio desglosado (extCalle, extNumExterior, extColonia, extMunicipio, extEstado, extPais, extCodigoPostal).

Facturas pendientes de un cliente

Útil para armar un complemento de pago sin recorrer todo el historial:

GET /api/authenticated/{org}/clients/{clientId}/ppd-invoices

Scope: invoices.read. Devuelve las facturas PPD de ese cliente con saldo pendiente. Ver Complemento de pago.