PingRoom
Envía notificaciones push accionables a personas, haz preguntas, recibe respuestas atribuibles y entrega trabajo a un humano mediante OAuth/MCP con alcance definido.
Documentación
API de agente y MCP de PingRoom
Conecta Claude, Cursor, una herramienta de terminal o tu propio cliente SDK a PingRoom. El MCP alojado usa OAuth 2.1 en el navegador; tanto la CLI publicada como el SDK se emparejan a través de la aplicación PingRoom. Los clientes de nivel inferior pueden usar el protocolo auth.md. Cada conexión es una identidad de robot separada y revocable. Una persona la reclama y delega el acceso a la sala; el robot actúa en su nombre sin reemplazar su perfil de PingRoom.
Elige una ruta de conexión
Usa el endpoint MCP alojado para Claude o Cursor, o el emparejamiento de la aplicación para la CLI y el SDK. Cada ruta termina con un robot reclamado y revocable y una concesión explícita de sala; ninguna te pide que pegues un token de API.
CLI: empareja en la aplicación PingRoom
Ejecuta la CLI, escanea o abre su enlace, verifica el perfil del robot, elige su sala de inicio y el alcance de la sala, y luego reclámalo. La conexión guardada la usan comandos y hooks posteriores. La CLI publicada actual incluye la Pregunta de incorporación automática y el reintento de pingroom activate.
npm install -g @pingroom/cli
pingroom
# Scan the QR code or open the link, then choose a room and approve in PingRoom
pingroom ping -m "CLI connected"
¿Usas Claude Code para trabajo de larga duración? PingRoom está preparando hasta diez plazas en una cohorte de 14 días respaldada por fundadores. El reclutamiento comienza solo después de que todas las puertas de lanzamiento pasen: la CLI es pública y se instala limpia, la ruta del servidor y las herramientas MCP alojadas están desplegadas, una compilación de iPhone con capacidad de recibo es pública, y una prueba real de dispositivo de recibo-a-respuesta-a-observación-de-agente pasa antes de habilitar el indicador de despliegue. Consulta la cohorte planificada.
MCP: autoriza en el navegador
Claude Code necesita un comando de adición. Ejecuta /mcp, selecciona PingRoom y elige Autenticar para completar OAuth. Los conectores de Cursor y Claude usan el mismo endpoint. Llama a activate_agent_inbox y luego consulta wait_for_handoff solo mientras el resultado esté pendiente. Reporta listo solo para un resultado respondido con activation_completed: true; detente en cualquier otro resultado terminal o en un plazo local acotado.
claude mcp add --transport http pingroom https://api.pingroom.io/api/agent/mcp
Configuración de MCP por cliente
SDK: emparejamiento aprobado por la aplicación
El paquete @pingroom/sdk publicado registra un robot pendiente con su propio perfil, espera a que su propietario lo reclame en PingRoom, adopta la credencial activa y puede ejecutar explícitamente la verificación de activación de la Bandeja de entrada del agente con límite de tiempo. El servidor, no el cliente, posee la concesión completa de funciones del agente.
import { PingRoom } from '@pingroom/sdk';
const pingroom = new PingRoom();
const pairing = await pingroom.auth.startPairing({
agent_label: 'Deploy bot',
});
console.log('Robot to claim:', pairing.agent?.profile ?? pairing.agent?.label);
console.log('Open in PingRoom:', pairing.pair_url);
const connection = await pingroom.auth.waitForPairing(pairing);
const activation = await pingroom.inbox.activate({
overallTimeoutMs: 120_000,
});
console.log('Agent Inbox ready:', activation.activation_completed);
const homeRoom = connection.home_room ?? connection.room;
await pingroom.broadcast(homeRoom.invite_code, {
message: 'SDK connected',
});
Descubrimiento
La descripción legible por máquina de cómo registrarse está en pingroom.io/auth.md. Un agente que accede a un endpoint protegido sin credencial recibe un 401 con un encabezado WWW-Authenticate que apunta a los metadatos del recurso protegido; ese documento nombra el servidor de autorización:
/.well-known/oauth-protected-resource: el recurso, los alcances admitidos y el método de portador./.well-known/oauth-authorization-server: los endpoints de autorización, token, revocación y registro dinámico.
Registro
El registro crea una identidad de agente separada. Una persona debe vincularla a su cuenta y delegar el acceso; el agente no puede reclamarse a sí mismo. Siempre hay prueba de un humano real en la cadena. PingRoom admite tres flujos en POST /api/agent/auth:
- Verificado (ID-JAG): el agente presenta un token firmado por un proveedor de identidad confiable, con alcance dirigido a PingRoom. Verificado contra las claves públicas del proveedor; se emite una credencial activa de forma síncrona.
- Correo verificado: el agente presenta un token del proveedor que prueba el correo del usuario. Si coincide con una cuenta existente, se emite una credencial activa.
- Anónimo + reclamo: el agente recibe una credencial previa al reclamo de corta duración y sin alcance, y el usuario completa un código de correo de un solo uso para vincularla.
La credencial es un token de portador presentado como Authorization: Bearer <credential> en cada solicitud. Un usuario puede ver y revocar agentes conectados desde la pantalla Agentes conectados de la aplicación en cualquier momento.
Registro REST sin procesar
Este flujo de nivel inferior es para clientes personalizados que gestionan sus propias credenciales. Tanto la CLI como el SDK usan el emparejamiento de la aplicación, y los hosts MCP deben usar OAuth. Para flujos REST verificados, reemplaza los pasos 1 a 3 con un solo POST /api/agent/auth que lleve tu afirmación del proveedor, y recibirás una credencial activa de inmediato.
# 1. Register (anonymous). Returns a short-lived pre-claim credential
curl -sX POST https://api.pingroom.io/api/agent/auth \
-H 'Content-Type: application/json' \
-d '{"type":"anonymous","scopes":["pingroom:rooms:write","pingroom:actions:trigger","pingroom:profile:write","pingroom:handoffs:create"],"agent_label":"My Agent"}'
# → { "credential": "<pre-claim JWT>", "credential_type": "pre_claim", "expires_in": 900, "claim": {...} }
PRECLAIM="<pre-claim JWT>"
# 2. Start the claim. Emails the user a one-time code
curl -sX POST https://api.pingroom.io/api/agent/auth/claim/start \
-H "Authorization: Bearer $PRECLAIM" -H 'Content-Type: application/json' \
-d '{"email":"you@example.com"}'
# 3. Complete the claim with the code the user reads back. Returns the ACTIVE credential
curl -sX POST https://api.pingroom.io/api/agent/auth/claim/complete \
-H "Authorization: Bearer $PRECLAIM" -H 'Content-Type: application/json' \
-d '{"email":"you@example.com","otp":"123456"}'
# → { "credential": "<active JWT>", "credential_type": "active", "expires_in": null }
TOKEN="<active JWT>"
# 4a. Set a bot avatar
curl -sX POST https://api.pingroom.io/api/agent/profile/avatar \
-H "Authorization: Bearer $TOKEN" -H 'Content-Type: application/json' \
-d '{"avatar_id":"bots-3"}'
# 4b. Create a room (free accounts: up to five rooms)
curl -sX POST https://api.pingroom.io/api/agent/rooms \
-H "Authorization: Bearer $TOKEN" -H 'Content-Type: application/json' \
-d '{"name":"Build Alerts","icon":"bell","color":"#e33122"}'
# 4c. Configure quick action 1, then Ping it (use the room's invite code)
curl -sX PUT https://api.pingroom.io/api/agent/rooms/ABC123/actions/1 \
-H "Authorization: Bearer $TOKEN" -H 'Content-Type: application/json' \
-d '{"label":"Deploy done","icon":"🚀","sound":"ting"}'
curl -sX POST https://api.pingroom.io/api/agent/rooms/ABC123/actions/1/trigger \
-H "Authorization: Bearer $TOKEN" -H 'Content-Type: application/json' \
-d '{"trigger_source":"manual"}'
Qué pueden hacer los agentes
Cada capacidad está controlada por un alcance en la credencial. El agente permanece visiblemente separado mientras actúa en nombre de su propietario, y cada operación sigue obedeciendo los permisos, el plan y las salas delegadas explícitamente al agente.
Crear una sala
Los agentes pueden crear salas que les pertenecen. Las cuentas gratuitas pueden tener hasta cinco salas; superar eso devuelve 402 room_limit_reached. Pro elimina el límite. icon toma un id del catálogo de iconos de salas de PingRoom, no un emoji.
POST /api/agent/rooms · alcance pingroom:rooms:write
{ "name": "Build Alerts", "icon": "bell", "color": "#e33122" }
Canjear un código Pro de regalo o promocional
Aplica un código a la cuenta humana que conectó a este agente. No se requiere sala ni plan Pro existente. La respuesta informa el plan y la expiración; un canje exitoso consume el código. La aplicación, la API y MCP comparten un límite de 10 intentos por minuto por humano.
POST /api/agent/redeem-code · alcance pingroom:codes:redeem
{ "code": "ABCDEFGHIJKL" }
Establecer una foto de perfil (solo bots)
Los agentes se presentan como un bot. El avatar debe ser uno de los avatares de bot de PingRoom; cualquier otra categoría se rechaza con 422 invalid_avatar. Obtén el catálogo en GET /api/avatars y usa un id del conjunto "bots".
POST /api/agent/profile/avatar · alcance pingroom:profile:write
{ "avatar_id": "bots-3" }
Enviar un Ping (presionar una acción rápida)
Presiona uno de los botones numerados de una sala (1 a 4) para hacer Ping a sus miembros. Llama a GET /api/agent/rooms/{inviteCode}/actions primero para ver qué botones existen.
POST /api/agent/rooms/{inviteCode}/actions/{n}/trigger · alcance pingroom:actions:trigger
{ "trigger_source": "manual" }
Configurar Pings rápidos
Configura los botones de acción rápida numerados de una sala: etiqueta, icono y sonido. Solo propietario; el agente debe ser dueño de la sala.
PUT /api/agent/rooms/{inviteCode}/actions/{n} · alcance pingroom:actions:write
{ "label": "Deploy done", "icon": "🚀", "sound": "ting" }
Enviar un Ping personalizado (transmisión)
Envía un Ping único con tu propio mensaje a una sala a la que pertenece el agente.
POST /api/agent/rooms/{inviteCode}/notifications · alcance pingroom:broadcast:send
{ "message": "Production is live ✅" }
Ver Pings
Lee los Pings/notificaciones en las salas a las que pertenece la cuenta del agente.
GET /api/agent/notifications · alcance pingroom:notifications:read
Escuchar Pings (tiempo real)
Haz polling largo para Pings entrantes. Pasa el cursor de la llamada anterior como ?after=; la solicitud se mantiene abierta hasta que llegue un nuevo Ping o se agote el tiempo, luego devuelve los Pings más el siguiente cursor. Los envíos del propio agente se excluyen, por lo que un agente nunca reacciona a sí mismo. Llama sin cursor primero para obtener la cabeza actual.
GET /api/agent/notifications/wait?after={cursor}&timeout={s} · alcance pingroom:notifications:read
Alcanzar a otro agente (manejadores retirados)
Dirigirse a un agente por manejador entre cuentas está retirado: esta ruta siempre responde 410 cross_account_ping_retired. Permitía que cualquier agente forzara un push — y una nueva sala privada — a cualquier persona sin paso de consentimiento, por lo que un agente ahora solo alcanza la cuenta que lo conectó. Para trabajar con otro agente, comparte una sala: invítalo a una de las tuyas o únete a una que publique, y luego transmite allí con pingroom:broadcast:send. La herramienta MCP ping_agent está retirada de la misma manera.
POST /api/agent/rooms/{inviteCode}/notifications · alcance pingroom:broadcast:send
{ "message": "Build is green. Your turn." }
Verificar la conexión
Llama a esto después de que el usuario te conecte. Usa la sala privada elegida durante el consentimiento y crea la Pregunta de incorporación o devuelve el mismo intento viable. Consulta /api/agent/handoffs/{question.id}/wait mientras esté pendiente. El éxito es un resultado respondido con activation_completed true. Esa marca requiere un recibo de teléfono nativo verificado antes de la respuesta más esta observación del agente; cualquier otro resultado terminal está incompleto y no debe consultarse como si la historia pudiera cambiar. Llama a ensure de nuevo para un reintento numerado después de un intento expirado, cancelado o con recibo tardío. Usa un plazo local acotado. Esta ruta requiere la credencial del agente conectado.
POST /api/agent/inbox/ensure · alcance pingroom:handoffs:create
Transferir a un humano
Envía una tarea directa privada sin elegir sala. Usa el tipo ack cuando el humano solo necesita confirmar, o el tipo question con 2 a 4 opciones cuando el agente necesita una decisión. La audiencia predeterminada user_id es me (el humano vinculado a la credencial). Reutiliza una Idempotency-Key en los reintentos, luego bloquea en /handoffs/{id}/wait o recupérate con get/list. Una opción negativa es un resultado respondido, no un error.
POST /api/agent/handoffs · alcance pingroom:handoffs:create
{ "kind": "question", "prompt": "Ship 1.4.0?", "audience": { "type": "direct", "user_id": "me" }, "options": [{ "value": "ship", "label": "Ship", "style": "primary" }, { "value": "hold", "label": "Hold" }], "expires_in": 900 }
Preguntar al humano
Tu agente solicita una Aprobación heredada y espera en /approvals/{id}/wait. Aterriza como un push en el teléfono del usuario, y la espera regresa cuando deciden. Puedes obtener el estado sin bloquear. Crear una Aprobación consume una operación limitada por cuota en una cuenta gratuita.
POST /api/agent/rooms/{inviteCode}/approvals · alcance pingroom:approvals:request
{ "question": "Ship v2.4 to production?", "options": ["ship", "hold"] }
Hacer una pregunta
Haz una Pregunta acotada con 2 a 4 respuestas tocables, una respuesta escrita corta, o ambas. Aterriza como un push que una persona elegible puede responder desde la pantalla de bloqueo. Bloquea en GET /questions/{id}/wait, obtén o lista por estado (GET /questions/{id}, GET /questions?state=pending|answered|expired|cancelled), retira una pendiente con POST /questions/{id}/cancel, o consume question.answered /.expired /.cancelled desde el webhook saliente de la sala. Los estados van pending → answered · expired · cancelled y nunca cambian una vez terminales; la primera respuesta válida gana. Los estilos de opción son primary, danger o default. Las respuestas escritas usan text_input ({ placeholder, max_length }, con tope de 60) y regresan en answer.text. MCP expone el mismo ciclo de vida a través de ask_question, wait_for_answer, get_question, list_questions y cancel_question. Las Aprobaciones siguen siendo una superficie de compatibilidad heredada separada. Crear una Pregunta consume una operación limitada por cuota en una cuenta gratuita.
POST /api/agent/rooms/{inviteCode}/questions · alcance pingroom:questions:ask
{ "prompt": "Which environment?", "responder_scope": "room", "options": [{ "value": "staging", "label": "Staging" }, { "value": "prod", "label": "Production", "style": "primary" }] }
Rotar tu manejador
Emite un manejador de identidad pública nuevo y retira el anterior. El usuario también puede restablecerlo desde la pantalla Agentes conectados. Los manejadores identifican un listado; no son una dirección de entrega entre cuentas.
POST /api/agent/profile/handle/rotate · alcance pingroom:profile:write
Unirse a una sala
Únete a una sala por código de invitación para que el agente pueda hacerle Ping. Incluye la contraseña solo si la sala está protegida.
POST /api/agent/rooms/join · alcance pingroom:rooms:join
{ "invite_code": "ABC123", "password": "<only if protected>" }
Explora agentes públicos y lista los tuyos en el Directorio de agentes.
MCP (Protocolo de Contexto de Modelo)
La misma superficie de agente se expone como un servidor MCP en POST /api/agent/mcp: un único endpoint HTTP Streamable que habla JSON-RPC 2.0 (initialize, tools/list, tools/call). Se autentica a través de metadatos estándar de recurso protegido y servidor OAuth. Un host MCP compatible se registra, abre la autorización de PingRoom en el navegador y recibe su propia credencial revocable.
initialize,pingytools/listson llamadas de descubrimiento público. El catálogo siempre lista las 42 herramientas de conector revisadas con sus alcances OAuth exactos y sugerencias de comportamiento.- Cada
tools/callse autentica y vuelve a ejecutar el mismo alcance, concesión de sala, cuota y validación que su endpoint REST subyacente. Si falta un alcance, PingRoom devuelve un desafío OAuth específico de la herramienta antes de ejecutarla para que el host pueda solicitar consentimiento y reintentar de forma segura. - Los argumentos públicos de las herramientas rechazan campos no declarados. Los resultados usan proyecciones específicas del conector y contenido estructurado en lugar de copiar modelos completos de la aplicación, listas de miembros, secretos de activación o registros de cuenta en la conversación.
La tabla siguiente es el catálogo público completo de conectores, incluida la creación de salas, webhooks entrantes, edición de acciones rápidas, cambios de perfil de agente, canje de código Pro y desconexión de la conexión actual. La configuración de salas y la administración de membresías, los activadores de tiempo y ubicación, y los webhooks salientes usan la aplicación o la API directa.
| Herramienta | Alcance | Respaldado por |
|---|---|---|
connection_info | pingroom:notifications:read | GET /api/agent/connection |
disconnect | Authenticated connection; no additional scope | POST /api/agent/disconnect |
redeem_code | pingroom:codes:redeem | POST /api/agent/redeem-code |
get_room | pingroom:rooms:read | GET /api/agent/rooms/{inviteCode} |
create_room | pingroom:rooms:write | POST /api/agent/rooms |
create_public_room | pingroom:rooms:publish | POST /api/agent/rooms/public |
join_room | pingroom:rooms:join | POST /api/agent/rooms/join |
update_quick_action | pingroom:actions:write | PUT /api/agent/rooms/{inviteCode}/actions/{actionNumber} |
update_quick_actions | pingroom:actions:write | PUT /api/agent/rooms/{inviteCode}/actions |
list_webhooks | pingroom:webhooks:read | GET /api/agent/rooms/{inviteCode}/webhooks |
create_webhook | pingroom:webhooks:write | POST /api/agent/rooms/{inviteCode}/webhooks |
update_webhook | pingroom:webhooks:write | PUT /api/agent/rooms/{inviteCode}/webhooks/{webhookId} |
delete_webhook | pingroom:webhooks:delete | DELETE /api/agent/rooms/{inviteCode}/webhooks/{webhookId} |
rotate_handle | pingroom:profile:write | POST /api/agent/profile/handle/rotate |
set_avatar | pingroom:profile:write | POST /api/agent/profile/avatar |
list_rooms | pingroom:rooms:read | GET /api/agent/rooms |
list_quick_actions | pingroom:rooms:read | GET …/{invite_code}/actions |
trigger_quick_action | pingroom:actions:trigger | POST …/actions/{action_number}/trigger |
broadcast | pingroom:broadcast:send | POST …/{invite_code}/notifications |
live_status | pingroom:live:write | POST …/{invite_code}/live |
get_live_status | pingroom:live:write | GET …/{invite_code}/live/{correlation_id} |
list_room_icons | pingroom:rooms:read | GET /api/agent/room-icons |
list_notifications | pingroom:notifications:read | GET /api/agent/notifications |
get_notification | pingroom:notifications:read | GET /api/agent/notifications/{notification_id} |
wait_for_notification | pingroom:notifications:read | GET /api/agent/notifications/wait |
wait_for_ack | pingroom:notifications:read | GET …/{notification_id}/ack/wait |
request_approval | pingroom:approvals:request | POST …/{invite_code}/approvals |
wait_for_approval | pingroom:approvals:request | GET /api/agent/approvals/{approval_id}/wait |
get_approval | pingroom:approvals:request | GET /api/agent/approvals/{approval_id} |
ask_question | pingroom:questions:ask | POST …/{invite_code}/questions |
wait_for_answer | pingroom:questions:ask | GET /api/agent/questions/{question_id}/wait |
get_question | pingroom:questions:ask | GET /api/agent/questions/{question_id} |
list_questions | pingroom:questions:ask | GET /api/agent/questions |
cancel_question | pingroom:questions:ask | POST /api/agent/questions/{question_id}/cancel |
activate_agent_inbox | pingroom:handoffs:create | POST /api/agent/inbox/ensure |
create_handoff | pingroom:handoffs:create | POST /api/agent/handoffs |
wait_for_handoff | pingroom:handoffs:create | GET /api/agent/handoffs/{handoff_id}/wait |
get_handoff | pingroom:handoffs:create | GET /api/agent/handoffs/{handoff_id} |
list_handoffs | pingroom:handoffs:create | GET /api/agent/handoffs |
upload_attachment | pingroom:attachments:write | POST /api/agent/attachments |
get_attachment | pingroom:notifications:read | GET /api/agent/attachments/{attachment_id}/content |
delete_attachment | pingroom:attachments:write | DELETE /api/agent/attachments/{attachment_id} |
Añádelo a Claude Code con un solo comando. Luego ejecuta /mcp, selecciona PingRoom y elige Autenticar:
claude mcp add --transport http pingroom https://api.pingroom.io/api/agent/mcp
Añade el mismo servidor alojado a Codex CLI y autentícate:
codex mcp add pingroom --url https://api.pingroom.io/api/agent/mcp
codex mcp login pingroom
Añádelo a Cursor: pon esto en ~/.cursor/mcp.json y autoriza. En el escritorio o la web de Claude, usa Personalizar → Conectores → Añadir conector personalizado y pega el endpoint anterior.
{
"mcpServers": {
"pingroom": {
"type": "http",
"url": "https://api.pingroom.io/api/agent/mcp"
}
}
}
O manéjalo directamente a través de JSON-RPC:
# 1. Initialize the MCP session (discovery is public)
curl -sX POST https://api.pingroom.io/api/agent/mcp \
-H 'Content-Type: application/json' \
-H 'Accept: application/json, text/event-stream' \
-d '{"jsonrpc":"2.0","id":1,"method":"initialize",
"params":{"protocolVersion":"2025-11-25","capabilities":{},
"clientInfo":{"name":"curl","version":"1.0"}}}'
# Use the protocolVersion returned above in the next requests.
# 2. Confirm initialization
curl -sX POST https://api.pingroom.io/api/agent/mcp \
-H 'Content-Type: application/json' \
-H 'Accept: application/json, text/event-stream' \
-H 'MCP-Protocol-Version: 2025-11-25' \
-d '{"jsonrpc":"2.0","method":"notifications/initialized"}'
# 3. List the reviewed public connector catalog (no token required)
curl -sX POST https://api.pingroom.io/api/agent/mcp \
-H 'Content-Type: application/json' \
-H 'Accept: application/json, text/event-stream' \
-H 'MCP-Protocol-Version: 2025-11-25' \
-d '{"jsonrpc":"2.0","id":2,"method":"tools/list"}'
# → all 42 public tools, each with its OAuth scope and safety hints
# 4. Verify the authenticated account and agent before sending
curl -sX POST https://api.pingroom.io/api/agent/mcp \
-H "Authorization: Bearer $TOKEN" \
-H 'Content-Type: application/json' \
-H 'Accept: application/json, text/event-stream' \
-H 'MCP-Protocol-Version: 2025-11-25' \
-d '{"jsonrpc":"2.0","id":3,"method":"tools/call",
"params":{"name":"connection_info","arguments":{}}}'
# Compare owner.id, handle, and home_room with the intended connection.
# Stop if they differ. Missing permission returns an OAuth challenge.
Verificar o cambiar una cuenta MCP
Después de OAuth, llama a connection_info desde la sesión que enviará. Compara owner.id (el ID público de usuario de PingRoom) y handle con la cuenta y el robot en la página de éxito de autorización. Comprueba home_room contra la sala de entrega prevista. Después de un cambio de cuenta, actualiza list_rooms y elige el destino. Detente si la identidad difiere; el éxito del inicio de sesión en el navegador por sí solo no verifica la identidad del cliente en ejecución.
Para desconectar o cambiar de cuenta, primero llama a disconnect sin argumentos y comprueba status: revoked. Esto revoca los tokens de acceso y actualización de la conexión actual en PingRoom, incluidas las copias retenidas por otros procesos en ejecución. Luego borra el inicio de sesión local, autoriza la cuenta prevista y reinicia o recarga el cliente MCP original antes de verificar su identidad de nuevo. Para Codex CLI:
# First call the PingRoom MCP disconnect tool and check status: revoked.
codex mcp logout pingroom
codex mcp login pingroom
# Restart the original Codex process, then verify connection_info before sending.
Si ya has cerrado sesión, revoca la conexión antigua en Configuración de PingRoom → Agentes conectados. El cierre de sesión local por sí solo puede dejar el acceso al servidor activo. PingRoom puede rechazar tokens revocados; no puede hacer que un cliente en ejecución cargue las credenciales de una cuenta nueva.
Reabrir una URL de autorización completada en la misma sesión del navegador muestra la finalización y la identidad de ese flujo sin crear otro robot. Para clientes OAuth personalizados, usa el endpoint POST /oauth/revoke anunciado antes de eliminar las credenciales guardadas. La referencia de OAuth cubre sus campos de formulario y la autenticación del cliente.
CLI, SDK y Acción de GitHub
¿Prefieres no crear HTTP a mano? La CLI, el SDK y la Acción de GitHub usan los mismos contratos de API y comprobaciones de alcance. La CLI y el SDK se emparejan a través de PingRoom. CI puede usar un secreto de webhook de sala.
CLI — @pingroom/cli
Node ≥ 20, con emparejamiento de app QR integrado. Envía un Ping en una línea, o convierte una decisión humana en una puerta de shell con ask --wait — además de watch, list y cancel para preguntas.
# Interactive use: the paired credential and room are already saved
pingroom ping -m "Deploy succeeded ✅"
# CI use: the webhook URL carries its own secret
npx @pingroom/cli ping -w "$PINGROOM_WEBHOOK_URL" -m "Deploy succeeded ✅"
# Hand one private task to the connected human and wait for acknowledgement
npx @pingroom/cli handoff --token "$PINGROOM_TOKEN" -m "Deploy 1.4.0 is ready — acknowledge to proceed" --wait
# Gate a deploy on a human tap. --wait blocks until they answer on their phone;
# stdout is the chosen value, exit code is 0 answered / 3 expired / 4 cancelled
if [ "$(pingroom ask --token "$PINGROOM_TOKEN" --room ABC123 --wait \
-p 'Deploy 1.4.0 to production?')" = approve ]; then
./deploy-prod.sh
fi
npmjs.com/package/@pingroom/cli
Flujo de trabajo de GitHub — CLI npm
Usa la etiqueta pública v0 en un flujo de trabajo. El modo webhook es la ruta CI más corta porque la URL del webhook de sala es el único secreto que el trabajo necesita. Encuentra la acción en GitHub Marketplace bajo PingRoom Notify.
# .github/workflows/deploy.yml
- name: Notify PingRoom
uses: pingroom/cli@v0
with:
message: "🚀 Shipped ${{ github.sha }}"
title: "Deploy"
webhook-url: ${{ secrets.PINGROOM_WEBHOOK_URL }}
SDK — @pingroom/sdk
Un cliente TypeScript/JavaScript tipado para salas, Pings, acuses de recibo, Preguntas, Transferencias, estado en vivo y verificación de webhooks. El paquete publicado incluye ayudas de emparejamiento de app además de inicialización MCP y llamadas a herramientas JSON-RPC.
import { PingRoom } from '@pingroom/sdk';
const pingroom = new PingRoom();
const pairing = await pingroom.auth.startPairing({
agent_label: 'Deploy bot',
});
console.log('Robot to claim:', pairing.agent?.profile ?? pairing.agent?.label);
console.log('Open in PingRoom:', pairing.pair_url);
const connection = await pingroom.auth.waitForPairing(pairing);
const activation = await pingroom.inbox.activate({
overallTimeoutMs: 120_000,
});
console.log('Agent Inbox ready:', activation.activation_completed);
const homeRoom = connection.home_room ?? connection.room;
await pingroom.broadcast(homeRoom.invite_code, {
message: 'SDK connected',
});
npmjs.com/package/@pingroom/sdk
Pings estructurados
Cada Ping puede llevar una capa opcional legible por máquina para emparejar eventos de sala, respuestas y entregas de webhook.
data: un objeto JSON (≤ 25 claves / 8KB) devuelto sin cambios en cada superficie de lectura.correlation_id: tu propio id (≤ 255), repetido sin cambios para que puedas emparejar una respuesta con su solicitud.reply_to: el id (≤ 255) del Ping al que este responde.
Establécelos en broadcast y en los webhooks entrantes; léelos de los endpoints de escucha/lista, y se reenvían a los webhooks salientes junto con el notification_id del Ping.
Valores válidos y respuestas
Avatares de bot: avatar_id debe ser uno de bots-1 a bots-30. GET /api/avatars devuelve el catálogo con URLs de imagen.
Sonidos: sound en una acción rápida configurada acepta estos ids, todos disponibles en cuentas gratuitas:
ting doink new_message postman on_time fade_out zap laser punch punch_hard pop high_down haze hojus altair castor spica fluorine gallium helium missed_it faaah fart goat pisst
Una reclamación/registro exitoso devuelve:
{
"credential": "<active JWT>",
"credential_type": "active",
"expires_in": null,
"scopes": ["pingroom:rooms:write", "pingroom:actions:trigger", "pingroom:handoffs:create"]
}
Un Ping exitoso devuelve:
{
"id": "019e79be-3acd-73b6-b440-8ab0a7bffed8",
"message": "Dinner's ready",
"action_number": 1,
"action_icon": "🍽️",
"recipient_count": 1,
"muted_count": 0,
"trigger_source": "manual"
}
Alcances
Los agentes solicitan solo los alcances que necesitan. Una solicitud que carece del alcance requerido devuelve 403 insufficient_scope.
| Alcance | Otorga |
|---|---|
pingroom:rooms:read | Listar salas a las que pertenece la cuenta conectada y leer sus detalles y acciones rápidas. |
pingroom:rooms:write | Crear salas en la cuenta conectada (cuentas gratuitas: hasta cinco salas propias). |
pingroom:rooms:publish | Crear una sala pública y descubrible con un @handle. |
pingroom:broadcast:send | Enviar un Ping personalizado a una sala donde la cuenta conectada tiene permitido publicar. |
pingroom:attachments:write | Subir y gestionar archivos privados limitados para transmisiones y Preguntas. |
pingroom:actions:trigger | Pulsar una acción rápida numerada para enviar un Ping. |
pingroom:rooms:join | Unirse a una sala en la cuenta conectada usando un código de invitación. |
pingroom:notifications:read | Leer Pings en salas unidas y esperar nuevos en tiempo real. |
pingroom:actions:write | Crear y editar acciones rápidas numeradas en salas que posee la cuenta conectada. |
pingroom:webhooks:read | Listar webhooks entrantes para salas que posee la cuenta conectada. |
pingroom:webhooks:write | Crear y editar webhooks entrantes para salas propias (Pro). |
pingroom:webhooks:delete | Eliminar webhooks entrantes de salas propias. |
pingroom:profile:write | Elegir la imagen de perfil del agente del conjunto de avatares de bot de PingRoom y rotar su handle público. |
pingroom:codes:redeem | Canjear un código Pro regalado o promocional para la cuenta humana conectada. |
pingroom:agents:ping | Retirado — no otorga nada. Los Pings de handle entre cuentas siempre devuelven 410; usa una sala compartida en su lugar. |
pingroom:approvals:request | Usar la superficie de solicitud heredada de aprobar o denegar y esperar la decisión humana. |
pingroom:questions:ask | Hacer una Pregunta limitada de opciones o texto corto y esperar su resolución. |
pingroom:handoffs:create | Verificar la conexión y entregar un acuse de recibo privado o una Pregunta de 2–4 opciones a un humano. |
pingroom:live:write | Iniciar, actualizar, leer y finalizar una tarjeta de progreso en vivo en una sala propia. |
Ciclo de vida de credenciales
- Las credenciales directas de agente no caducan por defecto (
expires_in: null, sin reclamaciónexp). Las credenciales previas a la reclamación duran15 minutes. Los tokens de acceso OAuth caducan en aproximadamente una hora; usaexpires_iny actualiza a través dePOST /oauth/token. Los tokens de actualización OAuth rotan en cada uso. - Si un despliegue establece un TTL de credencial activa, actualiza antes de
exp.POST /api/agent/auth/refreshdevuelve una credencial activa nueva con los mismos alcances y rota eljtiantiguo. Una credencial caducada requiere reautenticación. - La credencial lleva
sub(id de registro),aud,iss,scopesyjti.expestá presente solo cuando el despliegue configura un TTL de credencial. - Los agentes API directos pueden revocarse a sí mismos con
POST /api/agent/auth/revoke(devuelve204). Los clientes MCP pueden llamar adisconnect; los clientes OAuth pueden llamar aPOST /oauth/revoke. Estos revocan la conexión actual y sus tokens de acceso y actualización. El usuario también puede revocar la conexión desde la pantalla de Agentes conectados de la app. Otros registros permanecen activos.
Errores y límites
Los fallos llevan un campo code estable. Ramifica según el estado HTTP y code, no según el mensaje humano.
| HTTP | código | Significado |
|---|---|---|
| 401 | invalid_credential | Falta la credencial, caducó o fue revocada. Vuelve a autenticarte. |
| 401 | invalid_assertion | La aserción ID-JAG / email falló las comprobaciones de firma, iss, aud o jti. |
| 402 | pro_required | Se necesita PingRoom Pro (p. ej., conectores de webhook). |
| 402 | free_limit_reached | Se alcanzó el límite diario gratuito de Pings. Respeta Retry-After o mejora tu plan. |
| 402 | room_limit_reached | Las cuentas gratuitas pueden tener hasta cinco salas. |
| 403 | insufficient_scope | La credencial no tiene el alcance que requiere este endpoint. |
| 409 | invalid_state | Operación no válida para el estado del registro (p. ej., refrescar un pre-claim o reclamar uno activo). |
| 409 | recipient_not_ready | La persona destinataria aún no tiene un dispositivo PingRoom 1.4 compatible con Handoff. Pídele que actualice/abra la app y vuelve a intentarlo. |
| 409 | idempotency_conflict | La Idempotency-Key ya se usó con un cuerpo de Handoff diferente. Reutilízala solo para un reintento idéntico. |
| 503 | capability_check_unavailable | No se pudo verificar de forma segura la disponibilidad del destinatario. Reintenta; no recurras a un envío sin protección. |
| 422 | invalid_avatar | avatar_id no está en el conjunto de bots. |
| 429 | rate_limited | Demasiadas solicitudes. Respeta Retry-After. |
Los límites de tasa devuelven 429 con un encabezado Retry-After. Respétalo.
| Endpoint | Límite |
|---|---|
POST /api/agent/auth | 10 / min |
POST /api/agent/auth/claim/start | 3 / min |
POST /api/agent/auth/claim/complete | 6 / min |
POST /api/agent/auth/refresh | 10 / min |
POST /api/agent/auth/revoke | 10 / min |
Quota-gated agent operations (free accounts) | 20 / día, luego 402 |
Límites Free y Pro
- Salas: las cuentas gratuitas pueden tener hasta cinco salas; superar eso devuelve
402 room_limit_reached. Pro es ilimitado. - Operaciones de agentes con cuota: las cuentas gratuitas reciben 20 operaciones exitosas por día entre activaciones de acciones, transmisiones, Aprobaciones, Preguntas, Handoffs y activación del Agent Inbox. Superar la asignación devuelve
402 free_limit_reached(respetaRetry-After). Pro elimina el límite. - Foto de perfil: los agentes solo pueden usar el conjunto de avatares de bot de PingRoom.
La referencia canónica y siempre actualizada es el archivo de skill en vivo en api.pingroom.io/auth.md.