Reten Docs
Primeros Pasos

Autenticación

Autentícate con la API de Reten usando API keys o tokens JWT.

Todos los endpoints requieren autenticación a menos que estén marcados como Públicos. Reten soporta dos métodos de autenticación.

API Keys (Recomendado para Integraciones)

Las API keys proporcionan autenticación sin estado, ideal para integraciones, pipelines CI/CD y comunicación entre servicios.

Características Principales

  • Permisos acotados — cada key tiene una lista explícita de permisos elegida por su dueño (subconjunto de los permisos vigentes del dueño, editable por el dueño en cualquier momento); en cada solicitud, los permisos efectivos son la intersección de esa lista con los permisos vigentes del dueño
  • Vinculada a un tenant — cada key está asociada a un tenant específico (no se necesita el header x-tenant-id); su alcance decide si además queda atada a un proyecto (ver Contexto de Proyecto)
  • Almacenamiento seguro — solo se almacena un hash SHA-256; la key en texto plano se muestra una sola vez al crearla
  • Expiración opcional — las keys pueden tener una fecha de expiración tras la cual se rechazan automáticamente

Crear una API Key

Crea una API key vía POST /api/api-keys con los permisos deseados. La key en texto plano se devuelve una sola vez y debe almacenarse de forma segura.

Solicitud

CampoTipoRequeridoDescripción
namestringSíNombre legible para la key
permissionsstring[]SíPermisos a otorgar (subconjunto de tus permisos vigentes; editables después con PUT /api/api-keys/:id/permissions)
expiresAtISO 8601NoFecha de expiración
scopestringSíproject (la key queda atada a un proyecto) o tenant (la key sirve para todos los proyectos del tenant y envía x-project-id donde el endpoint lo exige o para acotar una solicitud a un proyecto) — ver Crear Clave de API
projectIdUUIDCon scope: "project"Proyecto al que pertenece la key
curl -X POST https://api.reten.ai/api/api-keys \
  -H "Authorization: Bearer <token>" \
  -H "x-tenant-id: <tenant-id>" \
  -H "Content-Type: application/json" \
  -d '{
    "name": "Integration Key",
    "permissions": ["activity:view", "activity:create"],
    "scope": "project",
    "projectId": "<project-id>"
  }'
import axios from 'axios';

const response = await axios.post(
  'https://api.reten.ai/api/api-keys',
  {
    name: 'Integration Key',
    permissions: ['activity:view', 'activity:create'],
    scope: 'project',
    projectId: '<project-id>',
  },
  {
    headers: {
      Authorization: 'Bearer <token>',
      'x-tenant-id': '<tenant-id>',
    },
  }
);

// Guarda esta key de forma segura — solo se muestra una vez
const apiKey = response.data.plaintextKey; // rtn_sk_...

Usar una API Key

Incluye la key en el header x-api-key en todas las solicitudes:

x-api-key: rtn_sk_<key>

Al usar una API key, el tenant se resuelve a partir de la key — no se necesita el header x-tenant-id. Que la key envíe además x-project-id depende de su alcance — ver Contexto de Proyecto.

Email + Contraseña (JWT)

Los tokens JWT se usan para sesiones interactivas de usuario. El flujo implica una solicitud de login que devuelve un access token y establece un refresh token como cookie.

Flujo de Autenticación

  1. Llama a POST /api/auth/login con email y contraseña
  2. Recibe un access token en el cuerpo de la respuesta; un refresh token se establece como cookie HTTP-only
  3. Incluye el access token en todas las solicitudes posteriores vía el header Authorization
  4. Cuando el access token expire (15 min), llama a POST /api/auth/refresh — el servidor valida la cookie de refresh y emite un nuevo access token
  5. Al cerrar sesión, se limpia la cookie de refresh

Tiempo de Vida de Tokens

TokenDuraciónTransporte
Access token15 minutosHeader Authorization: Bearer
Refresh token7 díasCookie HTTP-only

Solicitud de Login

CampoTipoRequeridoDescripción
identifierstringSíNombre de usuario o dirección de email
passwordstringSíContraseña del usuario (mín. 8 caracteres)
curl -X POST https://api.reten.ai/api/auth/login \
  -H "Content-Type: application/json" \
  -d '{
    "identifier": "admin@example.com",
    "password": "SecurePass123!"
  }'
import axios from 'axios';

const response = await axios.post(
  'https://api.reten.ai/api/auth/login',
  {
    identifier: 'admin@example.com',
    password: 'SecurePass123!',
  }
);

const { accessToken, user } = response.data;

Respuesta 201 Created

{
  "accessToken": "eyJhbGciOiJIUzI1NiIs...",
  "user": {
    "id": "550e8400-e29b-41d4-a716-446655440000",
    "username": "jdoe",
    "email": "jdoe@example.com",
    "firstName": "Jane",
    "lastName": "Doe",
    "roles": ["viewer"],
    "permissions": [
      "project:view",
      "user:view",
      "activity:view",
      "commerce-lifecycle-snapshot:view"
    ],
    "tenantIds": ["660e8400-e29b-41d4-a716-446655440000"]
  }
}

Usar JWT con Contexto de Tenant

Al autenticar con JWT, la mayoría de los endpoints requieren un contexto de tenant vía el header x-tenant-id:

Authorization: Bearer <access_token>
x-tenant-id: <tenant_uuid>

Puedes obtener la lista de tenants a los que pertenece tu usuario vía GET /api/tenant/mine.

Los endpoints project-scoped necesitan además el header x-project-id, y los endpoints project-optional lo aceptan — ver Contexto de Proyecto.

Contexto de Proyecto

Los datos de un tenant se dividen en proyectos. Los endpoints project-scoped trabajan en exactamente un proyecto por solicitud: el proyecto activo. Los endpoints tenant-level no miran el proyecto.

Los endpoints project-optional aceptan x-project-id pero no lo exigen. Si se envía, acota la solicitud a ese proyecto y se valida igual que en un endpoint project-scoped. Sin él, una lectura abarca todo el tenant y un resultado toma el proyecto de su actividad; un resultado sin activity_id no tiene actividad de la que tomar el proyecto, así que necesita el header — sin él la API responde 400. Una clave de proyecto siempre trabaja en su propio proyecto: no necesita el header, y un resultado sin activity_id va al proyecto de la clave.

El proyecto activo sale de:

CredencialProyecto activo
JWTEl header x-project-id; en un endpoint project-optional sin él, no hay proyecto activo
Clave de tenantEl header x-project-id; en un endpoint project-optional sin él, no hay proyecto activo
Clave de proyectoEl proyecto de la propia clave — no se necesita el header x-project-id

Envía el header junto a x-tenant-id. Los IDs de proyecto se obtienen con GET /api/projects:

Authorization: Bearer <access_token>
x-tenant-id: <tenant_uuid>
x-project-id: <project_uuid>

Los endpoints tenant-level ignoran el header: enviarlo o no, no cambia la respuesta. Con una clave de API el tenant sigue saliendo de la clave; sólo el proyecto depende del alcance de la clave — ver Integración → Autenticación.

Endpoints project-scoped, project-optional y tenant-level

EndpointsAlcance
Actividades — /api/activities/*, incluidos GET /api/activities/tasks, GET /api/activities/tasks/:id y POST /api/activities/tasks/:id/dispatchProject-scoped
Resultados de actividad — POST /api/activity-results/tasks, PATCH /api/activity-results/tasks/:idProject-scoped
Activity Generation Configs — /api/activity-generation-configs/*Project-scoped
Audiencias — /api/audience-criterias/*, incluido el catálogo (tables, tables/:tableName/columns)Project-scoped
Filtros de eventos — /api/event-criterias/*Project-scoped
Pilares de ciclo de vida — /api/activation-configs/*, /api/engagement-configs/*, /api/resurrection-configs/*Project-scoped
Integración — GET /api/integration/activities/tasks, POST /api/integration/activity-results/tasksProject-optional
Todos los demás endpoints: proyectos, API keys, auth, usuarios, tenants, comercios, commerce lifecycle snapshots, operadores, rutas, supervisores, configuraciones y proveedores de despacho, catálogos de activity config, lifecycle defaults; en la API de integración, GET /api/integration/task-result-type-configs y los endpoints batch-upsertTenant-level

GET /api/activity-results/tasks/sync es tenant-level: ignora x-project-id y devuelve los resultados de todos los proyectos del tenant.

Errores de proyecto

En un endpoint project-scoped, y en un endpoint project-optional que recibe el header, la API valida el proyecto antes que los permisos y el cuerpo de la solicitud. La excepción es el 400 de un resultado sin activity_id en un endpoint project-optional, que llega después de validar el cuerpo de la solicitud:

EstadoCuándomessage
403Una clave de proyecto envía un x-project-id que nombra otro proyectoLa API key pertenece a un proyecto distinto del que declara el header x-project-id.
400Falta el header en un endpoint project-scoped (JWT o clave de tenant)Falta el header obligatorio x-project-id.
400Se envía un resultado sin activity_id a un endpoint project-optional sin proyecto (JWT o clave de tenant sin el header)Falta el header obligatorio x-project-id: un resultado sin activity_id necesita proyecto.
400El header no es un UUID válido (JWT o clave de tenant)El header x-project-id debe ser un UUID válido.
404El proyecto no existe o pertenece a otro tenantEl proyecto no existe.