Este repositório é uma prova de conceito de UI agêntica: uma interface que não é desenhada com antecedência pelo desenvolvedor, mas gerada em tempo real por um agente de inteligência artificial com base no contexto da conversa.
O cenário escolhido é análise de currículo versus vaga de emprego. O usuário faz upload dos dois documentos em PDF, digita uma pergunta e o agente responde com cards estruturados contendo nota de aderência, lista de requisitos, pontos fortes e sugestões de melhoria.
Em aplicações tradicionais, o desenvolvedor decide com antecedência quais componentes a tela vai ter, onde cada um fica e quais dados ele exibe. O layout é estático e controlado inteiramente pelo código.
Em uma UI agêntica, essa decisão passa a ser do agente. Ele recebe uma tarefa, processa informações e decide quais blocos visuais fazem sentido exibir, em qual ordem e com quais dados. A interface muda a cada execução, moldada pela saída do modelo.
Isso não significa que o modelo gera HTML ou CSS livremente — o que produziria resultados imprevisíveis e difíceis de controlar. Em vez disso, ele chama funções bem definidas (chamadas tools) que constroem os componentes visuais com segurança usando uma especificação formal chamada A2UI.
O projeto é dividido em dois subprojetos que se comunicam via protocolo AG-UI.
Backend — construído com Mastra, um framework Node.js para agentes de IA. Ele recebe os PDFs, extrai o texto, repassa para o modelo Claude (Anthropic) e emite eventos em tempo real para o frontend.
Frontend — construído com Angular 21. Ele envia a requisição, escuta o stream de eventos e usa o renderer A2UI para montar os cards na tela conforme chegam.
AG-UI — protocolo padronizado de comunicação entre agentes e interfaces. Define um conjunto de tipos de eventos (início de stream, chunk de texto, resultado de tool, etc.) transmitidos via SSE (Server-Sent Events), que é um mecanismo HTTP de fluxo unidirecional do servidor para o cliente.
A2UI — especificação de formato para descrever componentes de interface em JSON. Em vez de HTML, o agente emite mensagens do tipo "crie uma surface com um Card contendo uma Column com estes Texts". O renderer no frontend interpreta essas mensagens e monta os componentes Angular reais.
Usuário
|
| upload dos PDFs + pergunta
v
Frontend (Angular :4200)
|
| POST com SSE para /awp
v
Backend (Mastra :4113)
|
| extrai texto dos PDFs antes de enviar ao modelo
| envia conversa ao Claude claude-sonnet-4-5
v
Anthropic API
|
| Claude analisa e chama renderSurface(template, dados)
v
Backend — tool renderSurface
|
| monta mensagens A2UI (createSurface + updateComponents + updateDataModel)
| emite TOOL_CALL_RESULT via SSE
v
Frontend — AgentService
|
| A2uiRendererService processa as mensagens A2UI
| atualiza lista de surfaces
v
<a2ui-v09-surface> renderiza o card na tela
O modelo nunca gera JSON de layout diretamente. Ele sempre chama a tool renderSurface passando apenas o nome do template e os dados extraídos dos documentos. O código da tool é quem monta as mensagens A2UI com estrutura garantida.
- Node.js 20 ou superior
- pnpm 9 ou superior (instale com
npm install -g pnpm) - Chave de API da Anthropic (crie em console.anthropic.com)
1. Clone o repositório
git clone <url-do-repo>
cd agentic-ui
2. Configure a chave da Anthropic
Crie um arquivo .env dentro da pasta backend:
cd backend
echo "ANTHROPIC_API_KEY=sk-ant-SUA_CHAVE_AQUI" > .env
Substitua sk-ant-SUA_CHAVE_AQUI pela sua chave real.
3. Instale as dependências e suba o backend
cd backend
pnpm install
PORT=4113 pnpm dev
Aguarde até aparecer no terminal:
mastra ready
Studio: http://localhost:4113
API: http://localhost:4113/api
4. Em outro terminal, suba o frontend
cd frontend
pnpm install
pnpm start
Aguarde o build terminar e acesse http://localhost:4200.
5. Use a aplicação
- Clique em "Currículo (PDF)" e selecione o arquivo do currículo
- Clique em "Vaga (PDF)" e selecione o arquivo da vaga
- Digite uma pergunta no campo de texto, por exemplo: "Sou adequado para esta vaga?"
- Pressione Enter ou clique em Analisar
- Aguarde o agente processar — os cards aparecem conforme cada bloco é gerado
Na segunda versão da POC, o usuário pode interagir com os cards gerados pelo agente. Cada requisito na lista de análise tem um botão Detalhar. Ao clicar, o agente recebe a ação, processa o requisito específico e responde com um novo card de detalhamento inserido na timeline — sem recarregar a página ou repetir a análise completa.
Essa é a essência da UI agêntica bidirecional: a interface não apenas exibe o que o agente gerou, mas também devolve ao agente sinais sobre o que o usuário quer explorar, e o agente responde com novos blocos visuais contextualizados.
Usuário clica em "Detalhar" em um requisito
|
| A2UI emite um A2uiClientAction com name="detail_requirement"
| e context={ requirement, status }
v
Frontend — A2uiActionBridge recebe a ação
|
| AgentService monta [mensagem inicial, mensagem de ação JSON]
| e abre um novo stream para o backend (mesmo threadId)
v
Backend — agente detecta a2uiAction no último user message
|
| chama renderSurface("requirementDetail", { requisito, status, analise, sugestoes })
v
Frontend — novo TOOL_CALL_RESULT chega no stream
|
| A2uiRendererService processa as mensagens A2UI
| novo card de detalhamento aparece na timeline
v
Usuário vê análise detalhada do requisito clicado
O backend é stateless — cada run de ação re-envia a mensagem inicial junto com o envelope de ação, sem depender de memória de sessão no servidor.
Backend
- Novo template
requirementDetailcom análise, status e sugestões do requisito - Template
requisitosreescrito: botão Detalhar embutido em cada linha com contexto literal (sem data-binding), garantindo que o valor correto chegue ao agente independente do item clicado
Frontend
A2uiActionBridge: serviço RxJS que desacopla oactionHandlerda configuração do renderer doAgentService, evitando dependência circular no injetor Angular- Chip de ação na timeline: aparece entre a requisição e o card de resposta, indicando qual requisito está sendo detalhado
- Correção de especificidade CSS para os botões A2UI: o Angular adiciona seletores de atributo nos estilos de componente, elevando a especificidade deles. A solução usa
:rootcomo prefixo para ganhar no empate
agentic-ui/
backend/ — servidor Mastra com agente, tools e templates A2UI
frontend/ — aplicação Angular com renderer A2UI
CHANGELOG.md — histórico de versões
README.md — este arquivo
Cada subprojeto tem seu próprio README com detalhes de arquitetura e decisões de design.