Skip to main content

10 分鐘內的 Npm 腳本教程!

使用 Node 進行開發時,必須使用 npm,腳本是 npm 的最強大和最常見的功能之一。

我將在本文中介紹如何使用 npm 腳本。

目錄

1. 什麼是 npm 腳本?

Npm 允許您使用文件中的scripts字段定義腳本命令package.json

{
...
"scripts": {
"build": "node build.js"
}
}

上面的代碼是package.json文件的一部分,scripts這裡的字段是一個對象。它的每個屬性都對應一個腳本。例如,與該build命令對應的腳本為node build.js

如果您npm run在命令行下使用該命令,腳本將被執行。

$ npm run build
# equivalent to execution
$ node build.js

在中定義的這些腳本package.json稱為 npm 腳本。有很多優點:

  • 與項目相關的腳本可以放在一個地方。
  • 用於不同項目的腳本命令可以使用相同的外部接口,只要它們具有相同的功能即可。用戶不需要知道如何測試您的項目,只需運行 npm run test 即可。
  • 您可以利用 npm 提供的許多輔助功能。

您可以使用npm run不帶任何參數的命令來查看當前項目的所有 npm 腳本命令。

$ npm run

2. 原則

npm 腳本的原理非常簡單。無論何時npm run執行,都會自動創建一個新的 shell,並且將在該 shell 中執行指定的腳本命令。因此,只要該命令可以由外殼程序(通常是 Bash)運行,它就可以用 npm 腳本編寫。

特殊的是,由創建的 shell npm runnode_modules/.bin當前目錄的子目錄添加到PATH變量中,並且該PATH變量將在執行後恢復。

這意味著可以直接通過腳本名稱來調用當前目錄的 node_modules / .bin 子目錄中的所有腳本,而無需添加路徑。例如,如果當前項目的依賴項中包含 Mocha,則只需mocha test直接編寫:

"test": "mocha test"

而不是像這樣寫:

"test": "./node_modules/.bin/mocha test"

由於對 npm 腳本的唯一要求是腳本可以在 shell 中執行,因此它們不一定是 Node 腳本,並且可以在其中編寫任何可執行文件。

npm 腳本的退出代碼也遵循 shell 腳本的規則。如果退出代碼不是0,則 npm 將假定腳本執行失敗。

3. 通配符

由於 npm 腳本是 Shell 腳本,因此可以使用 Shell 通配符。

"lint": "jshint *.js"
"lint": "jshint **/*.js"

在上面的代碼中,*表示任何文件名,**表示任何子目錄。

如果要將通配符傳遞給原始命令以防止被 Shell 逸出,則必須逸出星號。

"test": "tap test/\*.js"

4. 傳遞參數

使用--指示傳遞給 npm 腳本的參數。

"lint": "jshint **.js"

如果將參數傳遞給上述 npm run lint 命令,則必須編寫如下。

$ npm run lint --  --reporter checkstyle > checkstyle.xml

您也可以在中再次封裝命令package.json

"lint": "jshint **.js",
"lint:checkstyle": "npm run lint -- --reporter checkstyle > checkstyle.xml"

5. 執行順序

如果要在 npm 腳本中執行多個任務,則需要弄清執行順序。

如果是並行執行(並行並行執行),則可以使用&符號。

$ npm run script1.js & npm run script2.js

如果是順序執行(僅在成功執行前一個任務時才執行下一個任務),則可以使用該&&符號。

$ npm run script1.js && npm run script2.js

這兩個符號是 Bash 的功能。另外,您可以使用節點的任務管理模塊:script-runnernpm-run-allredrun

6. 默認值

通常,npm 腳本由用戶提供。但是,npm 為兩個腳本提供了默認值。換句話說,這兩個腳本無需定義即可直接使用。

"start": "node server.js",
"install": "node-gyp rebuild"

在上述代碼中,默認值npm run startnode server.js,提供有一個server.js在項目的根目錄腳本; 默認值npm run install就是node-gyp rebuild,只要有一個binding.gyp項目的根目錄下的文件。

7. 鉤子

npm 腳本有兩個鉤子:prepost。例如,build腳本命令的掛鉤是prebuildpostbuild

"prebuild": "echo I run before the build script",
"build": "cross-env NODE_ENV=production webpack",
"postbuild": "echo I run after the build script

當用戶執行時,它將按以下順序自動執行npm run build

npm run prebuild && npm run build && npm run postbuild

因此,可以在這兩個掛鉤中進行一些準備和清理。這是下面的例子。

"clean": "rimraf ./dist && mkdir dist",
"prebuild": "npm run clean",
"build": "cross-env NODE_ENV=production webpack"

Npm 默認提供以下鉤子:

  • 預發佈,後發佈
  • 預安裝,後安裝
  • preuninstall,postuninstall
  • 前版本,後版本
  • 前測,後測
  • 穿越,後停
  • 啟動前,記錄開始
  • 重啟前,重啟後

自定義腳本命令也可以與prepost掛鉤一起添加。例如,腳本命令myscript具有premyscriptpostmyscript鉤子。但是,double pres 和 posts 無效。例如,prepretestpostposttest是無效的。

npm_lifecycle_event由 npm 提供的變量返回當前運行的腳本的名稱,如pretesttestposttest,等。因此,您可以使用該變量為npm scripts同一腳本文件中的不同命令編寫代碼。讓我們看下面的例子。

const TARGET = process.env.npm_lifecycle_event;
if (TARGET === 'test') {
console.log('Running the test task!');
}
if (TARGET === 'pretest') {
console.log('Running the pretest task!');
}
if (TARGET === 'posttest') {
console.log('Running the posttest task!');
}

請注意,prepublish 掛鉤不僅將在 npm publish 命令之前運行,而且還將在 npm install(不帶任何參數)命令之前運行。但是,這種行為很容易使用戶感到困惑,因此 npm 4 引入了一個 prepare 行為類似於的新鉤子 prepublish。從 npm 5 開始,該 prepublish 鉤子只會在 npm publish 命令之前運行。

8. 縮寫形式

這是四個常用 npm 腳本的簡短版本。

  • npm start 是短的 npm run start
  • npm stop 是短的 npm run stop
  • npm test 是短的 npm run test
  • npm restart 是短的 npm run stop && npm run restart && npm run start

npm startnpm stopnpm restart都是很好的理解,而npm restart是實際執行三個腳本命令的化合物命令:stoprestartstart。並且執行順序如下。

  • 重新啟動
  • 調動
  • 郵件停止
  • 重新開始
  • 預啟動
  • 開始
  • 郵件開始
  • 重啟後

9. 變量

npm 腳本具有非常強大的功能,可讓您使用 npm 的內部變量。

首先,npm 腳本可以獲取package.json帶有npm_package_前綴的字段。例如,package.json下面是一個。

{
"name": "foo",
"version": "1.2.5",
"scripts": {
"view": "node view.js"
}
}

然後,該變量npm_package_name返回foo,並且該變量npm_package_version返回1.2.5

// view.js
console.log(process.env.npm_package_name); // foo
console.log(process.env.npm_package_version); // 1.2.5

在上面的代碼中,我們package.json通過環境變量process.env對象獲取的字段值。如果是Bash腳本,則可以使用$npm_package_name和獲得兩個值$npm_package_version

npm_package_前綴也支持嵌套的package.json領域。

"repository": {
"type": "git",
"url": "xxx"
},
scripts: {
"view": "echo $npm_package_repository_type"
}

在上面的代碼中,您可以使用獲取字段的type屬性。repositorynpm_package_repository_type

這是另一個例子。

"scripts": {
"install": "foo.js"
}

在上面的代碼中,npm_package_scripts_install變量的值等於foo.js

npm config get xxx也可以通過npm_config_前綴獲取 npm 的配置變量(命令返回的值)。例如,您可以使用獲取當前模塊的release標籤npm_config_tag

"view": "echo $npm_config_tag",

請注意,環境變量可以覆蓋中的 config 對象 package.json。

{
"name": "foo",
"config": { "port": "8080" },
"scripts": { "start": "node server.js" }
}

在上面的代碼中,npm_package_config_port 變量返回 8080。並且可以通過以下方法覆蓋此值。

$ npm config set foo:port 80

env 命令可以列出所有環境變量。

"env": "env"

10. 常見腳本示例

// delete the directory
"clean": "rimraf dist/*",
// build an HTTP service locally
"serve": "http-server -p 9090 dist/",
// open the browser
"open:dev": "opener http://localhost:9090",
// real-time refresh
"livereload": "live-reload --port 9091 dist/",
// build an HTML file
"build:html": "jade index.jade > dist/index.html",
// Re-execute the build as long as the CSS file has changed.
"watch:css": "watch 'npm run build:css' assets/styles/",
// Re-execute the build as long as the HTML file has changed
"watch:html": "watch 'npm run build:html' assets/html",
// Deploy to Amazon S3.
"deploy:prod": "s3-cli sync ./dist/ s3://example-com/prod-site/",
// build favicon
"build:favicon": "node scripts/favicon.js",

11.使用 nrm 管理 npm 鏡像

nrm(npm registry manager)是 npm 的鏡像源管理工具,有時候國外資源太慢,使用這個就可以快速地在 npm 源間切換。

在命令行執行以下命令,全局安裝nrm

npm install -g nrm

執行命令nrm ls查看可選的源。

10分鐘內的Npm腳本教程!

其中,帶*的是當前使用的源,上面的輸出表明當前源是 taobao 源。

如果要切換到 cnpm 源或者其他鏡像,您可以使用nrm use 源名稱進行切換:

nrm use cnpm

你可以增加定製的源,特別適用於添加企業內部的私有源,執行命令nrm add <registry> <url>,其中 reigstry 為源名,url 為源的路徑。

nrm add registry http://registry.npm.frp.trmap.cn/

刪除,執行以下命令:

nrm del <registry> url

你還可以通過 nrm test 測試相應源的響應時間,從而決定使用哪種鏡像!

nrm test taobao

如果您感覺文章對您有幫助,請幫忙點個贊 👍 吧!謝謝!

查看原文點擊 👉這裡

本文使用 mdnice 排版

相關文章

精講 JavaScript 的”switch”語句

現代 JavaScript 教程—邏輯運算符

基於 vue3.0.1beta,搭建仿京東的電商 H5 項目!

從基礎到進階(一),0 ~ 100 道 JavaScript 題目,測試你有多瞭解 JavaScript,刷新你的知識!🚀