Documentation / Open Atenta

View .md

Integrations: MCP, API and webhooks

Atenta is open: with one token a business connects its Atenta to Claude, ChatGPT, Zapier, Make, n8n or its own code. Everything done from there is the same as it would be in the app: same data, same rules, same limits.

  • MCP server: https://mcp.atenta.mx (Claude Code, Claude Desktop, Cursor, n8n and any MCP client that sends an Authorization header).
  • REST API: https://api.atenta.mx/v1 · OpenAPI 3.1 at https://api.atenta.mx/v1/openapi.json · documentation at https://api.atenta.mx/v1/docs.
  • Outgoing webhooks: Atenta notifies your URL when something happens (message, escalation, order, appointment, payment, call).

The per-integration pages, in the owner's language, are at /integraciones.

1. The token

It's created in the app → Settings → Integrations ("Connect" on the card you want, with the suggested permissions). It has the form atk_<business>_<32 characters> and is shown only once: store it in a password manager or an environment variable, never in a chat or a repository. Atenta keeps only its hash and a prefix to recognize it.

Permissions (pick only the ones the integration needs):

PermissionWhat it allows
leer_chatsread conversations, messages, quick replies and team
escribir_chatsreply in a chat, take over or hand back, pin/archive
pedidosview, create and update orders
citasview availability, book, move and cancel appointments; dates
clientessearch customers, profile, notes, tags, follow-ups, segments, import/export
finanzaswallet, credit and installments, collections, payment links, charge for orders
reportesmonthly report, PDF, call history and metrics
baseread the knowledge base, the menu, today's menu, the catalog and the settings; propose corrections (approving them is the owner's job, in the app)
integracionesview tokens and manage webhooks

Rules that always apply: 120 calls per minute per token; every write is recorded in the business's log with the token's name; whatever is only done from the app (approving the base, switching on, paying for the plan, campaigns, deleting) answers 403 solo_desde_la_app (app only); customers' phone numbers arrive redacted; a token only sees its own business. Revoking a token cuts the integration off instantly; "Revoke all" (red, with the confirmation REVOCAR TODO) cuts them all off.

2. Claude Code and Claude Desktop

Claude Code (terminal). Store the token in an environment variable; the configuration references it, it doesn't contain it:

export ATENTA_TOKEN="atk_..."   # the token the app gave you
claude mcp add --transport http atenta https://mcp.atenta.mx --header 'Authorization: Bearer ${ATENTA_TOKEN}'
claude mcp list                 # atenta: https://mcp.atenta.mx (HTTP) - ✓ Connected

Then, inside Claude Code: "Which conversations need me today?", "Book Laura for Thursday at 5", "Give me the day's summary". The tools are called atenta_chats_listar, atenta_pedidos_crear, atenta_citas_disponibles… (only the ones your token allows appear; atenta_yo tells you which).

Claude Desktop connects through a file (claude_desktop_config.json) with the mcp-remote bridge, which sends the token as a header. claude.ai's "custom connectors" authenticate with OAuth and Atenta authenticates with a token, so that path doesn't apply.

{
  "mcpServers": {
    "atenta": {
      "command": "npx",
      "args": ["-y", "mcp-remote", "https://mcp.atenta.mx", "--header", "Authorization: Bearer ${ATENTA_TOKEN}"],
      "env": { "ATENTA_TOKEN": "atk_..." }
    }
  }
}

Generic mcpServers block for any client that speaks Streamable HTTP (Cursor, Windsurf, VS Code…):

{
  "mcpServers": {
    "atenta": {
      "type": "http",
      "url": "https://mcp.atenta.mx",
      "headers": { "Authorization": "Bearer atk_..." }
    }
  }
}

What the MCP server exposes

Only the tools the token allows appear (plus atenta_yo, always).

ToolsPermission
atenta_chats_listar · atenta_chats_leerleer_chats
atenta_chats_escribir · atenta_chats_tomar_control · atenta_chats_devolverescribir_chats
atenta_pedidos_listar · atenta_pedidos_crear · atenta_pedidos_actualizarpedidos
atenta_pedidos_cobrar · atenta_finanzas_saldo · atenta_finanzas_recargar · atenta_finanzas_abonar · atenta_finanzas_cobranza · atenta_finanzas_linkfinanzas
atenta_citas_listar · atenta_citas_disponibles · atenta_citas_crear · atenta_citas_mover · atenta_citas_cancelarcitas
atenta_clientes_buscar · atenta_clientes_ficha · atenta_clientes_nota · atenta_clientes_seguimiento · atenta_clientes_etiquetarclientes
atenta_reporte_mes · atenta_llamadas_historialreportes
atenta_base_leer · atenta_base_proponer (stays as a proposed correction; approving is the owner's job, in the app) · atenta_menu_leer · atenta_menu_dia_hoybase

Resources (with base): atenta://base, atenta://menu-dia, atenta://catalogo, atenta://menu, atenta://horario, atenta://plan. Prompts: resumen_del_dia (day's summary), que_contesto_a_los_escalados (what to reply to the escalated chats; it proposes, it doesn't send), cobranza_de_hoy (today's collections).

3. ChatGPT

The path that works with a token is a custom GPT with Actions: under "Actions", import the schema from https://api.atenta.mx/v1/openapi.json, authentication API Key, type Bearer, value atk_.... The schema already includes servers, securitySchemes and one operation per action (chats_listar, pedidos_crear, citas_disponibles…). Suggested instruction for the GPT: "Use Atenta's actions to answer with real data from the business; never make up prices or hours; if an action fails, say the reason it returns".

ChatGPT's custom MCP connectors authenticate with OAuth or with no authentication; Atenta authenticates with a token, so for ChatGPT the Actions route is the one to use.

4. Zapier, Make and n8n

Two directions.

a) Atenta → your flow (webhooks). They're created in Settings → Integrations → Webhooks (public https URL + events) or through the API with the integraciones permission:

curl -X POST https://api.atenta.mx/v1/webhooks \
  -H "Authorization: Bearer $ATENTA_TOKEN" -H "Content-Type: application/json" \
  -d '{"url":"https://hooks.zapier.com/hooks/catch/123/abc","eventos":["pedido","cita","escalacion"]}'

The response includes secreto (whsec_…, shown only once). Each event arrives as a JSON POST:

{ "evento": "pedido", "tenant": "mi-negocio", "ts": "2026-09-21T18:03:11.000Z",
  "datos": { "id": 812, "cliente_id": 41, "estado": "nuevo", "total": 250, "moneda": "MXN", "canal": "whatsapp", "nuevo": true } }

with the headers X-Atenta-Evento, X-Atenta-Entrega (unique id: use it to avoid processing twice) and X-Atenta-Firma: t=<unix>,v1=<hmac>. To verify: v1 == HMAC_SHA256(secreto, t + "." + cuerpo_crudo) and |now − t| ≤ 300 s. In Node:

import { createHmac, timingSafeEqual } from "node:crypto";
export function firmaValida(secreto, cuerpoCrudo, firma) {
  const m = /^t=(\d+),v1=([0-9a-f]{64})$/.exec(firma ?? ""); if (!m) return false;
  if (Math.abs(Date.now() / 1000 - Number(m[1])) > 300) return false;
  const esperado = createHmac("sha256", secreto).update(`${m[1]}.`).update(cuerpoCrudo).digest("hex");
  return esperado.length === m[2].length && timingSafeEqual(Buffer.from(esperado), Buffer.from(m[2]));
}

Events: mensaje (every message in or out, with the full message), escalacion (Atenta asked for a person), pedido (new or status change), cita (new, moved or cancelled), pago (link paid or installment recorded), llamada (AI call finished). Retries: if your URL doesn't answer 2xx, Atenta retries 3 times (1 s, 5 s, 25 s); after 20 failures in a row the webhook switches itself off and you see it in the app (with its latest deliveries). The "Test" button = ping event. Maximum 5 webhooks per business; https URLs only.

In Zapier: Webhooks by Zapier → Catch Hook gives you the URL; in Make: Webhooks → Custom webhook; in n8n: a Webhook node (POST) and a Crypto or Code node to validate X-Atenta-Firma.

b) Your flow → Atenta (REST API). Any route of the business works at https://api.atenta.mx/v1/… with Authorization: Bearer atk_... (HTTP Request / Webhooks by Zapier → Custom Request modules). Examples:

# who am I and what can I do
curl https://api.atenta.mx/v1/yo -H "Authorization: Bearer $ATENTA_TOKEN"
# new orders
curl "https://api.atenta.mx/v1/crm/pedidos?estado=nuevo&limite=20" -H "Authorization: Bearer $ATENTA_TOKEN"
# free slots to book
curl "https://api.atenta.mx/v1/citas/disponibles?n=5" -H "Authorization: Bearer $ATENTA_TOKEN"
# book
curl -X POST https://api.atenta.mx/v1/citas -H "Authorization: Bearer $ATENTA_TOKEN" -H "Content-Type: application/json" \
  -d '{"inicio":"2026-09-25T17:00:00-06:00","nombre":"Laura","motivo":"corte","estado":"confirmada"}'
# reply in a chat as a person from the business
curl -X POST https://api.atenta.mx/v1/conversaciones/5214421234567/mensajes -H "Authorization: Bearer $ATENTA_TOKEN" -H "Content-Type: application/json" \
  -d '{"texto":"Your order is on its way, it arrives in 20 minutes."}'
# monthly report
curl "https://api.atenta.mx/v1/reporte?mes=2026-09" -H "Authorization: Bearer $ATENTA_TOKEN"

Errors, always with a short error and a human-readable motivo: 401 invalid or revoked token · 403 sin_permiso (says which permission is missing) · 403 solo_desde_la_app (app only) · 404 doesn't exist in this business · 409 a state that doesn't allow it (fuera_de_ventana, saldo_insuficiente…) · 422 incomplete data (campos) · 429 more than 120 calls in a minute (Retry-After). X-RateLimit-Limit and X-RateLimit-Remaining headers on every response.

5. Integrators (agencies)

An integrator token (atp_…, issued by Kalia Code) signs up businesses the same way the atenta.mx form does and reads their status; it never accesses a business's data (that's what the owner's token is for).

curl -X POST https://api.atenta.mx/v1/alta -H "Authorization: Bearer $ATENTA_INTEGRADOR" -H "Content-Type: application/json" \
  -d '{"negocio":"Taquería El Güero","giro":"fonda","whatsapp":"5214421234567","pais":"MX"}'
curl https://api.atenta.mx/v1/tenants -H "Authorization: Bearer $ATENTA_INTEGRADOR"
curl https://api.atenta.mx/v1/tenants/taqueria-el-guero/base -H "Authorization: Bearer $ATENTA_INTEGRADOR"

6. Security, in short

  • The token only exists on your side: Atenta stores a hash. If it leaks, revoke it in the app and create another.
  • Everything travels over HTTPS; responses never include secrets or customers' full phone numbers.
  • Every write made with a token is recorded in the business's log with the token's name.
  • External AIs read the business's data only with a token the owner created on purpose, with the permissions they chose and for as long as they don't revoke it. That AI's provider is a sub-processor chosen by the business itself, as the privacy notice says.
Missing something? Write to us from the home page.