Ir al contenido

APIs internas de Summit Auth

Estas APIs son para comunicación servidor a servidor entre backends del ecosistema Summit, no para llamarse desde una aplicación cliente pública. Requieren un access token con un permiso concedido a través de un flujo con usuario asociado — un token de Client Credentials nunca lleva permission y no puede autenticarse contra ellas.

Para consultar las suscripciones, planes y funcionalidades de un usuario por su token o por correo, consulta Suscripciones y funcionalidades.

POST /api/internal/product-access/sync
Authorization: Bearer <ACCESS_TOKEN>
Content-Type: application/json
{
"userId": "USER_ID",
"productKey": "climbedge",
"planKey": "pro",
"status": "active",
"startsAt": "2026-08-01T00:00:00Z",
"expiresAt": null,
"notes": "Otorgado manualmente por soporte"
}

Crea o actualiza el acceso de forma idempotente sobre userId + productKey; llamar de nuevo con el mismo estado no genera cambios adicionales. status acepta active, suspended, expired o cancelled. startsAt, expiresAt y notes son opcionales.

{
"userId": "USER_ID",
"productKey": "climbedge",
"planKey": "pro",
"status": "active",
"synced": true
}
Código Motivo
200 Sincronizado. Devuelve el estado final del acceso.
400 Cuerpo de la solicitud inválido.
404 userId no existe.
422 status no es un valor permitido.

Un acceso creado por esta vía queda como acceso personal del usuario. Si el producto es exclusivo para organizaciones, este otorgamiento directo no lo satisface.

Consultar las funcionalidades incluidas en el plan de un usuario

Sección titulada «Consultar las funcionalidades incluidas en el plan de un usuario»
GET /api/internal/product-access/{userId}/{productKey}/features
Authorization: Bearer <ACCESS_TOKEN>

Resuelve en vivo si el usuario tiene acceso activo al producto y, si lo tiene, la lista de funcionalidades incluidas en su plan actual.

{
"userId": "USER_ID",
"productKey": "climbedge",
"hasAccess": true,
"planKey": "pro",
"features": [
{ "key": "storage", "name": "Almacenamiento", "value": 50, "unit": "GB" },
{ "key": "priority_support", "name": "Soporte prioritario", "value": null, "unit": null }
]
}

Si el producto es exclusivo para organizaciones, hasAccess es false cuando el único acceso del usuario es personal. Cuando no hay acceso vigente o el producto no existe, hasAccess es false y planKey y features vienen vacíos.

Sincronizar acceso desde una suscripción de facturación

Sección titulada «Sincronizar acceso desde una suscripción de facturación»
POST /api/internal/billing/subscriptions/{subscriptionId}/sync-product-access
POST /api/internal/billing/users/{userId}/sync-product-access
POST /api/internal/billing/organizations/{organizationId}/sync-product-access
Authorization: Bearer <ACCESS_TOKEN>

Reconcilian una suscripción, todas las suscripciones de un usuario, o todas las de una organización, hacia sus registros de acceso a producto correspondientes. Son idempotentes. 404 si el recurso indicado no existe; la variante por suscripción además devuelve 422 si la suscripción no tiene producto o plan asignado.

La respuesta por suscripción incluye el estado de acceso resultante:

{
"subscriptionId": 25,
"synced": true,
"productKey": "summit_ai",
"planKey": "pro",
"productAccessStatus": "active"
}

Las variantes por usuario y por organización devuelven la cantidad de suscripciones procesadas:

{ "userId": "USER_ID", "syncedCount": 2 }
{ "organizationId": "11111111-2222-3333-4444-555555555555", "syncedCount": 3 }

Estos endpoints son de solo lectura y usan el sub del token para identificar al caller. Requieren un usuario autenticado y membresía activa en la organización consultada.

GET /api/organizations/{id}
GET /api/organizations/{id}/products
GET /api/organizations/{id}/products/{subscriptionId}/assignments
Authorization: Bearer <ACCESS_TOKEN>

Los tres endpoints responden 401 si falta autenticación. Responden 404 si la organización no existe, el caller no es miembro activo o la suscripción no pertenece a la organización; nunca 403, para no revelar recursos ajenos.

GET /api/organizations/{id} devuelve:

{
"id": "11111111-2222-3333-4444-555555555555",
"tenantId": "aaaaaaaa-bbbb-cccc-dddd-eeeeeeeeeeee",
"name": "Acme Ecuador",
"slug": "acme-ecuador",
"legalName": "Acme Ecuador S.A.",
"domain": "acme.example",
"logoUrl": "https://cdn.example.com/acme/logo.png",
"isActive": true,
"callerRole": "admin",
"callerPermissions": ["organization.read", "organization.products.read"]
}

legalName, domain y logoUrl pueden ser null. callerPermissions contiene los permisos efectivos del caller.

GET /api/organizations/{id}/products devuelve todas las suscripciones de la organización, independientemente de su estado:

[
{
"subscriptionId": 123,
"productKey": "summit",
"productName": "Summit",
"planKey": "pro",
"planName": "Pro",
"status": "active",
"seatLimit": 10,
"assignedSeats": 4,
"availableSeats": 6,
"features": [
{ "key": "storage", "name": "Almacenamiento", "value": 50, "unit": "GB" },
{ "key": "priority_support", "name": "Soporte prioritario", "value": null, "unit": null }
]
}
]

features se ordena alfabéticamente por name. assignedSeats cuenta solo asignaciones activas no expiradas. availableSeats es null cuando seatLimit es null; de lo contrario es el cupo restante y nunca es negativo.

GET /api/organizations/{id}/products/{subscriptionId}/assignments devuelve las filas de miembros y su estado para esa suscripción:

[
{
"membershipId": "22222222-3333-4444-5555-666666666666",
"userId": "USER_ID",
"email": "ana@example.com",
"role": "member",
"isActive": true,
"isAssigned": true,
"provenance": "subscription"
}
]

email puede ser null. isActive indica si la membresía sigue activa y isAssigned si el miembro tiene asignado el producto. Los callers con rol administrativo ven las filas de todos los miembros; los demás solo ven su propia fila. Si no tienen fila para la suscripción, reciben un arreglo vacío.