Integración por API
Cómo funciona la API
La API REST de Tavnit permite que tu propio código haga lo mismo que haces en la app: enviar documentos a un Flow, una Colección, un Splitter o un Pipeline; ejecutar Cleaners, Matchers, Inspectores, Fillers, Signals y Agentes; leer y escribir Buckets; gestionar los casos de un Subject, y aprobar o rechazar revisiones humanas.
- URL base:
https://run.tavnit.io/api. Todas las rutas de abajo son relativas a ella. - Cada solicitud lleva tu API key en el encabezado
X-API-Key. - El procesamiento es asíncrono. Los endpoints que inician trabajo responden de inmediato 202 Accepted con un id, y el trabajo corre en segundo plano. Obtienes el resultado consultando (runs, runs de Agentes, Catches, casos) o en un webhook configurado en la función.
Pipelines, Subjects, Matchers, Inspectores, Fillers, Signals y Nets están en Beta. Sus endpoints ya funcionan, pero algunos detalles todavía pueden cambiar.
Autenticación e IDs
API key
Abre Integraciones en la barra lateral de la app. La tarjeta Clave API muestra tu key (ahí puedes revelarla y copiarla). Cada miembro tiene su propia key en cada organización, y una solicitud actúa como ese miembro en esa organización.
Mantén tu API key en secreto. Regenerar, en la misma tarjeta, invalida la key actual de inmediato, y todo lo que la siga usando deja de funcionar.
Una solicitud sin una key válida recibe:
{
"success": false,
"error": "Authentication required",
"message": "Please provide a valid X-API-Key header"
}Roles
La key lleva tu rol. Los miembros con el rol Solo HITL solo pueden usar los endpoints de aprobar y rechazar revisiones humanas y los de la API key. Todos los endpoints de procesamiento y de datos los rechazan con 403 y Your role only permits HITL reviews. Consulta roles de usuario.
IDs
Cada Flow, Colección, Splitter, Cleaner, Bucket, Agente, Matcher, Inspector, Filler y Pipeline muestra su ID en su página de detalle, con un botón para copiarlo. Los recursos deben pertenecer a la organización de tu key: el ID de otra organización responde 403 o 404.
Envío de archivos
Los endpoints que reciben un documento lo aceptan de dos formas:
Envía el archivo como multipart/form-data en un campo llamado file, con los demás campos como campos del formulario. Funciona en todos los endpoints de archivos.
Envía un JSON con file_base64 (el contenido del archivo) y filename (con su extensión), más los demás campos. Es útil cuando una herramienta de automatización te da base64 en lugar de un archivo.
| Endpoint | Base64 | Archivos aceptados |
|---|---|---|
| POST /runs/process | Sí | PDF, imágenes (PNG, JPG, JPEG, JFIF, TIF, TIFF, WEBP, BMP, GIF), hojas de cálculo (XLSX, XLS, CSV) |
| POST /collections/process | Sí | Igual que runs |
| POST /splits/run | Sí | Igual que runs |
| POST /pipelines/{id}/execute | Sí | PDF e imágenes |
| POST /signals/{id}/run | Sí | Audio: MP3, MP4, MPEG, MPGA, M4A, WAV, WEBM |
| POST /sweeps/run | No | Hojas de cálculo: CSV, XLSX, XLS |
| Inspectores, Fillers, Subjects y casos | No | El documento como archivo multipart |
Una solicitud puede pesar hasta 150 MB. El tipo de archivo se toma de la extensión del nombre.
Respuestas y errores
Las respuestas son JSON con un indicador success. Los errores traen un texto en error, a veces un message y claves adicionales que explican el problema:
{
"success": false,
"error": "Bucket mismatch",
"message": "bucket_name does not match the target bucket. Verify both bucket_id and bucket_name before retrying."
}| Código | Significado |
|---|---|
| 200 / 201 | Hecho (lecturas, cancelaciones, aprobaciones) / creado (casos, fills, inspecciones). |
| 202 | Aceptado: el trabajo quedó en cola. Guarda el id que devuelve. |
| 400 | Falta un campo obligatorio o no es válido, el tipo de archivo no es compatible, o el recurso está inactivo o sin configurar. |
| 401 | Falta la X-API-Key o no es válida. |
| 402 | Tu organización no puede iniciar trabajo nuevo en este momento; contacta al equipo de Tavnit. |
| 403 | El recurso es de otra organización, tu rol es Solo HITL o no eres revisor de ese elemento. |
| 404 | El ID no existe en tu organización. |
| 409 | Conflicto con el estado actual: nombre de Bucket que no coincide, ya cancelado o terminado, caso cerrado, espacio ya ocupado. |
| 429 | Demasiados runs esperando turno en un Agente. |
| 500 | Error inesperado. Puedes reintentar más tarde. |
Referencia de endpoints
| Función | Método y ruta | Qué hace |
|---|---|---|
| Flows | POST /runs/process | Extrae un documento con un Flow |
| Flows | GET /runs/{run_id} | Estado del run y datos extraídos |
| Flows | GET /runs/{run_id}/source-file | El documento original |
| Colecciones | POST /collections/process | La IA dirige el documento al Flow o Splitter correcto |
| Colecciones | GET /collection-runs/{id}/source-file | El documento original |
| Splitters | POST /splits/run | Divide un archivo con varios documentos |
| Splitters | GET /splits/{split_id}/source-file | El archivo original completo |
| Cleaners | POST /sweeps/run | Sweep de una hoja de cálculo |
| Cleaners | POST /cleaners/{cleaner_id}/process | Sweep de filas enviadas como JSON |
| Buckets | POST /buckets/write | Agrega o reemplaza filas |
| Buckets | GET /buckets/read | Lee filas, paginadas |
| Agentes | POST /bots/{agent_id}/runs | Inicia un run del Agente |
| Agentes | GET /bot-runs/{bot_run_id} | Consulta un run del Agente |
| Agentes | GET /bots/{agent_id}/runs | Lista los runs de un Agente |
| Agentes | POST /bot-runs/{bot_run_id}/cancel | Cancela un run del Agente |
| Matchers | POST /matchers/{matcher_id}/run | Compara runs completados |
| Inspectores | POST /inspectors/{inspector_id}/process | Agrega un documento a una inspección |
| Fillers | POST /fillers/{filler_id}/fills | Abre un fill y agrega documentos |
| Pipelines | POST /pipelines/{pipeline_id}/execute | Ejecuta un Pipeline |
| Signals | POST /signals/{signal_id}/run | Estructura un archivo de audio (una Wave) |
| Subjects | POST /subjects/{subject_id}/process | Dirige un documento a un caso |
| Nets | POST /nets/{net_id}/catch | Inicia un Catch |
| Revisión Humana | POST /runs/{run_id}/hitl/approve | Aprueba o rechaza elementos en pausa |
| API key | GET /me/api-key | Lee o regenera tu key |
Abajo se detalla cada función, con sus demás endpoints.
Flows: procesa un documento
Envía un documento a un Flow. Tavnit crea un run y lo extrae en segundo plano.
| Campo | Obligatorio | Descripción |
|---|---|---|
| flow_id | Sí | El Flow que extrae el documento. |
| file | Sí* | El documento (multipart). |
| file_base64 + filename | Sí* | En lugar de file: el contenido en base64 y el nombre del archivo con su extensión. |
| content_type | No | Tipo MIME de un archivo en base64. |
| source | No | Etiqueta que se guarda en el run: api (predeterminada), email, manual_upload o collection. |
import requests
API_KEY = "YOUR_API_KEY"
FLOW_ID = "YOUR_FLOW_ID"
# ─────────────────────────────────────────────────────────────
# Option 1: Multipart file upload (binary)
# ─────────────────────────────────────────────────────────────
with open("document.pdf", "rb") as file:
response = requests.post(
"https://run.tavnit.io/api/runs/process",
headers={"X-API-Key": API_KEY},
data={
"flow_id": FLOW_ID,
"source": "api"
},
files={"file": file}
)
print(response.json())
# ─────────────────────────────────────────────────────────────
# Option 2: Base64-encoded file (JSON body)
# ─────────────────────────────────────────────────────────────
import base64
with open("document.pdf", "rb") as file:
file_base64 = base64.b64encode(file.read()).decode("utf-8")
response = requests.post(
"https://run.tavnit.io/api/runs/process",
headers={
"X-API-Key": API_KEY,
"Content-Type": "application/json"
},
json={
"flow_id": FLOW_ID,
"source": "api",
"filename": "document.pdf",
"file_base64": file_base64
}
)
print(response.json()){
"success": true,
"run_id": "8f1c2b7e-4d3a-4a91-9c11-2f7b6e0d5a44",
"status": "queued",
"auto_created_run": true,
"message": "Run accepted for background processing. Poll the run for status or await the webhook."
}Errores: 400 (sin archivo, sin flow_id, archivo no compatible o inválido), 403 (Flow de otra organización), 404 (Flow no encontrado). Una solicitud rechazada igual crea un run fallido cuando puede, y devuelve su run_id para que lo encuentres en Runs.
Consulta el run y sus datos
Consulta hasta que status sea final. Estados: queued, running, awaiting_approval (en pausa para revisión humana), completed, failed y cancelled. data trae las filas extraídas y sigue en null hasta que el run se completa, incluso mientras espera aprobación. Si columns viene con valor, úsalo para el orden de las columnas. attempt y previous_attempts muestran los reintentos automáticos. Agrega ?include_document=true para recibir también un enlace firmado al archivo original. Funciona con todos los runs, incluidos los creados por Colecciones, Splitters, Pipelines y correo.
{
"success": true,
"run_id": "8f1c2b7e-4d3a-4a91-9c11-2f7b6e0d5a44",
"status": "completed",
"flow_id": "3a9d51c0-77b2-4e18-9f6d-0c4a1b8e2d63",
"flow_name": "Supplier Invoices",
"source": "api",
"original_filename": "invoice.pdf",
"mime_type": "application/pdf",
"byte_size": 182734,
"pages_detected": 3,
"pages_processed": 3,
"created_at": "2026-09-01T14:02:11Z",
"started_at": "2026-09-01T14:02:13Z",
"finished_at": "2026-09-01T14:02:41Z",
"attempt": 1,
"previous_attempts": [],
"error_message": null,
"data": [
{ "Invoice Number": "001", "Vendor": "Acme Corp", "Total": 270.30 }
],
"columns": null
}import time
import requests
API_KEY = "YOUR_API_KEY"
HEADERS = {"X-API-Key": API_KEY}
with open("invoice.pdf", "rb") as f:
submit = requests.post(
"https://run.tavnit.io/api/runs/process",
headers=HEADERS,
data={"flow_id": "YOUR_FLOW_ID"},
files={"file": f},
)
run_id = submit.json()["run_id"]
while True:
run = requests.get(f"https://run.tavnit.io/api/runs/{run_id}", headers=HEADERS).json()
if run["status"] in ("completed", "failed", "cancelled"):
break
time.sleep(5)
print(run["status"], run["data"])Obtén el documento original
Devuelve una URL firmada al archivo tal como se subió, sin importar el estado del run. expires_in (opcional) define la vigencia del enlace en segundos (de 60 a 604800; por defecto 7 días). Con ?download=true la respuesta es el archivo en sí.
{
"success": true,
"kind": "run",
"run_id": "8f1c2b7e-4d3a-4a91-9c11-2f7b6e0d5a44",
"original_filename": "invoice.pdf",
"mime_type": "application/pdf",
"byte_size": 182734,
"bucket": "files",
"path": "<org_id>/<run_id>/invoice.pdf",
"url": "https://...signed-url...",
"expires_in": 604800
}Colecciones: deja que la IA dirija el documento
Envía un documento sin elegir el Flow: la IA escoge el mejor Flow o Splitter de la Colección. Úsalo cuando recibes tipos de documento mezclados.
El mismo cuerpo que /runs/process, con collection_id en lugar de flow_id (o pon el ID en la ruta: /collections/{collection_id}/process). La Colección debe estar activa y tener al menos un Flow o Splitter activo; si no, la llamada responde 400.
import requests
API_KEY = "YOUR_API_KEY"
COLLECTION_ID = "YOUR_COLLECTION_ID"
# ─────────────────────────────────────────────────────────────
# Option 1: Multipart file upload (binary)
# ─────────────────────────────────────────────────────────────
with open("document.pdf", "rb") as file:
response = requests.post(
"https://run.tavnit.io/api/collections/process",
headers={"X-API-Key": API_KEY},
data={
"collection_id": COLLECTION_ID,
"source": "api"
},
files={"file": file}
)
print(response.json())
# ─────────────────────────────────────────────────────────────
# Option 2: Base64-encoded file (JSON body)
# ─────────────────────────────────────────────────────────────
import base64
with open("document.pdf", "rb") as file:
file_base64 = base64.b64encode(file.read()).decode("utf-8")
response = requests.post(
"https://run.tavnit.io/api/collections/process",
headers={
"X-API-Key": API_KEY,
"Content-Type": "application/json"
},
json={
"collection_id": COLLECTION_ID,
"source": "api",
"filename": "document.pdf",
"file_base64": file_base64
}
)
print(response.json()){
"success": true,
"data": {
"collection_run_id": "b21e9f34-8c55-4d70-a6e2-91f0c7d43a18",
"status": "queued"
}
}El Flow elegido crea un run normal, y el payload de su webhook incluye collection_run_id para que relaciones el resultado con tu solicitud. El original está disponible de inmediato en GET /collection-runs/{collection_run_id}/source-file (con las mismas opciones que el archivo original de un run). Consulta Colecciones.
Splitters: divide un archivo con varios documentos
Envía un archivo que contiene varios documentos. El Splitter detecta dónde empieza y termina cada uno, lo clasifica y envía cada parte a donde indique su tipo de documento.
El mismo cuerpo que /runs/process, con splitter_id.
import requests
API_KEY = "YOUR_API_KEY"
SPLITTER_ID = "YOUR_SPLITTER_ID"
# ─────────────────────────────────────────────────────────────
# Option 1: Multipart file upload (binary)
# ─────────────────────────────────────────────────────────────
with open("document.pdf", "rb") as file:
response = requests.post(
"https://run.tavnit.io/api/splits/run",
headers={"X-API-Key": API_KEY},
data={
"splitter_id": SPLITTER_ID,
"source": "api"
},
files={"file": file}
)
print(response.json())
# ─────────────────────────────────────────────────────────────
# Option 2: Base64-encoded file (JSON body)
# ─────────────────────────────────────────────────────────────
import base64
with open("document.pdf", "rb") as file:
file_base64 = base64.b64encode(file.read()).decode("utf-8")
response = requests.post(
"https://run.tavnit.io/api/splits/run",
headers={
"X-API-Key": API_KEY,
"Content-Type": "application/json"
},
json={
"splitter_id": SPLITTER_ID,
"source": "api",
"filename": "document.pdf",
"file_base64": file_base64
}
)
print(response.json()){
"success": true,
"split_id": "c74a0b12-3e69-4f85-b0d7-58e2a9c61f70",
"status": "pending",
"pages_count": 12,
"message": "Split queued for processing."
}Las partes enviadas a Flows se convierten en runs propios, y sus webhooks traen split_id. El archivo original completo está en GET /splits/{split_id}/source-file. Consulta Splitters.
Cleaners: ejecuta un sweep
Un sweep pasa un Cleaner por filas de datos para normalizar, clasificar, buscar o enriquecer valores. Envía las filas como hoja de cálculo o como JSON.
| Campo | Obligatorio | Descripción |
|---|---|---|
| cleaner_id | Sí | El Cleaner que se ejecuta. |
| file | Sí | CSV, XLSX o XLS, solo multipart. Encabezados en la primera fila; cada campo base que el Cleaner exige debe ser una columna, sin duplicados. |
| sheet_name | No | Qué hoja del libro leer (por defecto, la primera). |
Envía un JSON con rows (un arreglo de objetos), o un file multipart como el de arriba.
{
"rows": [
{ "Vendor": "acme corp.", "Country": "usa" },
{ "Vendor": "GLOBEX INC", "Country": "Mexico" }
]
}import requests
API_KEY = "YOUR_API_KEY"
CLEANER_ID = "YOUR_CLEANER_ID"
# ─────────────────────────────────────────────────────────────
# Option 1: Sweep a spreadsheet (CSV, XLSX or XLS, multipart only)
# Column headers must be on the first row.
# ─────────────────────────────────────────────────────────────
with open("vendors.csv", "rb") as f:
response = requests.post(
"https://run.tavnit.io/api/sweeps/run",
headers={"X-API-Key": API_KEY},
data={"cleaner_id": CLEANER_ID},
files={"file": ("vendors.csv", f, "text/csv")},
)
print(response.json()) # 202: {"sweep_id": "...", "status": "queued", ...}
# ─────────────────────────────────────────────────────────────
# Option 2: Send the rows as JSON
# ─────────────────────────────────────────────────────────────
response = requests.post(
f"https://run.tavnit.io/api/cleaners/{CLEANER_ID}/process",
headers={"X-API-Key": API_KEY},
json={
"rows": [
{"Vendor": "acme corp.", "Country": "usa"},
{"Vendor": "GLOBEX INC", "Country": "Mexico"}
]
},
)
print(response.json()){
"success": true,
"sweep_id": "5d2e8a61-0b4f-4c3e-9a7d-1f6b2c8e4a90",
"status": "queued",
"cleaner_id": "YOUR_CLEANER_ID",
"message": "Sweep queued for processing."
}Un Cleaner con una configuración inválida responde 400 con validation_errors. Consulta Cleaners.
Buckets: escribe y lee filas
Envía filas a un Bucket desde tus propios sistemas, o lee lo que tus Flows guardaron ahí. El ID y el nombre del Bucket aparecen al tocar el ícono de información en su página. El nombre es una verificación de seguridad: si no coincide con el ID, la llamada responde 409.
| Campo | Obligatorio | Descripción |
|---|---|---|
| bucket_id | Sí | El Bucket. |
| bucket_name | Sí | Su nombre exacto. |
| overwrite | Sí | Booleano. false agrega las filas; true reemplaza todas las filas existentes. |
| rows | Sí | Arreglo de objetos, hasta 50,000 por solicitud. |
Envía el cuerpo como application/json. Cada fila debe tener exactamente las columnas del Bucket, por nombre de columna o nombre visible: una columna faltante o desconocida cancela toda la escritura con 400 e indica missing_columns y extra_columns.
import requests
API_KEY = "YOUR_API_KEY"
BUCKET_ID = "YOUR_BUCKET_ID"
BUCKET_NAME = "YOUR_BUCKET_NAME"
# ─────────────────────────────────────────────────────────────
# Append rows to existing data (overwrite=False)
# ─────────────────────────────────────────────────────────────
response = requests.post(
"https://run.tavnit.io/api/buckets/write",
headers={
"X-API-Key": API_KEY,
"Content-Type": "application/json"
},
json={
"bucket_id": BUCKET_ID,
"bucket_name": BUCKET_NAME,
"overwrite": False,
"rows": [
{"invoice_number": "INV-1001", "vendor": "Acme Corp", "amount": 1200.50},
{"invoice_number": "INV-1002", "vendor": "Globex", "amount": 430.00}
]
}
)
print(response.json())
# ─────────────────────────────────────────────────────────────
# Replace all rows (overwrite=True)
# ─────────────────────────────────────────────────────────────
response = requests.post(
"https://run.tavnit.io/api/buckets/write",
headers={
"X-API-Key": API_KEY,
"Content-Type": "application/json"
},
json={
"bucket_id": BUCKET_ID,
"bucket_name": BUCKET_NAME,
"overwrite": True,
"rows": [
{"invoice_number": "INV-3001", "vendor": "NewCo", "amount": 400.00}
]
}
)
print(response.json()){
"success": true,
"message": "Bucket write queued for background processing.",
"bucket_id": "YOUR_BUCKET_ID",
"bucket_name": "Invoices 2026",
"bucket_write_id": "e3a1c9d2-7f40-4b8e-a5c6-2d9f1b0e7a34",
"overwrite": false,
"rows_queued": 2,
"status": "queued"
}Lee filas
Parámetros de consulta: bucket_id y bucket_name (obligatorios), limit (de 1 a 1000; por defecto 100) y offset (por defecto 0). Avanza con offset mientras has_more sea true; total_count cuenta todas las filas. Las claves de data en cada fila son los nombres de columna; usa columns para los nombres visibles. Los enlaces a archivos guardados llegan como URLs firmadas nuevas.
curl "https://run.tavnit.io/api/buckets/read?bucket_id=YOUR_BUCKET_ID&bucket_name=Invoices%202026&limit=100&offset=0" \
-H "X-API-Key: YOUR_API_KEY"{
"success": true,
"bucket_id": "YOUR_BUCKET_ID",
"bucket_name": "Invoices 2026",
"columns": [
{ "name": "invoice_number", "display_name": "Invoice #", "data_type": "text" },
{ "name": "amount", "display_name": "Amount", "data_type": "number" }
],
"rows": [
{
"id": "0c6f...",
"row_number": 1,
"source_type": "api",
"created_at": "2026-09-01T14:05:00Z",
"updated_at": "2026-09-01T14:05:00Z",
"data": { "invoice_number": "INV-1001", "amount": 1200.5 }
}
],
"total_count": 1234,
"limit": 100,
"offset": 0,
"has_more": true
}Consulta Buckets.
Agentes: inicia y consulta runs
Inicia un Agente desde tu código y recoge lo que capturó. Los Agentes se habilitan por organización a pedido: contacta a soporte para activarlos.
El JSON opcional {"inputs": {...}} reemplaza las variables de entrada del Agente para este run. Solo se usan las variables que el Agente declara, y nunca se aceptan valores secretos. También puedes llamar a POST /bots/runs con bot_id en el cuerpo. Cada llamada inicia un run nuevo.
curl -X POST "https://run.tavnit.io/api/bots/YOUR_AGENT_ID/runs" \
-H "X-API-Key: YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{"inputs": {"invoice_month": "2026-08"}}'
# 202
{ "success": true, "bot_run_id": "a7c3...", "status": "queued" }status es queued, o waiting cuando el Agente ejecuta un run a la vez y está ocupado (empieza solo cuando le llega el turno). 409 si el Agente está archivado, 429 si ya hay demasiados runs esperando.
Consulta, lista y cancela
| Endpoint | Qué hace |
|---|---|
| GET /bot-runs/{bot_run_id} | Un run: estado, tiempos, input (sin secretos) y output con enlaces firmados a archivos. También en GET /bots/{agent_id}/runs/{bot_run_id}. |
| GET /bots/{agent_id}/runs | Del más reciente al más antiguo, sin input ni output. Consulta: status (queued, running, completed, failed, cancelled), limit (de 1 a 100; por defecto 20), offset. Devuelve runs y total. |
| POST /bot-runs/{bot_run_id}/cancel | Cancela un run en espera, en cola o en ejecución. 409 si el run ya terminó. También en POST /bots/{agent_id}/runs/{bot_run_id}/cancel. |
{
"success": true,
"run": {
"id": "a7c3...",
"bot_id": "YOUR_AGENT_ID",
"status": "completed",
"source": "api",
"created_at": "2026-09-01T09:00:00Z",
"started_at": "2026-09-01T09:00:04Z",
"finished_at": "2026-09-01T09:03:10Z",
"duration_seconds": 186,
"llm_requests": 9,
"error_message": null,
"replay_url": "https://...",
"input": { "invoice_month": "2026-08" },
"output": { "...": "what the agent captured, file links signed" }
}
}Consulta Agentes.
Matchers: compara runs
Compara runs completados del Flow del Matcher, por ejemplo facturas contra órdenes de compra.
| Campo | Obligatorio | Descripción |
|---|---|---|
| run_ids | Sí | Dos o más runs completados del Flow del Matcher. |
| benchmark_run_id | En modo benchmark | El run contra el que se comparan los demás. |
curl -X POST "https://run.tavnit.io/api/matchers/YOUR_MATCHER_ID/run" \
-H "X-API-Key: YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{"run_ids": ["RUN_A", "RUN_B"], "benchmark_run_id": "RUN_A"}'
# 202
{
"success": true,
"match_id": "...",
"status": "queued",
"mode": "benchmark",
"run_ids": ["RUN_A", "RUN_B"]
}No hay un endpoint de API para leer un match: recibe el resultado en el webhook o la salida por correo del Matcher, o en la app. Consulta Matchers.
Inspectores: revisa un conjunto de documentos
Una inspección reúne documentos, dirige cada uno a un espacio del Inspector, lo extrae y evalúa la lista de verificación.
file multipart. Sin inspection_id se crea una inspección nueva; envía el inspection_id devuelto para agregarle más documentos (debe seguir recibiendo archivos; si no, 409). El Inspector debe estar activo.
curl -X POST "https://run.tavnit.io/api/inspectors/YOUR_INSPECTOR_ID/process" \
-H "X-API-Key: YOUR_API_KEY" \
-F "file=@bill_of_lading.pdf"
# 202 — send the next files with -F "inspection_id=..."
{
"success": true,
"inspection_id": "...",
"inspection_file_id": "...",
"status": "queued"
}| Endpoint | Qué hace |
|---|---|
| POST /inspectors/{inspector_id}/inspections | Crea una inspección vacía (201) para agregarle documentos después. |
| POST /inspections/{inspection_id}/fire | Deja de recibir archivos y evalúa ahora. 400 con missing_inputs si a un espacio obligatorio le falta documento. |
El resultado llega al webhook o a la salida por correo del Inspector. Consulta Inspectores.
Fillers: llena formularios PDF
Un fill reúne los documentos que necesita un Filler, los extrae y escribe los valores en las plantillas PDF del Filler.
| Endpoint | Qué hace |
|---|---|
| POST /fillers/{filler_id}/fills | Abre un fill (201, devuelve fill_id). El Filler necesita una plantilla y el mapeo de campos. |
| POST /fills/{fill_id}/route-upload | Archivo multipart; la IA lo dirige a un espacio libre (202). |
| POST /fills/{fill_id}/inputs/{input_id}/upload | Archivo multipart para un espacio concreto; inicia el run de ese espacio (202). |
| POST /fills/{fill_id}/inputs/{input_id}/attach-run | JSON run_id: reutiliza un run completado para un espacio (202). |
| POST /fills/{fill_id}/fire | Llena ahora en lugar de esperar todos los espacios. 400 con missing_inputs si un espacio obligatorio está vacío. |
| POST /fillers/{filler_id}/templates | Agrega una plantilla PDF (archivo multipart, name opcional). Mapea sus campos en la app. |
# 1. Open a fill (201)
curl -X POST "https://run.tavnit.io/api/fillers/YOUR_FILLER_ID/fills" \
-H "X-API-Key: YOUR_API_KEY"
# 2. Upload documents and let AI pick the slot (202)
curl -X POST "https://run.tavnit.io/api/fills/FILL_ID/route-upload" \
-H "X-API-Key: YOUR_API_KEY" \
-F "file=@passport.jpg"
# 3. Optional: fill now instead of waiting for every slot (202)
curl -X POST "https://run.tavnit.io/api/fills/FILL_ID/fire" \
-H "X-API-Key: YOUR_API_KEY"Los PDF llenos llegan al webhook o a la salida por correo del Filler. Consulta Fillers.
Pipelines: ejecuta
Inicia una ejecución de un Pipeline con un documento.
file multipart o file_base64 + filename; PDF o imagen. 400 si el Pipeline está inactivo o su grafo no puede ejecutarse (con validation_errors).
curl -X POST "https://run.tavnit.io/api/pipelines/YOUR_PIPELINE_ID/execute" \
-H "X-API-Key: YOUR_API_KEY" \
-F "file=@invoice.pdf"
# 202
{
"success": true,
"execution_id": "...",
"pipeline_id": "YOUR_PIPELINE_ID",
"status": "running"
}Cancela con POST /pipelines/executions/{execution_id}/cancel (409 si no está en ejecución). Los resultados salen por los nodos Salida del Pipeline. Consulta Pipelines.
Signals: estructura un archivo de audio
Envía una grabación y el Signal la convierte en datos estructurados (una Wave).
file multipart o base64. Audio de hasta 150 MB y 8 horas, con un máximo de 2 horas de voz detectada.
curl -X POST "https://run.tavnit.io/api/signals/YOUR_SIGNAL_ID/run" \
-H "X-API-Key: YOUR_API_KEY" \
-F "file=@sales_call.mp3"
# 202
{
"success": true,
"wave_id": "...",
"signal_id": "YOUR_SIGNAL_ID",
"status": "queued",
"audio_seconds": 754,
"auto_created_wave": true
}El resultado llega al webhook del Signal o a la app. Consulta Signals.
Subjects y casos
Archiva documentos en los casos de un Subject y gestiona los casos desde tu código.
| Endpoint | Qué hace |
|---|---|
| POST /subjects/{subject_id}/process | Archivo multipart; Tavnit lo dirige a un caso (202, devuelve subject_doc_id). |
| POST /cases/{case_id}/docs | Archivo multipart directo a un caso, sin enrutamiento. doc_type_id es obligatorio salvo que el Subject tenga un solo tipo de documento. Devuelve el run_id (202). 409 si el caso está cerrado o ese tipo de documento ya está cubierto. |
| POST /subjects/{subject_id}/docs/{doc_id}/assign | JSON case_id y doc_type_id: archiva a mano un documento retenido (202). |
| POST /subjects/{subject_id}/cases | JSON name (obligatorio, único, hasta 200 caracteres) y params (objeto opcional). Crea un caso (201). 409 si el nombre ya existe. |
| GET /subjects/{subject_id}/cases | Consulta: state (open o closed), status, search, limit (hasta 200; por defecto 50), offset. Devuelve cases y total. |
| GET /cases/{case_id} | El caso y sus documentos, cada uno con el run_id para consultar en GET /runs/{run_id}. |
| POST /cases/{case_id}/close | Cierra el caso (200). Los documentos nuevos para él quedan retenidos en lugar de archivarse. 409 si ya está cerrado. |
| POST /cases/{case_id}/reopen | Lo reabre (200). 409 si está abierto. |
| POST /cases/{case_id}/inspections | JSON subject_inspector_id: ejecuta un Inspector vinculado sobre los runs completados del caso (202). |
# Create a case (201)
curl -X POST "https://run.tavnit.io/api/subjects/YOUR_SUBJECT_ID/cases" \
-H "X-API-Key: YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{"name": "Shipment 4471", "params": {"customer": "Acme"}}'
# Upload a document straight into that case (202)
curl -X POST "https://run.tavnit.io/api/cases/CASE_ID/docs" \
-H "X-API-Key: YOUR_API_KEY" \
-F "file=@invoice.pdf" \
-F "doc_type_id=DOC_TYPE_ID"{
"success": true,
"case": {
"id": "...",
"subject_id": "YOUR_SUBJECT_ID",
"ref": "<minted from the subject's prefix>",
"seq": 42,
"name": "Shipment 4471",
"state": "open",
"status": "<the subject's default case status>",
"params": { "customer": "Acme" },
"created_by": "...",
"created_at": "2026-09-01T10:00:00Z",
"updated_at": "2026-09-01T10:00:00Z",
"closed_at": null,
"closed_by": null
}
}Consulta Subjects.
Nets: inicia un Catch
Las Nets se habilitan por organización. Sin acceso, estos endpoints responden 403.
Sin cuerpo, el Catch continúa donde terminó el anterior. Envía window_start y/o window_end (fechas ISO) para recuperar un rango específico. 409 si la Net está inactiva o ya hay en curso un Catch que continúa desde el anterior.
curl -X POST "https://run.tavnit.io/api/nets/YOUR_NET_ID/catch" \
-H "X-API-Key: YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{}'
# 202
{ "success": true, "catch_id": "...", "net_id": "YOUR_NET_ID", "status": "queued", "window_mode": "since_last" }Consulta GET /catches/{catch_id}: estado, etapa, conteos y, una vez completado, output con columnas y filas. Cancela con POST /catches/{catch_id}/cancel. Consulta Nets.
Revisión Humana: aprueba o rechaza
Los elementos en pausa para revisión se pueden aprobar o rechazar desde tus propias herramientas. Solo puede hacerlo un revisor configurado de ese Flow, Matcher, Inspector o Filler (si no, 403), y el elemento debe estar en awaiting_approval (si no, 409). Estos endpoints están abiertos al rol Solo HITL.
| Endpoint | Cuerpo |
|---|---|
| POST /runs/{run_id}/hitl/approve | output_json (obligatorio): las filas finales; diff (lista opcional de ediciones). 400 con missing_fields si falta un campo obligatorio de entrada humana. |
| POST /matches/{match_id}/hitl/approve | groups (la agrupación final), excluded, diff. |
| POST /inspections/{inspection_id}/hitl/approve | waivers (item_id y reason de cada punto fallido que se dispensa), diff. |
| POST /fills/{fill_id}/hitl/approve | values (valores de campos por plantilla), diff, allow_missing_human_fields. |
| .../hitl/reject | Las mismas rutas terminadas en /hitl/reject, con un reason opcional. |
curl -X POST "https://run.tavnit.io/api/runs/RUN_ID/hitl/approve" \
-H "X-API-Key: YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{"output_json": {"rows": [{"Invoice Number": "001", "Total": 270.30}]}, "diff": []}'
curl -X POST "https://run.tavnit.io/api/runs/RUN_ID/hitl/reject" \
-H "X-API-Key: YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{"reason": "Wrong vendor"}'Aprobar reanuda la entrega (webhook, correo, Bucket). Rechazar un run lo cancela. Consulta Revisión Humana.
Endpoints de la API key
| Endpoint | Qué hace |
|---|---|
| GET /me/api-key | Devuelve tu key para la organización. |
| POST /me/api-key/regenerate | Emite una key nueva e invalida la anterior al instante. Actualiza todas tus integraciones. |
{
"success": true,
"api_key": "tvnt_...",
"user_id": "...",
"org_id": "..."
}Herramientas de automatización
No necesitas escribir código para conectar Tavnit con tus flujos de trabajo. Cualquier plataforma de automatización que pueda enviar una solicitud HTTP puede iniciar trabajo en Tavnit, y cualquiera que pueda recibir un webhook puede recoger los resultados.
Escenarios visuales: un módulo HTTP llama a Tavnit y un Custom webhook recibe los resultados.
Webhooks by Zapier: Catch Hook recibe los resultados y una acción POST inicia runs.
En tu servidor o en la nube: un nodo Webhook recibe los resultados y un nodo HTTP Request inicia runs.
Una acción HTTP llama a la API de la misma forma.
Cada solicitud necesita el encabezado X-API-Key con tu key de Integraciones.
Recibe los resultados en tu automatización
- 1En tu plataforma, crea un disparador de webhook (Make: Custom webhook; Zapier: Webhooks by Zapier → Catch Hook; n8n: nodo Webhook, POST) y copia su URL.
- 2En Tavnit, pégala como webhook de un Flow (panel Webhook) o de un nodo Salida de un Pipeline.
- 3Procesa un documento para que la plataforma aprenda el payload y luego mapea los campos a Sheets, un CRM, un ERP, etc.
El payload se describe en la página de webhooks.
Integración con Make
Make (antes Integromat) es una plataforma de automatización visual que te permite conectar apps y automatizar flujos de trabajo sin escribir código.
Visita MakePrimeros pasos con Make
- 1Ve a make.com y crea una cuenta
- 2Haz clic en "Create a new scenario" desde tu panel
- 3Verás un lienzo en blanco donde puedes agregar módulos
- 4Busca "HTTP" y agrega el módulo "Make a request"
Un escenario es un flujo de trabajo automatizado en Make. Está formado por módulos (apps) conectados entre sí. Cuando un módulo se activa o recibe datos, se los pasa al siguiente módulo.
Configura el módulo HTTP
Después de agregar el módulo HTTP, configúralo para enviar documentos a Tavnit. Puedes usar cualquiera de estos dos enfoques:
Opción 1: multipart/form-data (cuando tienes un objeto de archivo)
- 1Agrega un módulo HTTP "Make a request" a tu escenario
- 2Configura la solicitud:
- URL:
https://run.tavnit.io/api/runs/process - Método: POST
- URL:
- 3En la pestaña Headers, agrega:
- Nombre del encabezado: X-API-Key
- Valor del encabezado: YOUR_API_KEY
- 4Configura el tipo de Body como "multipart/form-data"
- 5Agrega los campos del formulario:
- flow_id: YOUR_FLOW_ID
- file: (mapéalo desde el módulo anterior)
- source: api (opcional)
- 6Ejecuta tu escenario para probarlo
Opción 2: JSON + base64 (cuando tienes una cadena base64)
Si el módulo anterior entrega una cadena base64 en lugar de un archivo, usa este enfoque:
- 1Configura el tipo de Body como "Raw" y selecciona "JSON (application/json)"
- 2En la pestaña Headers, agrega también:
- Nombre del encabezado: Content-Type
- Valor del encabezado: application/json
- 3Define el cuerpo JSON así:
{
"flow_id": "YOUR_FLOW_ID",
"source": "api",
"filename": "document.pdf",
"file_base64": "{{previous_module.base64_content}}"
}Reemplaza {{previous_module.base64_content}} por el mapeo real de tu módulo anterior. En Make, haz clic en el campo y selecciona la salida base64 del módulo que entrega tu archivo. Conserva la extensión en filename: Tavnit la usa para detectar el tipo de archivo.
La llamada responde de inmediato con un run_id. Los datos extraídos llegan después al webhook del Flow, o puedes pedirlos con un segundo módulo HTTP que llame a GET https://run.tavnit.io/api/runs/{run_id}.
Otras plataformas (Zapier, Power Automate, n8n)
El mismo enfoque funciona con cualquier plataforma de automatización que admita solicitudes HTTP:
Usa multipart/form-data con un campo “file” que contenga el archivo, más el campo flow_id.
Usa un cuerpo JSON con flow_id, filename y file_base64 (el contenido base64 del paso anterior).
Ambos métodos llaman al mismo endpoint y producen los mismos resultados de extracción. Para procesar archivos que llegan a Google Drive, OneDrive o Dropbox, dispara con “Nuevo archivo en carpeta” y envía el archivo por POST de la misma forma.
Uso de la API de Colecciones
Si recibes distintos tipos de documento y quieres que la IA dirija cada uno al Flow correcto, llama a la Colección en lugar de a un Flow.
- URL:
https://run.tavnit.io/api/collections/process - Usa
collection_iden lugar deflow_id
{
"collection_id": "YOUR_COLLECTION_ID",
"source": "api",
"filename": "document.pdf",
"file_base64": "{{previous_module.base64_content}}"
}Uso de la API de Splitters
Si recibes PDFs combinados con varios documentos y necesitas separarlos, llama al Splitter.
- URL:
https://run.tavnit.io/api/splits/run - Usa
splitter_iden lugar deflow_id
{
"splitter_id": "YOUR_SPLITTER_ID",
"source": "api",
"filename": "combined_docs.pdf",
"file_base64": "{{previous_module.base64_content}}"
}Inicia un Pipeline
Para ejecutar un Pipeline completo en lugar de un solo Flow, envía el archivo por POST (file multipart, o JSON con file_base64 + filename) a https://run.tavnit.io/api/pipelines/YOUR_PIPELINE_ID/execute con el mismo encabezado. El ID del Pipeline va en la URL.
Uso de la API de Cleaners
Para limpiar filas de datos desde tu automatización, envíalas como JSON al Cleaner. Un archivo de hoja de cálculo va, en cambio, a https://run.tavnit.io/api/sweeps/run como multipart con cleaner_id (ese endpoint no acepta base64).
- URL:
https://run.tavnit.io/api/cleaners/YOUR_CLEANER_ID/process - Método: POST, Content-Type: application/json
{
"rows": [
{ "Vendor": "acme corp.", "Country": "usa" },
{ "Vendor": "GLOBEX INC", "Country": "Mexico" }
]
}Uso de la API de Buckets
Para enviar filas a un Bucket sin mandar un documento, usa el endpoint de escritura. Cada fila debe incluir todas las columnas del Bucket.
- URL:
https://run.tavnit.io/api/buckets/write - Método: POST, Content-Type: application/json
- Encabezado:
X-API-Key: YOUR_API_KEY
{
"bucket_id": "YOUR_BUCKET_ID",
"bucket_name": "YOUR_BUCKET_NAME",
"overwrite": false,
"rows": [
{ "column_one": "value", "column_two": 123 }
]
}Abre la página de detalle del Bucket y toca el ícono de información. Ambos valores se copian con un solo toque.
Otras funciones
Agentes, Matchers, Inspectores, Fillers, Signals, Subjects y Nets se inician de la misma forma: una solicitud HTTP con el encabezado X-API-Key. Cambia a la pestaña Código para ver los campos de cada endpoint.
