瞭解可執行的NPM包

NPMNode.js的包管理工具,隨着Node.js的出現,以及前端開發開始使用gulpwebpackrollup以及其餘各類優秀的編譯打包工具(大多數採用Node.js來實現),你們都開始接觸到一些Node.js,發現了使用NPM來管理一些第三方模塊會很方便。
你們搬磚的模式也是從以前的去插件官網下載XXX.min.js改成了npm install XXX,而後在項目中require或者import前端

固然,NPM上邊不只僅存在一些用來打包、引用的第三方模塊,還有不少優秀的工具(包括部分打包工具),他們與上邊提到的模塊的區別在於,使用npm install XXX之後,是能夠直接運行的。vue

常見的那些包

能夠回想一下,webpack官網中是否有過這樣的字樣:node

```> npm install webpack -g

> webpackreact

<blockquote>固然,如今是不推薦使用全局安裝模式的,具體緣由會在下邊提到</blockquote>
<p>以及非全局的安裝使用步驟:</p>
```&gt; npm install webpack

而後編輯你的package.json文件:webpack

{
  "scripts": {
+    "webpack": "webpack"
  }
}
```

再使用就能夠調用了:git

```> npm run webpack ```
以上非全局的方案是比較推薦的作法

不過還能夠順帶一提的是在更新的一個新的工具,叫作,_並不打算細說它,但它確實是一個很方便的小工具,在官網中也提到了簡單的使用方法_ github

就像上邊所提到的修改,添加而後再執行的方式,能夠很簡單的使用來完成相同的效果,沒必要再去修改額外的文件。_(固然,能夠作更多的事情,在這裏先認爲它是的簡寫就行了)_ web

包括其餘經常使用的一些,像、、這些工具,都會直接提供一個命令讓你能夠進行操做。面試

本身造一個簡易的工具

最近面試的時候,有同窗的回答讓人啼笑皆非: vue-cli

Q:大家前端開發完成後是怎樣打包的呢?
A:。

[黑人問號臉.png]。通過再三確認後,該同窗表示並無研究過具體是什麼,只知道執行完這個命令之後就能夠了。
我本覺得這僅僅是網上的一個段子,但沒想到真的被我碰到了。_也不知道是好事兒仍是壞事兒。。_

從我我的的角度考慮,仍是建議瞭解下你所使用的工具。_至少看下里邊究竟寫的是什麼咯 :)_
P.S. 中不只僅能夠執行模塊,普通的命令都是支持的

建立工程

首先的第一步,就是你須要有一個文件夾來存放你的包,由於是一個簡單的示例,因此不會真實的進行上傳,會使用來代替 + 。

隨便建立一個文件夾便可,文件夾的名字也並不會產生太大的影響。
而後須要建立一個文件,能夠經過來快速的生成,我我的更喜歡添加標識來跳過一些非必填的字段。

```> mkdir test-util > cd test-util > npm init -y ```

建立執行文件

由於咱們這個模塊就是用來執行使用的,因此有沒有入口文件其實是沒有必要的,咱們僅僅須要建立對應的執行文件便可,須要注意的一點是:__與普通的文件區別在於頭部必定要寫上__


註冊執行命令

而後就是修改來告訴咱們的執行文件在哪:

{
+  "bin": "./index.js"
}
```

在只有一個,且要註冊的命令與中的字段相同時,則能夠寫成上邊那種形式,若是要註冊多個可執行命令,那麼就能夠寫成一個結構的參數:



  
  
  
  
調用時就是 command1 | command2

模擬執行

接下來咱們去找另外一個文件夾模擬安裝模塊,再執行就能夠了,再執行對應的命令之後你應該會看到上邊的輸出了:

```> cd .. && mkdir fake-repo && cd fake-repo > npm ln ../test-util

> test-util # global
first util
> npx test-util # local
first util


由於繞過了的安裝步驟,必定要記得來讓知道咱們的包註冊了

這時候咱們修改腳本文件,在腳本中添加當前執行目錄的輸出

#!/usr/bin/env node

   
   
   
   
  • console.log('first util')
  • console.log(process.execPath) // 返回JS文件上層文件夾的完整路徑

{
"script": {
"start": "nodemon ./server.js"
}
}



   
   
   
   
這樣的命令是徹底有效的,webpack 會使用 ts 的解釋器去執行對應的配置文件

由於不只僅支持這一種解釋器,有不少種,相似也是支持的。
因此確定不可以將各類語言的解釋器依賴都放到自身的依賴模塊中去,而是會根據傳入的文件後綴名來動態的判斷應該添加哪些解釋器,這些在的源碼中很容易找到:

  1. 獲取配置文件後綴
  2. 獲取對應的解釋器並引入模塊註冊

根據動態獲取解釋器的模塊interpret來看,類型的文件會引入這些模塊:,可是在的依賴中你是找不到這些的。

在源碼中也能夠看到,在執行以前動態的引入了這些解釋器模塊。

這裏也能夠稍微提一下中引入全局模塊的一些事兒,咱們都知道,經過安裝的模塊,均可以經過來直接引用,若是一些第三方模塊須要引入某些其餘的模塊,那麼這個模塊也須要存在於它所處目錄下的文件夾中才可以正確的引入。

首先有一點你們應該都知道的,目前版本的,不會再有黑洞那樣深的了,而是會將依賴平鋪放在文件夾下。好比說你引入的模塊,的內部引用了模塊,那麼你也能夠直接引用模塊,由於和都存在於下。

仍是拿咱們剛纔作的那個小工具來實驗,咱們在中添加的依賴,而後在中添加的依賴,並在中上述的兩個模塊。

你會發現,運行正確,而卻直接報錯了,提示不存在。

咱們能夠經過的一個命令來解釋這個緣由:

```> npm root <current>/node_modules > npm root -g <global>/node_modules ```

這樣輸出兩個路徑應該就能看的比較明白了,模塊是沒有問題的,由於都是存在於這些路徑下的,而則只存在於下,全局調用下,是找不到的。

```# global 下的結構 . ├── /usr/local/lib/node_modules # npm root 的位置 │  ├── koa │   └── test-util # 執行腳本所處的位置 └── <workspace> # 本地的項目    ├── node_modules    │  └── express    └── .

local 下的結構

└── <workspace> # 本地的項目
├── node_modules # npm root 的位置
│  ├── koa
│  ├── test-util # 執行腳本所處的位置
│  └── express
└── .


以及一個相反的栗子🌰,若是有些依賴在下安裝了,可是沒有在下進行安裝,也許會出現這樣的狀況,命令直接調用的話,徹底沒有問題,可是放到中,或者使用來進行調用,則發現提示模塊不存在各類balabala的異常。
P.S. 在中,若是模塊不存在,並不會給你報錯,而是默認按照的方式進行解析,因此可能會遇到提示語法錯誤,這時候不用想了,必定是缺乏依賴

也能夠說是個好東西,儘可能使用的方式來調用,能少踩一些、的坑

最終的上線

固然了,真實的開發完一個工具之後,就須要進行提交到上了,這個也是一個很簡單的步驟,便可,會自動獲取中的做爲包名(重複了會報錯)。

小結

總結了一下關於可執行的包相關的一些東東,但願可以幫你們簡單的理解這是個什麼,以及和下一些可能會遇到的問題,但願可以讓你們繞過這些坑。
如文中有誤還請指出,工具相關的問題也歡迎來討論。

參考資料

來源:http://www.javashuo.com/article/p-tnlwxtcu-y.html

npm runNPM 5.xnpxwebpackpackage.jsonscriptsnpx webpacknpx./node_modules/webpack/bin/webpack.jsncreate-react-appvue-clinpm run buildscriptsnpm scriptsNPMshellNPMnpm lnnpm publishnpm installpackage.jsonnpm init-yJS#!/usr/bin/env node#!/usr/bin/env node // index.js console.log('first util')package.jsonNPMbinpackage.jsonnamek/v{ "bin": { "command1": "./command1.js", "command2": "./command2.js" } }NPMnpm lnlog<p>這樣一個最簡易的可執行包就建立完成了。</p> <blockquote>npm ln 爲 npm link 的簡寫 <br>npm ln &lt;模塊路徑&gt; 至關於 cd &lt;模塊路徑&gt; &amp;&amp; npm ln + npm ln &lt;模塊名&gt; <br>要注意是 <strong>模塊名__,而非文件夾名, __模塊名</strong> 爲<code>package.json</code>中所填寫的<code>name</code>字段</blockquote> <h3>global 與 local 的區別</h3> <p>由於<code>npm link</code>執行的<a href="https://docs.npmjs.com/cli/link#description" rel="nofollow noreferrer">特性</a>,會將<code>global</code>+<code>local</code>的依賴都進行安裝,因此在使用上不太好體現出二者的差別,因此咱們決定將代碼直接拷貝到<code>node_modules</code>下:</p> ```&gt; npm unlink --no-save test-util # 僅移除 local 的依賴 &gt; cp -R ../test-util ./node_modules/ &gt; npm rebuildNPMnpm rebuildNPMbin<p>這時再次執行兩種命令,就能夠看到區別了。 </p> <p>之因此要提到<code>global</code>與<code>local</code>,是由於在開發的過程當中可能會不經意的在這裏踩坑。 <br>好比說咱們在開發<code>Node</code>項目時,常常會用到<code>nodemon</code>來幫助在開發期間監聽文件變化並自動重啓。 <br>爲了使用方便,極可能會將預約的一個啓動命令放到<code>npm scripts</code>中去,相似這樣的:</p><h4>二者混用會帶來的問題</h4> <p>這樣的項目在你本地使用是徹底沒有問題的,可是若是有其餘的同事須要運行你的這個項目,在第一步執行<code>npm start</code>時就會出異常,由於他本地可能並無安裝<code>nodemon</code>。 </p> <p>以及這樣的作法極可能會致使一些其它包引用的問題。 <br>好比說,<code>webpack</code>其實是支持多種語言編寫<code>config</code>配置文件的,就拿<code>TypeScript</code>舉例吧,最近也一直在用這個。</p> ```&gt; webpack --config webpack.config.tswebpackCoffeeScriptwebpackconfigwebpackwebpack.ts['ts-node/register', 'typescript-node/register', 'typescript-register', 'typescript-require']webpackwebpackconfigNodenpm installrequire('XXX')node_modulesNPMnode_modulesnode_modulesAABBABnode_modulesfake-repoexpresstest-utilkoatest-util/index.jsrequirenpx test-utiltest-utilexpressNPMkoanode_modulesexpress<current>/node_modules/test-util/node_modulesrequireexpress<p>因此這也從側面說明了爲何<code>webpack</code>能夠直接在本身的文件中引用並不存在於本身模塊下的依賴。 </p> <p>由於<code>webpack</code>認爲若是你要使用<code>TypeScript</code>,那麼必定會有對應的依賴,這個模塊就是與<code>webpack</code>同級的依賴,也就是說<code>webpack</code>能夠放心的進行<code>require</code>,大體這樣的結構:</p> ```├── node_modules # npm root 的位置 │   ├── webpack │   └── typescript └── . # 在這裏執行腳本globallocalnpm scriptsnpxwebpackJSnpxnpxgloballocalNPMnpm publishpackage.jsonnameNPMgloballocalNPM
相關文章
相關標籤/搜索