搞定 NodeJS 开发调试
代码调试有时候是一种充满挑战的工作,如果有一个趁手的调试工具的话,往往可以做到事半功倍的效果。得益于这些年的快速发展,在 NodeJS 生态中已经有了多种调试工具可以使用。我们今年就来分享几个常用的调试工具。
在 NodeJS 的代码调试中,通常又两大类调试方法,一种是打印日志,另一种是直接调试代码。我们现在来分别说明。
日志
日志可以帮助我们记录在程序运行过程中的一些状态和错误信息。通过日志,我们可以快速的找到出问题的代码。比如借助于异常日志,我们可以快速的定位到具体的代码行。
debug 模块
debug 是很多 NodeJS 包和框架使用的日志工具。这个包的优点是可以通过环境变量的形式细粒度的控制打印哪些日志。
比如在下面的代码中,假设我们先发送了一些请求,然后又接受到了响应数据。
// index.js
const debugHttpIncoming = require('debug')('http:incoming')
const debugHttpOutgoing = require('debug')('http:outgoing')
let outgoingRequest = {
url: 'https://google.com'
}
// sending some request
debugHttpOutgoing('sending request to %s', outgoingRequest.url)
let incomingRequest = {
body: '{"status": "ok"}'
}
// serving some request
debugHttpOutgoing('got JSON body %s', incomingRequest.body)
当我们通过如下方式启动程序的时候:
DEBUG=http:incoming,http:outgoing node index.js
日志展示如下:

同时,debug 模块还支持 * 通配符,我们可以通过 DEBUG=http:* node index.js 获得上面相同的日志输出。
记录日志到文件
通常,我们需要将应用运行的日志做持久化处理,最简单的方式就是记录到文件。
pino 是一个高性能的日志模块,与 bunyan 类似,但是性能更好。
以下是几种日志模块的性能数据对比:
benchWinston*10000: 2226.117ms
benchBunyan*10000: 1355.229ms
benchDebug*10000: 445.291ms
benchLogLevel*10000: 322.181ms
benchBole*10000: 291.727ms
benchPino*10000: 269.109ms
benchPinoExtreme*10000: 102.239ms
pino 使用非常简单:
const pino = require('pino')()
pino.info('hello pino')
pino.info('the answer is %d', 42)
pino.error(new Error('an error'))
上面的代码,日志输出如下:
{"level":30,"time":1632626946507,"pid":77749,"hostname":"everfind-MacBook-Pro.local","msg":"hello pino"}
{"level":30,"time":1632626946508,"pid":77749,"hostname":"everfind-MacBook-Pro.local","msg":"the answer is 42"}
{"level":50,"time":1632626946508,"pid":77749,"hostname":"everfind-MacBook-Pro.local","stack":"Error: an error\n at Object.<anonymous> (/Users/everfind/workspace/ztest/test/pino.js:5:12)\n at Module._compile (internal/modules/cjs/loader.js:1072:14)\n at Object.Module._extensions..js (internal/modules/cjs/loader.js:1101:10)\n at Module.load (internal/modules/cjs/loader.js:937:32)\n at Function.Module._load (internal/modules/cjs/loader.js:778:12)\n at Function.executeUserEntryPoint [as runMain] (internal/modules/run_main.js:76:12)\n at internal/main/run_main_module.js:17:47","type":"Error","msg":"an error"}
调试
NodeJS 内置调试模块
NodeJS 提供了内置的调试模块。使用起来非常简单直接,缺点是没有 UI 页面,纯命令行操作。
$ node debug index.js
我们通过 debugger 语句来设置断点。
const express = require('express');
const app = express();
app.get('/', (req, res) => {
debugger;
res.send('ok');
});
app.listen(3000);
内置的调试模块支持如下命令:
- cont 或 c –- 继续执行
- next 或 n –- 往下一步
- step 或 s –- 进入函数
- out 或 o –- 退出函数
- repl –- 刷新上下文信息

V8 Inspector
我们还可以通过 V8 inspector,使用 Chrome 的 DevTools 来调试 NodeJS 代码。
$ node --inspect index.js
上面这条命令,通过 --inspect 参数告诉 NodeJS 启用 V8 Inspector。之后我们在 Chrome 中输入 chrome://inspect/,然后找到我们要调试的那个文件,就可以使用 Chrome DevTools 调试代码了。
有时候,我们需要在代码的入口处开始调试,则可以通过 --inspect-brk 来在起始地点开始调试。
$ node --inspect-brk index.js

VSCode
最后我们介绍如何在 VSCode 中调试代码,这也是最高频使用的。

通常我们可以直接通过菜单启动调试,就像上面的演示效果那样。
如果我们需要一些高级设置,VSCode 允许我们配置一个 .vscode/launch.json 文件,来告诉 VSCode 如何启动调试器。
默认的配置项如下:
{
"version": "0.2.0",
"configurations": [
{
"type": "node",
"request": "launch",
"name": "Launch Program",
"program": "${workspaceRoot}/index.js"
},
{
"type": "node",
"request": "attach",
"name": "Attach to Port",
"address": "localhost",
"port": 5858
}
]
}
关于每个配置项的作用和具体用法,可以在 VSCode 的文档中查询。
另外,如果我们在 VSCode 的内置命令行通过 node --inspect 启动程序的话,会自动激活 VSCode 的调试功能。
常见面试知识点、技术解决方案、教程,都可以扫码关注公众号“众里千寻”获取,或者来这里 https://everfind.github.io 。

搞定 NodeJS 开发调试的更多相关文章
- Facebook新框架React Native,一套搞定App开发[转]
Facebook新框架React Native,一套搞定App开发 本文来自微信公众号“给产品经理讲技术”(pm_teacher),欢迎关注. 做为一名产品经理,你是否遇到过这样的窘境,“帮我把字体调 ...
- nodejs开发调试时,使用supervisor
如果你有 PHP 开发经验,会习惯在修改 PHP 脚本后直接刷新浏览器以观察结果,而你在开发 Node.js 实现的 HTTP 应用时会发现,无论你修改了代码的哪一部份,都必须终止Node.js 再重 ...
- 五步搞定Android开发环境部署
引言 在windows安装Android的开发环境不简单也说不上算复杂,本文写给第一次想在自己Windows上建立Android开发环境投入 Android浪潮的朋友们,为了确保大家能顺利完成开发 ...
- 五步搞定Android开发环境部署——非常详细的Android开发环境搭建教程
在windows安装Android的开发环境不简单也说不上算复杂,本文写给第一次想在自己Windows上建立Android开发环境投入Android浪潮的朋友们,为了确保大家能顺利完成开发环境的搭 ...
- 一分钟搞定pychram远程调试和同步代码
首先说一下需求,否则很多人都不知道pycharm这个远程同步和调试到底是干嘛使的. 需求很简单,我想要在本地的windows机器上跑一个程序,但是程序运行会加载一些很占内存的树型数据结构,称其为tre ...
- [Modern OpenGL系列(一)]十步搞定OpenGL开发环境
本文已同步发表在CSDN:http://blog.csdn.net/wenxin2011/article/details/51292143 OpenGL官网:https://www.opengl.or ...
- 10分钟,AppCan帮你搞定跨平台开发APP问题!
跨平台开发APP时,开发者总会遇到一些问题,如打包失败等等,尤其对于iOS来说,由于它的限制性会导致一些状况发生(如证书上传问题等),小编总结了几个AppCan在线IOS打包失败常见的情况及排查技巧, ...
- 彻底搞定Android开发中软键盘的常见问题
软键盘显示的原理 软件盘的本质是什么?软键盘其实是一个Dialog. InputMethodService为我们的输入法创建了一个Dialog,并且将该Dialog的Window的某些参 ...
- ImageKnife组件,让小白也能轻松搞定图片开发
本期我们给大家带来的是开发者周黎生的分享,希望能给你的HarmonyOS开发之旅带来启发~ 图片是UI界面的重要元素之一, 图片加载速度及效果直接影响应用体验.ArkUI开发框架提供了丰富的图像处理能 ...
随机推荐
- ReentrantLock中的Condition(等待和唤醒)
Condition 类的 awiat 方法和 Object 类的 wait 方法等效 Condition 类的 signal 方法和 Object 类的 notify 方法等效 Condition 类 ...
- spring boot 2.0.0 + shiro + redis实现前后端分离的项目
简介 Apache Shiro是一个强大且易用的Java安全框架,执行身份验证.授权.密码学和会话管理.使用Shiro的易于理解的API,您可以快速.轻松地获得任何应用程序,从最小的移动应用程序到最大 ...
- 新书介绍 -- 《Redis核心原理与实践》
大家好,今天给大家介绍一下我的新书 -- <Redis核心原理与实践>. 后端开发的同学应该对Redis都不陌生,Redis由于性能极高.功能强大,已成为业界非常流行的内存数据库. < ...
- DeltaLake数据湖解决方案
Delta Lake 是DataBricks公司推出的一种数据湖解决方案,Delta为该方案的核心组件.围绕数据流走向(数据入湖从流入数据湖.数据组织管理.数据查询到流出数据湖)推出了一系列功能特性, ...
- Spark消费Kafka如何实现精准一次性消费?
1.定义 精确一次消费(Exactly-once) 是指消息一定会被处理且只会被处理一次.不多不少就一次处理. 如果达不到精确一次消费,可能会达到另外两种情况: 至少一次消费(at least onc ...
- Android WorkManager 定时任务
App有时可能需要定期运行某些工作.例如,可能要定期备份数据.上传信息到服务器,定期获取新的内容等等. 在app运行期间,我们使用Handler也可以完成定期的功能.在这里我们介绍WorkManage ...
- 跨平台APP推荐收藏
时间:2019-04-11 整理:pangYuaner 标题:十大跨平台优秀软件 地址:https://www.cnblogs.com/the-king-of-cnblogs/p/3154758.ht ...
- Java并发之AQS原理解读(三)
上一篇:Java并发之AQS原理解读(二) 前言 本文从源码角度分析AQS共享锁工作原理,并介绍下使用共享锁的子类如何工作的. 共享锁工作原理 共享锁与独占锁的不同之处在于,获取锁和释放锁成功后,都会 ...
- AbpVnext使用分布式IDistributedCache Redis缓存(自定义扩展方法)
AbpVnext使用分布式IDistributedCache缓存from Redis(带自定义扩展方法) 我的依赖包的主要版本以及Redis依赖如下 1:添加依赖 <PackageReferen ...
- 【曹工杂谈】Maven源码调试工程搭建
Maven源码调试工程搭建 思路 我们前面的文章<[曹工杂谈]Maven和Tomcat能有啥联系呢,都穿打补丁的衣服吗>分析了Maven大体的执行阶段,主要包括三个阶段: 启动类阶段,负责 ...