Agentes de VozURAAgentes de IATutorial

Substitua sua URA por um Agente de Voz

Digite 1 para vendas é uma tabela de roteamento lida em voz alta. Crie um agente de voz que atende, entende, resolve e passa para uma pessoa quando é o caso.

Escrito por: Victor VillalobosRevisado por: Jennifer Villalobos26 de julho de 202611 min de leitura
Ver como Markdown

Todo menu telefônico é o mesmo pedido de desculpas. Digite 1 para vendas. Digite 2 para suporte. Digite 3 para ouvir estas opções novamente.

É uma tabela de roteamento, lida em voz alta, na velocidade da fala. Quem liga já sabe o que quer. Só precisa esperar enquanto recitam o seu organograma e depois adivinhar em qual ramo alguém como ele se encaixa.

A alternativa não é um menu melhor. É nenhum menu: o telefone é atendido, a pessoa diz o que precisa, e do outro lado alguma coisa entende, resolve, e coloca um humano na linha quando um humano é realmente necessário.

Isso é um agente de voz, e é mais ou menos uma tarde de trabalho.

O que a central antiga custa de verdade

Não a assinatura da linha. Outras três coisas.

Chamadas abandonadas. Cada camada de menu perde gente. Desligam e tentam um concorrente, ou escolhem o ramo errado e caem com alguém que não pode ajudar, o que é pior porque agora duas pessoas perderam tempo.

Nenhum registro do que as pessoas queriam. Uma URA sabe que digitaram 2. Não sabe que estavam perguntando sobre o reembolso de um pedido de março. Essa intenção é a coisa mais valiosa da ligação e a sua central joga fora toda vez.

Ela não consegue fazer nada. Um menu roteia. Não consulta uma reserva, não cota um preço, não atualiza um endereço. Tudo vira repasse para uma pessoa, incluindo a metade das ligações que essa pessoa vai resolver lendo um campo numa tela.

Um agente de voz resolve as três pelo mesmo motivo: é uma conversa, então ouve a intenção, e tem tools, então consegue agir sobre ela.

O que você vai construir

O menu antigoUm agente de voz da Zavu
Digite 1 para vendasQuem liga diz o que quer
Uma árvore que você mantém num portalUm prompt no seu repo, com version control
Roteia e se desliga do assuntoConsulta e responde durante a ligação
Transfere às cegasTransfere quando o seu prompt manda, para o número que você definiu
Sabe que um dígito foi apertadoTranscrição completa, duração e custo por ligação

O agente não é um produto separado do que atende no WhatsApp. É o mesmo agente com um bloco voice: mesmo prompt, mesmo modelo, mesmas tools, mesma knowledge base.

Antes de começar

Três pré-requisitos, e um deles leva um dia.

  • Um sender com número de telefone. Esse número é para onde as pessoas ligam.
  • Voice Agents habilitado para o seu team. Está em beta e é ligado por team, então os endpoints de voz retornam 403 até alguém ativar. Escreva para hi@zavu.dev e peça.
  • Saldo positivo. As ligações são cobradas por minuto conectado. Ligações recebidas só são atendidas enquanto o seu saldo está acima de zero, que é um modo de falha que convém conhecer antes de acontecer numa segunda-feira.

Quem faz o quê

Você entra com a conta, o número e o critério sobre quando uma pessoa deve atender. Seu coding agent escreve e publica o resto.

VocêSeu coding agent
Cria a conta ZavuEncontra ou cria o sender
Roda zavu login e autorizaEscreve defineAgent com o bloco de voz
Pede para habilitarem Voice AgentsEscreve as tools que ele chama durante a ligação
Aprova a compra de um númeroDefine os secrets e deploya
Atende a primeira ligação de testeLê a transcrição e corrige o prompt

A única parte que você digita

bash
npx skills add zavudev/zavu-skills npx zavudev login

O primeiro comando instala as skills da Zavu no seu coding agent. Claude Code, Cursor, Copilot, Codex e uns 40 outros são suportados; o installer pergunta quais. Uma dessas skills é voice-agent, que é o que impede o seu agente de inventar campos de configuração que não existem.

login abre o browser, você escolhe o projeto, e a key fica em ~/.zavu/credentials.json. Daqui para frente você descreve.

Depois você descreve o agente

text
Construa um voice agent Zavu para a minha clínica no meu sender atual. Que atenda em português, informe os horários, busque uma consulta por número de telefone, remarque, e transfira para +14155551234 quando pedirem uma pessoa ou soarem irritados. Teto de doze minutos. Faça o deploy.

Você não precisa conhecer os comandos abaixo. Eles estão aqui para você reconhecer o que passa na tela, e para perceber se uma etapa foi pulada.

bash
npx zavudev whoami # qual projeto eu vou mexer npx zavudev senders list # o número para onde as pessoas ligam npx zavudev fn secrets set SENDER_ID "jn76vnxet8g5nq661by3v06y1581bmmn" npx zavudev deploy

Se preferir partir de algo testado, existe um catálogo de agentes de voz prontos:

bash
npx zavudev agents catalog
text
id name voice tools category fermi Fermi, Lead Qualification yes 5 sales curie Curie, Customer Support yes 5 support kepler Kepler, Video Call Booking yes 2 frontDesk hopper Hopper, Lead Capture and Booking yes 5 sales aria Aria, Multi-channel concierge yes 3 frontDesk atlas Atlas, Product Expert yes 0 support

npx zavudev agents pull curie --sender "$SENDER_ID" baixa um para o seu repo como TypeScript editável. É um ponto de partida que é seu, não uma caixa preta que você aluga.

Leia o que ele escreveu

ts
import { defineAgent, defineTool } from "@zavudev/functions" defineAgent({ senderId: process.env.SENDER_ID!, name: "Clínica Norte", provider: "zavu", model: "openai/gpt-4o-mini", channels: ["voice", "whatsapp"], voice: { enabled: true, model: "openai/gpt-4o", greeting: "Clínica Norte, bom dia. Como posso ajudar?", language: "pt-BR", interruptible: true, maxCallDurationMinutes: 12, maxIdleSeconds: 30, transferPhoneNumber: "+14155551234", voicemailAction: "hangup", }, prompt: "Você é a recepção da Clínica Norte. Responda em português, uma ou duas frases. Transfira para uma pessoa quando pedirem, ou quando estiverem irritados.", })

Cinco campos decidem se a ligação parece humana.

interruptible é barge-in. Quem liga pode cortar o agente no meio da frase e ele para para ouvir. Deixe ligado. Um agente que fala por cima das pessoas é exatamente o que todo mundo já odeia nas ligações automáticas.

maxIdleSeconds encerra a ligação depois de silêncio, para que um celular de cara para baixo numa mochila não te cobre doze minutos.

maxCallDurationMinutes é o freio duro. Existe porque uma conversa que deu errado costuma dar errado por muito tempo.

voicemailAction define o que acontece quando uma secretária eletrônica atende numa ligação de saída: hangup em silêncio, ou leave_message e falar. Deixar recado quando você queria falar com uma pessoa é como um agente útil vira um incômodo.

transferPhoneNumber é a saída de emergência, e merece a própria seção.

A transferência é o que julgam em você

Se você define transferPhoneNumber, o agente ganha uma tool de transferência. Ele também sempre ganha uma de desligar, então consegue encerrar sozinho uma ligação que já acabou.

Duas coisas para saber, e a segunda surpreende.

A transferência só existe se o sender também tiver um número para discar. Se você define o destino e esquece o número do sender, o agente fica sem com o que escalar e sem como avisar.

Uma transferência encaminha a ligação. Ela não explica nada para o humano. Seu colega atende um telefone tocando sem ideia de que quem ligou já passou noventa segundos se explicando. Se você quer que ele saiba, isso é você que constrói: a transcrição completa está no registro da ligação e no webhook call.completed, então dá para mandar um resumo para o Slack, WhatsApp ou o seu helpdesk no momento da transferência. Diga isso no prompt também, para o agente avisar o que vai acontecer em vez de ficar mudo.

Dê algo para ele fazer

Um menu roteia. Esta é a parte que faz um agente valer mais que um menu:

ts
defineTool({ name: "find_appointment", description: "Busca a próxima consulta de um paciente pelo número de telefone.", parameters: { type: "object", properties: { phone: { type: "string", description: "Número no formato E.164" } }, required: ["phone"], }, handler: async ({ phone }) => { const res = await fetch("https://api.clinica.example/consultas?phone=" + phone) if (!res.ok) return { found: false, reason: "lookup_failed" } return { found: true, ...(await res.json()) } }, })

Vale dizer com todas as letras: as tools rodam em voz, sim. No path de texto puro não rodam, o que confunde as pessoas na direção contrária. Um agente de voz consegue consultar coisas de verdade no meio da frase, e essa é toda a razão para apontar um deles para o seu número.

Teste o handler sozinho, antes de qualquer ligação:

bash
npx zavudev fn invoke --tool find_appointment --args '{"phone":"+14155551234"}'

Isso roda na sua máquina, contra código sem commit, em menos de um segundo.

Ouça antes de um cliente ouvir

Dois testes diferentes, que pegam falhas diferentes.

bash
npx zavudev agents test --sender "$SENDER_ID" --message "quero remarcar minha consulta de terça"

Isso exercita o cérebro: prompt, modelo, knowledge base. Nada é entregue, nada é cobrado, nada é registrado. Também imprime warnings sobre o que um dry run não consegue provar, e num agente de voz o mais útil é que esse path não chama tools mesmo que a ligação vá chamar.

Depois ligue para você mesmo:

bash
npx zavudev calls create --to "+55SEUPROPRIONUMERO"

Seu telefone toca e o agente fala com você. Nenhuma outra coisa vai te dizer que a saudação está três segundos longa demais, ou que a voz lê um número de telefone como um inteiro gigante. Preste atenção na interrupção: fale por cima de propósito e veja se ele para.

Depois leia a ligação:

bash
npx zavudev calls list --limit 5 npx zavudev calls get <callId>

list mostra direção, status, duração e por que cada ligação terminou. get devolve a transcrição turno a turno. Essa transcrição é o que a sua central nunca te deu, e é de onde sai a próxima versão do prompt.

Depois entregue o loop:

text
Leia a transcrição das minhas últimas três ligações. Todo mundo perguntou sobre estacionamento e o agente não sabia. Adicione isso na knowledge base, encurte a saudação, e faça o deploy de novo.

Ele também liga para fora

O mesmo agente coloca ligações:

bash
npx zavudev calls create --to "+5511999999999" --language pt-BR --max-minutes 5

Lembretes de consulta, janelas de entrega, um pagamento que falhou. --language aceita auto para seguir o idioma de quem atende. voicemailAction define o que acontece quando uma máquina atende, que em campanhas de saída é a maioria das vezes.

Saída também é onde um agente deixa de ser uma comodidade e vira uma coisa capaz de incomodar milhares de pessoas rápido. Lembretes que a pessoa pediu, sim. Ligações frias, não. Consentimento e horários permitidos são responsabilidade sua, e nem o modelo nem a API vão respeitar isso por você.

O que fica de cada ligação

Quatro eventos de webhook disparam: call.initiated, call.answered, call.completed, call.failed. Todos levam o id da ligação, direção, from, to, status, duração e por que terminou.

Os dois terminais ainda levam cost, em USD, depois que a ligação foi cobrada. Esse não é o número cru da operadora: é o que você foi realmente faturado, telefonia e pipeline de voz juntos, então dá para colocar um preço real ao lado de uma conversa real.

Como isso é cobrado na Zavu

Voz é por minuto conectado. O pipeline gerenciado custa $0.0625 por minuto mais telefonia, contados de quando atendem até desligarem. Os modelos padrão estão cobertos por essa tarifa; um modelo premium soma o próprio custo de tokens. Ao colocar a chamada se reserva uma estimativa curta, liquidada contra a duração real no fim.

O plano cobre tudo em volta. Free é $0, Hobby é $25 por mês, e daí escala. Cada plano inclui uma cota de números, três no Hobby, e o primeiro número dos Estados Unidos é grátis para cada team. Números extras custam cerca de um dólar por mês cada.

Construir é grátis. Skills, CLI, SDKs, deploy e cada redeploy. agents test não cobra. fn invoke roda local. O que você paga é uma ligação conectada.

O número para guardar: uma ligação de cinco minutos no pipeline gerenciado dá uns trinta centavos mais telefonia. Compare com o que uma pessoa custa nesses mesmos cinco minutos, e depois com o que custa uma chamada abandonada, que é a ordem de grandeza que importa.

As tarifas mudam. A página de preços é a que está atualizada.

Três regras que mantêm isso honesto

Nunca finja um sucesso. Uma tool que reporta uma consulta remarcada que nunca remarcou faz o agente dizer a uma pessoa real, em voz alta e com tom confiante, que a terça dela está resolvida. Devolva a falha. O agente vai dizer, e quem ligou pode fazer alguma coisa a respeito. Isso é pior em voz do que em qualquer outro lugar, porque ninguém relê uma ligação.

Avise que vai transferir. Silêncio seguido de toque parece que desligaram na sua cara. Uma frase, depois a transferência.

Um dry run não é uma ligação. agents test prova que o prompt faz sentido. Não prova que a saudação soa bem, que a voz pronuncia o nome da sua empresa, nem que o agente para quando é interrompido. Só uma ligação real prova isso, então faça a primeira para o seu próprio telefone.

Onde isso te deixa

O seu número agora atende, entende, consulta algo real e coloca uma pessoa na linha quando é o caso. O comportamento vive num arquivo em que você consegue dar diff, com uma transcrição por ligação e um custo ao lado.

O menu nunca foi o produto. Era o acordo que você aceitou porque software não conseguia sustentar uma conversa. Agora consegue.

Precisa de ajuda? Contate-nos ou junte-se à nossa comunidade Discord para suporte.

Follow us on social media

Pronto para começar?

Comece a construir gratuitamente ou agende uma chamada para discutir seu caso de uso específico.

Substitua sua URA por um Agente de Voz com IA | Zavu Blog