Equipo y plan
Las personas del espacio de trabajo, lo que puede hacer cada una y en qué plan está el espacio de trabajo. Lo mismo que muestran las pantallas Equipo y Plan, para un espacio de trabajo configurado o comprobado mediante una máquina.
| Método | Ruta | Permiso |
|---|---|---|
GET | /v1/team/users | team:read |
POST | /v1/team/users | team:write |
PATCH | /v1/team/users/{userId} | team:write |
POST | /v1/team/users/{userId}/resend | team:write |
POST | /v1/team/users/{userId}/delete | team:write |
GET | /v1/licence | plan:read |
POST | /v1/licence/offer/{offerId}/accept | persona con sesión iniciada: el propietario |
POST | /v1/licence/offer/billing-details | persona con sesión iniciada: el propietario |
POST | /v1/team/name | persona con sesión iniciada: el propietario |
POST | /v1/team/leave | persona con sesión iniciada: un colega |
GET | /v1/team/markets | persona con sesión iniciada |
POST | /v1/team/markets | persona con sesión iniciada: el propietario |
El permiso Equipo solo se ofrece en un plan con equipo (Small business y Enterprise). Cambiar el nombre del espacio de trabajo, abandonarlo, elegir sus sectores y cambiar el plan corresponden a una persona con sesión iniciada, y ninguna clave puede acceder a ellos: consulte Solo para una persona con sesión iniciada.
Una clave con team:write es una vía de entrada al espacio de trabajo, no solo una forma de leerlo: puede invitar a un colega con el permiso de Administración, que gestiona las claves de API. Consulte Autenticación. Désela solo a una clave cuya tarea sea configurar espacios de trabajo. La conexión de un asistente de IA nunca la tiene, ni siquiera una autorizada a actuar, porque de otro modo una instrucción introducida en algo que lee el asistente podría invitar a alguien cuyo acceso sobreviva a la conexión: a una clave creada a mano sí se le puede dar.
Las personas
curl http://localhost:4000/v1/team/users \
-H "Authorization: Bearer rw_your_key_here"
{
"workspace": { "name": "Northwind Markets" },
"users": [
{
"id": "01M38Z6Y78B0DG1817DA49VCMJ",
"email": "sam.carter@northwind.example",
"displayName": "Sam Carter",
"role": "OWNER",
"powers": [],
"lastLoginAt": "2026-09-24T20:26:39.741Z",
"createdAt": "2026-09-24T05:46:29.539Z"
},
{
"id": "01M390CPHEWQ9GWKYWBPTM5YTC",
"email": "priya.nair@northwind.example",
"displayName": "Priya Nair",
"role": "MEMBER",
"powers": ["operate"],
"lastLoginAt": null,
"createdAt": "2026-09-24T06:07:06.889Z"
}
],
"seats": { "used": 3, "max": 10, "included": 10, "additional": 0, "granted": 0 }
}
role es OWNER para la persona a la que pertenece el espacio de trabajo, que tiene todos los permisos (así que su lista powers está vacía), y MEMBER para todos los demás. powers es lo que puede hacer un colega:
| Permiso | En la pantalla Equipo | Qué abre |
|---|---|---|
operate | Operaciones | Canales, marcas, fuentes de contenido y la canalización: el día a día. |
approve | Aprobaciones | Aprobar y Rechazar en publicaciones, y en actualizaciones de publicaciones, que esperan aprobación, y no editar. También es lo que desactiva la aprobación de un canal, y en Enterprise lee el registro de cumplimiento y establece sus reglas de aprobación. |
admin | Administración | Las pantallas Equipo, Claves de API y Webhook: las personas, las credenciales que llegan al exterior (claves de API, las claves de los servicios de IA, el conector de plataforma de un canal), mostrar de nuevo una clave o el secreto de firma del webhook tras su propia contraseña, y la dirección del webhook, su entrega de prueba y reenviar una entrega. En Enterprise lee también el registro de cumplimiento y añade y elimina a sus auditores. |
Ningún permiso rodea a otro. Un administrador crea claves de API, pero solo puede dar a una clave approvals:write mientras tenga Aprobaciones, y plan:read solo como propietario, ya que el plan lleva los precios y la próxima factura; pedirlo de otra manera es un 403 (consulte Autenticación). Qué correos trae cada permiso está en la página de la pantalla Equipo, Quién recibe qué correo: nada de lo que paga el espacio de trabajo llega a nadie que no sea el propietario.
Un auditor (Enterprise) no es un colega: los auditores no están en esta lista, no ocupan ningún usuario, y se añaden y eliminan en Cumplimiento; las rutas de aquí responden a uno con un 409.
seats cuenta colegas, nunca al propietario: used de max, donde max es la suma de lo que incluye el plan (included, o un número acordado con Reelwire), los usuarios comprados como extra (additional) y los usuarios concedidos por Reelwire (granted). lastLoginAt es null para alguien que aún no ha iniciado sesión.
Invitar a un colega
curl -X POST http://localhost:4000/v1/team/users \
-H "Authorization: Bearer rw_your_key_here" \
-H "Content-Type: application/json" \
-d '{ "email": "lea.martin@northwind.example", "displayName": "Lea Martin", "powers": ["operate"] }'
| Campo | Para qué sirve |
|---|---|
email | Su dirección, hasta 320 caracteres. Le sirve para iniciar sesión, y tiene que estar sin usar en cualquier parte de Reelwire. |
displayName | Opcional, hasta 120 caracteres. Puede cambiarlo él mismo en su perfil. |
powers | Al menos uno de operate, approve y admin: con ninguno iniciaría sesión en un panel vacío, así que eso es un 400. |
Responde 201 con el nuevo colega (user, tal como lo muestra la lista), password, una contraseña inicial creada para él, y minutes, que es null porque el enlace de configuración no caduca. La cuenta está lista de inmediato: se envía un correo a la dirección con un enlace para elegir su propia contraseña, que es como se pretende que entre. Enviar un enlace más reciente hace que deje de funcionar cada uno anterior. La contraseña inicial está en esta respuesta y en ningún otro sitio: solo se conserva como hash, así que no se puede leer de nuevo.
Un 409 indica por qué no se pudo hacer: el plan no tiene equipo (súbalo de nivel), todos los usuarios están ocupados (elimine a alguien, o compre usuarios en la pantalla Plan), o la dirección no se puede usar aquí, que es todo lo que dice sobre una dirección que pertenece a otra persona.
Cambiar, reenviar y eliminar
PATCH /v1/team/users/{userId} admite powers (el conjunto completo con el que termina, al menos uno: los permisos se sustituyen, no se combinan) y displayName (una cadena vacía quita el nombre), y responde con el user cambiado. Nadie puede cambiar los permisos del propietario ni los propios; ambas cosas son un 409.
POST /v1/team/users/{userId}/resend envía un enlace de configuración nuevo a alguien que perdió el suyo, y responde { "sent": true, "email": "...", "minutes": null }. No al propietario, que restablece su propia contraseña, y no dos veces en un minuto a la misma persona: ambas cosas son un 409.
POST /v1/team/users/{userId}/delete elimina a alguien de inmediato y responde { "removed": true }: se cierra su sesión en todas partes, se elimina su cuenta y un correo se lo comunica. Lo que hizo queda en el registro de auditoría y en las publicaciones que aprobó. El propietario no se puede eliminar, y nadie puede eliminarse a sí mismo.
El plan
curl http://localhost:4000/v1/licence \
-H "Authorization: Bearer rw_your_key_here"
{
"licence": {
"plan": "ENTERPRISE",
"state": "ACTIVE",
"term": "MONTHLY",
"capabilities": ["customApi", "team", "approvals", "compliance", "syndicate", "priorityRendering"],
"watermark": false,
"paysBy": "CARD",
"invoiceDays": 30,
"offer": null,
"colleagues": 3,
"pending": null,
"costs": {
"renewsAt": "2026-10-24T05:46:29.135Z",
"lines": [
{ "key": "plan", "label": "Reelwire Enterprise subscription (4000 videos a month, 25 seats, 300 syndication participants, 80000 MB storage)", "cents": 120000 }
],
"totalCents": 120000,
"currency": "EUR"
}
},
"plans": [
{ "id": "FREE", "name": "Free", "priceCents": 0, "renders": 15, "seats": 0, "syndicationPartners": 0, "storageMb": 50, "watermark": false, "capabilities": ["customApi"] }
]
}
Abreviado aquí: la respuesta lleva más de costs y los cuatro planes. Responde al propietario, o a una clave con plan:read, que solo el propietario puede dar; cualquier otro colega es rechazado con un 403, porque lleva los precios y la próxima factura. capabilities es lo que activa el plan de este espacio de trabajo, y la misma lista decide lo que ofrece el panel y lo que permite cada ruta: customApi (sus feeds propios), team, approvals (un canal puede retener publicaciones para un revisor: Small business y Enterprise), compliance (el registro de cumplimiento, Enterprise), syndicate y priorityRendering. holds es lo que se compró además del plan, pending un cambio ya elegido que empieza en la siguiente renovación, como el paso a un plan menor. plans lista cada plan con su precio y sus cuotas, el más barato primero; syndicationPartners es su cuota de participantes de sindicación.
paysBy es cómo paga el espacio de trabajo: CARD, o INVOICE, donde Stripe envía cada factura por correo, pagadera en invoiceDays días, y no se cobra nada de una tarjeta. Solo una oferta Enterprise establece INVOICE; invoiceDays no significa nada mientras paysBy sea CARD. En Enterprise, las cuotas del plan y los precios de sus extras son los acordados en la oferta que aceptó el espacio de trabajo, y la entrada Enterprise de plans lleva su precio y sus cuotas acordados.
Enterprise se acuerda con Reelwire, no se elige. Para un espacio de trabajo que no está en él, su entrada en plans tiene contact: true, y sus precios (priceCents, monthlyCents, yearlyCents) y cuotas (renders, seats, syndicationPartners, storageMb) son null; cada otra entrada tiene contact: false. Pedir Enterprise al cambiar el plan, o en el pago, es un 409 que indica usar Contáctenos en la pantalla Plan. offer es la oferta que Reelwire hizo a este espacio de trabajo y que aún no ha aceptado, o null.
Cuánto queda de la cuota de este mes, y de usuarios, participantes de sindicación y almacenamiento, está en GET /v1/renders/quota (allowance:read); lo que cuestan los extras aparece en esa respuesta solo para el propietario o una clave con plan:read. Consulte Renders.
Cambiar el plan, comprar extras y las facturas son del propietario, en las pantallas Plan, Cuota y Facturación: cambian lo que paga el espacio de trabajo, y ninguna clave puede acceder a ellas.
Una oferta Enterprise
Lo que Reelwire acuerda con un cliente para Enterprise se escribe como una oferta para su espacio de trabajo, que el propietario acepta en la pantalla Plan. Mientras hay una vigente, GET /v1/licence la lleva como offer:
{
"licence": {
"plan": "FREE",
"paysBy": "CARD",
"invoiceDays": 30,
"offer": {
"id": "eo_01M3C8Q0Y7ZK4D2N6R9T1V3W5X",
"term": "YEARLY",
"monthlyCents": 69000,
"priceCents": 690000,
"yearlyCents": 690000,
"currency": "EUR",
"renders": 3000,
"seats": 25,
"partners": 250,
"storageMb": 5000,
"extras": [
{ "stepId": "renders-250", "dimension": "renders", "amount": 250, "listCents": 12900, "cents": 9900 },
{ "stepId": "seats-1", "dimension": "seats", "amount": 1, "listCents": 3900, "cents": 3900 },
{ "stepId": "storage-100", "dimension": "storage", "amount": 100, "listCents": 199, "cents": 199 }
],
"paysBy": "INVOICE",
"invoiceDays": 45,
"expiresAt": "2026-11-15T09:12:44.000Z",
"road": "new-invoice",
"billing": null,
"needsBilling": true
}
}
}
Abreviado: el resto de licence y plans como arriba.
| Campo | Qué es |
|---|---|
id | La oferta, para aceptarla. |
term | MONTHLY o YEARLY: el período de facturación con el que empieza el plan. |
monthlyCents | El precio acordado por un mes, antes de impuestos. |
priceCents | Lo que cuesta un período de term, antes de impuestos. |
yearlyCents | Lo que cuesta un año, antes de impuestos: diez meses, como en todos los planes. |
renders, seats, partners, storageMb | Lo que incluye el plan para este espacio de trabajo: videos al mes, usuarios además del propietario, participantes de sindicación y almacenamiento en MB. |
extras | Cada extra que el espacio de trabajo puede añadir por sí mismo, un escalón cada uno, con su precio de lista (listCents) y el precio acordado (cents), ambos mensuales. Los participantes de sindicación nunca están entre ellos: más son una oferta nueva. |
paysBy, invoiceDays | CARD, o INVOICE, pagadera en invoiceDays días. |
expiresAt | Cuándo deja de estar vigente la oferta. Una oferta nueva sustituye a la anterior. |
road | Qué hace aceptar aquí: checkout (el pago de Stripe, con tarjeta), amend-card (el plan de pago sube, cargado a la tarjeta registrada), new-invoice (una suscripción facturada desde el principio) o amend-invoice (el plan de pago sube y pasa a factura). |
billing | Para una oferta pagada por factura, los datos de facturación que tiene Stripe: company, forename, surname, street, postalCode, city, province, country y vatNumber. null donde no hay ninguno registrado. |
needsBilling | true mientras una oferta pagada por factura no se puede aceptar, porque faltan los datos de facturación a los que se extienden sus facturas. |
POST /v1/licence/offer/{offerId}/accept, sin cuerpo, la acepta, según su road, y responde con uno de:
{ "licence": { ... } }, el plan tal como queda, donde el cambio se hizo de inmediato: con tarjeta en un plan de pago, o por factura. La primera factura de una suscripción nueva con facturación llega por correo en una hora.{ "checkout": { "url": "...", "sessionId": "..." } }, el pago de Stripe que hay que abrir, donde el primer período se paga con tarjeta. No cambia nada hasta que el pago se realiza.202con{ "confirmation": { "url": "...", "label": "...", "expiresAt": "..." } }, donde el banco pide al titular de la tarjeta que confirme el pago, como en cualquier subida de nivel: no cambia nada hasta que se confirma en la página de Stripe enurl.
Es un 404 para una oferta que no se hizo a este espacio de trabajo, y un 409 que indica por qué para una que ya no está vigente (aceptada, retirada o pasado expiresAt), para una oferta pagada por factura sin datos de facturación todavía, y para una oferta anual mientras algo más espera la fecha de cobro. Es un 403 mientras la dirección de correo del propietario no esté confirmada: no se paga nada desde una dirección que nadie ha confirmado, ni aquí ni en el pago, así que siga primero el enlace del correo de confirmación.
POST /v1/licence/offer/billing-details responde { "url": "..." }: la página de facturación de Stripe, donde el propietario introduce los datos a los que se extiende una oferta pagada por factura. Allí no se cobra ni se suscribe nada. Es un 409 mientras no haya ninguna oferta vigente.
Ambas responden al propietario con la sesión iniciada y a nadie más: una clave es rechazada tenga los permisos que tenga.
Solo para una persona con sesión iniciada
Estas responden a una sesión del panel y nunca a una clave, porque una clave no tiene rol y no es la pertenencia de nadie:
POST /v1/team/namecon{ "name": "Northwind Markets" }(hasta 120 caracteres) cambia el nombre del espacio de trabajo y responde{ "workspace": { "name": "..." } }. Solo del propietario, ya que todos los colegas ven el nombre; cualquier otra persona es rechazada con un 403.POST /v1/team/leavesaca a un colega del espacio de trabajo y lo pasa a uno nuevo propio en Free, del que es propietario, y responde{ "workspace": { "id": "...", "name": "...", "plan": "FREE" } }; nada del espacio de trabajo antiguo se va con él. El propietario no puede salir (un 409).GET /v1/team/marketsresponde con cada sector (markets[]:id,name,description,chosen), cuándo eligió el espacio de trabajo (chosenAt) y si esta persona puede cambiarlo (canChange).POST /v1/team/marketscon{ "markets": ["brokers", "tech"] }(ids de esa lista:brokerses Finanzas) sustituye la elección y responde con los ids que conservó ychosenAt. Es solo del propietario (cualquier otra persona recibe un 403), un id que no conoce se descarta, y tiene que quedar al menos uno: ninguno es un 400. Los sectores deciden qué feeds y plantillas se ofrecen al espacio de trabajo.