06-03-04 — Agent Framework 1.0: MCP nativo, A2A, graph workflow engine
TL;DR
O AF 1.0 tem três features que o diferenciam tecnicamente: MCP nativo (agentes descobrem e consomem tools de qualquer servidor MCP sem código extra), A2A protocol (agentes de diferentes frameworks colaboram por HTTP/JSON), e graph workflow engine (herança do AutoGen: fluxos com estado, condicionais e paralelismo). Juntos, esses três pilares tornam o AF 1.0 o framework mais interoperável para enterprise.
MCP — Model Context Protocol nativo
MCP (Anthropic, 2024) define um protocolo padrão para que LLMs descubram e invoquem ferramentas. O AF 1.0 implementa tanto o lado client (consumir tools de servidores MCP) quanto o lado server (expor plugins como servidor MCP).
Consumindo um servidor MCP externo
using Microsoft.AgentFramework.MCP;
// Conecta a um servidor MCP (ex: servidor de acesso a banco de dados)
var mcpClient = new McpClient("https://meu-servidor-mcp.empresa.com");
// AF 1.0 descobre as tools automaticamente e as registra no Kernel
await kernel.AddMcpToolsAsync(mcpClient);
// A partir daqui, o agente pode usar qualquer tool do servidor MCP
// como se fossem plugins nativos — sem código adicional
var resultado = await kernel.InvokePromptAsync(
"Quantos contratos vencem nos próximos 30 dias?",
new KernelArguments(new OpenAIPromptExecutionSettings
{
FunctionChoiceBehavior = FunctionChoiceBehavior.Auto()
}));
Expondo um agente como servidor MCP
// O agente AF 1.0 pode ser consumido por Claude, Cursor, qualquer cliente MCP
builder.Services.AddMcpServer(options =>
{
options.ServerName = "Assistente Empresarial Impar";
options.ServerVersion = "1.0.0";
options.ExposeKernelFunctions = true; // todos os plugins viram tools MCP
});
app.MapMcpEndpoints("/mcp"); // SSE em /mcp/sse, HTTP em /mcp/messages
A2A — Agent-to-Agent Protocol
A2A (Google, 2025 — adotado pela Microsoft no AF 1.0) permite que agentes de frameworks diferentes se descubram e colaborem:
using Microsoft.AgentFramework.A2A;
// Descobrir um agente remoto via URL do Agent Card
var remoteAgent = await A2AClient.DiscoverAgentAsync(
"https://agente-clima.parceiro.com/.well-known/agent.json");
// Delegar tarefa — AF 1.0 trata o agente remoto como qualquer plugin
var resultado = await remoteAgent.SendTaskAsync(new A2ATask
{
Message = new A2AMessage
{
Role = "user",
Parts = [new TextPart("Qual a previsão para SP esta semana?")]
}
});
// Streaming de resposta
await foreach (var evento in remoteAgent.StreamTaskAsync(task))
{
Console.Write(evento.Delta?.Text);
}
Registrando seu agente para ser descoberto
// AF 1.0 gera e serve o Agent Card automaticamente
builder.Services.AddA2AServer(options =>
{
options.AgentName = "Assistente Financeiro Impar";
options.Description = "Análise financeira com acesso ao ERP SAP";
options.Provider = new A2AProvider { Name = "Impar", Url = "https://impar.com.br" };
options.Capabilities = new A2ACapabilities
{
Streaming = true,
PushNotifications = true
};
options.Skills = [
new A2ASkill { Id = "analise-contratos", Name = "Análise de Contratos" },
new A2ASkill { Id = "kpis-financeiros", Name = "KPIs Financeiros" }
];
});
app.MapA2AEndpoints(); // serve /.well-known/agent.json e /a2a/tasks/*
Graph Workflow Engine
Herdado do AutoGen v0.4, o graph engine do AF 1.0 permite fluxos de trabalho com estado que vão além de simples tool calling:
using Microsoft.AgentFramework.Graph;
// Define o estado do workflow
record WorkflowState(string UserQuery, string? ResearchResult, string? FinalReport);
// Cria o grafo de workflow
var workflow = new AgentWorkflow<WorkflowState>()
.AddNode("pesquisa", async (state, ctx) =>
{
var resultado = await ctx.InvokeAgentAsync<PesquisaAgent>(state.UserQuery);
return state with { ResearchResult = resultado };
})
.AddNode("redacao", async (state, ctx) =>
{
var relatorio = await ctx.InvokeAgentAsync<RedacaoAgent>(state.ResearchResult!);
return state with { FinalReport = relatorio };
})
.AddNode("revisao", async (state, ctx) =>
{
// Human-in-the-loop: pausa aguardando aprovação
var aprovado = await ctx.RequestHumanApprovalAsync(
state.FinalReport!,
"Aprovar relatório para envio?");
return state;
})
.AddConditionalEdge("pesquisa", state =>
state.ResearchResult?.Length > 100 ? "redacao" : "pesquisa") // retry se insuficiente
.AddEdge("redacao", "revisao")
.SetEntryPoint("pesquisa");
// Executar com checkpointing
var runner = new WorkflowRunner(workflow, checkpointer: new AzureTableCheckpointer());
var resultado = await runner.RunAsync(new WorkflowState("Analise concorrência Q2 2026"));
Exemplo integrado: MCP + A2A + Graph
// Um workflow que usa MCP para tools locais e A2A para delegar pesquisa
var workflow = new AgentWorkflow<RelatorioState>()
.AddNode("coleta_dados", async (state, ctx) =>
{
// Tools via MCP (servidor de dados SAP)
var kpis = await ctx.Kernel.InvokePromptAsync(
"Busque KPIs do trimestre via MCP");
return state with { KPIs = kpis.ToString() };
})
.AddNode("pesquisa_mercado", async (state, ctx) =>
{
// Delega pesquisa para agente especializado via A2A
var agentePesquisa = await A2AClient.DiscoverAgentAsync(pesquisaAgentUrl);
var pesquisa = await agentePesquisa.SendTaskAsync(
new A2ATask { Message = state.KPIs! });
return state with { MarketResearch = pesquisa.Result };
})
.AddNode("gera_relatorio", async (state, ctx) =>
{
// Geração local com todos os dados
var relatorio = await ctx.Kernel.InvokePromptAsync(
$"Gere relatório executivo com: KPIs={state.KPIs}, Mercado={state.MarketResearch}");
return state with { Report = relatorio.ToString() };
})
.SetEntryPoint("coleta_dados");
Como isso se conecta
- 06-03-03 AF 1.0: visão geral — contexto e lifecycle do framework
- Módulo 07 (MCP/A2A) — aprofundamento nos protocolos MCP e A2A
- 06-04-02 Google ADK — ADK também implementa A2A; agentes ADK e AF 1.0 interoperam
- 06-04-04 Desafio — o mesmo agente implementado com graph workflow do AF 1.0