1. Resultado
A API Inspector do Node é uma solução nativa para medir o uso de CPU, permitindo realizar profiling de CPU e capturar dados detalhados de execução que ajudam a identificar onde os recursos estão sendo mais demandados, sem a necessidade de instalar e configurar ferramentas. Neste artigo, vamos explorar como configurar e utilizar a API Inspector para capturar e interpretar dados de CPU em sua aplicação Node.js, permitindo que você descubra gargalos nas suas aplicações Node.
2. Situação
Em ambientes de produção, gargalos de CPU podem impactar negativamente a experiência do usuário e o consumo de recursos, tornando essencial o monitoramento do uso de CPU. Mas como entender quais partes do código estão consumindo mais CPU em uma aplicação Node?
3. Impacto
Identificação de funções críticas com alto uso de CPU.
Possibilidade de otimização do código para reduzir tempos de resposta.
Melhoria significativa na experiência do usuário e eficiência operacional.
4. Resolução
A API Inspector é uma interface nativa no Node que permite acessar o protocolo de inspeção V8, o mesmo utilizado pelo Chrome DevTools e para debugar aplicações Node. Esse protocolo oferece uma série de métodos para inspecionar e analisar o desempenho de aplicações Node, incluindo o profiling de CPU, de heap, ou debug. Com essa API, é possível capturar dados detalhados sobre a execução do código ou armazená-los para análise posterior.
A API Inspector funciona criando uma Session, através da qual podemos iniciar o profiling, controlando o acesso aos dados do tempo de execução da aplicação. Esse método permite identificar gargalos e otimizar o uso de CPU em trechos específicos do código, monitorando o custo computacional de funções.
4.1. Exemplo prático
Para esse exemplo você precisa ter configurado o Node e o Google Chrome (iremos usá-lo para visualizar os dados).
Vamos começar com uma API simples em express com duas funções que são acessadas através da rota “/crypto”, as funções “delay” e “encrypt” são funções que utilizam a CPU massivamente, porém de formas diferentes. A função “delay” testa números até 10 milhões e separa os números primos, já a função “encrypt” gera uma chave hash através de 1 milhão de iterações. Provavelmente você já percebeu um problema grave nessa aplicação, não se preocupe iremos resolvê-lo no final desse artigo, por enquanto vamos concentrar nosso foco em capturar dados de uso de CPU.
Você também pode acessar o projeto completo no repositório.
4.2. Configurando e Utilizando a API Inspector para Medir o Uso de CPU
Primeiro vamos iniciar uma sessão com o Node Inspector
const { Session } = require(‘node:inspector/promises’);
Agora podemos interagir com a API do V8 Inspector através do comando:
await session.post(v8_method)
A lista completa dos métodos pode ser acessada aqui.
Vamos ativar e iniciar o profiling da aplicação com esses comandos
await session.post(‘Profiler.enable’);
await session.post(‘Profiler.start’);
Executamos o código que desejamos monitorar e por fim finalizamos o profiling e salvamos o resultado em um arquivo assim:
const { profile } = await session.post(‘Profiler.stop’);
fs.writeFileSync(‘./profileSync.cpuprofile’, JSON.stringify(profile));
4.3. Interpretando os resultados de CPU com o DevTools do Chrome
Vamos iniciar a aplicação e executar uma requisição para a rota /crypto, você vai notar que a requisição leva um tempo considerável, em média 5 segundos. Após a execução o arquivo “profileSync.cpuprofile” será criado na raiz do projeto, abra o Google Chrome e abra o DevTools (uma das formas é clicar com o botão direito em Inspecionar), na aba Performance basta arrastar o arquivo gerado para dentro dela.
Imagem 1 – Visualização do CPU profiler via Chrome DevTools
Na visão “Call tree” (porção inferior) podemos ver o tempo e uso do CPU de cada uma das funções. Ambas estão críticas:
encrypt: 2,5 segundos (53,2%)
delay: 2,2 segundos (46,7%)
Agora que medimos descobrimos onde é o gargalo da nossa aplicação, o trabalho de melhoria de performance não para aqui, agora precisamos analisar as duas funções e descobrir se há espaço para otimiza-las, se houver fazemos e medimos novamente para validar se a otimização de fato funcionou.
4.4. Resolvendo o problema e interpretando os novos resultados
O objetivo deste artigo é mostrar como medir o uso de CPU em aplicações Node, por isso não entrarei em detalhes sobre a otimização aplicada, porém no arquivo index_async.js as otimizações foram implementadas. Execute os testes com esse arquivo, ele irá gerar um novo arquivo de profiling que iremos examinar.
Imagem 2 – Visualização do CPU profiler via Chrome DevTools após correção
Após a correção o tempo total de execução caiu para quase a metade e ambas as funções foram executadas. O tempo de idle corresponde ao tempo de espera para terminar a requisição, isso significa que houve um tempo de espera (idle) de 117 ms.
Podemos fazer pequenos ajustes no código para executar apenas a função encrypt e teremos um arquivo de profiling semelhante a esse:
Imagem 3 – Visualização do CPU profiler via Chrome DevTools apenas para a função encrypt
Todo tempo de execução da aplicação foi computado como idle, isto significa que a função encrypt levou todo esse tempo para executar, a razão pela qual vemos como idle é porque o V8 Inspector captura apenas o processo executado na main thread por isso vemos que a main thread esperou o tempo total em idle até a função encrypt ser resolvida.
5. Conclusão
Medir e entender o uso de CPU é essencial para otimizar o desempenho de aplicações Node.js, especialmente em cenários de produção onde a eficiência de recursos é fundamental. Neste artigo, vimos como utilizar a API Inspector do Node para realizar o profiling de CPU e capturar dados detalhados sobre o consumo de recursos em tempo de execução. Analisar esses dados permite identificar funções e operações que demandam alto uso de CPU, possibilitando otimizações focadas e melhorias de desempenho.
Existem outras ferramentas e abordagens para analisar com mais detalhes aplicações Node, como por exemplo instrumentar a aplicação com dados de Log, Tracing e Metrics, possibilitando a coleta de dados em tempo real. Porém esse é um assunto para um próximo artigo.
Quer continuar aprimorando suas habilidades em Node? Siga o blog da EximiaCo para mais conteúdos sobre melhores práticas em desenvolvimento Node.
The post Medindo o Uso de CPU em Aplicações Node.js com a API Inspector appeared first on Insights – EximiaCo.