一群嗤、debug模塊
參考
npm debug模塊
開始學(xué)nodejs —— 調(diào)試篇
debug模塊詳解
一般在nodejs需要進(jìn)行調(diào)試的時候堪伍,可以使用console.log()方法來將調(diào)試信息輸出到控制臺形耗,當(dāng)發(fā)布到生產(chǎn)環(huán)境的時候,需要將這些調(diào)試信息都注釋掉玻募,為了方便切換而不需要改動程序代碼次和,可以使用nodejs的debug模塊
首先安裝一下npm install debug
var debug = require('debug')('myapp:main');
debug('現(xiàn)在的時間是 %s' , new Date());
如果是開發(fā)環(huán)境,只需要設(shè)置環(huán)境變量set debug=myapp:*
就可以輸出調(diào)試信息拖云。如果需要關(guān)閉調(diào)試信息贷笛,則設(shè)置set debug=null
1.注意Windows下,CMD和PowerShell的區(qū)別:
但是宙项,PowerShell的DEBUG參數(shù)并沒有傳進(jìn)去乏苦。查看debug模塊的源碼,在node.js的load方法中console一下:
/**
* Load `namespaces`.
*
* @return {String} returns the previously persisted debug modes
* @api private
*/
function load() {
console.log("process.env.DEBUG:",process.env.DEBUG);
return process.env.DEBUG;
}
發(fā)現(xiàn)PowerShell這個參數(shù)尤筐,居然是undefined
2.避開了PowerShell的坑汇荐,用CMD還是不行洞就,查看源代碼中的debug.js發(fā)現(xiàn):
/**
* Returns true if the given mode name is enabled, false otherwise.
*
* @param {String} name
* @return {Boolean}
* @api public
*/
function enabled(name) {
if (name[name.length - 1] === '*') {
return true;
}
var i, len;
for (i = 0, len = exports.skips.length; i < len; i++) {
if (exports.skips[i].test(name)) {
return false;
}
}
for (i = 0, len = exports.names.length; i < len; i++) {
console.log("enabled name:",name,"exports.names[i]",exports.names[i]);
//enabled name: myapp:main exports.names[i] /^'myapp:main'$/
//if (exports.names[i].test(name)) {
if (exports.names[i].test('\''+name+'\'')) {
return true;
}
}
return false;
}
注意看,正則匹配那里沒有通過拢驾,原因是生成的正則兩側(cè)有單引號,但是傳進(jìn)來的name改基,也就是namespace沒有單引號繁疤,所以匹配不上去。我改成if (exports.names[i].test('\''+name+'\'')) {
就可以使用了秕狰。所以源碼有問題稠腊??鸣哀?再仔細(xì)看看自己的cmd命令架忌,原來是自己多打了單引號:E:\node\debugTools>set DEBUG='myapp:main' & node app.js
。改為E:\node\debugTools>set DEBUG=myapp:main & node app.js
即可我衬。
3.給幾個例子:
01.js
/**
* debug基礎(chǔ)例子
*/
var debug = require('debug')('app');
// 運(yùn)行 DEBUG=app node 01.js
// 輸出:app hello +0ms
debug('hello');
02.js
/**
* debug例子:命名空間
*/
var debug = require('debug');
var appDebug = debug('app');
var apiDebug = debug('api');
console.log("appDebug eanbled",appDebug.enabled);
console.log("apiDebug eanbled",apiDebug.enabled);
// 分別運(yùn)行下面幾行命令看下效果
//
// DEBUG=app node 02.js
// DEBUG=api node 02.js
// DEBUG=app,api node 02.js
// DEBUG=a* node 02.js
//
appDebug('hello');
apiDebug('hello');
03.js
/**
* debug例子:排查命名空間
*/
var debug = require('debug');
var listDebug = debug('app:list');
var profileDebug = debug('app:profile');
var loginDebug = debug('account:login');
// 分別運(yùn)行下面幾行命令看下效果
//
// DEBUG=* node 03.js
// DEBUG=*,-account* node 03.js
//
listDebug('hello');
profileDebug('hello');
loginDebug('hello');
04.js
/**
* debug:自定義格式化
*/
var createDebug = require('debug')
createDebug.formatters.h = function(v) {
return v.toUpperCase();
};
var debug = createDebug('foo');
// 運(yùn)行 DEBUG=foo node 04.js
// 輸出 foo My name is CHYINGP +0ms
debug('My name is %h', 'chying');
二叹放、在chrome中調(diào)試
參考 3分鐘干貨學(xué)會使用node-inspector調(diào)試NodeJS代碼
先安裝:npm install -g node-inspector
然后打開命令行,輸入node-inspector
,會提示visit http://127.0.0.1:8080/?port=5858 to start debug
然后打開另一個命令行挠羔,輸入node --debug-brk test.js
,再去chrome中打開http://127.0.0.1:8080/?port=5858
即可
三井仰、在vscode中調(diào)試
參考vscode 調(diào)試node.js
1.這里以express應(yīng)用為例,參考Node.js Express Helloworld破加,使用命令行npm start俱恶,然后訪問localhost:3000確認(rèn)可以正常訪問。
2.命令行中使用code .
范舀,使用vscode打開express應(yīng)用
注:在當(dāng)前項(xiàng)目下創(chuàng)建ExpressApp.bat合是,輸入“code .”即可,下次直接此文件直接使用VSCode打開Nodejs項(xiàng)目
@echo off
code.
選擇完成之后锭环,在項(xiàng)目的根目錄中會生成一個.vscode的目錄聪全,這個目錄中存放了各種各樣的VScode編輯器的配置。現(xiàn)在這個目錄中就包含了一個文件名為lanuch.json的配置文件辅辩,配置文件的內(nèi)容如下:
其中最重要的配置項(xiàng)就是“Program”字段荔烧,這個字段定義了整個應(yīng)用的入口,開啟調(diào)試器的時候會從這個入口啟動應(yīng)用汽久。我們發(fā)現(xiàn)當(dāng)前這個字段已經(jīng)有值了鹤竭,不要慌,那是因?yàn)閂Scode在初始化這個配置文件的時候景醇,會查看package.json中是否有包含了鍵名為start的scripts臀稚,如果有的話,就會把start配置的內(nèi)容作為“program”字段的值三痰。點(diǎn)擊開始調(diào)試按鈕(綠色三角形)吧寺,就可以開始調(diào)試了窜管。
四、supervisor / nodemon + Browsersync
如果你有 PHP 開發(fā)經(jīng)驗(yàn)稚机,會習(xí)慣在修改 PHP 腳本后直接刷新瀏覽器以觀察結(jié)果幕帆,而你在開發(fā) Node.js 實(shí)現(xiàn)的 HTTP 應(yīng)用時會發(fā)現(xiàn),無論你修改了代碼的哪一部份赖条,都必須終止Node.js 再重新運(yùn)行才會奏效失乾。這是因?yàn)?Node.js 只有在第一次引用到某部份時才會去解析腳本文件呻逆,以后都會直接訪問內(nèi)存峭判,避免重復(fù)載入,而 PHP 則總是重新讀取并解析腳本(如果沒有專門的優(yōu)化配置)彬祖。Node.js的這種設(shè)計(jì)雖然有利于提高性能仿贬,卻不利于開發(fā)調(diào)試纽竣,因?yàn)槲覀冊陂_發(fā)過程中總是希望修改后立即看到效果,而不是每次都要終止進(jìn)程并重啟茧泪。supervisor 或者nodemon 蜓氨,可以幫助你實(shí)現(xiàn)這個功能,它會監(jiān)視你對代碼的改動队伟,并自動重啟 Node.js语盈。
supervisor修改代碼時可以自動重啟服務(wù)器但不更新瀏覽器。Browsersync能讓瀏覽器實(shí)時缰泡、快速響應(yīng)您的文件更改(html刀荒、js、css棘钞、sass缠借、less等)并自動刷新頁面。
五宜猜、ts-node
參考使用ts-node和vsc來調(diào)試TypeScript代碼
我之前寫過一篇用vsc+gulp來自動編譯ts并重啟程序的文章泼返,不過后來發(fā)現(xiàn)這樣做的工作比較多而且有很多不足,比如
- 運(yùn)行或者調(diào)試需要等待編譯完成姨拥,項(xiàng)目大了之后編譯這一步還是需要一定的時間的
- 難以調(diào)試測試代碼绅喉,一般來說項(xiàng)目采用ts,測試代碼也應(yīng)該采用ts去編寫叫乌,而采用編譯+sourcemap的方式就很難調(diào)試測試代碼
可以看出這些不足都來自于一個根本原因柴罐,運(yùn)行之前需要編譯。后來我就發(fā)現(xiàn)了一個很強(qiáng)大的工具ts-node憨奸,來看下ts-node的簡介:
TypeScript execution environment and REPL for node.
簡單的說就是它提供了TypeScript的運(yùn)行環(huán)境革屠,讓我們免去了麻煩的編譯這一步驟。
# Locally in your project
npm install -D ts-node
npm install -D typescript
# Or globally (not recommended)
npm install -g ts-node
npm install -g typescript
官網(wǎng)提示還要本地安裝typescript,我沒裝似芝,果然報(bào)錯:
Error: Cannot find module 'typescript'
at Function.Module._resolveFilename (module.js:469:15)
at Function.Module._load (module.js:417:25)
at Module.require (module.js:497:17)
at require (internal/module.js:20:19)
at Object.register (E:\node\ts-node-starter\node_modules\ts-node\src\index.ts:227:26)
at Object.<anonymous> (E:\node\ts-node-starter\node_modules
\ts-node\register\index.js:1:16) at Module._compile (module.js:570:32)
at Object.Module._extensions..js (module.js:579:10) at Module.load (module.js:487:32)
at tryModuleLoad (module.js:446:12)
Waiting for the debugger to disconnect...
修改項(xiàng)目的launch.json文件那婉,添加一個新的啟動方式
{
"name": "Current TS File",
"type": "node",
"request": "launch",
"args": [
"${workspaceRoot}/src/index.ts" // 入口文件
],
"runtimeArgs": [
"--nolazy",
"-r",
"ts-node/register"
],
"sourceMaps": true,
"cwd": "${workspaceRoot}",
"protocol": "inspector",
"console": "integratedTerminal",
"internalConsoleOptions": "neverOpen"
}
這下可以愉快地調(diào)試Ts了。具體配置參見作者ts-debug-example党瓮,下載之后npm install一下就能運(yùn)行详炬。