Os chatbots de IA genéricos enganam-se com toda a confiança sobre o seu produto. Faça-lhes uma pergunta sobre a sua própria documentação e ou alucinam ou pedem desculpa. A solução é o RAG — Retrieval-Augmented Generation —, em que o modelo responde a partir do seu conteúdo e não dos dados com que foi treinado. Eis como criei um chatbot RAG sobre conteúdo do WordPress, do princípio ao fim.
Este é o complemento prático do meu artigo sobre o uso do WordPress como backend de RAG. Esse artigo cobre a arquitetura de armazenamento e indexação — a base de conhecimento, a divisão em blocos (chunking), os embeddings e a base de dados vetorial Qdrant. Aqui concentro-me na outra metade: o ciclo que vai da recuperação à resposta e transforma esse índice num chatbot a funcionar.
O que vamos construir
O chatbot tem uma única tarefa: receber a pergunta de um utilizador, encontrar os excertos mais relevantes do seu conteúdo no WordPress e deixar o LLM responder usando apenas esses excertos — com uma ligação para o artigo de origem. São quatro peças:
- A base de conhecimento — os seus artigos e páginas do WordPress, expostos pela REST API.
- O índice — blocos desse conteúdo convertidos em embeddings e guardados numa base de dados vetorial (eu uso o Qdrant).
- O ciclo de recuperação — gerar o embedding da pergunta, pesquisar no índice, obter os melhores resultados.
- O passo da resposta — entregar esses resultados ao LLM como contexto e transmitir a resposta em streaming.
As partes 1 e 2 estão cobertas no artigo sobre o backend. Este guia constrói as partes 3 e 4.
Passo 1: obter o conteúdo do WordPress
Tudo começa na REST API. O WordPress já serve o seu conteúdo publicado em JSON — sem precisar de nenhum plugin:
// Fetch published posts to index
const res = await fetch(
'https://cms.example.com/wp-json/wp/v2/posts?per_page=100&_fields=id,link,title,content,modified'
)
const posts = await res.json()O campo modified é importante — é com ele que mais tarde se mantém o índice atualizado. Remova o HTML de content.rendered até ficar com texto limpo antes de o dividir em blocos.
Passo 2: dividir em blocos e gerar embeddings
Divida cada artigo em excertos sobrepostos de algumas centenas de tokens, gere o embedding de cada um e guarde o vetor com os respetivos metadados (ID do artigo, título, URL, data de modificação). Este é o passo de indexação descrito em detalhe no artigo sobre o backend, por isso não o vou repetir — o resultado que interessa é uma coleção no Qdrant em que cada vetor sabe de que artigo do WordPress veio.
Passo 3: o ciclo de recuperação
Este é o coração do chatbot. Quando chega uma pergunta, gere o embedding com o mesmo modelo que usou para o conteúdo e peça ao Qdrant os blocos mais próximos:
async function retrieve(question, k = 5) {
// 1. Embed the question with the same embedding model as the content
const { data } = await embed(question)
const vector = data[0].embedding
// 2. Find the k closest chunks in Qdrant
const hits = await qdrant.search('wp_knowledge', {
vector,
limit: k,
with_payload: true,
})
// 3. Return the text plus where it came from
return hits.map(h => ({
text: h.payload.text,
title: h.payload.title,
url: h.payload.url,
score: h.score,
}))
}Há duas coisas que decidem a qualidade da recuperação: usar o mesmo modelo de embeddings dos dois lados e manter o k pequeno (3–5). Meter vinte blocos no contexto piora as respostas, não as melhora.
Passo 4: montar o prompt e responder
Agora junte os excertos recuperados num prompt ancorado no contexto. É na instrução de sistema que se travam as alucinações — diga ao modelo para responder apenas a partir do contexto e para admitir quando não consegue:
function buildMessages(question, chunks) {
const context = chunks
.map((c, i) => `[${i + 1}] ${c.title}\n${c.text}\nSource: ${c.url}`)
.join('\n\n')
return [
{
role: 'system',
content:
'You answer using ONLY the context below. ' +
'If the answer is not there, say you do not know. ' +
'Cite sources as [1], [2] and list their URLs.',
},
{ role: 'user', content: `Context:\n${context}\n\nQuestion: ${question}` },
]
}Passe essas mensagens ao seu LLM (eu transmito a resposta em streaming para que o chat pareça ao vivo) e depois apresente os URLs citados como ligações para os artigos originais do WordPress. É este passo das citações que torna o bot digno de confiança — cada afirmação fica a um clique da sua fonte.
Passo 5: ligar a interface de chat
O frontend é a parte fácil. Exponha o ciclo acima como um único endpoint de API (POST /api/chat) que recebe uma pergunta e devolve a resposta em streaming. Depois coloque um widget de chat onde quiser — um componente React no site, uma página do WordPress ou um painel de administração interno. O mesmo endpoint pode servir um assistente público de documentação e uma ferramenta privada de suporte; só muda o conteúdo de origem.
Passo 6: mantê-lo honesto e atualizado
Há duas regras que mantêm um chatbot RAG útil em produção:
- Citar sempre e permitir sempre o «não sei». Um bot que inventa respostas é pior do que não ter bot. Ancorar as respostas no conteúdo e citar as fontes é o objetivo de tudo isto.
- Reindexar a cada edição. Ligue-se aos eventos de gravação e publicação do WordPress para que os artigos alterados voltem a passar automaticamente pelos embeddings. Associe isso ao campo de data
modifiede o índice nunca se afasta do que está publicado.
A stack e o custo
WordPress (conteúdo) + um modelo de embeddings + Qdrant (vetores) + qualquer LLM (respostas) + uma API fina que une tudo. O Qdrant é open source e pode ser alojado por conta própria, o WordPress já o tem a funcionar, e o único custo medido são os tokens de embeddings e de geração de respostas — cêntimos numa base de conhecimento normal. Sem mensalidade por utilizador de um chatbot SaaS.
Armadilhas em que caí
- Blocos demasiado grandes. Artigos inteiros num único vetor recuperam-se mal. Ganham os excertos mais pequenos e sobrepostos.
- Modelos de embeddings diferentes. Indexe com um modelo, consulte com outro, e as pontuações de semelhança deixam de ter significado.
- Sem mecanismo de atualização. Um índice estático fica desatualizado sem ninguém dar por isso, e o bot começa a citar conteúdo apagado.
- Recuperação em excesso. Mais contexto não é melhor — dilui o sinal e aumenta o custo.
Conclusão
Um chatbot RAG no WordPress é sobretudo canalização que já existe: a REST API para o conteúdo, uma base de dados vetorial para a recuperação e um LLM para a resposta final. Acerte na divisão em blocos e nas citações e fica com um assistente que responde a partir da sua base de conhecimento real — e não da imaginação de um modelo. Comece pela arquitetura do backend e depois construa por cima o ciclo descrito acima.
Perguntas frequentes
Como se cria um chatbot RAG com conteúdo do WordPress?
Exponha os seus artigos através da REST API do WordPress, divida-os em blocos sobrepostos e guarde os embeddings desses blocos numa base de dados vetorial como o Qdrant. Depois, no momento da conversa, gere o embedding da pergunta do utilizador, recupere os blocos mais próximos e passe-os a um LLM como contexto. O modelo responde a partir do seu conteúdo e cita os artigos de origem.
É preciso um plugin para fazer um chatbot RAG no WordPress?
Não. A REST API nativa do WordPress já serve o seu conteúdo em JSON, e é só disso que o pipeline de recuperação precisa. Pode acrescentar um pequeno plugin ou mu-plugin para desencadear a reindexação ao gravar, mas o chatbot em si vive num serviço externo (uma API em Node, um Worker ou semelhante), não dentro do WordPress.
Que LLM deve usar um chatbot RAG no WordPress?
Qualquer LLM com capacidade de conversação serve, porque o RAG é independente do modelo — é o contexto recuperado que faz o trabalho pesado. Escolha com base no custo, na latência e nos requisitos de tratamento de dados. Mais importante do que o modelo é ancorar o prompt nos blocos recuperados e obrigá-lo a citar as fontes.
Como é que o chatbot se mantém sincronizado com as edições no WordPress?
Ligue-se aos eventos de gravação, publicação e eliminação do WordPress, para que qualquer artigo alterado volte a passar pelos embeddings e seja atualizado (ou removido) na base de dados vetorial. Associar a sincronização à data de modificação do artigo garante que o chatbot responde a partir da versão atual do seu conteúdo.
Como impedir que um chatbot RAG alucine?
Instrua o modelo a responder apenas a partir do contexto recuperado, a dizer «não sei» quando a resposta não está lá e a citar cada fonte. Em conjunto com uma boa recuperação (o mesmo modelo de embeddings dos dois lados, um top-k pequeno), ancorar as respostas e citar as fontes mantém-nas presas ao seu conteúdo real.
É barato manter um chatbot RAG no WordPress?
Sim. Reutiliza o WordPress para o conteúdo e uma base de dados vetorial open source em alojamento próprio, como o Qdrant, para a recuperação, pelo que o único custo medido são os tokens de embeddings e de geração de respostas — normalmente cêntimos numa base de conhecimento normal, sem subscrição por utilizador de um chatbot SaaS.



