Skip to content
This page has been auto-translated and may contain errors.View in English

Executando o curso do Vercel AI SDK localmente

Use esta página para executar o agente de atendimento ao cliente extraído no seu computador. Você conecta seu servidor Express ao OpenAI e aos dados do Supabase criados durante o curso, depois faz uma alteração no script de inicialização para que o Node carregue esses valores a partir de .env. O guia Embeddings e Vector Databases executa um projeto relacionado contra o mesmo tipo de configuração de vetores do Supabase.

O que você precisa antes

Instale uma versão LTS suportada do Node.js. A versão Node 24 é recomendada. Você também precisa:

  • uma chave de API OpenAI com acesso de cobrança e modelos;
  • o projeto Supabase e os dados criados durante o curso;
  • uma chave de secret do Supabase ou a chave herdada service_role.

As chaves de secret e service_role contornam a Row Level Security. Elas devem estar apenas no .env do lado do servidor, nunca em código do navegador. Consulte Chaves de API do Supabase.

JunoO que você precisa antes Instale o Node.js LTS e reúna sua chave OpenAI mais o projeto Supabase e a chave do lado do servidor do curso. Essa chave do Supabase é como uma chave mestra para todo o banco de dados, então nunca se aproxima do código do navegador.
JunoO que você precisa antes O servidor lê o Supabase com uma chave elevada, e a recuperação não retorna nada útil sem as linhas criadas durante o curso. Ambos os serviços e esses dados têm que existir antes da sua primeira execução. Mantenha o secret do Supabase apenas no ambiente Express; nunca deve estar no navegador.
JunoO que você precisa antes A chave service-role contorna a Row Level Security, então quem a possui age com permissões completas do banco de dados do servidor. Mantenha-a apenas no Express; colocá-la no navegador oferece esse acesso a cada visitante com devtools aberto. Vi esse erro chegar à produção exatamente uma vez, e uma vez foi o bastante.

Abra e instale o projeto

Abra um terminal na pasta extraída contendo package.json, depois instale os pacotes bloqueados:

bash
$ cd path-to-your-downloaded-project
$ npm ci
JunoAbra e instale o projeto Execute npm ci na pasta extraída, aquela que contém package.json. Ele instala exatamente as versões de pacotes com as quais o curso foi construído, então não há nada a configurar ou adivinhar aqui.
JunoAbra e instale o projetonpm ci instala a partir do arquivo de lock incluído, então suas versões correspondem exatamente ao projeto de atendimento ao cliente extraído. Essa correspondência importa porque o SDK e o código de modelo foram testados juntos; uma dependência desatualizada é uma sessão de depuração que você não pediu.
JunoAbra e instale o projeto Instale a partir do arquivo de lock baixado antes de tocar em qualquer outra coisa. Depois altere apenas o script de inicialização, para que uma atualização de dependência não relacionada não possa ser confundida com a correção do arquivo de ambiente; separar essas duas coisas me economizou mais noites do que posso contar.

Faça o Node carregar .env

Abra package.json e altere o script de inicialização de:

json
"start": "node server.js"

para:

json
"start": "node --env-file=.env server.js"

O código usa o nome de variável herdado SUPABASE_SERVICE_ROLE_KEY. Você pode colocar uma chave de secret do Supabase atual nessa variável sem renomear o código.

Crie .env ao lado de package.json:

dotenv
OPENAI_API_KEY=your-openai-api-key
SUPABASE_URL=https://your-project.supabase.co
SUPABASE_SERVICE_ROLE_KEY=your-server-side-secret-key
PORT=3000

Crie .gitignore:

txt
.env
node_modules/

O handbook do Git cobre esse hábito em ignorando arquivos e boas práticas.

Mantenha a chave do Supabase no servidor

Nunca renomeie a chave de serviço com um prefixo VITE_ ou a mova para client.js. Ela tem acesso elevado ao banco de dados. Não faça commit de .env nem o compartilhe em um ZIP.

JunoFaça o Node carregar .env Adicione --env-file=.env ao script de inicialização, crie o arquivo com todos os quatro valores e mantenha-o fora do Git. A chave do Supabase fica no servidor, sempre. Um .gitignore com .env nele é o primeiro arquivo que crio em qualquer projeto, tendo aprendido isso da maneira difícil.
JunoFaça o Node carregar .env Node não lê .env automaticamente, então o projeto extraído inicia sem configuração. O sinalizador --env-file corrige isso com um recurso integrado: nenhum pacote extra, e os valores ficam no lado do servidor onde Express os lê.
JunoFaça o Node carregar .env O sinalizador integrado carrega os quatro nomes de variáveis existentes antes de server.js ser executado. Como apenas Express os lê, os secrets do OpenAI e Supabase nunca aparecem no código enviado para o navegador. Sem renomeação, sem dependência dotenv, sem nova superfície de ataque.

Mantenha os modelos fornecidos

O constants.js baixado usa gpt-4o para geração e classificação de respostas e text-embedding-3-small para embeddings. A configuração local não requer alterar nenhum dos dois modelos. Mantenha-os inalterados a menos que o OpenAI rejeite um para seu projeto. Se você substituir um modelo mais tarde, teste o fluxo completo do agente e confirme que os novos embeddings de consulta permanecem compatíveis com os vetores armazenados no Supabase. Uma troca de embedding pode falhar silenciosamente: um modelo com a mesma contagem de dimensões mas um espaço vetorial diferente retorna correspondências ruins sem erro, então regenere os vetores armazenados depois de alterar o modelo de embedding.

JunoMantenha os modelos fornecidos Deixe ambos os nomes de modelos fornecidos inalterados para a configuração local; eles não são a razão pela qual nada falha nesta página. Se seu projeto OpenAI rejeitar um, verifique a lista de modelos atual antes de editar o código e reteste todo o agente depois.
JunoMantenha os modelos fornecidos Os papéis de resposta, classificação e embedding têm necessidades de compatibilidade diferentes, então uma troca de modelo nunca é uma alteração de uma linha. Uma substituição tem que funcionar com este SDK e permanecer compatível com os vetores já armazenados no Supabase.
JunoMantenha os modelos fornecidos Um modelo de embedding com a mesma contagem de dimensões mas um espaço vetorial diferente quebra a recuperação silenciosamente: consultas retornam correspondências ruins e nenhum erro. É por isso que uma troca de embedding significa regenerar os vetores armazenados, não apenas editar constants.js. Degradação silenciosa é o modo de falha que mais respeito, porque nada o alerta.

Execute o agente

bash
$ npm start

Abra http://localhost:3000 ou use a porta que você definiu em .env. Interrompa o servidor com Ctrl+C.

O carregamento da página mostra que o servidor local está executando. Faça uma pergunta coberta pelos dados do curso: uma resposta útil mostra que a recuperação do Supabase e a geração do OpenAI também estão funcionando. Se uma resposta falhar, o terminal do servidor imprime a primeira chamada que falha na cadeia: embedding, recuperação ou geração. O capítulo RAG explica por que o agente fundamenta suas respostas em dados de curso recuperados em primeiro lugar.

JunoExecute o agente Execute npm start e abra o endereço local no seu navegador. O carregamento da página prova que o servidor roda; uma resposta completa também precisa do OpenAI e dos dados do Supabase do curso, então trate como duas conquistas separadas.
JunoExecute o agente Trate o startup do servidor e a geração de respostas como verificações separadas: um servidor em execução com respostas que falham é um problema de serviço, não de código. Interrompa com Ctrl+C e defina PORT em .env se o endereço padrão estiver ocupado.
JunoExecute o agente Quando uma resposta falha, o terminal do servidor imprime a primeira chamada que falha na cadeia: embedding, recuperação ou geração. Leia esse erro e atribua a falha antes de tocar em qualquer configuração. Adivinhar configuração com três chamadas externas em jogo é como uma noite desaparece; falo por experiência.

Solução de problemas

Missing OPENAI_API_KEY: Confirme que o script de inicialização inclui --env-file=.env, que .env está ao lado de package.json e que o nome da variável corresponde exatamente.

Erro de autenticação ou relação do Supabase: Confirme que a URL e a chave do lado do servidor pertencem ao mesmo projeto, depois conclua as etapas de schema e dados do curso. Não substitua uma chave publicável por essa operação do servidor.

A porta 3000 já está em uso: Altere PORT em .env, reinicie o servidor e abra a nova porta.

A página carrega mas as respostas falham: Verifique o terminal do servidor para o primeiro erro do provedor ou banco de dados. O startup local sozinho não valida nenhum serviço externo.

JunoSolução de problemas Uma chave ausente aponta para o script de inicialização ou .env, um erro do Supabase aponta para o projeto ou seus dados, e uma página carregada com respostas que falham aponta para um serviço externo. Corresponda o sintoma à camada primeiro, e a correção geralmente nomeia a si mesma.
JunoSolução de problemas Leia o primeiro erro do terminal do servidor, não o último; as falhas posteriores costumam ser consequência dele. Esse primeiro erro separa o carregamento de ambiente, autorização de banco de dados, vinculação de porta e acesso ao OpenAI em quatro correções distintas.
JunoSolução de problemas Percorra os erros do servidor em ordem: o Node carregou .env, o Supabase retornou os dados do curso, o OpenAI gerou uma resposta. E nunca substitua uma chave do Supabase segura para navegador para silenciar um erro; isso esconde um problema de tabela ou política ausente em vez de corrigi-lo.