Corrigir Erro: 'listen EADDRINUSE: address already in use' no Node.js
  O temido erro EADDRINUSE surge quando você menos espera. Você está pronto para iniciar seu servidor Node.js, mas em vez de uma aplicação em execução, você recebe: Error: listen EADDRINUSE: address already in use :::3000. Este erro EADDRINUSE do Node.js significa que outro processo já está usando a porta que você está tentando vincular. Veja como identificar e corrigir este conflito de porta no Node.js rapidamente.
Pontos-Chave
- O erro EADDRINUSE ocorre quando uma porta já está ocupada por outro processo
 - Use 
lsofno macOS/Linux ounetstatno Windows para identificar o processo bloqueador - Encerre o processo usando seu PID ou implemente manipuladores de desligamento gracioso
 - Previna conflitos futuros com seleção dinâmica de porta e tratamento adequado de sinais
 
O Que Causa o Erro EADDRINUSE?
O erro listen EADDRINUSE ocorre quando sua aplicação Node.js tenta vincular-se a uma porta que já está ocupada. Os culpados comuns incluem:
- Uma instância anterior do seu servidor ainda em execução
 - Outra aplicação usando a mesma porta
 - Processos zumbi de aplicações Node.js que travaram
 - Ferramentas de hot-reload como nodemon falhando na limpeza
 - Terminais integrados de IDEs mantendo processos ativos
 
Como Descobrir Qual Processo Está Usando a Porta
Antes de poder liberar a porta ocupada, você precisa identificar o que está usando-a. Os comandos diferem por sistema operacional.
macOS e Linux
Use lsof para encontrar o processo:
lsof -i :3000
Isso retorna detalhes do processo incluindo o PID (ID do Processo):
COMMAND   PID    USER   FD   TYPE             DEVICE SIZE/OFF NODE NAME
node     12345   you   11u  IPv6 0xac745b2749fd2be3      0t0  TCP *:3000 (LISTEN)
Windows
Use netstat para identificar o processo:
netstat -ano | findstr :3000
A saída mostra o PID na última coluna:
TCP    0.0.0.0:3000    0.0.0.0:0    LISTENING    12345
Como Encerrar o Processo e Liberar a Porta
Uma vez que você tenha o PID, pode terminar o processo para liberar a porta.
Soluções para macOS e Linux
Comando rápido em uma linha:
lsof -ti:3000 | xargs kill -9
Abordagem manual:
kill -15 12345  # Desligamento gracioso (preferível)
kill -9 12345   # Forçar encerramento se -15 não funcionar
Alternativa usando fuser:
sudo fuser -k 3000/tcp
Soluções para Windows
Prompt de Comando:
taskkill /PID 12345 /F
PowerShell:
Stop-Process -Id 12345 -Force
Método GUI: Abra o Gerenciador de Tarefas (Ctrl+Shift+Esc), encontre o processo Node.js e finalize-o.
Discover how at OpenReplay.com.
Prevenindo Conflitos de Porta Futuros
Implemente Desligamento Gracioso
Adicione manipuladores de limpeza adequados ao seu servidor Node.js para prevenir erros de porta:
const server = app.listen(PORT, () => {
  console.log(`Server running on port ${PORT}`);
});
// Handle termination signals
process.on('SIGTERM', () => {
  server.close(() => {
    console.log('Server closed gracefully');
    process.exit(0);
  });
});
process.on('SIGINT', () => {
  server.close(() => {
    console.log('Server closed gracefully');
    process.exit(0);
  });
});
Use Seleção Dinâmica de Porta
Evite codificar portas fixas. Use variáveis de ambiente ou encontre uma porta disponível automaticamente:
const PORT = process.env.PORT || 3000;
// Or check port availability before binding
const net = require('net');
function getAvailablePort(startPort) {
  return new Promise((resolve) => {
    const server = net.createServer();
    server.listen(startPort, () => {
      const port = server.address().port;
      server.close(() => resolve(port));
    });
    server.on('error', () => {
      getAvailablePort(startPort + 1).then(resolve);
    });
  });
}
Trate o Erro Programaticamente
Capture o erro e responda adequadamente:
server.on('error', (err) => {
  if (err.code === 'EADDRINUSE') {
    console.error(`Port ${PORT} is already in use`);
    // Try another port or exit gracefully
    process.exit(1);
  }
});
Cenários Comuns e Correções Rápidas
Nodemon Não Liberando Portas
Se estiver usando nodemon, certifique-se de pará-lo com Ctrl+C, não Ctrl+Z. Este último suspende o processo sem liberar a porta.
Conflitos de Container Docker
Verifique containers em execução:
docker ps
docker stop <container_id>
Problemas com Terminal do VS Code
Feche todos os terminais integrados antes de reiniciar seu servidor. Às vezes o VS Code mantém processos ativos em segundo plano.
Múltiplas Instâncias de Servidor no Código
Certifique-se de não estar chamando app.listen() múltiplas vezes no seu código. Este erro comum dispara o erro address already in use imediatamente.
Conclusão
O erro EADDRINUSE do Node.js é frustrante mas facilmente corrigível. Encontre o processo usando sua porta com lsof ou netstat, encerre-o e implemente manipuladores de desligamento adequados para prevenir ocorrências futuras. Lembre-se: desligamentos graciosos com manipuladores de sinal e seleção dinâmica de porta vão poupar você de lidar repetidamente com este erro de porta do servidor Node.js.
Perguntas Frequentes
Sim, você pode implementar mudança automática de porta capturando o erro EADDRINUSE e tentando a próxima porta disponível. Use uma função recursiva ou loop para testar portas sequencialmente até encontrar uma aberta, ou use bibliotecas como portfinder que lidam com isso automaticamente.
Fechar uma janela de terminal nem sempre termina processos em execução. Processos em segundo plano, especialmente aqueles iniciados com nohup ou como serviços, continuam executando. Sempre use comandos de terminação adequados como Ctrl+C ou explicitamente encerre o processo usando seu PID para garantir que a porta seja liberada.
Usar kill -9 força terminação imediata sem permitir limpeza, o que pode causar perda ou corrupção de dados. Sempre tente kill -15 primeiro para desligamento gracioso. Reserve kill -9 para processos que não respondem. Implemente manipuladores de sinal adequados no seu código para garantir desligamentos limpos.
Gain Debugging Superpowers
Unleash the power of session replay to reproduce bugs, track slowdowns and uncover frustrations in your app. Get complete visibility into your frontend with OpenReplay — the most advanced open-source session replay tool for developers. Check our GitHub repo and join the thousands of developers in our community.