JavaScript é frequentemente a maior causa de performance ruim em sites modernos. Um script de 500KB não é apenas 500KB para transferir - é 500KB para parsear, compilar e executar no browser do usuário. Em dispositivos móveis intermediários, isso pode levar 3-5 segundos de processamento.

Por que JavaScript é caro

Imagens pesadas atrasam o download. JavaScript pesado atrasa o download e o processamento. Um arquivo JS de 500KB:

  • Transfere 500KB (ou menos comprimido)
  • Parseia no browser
  • Compila para bytecode
  • Executa o código

Em um desktop moderno, isso é rápido. Em um Moto G4 ou smartphone de entrada popular no Brasil, pode levar 5x mais tempo.

Como identificar o problema

PageSpeed Insights:

  • “Reduce unused JavaScript” - lista scripts com grande quantidade de código não usado
  • “Minify JavaScript” - scripts sem minificação
  • “Remove render-blocking resources” - scripts bloqueando a renderização

Chrome DevTools - Coverage:

  1. F12 > menu ”…” > More tools > Coverage
  2. Clique em Record e recarregue a página
  3. Veja a porcentagem de código não usado (vermelho) em cada arquivo

Índices acima de 60-70% de código não usado indicam problema de bloat ou inclusão de bibliotecas completas quando se usa apenas parte delas.

defer e async: os atributos fundamentais

Por padrão, scripts <script> bloqueiam o parsing do HTML enquanto baixam e executam.

<!-- BLOQUEIA o HTML - nunca usar para scripts externos -->
<script src="heavy.js"></script>

<!-- NÃO bloqueia - baixa em paralelo, executa depois do HTML -->
<script src="analytics.js" defer></script>

<!-- NÃO bloqueia - baixa e executa assim que disponível, sem garantia de ordem -->
<script src="widget.js" async></script>

Quando usar defer: scripts que dependem do DOM ou de outros scripts (devem manter ordem de execução)

Quando usar async: scripts completamente independentes (analytics, chat, pixels) que não dependem do DOM nem de outros scripts

Code splitting: carregue apenas o que a página precisa

Se seu site tem 10 páginas e todas compartilham um bundle JS gigante, cada página baixa o código das outras 9. Code splitting resolve isso dividindo o bundle por rota ou componente.

Em frameworks modernos (React, Vue, Svelte, Astro):

// Em vez de importar tudo no inicio
import { GaleriaCompleta } from './galeria';

// Importe dinamicamente quando necessário
const GaleriaCompleta = await import('./galeria');

Em Astro (que já usa code splitting automaticamente por página), adicione client:visible para carregar componentes interativos somente quando entram na viewport:

<MeuComponente client:visible />

Tree shaking: elimine código não usado

Tree shaking é o processo de remover exports de módulos que não são importados em lugar nenhum.

Funciona com bundlers (Vite, Webpack, Rollup) e com módulos ES nativos. Não funciona com CommonJS (require).

// BOM para tree shaking (ES modules)
import { formatDate } from './utils'; // só importa o que usa

// RUIM para tree shaking
const utils = require('./utils'); // carrega tudo

Atenção com bibliotecas: lodash, moment.js e jQuery têm versões modernas mais leves. Se você usa apenas 2-3 funções do lodash, importe-as diretamente:

// BOM: carrega só a função necessária
import debounce from 'lodash/debounce';

// RUIM: carrega a biblioteca toda (80KB)
import _ from 'lodash';
const result = _.debounce(fn, 300);

Minificação e compressão

Todo arquivo JS deve ser minificado para produção - remove espaços, comentários e encurta nomes de variáveis.

Ferramentas de build (Vite, webpack) minificam automaticamente em build de produção. Verifique se sua build tem esse passo ativo.

Além da minificação, o servidor deve servir os arquivos com compressão:

  • Brotli: melhor compressão, suportado por 97% dos browsers
  • GZIP: fallback universal

Um arquivo JS de 300KB pode virar 60-80KB depois de Brotli. O Cloudflare ativa Brotli automaticamente no plano gratuito.

Auditar e remover scripts de terceiros

Scripts de terceiros são frequentemente ignorados nas auditorias de performance mas são dos maiores contribuidores para JS pesado:

  • Pixel do Facebook: 80-100KB
  • Google Tag Manager com 10+ tags: 200-400KB total
  • Hotjar: 100-150KB
  • Intercom/Zendesk Chat: 200-300KB

Para cada script de terceiros, pergunte:

  1. É realmente necessário nesta página?
  2. Pode ser carregado com delay de 3-5 segundos?
  3. Tem alternativa mais leve?

Use Google Tag Manager para centralizar e ter controle sobre quando cada script carrega.

Performance Web

JavaScript pesado está atrasando seu site?

Auditamos o JavaScript do seu site, identificamos bloat, scripts desnecessários e configuramos loading otimizado.

Otimizar JavaScript do meu site

FAQ

Meu site usa WordPress com vários plugins. Como saber quais scripts são pesados?

No Chrome DevTools > Network, filtre por “JS” e ordene por tamanho. Os maiores scripts aparecerão primeiro. Também use o PageSpeed Insights > “Reduce unused JavaScript” para ver quais scripts têm mais código não aproveitado.

Tree shaking funciona com plugins de WordPress?

Não diretamente. Plugins de WordPress geralmente carregam seus scripts como arquivos JS já compilados. Para otimizar, você pode usar a configuração de “Script Loading” de plugins como WP Rocket para adiar o carregamento de scripts específicos.

Qual a diferença entre minificação e compressão?

Minificação remove espaços e comentários do código fonte (processo irreversível, arquivo menor permanentemente). Compressão (GZIP/Brotli) comprime o arquivo na transmissão - o browser descomprime para usar. Os dois são complementares: minifique o arquivo, depois o servidor comprime na entrega.

Devo evitar jQuery no site?

jQuery é uma biblioteca de 30-87KB (dependendo da versão) que adiciona funcionalidades que browsers modernos já têm nativo. Para sites novos, evite jQuery e use JavaScript moderno. Para sites existentes com jQuery: não remova abruptamente se tiver plugins que dependem dele, mas evite adicionar mais dependências em jQuery.