讀懂package.json -- 依賴管理

npm做為Javascript項目的包管理工具,由于其與Node.js的緊密配合(npm和Node.js出自一人之手),目前已經(jīng)基本沒有競爭對手。

包管理工具要解決的主要問題就是依賴包的安裝,在Javascript項目中,包的依賴關系是由package.json給出的,這篇文件將介紹package.json中描述的依賴信息。

依賴管理

在package.json中,有如下幾項涉及到依賴包的描述:

  • dependencies
    項目中使用到的包,但不包括測試所使用的包

  • devDependencies

    主要是在測試時使用的包,也包括一些代碼編譯的包,比如將coffee-script編譯為javascript。也就是說在僅僅使用該項目的時候(而不進行測試等環(huán)節(jié)),不需要安裝的包可以放在devDependencies中

  • peerDependencies

    如果改項目需要指明一些有協(xié)作關系的包的版本時,使用peerDependencies。這里使用了協(xié)作,而不是依賴,是我個人的理解。peerDependencies并不是必須安裝的包,但如果一旦要安裝,就要符合要求。比如react-dom的package.json中有如下的描述:

    "peerDependencies": {
        "react": "^15.6.1"
     },
    

    peerDependencies至少打消了一些顧慮,比如react生態(tài)中用到的一些包在升級的時候會不會不匹配?

  • optionalDependencies

    如果有一些依賴包即使安裝失敗,項目仍然能夠運行或者希望npm繼續(xù)運行,就可以使用optionalDependencies。另外optionalDependencies會覆蓋dependencies中的同名依賴包,所以不要在兩個地方都寫。

  • bundledDependencies/bundleDependencies

    如果在打包發(fā)布的使用希望一些依賴包也出現(xiàn)在最終的包里,那么可以將包的名字放在bundledDependencies,bundledDependencies的值是一個字符串數(shù)組,如:

    "name": "awesome-web-framework",
    "version": "1.0.0",
    "bundledDependencies": [
        'renderized', 'super-streams'
     ]
    

    npm pack會將renderizedsuper-streams放入生成的包awesome-web-framework-1.0.0.tgz中,并且在npm install awesome-web-framework-1.0.0.tgz時,renderizedsuper-streams也會被一同安裝。

這些項的內容形式都是一樣的(除了bundledDependencies),只是作用不同,如:

  "dependencies": {
    "base62": "~0.1.1",
    "commoner": "~0.7.0",
    "esprima": "https://github.com/facebook/esprima/tarball/ca28795124d45968e62a7b4b336d23a053ac3a84",
    "recast": "~0.4.8",
    "source-map": "~0.1.22"
  }

key就是項目的名詞,而value可以有多種形式

  • version,遵循semver
  • 一個tarball的url
  • 一個git url
  • 本地路徑

關于semver會在另一篇文章中介紹(先挖個坑)。

依賴樹

不同于很多語言的依賴管理,npm使用的是依賴樹。也就是說每個依賴包會有一套自己指定的(在package.json中說明的)依賴包,而不會和其他包共享。
例如,mod-a依賴mod-b@1.0.0,mod-c依賴mod-b@2.0.0,而現(xiàn)在有一個項目依賴mod-a和mod-c,那么最終安裝的依賴包如下:

├─┬ node_modules
│ ├─┬ mod-a
│ │ ├── mod-b@1.0.0
│ ├─┬ mod-c
│ │ ├── mod-b@2.0.0

而Node.js在加載依賴包的時候會處理這個問題。之所以文章最開始說npm和Node.js的緊密合作也是這個原因。

使用依賴樹來管理包帶來了一個明顯的好處,不用處理依賴沖突的問題。這個問題在早期的Java項目中比較常見,而在使用了Maven和Gradle之后,情況有所緩解,但只能減輕同一個包多個版本被放入發(fā)布的包中這種情況,仍然無法解決依賴沖突這個根本問題。

依賴樹也有一些缺點:

  • 代碼量增加。由于不能共享相同的包(在npm v3中,嘗試著共享相同版本的庫,但還是比較弱),導致最終打包的時候有同一個庫的多個版本的代碼出現(xiàn)在最終包中。
  • 潛在的運行時沖突。以上面的例子為例,可能有些時候,mod-b的兩個版本無法同時運行,而這只有在運行或者測試的時候才能被發(fā)現(xiàn)。

希望以上的介紹能夠幫助你更好的理解npm的依賴管理。

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯(lián)系作者
【社區(qū)內容提示】社區(qū)部分內容疑似由AI輔助生成,瀏覽時請結合常識與多方信息審慎甄別。
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發(fā)布,文章內容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務。

相關閱讀更多精彩內容

  • Spring Cloud為開發(fā)人員提供了快速構建分布式系統(tǒng)中一些常見模式的工具(例如配置管理,服務發(fā)現(xiàn),斷路器,智...
    卡卡羅2017閱讀 136,554評論 19 139
  • Android 自定義View的各種姿勢1 Activity的顯示之ViewRootImpl詳解 Activity...
    passiontim閱讀 179,034評論 25 709
  • 原文地址:https://tech.meituan.com/npm-shrinkwrap.html 在一次項目開發(fā)...
    RiverSouthMan閱讀 1,357評論 0 0
  • 什么是 NPM npm之于Node,就像pip之于Python,gem之于Ruby,composer之于PHP。 ...
    ihoey閱讀 6,366評論 2 36
  • 現(xiàn)在開始寫文字得時間是1:50。我能說說我現(xiàn)在想說的話嗎? 我總是喜歡在這種夜深,人靜得時候,躲在被窩里寫文字?,F(xiàn)...
    angeli_qin閱讀 370評論 0 0

友情鏈接更多精彩內容