Los eventos indican qué sucede mientras trabaja un agente. Los elementos son los mensajes y las llamadas a herramientas que se guardan y que puedes recuperar más adelante. Usa los eventos para actualizar tu aplicación en tiempo real y los elementos para mostrar el historial guardado.
Tu aplicación usa eventos de entrada para enviar mensajes, cancelar turnos o devolver resultados de herramientas. El agente envía eventos que informan sobre la salida y los cambios en la sesión. Para enviar datos de entrada, consulta Ejecutar y continuar sesiones.
Consumir un flujo de eventos
Suscríbete antes de enviar una tarea para que tu aplicación reciba los primeros eventos del turno. Pasa como argumentos tu cliente de API, el ID de sesión de la conversación y un manejador de eventos:
# Pass your saved session ID to this helper.
def stream_session(client: OpenAI, session_id: str, handle_event):
with client.beta.agents.sessions.events.stream(session_id) as events:
for event in events:
handle_event(event)
match event.type:
case "agent.session.idle":
continue
case "error":
raise RuntimeError(event.error.message)
case "agent.session.failed" | "agent.session.environment.failed":
raise RuntimeError(f"Agent lifecycle failure: {event.type}")
case "agent.session.turn.failed":
if event.turn.subagent_id is None:
detail = event.turn.error.message if event.turn.error else ""
raise RuntimeError(f"{event.type}: {detail}")
case "agent.session.turn.cancelled":
if event.turn.subagent_id is None:
raise RuntimeError("The agent turn was cancelled")
case "agent.session.turn.completed":
if event.turn.subagent_id is None:
return
raise RuntimeError("Stream closed before a turn ended. Retrieve the saved state.")La función auxiliar pasa cada evento a tu manejador y luego comprueba si corresponde a uno de los tipos de evento habituales. Si recibe agent.session.idle, sigue procesando eventos. Cuando se completa el turno del agente raíz, la función devuelve el control al código que la llamó. Lanza un error si el turno del agente raíz falla o se cancela, si falla la sesión o el entorno, o si llega un evento error. Los eventos de los turnos de subagentes no ponen fin al flujo. Tu manejador decide cómo mostrar la salida. El código que llama a la función auxiliar se encarga de manejar los errores que esta lanza. Si el flujo se cierra antes de que termine un turno, la función auxiliar lanza un error. Consulta Cómo recuperar un flujo tras una desconexión.
Enviar un mensaje después de suscribirte
Esta versión acepta un mensaje y lo envía después de abrir el flujo:
# Pass your saved session ID and message to this helper.
def send_and_stream(client: OpenAI, session_id: str, text, handle_event):
with client.beta.agents.sessions.events.stream(session_id) as events:
client.beta.agents.sessions.events.create(
session_id,
events=[
{
"type": "agent.session.input.message",
"input": [
{
"role": "user",
"content": [{"type": "input_text", "text": text}],
}
],
}
],
)
for event in events:
handle_event(event)
match event.type:
case "agent.session.idle":
continue
case "error":
raise RuntimeError(event.error.message)
case "agent.session.failed" | "agent.session.environment.failed":
raise RuntimeError(f"Agent lifecycle failure: {event.type}")
case "agent.session.turn.failed":
if event.turn.subagent_id is None:
detail = event.turn.error.message if event.turn.error else ""
raise RuntimeError(f"{event.type}: {detail}")
case "agent.session.turn.cancelled":
if event.turn.subagent_id is None:
raise RuntimeError("The agent turn was cancelled")
case "agent.session.turn.completed":
if event.turn.subagent_id is None:
return
raise RuntimeError("Stream closed before a turn ended. Retrieve the saved state.")Manejar las actualizaciones
Usa el campo type del evento para decidir qué debe hacer tu aplicación:
- Mostrar texto: agrega el texto de
agent.session.turn.output_text.deltaal final de la parte del contenido que corresponda. Cuando llegueagent.session.turn.output_text.done, reemplaza esa parte con el texto completo. Es posible que no recibas actualizaciones parciales. - Seguir el progreso: los eventos de sesión, turno y elemento indican cómo avanza el trabajo. Comprueba si recibes
agent.session.turn.completed,agent.session.turn.failedoagent.session.turn.cancelledpara determinar el resultado del turno. - Proporcionar los datos de entrada requeridos: cuando recibas
agent.session.requires_action, recupera la sesión y revisarequired_actions. Es posible que tu código deba devolver el resultado de una función, conectar un entorno o gestionar el acceso a un origen desde el navegador o el inicio de sesión.
Que la sesión esté inactiva o que el flujo se haya cerrado no basta para confirmar que el turno se completó correctamente. Que un turno se haya completado tampoco garantiza que todas las herramientas se hayan ejecutado correctamente. Revisa la salida del agente.
Usa item_id, output_index y content_index para asociar las actualizaciones de texto con la misma parte del contenido. Por ejemplo, estos eventos abreviados actualizan una misma parte:
{
"type": "agent.session.turn.output_text.delta",
"item_id": "msg_789",
"output_index": 0,
"content_index": 0,
"delta": "Acme competes"
}
{
"type": "agent.session.turn.output_text.done",
"item_id": "msg_789",
"output_index": 0,
"content_index": 0,
"text": "Acme competes on price and distribution."
}
Cada evento tiene su propio event_id. El item_id que comparten identifica el elemento guardado, que incluye el contenido, el estado y la fase del mensaje. Consulta Recuperar el trabajo guardado.
Consulta la referencia de eventos en tiempo real para ver todos los tipos de eventos y sus campos. Los eventos de este flujo son distintos de los webhooks. Para ver la actividad de los subagentes y saber cuál ejecutó cada comando, consulta Observar la delegación.
Obtener elementos y turnos
Usa el ID de sesión que figura en el estado de la conversación de tu aplicación para recuperar el trabajo guardado:
- Elementos de la sesión: obtén la lista de elementos para recuperar los mensajes y las llamadas a herramientas del agente raíz a lo largo de los turnos.
- Turnos: obtén la lista de turnos para explorar el trabajo de la sesión. Recupera un turno por su ID para revisar su estado, sus marcas de tiempo, sus datos de uso y cualquier error registrado.
- Elementos de un turno: para un turno del agente raíz, usa el punto de acceso Listar elementos del turno. Cada subagente tiene su propio historial de elementos y un punto de acceso para consultar los elementos de cada turno.
Los puntos de acceso que devuelven listas entregan una página a la vez. Usa las funciones auxiliares de paginación del SDK o el cursor after para recuperar más resultados. Es posible que una sola página no contenga todos los elementos de un turno. Usa order: "asc" para leer los elementos del más antiguo al más reciente.
Cómo recuperar un flujo tras una desconexión
Recupera la salida que no recibiste a partir de los elementos guardados. Para restaurar la vista de tu aplicación:
- Abre un flujo nuevo y almacena temporalmente los eventos entrantes.
- Recupera la sesión y sus elementos guardados mientras el flujo sigue conectado.
- Restaura el estado local a partir de esos elementos y usa el ID de cada elemento como clave.
- Usa
item_idpara aplicar a cada elemento las actualizaciones que almacenaste temporalmente. Descarta las actualizaciones de los elementos que ya alcanzaron su estado final en el historial recuperado. - Reanuda el procesamiento de eventos en tiempo real.
Cuando te vuelves a conectar a una sesión que falló, el flujo informa del fallo registrado y se cierra.
Si la sesión recuperada tiene status: "failed" o recibes agent.session.failed,
deja de intentar conectarte y sigue las
instrucciones para recuperar la sesión.
Restaura los formularios de entrada pendientes a partir de required_actions de la sesión recuperada.
Los elementos del historial no indican qué solicitudes aún requieren una respuesta. Para las aprobaciones del navegador, identifica el formulario de cada solicitud mediante request_id y elimina los formularios de las solicitudes que ya no estén pendientes. Después de volver a conectarte, no necesitas reenviar la tarea ni las aprobaciones anteriores.
Un evento output_text.done puede reemplazar el contenido de un búfer de texto temporal con el texto completo. Los elementos guardados te permiten recuperar el trabajo completado, pero no todos los eventos intermedios que no recibiste.