Teams retiene a quienes se unen de forma anónima en la sala de espera y cada vez más los bloquea con un captcha. Iniciar la sesión del bot en una cuenta real de Microsoft 365 elimina ambas cosas. Aquí están la API, la configuración del tenant y por qué Teams funciona distinto que Meet.

Un bot anónimo que se une a una reunión de Teams va a la sala de espera (lobby). Alguien tiene que fijarse en el aviso de "hay alguien esperando" y dejarlo entrar. Si nadie lo hace, el bot agota su tiempo de espera y usted se queda sin grabación. Microsoft también ha ido añadiendo de forma constante desafíos captcha en el camino de unión como invitado, que un navegador headless no puede resolver.
Un bot con la sesión iniciada en una cuenta real de Microsoft 365 se salta todo eso. Sin sala de espera, sin aviso que el anfitrión pueda pasar por alto, sin captcha. Su nombre en la lista de participantes viene de la cuenta.

Opcional y por bot. Omita teams_config y sus bots siguen uniéndose como invitados, sin cambios.
Por qué esto no es SAML
Lanzamos los bots autenticados de Google Meet usando SAML, con nuestra API actuando como proveedor de identidad para un Workspace que usted posee. La pregunta obvia es por qué Teams no funciona igual.
Microsoft no ofrece un camino equivalente. Conseguir que Entra ID acepte un IdP de terceros implica la federación completa del tenant, que es un compromiso mucho más pesado que subir un certificado a un perfil de SSO heredado (Legacy SSO profile), y no es algo que le pediríamos a un cliente. Así que Teams se autentica como lo hace una persona: correo, luego contraseña, escritos en login.microsoftonline.com.
Esa única diferencia determina todo lo demás:
| Google Meet | Microsoft Teams | |
|---|---|---|
| Mecanismo | Aserción SAML, actuamos como IdP | Usuario y contraseña |
| El recurso workspace guarda | Dominio, certificado, clave privada | Solo el dominio del tenant |
| ¿La credencial sale de nuestros servidores? | No. Firmamos una aserción del lado del servidor. | Sí. El bot la obtiene una vez sobre TLS. |
| Secreto almacenado | private_key_pem | password, cifrada |
| Modo de fallo | Certificado que no coincide, usuario suspendido | Contraseña incorrecta, solicitud de MFA |
El bot de Teams tiene que tener la contraseña real en el momento de unirse, porque no hay otra forma de escribirla. La obtiene una sola vez desde un endpoint autenticado de resolución, identificado por un id de sesión de vida corta, con la misma forma en que el bot de Zoom obtiene su token OBF. La contraseña se cifra en reposo con AES-256-GCM y ningún endpoint de lectura la devuelve nunca.
La API
La misma estructura de dos niveles que en Meet: un workspace que representa un tenant de Microsoft 365, y logins que cuelgan de él.
POST /v2/teams-workspaces
GET /v2/teams-workspaces
GET /v2/teams-workspaces/:workspace_id
PATCH /v2/teams-workspaces/:workspace_id
DELETE /v2/teams-workspaces/:workspace_id
POST /v2/teams-logins
GET /v2/teams-logins
GET /v2/teams-logins/utilization
GET /v2/teams-logins/:credential_id
PATCH /v2/teams-logins/:credential_id
DELETE /v2/teams-logins/:credential_idEl workspace es ligero, porque no hay ningún certificado que guardar. Existe para que las cuentas de un mismo tenant se agrupen y se puedan deshabilitar como una unidad:
{
"name": "Contoso Production Tenant",
"domain": "contoso.onmicrosoft.com"
}Se le pueden agregar cuentas de cualquiera de los dominios verificados del tenant.
Después, cada cuenta:
{
"workspace_id": "f0e1d2c3-b4a5-6789-0123-456789abcdef",
"name": "Teams Bot Pool — Account 1",
"email": "bot1@contoso.onmicrosoft.com",
"password": "...",
"email_group": "bots@contoso.onmicrosoft.com"
}password es de solo escritura. Leer el login de vuelta le da todo excepto la contraseña:
{
"credential_id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
"workspace_id": "f0e1d2c3-b4a5-6789-0123-456789abcdef",
"name": "Teams Bot Pool — Account 1",
"email": "bot1@contoso.onmicrosoft.com",
"email_group": "bots@contoso.onmicrosoft.com",
"state": "active",
"last_error_message": null,
"last_error_at": null,
"last_used_at": "2026-08-10T14:22:03.000Z",
"active_session_count": 3,
"extra": null,
"created_at": "2026-08-01T09:12:44.000Z",
"updated_at": "2026-08-10T14:22:03.000Z"
}Rotar una contraseña es un PATCH con la nueva. No cambia nada más y los bots en ejecución conservan sus slots.
En un bot
{
"meeting_url": "https://teams.microsoft.com/l/meetup-join/...",
"bot_name": "Recording Bot",
"teams_config": {
"email_group": "bots@contoso.onmicrosoft.com",
"fallback": "anonymous"
}
}teams_config se resuelve igual que meet_config:
| Lo que envía | Qué ocurre |
|---|---|
null (el valor predeterminado) | Unión anónima como invitado. |
{ "email_group": "X" } | Round-robin entre los logins activos del grupo X. |
{ "credential_id": "Y" } | Fija el login Y. |
| Ambos, con un grupo no vacío | Gana email_group. |
{ "email_group": "" } solo | Round-robin entre todos los logins activos del equipo. |
{ "email_group": "", "credential_id": "Y" } | Se fija el login Y. Un grupo vacío no es un grupo, así que manda credential_id. |
En caso de saturación, fallback: "fail" devuelve FST_ERR_TEAMS_LOGIN_UNAVAILABLE con un 503 y fallback: "anonymous" recurre a una unión como invitado. Para Teams en concreto, "anonymous" es un valor predeterminado más razonable que para Meet, porque unirse como invitado a menudo sigue funcionando, solo que es más lento y menos fiable.
¿Cuántos bots puede ejecutar una sola cuenta a la vez?
Esto sale todo el tiempo, porque todo el mundo ha visto a Teams decir que solo puede estar activo en una reunión y que debe poner las demás en espera.
Ese límite es por sesión de cliente, no por cuenta. Viene de que una instancia de la app de Teams es dueña de un stack de audio. La página de límites publicada por Microsoft no tiene ningún tope por usuario de reuniones concurrentes, y su propia guía para estar en dos reuniones a la vez es usar un segundo dispositivo o un segundo perfil de navegador.
Cada bot de MeetingBaaS es su propio pod, con su propio navegador y su propio inicio de sesión nuevo en login.microsoftonline.com. Cada bot es una sesión de cliente distinta. Una cuenta puede respaldar muchos bots en reuniones diferentes de forma simultánea.
El tope predeterminado por login es de 20 sesiones concurrentes, y GET /v2/teams-logins/utilization informa contra él:
{
"logins_total": 3,
"logins_active": 3,
"logins_invalid": 0,
"concurrent_sessions": 41,
"concurrent_capacity": 60,
"utilization_pct": 68,
"by_email_group": [
{ "email_group": "bots@contoso.onmicrosoft.com", "logins": 3, "concurrent": 41, "capacity": 60 }
]
}Aun así, el techo real no es Teams. Es Entra ID. N inicios de sesión simultáneos de una cuenta desde N IP de pods distintos es exactamente el patrón que el Acceso condicional (Conditional Access) basado en riesgo está hecho para marcar, y cuando se dispara le llega un desafío de MFA que un navegador headless no puede responder. Si está llegando a la saturación, vale la pena probar a subir el tope por cuenta antes de aprovisionar más cuentas, pero mida con 5, luego 10, luego 20 en una sola cuenta y vigile los fallos de inicio de sesión en lugar de saltar directo a un número alto.
Configuración del tenant
Esta es la parte que requiere cuidado, así que lea la sección entera antes de cambiar nada.
Use un tenant dedicado
Cree las cuentas de bot en un tenant propio, por ejemplo bot1@contoso-bots.onmicrosoft.com. Con Business Basic basta.
Los bots autenticados necesitan ajustes a nivel de cuenta que no debería aplicar en un tenant donde inician sesión personas reales. Un tenant separado deja ese radio de impacto en cero. Esto no es un extra deseable, es la condición previa para todo lo que viene a continuación.
Asegúrese de que las cuentas de bot no reciban una solicitud de MFA
Un tenant nuevo viene con los valores predeterminados de seguridad (Security Defaults) activados, lo que fuerza la página de registro "Let's keep your account secure" en el primer inicio de sesión. Un navegador headless no puede superarla, y es la razón más común, con diferencia, de que falle un login de Teams.
Hay dos caminos, y cuál elegir depende del tenant:
Tenant dedicado a bots, sin cuentas humanas. Desactive Security Defaults en todo el tenant: entra.microsoft.com → Identidad (Identity) → Información general (Overview) → Propiedades (Properties) → Administrar valores predeterminados de seguridad (Manage security defaults) → Deshabilitado (Disabled).
Tenant con cuentas humanas dentro. Deje la MFA activada. Ponga las cuentas de bot en un grupo y excluya solo ese grupo de su política de Acceso condicional de "requerir MFA". Esto necesita Entra ID P1. Es más lento de configurar y mucho mejor higiene.
En cualquiera de los dos casos, compruebe también que la MFA heredada por usuario esté deshabilitada para las cuentas de bot, y desactive la campaña de registro de métodos de autenticación para que no reintroduzca la solicitud más adelante.
El estado final al que apunta: iniciar sesión como cuenta de bot le da correo, contraseña y luego "Stay signed in?", y nada en medio.
Inicie sesión una vez, a mano
Entre manualmente en cada cuenta de bot desde un navegador normal y despeje los intersticiales de primera ejecución que muestre Microsoft. El mismo razonamiento que el paso de onboarding de Workspace del lado de Meet: el primer inicio de sesión es interactivo tanto si le gusta como si no, así que quíteselo de encima antes de que un bot necesite la cuenta.
Registre el workspace y los logins
curl -X POST https://api.meetingbaas.com/v2/teams-workspaces \
-H "x-meeting-baas-api-key: $API_KEY" \
-H "Content-Type: application/json" \
-d '{"domain": "contoso-bots.onmicrosoft.com"}'Luego un POST /v2/teams-logins por cuenta.
Cómo se ve un fallo
Un inicio de sesión que falla de una forma que seguirá fallando pasa el login a invalid y deja de asignarlo. Las tres causas:
| Causa | Qué significa |
|---|---|
| Credenciales incorrectas | La contraseña cambió, o se escribió mal al crear el login. |
| Se requiere MFA | Security Defaults, una política de Acceso condicional o una detección de riesgo está desafiando a la cuenta. |
| Tiempo de espera agotado | Microsoft fue lento o el flujo se quedó atascado. |
Los tiempos de espera agotados se tratan como transitorios y no invalidan nada. Las otras dos causas sí, y registran last_error_message, last_error_at y failure_data con el bot que se topó con el problema.
Reactívelo una vez que haya corregido la causa:
PATCH /v2/teams-logins/:credential_id
{ "state": "active" }Si una cuenta empieza a fallar con MFA requerida después de semanas funcionando bien, casi siempre es el Acceso condicional basado en riesgo reaccionando a su concurrencia, no una contraseña cambiada. Revise los logs de inicio de sesión en Entra antes de ponerse a resetear nada.
Eliminar un login con sesiones en curso devuelve 409. Los slots se liberan cuando el proceso del bot termina, incluso cuando se cae, así que un pod muerto no filtra capacidad de forma permanente.
Relacionado
- Bots autenticados de Google Meet — el mismo problema, resuelto con SAML, y por qué difieren los dos
- Referencia de la API de Meeting BaaS
Si está calculando cuántas cuentas necesita su volumen, o si la exclusión de Acceso condicional va a pasar con su equipo de seguridad, con gusto lo conversamos.