DEV Community

Cover image for How to Debug Nodejs, TypeScript Code in VSCode
Mark Abeto
Mark Abeto

Posted on • Edited on

How to Debug Nodejs, TypeScript Code in VSCode

Hi Guys Good Day!

It's been almost two years since I've been using TypeScript in my projects. One of the problems that I was having when starting using TypeScript in VSCode was how to debug it. Yea, TypeScript compiles to plain old JavaScript, we could debug the output JavaScript code but I don't want to do that and also the JavaScript output code is old but not that old it depends on your configuration. So, I wanna show you how to debug TypeScript code with VSCode.

And also I wanna mention, TypeScript is one of the most popular programming languages right now. Check out these links.

State of JS - JavaScript Flavors
Stack Overflow Survey - 2019
RedMonk - Most Programming Languages - January 2020

So, Let's start coding.

First, you need to have Node.js and VSCode installed on your computer and TypeScript. The links are down below.

Node.js
VSCode

To install TypeScript, run this command after installing Nodejs.

npm i -g typescript
Enter fullscreen mode Exit fullscreen mode

After installing TypeScript globally, from your desktop run these commands.

 md typescript-debug && cd typescript-debug && code .
Enter fullscreen mode Exit fullscreen mode

Basically what this means is that we are making a directory (md) that has a name of typescript-debug and changing our current directory (cd) Desktop to typescript-debug and opening the VSCode in the typescript-debug directory with the (code .) command.

Inside the directory, run these commands.

 npm init --y && tsc --init
Enter fullscreen mode Exit fullscreen mode

What these commands mean is that where initializing a Node project and using the default configuration(npm init --y) and we're gonna use TypeScript in this project (tsc --init).

And lastly, (bear with me) we're gonna install express and the type definitions for express module using these commands.

  npm i -P express && npm i -D @types/express
Enter fullscreen mode Exit fullscreen mode

npm i is alias for npm install. -P means that the package is a Dependency in our project and -D means that the package is a Development Dependency in our project.

Our package.json file.

{
  "name": "typescript-debug",
  "version": "1.0.0",
  "description": "",
  "main": "app.js",
  "dependencies": {
    "express": "^4.17.1"
  },
  "devDependencies": {},
  "scripts": {
    "start": "tsc"
  },
  "keywords": [],
  "author": "",
  "license": "ISC"
}
Enter fullscreen mode Exit fullscreen mode

Our tsconfig.json file.

{
  "compilerOptions": {
    "target": "es5",
    "lib": [
      "ES2015",
      "DOM"
    ],
    "sourceMap": true,
    "outDir": "./build",
    "rootDir": "./src",
    "strict": true,
    "esModuleInterop": true,
    "noEmitOnError": true,
    "watch": true
  },
  "exclude": [
    "node_modules"
  ]
}
Enter fullscreen mode Exit fullscreen mode

Ok, I'm gonna explain the most important parts in the tsconfig.json config.

exclude - The files or directories that we don't want to be compiled. In this example, we don't want the typescripts files inside the node_modules folder to be compiled to javascript.

target - The target version of our javascript output code.

lib - This is a list of the helper libraries that we're gonna use in our typescript code and also in the compilation.

sourceMap - A boolean indicating if we want a source map file for each typescript file.

outDir - The path or folder name to our javascript output code.

rootDir - The root directory for our typescript files.

strict - A boolean indicating if we want strict checking in our typescript code.

esModuleInterop - This option needs a lot more explanation. So, I'm gonna just give you an example. This is a boolean value.

If we set this to false. Our import statement would like this.

import * as express from 'express';
Enter fullscreen mode Exit fullscreen mode

If we set this to true. Our import statement would like this.

import express from 'express';
Enter fullscreen mode Exit fullscreen mode

For more details, read this.

noEmitOnError - A boolean indicating if an error occurred in type checking
will not emit or compile javascript code.

watch - A boolean indicating that we run the compiler in watch mode. If any files change in our rootDir, it will compile new files automatically.

Our launch.json file inside the .vscode folder.

{
    // Use IntelliSense to learn about possible attributes.
    // Hover to view descriptions of existing attributes.
    // For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387
    "version": "0.2.0",
    "configurations": [
        {
            "type": "node",
            "request": "launch",
            "name": "Launch Program",
            "program": "${workspaceFolder}/src/app.ts",
            "sourceMaps": true,
            "trace": "all",
            "outFiles": [
                "${workspaceFolder}/build/**/*.js"
            ]
        }
    ]
}
Enter fullscreen mode Exit fullscreen mode

And lastly, the app.ts file inside the src folder.

import express, { Request, Response } from 'express';

const app: express.Application = express();
const port: number = 3000;


app.get('/', (req: Request, res: Response) => {
    res.send('Hello World');
});


app.get('/:name', (req: Request, res: Response) => {
    res.send(`Hello ${req.param('name', 'Mark')}`);
});


app.listen(port, () => {
    console.log(`Server listening at port: ${port}`);
});
Enter fullscreen mode Exit fullscreen mode

Before starting the debug server, place breakpoints anywhere in the app.ts file and run the npm start command to start the TypeScript Compilation Server and then press F5 and open your browser and navigate to http://localhost:3000 or http://localhost:3000/anna. And, if it's working and it passes your breakpoints then great but if not then maybe there's something with your configurations, please follow the instructions above and retrace the things that you missed.

By the way, I haven't mentioned the most important thing that allows us to debug our TypeScript code. It's Source Maps. Most of our code (JS/CSS) in production are combined and minified so that we can dramatically reduce the size of our assets and also reduce the number of files in production to improve the load time performance of a website. But debugging in a minified code is hard, sorry "hard" is a soft word for this, it's impossible. This is where Source Maps comes into play. Basically, a Source map is a file that maps the minified/transformed source to the original source. This helps us, developers, a lot because we can debug that minified code with the original code. Source maps are awesome.

Thanks guys for reading this post.

Have a Nice Day ๐Ÿ˜ƒ!.

Top comments (8)

Collapse
 
jdforsythe profile image
Jeremy Forsythe

I find it much easier to use ts-node and you never have to run the compile task. You can just debug the ts files directly. Check out the launch configs in this repo: github.com/jdforsythe/bloch

Collapse
 
lesha profile image
lesha ๐ŸŸจโฌ›๏ธ

launch.json
MINER_PRIV_KEY

I hope these are temporary keys

Collapse
 
jdforsythe profile image
Jeremy Forsythe • Edited

It's not a real (or secure) network! It was an example for demonstrating blockchain concepts and TypeScript during a presentation I gave to a local college. You can see the slides in the repo, as well.

Collapse
 
ezzabuzaid profile image
ezzabuzaid

Thank you for sharing, it's very helpfull

Collapse
 
macmacky profile image
Mark Abeto

Thanks! I'm glad that it helped you.

Collapse
 
macmacky profile image
Mark Abeto

Thank you for this info man! Much appreciated.

Collapse
 
vadorequest profile image
Vadorequest

Configuring TypeScript is complicated. Making it work seamlessly with Jest, and various tools that need its source map is even more complicated.

We recently released a boilerplate for quick getting started with a production-grade project featuring the Next.js framework, hosted on Zeit platform at github.com/UnlyEd/next-right-now. It has full TS support.

It can be used as a boilerplate, but many of you may find it interesting as a learning resource as well. It's very well documented!

Collapse
 
vinicius5581 profile image
Vinicius Santana

This is great, but I would love to see your take on how to accomplish the same having typescript installed as a dev dependency instead of installing it globally. :)