Referência: https://github.com/a2aproject/a2a-python/blob/main/src/a2a/server/agent_execution/context.py#L15
Como usar?
1. Visão geral
RequestContext
encapsula todas as informações de uma requisição que chega ao servidor A2A — mensagem do usuário, IDs de tarefa e contexto, tarefas relacionadas e metadados de chamada.
Ao receber uma mensagem, o Dispatcher do SDK cria (ou reaproveita) um RequestContext
e o encaminha aos seus AgentExecutors. Dentro do executor você não precisa alterar a infraestrutura: basta ler ou, em alguns casos, complementar o objeto.
2. Ciclo de vida resumido
sequenceDiagram
participant Client
participant Dispatcher
participant AgentExecutor
Client->>Dispatcher: MessageSendParams
Dispatcher->>Dispatcher: Cria RequestContext
Dispatcher->>AgentExecutor: context (RequestContext)
AgentExecutor->>AgentExecutor: Processa context
AgentExecutor-->>Dispatcher: Resultado + context.related_tasks
3. Acesso rápido às propriedades
Propriedade | Tipo | Uso típico dentro do Executor |
---|---|---|
context.message | Message | None | Conteúdo bruto da mensagem do usuário (texto, anexos) |
context.task_id | str | None | Identificador único da tarefa corrente |
context.context_id | str | None | Identificador do “chat” ou sessão |
context.current_task | Task | None | Objeto persistido da tarefa, se já existir |
context.related_tasks | list[Task] | Tarefas auxiliares (p.ex. execução de ferramenta) |
context.configuration | MessageSendConfiguration | None | Configurações de envio definidas pelo cliente |
context.call_context | ServerCallContext | None | Contexto gRPC/HTTP — cabeçalhos, deadline, etc. |
Métodos úteis:
get_user_input(delimiter="\n")
→ str
Concatena todas as partes de texto da mensagem.attach_related_task(task)
Adiciona uma novaTask
relacionada ao processamento atual.
4. Exemplo mínimo
from agent2agent.executors import AgentExecutor
from agent2agent.context import RequestContext
class EchoExecutor(AgentExecutor):
async def run(self, context: RequestContext) -> str:
# 1. Obter texto do usuário
user_text = context.get_user_input()
# 2. (Opcional) acessar IDs
print(f"Task: {context.task_id} Context: {context.context_id}")
# 3. Responder algo
return f"Você disse: {user_text}"
Observação: você não cria
RequestContext
manualmente no executor; ele chega pronto no métodorun
.
5. Exemplo avançado com tarefas relacionadas
Imagine que seu agente precise chamar uma tool externa que gera uma tarefa independente:
from agent2agent.models import Task
class SummarizeExecutor(AgentExecutor):
async def run(self, context: RequestContext) -> str:
text = context.get_user_input()
summary = await self._call_summarizer_tool(text)
# Criar uma Task representando a execução da tool
tool_task = Task(
id="tool-" + context.task_id,
contextId=context.context_id,
status="completed",
result=summary,
)
context.attach_related_task(tool_task) # 🔑
return summary
async def _call_summarizer_tool(self, text: str) -> str:
...
Ao final do processamento, o Dispatcher persiste tool_task
porque está listado em context.related_tasks
.
6. Boas práticas
- Somente leitura: trate as propriedades como read-only; altere apenas se for realmente necessário (ex.:
current_task
quando criar/atualizar uma tarefa). - Evite mutações profundas em
context.message
; se precisar, clone o objeto. - Gerencie erros cedo: se faltar informação vital, lance exceções específicas — o Dispatcher converte para
InvalidParamsError
. - Anexe tarefas relacionadas sempre que seu executor criar subtarefas (tool use, chain-of-thought explicita etc.).
- Deadline awareness: utilize
context.call_context.deadline
(quando disponível) para respeitar tempos máximos de execução.
7. Tratamento de erros
from agent2agent.errors import ServerError, InvalidParamsError
class SafeExecutor(AgentExecutor):
async def run(self, context: RequestContext) -> str:
if not context.message:
raise ServerError(InvalidParamsError("Mensagem vazia"))
# processamento normal …