19 pontos por GN⁺ 2025-10-09 | 6 comentários | Compartilhar no WhatsApp
  • Recentemente, o Node.js vem evoluindo rapidamente ao incorporar ao runtime recursos que antes só eram possíveis com pacotes npm
  • Isso permite reduzir riscos de segurança na cadeia de suprimentos, melhorar a portabilidade do código, diminuir dependências e simplificar a manutenção, além de contribuir para garantir desempenho e estabilidade em ambientes de produção
  • Com a adição de APIs globais como fetch(), WebSocket e node:test, agora é possível desenvolver sem pacotes famosos como node-fetch, ws e mocha
  • A expansão dos recursos do sistema de arquivos trouxe opções em fs.glob(), fs.rm() e fs.mkdir() que substituem glob, rimraf e mkdirp
  • Nas APIs utilitárias e de criptografia, crypto.randomUUID(), util.styleText(), atob/btoa e outras já fazem parte do padrão, tornando desnecessários pacotes como uuid e chalk
  • Alguns recursos (node:sqlite, URLPattern, --env-file, execução de TypeScript etc.) ainda permanecem em fase experimental
  • O ponto importante é que, com a própria evolução do Node.js, já é possível desenvolver aplicações modernas apenas com o runtime padrão

Principais pacotes npm substituídos por recursos nativos do Node.js

  • Durante muito tempo, o Node.js dependeu de diversos pacotes npm para utilitários HTTP, helpers de sistema de arquivos e outras funções
  • Porém, nas versões recentes (v18~v22), a tendência de integrar esses recursos diretamente ao runtime vem se fortalecendo
  • Com isso, há uma redução na complexidade do gerenciamento de pacotes e na exposição a riscos de segurança

1. node-fetch → Global fetch()

  • Desde o Node.js 18, o mesmo fetch() do navegador é fornecido como função global
  • É possível fazer requisições HTTP sem node-fetch
  • Foi introduzido experimentalmente na v17.5.0 e estabilizado na v18.0.0
  • No entanto, em versões anteriores à 18, node-fetch ainda é necessário

2. ws → Global WebSocket

  • Desde o Node.js 21, a classe global WebSocket dá suporte a conexões WebSocket no lado do cliente
    • Adicionada experimentalmente na v21.0.0, segue em fase experimental até agora
  • Para implementação de WebSocket no lado do servidor, ainda é necessário usar o pacote ws ou bibliotecas relacionadas

3. Frameworks de teste → node:test

  • Desde o Node.js 18, há o runner de testes nativo node:test, que pode substituir mocha, jest e outros
    • Introduzido experimentalmente na v18.0.0 e estabilizado na v20.0.0
    • Suporta escrita e execução de testes unitários básicos
  • Se forem necessários snapshots, mocking e plugins mais completos, frameworks de terceiros ainda são úteis
    • Ele é suficiente para testes em nível de módulo, mas frameworks tradicionais ainda têm vantagens no desenvolvimento de aplicações full stack

4. sqlite3 / better-sqlite3node:sqlite

  • O Node.js está introduzindo o módulo experimental node:sqlite para acesso ao SQLite
    • Resolve problemas de compilação e erros em upgrades comuns em pacotes com bindings nativos
    • Suporta tarefas básicas como criar bancos de dados em memória e criar tabelas
  • Como ainda está em fase experimental, é recomendável usar pacotes da comunidade quando forem necessários ajustes avançados de desempenho ou recursos adicionais

5. chalk / kleurutil.styleText()

  • Desde o Node.js 20.12.0, é possível fazer estilização de texto no console com util.styleText()
    • Estabilizado na v22.17.0
    • Aplica estilos básicos como cor, negrito e sublinhado
  • Se forem necessários temas complexos, sintaxe encadeada e compatibilidade retroativa, ainda é possível continuar usando chalk e similares

6. strip-ansiutil.stripVTControlCharacters()

  • O Node.js fornece nativamente a função de remover códigos de escape ANSI
    • Permite remover com segurança caracteres de controle de logs
  • A maioria dos casos de uso já é coberta nativamente, tornando desnecessários pacotes de terceiros

7. globfs.glob()

  • Desde o Node.js 22, foi adicionado o recurso nativo fs.glob() para busca por padrões de arquivos
    • Adicionado na v22.0.0 e estabilizado na v22.17.0 LTS
    • Permite buscar arquivos com padrões glob como **/*.js
  • Se for necessária compatibilidade com versões antigas do Node.js, use o pacote glob

8. rimraffs.rm({ recursive: true })

  • A remoção recursiva de diretórios é suportada pela API nativa do Node.js
    • Implementada com as opções recursive e force de fs.rm()
    • Disponível desde aproximadamente a v12.10.0 e estabilizada em todas as versões LTS atuais
  • É possível remover diretórios com segurança sem o pacote rimraf

9. mkdirpfs.mkdir({ recursive: true })

  • A criação recursiva de diretórios é fornecida pela opção recursive de fs.mkdir()
    • Adicionada desde a v10.12.0 e estabilizada há bastante tempo
  • É possível criar diretórios aninhados sem pacote adicional

10. uuidcrypto.randomUUID()

  • Desde o Node.js 14.17.0, existe a função de geração de UUID crypto.randomUUID()
    • Incluída como um recurso estável do módulo de criptografia
  • É possível gerar IDs aleatórios seguros sem o pacote uuid

11. base64-js / atobatob, btoa

  • Desde o Node.js 20, as funções globais atob e btoa estão disponíveis
    • A mesma API de codificação/decodificação Base64 do navegador
    • Oferece uma opção adicional além do Buffer tradicional
  • É possível processar Base64 sem polyfill

12. url-patternURLPattern

  • Desde o Node.js 20, a API global URLPattern é oferecida experimentalmente
    • Dá suporte a route matching, extração de parâmetros de caminho e mais
    • Ainda está em fase experimental e precisa de estabilização
  • É possível tratar correspondência de padrões de URL com uma Web API padrão

13. dotenv → flag --env-file

  • Desde o Node.js 20.10.0, há suporte ao carregamento de variáveis de ambiente com a flag --env-file
    • Carrega diretamente o arquivo .env na execução
    • Ainda está em fase experimental
  • Para recursos avançados como expansão de variáveis e múltiplos arquivos env, o pacote dotenv ainda é necessário

14. event-target-shimEventTarget

  • Desde o Node.js 15.0.0, o Node.js fornece globalmente o sistema de eventos padrão da Web, EventTarget
    • Estabilizado na v15.4.0
    • Suporta o mesmo modelo de tratamento de eventos do navegador
  • Pode ser usado como alternativa ao EventEmitter

15. tsc → execução de TypeScript no Node.js

  • Desde o Node.js 21, é possível executar arquivos .ts diretamente com a flag --experimental-strip-types
    • Apenas remove tipos; não oferece verificação de tipos completa
    • Ainda está em fase experimental
  • Para builds de produção, checagem estática de tipos, geração de arquivos de declaração e verificação completa de tipos, tsc ainda é necessário

Conclusão

  • A direção da evolução do Node.js é reduzir a dependência de pacotes externos e elevar a completude da própria plataforma
  • Na versão LTS mais recente (v22), muitos pacotes npm já se tornaram desnecessários,
    o que representa uma grande melhoria em segurança, desempenho e manutenibilidade
  • Em ambientes operacionais corporativos, soluções como N|Solid estão sendo usadas para monitorar essas mudanças em tempo real
    • Análise do desempenho em cargas reais de recursos nativos (fetch, node:test, crypto.randomUUID() etc.)
    • O agente de IA N|Sentinel fornece monitoramento de uso e recomendações de otimização em nível de código

6 comentários

 
nemorize 2025-10-09

As APIs fornecidas pelo runtime estão aumentando cada vez mais..
Especialmente APIs de rede, URL, b64 e APIs de processamento de strings, entre outras...

Isso é totalmente... PH..

 
carnoxen 2025-10-09

Parece que o UUID v7 ainda é cedo demais.

 
click 2025-10-09

Acho que drivers de banco de dados precisam ser vistos por uma perspectiva diferente de recursos que deveriam entrar em outras bibliotecas padrão; tanto no Bun quanto aqui, qual seria o motivo para querer embutir um driver de SQLite no runtime?
Será que é porque o Python já traz isso embutido?

Em vez de embutir funcionalidades de SQLite, acho mais importante criar um padrão de interface para drivers de banco de dados.
Como a interface muda de driver para driver, não é esse o problema que torna difícil dar suporte a bancos heterogêneos sem usar ORM?

 
aer0700 2025-10-09

Acho que colocaram isso porque, para serviços pequenos, no nível de um blog pessoal, muitas vezes só o sqlite já é suficiente. É útil de ter.

 
tujuc 2025-10-09

Acho que colocaram o sqlite porque ele tem a interface mais simples e serve como uma boa referência para consulta.

E também não sei por que seria necessário criar esse padrão de interface para drivers de banco de dados que você mencionou. Tenho a vaga lembrança de já ter visto algo parecido em PHP.

Como ainda uso consultas RAW para queries complexas que o ORM não consegue resolver...
Pelo visto você usa vários tipos diferentes de banco de dados com frequência... que tal criar uma biblioteca? :)

 
click 2025-10-10

Em runtimes como Python, Java, C#, Go etc., é bem comum haver uma padronização da interface de drivers de banco de dados.
Mas no Node, até entre drivers voltados para o mesmo SQLite, a execução de statements muda entre execute() e exec(), então até trocar apenas o driver já exige certo nível de modificação.

Não é algo que acontece com frequência, mas quando é preciso trocar de banco também é inconveniente.
Se você estiver usando MySQL e passar a não gostar do que a Oracle faz, ou precisar muito de alguma extensão do PostgreSQL e decidir migrar para ele,
em casos com interface padrão como o JDBC basta validar o SQL, mas no ecossistema Node há o efeito colateral de ter que refazer toda a lógica de chamadas ao banco.

+Você me recomendou criar uma biblioteca, mas para isso ajuda muito existir um padrão de interface comum.
Na empresa usamos Java, e no framework interno precisamos dar suporte a MySQL, DB2, Oracle e MSSQL, então na manutenção dos adaptadores de cada banco eu já me beneficiei bastante do padrão JDBC.