Redux dominou uma década de React e hoje vive como legado na maioria dos projetos novos. Zustand, Jotai e signals reduzem o custo de re-render a níveis que a context API nunca alcançou. Benchmarks de render e o tipo de aplicação decidem entre os três modelos.
Redux: onde ainda compensa
Times grandes valorizam devtools maduros com time-travel, o ecossistema de middleware e os padrões que o framework impõe. createSlice e RTK Query encolheram o boilerplate e cobrem mutations e cache sem cerimônia extra. A disciplina continua obrigatória: subscription via selector mal escrito provoca tempestade de re-renders. A documentação do React sobre useSyncExternalStore explica como seletores instáveis transformam a store em gargalo de render.
Zustand: store único sem providers
Um store, hooks como seletores, zero providers e nenhum dispatch. Cada componente assina o pedaço de estado que usa, e funções de igualdade (shallow de zustand/shallow) controlam o re-render no nível do campo. O pacote pesa pouco mais de 1 kB minificado, e o middleware persist sincroniza com localStorage em duas linhas. A documentação oficial descreve o padrão de seleção por campo.
Jotai: derivações em cadeia
Jotai monta o estado de baixo para cima: átomos derivados calculam valores a partir de outros átomos, e átomos async suspendem com React Suspense nativo. Esse modelo resolve estados dependentes complexos, como wizards de formulário multi-etapa e filtros combinatórios em tempo real. Quando a derivação domina o domínio, Jotai economiza código e bugs. A documentação do Jotai lista os padrões de composição de átomos.
Signals: reatividade fora do ciclo de render
Signals tocam o nó exato do DOM e pulam o re-render de componente. Solid.js prova o modelo em produção, Preact expõe signals na API pública, e a proposta TC39 avança a padronização dentro do React. A interop com React ainda tem fricção: avalie signals por projeto, onde a stack permitir.
Benchmark: 10 mil linhas
Uma tabela de 10 mil linhas atualizando uma célula: estado em Context re-renderiza tudo, Zustand com seletores re-renderiza a linha, signals atualizam a célula. As diferenças chegam a ordens de magnitude no tempo de commit. Quanto maior a lista e mais frequente a escrita, maior o abismo entre os modelos.
Critério de escolha
- Estado de servidor domina? TanStack Query carrega o peso e o estado cliente se reduz a concerns de UI
- Caso geral? Zustand como default pragmático
- Derivações em cadeia dominam? Jotai
- Performance de render é contratual (dashboards em tempo real, editores)? Signals onde a stack permite
Migração incremental
A coexistência funciona: converta providers de Context em stores Zustand aos poucos, um domínio por PR. Mantenha Redux onde fluxos de devtools fazem parte do trabalho do time. Adote signals por ilha em páginas híbridas, começando pelos componentes de maior frequência de atualização.
Curtiu o conteúdo?
Construo produtos web e soluções com IA do jeito certo — arquitetura sólida, código sustentável e entrega real.
Vamos conversar