Exercício – Usar o depurador interno do Node.js

Concluído

Para colocar em prática os conceitos de depuração que você acabou de ver, você criará um aplicativo Node.js curto para calcular o N.º número da sequência Fibonacci.

A sequência Fibonacci é um conjunto de números que começa com 0 e 1, em que cada número seguinte é a soma dos dois números anteriores. A sequência continua assim:

0, 1, 1, 2, 3, 5, 8, 13, 21...

Vamos criar um novo aplicativo Node.js para ilustrar o conceito.

Abrir projeto no contêiner de desenvolvimento

Este módulo de treinamento oferece um contêiner de desenvolvimento, em um navegador ou em seu computador local. Este contêiner fornece todo o ambiente necessário para que você possa usar este módulo de treinamento sem precisar instalar um IDE ou Node.js. Você não precisa saber nada sobre o contêiner para concluir este módulo de treinamento.

  1. Inicie o processo para criar um GitHub Codespace no branch main do repositório GitHub MicrosoftDocs/node-essentials.

  2. Na página Criar um codespace, revise as definições de configuração do codespace e, a seguir, selecione Criar codespace

    Screenshot of the confirmation screen before creating a new codespace.

  3. Aguarde até que o codespace seja iniciado. Esse processo de inicialização pode levar alguns minutos.

  4. Abra um novo terminal no codespace.

    Dica

    Você pode usar o menu principal para navegar até a opção de menu Terminal e, em seguida, selecionar a opção Novo Terminal.

    Screenshot of the codespaces menu option to open a new terminal.

  5. Valide se o .NET 7 está instalado em seu ambiente:

    node --version
    

    O contêiner de desenvolvimento usa uma versão do Node.js LTS. A versão exata pode ser diferente.

  6. Os exercícios restantes neste projeto ocorrem no contexto desse contêiner de desenvolvimento.

Preparar o ambiente

Antes de começar o exercício, primeiro precisamos preparar o código e o ambiente.

  1. Abra a subpasta ./nodejs-debug e crie um novo arquivo JavaScript chamado myfibonacci.js. O arquivo que já existe na pasta é uma solução para o exercício, com a correção necessária para o bug encontrado durante a depuração.

  2. Cole esse código no arquivo:

    function fibonacci(n) {
      let n1 = 0;
      let n2 = 1;
      let sum = 0;
    
      for (let i = 2; i < n; i++) {
        sum = n1 + n2;
        n1 = n2;
        n2 = sum;
      }
    
      return n === 0 ? n1 : n2;
    }
    
    const result = fibonacci(5);
    console.log(result);
    
  3. Salve o arquivo, CTRL + S.

  4. Clique com o botão direito do mouse na subpasta ./nodejs-debug, selecione Open in integrated terminal e execute o programa usando o seguinte comando:

    node fibonacci.js
    

O aplicativo deve exibir o resultado 3 (três) no console. Opa, parece que há um bug ali, pois esperávamos ver 5 (cinco) como resultado. Vamos ver o que está errado usando o depurador interno do Node.js.

Folha de dicas de comandos do depurador

O depurador interno Node.js vem com um conjunto de comandos que você pode usar para controlar a execução do programa. Aqui está uma planilha de dicas rápidas sobre os comandos mais comuns:

Comando Descrição
c continuar. Continua a execução até o ponto de interrupção seguinte ou até o fim do programa.
next Contornar. Esse comando é semelhante ao comando step, exceto que, se a próxima linha de código for uma chamada de função, ele executará a função sem entrar nela.
s Intervir. Esse comando é semelhante ao comando next, exceto que, se a próxima linha de código for uma chamada de função, vá para a primeira linha do código dessa função.
sb() adicionar um ponto de interrupção na linha atual.
exec <EXPR> avalie uma expressão dentro do contexto de execução atual. Esse comando é útil para ajudar você a obter informações sobre o estado atual. Por exemplo, você pode obter o valor de uma variável chamada i usando exec i.
Ctrl + D Pare o depurador.

Iniciar o depurador interno

Inicie novamente o programa, desta vez com o depurador interno habilitado. Insira este comando no terminal:

node inspect fibonacci.js

No terminal, você deverá ver o prompt do depurador sendo exibido. Agora, entre no código executando s + <Enter> até que o ponto de execução esteja localizado no início da função fibonacci, desta forma:

break in fibonacci.js:2
  1 function fibonacci(n) {
> 2   let n1 = 0;
  3   let n2 = 1;
  4   let sum = 0;
debug>

Nesse ponto, podemos verificar o valor do parâmetro n passado na função executando o seguinte comando:

exec n

Você deverá ver 5 (cinco) como o resultado no console. Continue a intervir no código executando o comando s até que o ponto de execução esteja dentro do início do loop. São necessárias cinco intervenções com o comando s para chegar a este ponto:

break in fibonacci.js:7
  5
  6   for (let i = 2; i < n; i++) {
> 7     sum = n1 + n2;
  8     n1 = n2;
  9     n2 = sum;
debug>

Observação

Talvez você tenha observado que são necessárias várias intervenções para percorrer a linha for(...) {} com os comandos de deputação. Isso ocorre porque há várias instruções nessa linha. Quando intervém, você passa para a instrução seguinte no código. Normalmente, há uma instrução por linha. Se não for esse o caso, você precisará de várias intervenções para passar para a próxima linha.

Localizar o bug com pontos de interrupção

Agora vamos adicionar um ponto de interrupção nesta linha para que possamos percorrer rapidamente as iterações do loop. Insira o seguinte comando no terminal:

sb()

Você deverá ver as mesmas linhas novamente no console, indicando que um ponto de interrupção foi definido nessa linha. Quando o ponto de execução atual for movido, você verá um asterisco * na linha em que você definiu o ponto de interrupção.

Avance para a próxima iteração do loop usando o comando c no terminal:

c

Podemos verificar o estado de iteração atual com o comando exec e ver o valor de várias variáveis usando uma matriz como o parâmetro de comando. Para ver os valores do iterador i e do sum total, usamos a sintaxe [i, sum]. Insira este comando no terminal:

exec [i, sum]

Você deverá ver o resultado [ 3, 1 ] no console.

O código ainda não atualizou o valor da variável sum para a iteração atual, que é 3 (três). O valor da variável sum ainda mostra o número de Fibonacci da iteração anterior. Este é o cálculo que estamos usando no código para obter o valor sum atual:

fibonacci(2) = fibonacci(0) + fibonacci(1)
             = 0 + 1
             = 1

Com base em nosso cálculo, parece que o programa foi executado corretamente até este ponto.

Continue para a próxima iteração de loop executando o comando c no terminal e verifique o estado novamente:

c
exec [i, sum]

Você deverá ver o resultado [ 4, 2 ] no console.

Agora, estamos no ponto logo antes do número de iteração de nosso interesse, que é 5 (cinco). Com cautela, vamos acompanhar passo a passo essa iteração usando o comando s. Tente chegar ao ponto de interrupção anterior, mas um passo por vez. Não ultrapasse o ponto de interrupção!

O que aconteceu?

Corrigir o bug

Depois de verificar a condição de loop i < n, a execução passou repentinamente para a linha que tem o comando return. Veja o que você deve ver no terminal:

break in fibonacci.js:12
 10   }
 11
>12   return n === 0 ? n1 : n2;
 13 }
 14

É isso, acabamos de encontrar nosso bug. Em vez de atualizar a soma da iteração 5 (cinco), o código saiu do loop. Por isso, recebemos o resultado da iteração anterior 3 (três) na execução inicial.

Precisamos corrigir a condição de loop no código fibonacci.js. No editor de código, altere o valor da instrução de teste de menor que < para menor ou igual a <=:

for (let i = 2; i <= n; i++) {
  sum = n1 + n2;
  n1 = n2;
  n2 = sum;
}

Salve suas alterações no editor de código e saia do depurador selecionando Ctrl+D.

Agora, execute o programa novamente no terminal:

node fibonacci.js

Você deverá ver o resultado esperado no console, que é 5 (cinco).

Use o depurador interno do Node.js para aprender os princípios básicos da depuração e para sessões de depuração rápidas. Pode ser trabalhoso inserir os comandos e ele pode ser muito limitado e difícil de usar com programas complexos.

Nas próximas seções, veremos como usar o depurador do Visual Studio Code em vez de fazer isso.