npm package.jsonファイルの依存関係、devDependencies、およびpeerDependenciesの違いは何ですか?


2029

このドキュメントは私の質問に非常によく答えていません。私はそれらの説明を理解できませんでした。誰かがもっと簡単な言葉で言うことができますか?簡単な単語を選ぶのが難しい場合は、例を挙げますか?

EDITも追加されましたpeerDependencies。これは密接に関連しており、混乱を引き起こす可能性があります。


48
optionalDependencies現在もあることに注意してください。
Aidan Feldman 2016年

118
@AidanFeldman "optionalDependencies"は私の今日のオキシモンです
Nick Bull

1
npmドキュメントは言う:「依存関係」:本番環境のアプリケーションで必要なパッケージ。"devDependencies":ローカルでの開発とテストにのみ必要なパッケージ。リンクを参照してください。docs.npmjs.com/...
デケ

回答:


2366

重要な動作の違いの要約:

  • dependencies 両方にインストールされています:

    • npm install を含むディレクトリから package.json
    • npm install $package 他のディレクトリ
  • devDependencies 次のとおりです。

    • フラグを渡さない限り、npm installを含むディレクトリにもインストールされpackage.jsonます--productionGayan Charithの回答に賛成してください)。
    • オプションnpm install "$package"を指定しない限り、他のディレクトリにはインストールされません--dev
    • 推移的にインストールされません。
  • peerDependencies

    • 3.0より前:存在しない場合は常にインストールされ、異なる依存関係によって互換性のないバージョンの依存関係が複数使用される場合はエラーが発生します。
    • 3.0で開始する予定です(テストされていnpm installません):で不足している場合は警告を表示し、手動で依存関係を解決する必要があります。実行時に依存関係が欠落していると、エラーが発生します(@nextgentechで言及)
  • 推移性(ベン・ハチソンによる言及):

    • dependencies は推移的にインストールされます。AがBを必要とし、BがCを必要とする場合、Cがインストールされます。そうでない場合、Bは機能せず、Aも機能しません。

    • devDependenciesは一時的にインストールされません。たとえば、AをテストするためにBをテストする必要はないので、Bのテストの依存関係は省略できます。

ここで説明されていない関連オプション:

devDependencies

dependencies実行にdevDependenciesは、開発のみが必要です。例:単体テスト、CoffeeScriptからJavaScriptへの変換、縮小、...

パッケージを開発する場合は、(たとえばを介してgit clone)ダウンロードし、を含むルートに移動して、次のコマンドをpackage.json実行します。

npm install

あなたは実際のソースを持っているので、あなたがそれを開発したいのは明らかなので、デフォルトでは、両方とも dependencies(もちろん、開発のために実行する必要があるため)とdevDependency依存関係の両方もインストールされます。

ただし、パッケージをインストールしてそれを使用したいだけのエンドユーザーである場合は、任意のディレクトリから実行します。

npm install "$package"

その場合、通常は開発の依存関係は必要ないので、パッケージを使用するために必要なものを取得するだけです。 dependencies

その場合に開発パッケージを本当にインストールしたい場合は、コマンドラインから次のdevように設定オプションをtrueに設定できます。

npm install "$package" --dev

オプションは falseこれはあまり一般的ではないので、このデフォルトです。

peerDependencies

(3.0以前にテスト済み)

出典:https//nodejs.org/en/blog/npm/peer-dependencies/

通常の依存関係では、依存関係の複数のバージョンを持つことができます。それは単に内部にインストールされます node_modules。依存関係のです。

たとえばdependency1dependency2両方がdependency3異なるバージョンに依存している場合、プロジェクトツリーは次のようになります。

root/node_modules/
                 |
                 +- dependency1/node_modules/
                 |                          |
                 |                          +- dependency3 v1.0/
                 |
                 |
                 +- dependency2/node_modules/
                                            |
                                            +- dependency3 v2.0/

ただし、プラグインは、通常、このコンテキストではホストと呼ばれる他のパッケージを必要としないパッケージです。代わりに:

  • ホストにはプラグインが必要です
  • プラグインは、ホストが見つけることを期待する標準インターフェースを提供します
  • ホストのみがユーザーによって直接呼び出されるため、その単一バージョンが必要です。

たとえばdependency1dependency2ピアがに依存しているdependency3場合、プロジェクトツリーは次のようになります。

root/node_modules/
                 |
                 +- dependency1/
                 |
                 +- dependency2/
                 |
                 +- dependency3 v1.0/

これdependency3は、package.jsonファイルで決して言及していなくても起こります。

これはInversion of Controlデザインパターンのインスタンスだと思います。

ピアの依存関係の典型的な例は、Grunt、ホスト、およびそのプラグインです。

たとえば、https://github.com/gruntjs/grunt-contrib-uglifyなどのGruntプラグインでは、次のようになります

  • gruntpeer-dependency
  • 唯一のrequire('grunt')下にあるtests/:それは実際にプログラムによって使用されていません。

次に、ユーザーがプラグインを使用するときに、行をGruntfile追加して暗黙的にプラグインを要求しますが、ユーザーが直接呼び出すことになります。grunt.loadNpmTasks('grunt-contrib-uglify')grunt

各プラグインに異なるGruntバージョンが必要な場合、これは機能しません。

マニュアル

ドキュメンテーションはこの質問にかなりよく答えていると思います。おそらくあなたは、ノードや他のパッケージマネージャーに十分に精通しているだけではないでしょう。Rubyバンドルについて少し知っているので、おそらくそれだけを理解しています。

重要な行は次のとおりです。

これらのものは、パッケージのルートからnpm linkまたはnpm installを実行するとインストールされ、他のnpm構成パラメーターと同様に管理できます。このトピックの詳細については、npm-config(7)を参照してください。

そして、npm-config(7)の下でfind dev

Default: false
Type: Boolean

Install dev-dependencies along with packages.

5
ああ。誤解しているようです。あなたの答えnpm install packageは、私が今思っていることではなく、devの依存関係ではないすべてのパッケージをインストールするために使用するコマンドであると解釈します。これを読む前に。もし私があなただったら、あなたが意味するところが 'insert-name-here'であることを明確に示す[package-name]と編集するでしょう。
トムW

184
これは素晴らしい!気づかなかったが、この回答から、依存関係とdevDependenciesの違いは、npmパッケージを公開する場合にのみ適用できることがわかりました。アプリケーションやサイトで作業しているだけであれば、それほど問題になりません。ありがとう!
jedd.ahyoung 2014

3
この投稿はpeerDependencies、今後のnpm @ 3で変更された動作を反映するように更新する必要があります。blog.npmjs.org/post/110924823920/npm-weekly-5から:「ピアの依存関係は自動的にダウンロードされなくなります。代わりに、ピアの依存関係がまだインストールされていない場合は警告が表示されます。これには、 peerDependencyの競合を手動で解決するには、手動で行いますが、長期的には、パッケージの依存関係が厄介な場所になる可能性が低くなります。」
nextgentech

8
また、devDependenciesは依存パッケージによって推移的にインストールされません。例:パッケージAはパッケージに依存B.パッケージBがパッケージCに依存し、パッケージD.上のBもdevDependsあなたが実行している場合npm install、パッケージAから、あなたはBとCではなくD.取得します
ベン・ハチソン

9
がに設定devDependenciesされている場合NODE_ENVはインストールされないことに注意してくださいproduction
アウグストフランゾイア2018

491

devDependenciesをインストールしたくない場合は、 npm install --production


1
npm install --saveはソフトウェアに依存していますか?
Vamsi Pavan Mahesh 2015

19
npm installはすべての依存関係をインストールします。--saveフラグは、特定のモジュールをpackage.jsonにも追加する場合に使用されます。ex:-npm install uglify --saveは、プロジェクトフォルダーにuglifyをインストールし、uglifyをプロジェクトのpackage.jsonファイルに追加します。
ガイアンチャリス

6
また、ここではdevDependenciesについて説明しているため、-save-devを使用して新しいモジュールをdevDependencyとして保存できます。例:npm install uglify --save-dev
Mykaelos '29

9
npm 5以降、この--saveオプションは不要になりました。「npm install my-package」を実行すると、my-packageが依存関係としてpackage.jsonファイルに追加されます。
マーティンカレル2018

ちょうどnpmのインストール
スルタンaslam

116

例として、モカは通常devDependencyです。本番環境ではテストは必要ありませんが、エクスプレスは依存関係です。


4

47
テストを実行し、テストに合格した場合は本番環境にデプロイするHudsonやCircleCIなどの継続的インテグレーションサービスを使用することをお勧めします。
Dan Kohn

1
CIサーバーがprodサーバーと何らかの形で異なる可能性があるため、実際のサーバーをテストすることは依然として適切である可能性があり、この違いにより、たとえばアプリの起動が妨げられる可能性があります...
Nicole

2
@Nicoleステージングサーバーの構成を製品と同じにしないのはなぜですか?
ルーカス

1
次に、テストの依存関係を通常の依存関係として追加すると、追加のライブラリが大量に導入され、それぞれが何らかの方法で失敗する可能性があります。私は、可能な限りコードが少ない軽量の本番サーバーに傾倒します(しゃれます!)。覚えておいてください、最良のコードはコードではありません!
Stijn de Witt

69

依存
関係コードから呼び出す関数を提供するライブラリのように、プロジェクトを実行する必要がある依存関係。
それらは推移的にインストールされます(AがBに依存し、BがCに依存する場合、npm install on AはBとCをインストールします)。
例:lodash:プロジェクトがいくつかのlodash関数を呼び出します。

devDependencies
コードを取得してJavaScriptにコンパイルするコンパイラー、テストフレームワーク、ドキュメントジェネレーターなど、開発中またはリリース中にのみ必要な依存関係。
それらは推移的にインストールされません(AがBに依存している場合、devはCに依存し、npm install on AはBのみをインストールします)。
例:grunt:プロジェクトはgruntを使用してそれ自体をビルドします。

peerDependencies
プロジェクトが親プロジェクトにフックまたは変更する依存関係。通常は、他のライブラリまたはツールのプラグインです。これは、親プロジェクト(プロジェクトに依存するプロジェクト)がフックするプロジェクトに依存していることを確認するためのものです。したがって、ライブラリBに機能を追加するプラグインCを作成する場合、プロジェクトAを作成する人は、Cに依存している場合、Bに依存している必要があります。
それらはインストールされていません(npm <3でない限り)、チェックしました。
例:grunt:プロジェクトはgruntに機能を追加し、gruntを使用するプロジェクトでのみ使用できます。

このドキュメントは、ピアの依存関係を非常によく説明しています:https : //nodejs.org/en/blog/npm/peer-dependencies/

また、npmのドキュメントは時間の経過とともに改善され、さまざまなタイプの依存関係の説明が改善されました。https//github.com/npm/cli/blob/latest/doc/files/package.json.md#devdependencies


63

パッケージをdev依存関係としてpackage.jsonに保存するには:

npm install "$package" --save-dev

あなたが実行するとnpm install、それは両方をインストールしますdevDependenciesdependencies。インストールを回避するにdevDependenciesは:

npm install --production

3
次も使用できます:npm i -S
Maysara Alhindi '28 / 07/28

36

開発にのみ必要なモジュールとパッケージがいくつかありますが、本番環境では必要ありません。それがドキュメントでそれを言うように:

プログラムでモジュールをダウンロードして使用することを計画している人は、おそらく、使用する外部テストまたはドキュメントフレームワークをダウンロードしてビルドすることを望まないか、必要としないでしょう。この場合、これらの追加項目をdevDependenciesハッシュにリストするのが最善です。


本番環境でbundle.jsファイルのみを実行している場合はどうなりますか?あなたは本当にそれらの依存関係が必要ですか?
RegarBoy 2018

サーバー上でbundle.jsを実行している場合は、サーバー側のwebpackなどを実行しています...通常はそうではなく、実際に正しく実行するには多くの作業が必要になるため、そうであるかどうかを確認してください(私は私がそれをしたので知っています)。あなたのbundle.jsはブラウザまで提供され、クライアント側のコードが含まれていると思います。
Stijn de Witt

16

私にそれをより明確にした簡単な説明は:

アプリをデプロイする場合、依存関係のモジュールをインストールする必要があります。そうしないと、アプリが機能しません。devDependenciesのモジュールは、そのマシンで開発していないため、運用サーバーにインストールする必要はありません。 リンク


2
それで、私たちがウェブサイトを作成していて、製品版ですべてのライブラリがにインライン化されるvendor.js場合、コンパイルされたコードがリポジトリにコミットされる場合、すべてのdepはdev depsである必要がありますか?そして、コミットする必要があります。それ以外の場合は、単にインストールするだけでなく、モジュールをコンパイルする必要があるのは奇妙です(そして、サブモジュールの変更はリグレッションにつながる可能性があるため、テストもここのどこかで行われます)...
Qwertiy

すばらしい答えですが、質問がありますか?可能なWebpackは破損したバンドルを構築しますか?私の推測では、devDependenciesパッケージは製品バージョンでは機能しませんwebpack -p。私の質問に答えてください。
AmerllicA 2017年

プロダクションビルド中に問題が発生した場合は、ビルド時にエラーが表示され、破損したコードがプロダクションにプッシュされないようにデプロイメントプロセスを設計する必要があります(たとえば、Jenkinsを試すことができます)。いずれにしても、依存関係は運用サーバーにインストールする必要はありません。
Jyoti Duhan 2017

ピアの依存関係はどうですか?
dev27

13

これらの依存関係の説明に対する私の見解を回答に追加したいと思います

  • dependencies コードベースで直接使用するために使用されます。通常、最終的に製品コードになるもの、またはコードのチャンク
  • devDependencies ビルドプロセス、エンドコードの最終的な管理に役立つツール、サードパーティのテストモジュール(webpackなど)に使用されます

CSSアセットについてはどうですか?
Brian Zelip

8

要するに

  1. 依存関係 - npm install <package> --save-prod本番環境でアプリケーションに必要なパッケージをインストールします。

  2. DevDependencies - npm install <package> --save-devインストールパッケージは、ローカルの開発およびテストのために必要

  3. 入力npm installするだけで、package.jsonに記載されているすべてのパッケージがインストールされます

ローカルコンピュータで作業している場合は、入力npm installして続行してください:)


6

peerDependencies上記のトピックCiroに関するブログ投稿からこのスニペットを読むまで、私にはまったく意味がありませんでした:

[ plugins ]に必要なのは、プラグインとホストパッケージの間のこれらの「依存関係」を表現する方法です。「私は自分のホストパッケージのバージョン1.2.xにプラグインしたときにのみ機能するので、インストールする場合は、互換性のあるホストと一緒にインストールするようにしてください。」この関係をピア依存関係と呼びます。

プラグインは期待していますホストの特定のバージョンをています...

peerDependenciesプラグイン、機能を実行するために「ホスト」ライブラリを必要とするライブラリ用ですが、以前に作成された可能性がありますの最新バージョンがリリースさ。

つまり、私が書いPluginX v1HostLibraryX v3立ち去ったとしても、PluginX v1いつ動作するHostLibraryX v4かは保証されません(またはHostLibraryX v3.0.1リリースされたリリースされた)が。

...しかし、プラグインは依存しませんホストにし ...

プラグインの観点からは、ホストライブラリに関数を追加するだけです。プラグインに依存関係を追加するためにホストを実際に「必要とする」ことはありません。プラグインは、文字通りホストに依存していないことがよくあります。ホストがない場合、プラグインは無害です。

これはdependencies、プラグインの正しいコンセプトではないことを意味します。

さらに悪いことに、私のホストが依存関係のように扱われた場合、同じブログ投稿がこの状況になってしまいます(この回答を使用するために少し編集して、ホストとプラグインを構成しました)。

しかし、[HostLibraryXの最新バージョンをPluginXの依存関係として扱う場合]を実行npm installすると、次の予期しない依存関係グラフが生成されます。

├── HostLibraryX@4.0.0
└─┬ PluginX@1.0.0
  └── HostLibraryX@3.0.0

メインアプリケーションとは異なる[HostLibraryX] APIを使用するプラグインから発生する微妙なエラーは、想像に任せます。

...そしてホストは明らかにプラグインに依存していません...

...それがプラグインの要点です。ホストがそのすべてのプラグインの依存関係情報を含めるのに十分良ければ、それで問題は解決しますが、それによって大きな新しい文化的な問題、つまりプラグイン管理も導入されます。

プラグインの要点は、匿名でペアリングできることです。完璧な世界では、ホストにすべてを管理させることはきちんと整頓されていますが、私たちは図書館の群れ猫を必要としないでしょう。

階層的に依存していない場合は、おそらく依存関係のあるピアです...

代わりに、私たちは仲間であるという概念を持っています。ホストもプラグインも、他の依存関係バケットにはありません。どちらもディペンデンシーグラフの同じレベルにあります。


...しかし、これは自動化可能な関係ではありません。<<< Moneyball !!!

私がそうでPluginX v1あり、(つまり、peerDependencyが)のピアを期待している場合は、そのように言います。あなたはきた最新の自動アップグレードした場合(ノートのバージョンその4しているインストールされ、あなたは、右知っている必要がありますか?HostLibraryX v3HostLibraryX v4Plugin v1

npm 私にはこの状況を管理できません-

「ねえ、あなたが使っているようですPluginX v1!私は自動的にHostLibraryXv4からv3にダウングレードします、kk?」

...または...

「お使いのを確認しましたPluginX v1HostLibraryX v3前回のアップデートでが残っていたはずです。念のため、自動的にアンインストールしますPlugin v1!! 1!

いやいや、npm ?!

だからnpmはしません。状況を警告し、HostLibraryX v4がの適切なピアであるかどうかを判断できますPlugin v1


コーダ

グッドpeerDependencyプラグインでの管理は、実際には、より直感的にこの概念の作業を行います。ブログ投稿から、まだまた...

アドバイスの1つ:ピアの依存関係の要件は、通常の依存関係の要件とは異なり、寛大でなければなりません。ピアの依存関係を特定のパッチバージョンに限定しないでください。あるChaiプラグインがChai 1.4.1にピア依存していて、別のChaiプラグインがChai 1.5.0に依存しているとしたら、それは本当に面倒なことです。と互換性があります。


4

依存関係と開発依存関係

Devの依存関係は、開発時にのみ必要なモジュールですが、依存関係は実行時に必要です。アプリケーションをデプロイする場合は、依存関係をインストールする必要があります。そうしないと、アプリが機能しません。プログラムの実行を可能にするコードから呼び出すライブラリは、依存関係と見なすことができます。

たとえば、React、React-dom

開発マシンではコードをjavascriptに変換する.compilersで開発しないので、dev依存モジュールを本番サーバーにインストールする必要はありません。テストフレームワークとドキュメントジェネレータは、開発中にのみ必要であるため、dev依存と見なすことができます。

例-ESLint、Babel、webpack

@ご参考までに、

mod-a
  dev-dependents:
    - mod-b
  dependents:
    - mod-c

mod-d
  dev-dependents:
    - mod-e
  dependents:
    - mod-a

----

npm install mod-d

installed modules:
  - mod-d
  - mod-a
  - mod-c

----

checkout the mod-d code repository

npm install

installed modules:
  - mod-a
  - mod-c
  - mod-e

npmに公開する場合は、正しいモジュールに正しいフラグを使用することが重要です。npmモジュールが機能する必要がある場合は、「-save」フラグを使用してモジュールを依存関係として保存します。モジュールが機能する必要はないものの、テストには必要な場合は、「-save-dev」フラグを使用します。

# For dependent modules
npm install dependent-module --save

# For dev-dependent modules
npm install development-module --save-dev

1

npmパッケージを配布する場合は、の使用を避けてくださいdependencies。代わりに、への追加peerDependenciesまたは削除を検討する必要がありますdependencies


弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.