Skip to content

Autenticación

La Kalipto Devs Platform usa API keys con scopes atadas a tu cuenta de desarrollador. Las keys se generan desde el dashboard en Cuenta → API keys (no se exponen por la API).

Todas las peticiones autenticadas usan:

X-API-Key: <plaintext_key>
  1. SHA-256 del texto plano: key_hash = hashlib.sha256(x_api_key.encode()).hexdigest().
  2. Búsqueda en platform_api_keys con key_hash = ? AND is_active = TRUE.
  3. Si expires_at está seteado y ya pasó, devuelve 401.
  4. Rate limit Redis sliding-window por key (por defecto 60 por minuto, configurable vía rate_limit_per_minute). El budget es separado del rate limit de v1/v2. Tu key no comparte cupo con keys de otros namespaces.
  5. Se actualiza last_used_at después del check de rate limit (las peticiones bloqueadas por rate limit NO cuentan para el uso).

DeveloperContext no lleva business_id: la plataforma es un sistema independiente del backend managed.

Códigos de error de la capa de autenticación

Section titled “Códigos de error de la capa de autenticación”
CódigoTrigger
401 UnauthorizedKey ausente / inválida / inactiva / expirada
403 ForbiddenKey válida pero le falta el scope que el endpoint requiere
429 Too Many RequestsRate limit excedido para esta key

Once scopes forman el vocabulario, todos LIVE: send:messages, manage:templates, upload:media, read:messages, read:conversations, read:contacts, manage:data, manage:webhooks, manage:channels (WF8), send:broadcasts (WF9) y read:channels (v399). El resto del control-plane (cuenta, billing, gestión de keys, y la conexión/onboarding de canales) vive bajo /platform/dashboard/* y es cookie-only (lo consume el dashboard web) — ojo que manage:channels (WF8) habilita las operaciones sobre un canal ya conectado (health, perfil, bloqueo, 2FA, kill-switch de inbound), distinto de la conexión/desconexión que es cookie-only.

read:channels no es lo mismo que manage:channels. Una key con manage:channels pero sin read:channels recibe 403 en GET /platform/v1/channels. Son scopes independientes: uno lista, el otro opera.

Si tu key fue creada antes de esta versión, NO tiene read:channels automáticamente — el scope no se otorga retroactivamente a keys existentes. Si tu integración necesita listar canales por API, creá una key nueva marcando read:channels. El texto plano se muestra una sola vez, igual que con cualquier key.

Scope¿Accesible desde API key?EndpointDescripción
send:messagesPOST /platform/v1/messages + POST /platform/v1/messages/mark-readEnviar mensajes (13 tipos) por un canal de tu cuenta y emitir read receipts.
manage:templates/platform/v1/templates/* (7 rutas post-WF6)CRUD de templates de WhatsApp + submit a Meta + edición + sync desde Meta + subida resumable de header media. Cubre la superficie completa de componentes Meta (HEADER text/media/location, BODY positional/NAMED, FOOTER, BUTTONS incl. OTP, CAROUSEL, categoría authentication). Ver Templates.
upload:mediaPOST /platform/v1/media + GET /platform/v1/media/{id}/url + DELETE /platform/v1/media/{id}Subir, consultar URL temporal y borrar binarios en Meta.
read:messagesSí (solo lectura)GET /platform/v1/messages + GET /platform/v1/messages/{id}Consultar el historial de mensajes persistidos. Solo lectura — no permite mutar nada. Ver Data plane.
read:conversationsSí (solo lectura)GET /platform/v1/conversations + GET /platform/v1/conversations/{id}Consultar conversaciones. Solo lectura — para cerrar una conversación necesitás manage:data.
read:contactsSí (solo lectura)GET /platform/v1/contacts + GET /platform/v1/contacts/{id}Consultar la lista de contactos por canal. Solo lectura — para editar o borrar un contacto necesitás manage:data.
manage:dataSí (mutación)PATCH /platform/v1/conversations/{id} + PATCH /platform/v1/contacts/{id} + DELETE /platform/v1/contacts/{id}Mutar filas del data plane: cerrar conversaciones, editar metadata de contactos, borrar contactos con cascada asíncrona. Independiente de los read:* — una key con read:contacts puede consultar pero NUNCA borrar.
manage:webhooks (WF7 — LIVE)Sí (key o cookie)/platform/v1/webhooks/subscriptions/* (CRUD + rotate-secret + resume + test) + /platform/v1/webhooks/deliveries/* (observabilidad — mode=kalipto|meta)Gestionar suscripciones a eventos normalizados de Kalipto. Crear / listar / editar / borrar suscripciones, rotar el HMAC secret, reanudar una suscripción auto-pausada, lanzar un evento de prueba firmado, y observar entregas en ambos modos (kalipto = eventos normalizados, meta = forward crudo). Ver Webhooks normalizados.
manage:channels (WF8 — LIVE)Sí (key o cookie)/platform/v1/channels/{id}/{health,profile,display-name,block-users,two-factor,inbound} (9 rutas)Operar un canal ya conectado: probar la salud (health), leer/actualizar el perfil de empresa, leer el estado del display name (el submit devuelve 501 — Meta lo gestiona desde Business Manager), bloquear/desbloquear usuarios, registrar el PIN de 2FA, y prender/apagar el procesamiento de inbound (kill-switch). Todas WhatsApp-only salvo PATCH /inbound (sirve para WA e IG). Distinto de la conexión/desconexión del canal, que es cookie-only bajo /platform/dashboard/channels/*. Ver Gestión de canales.
send:broadcasts (WF9 — LIVE)Sí (key o cookie)/platform/v1/broadcasts/* (8 rutas)Campañas masivas basadas en templates (WhatsApp-only): crear borrador, cargar hasta 1000 destinatarios por llamada, agendar / cancelar / enviar, y leer métricas por destinatario. Caps por plan (broadcast_recipients_limit / broadcasts_per_month) — el plan free está deshabilitado (403). Ver Broadcasts.
read:channels (v399 — LIVE)Sí (SOLO key, sin cookie)GET /platform/v1/channelsListar los canales de tu cuenta — el channel_id que toda otra ruta de /platform/v1/* requiere. Newest-first, [] si no tenés canales, nunca devuelve material de token. No otorgado retroactivamente a keys existentes.

Separación lectura ↔ mutación: las rutas PATCH y DELETE del data plane NO se habilitan con un scope read:*. Necesitás explícitamente manage:data. Esto preserva el modelo de seguridad: una key de solo-lectura filtrada NO puede borrar contactos ni cerrar conversaciones. Si tu integración solo necesita leer, dejala con read:* y dormís tranquilo.

Los scopes se eligen al crear la key. Por defecto el formulario viene con TODOS los scopes disponibles tildados (decisión de producto WF v321-A) — destildás los que tu integración NO necesite, en lugar de sumar opt-in desde cero.

  • X-API-Key: para integraciones backend (server-to-server, scripts, cron jobs). Es el modo recomendado para producción. Las rutas accesibles por key son POST /platform/v1/messages, POST /platform/v1/messages/mark-read, /platform/v1/media/*, /platform/v1/templates/*, el Data plane (GET /platform/v1/messages*, GET/PATCH /platform/v1/conversations*, GET/PATCH/DELETE /platform/v1/contacts*), /platform/v1/webhooks/* (WF7), /platform/v1/channels/{id}/* de gestión de canal (WF8), /platform/v1/broadcasts/* (WF9), y GET /platform/v1/channels para descubrimiento de canales (v399, SOLO key, sin cookie).
  • Cookie JWT (access_token_dev): para el dashboard web. Cubre el resto del control-plane (cuenta, canales, billing, gestión de keys) bajo /platform/dashboard/*. Si estás usando solo el dashboard, no necesitás API keys.

Ambos mecanismos coexisten en /platform/v1/templates/* (esa es la única ruta cross-method de control-plane). El resto del control-plane (cuenta, canales, billing, gestión de keys) es cookie-only.

  • Quickstart: registrar cuenta, conectar un canal, generar key y enviar el primer mensaje.