@veriko-mx/sdk 0.4.10 → 0.4.12

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (55) hide show
  1. package/CHANGELOG.md +51 -0
  2. package/README.md +237 -41
  3. package/dist/cjs/client.d.ts +6 -3
  4. package/dist/cjs/client.d.ts.map +1 -1
  5. package/dist/cjs/client.js +6 -3
  6. package/dist/cjs/client.js.map +1 -1
  7. package/dist/cjs/generated/openapi.d.ts +835 -33
  8. package/dist/cjs/generated/openapi.d.ts.map +1 -1
  9. package/dist/cjs/http.d.ts +2 -0
  10. package/dist/cjs/http.d.ts.map +1 -1
  11. package/dist/cjs/http.js +1 -1
  12. package/dist/cjs/http.js.map +1 -1
  13. package/dist/cjs/index.d.ts +2 -2
  14. package/dist/cjs/index.d.ts.map +1 -1
  15. package/dist/cjs/index.js +6 -2
  16. package/dist/cjs/index.js.map +1 -1
  17. package/dist/cjs/resources.d.ts +88 -4
  18. package/dist/cjs/resources.d.ts.map +1 -1
  19. package/dist/cjs/resources.js +166 -8
  20. package/dist/cjs/resources.js.map +1 -1
  21. package/dist/cjs/types.d.ts +129 -13
  22. package/dist/cjs/types.d.ts.map +1 -1
  23. package/dist/cjs/types.js +6 -0
  24. package/dist/cjs/types.js.map +1 -1
  25. package/dist/cjs/webhooks.d.ts +41 -1
  26. package/dist/cjs/webhooks.d.ts.map +1 -1
  27. package/dist/cjs/webhooks.js +94 -6
  28. package/dist/cjs/webhooks.js.map +1 -1
  29. package/dist/esm/client.d.ts +6 -3
  30. package/dist/esm/client.d.ts.map +1 -1
  31. package/dist/esm/client.js +6 -3
  32. package/dist/esm/client.js.map +1 -1
  33. package/dist/esm/generated/openapi.d.ts +835 -33
  34. package/dist/esm/generated/openapi.d.ts.map +1 -1
  35. package/dist/esm/http.d.ts +2 -0
  36. package/dist/esm/http.d.ts.map +1 -1
  37. package/dist/esm/http.js +1 -1
  38. package/dist/esm/http.js.map +1 -1
  39. package/dist/esm/index.d.ts +2 -2
  40. package/dist/esm/index.d.ts.map +1 -1
  41. package/dist/esm/index.js +1 -1
  42. package/dist/esm/index.js.map +1 -1
  43. package/dist/esm/resources.d.ts +88 -4
  44. package/dist/esm/resources.d.ts.map +1 -1
  45. package/dist/esm/resources.js +166 -8
  46. package/dist/esm/resources.js.map +1 -1
  47. package/dist/esm/types.d.ts +129 -13
  48. package/dist/esm/types.d.ts.map +1 -1
  49. package/dist/esm/types.js +6 -0
  50. package/dist/esm/types.js.map +1 -1
  51. package/dist/esm/webhooks.d.ts +41 -1
  52. package/dist/esm/webhooks.d.ts.map +1 -1
  53. package/dist/esm/webhooks.js +91 -5
  54. package/dist/esm/webhooks.js.map +1 -1
  55. package/package.json +1 -1
@@ -65,7 +65,11 @@ export interface paths {
65
65
  * - Clave de rastreo / Referencia numérica.
66
66
  * - Banco emisor.
67
67
  * - Banco receptor.
68
- * - Cuenta beneficiaria.
68
+ * - Cuenta beneficiaria, o una lista de cuentas candidatas.
69
+ *
70
+ * La cuenta beneficiaria (`cuenta_beneficiaria`) es obligatoria en esta operación, salvo que se envíe `cuentas_candidatas`. Si faltan las dos, la petición se rechaza con `422 preflight_failed` y el error de campo `cuenta_required`: el servicio no la busca entre los beneficiarios guardados.
71
+ *
72
+ * Cuando no se sabe a cuál de varias cuentas se hizo el pago, `cuentas_candidatas` sustituye a `cuenta_beneficiaria`: de 2 a 3 cuentas en una sola validación y con una sola unidad de cuota. La consulta recorre las candidatas en el orden enviado y adopta la primera que coincide con la transferencia; esa cuenta vuelve completa en `normalized_data.cuenta_beneficiaria` y su posición en `candidate_match`. Si ninguna coincide, la respuesta es un estado HTTP `422` con el motivo en `code`. Las dos formas no pueden enviarse juntas (`422 cuenta_y_candidatas_excluyentes`) y una lista que no cumple se rechaza con `422 cuentas_candidatas_invalidas`, las dos antes de consumir cuota.
69
73
  *
70
74
  * El veredicto final (estado terminal) de una validación puede ser alguno de estos:
71
75
  *
@@ -133,7 +137,17 @@ export interface paths {
133
137
  *
134
138
  * {% callout type="info" %}
135
139
  * El campo `cuenta_beneficiaria` permite enviar explícitamente la cuenta receptora de la transferencia, enviarlo es especialmente útil cuando la imagen no lleva este dato o lo lleva incompleto.\
136
- * Puedes guardar esa cuenta como beneficiario (en `POST /v1/beneficiaries`) para no enviarla en cada validación, el sistema detectará en automático los dígitos visibles en cada imagen.
140
+ * Un beneficiario guardado (con `POST /v1/beneficiaries`) no sustituye a este campo: solo sirve para completar los dígitos de la cuenta que la imagen sí muestra. Si la imagen no trae dígitos suficientes, la validación se rechaza con `cuenta_unresolvable`, porque las cuentas guardadas no se prueban una por una.\
141
+ * \
142
+ * Cuando no se sabe cuál de varias cuentas recibió el pago, `cuentas_candidatas` las prueba en una sola validación (de 2 a 3 cuentas, una sola unidad de cuota, también con `?async=1`) y sustituye a `cuenta_beneficiaria`: enviar las dos se rechaza con `422 cuenta_y_candidatas_excluyentes`, y una lista que no cumple, con `422 cuentas_candidatas_invalidas`, las dos antes de consumir cuota. La lista tiene prioridad sobre la cuenta que se lea en la imagen; la ganadora vuelve completa en `normalized_data.cuenta_beneficiaria` y su posición en `candidate_match`. Si ninguna coincide, la respuesta es un estado HTTP `422` con el motivo en `code`.
143
+ *
144
+ * {% /callout %}
145
+ *
146
+ * {% callout type="info" %}
147
+ * **Retención del comprobante:**\
148
+ * De forma predeterminada el archivo del comprobante se conserva y se sirve con `GET /v1/validations/{id}/image`. Con `retain_image=false`, se borra cuando la validación llega a un estado terminal del que ya no se necesita, y el veredicto y los datos extraídos se conservan. La validación publica `image_retained=false` y la imagen responde un estado HTTP `410` (con `image_not_retained` en el cuerpo).\
149
+ * \
150
+ * Un valor que no es booleano responde un estado HTTP `422` (con `invalid_retain_image` en el cuerpo), antes de consumir cuota. Para borrar después una validación y todo lo que dejó, está `POST /v1/validations/{id}/purge/prepare`, descrito en {% concept slug="data-retention" %}la retención de comprobantes y datos{% /concept %}.
137
151
  *
138
152
  * {% /callout %}
139
153
  *
@@ -194,7 +208,7 @@ export interface paths {
194
208
  *
195
209
  * - `status`: Acepta un estado, o varios separados por comas.
196
210
  * - `with_deleted`: Distingue entre los registros activos y los retirados.
197
- * - **Los demás** acotan por: modalidad, fecha, contenido, banco, importe, origen y ciclo de reintentos.
211
+ * - **Los demás** acotan por: modalidad, fecha, contenido, banco, importe, origen, referencia propia (`client_ref`) y ciclo de reintentos.
198
212
  *
199
213
  * La forma de la respuesta está descrita en {% concept slug="pagination" %}la paginación{% /concept %}.
200
214
  *
@@ -279,6 +293,12 @@ export interface paths {
279
293
  * Si el `ETag` enviado en `If-None-Match` sigue vigente, responde con un estado HTTP `304` sin cuerpo, como describe {% concept slug="conditional-caching" %}la caché condicional{% /concept %}.
280
294
  *
281
295
  * {% /callout %}
296
+ *
297
+ * {% callout type="info" %}
298
+ * **Validaciones purgadas:**\
299
+ * Una validación purgada con `POST /v1/validations/{id}/purge/execute` responde con un estado HTTP `200` y queda como una lápida: conserva el veredicto, las fechas y el monto, y trae `purged_at`. Ya no tiene `request_data`, `ocr_result`, `banxico_result` ni archivos.
300
+ *
301
+ * {% /callout %}
282
302
  */
283
303
  get: operations["getValidation"];
284
304
  put?: never;
@@ -288,6 +308,8 @@ export interface paths {
288
308
  * @description Retira una validación del historial de validaciones del usuario autenticado.
289
309
  *
290
310
  * La eliminación es lógica, no física. Lo que quiere decir que puede seguir apareciendo en las listas como `GET /v1/validations` si se usa el filtro `with_deleted` u otros.
311
+ *
312
+ * El registro, el CEP, los datos extraídos y el archivo del comprobante se conservan. Para borrarlos de forma definitiva está `POST /v1/validations/{id}/purge/prepare`, seguido de `POST /v1/validations/{id}/purge/execute`.
291
313
  */
292
314
  delete: operations["deleteValidation"];
293
315
  options?: never;
@@ -362,6 +384,8 @@ export interface paths {
362
384
  * para que un navegador no lo abra dentro del propio origen.
363
385
  *
364
386
  * Si la validación no tiene imagen disponible, responde con un estado HTTP `404` (con `image_not_available` en el cuerpo).
387
+ *
388
+ * Si la validación se creó con `retain_image=false`, responde con un estado HTTP `410` (con `image_not_retained` en el cuerpo); si se purgó, con un estado HTTP `410` (con `validation_purged` en el cuerpo). Un `410` no se resuelve reintentando: el archivo no existe.
365
389
  */
366
390
  get: operations["getValidationImage"];
367
391
  put?: never;
@@ -456,6 +480,146 @@ export interface paths {
456
480
  patch?: never;
457
481
  trace?: never;
458
482
  };
483
+ "/validations/{id}/recheck": {
484
+ parameters: {
485
+ query?: never;
486
+ header?: never;
487
+ path?: never;
488
+ cookie?: never;
489
+ };
490
+ get?: never;
491
+ put?: never;
492
+ /**
493
+ * Volver a consultar el estado de pago de una validación
494
+ * @description Vuelve a consultar a Banxico el estado del pago de una validación `valid` y, si lo reporta devuelto, la pasa a `returned`.
495
+ *
496
+ * Un veredicto `valid` es la foto del momento de la consulta: el CEP acredita que la transferencia se liquidó, no que el dinero siguiera en la cuenta del beneficiario, y la institución receptora puede devolverlo horas o días después. Esta operación hace sólo esa consulta, con los datos que la validación ya guardó:
497
+ *
498
+ * - No usa IA ni descarga otro CEP.
499
+ * - **No consume cuota** ni cuenta como una validación nueva.
500
+ * - Guarda la respuesta de Banxico en `banxico_result._payment_status`.
501
+ * - Con el estado `devuelto` o `en_proceso_devolucion`, cambia `status` y `banxico_status` a `returned`, conserva el CEP y emite el webhook `validation.returned`.
502
+ *
503
+ * Qué admite:
504
+ *
505
+ * - `valid` creada hace 72 horas como máximo: se consulta. Pasado ese plazo responde con un estado HTTP `422` (con `recheck_window_expired` en el cuerpo).
506
+ * - `returned`: responde su estado actual sin consultar a Banxico, con `meta.recheck.checked_at` en `null`.
507
+ * - Cualquier otro estado: responde con un estado HTTP `422` (con `recheck_not_eligible` en el cuerpo).
508
+ *
509
+ * Cada validación admite una consulta cada 10 minutos. Si se repite antes, responde con un estado HTTP `429` (con `recheck_rate_limited` en el cuerpo) y la cabecera `Retry-After` indica los segundos que faltan. Ese tope se suma a los de la clave de API.
510
+ *
511
+ * La respuesta es la misma validación que devuelve `GET /v1/validations/{id}`, con el resultado de la revisión en `meta.recheck`:
512
+ *
513
+ * - `checked_at`: Fecha y hora de la consulta a Banxico, en ISO 8601 UTC. `null` cuando no se consultó nada porque la validación ya estaba `returned`.
514
+ * - `changed`: `true` cuando esta consulta pasó la validación de `valid` a `returned`.
515
+ * - `previous_status`: Veredicto de Banxico antes de la consulta, `valid` o `returned`.
516
+ *
517
+ * {% callout type="info" %}
518
+ * **Si Banxico no responde:**\
519
+ * Cuando Banxico no entrega un estado legible, responde con un estado HTTP `503` (con `recheck_unavailable` en el cuerpo) y la validación conserva su intervalo: se puede reintentar de inmediato. Un `503` no dice nada sobre la transferencia.
520
+ *
521
+ * {% /callout %}
522
+ *
523
+ * El significado de `valid` y de `returned` está en {% concept slug="cep-concept" %}el CEP y sus veredictos{% /concept %}, y la entrega del evento en {% concept slug="webhooks-architecture" %}la arquitectura de webhooks{% /concept %}.
524
+ */
525
+ post: operations["recheckValidation"];
526
+ delete?: never;
527
+ options?: never;
528
+ head?: never;
529
+ patch?: never;
530
+ trace?: never;
531
+ };
532
+ "/validations/{id}/purge/prepare": {
533
+ parameters: {
534
+ query?: never;
535
+ header?: never;
536
+ path?: never;
537
+ cookie?: never;
538
+ };
539
+ get?: never;
540
+ put?: never;
541
+ /**
542
+ * Preparar el borrado definitivo de una validación
543
+ * @description Describe lo que borraría el borrado definitivo de una validación propia y emite el token con el que `POST /v1/validations/{id}/purge/execute` lo confirma. No cambia nada: la validación y sus archivos quedan como estaban.
544
+ *
545
+ * `DELETE /v1/validations/{id}` solo retira la validación del historial; el registro, el CEP, los datos extraídos y el archivo del comprobante siguen existiendo. El borrado definitivo, en dos pasos, los elimina.
546
+ *
547
+ * La respuesta incluye:
548
+ *
549
+ * - `confirmation_token`: Token de un solo uso, atado a la cuenta y a esta validación, que caduca en `expires_in` segundos.
550
+ * - `will_delete`: Lo que se borrará: el archivo, el CEP, los campos con contenido y la cantidad de registros derivados.
551
+ * - `will_keep`: Los campos que conserva la lápida en que queda la validación.
552
+ * - `cancels_pending_retries`: `true` cuando hay un ciclo de reintentos abierto, que el borrado cancela.
553
+ * - `same_image_validation_ids`: Otras validaciones de la cuenta con el mismo comprobante, que no se tocan.
554
+ * - `irreversible`: `true` siempre.
555
+ *
556
+ * Solo se admite una validación propia en un estado terminal. Una validación en curso responde un estado HTTP `409` (con `purge_validation_in_progress` en el cuerpo), y una ya purgada, un estado HTTP `410` (con `validation_purged` en el cuerpo).
557
+ *
558
+ * {% callout type="warning" %}
559
+ * **El borrado es irreversible:**\
560
+ * Lo borrado no se recupera, ni siquiera desde la plataforma. La validación queda como una lápida y **no devuelve cuota**.\
561
+ * Los respaldos de infraestructura no se alteran: conservan una copia hasta que el ciclo de respaldos la retira.
562
+ *
563
+ * {% /callout %}
564
+ *
565
+ * La lápida, lo que se borra y las limitaciones están en {% concept slug="data-retention" %}la retención de comprobantes y datos{% /concept %}.
566
+ */
567
+ post: operations["prepareValidationPurge"];
568
+ delete?: never;
569
+ options?: never;
570
+ head?: never;
571
+ patch?: never;
572
+ trace?: never;
573
+ };
574
+ "/validations/{id}/purge/execute": {
575
+ parameters: {
576
+ query?: never;
577
+ header?: never;
578
+ path?: never;
579
+ cookie?: never;
580
+ };
581
+ get?: never;
582
+ put?: never;
583
+ /**
584
+ * Ejecutar el borrado definitivo de una validación
585
+ * @description Borra de forma definitiva el contenido de una validación propia, con el token que emitió `POST /v1/validations/{id}/purge/prepare`. Es el segundo paso de un flujo de dos pasos: sin ese token no se borra nada.
586
+ *
587
+ * Se borra:
588
+ *
589
+ * - El archivo del comprobante, imagen o PDF.
590
+ * - El CEP, en XML y en PDF.
591
+ * - `request_data`, `ocr_result`, `banxico_result` y las advertencias de normalización. De `normalized_data` solo se conserva el monto.
592
+ * - Los registros derivados con datos personales: intentos de reintento, sondeos de cuenta, respuestas guardadas de `Idempotency-Key` y notificaciones de la bandeja.
593
+ * - El cuerpo enviado y la respuesta del receptor en las entregas de webhook de esa validación, y el contenido de sus notificaciones. El registro de cada entrega se conserva.
594
+ * - Los cuerpos de las filas de auditoría que nombran la validación, y el contexto libre de sus eventos de seguridad.
595
+ *
596
+ * La validación queda como una lápida: conserva `id`, `validation_type`, `status`, `banxico_status`, las fechas, `processing_time_ms`, `error_code`, el monto y `purged_at`. Con eso la cuota, las estadísticas, finanzas y el historial siguen cuadrando. **El borrado no devuelve cuota.**
597
+ *
598
+ * Después del borrado, `GET /v1/validations/{id}` responde la lápida con un estado HTTP `200` y `purged_at`. La imagen, el CEP, los reintentos y la revisión posterior responden un estado HTTP `410` (con `validation_purged` en el cuerpo), y los webhooks, los reintentos y los barridos la ignoran. Un ciclo de reintentos abierto se cancela.
599
+ *
600
+ * El token se verifica antes de borrar:
601
+ *
602
+ * - Falta, está mal formado, su firma no es válida o venció: responde un estado HTTP `422` con su código (`confirmation_token_missing`, `confirmation_token_malformed`, `confirmation_token_signature_invalid` o `confirmation_token_expired`).
603
+ * - Es de otra validación, de otra cuenta o de otra operación: responde un estado HTTP `422` (con `purge_token_mismatch` o `confirmation_token_operation_mismatch` en el cuerpo).
604
+ * - Ya se usó: responde un estado HTTP `409` (con `confirmation_token_already_used` en el cuerpo).
605
+ *
606
+ * Si la respuesta no llega, `GET /v1/validations/{id}` dice si el borrado se completó: una validación purgada trae `purged_at`. Repetir este paso sobre una validación purgada responde un estado HTTP `410`.
607
+ *
608
+ * {% callout type="warning" %}
609
+ * **El borrado es irreversible:**\
610
+ * Lo borrado no se recupera, ni siquiera desde la plataforma. Los respaldos de infraestructura no se alteran y el catálogo global de cuentas, que no guarda vínculo con la validación, no se toca.
611
+ *
612
+ * {% /callout %}
613
+ *
614
+ * Lo que se borra, la lápida y las limitaciones están en {% concept slug="data-retention" %}la retención de comprobantes y datos{% /concept %}.
615
+ */
616
+ post: operations["executeValidationPurge"];
617
+ delete?: never;
618
+ options?: never;
619
+ head?: never;
620
+ patch?: never;
621
+ trace?: never;
622
+ };
459
623
  "/public/banks": {
460
624
  parameters: {
461
625
  query?: never;
@@ -1066,6 +1230,7 @@ export interface paths {
1066
1230
  * Cada endpoint puede suscribirse a diferentes eventos, entre ellos:
1067
1231
  *
1068
1232
  * - Eventos `validation.*`: Esperan cualquier estado terminal de una validación para notificar ese estado mediante el webhook (p. ej: `validation.completed`, `validation.error`, etc).
1233
+ * - Evento `validation.returned`: avisa cuando una validación que ya había salido `valid` pasa después a `returned` porque Banxico reportó la devolución; no se emite al crear la validación, donde el evento es `validation.completed`. Para recibirlo hay que suscribirse a él además de a `validation.completed`.
1069
1234
  * - Eventos `billing.*`: No producen entregas hasta que haya algún movimiento en la suscripción del usuario (p. ej: `billing.subscription_canceled`, `billing.payment_succeeded`, cuotas de uso, etc).
1070
1235
  *
1071
1236
  * Si se alcanza el tope de endpoints registrados, la creación responde con un estado HTTP `422` (con `webhook_limit_reached` en el cuerpo) y con el valor del límite en el campo `meta.limit`.
@@ -1080,6 +1245,7 @@ export interface paths {
1080
1245
  * **Firma secreta:**\
1081
1246
  * El `secret` de firma se devuelve **únicamente en esta respuesta** y no puede recuperarse después. Un secreto perdido se sustituye con `POST /v1/webhooks/{id}/regenerate-secret`, que devuelve el nuevo e invalida el anterior de inmediato — el endpoint no hay que volver a registrarlo.\
1082
1247
  * Ese secreto verifica cada entrega: el HMAC-SHA256 del cuerpo recibido debe coincidir con la cabecera `X-Webhook-Signature: sha256=<hex>`.\
1248
+ * Cada entrega lleva además `X-Webhook-Signature-Timestamped: t=<segundos>,v1=<hex>`, donde `v1` es el HMAC-SHA256 de `<t>.<cuerpo>`. Esa firma incluye la hora del intento, y la ventana de tolerancia recomendada es de 5 minutos contra `t`, no contra el `timestamp` del cuerpo: los reintentos llegan hasta unas 8,6 horas después del evento.\
1083
1249
  * \
1084
1250
  * La firma, y más detalles se describen en {% concept slug="webhooks-architecture" %}la arquitectura de webhooks{% /concept %}.
1085
1251
  *
@@ -1440,13 +1606,20 @@ export interface paths {
1440
1606
  * Consultar los límites de tasa (rate-limits)
1441
1607
  * @description Devuelve los límites de tasa aplicables al usuario autenticado, por contexto.
1442
1608
  *
1443
- * Los dos contextos no llevan los mismos límites: `api` limita por IP y por
1444
- * minuto; `login` limita por IP y por correo electrónico, cada uno por minuto y
1445
- * por hora.
1609
+ * Los contextos no llevan los mismos límites. `api` limita las peticiones
1610
+ * autenticadas por clave y por minuto, con el valor del plan de la cuenta
1611
+ * (`key_per_minute`), y suma un techo por IP (`ip_ceiling_per_minute`); las
1612
+ * peticiones sin clave se limitan por IP (`ip_per_minute`). `webhooks` fija las
1613
+ * entregas por minuto que la cuenta puede enviar hacia un mismo host destino,
1614
+ * según su plan (`host_per_minute`), y el tope de todos los clientes juntos
1615
+ * sobre ese host (`host_global_per_minute`). `login` limita por IP y por correo
1616
+ * electrónico, cada uno por minuto y por hora.
1446
1617
  *
1447
1618
  * No devuelve contadores en vivo, sólo la configuración vigente. Estos límites
1448
1619
  * son ajenos a la cuota mensual de validaciones, que devuelve
1449
- * [`GET /v1/usage/summary`](/es/v1/usage/get-usage-summary).
1620
+ * [`GET /v1/usage/summary`](/es/v1/usage/get-usage-summary). El consumo de la
1621
+ * ventana en curso lo informan, en cada respuesta autenticada de la API, las
1622
+ * cabeceras `X-RateLimit-*`.
1450
1623
  *
1451
1624
  * {% callout type="note" %}
1452
1625
  * Al superarse uno de estos límites, la operación afectada responde con estado
@@ -2177,8 +2350,8 @@ export interface components {
2177
2350
  */
2178
2351
  outcomes?: ("not_found" | "cep_unavailable" | "error")[];
2179
2352
  };
2180
- /** @description Cuerpo de `POST /v1/validate` para una validación manual SPEI; exige `clave_rastreo` o `referencia_numerica`. */
2181
- ValidationRequest: {
2353
+ /** @description Cuerpo de `POST /v1/validate` para una validación manual SPEI; exige `clave_rastreo` o `referencia_numerica`, y una sola de las dos formas de indicar la cuenta: `cuenta_beneficiaria` o `cuentas_candidatas`. */
2354
+ ValidationRequest: ({
2182
2355
  /**
2183
2356
  * Format: date
2184
2357
  * @description Fecha de la transferencia en formato ISO 8601 (YYYY-MM-DD).
@@ -2212,10 +2385,22 @@ export interface components {
2212
2385
  */
2213
2386
  receptor?: string;
2214
2387
  /**
2215
- * @description Cuenta bancaria receptora de la transferencia. Puede ser CLABE (18 dígitos), tarjeta (16 dígitos) o celular DiMo (10 dígitos), y el tipo se identifica por la longitud de sus dígitos. Los espacios y guiones que separan grupos ("0121 8000 4412 345678") se ignoran automáticamente antes de contar la longitud. Para celular DiMo, si el banco receptor no puede resolverse por el campo `receptor`, por los beneficiarios registrados ni por el directorio de cuentas, la respuesta es un estado HTTP `422` (con `bank_code_unresolvable_for_phone` en el cuerpo).
2388
+ * @description Cuenta bancaria receptora de la transferencia. Es obligatoria cuando no se envía `cuentas_candidatas`: si faltan las dos, la respuesta es un estado HTTP `422` (con `preflight_failed` y el error de campo `cuenta_required`); si vienen las dos, un `422` con `cuenta_y_candidatas_excluyentes`. Puede ser CLABE (18 dígitos), tarjeta (16 dígitos) o celular DiMo (10 dígitos), y el tipo se identifica por la longitud de sus dígitos. Los espacios y guiones que separan grupos ("0121 8000 4412 345678") se ignoran automáticamente antes de contar la longitud. Para celular DiMo, si el banco receptor no puede resolverse por el campo `receptor`, por los beneficiarios registrados ni por el directorio de cuentas, la respuesta es un estado HTTP `422` (con `bank_code_unresolvable_for_phone` en el cuerpo).
2216
2389
  * @example 012180004412345678
2217
2390
  */
2218
2391
  cuenta_beneficiaria?: string;
2392
+ /**
2393
+ * @description Cuentas entre las que está la receptora de la transferencia, para cuando no se sabe cuál fue. Va en lugar de `cuenta_beneficiaria`: enviar las dos responde un estado HTTP `422` (con `cuenta_y_candidatas_excluyentes` en el cuerpo).
2394
+ *
2395
+ * Admite de 2 al máximo vigente de la plataforma, 3 por defecto y nunca más de 10; el `422` por exceso informa el máximo en `meta.max`. Cada cuenta es una CLABE (18 dígitos), una tarjeta (16) o un celular DiMo (10), con su dígito verificador válido y sin repetirse. Una lista que no cumple responde un `422` con `cuentas_candidatas_invalidas`, y señala en `field_errors` la posición que falló. Los dos errores ocurren antes de consumir cuota.
2396
+ *
2397
+ * Consume una sola unidad de cuota, lleve las cuentas que lleve. La consulta recorre las candidatas en el orden enviado y adopta la primera que coincide con la transferencia. La ganadora se publica completa en `normalized_data.cuenta_beneficiaria`, y `candidate_match` indica su posición. Si ninguna coincide, la respuesta es un estado HTTP `422` con el motivo en `code` (`cuenta_unresolvable_after_probes` cuando no hay un diagnóstico más preciso).
2398
+ * @example [
2399
+ * "012180004412345678",
2400
+ * "002010077777777771"
2401
+ * ]
2402
+ */
2403
+ cuentas_candidatas?: string[];
2219
2404
  /**
2220
2405
  * @description Indica si el beneficiario de la transferencia es directamente la institución receptora del pago («Pago a Banco» en el CEP de Banxico) y no uno de sus cuentahabientes. `0` para una transferencia a un cuentahabiente (valor por defecto); `1` para pagos cuyo beneficiario es el banco —pago de tarjeta de crédito, de crédito o de servicios a la propia institución. Opcional: si se omite se asume `0`.
2221
2406
  * @default 0
@@ -2225,7 +2410,12 @@ export interface components {
2225
2410
  receptor_participante: 0 | 1;
2226
2411
  /** @description Política de **reintentos automáticos** para esta validación. Si se omite, se aplica la política general configurada para el usuario. Los reintentos NO consumen cuota de validaciones. */
2227
2412
  retry_policy?: components["schemas"]["RetryPolicy"];
2228
- } | unknown | unknown;
2413
+ /**
2414
+ * @description Referencia propia que se devuelve tal cual en la validación, en los webhooks de validación y como filtro exacto de `GET /v1/validations`. Texto de 1 a 64 caracteres, sin saltos de línea ni emoji; se recorta antes de guardarse. Un valor que no cumple se rechaza con un estado HTTP `422` (con `invalid_client_ref` en el cuerpo). No debe contener datos personales.
2415
+ * @example orden-4812
2416
+ */
2417
+ client_ref?: string;
2418
+ } & (unknown | unknown)) | unknown | unknown;
2229
2419
  /**
2230
2420
  * @description Código estable del fallo de una validación.
2231
2421
  * @enum {string}
@@ -2311,7 +2501,7 @@ export interface components {
2311
2501
  */
2312
2502
  status?: "queued" | "processing" | "valid" | "not_found" | "cep_unavailable" | "invalid" | "returned" | "failed" | "error";
2313
2503
  /**
2314
- * @description Veredicto reportado por Banxico. Puede ser: `valid`, `not_found`, `cep_unavailable`, `invalid`, `returned` o `error`. Permanece `pending` mientras no exista un veredicto de Banxico. `returned` significa que la operación se liquidó y la institución beneficiaria la devolvió después — el CEP, si existe, se sigue entregando. Solo toma `error` cuando la petición llegó a Banxico y el servicio falló; `error_code` identifica la causa.
2504
+ * @description Veredicto reportado por Banxico. Puede ser: `valid`, `not_found`, `cep_unavailable`, `invalid`, `returned` o `error`. Permanece `pending` mientras no exista un veredicto de Banxico. `returned` significa que la operación se liquidó y la institución beneficiaria la devolvió después — el CEP, si existe, se sigue entregando. Un `valid` no es definitivo: es el veredicto del momento de la consulta, y pasa a `returned` cuando Banxico reporta la devolución en una revisión posterior, que se pide con `POST /v1/validations/{id}/recheck` o que el servicio hace solo durante las primeras 72 horas (se emite el webhook `validation.returned`). Solo toma `error` cuando la petición llegó a Banxico y el servicio falló; `error_code` identifica la causa.
2315
2505
  * @example valid
2316
2506
  */
2317
2507
  banxico_status?: string | null;
@@ -2324,6 +2514,11 @@ export interface components {
2324
2514
  request_data?: {
2325
2515
  [key: string]: unknown;
2326
2516
  };
2517
+ /**
2518
+ * @description Referencia propia que se envió en la petición (`client_ref`), devuelta tal cual. Solo aparece cuando la petición la incluyó. Sirve para relacionar la validación con un pedido propio, y `GET /v1/validations` la acepta como filtro exacto. No debe contener datos personales.
2519
+ * @example orden-4812
2520
+ */
2521
+ client_ref?: string;
2327
2522
  /**
2328
2523
  * Format: date-time
2329
2524
  * @description Fecha y hora, en ISO 8601 UTC, de creación de la validación.
@@ -2360,10 +2555,25 @@ export interface components {
2360
2555
  */
2361
2556
  etag_version?: number | null;
2362
2557
  /**
2363
- * @description Referencia relativa del comprobante, imagen o PDF (solo si `validation_type` es del tipo `ocr`).
2558
+ * @description Referencia relativa del comprobante, imagen o PDF (solo si `validation_type` es del tipo `ocr`). No se publica cuando el archivo no se conserva: ver `image_retained`.
2364
2559
  * @example ocr/2026/04/a1b2c3d4.jpg
2365
2560
  */
2366
2561
  image_path?: string | null;
2562
+ /**
2563
+ * @description `true` cuando la plataforma conserva el archivo del comprobante; `false` cuando no, porque la petición envió `retain_image=false` o porque la validación se purgó. Solo aparece en las validaciones de tipo `ocr`.
2564
+ *
2565
+ * Con `false`, `GET /v1/validations/{id}/image` responde un estado HTTP `410` (con `image_not_retained` o `validation_purged` en el cuerpo).
2566
+ * @example true
2567
+ */
2568
+ image_retained?: boolean;
2569
+ /**
2570
+ * Format: date-time
2571
+ * @description Fecha y hora, en ISO 8601 UTC, en que la validación se purgó con `POST /v1/validations/{id}/purge/execute`. Solo aparece en una validación purgada, que queda como una lápida.
2572
+ *
2573
+ * Una lápida conserva `id`, `validation_type`, `status`, `banxico_status`, las fechas, `processing_time_ms`, `error_code` y el monto en `normalized_data.monto`. No conserva el archivo, el CEP, `request_data`, `ocr_result` ni `banxico_result`, y sus recursos derivados responden un estado HTTP `410` (con `validation_purged` en el cuerpo).
2574
+ * @example 2026-10-02T09:30:00Z
2575
+ */
2576
+ purged_at?: string;
2367
2577
  /**
2368
2578
  * @description Campos extraídos del comprobante (solo si `validation_type` es del tipo `ocr`).
2369
2579
  *
@@ -2385,7 +2595,60 @@ export interface components {
2385
2595
  } | null;
2386
2596
  /** @description Advertencias de normalización presentes. Permiten explicar un resultado `not_found` inesperado. */
2387
2597
  normalization_warnings?: string[] | null;
2388
- /** @description Indica si el número de tarjeta está enmascarado en el comprobante cargado (solo si `validation_type` es del tipo `ocr`). */
2598
+ /**
2599
+ * @description Validación previa que ya había confirmado esta misma transferencia en la misma cuenta. Solo aparece cuando existe una validación `valid`, no retirada, con la misma clave de rastreo; nunca apunta a una validación de otra cuenta.
2600
+ *
2601
+ * Es la forma estructurada del aviso que también se añade a `normalization_warnings`. No cambia el veredicto: la validación se consulta y se cobra igual.
2602
+ */
2603
+ duplicate_of?: {
2604
+ /**
2605
+ * Format: uuid
2606
+ * @description Identificador de la validación previa.
2607
+ * @example 3fa85f64-5717-4562-b3fc-2c963f66afa6
2608
+ */
2609
+ id: string;
2610
+ /**
2611
+ * Format: date-time
2612
+ * @description Fecha y hora, en ISO 8601 UTC, de creación de la validación previa.
2613
+ * @example 2026-10-01T15:04:05Z
2614
+ */
2615
+ created_at: string;
2616
+ };
2617
+ /**
2618
+ * @description Conflicto entre la cuenta enviada y la que muestra la imagen. Solo aparece en validaciones de tipo `ocr`, cuando se envió `cuenta_beneficiaria` y la imagen muestra otra cuenta completa de la misma longitud, válida y con confianza suficiente.
2619
+ *
2620
+ * Prevalece la cuenta enviada, que es la que se consulta en Banxico: el campo no cambia el veredicto. Si el pago fue a la cuenta de la imagen, lo esperable es un `not_found`. Solo trae los últimos 4 dígitos de cada cuenta, y el conflicto también se añade a `normalization_warnings`.
2621
+ */
2622
+ account_conflict?: {
2623
+ /**
2624
+ * @description Últimos 4 dígitos de la cuenta enviada en `cuenta_beneficiaria`.
2625
+ * @example 5678
2626
+ */
2627
+ sent_last4: string;
2628
+ /**
2629
+ * @description Últimos 4 dígitos de la cuenta completa que muestra la imagen.
2630
+ * @example 9012
2631
+ */
2632
+ read_last4: string;
2633
+ };
2634
+ /**
2635
+ * @description Cuál de las `cuentas_candidatas` enviadas ganó. Solo aparece cuando la petición llevó esa lista y una de las cuentas coincidió con la transferencia.
2636
+ *
2637
+ * La cuenta completa va en `normalized_data.cuenta_beneficiaria`; este objeto indica qué posición de la lista es, para correlacionarla con la entidad propia del integrador sin comparar cuentas. No cambia el veredicto.
2638
+ */
2639
+ candidate_match?: {
2640
+ /**
2641
+ * @description Posición (desde 0) de la cuenta ganadora en el arreglo `cuentas_candidatas`, tal como se envió.
2642
+ * @example 1
2643
+ */
2644
+ index: number;
2645
+ /**
2646
+ * @description Últimos 4 dígitos de la cuenta ganadora.
2647
+ * @example 7771
2648
+ */
2649
+ account_last4: string;
2650
+ };
2651
+ /** @description Indica si la cuenta beneficiaria viene enmascarada en el comprobante cargado, sea una CLABE, una tarjeta o un celular. Solo se incluye cuando vale `true` y solo si `validation_type` es del tipo `ocr`. */
2389
2652
  is_masked?: boolean | null;
2390
2653
  /**
2391
2654
  * @description Datos devueltos por Banxico. Las propiedades tipadas abajo son las 20 que declara el esquema oficial del complemento SPEI.
@@ -2396,6 +2659,12 @@ export interface components {
2396
2659
  * `authenticated` es `true` cuando su sello y su cadena original coinciden con los del CEP oficial;
2397
2660
  * con `false`, `differing_fields` lista los campos que difieren y `normalization_warnings` lo avisa.
2398
2661
  * El veredicto sigue siendo el de Banxico.
2662
+ *
2663
+ * `_payment_status` es el estado oficial del pago, tal como lo dio Banxico la última vez que se le preguntó:
2664
+ * `code` (`liquidado`, `en_proceso`, `cancelado`, `rechazado`, `en_proceso_devolucion`, `devuelto` o `desconocido`),
2665
+ * `label`, `settled`, `reversed` y `checked_at` (ISO 8601 UTC).
2666
+ * Su ausencia significa que no se pudo saber, nunca que el pago esté liquidado.
2667
+ * Se actualiza en cada revisión posterior, y con `devuelto` o `en_proceso_devolucion` la validación pasa a `returned`.
2399
2668
  */
2400
2669
  banxico_result?: ({
2401
2670
  /**
@@ -2545,6 +2814,11 @@ export interface components {
2545
2814
  expires_at?: components["schemas"]["TimestampUTC"];
2546
2815
  /** @description Estado del ciclo de reintentos automáticos al momento del encolamiento. Siempre presente; si no se configuró `retry_policy` en el body ni en la política del usuario, `enabled=false` y los campos de política son `null`. */
2547
2816
  retry_state?: components["schemas"]["RetryStateFull"];
2817
+ /**
2818
+ * @description Referencia propia enviada en la petición (`client_ref`), devuelta tal cual. Solo aparece cuando la petición la incluyó.
2819
+ * @example orden-4812
2820
+ */
2821
+ client_ref?: string;
2548
2822
  };
2549
2823
  };
2550
2824
  /** @description Metadatos de control del flujo de polling. */
@@ -2561,7 +2835,7 @@ export interface components {
2561
2835
  playground?: boolean;
2562
2836
  };
2563
2837
  };
2564
- /** @description Cuerpo de `POST /v1/validate-ocr` con el comprobante en `image` o `image_url`; exige al menos uno de ambos campos. */
2838
+ /** @description Cuerpo de `POST /v1/validate-ocr` con el comprobante en `image` o `image_url`; exige al menos uno de ambos campos. `cuenta_beneficiaria` y `cuentas_candidatas` no pueden ir juntas. */
2565
2839
  OcrValidationRequest: {
2566
2840
  /**
2567
2841
  * Format: byte
@@ -2576,12 +2850,39 @@ export interface components {
2576
2850
  */
2577
2851
  image_url?: string;
2578
2852
  /**
2579
- * @description Cuenta receptora de la transferencia (útil cuando falta o está incompleta en la imagen). Requerida para celular DiMo; opcional si la cuenta está guardada como beneficiario. Acepta CLABE (18 dígitos), tarjeta (16 dígitos) o celular DiMo (10 dígitos).
2853
+ * @description Cuenta receptora de la transferencia (útil cuando falta o está incompleta en la imagen). Requerida para celular DiMo; opcional si la imagen muestra la cuenta completa o sus últimos dígitos, que se completan con los beneficiarios guardados (estos no sustituyen a este campo). Acepta CLABE (18 dígitos), tarjeta (16 dígitos) o celular DiMo (10 dígitos). No puede enviarse junto con `cuentas_candidatas`: enviar las dos responde un estado HTTP `422` (con `cuenta_y_candidatas_excluyentes` en el cuerpo).
2580
2854
  * @example 012180004412345678
2581
2855
  */
2582
2856
  cuenta_beneficiaria?: string;
2857
+ /**
2858
+ * @description Cuentas entre las que está la receptora de la transferencia, para cuando la imagen no la muestra y no se sabe cuál fue. Va en lugar de `cuenta_beneficiaria`: enviar las dos responde un estado HTTP `422` (con `cuenta_y_candidatas_excluyentes` en el cuerpo). Tiene prioridad sobre la cuenta que se lea en la imagen.
2859
+ *
2860
+ * Admite de 2 al máximo vigente de la plataforma, 3 por defecto y nunca más de 10; el `422` por exceso informa el máximo en `meta.max`. Cada cuenta es una CLABE (18 dígitos), una tarjeta (16) o un celular DiMo (10), con su dígito verificador válido y sin repetirse. Una lista que no cumple responde un `422` con `cuentas_candidatas_invalidas`, y señala en `field_errors` la posición que falló. Los dos errores ocurren antes de consumir cuota.
2861
+ *
2862
+ * Consume una sola unidad de cuota, lleve las cuentas que lleve, también con `?async=1`. La consulta recorre las candidatas en el orden enviado y adopta la primera que coincide con la transferencia. La ganadora se publica completa en `normalized_data.cuenta_beneficiaria`, y `candidate_match` indica su posición. Si ninguna coincide, la respuesta es un estado HTTP `422` con el motivo en `code` (`cuenta_unresolvable_after_probes` cuando no hay un diagnóstico más preciso).
2863
+ * @example [
2864
+ * "012180004412345678",
2865
+ * "002010077777777771"
2866
+ * ]
2867
+ */
2868
+ cuentas_candidatas?: string[];
2583
2869
  /** @description Política de reintentos automáticos para esta validación. Si se omite, se aplica la política general del usuario, configurada en `PUT /v1/users/me/retry-policy`. **Los reintentos no consumen cuota de validaciones**. */
2584
2870
  retry_policy?: components["schemas"]["RetryPolicy"];
2871
+ /**
2872
+ * @description Referencia propia que se devuelve tal cual en la validación, en los webhooks de validación y como filtro exacto de `GET /v1/validations`. Texto de 1 a 64 caracteres, sin saltos de línea ni emoji; se recorta antes de guardarse. Un valor que no cumple se rechaza con un estado HTTP `422` (con `invalid_client_ref` en el cuerpo). No debe contener datos personales.
2873
+ * @example orden-4812
2874
+ */
2875
+ client_ref?: string;
2876
+ /**
2877
+ * @description `true` cuando la plataforma conserva el archivo del comprobante después de validarlo, que es lo habitual. Con `false`, el archivo se borra en cuanto la validación llega a un estado terminal del que ya no se necesita; el veredicto y los datos extraídos se conservan.
2878
+ *
2879
+ * Con `false`, la validación publica `image_retained=false` y `GET /v1/validations/{id}/image` responde un estado HTTP `410` (con `image_not_retained` en el cuerpo). Vale igual con `?async=1`.
2880
+ *
2881
+ * El archivo existe mientras la validación se procesa. Si entró como un CEP en PDF y tiene reintentos automáticos activos, el borrado espera a que ese ciclo cierre, porque cada reintento vuelve a comparar el sello del PDF. Un valor que no es booleano responde un estado HTTP `422` (con `invalid_retain_image` en el cuerpo), antes de consumir cuota.
2882
+ * @default true
2883
+ * @example false
2884
+ */
2885
+ retain_image: boolean;
2585
2886
  } | unknown | unknown;
2586
2887
  /** @description Estado resumido del ciclo de reintentos, con la configuración representada como `null`. */
2587
2888
  RetryStateCompact: {
@@ -2667,7 +2968,14 @@ export interface components {
2667
2968
  created_at?: components["schemas"]["TimestampUTC"];
2668
2969
  /** @description Fecha de retiro del historial, en ISO 8601 UTC. */
2669
2970
  deleted_at?: components["schemas"]["TimestampUTC"] | null;
2971
+ /** @description Fecha y hora, en ISO 8601 UTC, en que la validación se purgó. Solo aparece en una validación purgada, que queda como una lápida con su veredicto, sus fechas y su monto. */
2972
+ purged_at?: components["schemas"]["TimestampUTC"];
2670
2973
  retry_state?: components["schemas"]["RetryStateCompact"];
2974
+ /**
2975
+ * @description Referencia propia enviada al validar (`client_ref`), devuelta tal cual. Solo aparece cuando la petición la incluyó.
2976
+ * @example orden-4812
2977
+ */
2978
+ client_ref?: string;
2671
2979
  };
2672
2980
  } & WithRequired<components["schemas"]["JsonApiResourceBase"], "type" | "id">;
2673
2981
  /** @description Recurso JSON:API con contadores por `banxico_status`, estado del ciclo de vida y modalidad de validación. */
@@ -2851,6 +3159,211 @@ export interface components {
2851
3159
  CancelValidationRetriesAttributes: {
2852
3160
  retry_state?: components["schemas"]["RetryStateFull"];
2853
3161
  };
3162
+ /** @description Resultado de la revisión que acompaña, dentro de `meta`, la respuesta de `POST /v1/validations/{id}/recheck`. */
3163
+ ValidationRecheckMeta: {
3164
+ /**
3165
+ * Format: date-time
3166
+ * @description Fecha y hora, en ISO 8601 UTC, en que se consultó el estado del pago a Banxico. `null` cuando no se consultó nada porque la validación ya estaba en `returned`.
3167
+ * @example 2026-10-01T18:42:07Z
3168
+ */
3169
+ checked_at: string | null;
3170
+ /**
3171
+ * @description `true` cuando esta consulta pasó la validación de `valid` a `returned`. En ese caso también se emitió el webhook `validation.returned`.
3172
+ * @example false
3173
+ */
3174
+ changed: boolean;
3175
+ /**
3176
+ * @description Veredicto de Banxico antes de esta consulta — `valid`: La validación seguía confirmada; `returned`: La validación ya estaba devuelta y no se consultó nada.
3177
+ * @example valid
3178
+ * @enum {string}
3179
+ */
3180
+ previous_status: "valid" | "returned";
3181
+ };
3182
+ /** @description Respuesta de `POST /v1/validations/{id}/purge/prepare`: lo que borraría el borrado definitivo, lo que conservaría y el token que lo confirma. Todavía no ha cambiado nada. */
3183
+ ValidationPurgePrepareResponse: {
3184
+ /** @description Recurso JSON:API de la preparación. Su `id` es el de la validación. */
3185
+ data: components["schemas"]["JsonApiResourceBase"] & {
3186
+ /**
3187
+ * @description Tipo del recurso, fijo para esta operación. Forma parte de su identidad en la envoltura JSON:API. Siempre `validation_purge`.
3188
+ * @example validation_purge
3189
+ * @enum {string}
3190
+ */
3191
+ type: "validation_purge";
3192
+ /**
3193
+ * Format: uuid
3194
+ * @description Identificador de la validación que se borraría.
3195
+ * @example 3fa85f64-5717-4562-b3fc-2c963f66afa6
3196
+ */
3197
+ id: string;
3198
+ /** @description Resumen del borrado y token de confirmación. */
3199
+ attributes: {
3200
+ /**
3201
+ * @description Token de un solo uso, atado a la cuenta y a esta validación, que `POST /v1/validations/{id}/purge/execute` exige para borrar. Caduca en `expires_in` segundos.
3202
+ * @example eyJhZG1pbl9pZCI6Ii4uLiJ9.q1w2e3r4t5y6u7i8o9p0
3203
+ */
3204
+ confirmation_token: string;
3205
+ /**
3206
+ * @description Segundos de vigencia del token.
3207
+ * @example 120
3208
+ */
3209
+ expires_in: number;
3210
+ /**
3211
+ * @description `true` siempre: el borrado no se puede deshacer. Un respaldo de infraestructura no lo revierte para el cliente.
3212
+ * @example true
3213
+ */
3214
+ irreversible: boolean;
3215
+ /** @description Lo que borraría el borrado definitivo. */
3216
+ will_delete: {
3217
+ /**
3218
+ * @description `true` cuando hay un archivo del comprobante (imagen o PDF) que se borraría.
3219
+ * @example true
3220
+ */
3221
+ image: boolean;
3222
+ /**
3223
+ * @description `true` cuando hay un CEP (el XML o el PDF) que se borraría.
3224
+ * @example true
3225
+ */
3226
+ cep: boolean;
3227
+ /**
3228
+ * @description Campos de la validación con contenido que se vaciarían. De `normalized_data` se conserva únicamente el monto.
3229
+ * @example [
3230
+ * "request_data",
3231
+ * "ocr_result",
3232
+ * "normalized_data",
3233
+ * "banxico_result"
3234
+ * ]
3235
+ */
3236
+ stored_data: ("request_data" | "ocr_result" | "normalized_data" | "normalization_warnings" | "banxico_result")[];
3237
+ /**
3238
+ * @description Cantidad de intentos de reintento que se borrarían.
3239
+ * @example 2
3240
+ */
3241
+ retry_attempts: number;
3242
+ /**
3243
+ * @description Cantidad de sondeos de cuenta candidata que se borrarían.
3244
+ * @example 0
3245
+ */
3246
+ probe_attempts: number;
3247
+ /**
3248
+ * @description Cantidad de entregas de webhook de esta validación a las que se les quitaría el cuerpo enviado y la respuesta del receptor. El registro de cada entrega se conserva.
3249
+ * @example 1
3250
+ */
3251
+ webhook_deliveries: number;
3252
+ /**
3253
+ * @description Cantidad de entregas de notificación de esta validación cuyo contenido se vaciaría. Las notificaciones de la bandeja de la cuenta se borrarían.
3254
+ * @example 1
3255
+ */
3256
+ notifications: number;
3257
+ /**
3258
+ * @description Cantidad de respuestas guardadas de `Idempotency-Key` que se borrarían.
3259
+ * @example 1
3260
+ */
3261
+ idempotency_responses: number;
3262
+ /**
3263
+ * @description `true` siempre: los cuerpos de las filas de auditoría que nombran la validación se quitarían, y el contexto libre de sus eventos de seguridad se reduciría a ids y códigos.
3264
+ * @example true
3265
+ */
3266
+ audit_traces: boolean;
3267
+ };
3268
+ /**
3269
+ * @description Campos que conserva la lápida en que queda la validación: bastan para que la cuota, las estadísticas, finanzas y el historial sigan cuadrando.
3270
+ * @example [
3271
+ * "id",
3272
+ * "validation_type",
3273
+ * "status",
3274
+ * "banxico_status",
3275
+ * "amount",
3276
+ * "created_at",
3277
+ * "purged_at"
3278
+ * ]
3279
+ */
3280
+ will_keep: string[];
3281
+ /**
3282
+ * @description `true` cuando la validación tiene un ciclo de reintentos abierto, que el borrado cancela.
3283
+ * @example false
3284
+ */
3285
+ cancels_pending_retries: boolean;
3286
+ /**
3287
+ * @description `false` siempre: el borrado no devuelve cuota ni cambia lo cobrado.
3288
+ * @example false
3289
+ */
3290
+ refunds_quota: boolean;
3291
+ /**
3292
+ * @description Identificadores de otras validaciones de la misma cuenta con el mismo comprobante (hasta 20). No se tocan: cada una guarda su propia copia de lo extraído y se borra por separado.
3293
+ * @example []
3294
+ */
3295
+ same_image_validation_ids: string[];
3296
+ };
3297
+ };
3298
+ };
3299
+ /** @description Cuerpo de `POST /v1/validations/{id}/purge/execute`: el token del paso de preparación. */
3300
+ ValidationPurgeExecuteRequest: {
3301
+ /**
3302
+ * @description Token que devolvió `POST /v1/validations/{id}/purge/prepare` para esta misma validación y esta misma cuenta. Es de un solo uso y caduca en el plazo que indicó `expires_in`.
3303
+ * @example eyJhZG1pbl9pZCI6Ii4uLiJ9.q1w2e3r4t5y6u7i8o9p0
3304
+ */
3305
+ confirmation_token: string;
3306
+ };
3307
+ /** @description Respuesta de `POST /v1/validations/{id}/purge/execute`: la validación quedó purgada y esto es lo que se borró. */
3308
+ ValidationPurgeExecuteResponse: {
3309
+ /** @description Recurso JSON:API del borrado. Su `id` es el de la validación. */
3310
+ data: components["schemas"]["JsonApiResourceBase"] & {
3311
+ /**
3312
+ * @description Tipo del recurso, fijo para esta operación. Forma parte de su identidad en la envoltura JSON:API. Siempre `validation_purge`.
3313
+ * @example validation_purge
3314
+ * @enum {string}
3315
+ */
3316
+ type: "validation_purge";
3317
+ /**
3318
+ * Format: uuid
3319
+ * @description Identificador de la validación purgada.
3320
+ * @example 3fa85f64-5717-4562-b3fc-2c963f66afa6
3321
+ */
3322
+ id: string;
3323
+ /** @description Resultado del borrado. */
3324
+ attributes: {
3325
+ /**
3326
+ * Format: date-time
3327
+ * @description Fecha y hora, en ISO 8601 UTC, en que la validación quedó purgada.
3328
+ * @example 2026-10-02T09:30:00Z
3329
+ */
3330
+ purged_at: string;
3331
+ /**
3332
+ * @description Estado del borrado de los archivos — `complete`: Los archivos ya no existen; `pending`: Algún archivo no se pudo borrar en este momento y el barrido diario lo termina. El contenido de la base de datos ya está borrado en los dos casos y el archivo no se sirve.
3333
+ * @example complete
3334
+ * @enum {string}
3335
+ */
3336
+ file_removal: "complete" | "pending";
3337
+ /** @description Lo que se borró. Los contadores cuentan filas tocadas; los booleanos dicen si había algo que borrar. */
3338
+ deleted: {
3339
+ /** @description `true` cuando había un archivo del comprobante. */
3340
+ image?: boolean;
3341
+ /** @description `true` cuando había un PDF del CEP. */
3342
+ cep_pdf?: boolean;
3343
+ /** @description `true` cuando el borrado cerró un ciclo de reintentos que seguía abierto. */
3344
+ retry_cycle_cancelled?: boolean;
3345
+ /** @description Intentos de reintento borrados. */
3346
+ retry_attempts?: number;
3347
+ /** @description Sondeos de cuenta candidata borrados. */
3348
+ probe_attempts?: number;
3349
+ /** @description Entregas de webhook a las que se les quitó el cuerpo enviado y la respuesta del receptor. */
3350
+ webhook_deliveries?: number;
3351
+ /** @description Entregas de notificación cuyo contenido se vació. */
3352
+ notification_deliveries?: number;
3353
+ /** @description Notificaciones de la bandeja que se borraron. */
3354
+ notifications?: number;
3355
+ /** @description Respuestas guardadas de `Idempotency-Key` que se borraron. */
3356
+ idempotency_responses?: number;
3357
+ /** @description Filas de importación masiva cuyo contenido se vació. */
3358
+ import_rows?: number;
3359
+ /** @description Filas de auditoría a las que se les quitaron los cuerpos. Falta cuando ese barrido no se pudo completar. */
3360
+ audit_log_rows?: number;
3361
+ /** @description Eventos de seguridad cuyo contexto se redactó. Falta cuando ese barrido no se pudo completar. */
3362
+ security_events_rows?: number;
3363
+ };
3364
+ };
3365
+ };
3366
+ };
2854
3367
  /** @description Banco participante del catálogo SPEI, en formato JSON:API. `id` y `attributes.code` son siempre iguales (`id` se conserva como identificador estable del recurso aunque `code` lo duplique). */
2855
3368
  BankResource: components["schemas"]["JsonApiResourceBase"] & {
2856
3369
  /**
@@ -3818,7 +4331,7 @@ export interface components {
3818
4331
  */
3819
4332
  url: string;
3820
4333
  /** @description Eventos a los que se suscribe el endpoint webhook. Entre 1 y 10. */
3821
- events: ("validation.completed" | "validation.failed" | "validation.error" | "validation.retry.scheduled" | "validation.retry.resolved" | "validation.retry.exhausted" | "billing.payment_succeeded" | "billing.payment_failed" | "billing.trial_will_end" | "billing.subscription_canceled" | "billing.invoice_upcoming")[];
4334
+ events: ("validation.completed" | "validation.failed" | "validation.error" | "validation.retry.scheduled" | "validation.retry.resolved" | "validation.retry.exhausted" | "validation.returned" | "billing.payment_succeeded" | "billing.payment_failed" | "billing.trial_will_end" | "billing.subscription_canceled" | "billing.invoice_upcoming")[];
3822
4335
  /**
3823
4336
  * @description Etiqueta libre para distinguir el endpoint webhook de los demás.
3824
4337
  * @example Alta de pagos en el ERP
@@ -3838,7 +4351,7 @@ export interface components {
3838
4351
  /** @description Fecha y hora de la última entrega exitosa, en ISO 8601 UTC. `null` cuando el endpoint aún no completó ninguna entrega. */
3839
4352
  last_delivery_at: components["schemas"]["TimestampUTC"] | null;
3840
4353
  /**
3841
- * @description Clave compartida para verificar firmas. **Solo presente** en la respuesta de creación y de rotación del endpoint; se omite en cualquier otra respuesta. Se usa para validar la cabecera `X-Webhook-Signature` de cada entrega.
4354
+ * @description Clave compartida para verificar firmas. **Solo presente** en la respuesta de creación y de rotación del endpoint; se omite en cualquier otra respuesta. Se usa para validar las cabeceras `X-Webhook-Signature` y `X-Webhook-Signature-Timestamped` de cada entrega.
3842
4355
  * @example a0b1c2d3e4f5061728394a5b6c7d8e9f00112233445566778899aabbccddeeff
3843
4356
  */
3844
4357
  secret?: string;
@@ -3860,7 +4373,7 @@ export interface components {
3860
4373
  */
3861
4374
  url: string;
3862
4375
  /** @description Eventos a los que se suscribe el endpoint webhook. Entre 1 y 10. */
3863
- events: ("validation.completed" | "validation.failed" | "validation.error" | "validation.retry.scheduled" | "validation.retry.resolved" | "validation.retry.exhausted" | "billing.payment_succeeded" | "billing.payment_failed" | "billing.trial_will_end" | "billing.subscription_canceled" | "billing.invoice_upcoming")[];
4376
+ events: ("validation.completed" | "validation.failed" | "validation.error" | "validation.retry.scheduled" | "validation.retry.resolved" | "validation.retry.exhausted" | "validation.returned" | "billing.payment_succeeded" | "billing.payment_failed" | "billing.trial_will_end" | "billing.subscription_canceled" | "billing.invoice_upcoming")[];
3864
4377
  /**
3865
4378
  * @description Etiqueta libre para distinguir el endpoint webhook de los demás. `null` la omite; más de 255 caracteres responde `422 webhook_description_too_long`.
3866
4379
  * @example Alta de pagos en el ERP
@@ -3876,7 +4389,7 @@ export interface components {
3876
4389
  */
3877
4390
  url?: string;
3878
4391
  /** @description Nuevos eventos a los que se suscribe el endpoint webhook. Sustituyen a la lista anterior. Entre 1 y 10. */
3879
- events?: ("validation.completed" | "validation.failed" | "validation.error" | "validation.retry.scheduled" | "validation.retry.resolved" | "validation.retry.exhausted" | "billing.payment_succeeded" | "billing.payment_failed" | "billing.trial_will_end" | "billing.subscription_canceled" | "billing.invoice_upcoming")[];
4392
+ events?: ("validation.completed" | "validation.failed" | "validation.error" | "validation.retry.scheduled" | "validation.retry.resolved" | "validation.retry.exhausted" | "validation.returned" | "billing.payment_succeeded" | "billing.payment_failed" | "billing.trial_will_end" | "billing.subscription_canceled" | "billing.invoice_upcoming")[];
3880
4393
  /**
3881
4394
  * @description Nueva etiqueta libre para distinguir el endpoint webhook de los demás. `null` la elimina; más de 255 caracteres responde `422 webhook_description_too_long`.
3882
4395
  * @example Alta de pagos en el ERP
@@ -3943,7 +4456,7 @@ export interface components {
3943
4456
  * @example validation.completed
3944
4457
  * @enum {string}
3945
4458
  */
3946
- event_type: "validation.completed" | "validation.failed" | "validation.error" | "validation.retry.scheduled" | "validation.retry.resolved" | "validation.retry.exhausted" | "billing.payment_succeeded" | "billing.payment_failed" | "billing.trial_will_end" | "billing.subscription_canceled" | "billing.invoice_upcoming" | "test";
4459
+ event_type: "validation.completed" | "validation.failed" | "validation.error" | "validation.retry.scheduled" | "validation.retry.resolved" | "validation.retry.exhausted" | "validation.returned" | "billing.payment_succeeded" | "billing.payment_failed" | "billing.trial_will_end" | "billing.subscription_canceled" | "billing.invoice_upcoming" | "test";
3947
4460
  /**
3948
4461
  * Format: uuid
3949
4462
  * @description Identificador único de la validación (UUID v4) asociada cuando el evento es `validation.*`. `null` cuando el evento es otro.
@@ -4327,10 +4840,30 @@ export interface components {
4327
4840
  type?: "usage_limits";
4328
4841
  /** @description Datos de los límites: los límites por contexto y sus notas. */
4329
4842
  attributes?: {
4330
- /** @description Límites de tasa por contexto. Cada entrada trae sólo los que ese contexto aplica: `api` lleva `ip_per_minute`; `login`, los cuatro. */
4843
+ /** @description Límites de tasa por contexto. Cada entrada trae sólo los que ese contexto aplica: `api` lleva `key_per_minute`, `ip_ceiling_per_minute` e `ip_per_minute`; `webhooks`, `host_per_minute` y `host_global_per_minute`; `login`, los cuatro de IP y correo electrónico. `key_per_minute` y `host_per_minute` los fija el plan de la cuenta. */
4331
4844
  rate_limits?: {
4332
4845
  [key: string]: {
4333
- /** @description Cantidad máxima de peticiones por dirección IP por minuto. */
4846
+ /**
4847
+ * @description Peticiones por minuto de una clave de la cuenta en la API, según su plan. Rige a las peticiones autenticadas.
4848
+ * @example 240
4849
+ */
4850
+ key_per_minute?: number;
4851
+ /**
4852
+ * @description Techo de peticiones por minuto por dirección IP para las peticiones autenticadas, todas las claves de un mismo origen juntas.
4853
+ * @example 1200
4854
+ */
4855
+ ip_ceiling_per_minute?: number;
4856
+ /**
4857
+ * @description Entregas de webhook por minuto que la cuenta puede enviar hacia un mismo host destino, según su plan.
4858
+ * @example 60
4859
+ */
4860
+ host_per_minute?: number;
4861
+ /**
4862
+ * @description Tope de entregas de webhook por minuto hacia un mismo host destino, todos los clientes juntos.
4863
+ * @example 600
4864
+ */
4865
+ host_global_per_minute?: number;
4866
+ /** @description Cantidad máxima de peticiones por dirección IP por minuto. En `api` sólo rige a las peticiones anónimas, sin clave. */
4334
4867
  ip_per_minute?: number;
4335
4868
  /** @description Cantidad máxima de peticiones por dirección IP por hora. */
4336
4869
  ip_per_hour?: number;
@@ -5062,6 +5595,30 @@ export interface components {
5062
5595
  "application/json": components["schemas"]["ErrorResponse"];
5063
5596
  };
5064
5597
  };
5598
+ /** @description El cuerpo de la petición llegó vacío cuando la operación necesita datos (`body_empty`). */
5599
+ BodyEmpty: {
5600
+ headers: {
5601
+ [name: string]: unknown;
5602
+ };
5603
+ content: {
5604
+ /**
5605
+ * @example {
5606
+ * "errors": [
5607
+ * {
5608
+ * "status": "400",
5609
+ * "code": "body_empty",
5610
+ * "detail": "El cuerpo de la petición está vacío."
5611
+ * }
5612
+ * ],
5613
+ * "meta": {
5614
+ * "version": "1.51.0",
5615
+ * "request_id": "2b3c4d5e6f7a"
5616
+ * }
5617
+ * }
5618
+ */
5619
+ "application/json": components["schemas"]["ErrorResponse"];
5620
+ };
5621
+ };
5065
5622
  /** @description Se requiere autenticación o las credenciales son inválidas */
5066
5623
  Unauthorized: {
5067
5624
  headers: {
@@ -5091,11 +5648,11 @@ export interface components {
5091
5648
  headers: {
5092
5649
  /** @description Segundos a esperar antes de reintentar. Coincide con la ventana de rate-limit del endpoint (típicamente 60s para listas, 1-5s para operaciones idempotentes en vuelo). */
5093
5650
  "Retry-After"?: number;
5094
- /** @description Límite de solicitudes configurado para este bucket (emitido sólo en 429). */
5651
+ /** @description Límite de solicitudes configurado para este bucket. Se emite en cada 429 y, en la API autenticada, también en las respuestas correctas, donde es el tope por clave del plan de la cuenta. */
5095
5652
  "X-RateLimit-Limit"?: number;
5096
- /** @description Solicitudes restantes en la ventana actual — siempre 0 en el momento del 429 (emitido sólo en 429). */
5653
+ /** @description Solicitudes restantes en la ventana actual. Siempre 0 en el momento del 429; en una respuesta correcta de la API autenticada es lo que queda del tope por clave. */
5097
5654
  "X-RateLimit-Remaining"?: number;
5098
- /** @description Unix epoch absoluto (segundos) en que se reinicia la ventana. Emitido sólo en 429, junto con Retry-After. Puede existir sobreescritura por endpoint (p. ej. `rate_limited_login`). */
5655
+ /** @description Unix epoch absoluto (segundos) en que se reinicia la ventana. Se emite en cada 429, junto con Retry-After, y en las respuestas correctas de la API autenticada. Puede existir sobreescritura por endpoint (p. ej. `rate_limited_login`). */
5099
5656
  "X-RateLimit-Reset"?: number;
5100
5657
  [name: string]: unknown;
5101
5658
  };
@@ -5223,6 +5780,30 @@ export interface components {
5223
5780
  "application/json": components["schemas"]["ErrorResponse"];
5224
5781
  };
5225
5782
  };
5783
+ /** @description La validación se purgó y este recurso ya no existe (`validation_purged`). */
5784
+ ValidationPurged: {
5785
+ headers: {
5786
+ [name: string]: unknown;
5787
+ };
5788
+ content: {
5789
+ /**
5790
+ * @example {
5791
+ * "errors": [
5792
+ * {
5793
+ * "status": "410",
5794
+ * "code": "validation_purged",
5795
+ * "detail": "La validación se purgó y este recurso ya no existe."
5796
+ * }
5797
+ * ],
5798
+ * "meta": {
5799
+ * "version": "1.61.0",
5800
+ * "request_id": "1a2b3c4d5e6f"
5801
+ * }
5802
+ * }
5803
+ */
5804
+ "application/json": components["schemas"]["ErrorResponse"];
5805
+ };
5806
+ };
5226
5807
  /** @description El recurso no existe o no es visible para el cliente */
5227
5808
  NotFound: {
5228
5809
  headers: {
@@ -5348,7 +5929,7 @@ export interface operations {
5348
5929
  };
5349
5930
  };
5350
5931
  responses: {
5351
- /** @description Veredicto final de la validación. El campo `status` puede ser: `valid`, `not_found`, `cep_unavailable`, `returned` o `error`. Cuando `has_cep: true` el certificado CEP está disponible vía `GET /v1/validations/{id}/cep`. */
5932
+ /** @description Veredicto final de la validación. El campo `status` puede ser: `valid`, `not_found`, `cep_unavailable`, `returned` o `error`. Cuando la respuesta trae `links.cep_pdf` y `links.cep_xml`, el certificado CEP está disponible en `GET /v1/validations/{id}/cep`. */
5352
5933
  200: {
5353
5934
  headers: {
5354
5935
  /** @description Presente solo cuando la petición incluyó la cabecera `Idempotency-Key`. `false` para respuestas frescas; `true` cuando la respuesta es reutilizada desde el caché de idempotencia, con una vigencia de 24 horas por combinación de cuenta, endpoint y clave. */
@@ -5366,7 +5947,7 @@ export interface operations {
5366
5947
  401: components["responses"]["Unauthorized"];
5367
5948
  409: components["responses"]["IdempotencyKeyInProgress"];
5368
5949
  413: components["responses"]["PayloadTooLarge"];
5369
- /** @description Falló la validación de la petición. Códigos típicos: `clave_or_ref_required`, `required` (fecha/monto), `invalid_date`, `invalid_amount`, `invalid_account_format`, `invalid_account_length`, `invalid_clabe_checksum`, `invalid_card_luhn`, `invalid_bank_code` (`emisor`/`receptor` no reconocidos), `intra_bank_no_cep` (emisor y receptor son el mismo banco), `invalid_field_type` (un campo que debe ser texto llegó como arreglo u objeto — p. ej. `emisor`, `receptor` o `referencia_numerica`), `invalid_receptor_participante`, `retry_policy_invalid`, `retry_pending_cap_exceeded`. También se emite cuando se reutiliza `Idempotency-Key` con un cuerpo distinto (`idempotency_key_reused`). Cuando los datos se contradicen entre sí, la petición se rechaza antes de consultar a Banxico con `preflight_failed` y el detalle por campo en `errors` (`clabe_receptor_mismatch` y `tarjeta_receptor_mismatch`: la cuenta pertenece a otro banco que el `receptor`; `cuenta_invalid_luhn`; `clave_fecha_incoherente`; `clave_longitud_invalida`). Ningún rechazo `preflight_failed` de esta ruta consume cuota, sea por datos que se contradicen o por un campo mal formado. */
5950
+ /** @description Falló la validación de la petición. Códigos típicos: `clave_or_ref_required`, `required` (fecha/monto), `invalid_date`, `invalid_amount`, `invalid_account_format`, `invalid_account_length`, `invalid_clabe_checksum`, `invalid_card_luhn`, `invalid_bank_code` (`emisor`/`receptor` no reconocidos), `intra_bank_no_cep` (emisor y receptor son el mismo banco), `invalid_field_type` (un campo que debe ser texto llegó como arreglo u objeto — p. ej. `emisor`, `receptor` o `referencia_numerica`), `invalid_receptor_participante`, `retry_policy_invalid`, `retry_pending_cap_exceeded`, `cuenta_y_candidatas_excluyentes` (`cuenta_beneficiaria` y `cuentas_candidatas` juntas), `cuentas_candidatas_invalidas` (la lista no tiene de 2 al máximo vigente de cuentas válidas y distintas) y `cuenta_unresolvable_after_probes` (ninguna candidata coincidió con la transferencia). También se emite cuando se reutiliza `Idempotency-Key` con un cuerpo distinto (`idempotency_key_reused`). Cuando los datos se contradicen entre sí, la petición se rechaza antes de consultar a Banxico con `preflight_failed` y el detalle por campo en `errors` (`clabe_receptor_mismatch` y `tarjeta_receptor_mismatch`: la cuenta pertenece a otro banco que el `receptor`; `cuenta_invalid_luhn`; `clave_fecha_incoherente`; `clave_longitud_invalida`). También se rechaza con `preflight_failed` cuando falta `cuenta_beneficiaria` (`cuenta_required`). Ningún rechazo `preflight_failed` de esta ruta consume cuota, sea por datos que se contradicen, por un campo mal formado o por una cuenta ausente. */
5370
5951
  422: {
5371
5952
  headers: {
5372
5953
  [name: string]: unknown;
@@ -5424,7 +6005,7 @@ export interface operations {
5424
6005
  401: components["responses"]["Unauthorized"];
5425
6006
  409: components["responses"]["IdempotencyKeyInProgress"];
5426
6007
  413: components["responses"]["PayloadTooLarge"];
5427
- /** @description La imagen o los datos de la petición no son válidos. Códigos posibles: `image_or_image_url_required`, `invalid_image`, `invalid_image_format`, `image_too_large`, `invalid_url`, `invalid_url_scheme`, `url_ssrf_blocked`, `invalid_clabe_checksum`. También puede devolver: `image_too_small`, `image_mime_mismatch`, `image_dimensions_too_large`, `image_decompression_bomb`, `image_polyglot_detected`, `image_url_unreachable`, `image_url_too_large`, `image_url_too_many_redirects`. Con un PDF: `pdf_invalid_structure`, `pdf_encrypted`, `pdf_active_content`, `pdf_hidden_content`, `pdf_modified_after_issue`, `pdf_too_many_pages`, `pdf_unsupported_image`, `pdf_text_layer_too_large` y `pdf_multiple_receipts`. En modo asíncrono, un fallo genérico de la imagen se reporta como `image_invalid`. Reutilizar `Idempotency-Key` con un cuerpo distinto produce `idempotency_key_reused`. */
6008
+ /** @description La imagen o los datos de la petición no son válidos. Códigos posibles: `image_or_image_url_required`, `invalid_image`, `invalid_image_format`, `image_too_large`, `invalid_url`, `invalid_url_scheme`, `url_ssrf_blocked`, `invalid_clabe_checksum`. También puede devolver: `image_too_small`, `image_mime_mismatch`, `image_dimensions_too_large`, `image_decompression_bomb`, `image_polyglot_detected`, `image_url_unreachable`, `image_url_too_large`, `image_url_too_many_redirects`. Con un PDF: `pdf_invalid_structure`, `pdf_encrypted`, `pdf_active_content`, `pdf_hidden_content`, `pdf_modified_after_issue`, `pdf_too_many_pages`, `pdf_unsupported_image`, `pdf_text_layer_too_large` y `pdf_multiple_receipts`. Con `retain_image` que no es booleano: `invalid_retain_image`. Con `cuentas_candidatas`: `cuenta_y_candidatas_excluyentes`, `cuentas_candidatas_invalidas` y, si ninguna candidata coincide, `cuenta_unresolvable_after_probes`. En modo asíncrono, un fallo genérico de la imagen se reporta como `image_invalid`. Reutilizar `Idempotency-Key` con un cuerpo distinto produce `idempotency_key_reused`. */
5428
6009
  422: {
5429
6010
  headers: {
5430
6011
  [name: string]: unknown;
@@ -5483,6 +6064,11 @@ export interface operations {
5483
6064
  * @example scotiabank
5484
6065
  */
5485
6066
  search?: string;
6067
+ /**
6068
+ * @description Coincidencia exacta con la `client_ref` enviada al validar. Distingue mayúsculas, acentos y espacios internos. Un valor vacío o que no cumple las reglas de `client_ref` devuelve un estado HTTP `422` (con `invalid_filter` en el cuerpo).
6069
+ * @example orden-4812
6070
+ */
6071
+ client_ref?: string;
5486
6072
  /**
5487
6073
  * @description Filtro — Muestra solo las validaciones del banco de pruebas (Playground). Si se envía, el único valor admitido es `1`; cualquier otro devuelve un estado HTTP `422`.
5488
6074
  * @example 1
@@ -5583,6 +6169,11 @@ export interface operations {
5583
6169
  * @example MXBA
5584
6170
  */
5585
6171
  search?: string;
6172
+ /**
6173
+ * @description Coincidencia exacta con la `client_ref` enviada al validar. Distingue mayúsculas, acentos y espacios internos. Un valor vacío o que no cumple las reglas de `client_ref` devuelve un estado HTTP `422` (con `invalid_filter` en el cuerpo).
6174
+ * @example orden-4812
6175
+ */
6176
+ client_ref?: string;
5586
6177
  /**
5587
6178
  * @description Filtro — Muestra solo las validaciones del banco de pruebas (Playground). Si se envía, el único valor admitido es `1`; cualquier otro devuelve un estado HTTP `422`.
5588
6179
  * @example 1
@@ -5686,6 +6277,11 @@ export interface operations {
5686
6277
  * @example MXBA20250315001234
5687
6278
  */
5688
6279
  search?: string;
6280
+ /**
6281
+ * @description Coincidencia exacta con la `client_ref` enviada al validar. Distingue mayúsculas, acentos y espacios internos. Un valor vacío o que no cumple las reglas de `client_ref` devuelve un estado HTTP `422` (con `invalid_filter` en el cuerpo).
6282
+ * @example orden-4812
6283
+ */
6284
+ client_ref?: string;
5689
6285
  /**
5690
6286
  * @description Filtro — Muestra solo las validaciones del banco de pruebas (Playground). Si se envía, el único valor admitido es `1`; cualquier otro devuelve un estado HTTP `422`.
5691
6287
  * @example 1
@@ -5901,6 +6497,7 @@ export interface operations {
5901
6497
  "application/json": components["schemas"]["ErrorResponse"];
5902
6498
  };
5903
6499
  };
6500
+ 410: components["responses"]["ValidationPurged"];
5904
6501
  /** @description UUID inválido en la ruta (`invalid_uuid`). */
5905
6502
  422: {
5906
6503
  headers: {
@@ -5967,6 +6564,7 @@ export interface operations {
5967
6564
  "application/json": components["schemas"]["ErrorResponse"];
5968
6565
  };
5969
6566
  };
6567
+ 410: components["responses"]["ValidationPurged"];
5970
6568
  /** @description UUID inválido en la ruta (`invalid_uuid`). */
5971
6569
  422: {
5972
6570
  headers: {
@@ -6033,6 +6631,15 @@ export interface operations {
6033
6631
  "application/json": components["schemas"]["ErrorResponse"];
6034
6632
  };
6035
6633
  };
6634
+ /** @description La imagen no existe por decisión del cliente: la validación se creó con `retain_image=false` (`image_not_retained`) o se purgó (`validation_purged`). */
6635
+ 410: {
6636
+ headers: {
6637
+ [name: string]: unknown;
6638
+ };
6639
+ content: {
6640
+ "application/json": components["schemas"]["ErrorResponse"];
6641
+ };
6642
+ };
6036
6643
  /** @description UUID inválido en la ruta (`invalid_uuid`). */
6037
6644
  422: {
6038
6645
  headers: {
@@ -6078,6 +6685,7 @@ export interface operations {
6078
6685
  "application/json": components["schemas"]["ErrorResponse"];
6079
6686
  };
6080
6687
  };
6688
+ 410: components["responses"]["ValidationPurged"];
6081
6689
  /** @description UUID inválido en la ruta (`invalid_uuid`). */
6082
6690
  422: {
6083
6691
  headers: {
@@ -6148,6 +6756,7 @@ export interface operations {
6148
6756
  "application/json": components["schemas"]["ErrorResponse"];
6149
6757
  };
6150
6758
  };
6759
+ 410: components["responses"]["ValidationPurged"];
6151
6760
  413: components["responses"]["PayloadTooLarge"];
6152
6761
  /** @description Política inválida o precondición no cumplida. `retry_policy_invalid`, la forma, el rango o el resultado no se admiten; `retry_not_supported_for_bulk`, la validación nació de una importación; `retry_not_applicable`, su estado queda fuera de los tres que admiten reintento (`not_found`, `cep_unavailable`, `error`) o cambió mientras tanto; `retry_already_resolved`, el ciclo ya cerró; `retry_age_exceeded`, la validación es más vieja que `max_age_seconds`; `retry_pending_cap_exceeded`, se alcanzó el tope de pendientes de la cuenta de usuario o el de despachados en 24 horas; `reactivation_cap_exceeded`, se alcanzó el tope de reactivaciones de esa validación. */
6153
6762
  422: {
@@ -6206,6 +6815,7 @@ export interface operations {
6206
6815
  "application/json": components["schemas"]["ErrorResponse"];
6207
6816
  };
6208
6817
  };
6818
+ 410: components["responses"]["ValidationPurged"];
6209
6819
  /** @description No hay ciclo de reintentos activo que cancelar (código `retry_not_active`). UUID inválido (`invalid_uuid`). */
6210
6820
  422: {
6211
6821
  headers: {
@@ -6217,6 +6827,198 @@ export interface operations {
6217
6827
  };
6218
6828
  };
6219
6829
  };
6830
+ recheckValidation: {
6831
+ parameters: {
6832
+ query?: never;
6833
+ header?: never;
6834
+ path: {
6835
+ /** @description Identificador (UUID) de la validación */
6836
+ id: components["parameters"]["ValidationId"];
6837
+ };
6838
+ cookie?: never;
6839
+ };
6840
+ requestBody?: never;
6841
+ responses: {
6842
+ /** @description Estado de pago consultado. Devuelve la validación y, en `meta.recheck`, cuándo se consultó, si cambió a `returned` y qué veredicto tenía antes. */
6843
+ 200: {
6844
+ headers: {
6845
+ /** @description ETag débil de la validación después de la consulta. Sigue el formato `W/"{etag_version}-{status}"` y sube en cada consulta, aunque el veredicto no cambie. */
6846
+ ETag?: string;
6847
+ [name: string]: unknown;
6848
+ };
6849
+ content: {
6850
+ "application/json": components["schemas"]["SuccessEnvelope"] & {
6851
+ data?: components["schemas"]["Validation"];
6852
+ meta?: {
6853
+ recheck?: components["schemas"]["ValidationRecheckMeta"];
6854
+ };
6855
+ };
6856
+ };
6857
+ };
6858
+ 401: components["responses"]["Unauthorized"];
6859
+ 403: components["responses"]["Forbidden"];
6860
+ /** @description Validación no encontrada, retirada o ajena a la cuenta de usuario (`not_found`). */
6861
+ 404: {
6862
+ headers: {
6863
+ [name: string]: unknown;
6864
+ };
6865
+ content: {
6866
+ "application/json": components["schemas"]["ErrorResponse"];
6867
+ };
6868
+ };
6869
+ 410: components["responses"]["ValidationPurged"];
6870
+ /** @description La validación no se puede consultar: su estado no es `valid` ni `returned` (código `recheck_not_eligible`, con el estado en `meta.status`) o tiene más horas que la ventana (código `recheck_window_expired`, con la ventana en `meta.window_hours`). UUID inválido (`invalid_uuid`). */
6871
+ 422: {
6872
+ headers: {
6873
+ [name: string]: unknown;
6874
+ };
6875
+ content: {
6876
+ "application/json": components["schemas"]["ErrorResponse"];
6877
+ };
6878
+ };
6879
+ /** @description La validación se consultó hace menos de 10 minutos (código `recheck_rate_limited`). `Retry-After` y `meta.retry_after` dan los segundos que faltan. También responde así el límite de peticiones de la clave de API (`rate_limit_exceeded`). */
6880
+ 429: {
6881
+ headers: {
6882
+ /** @description Segundos que faltan para poder consultar esta validación de nuevo. */
6883
+ "Retry-After"?: number;
6884
+ [name: string]: unknown;
6885
+ };
6886
+ content: {
6887
+ "application/json": components["schemas"]["ErrorResponse"];
6888
+ };
6889
+ };
6890
+ /** @description Banxico no entregó un estado legible, o la consulta de estado está apagada (código `recheck_unavailable`). La validación no cambia y conserva su intervalo. `Retry-After` y `meta.retry_after` sugieren esperar 60 segundos. */
6891
+ 503: {
6892
+ headers: {
6893
+ /** @description Segundos que se sugiere esperar antes de reintentar. */
6894
+ "Retry-After"?: number;
6895
+ [name: string]: unknown;
6896
+ };
6897
+ content: {
6898
+ "application/json": components["schemas"]["ErrorResponse"];
6899
+ };
6900
+ };
6901
+ };
6902
+ };
6903
+ prepareValidationPurge: {
6904
+ parameters: {
6905
+ query?: never;
6906
+ header?: never;
6907
+ path: {
6908
+ /** @description Identificador (UUID) de la validación */
6909
+ id: components["parameters"]["ValidationId"];
6910
+ };
6911
+ cookie?: never;
6912
+ };
6913
+ requestBody?: never;
6914
+ responses: {
6915
+ /** @description Resumen de lo que se borraría y token de confirmación. La validación no cambió. */
6916
+ 200: {
6917
+ headers: {
6918
+ [name: string]: unknown;
6919
+ };
6920
+ content: {
6921
+ "application/json": components["schemas"]["SuccessEnvelope"] & components["schemas"]["ValidationPurgePrepareResponse"];
6922
+ };
6923
+ };
6924
+ 401: components["responses"]["Unauthorized"];
6925
+ 403: components["responses"]["Forbidden"];
6926
+ /** @description Validación no encontrada, o ajena a la cuenta de usuario (`not_found`). */
6927
+ 404: {
6928
+ headers: {
6929
+ [name: string]: unknown;
6930
+ };
6931
+ content: {
6932
+ "application/json": components["schemas"]["ErrorResponse"];
6933
+ };
6934
+ };
6935
+ /** @description La validación sigue en curso (`queued` o `processing`) y todavía no se puede purgar (`purge_validation_in_progress`, con el estado en `meta.status`). */
6936
+ 409: {
6937
+ headers: {
6938
+ [name: string]: unknown;
6939
+ };
6940
+ content: {
6941
+ "application/json": components["schemas"]["ErrorResponse"];
6942
+ };
6943
+ };
6944
+ 410: components["responses"]["ValidationPurged"];
6945
+ /** @description UUID inválido en la ruta (`invalid_uuid`). */
6946
+ 422: {
6947
+ headers: {
6948
+ [name: string]: unknown;
6949
+ };
6950
+ content: {
6951
+ "application/json": components["schemas"]["ErrorResponse"];
6952
+ };
6953
+ };
6954
+ 429: components["responses"]["RateLimited"];
6955
+ };
6956
+ };
6957
+ executeValidationPurge: {
6958
+ parameters: {
6959
+ query?: never;
6960
+ header?: never;
6961
+ path: {
6962
+ /** @description Identificador (UUID) de la validación */
6963
+ id: components["parameters"]["ValidationId"];
6964
+ };
6965
+ cookie?: never;
6966
+ };
6967
+ requestBody: {
6968
+ content: {
6969
+ /**
6970
+ * @example {
6971
+ * "confirmation_token": "eyJhZG1pbl9pZCI6Ii4uLiJ9.q1w2e3r4t5y6u7i8o9p0"
6972
+ * }
6973
+ */
6974
+ "application/json": components["schemas"]["ValidationPurgeExecuteRequest"];
6975
+ };
6976
+ };
6977
+ responses: {
6978
+ /** @description Validación purgada. Devuelve cuándo se purgó, el estado del borrado de los archivos y lo que se borró. */
6979
+ 200: {
6980
+ headers: {
6981
+ [name: string]: unknown;
6982
+ };
6983
+ content: {
6984
+ "application/json": components["schemas"]["SuccessEnvelope"] & components["schemas"]["ValidationPurgeExecuteResponse"];
6985
+ };
6986
+ };
6987
+ 400: components["responses"]["BodyEmpty"];
6988
+ 401: components["responses"]["Unauthorized"];
6989
+ 403: components["responses"]["Forbidden"];
6990
+ /** @description Validación no encontrada, o ajena a la cuenta de usuario (`not_found`). */
6991
+ 404: {
6992
+ headers: {
6993
+ [name: string]: unknown;
6994
+ };
6995
+ content: {
6996
+ "application/json": components["schemas"]["ErrorResponse"];
6997
+ };
6998
+ };
6999
+ /** @description El token ya se usó (`confirmation_token_already_used`), o la validación sigue en curso y todavía no se puede purgar (`purge_validation_in_progress`, con el estado en `meta.status`). */
7000
+ 409: {
7001
+ headers: {
7002
+ [name: string]: unknown;
7003
+ };
7004
+ content: {
7005
+ "application/json": components["schemas"]["ErrorResponse"];
7006
+ };
7007
+ };
7008
+ 410: components["responses"]["ValidationPurged"];
7009
+ 413: components["responses"]["PayloadTooLarge"];
7010
+ /** @description El token no sirve. Códigos posibles: `confirmation_token_missing`, `confirmation_token_malformed`, `confirmation_token_signature_invalid`, `confirmation_token_expired`, `confirmation_token_operation_mismatch` y `purge_token_mismatch` (el token es de otra validación o de otra cuenta). UUID inválido en la ruta (`invalid_uuid`). */
7011
+ 422: {
7012
+ headers: {
7013
+ [name: string]: unknown;
7014
+ };
7015
+ content: {
7016
+ "application/json": components["schemas"]["ErrorResponse"];
7017
+ };
7018
+ };
7019
+ 429: components["responses"]["RateLimited"];
7020
+ };
7021
+ };
6220
7022
  listBanks: {
6221
7023
  parameters: {
6222
7024
  query?: never;
@@ -7681,11 +8483,11 @@ export interface operations {
7681
8483
  */
7682
8484
  status?: "success" | "failed" | "retrying" | "pending";
7683
8485
  /**
7684
- * @description Filtro — Tipo de evento que originó la entrega. **De validaciones**: `validation.completed` cuando termina bien, `validation.failed` cuando termina mal y `validation.error` cuando hay un error del servicio. **De los reintentos automáticos:** `validation.retry.scheduled` al programar un reintento automático, `validation.retry.resolved` cuando un reintento automático encuentra el CEP, y `validation.retry.exhausted` cuando los reintentos se agotan sin encontrar el CEP.\
8486
+ * @description Filtro — Tipo de evento que originó la entrega. **De validaciones**: `validation.completed` cuando termina bien, `validation.failed` cuando termina mal y `validation.error` cuando hay un error del servicio. **De los reintentos automáticos:** `validation.retry.scheduled` al programar un reintento automático, `validation.retry.resolved` cuando un reintento automático encuentra el CEP, y `validation.retry.exhausted` cuando los reintentos se agotan sin encontrar el CEP. **De la revisión posterior de un `valid`:** `validation.returned` cuando una validación que había salido `valid` pasa a `returned` porque Banxico reportó la devolución.\
7685
8487
  * **De la suscripción:** `billing.payment_succeeded` y `billing.payment_failed` por cada cobro, `billing.invoice_upcoming` antes de la siguiente factura, `billing.trial_will_end` antes de que acabe la prueba gratuita, y `billing.subscription_canceled` al cancelar la suscripción. Las entregas sintéticas (envío de prueba) se marcan como `test`.
7686
8488
  * @example validation.completed
7687
8489
  */
7688
- event_type?: "validation.completed" | "validation.failed" | "validation.error" | "validation.retry.scheduled" | "validation.retry.resolved" | "validation.retry.exhausted" | "billing.payment_succeeded" | "billing.payment_failed" | "billing.trial_will_end" | "billing.subscription_canceled" | "billing.invoice_upcoming" | "test";
8490
+ event_type?: "validation.completed" | "validation.failed" | "validation.error" | "validation.retry.scheduled" | "validation.retry.resolved" | "validation.retry.exhausted" | "validation.returned" | "billing.payment_succeeded" | "billing.payment_failed" | "billing.trial_will_end" | "billing.subscription_canceled" | "billing.invoice_upcoming" | "test";
7689
8491
  };
7690
8492
  header?: never;
7691
8493
  path?: never;
@@ -7736,11 +8538,11 @@ export interface operations {
7736
8538
  */
7737
8539
  status?: "success" | "failed" | "retrying" | "pending";
7738
8540
  /**
7739
- * @description Filtro — Tipo de evento que originó la entrega. **De validaciones**: `validation.completed` cuando termina bien, `validation.failed` cuando termina mal y `validation.error` cuando hay un error del servicio. **De los reintentos automáticos:** `validation.retry.scheduled` al programar un reintento automático, `validation.retry.resolved` cuando un reintento automático encuentra el CEP, y `validation.retry.exhausted` cuando los reintentos se agotan sin encontrar el CEP.\
8541
+ * @description Filtro — Tipo de evento que originó la entrega. **De validaciones**: `validation.completed` cuando termina bien, `validation.failed` cuando termina mal y `validation.error` cuando hay un error del servicio. **De los reintentos automáticos:** `validation.retry.scheduled` al programar un reintento automático, `validation.retry.resolved` cuando un reintento automático encuentra el CEP, y `validation.retry.exhausted` cuando los reintentos se agotan sin encontrar el CEP. **De la revisión posterior de un `valid`:** `validation.returned` cuando una validación que había salido `valid` pasa a `returned` porque Banxico reportó la devolución.\
7740
8542
  * **De la suscripción:** `billing.payment_succeeded` y `billing.payment_failed` por cada cobro, `billing.invoice_upcoming` antes de la siguiente factura, `billing.trial_will_end` antes de que acabe la prueba gratuita, y `billing.subscription_canceled` al cancelar la suscripción. Las entregas sintéticas (envío de prueba) se marcan como `test`.
7741
8543
  * @example validation.completed
7742
8544
  */
7743
- event_type?: "validation.completed" | "validation.failed" | "validation.error" | "validation.retry.scheduled" | "validation.retry.resolved" | "validation.retry.exhausted" | "billing.payment_succeeded" | "billing.payment_failed" | "billing.trial_will_end" | "billing.subscription_canceled" | "billing.invoice_upcoming" | "test";
8545
+ event_type?: "validation.completed" | "validation.failed" | "validation.error" | "validation.retry.scheduled" | "validation.retry.resolved" | "validation.retry.exhausted" | "validation.returned" | "billing.payment_succeeded" | "billing.payment_failed" | "billing.trial_will_end" | "billing.subscription_canceled" | "billing.invoice_upcoming" | "test";
7744
8546
  /**
7745
8547
  * @description Formato del archivo a descargar. Valores aceptados: `csv` y `xlsx`. Cualquier otro valor se sirve como `csv`.
7746
8548
  * @example csv