いろんなNPMパッケージのサイズの内訳を調べていくよ

# こんな経験ありませんか？

Node.jsを使ってライブラリもしくはツールを作っていたとします．その開発の過程において，

* 最新の言語仕様をベースにコードを書きたいよね<br/> → Babel
* シンタックスチェックしとこ<br/> → ESLint
* テスト書くのは基本だろ<br/> → Jest
* 毎回コマンドラインから`npm test`するの面倒だから，タスクランナーでwatchしとくか<br/> → Gulp

などとパッケージを`npm install --save-dev`でどんどん追加していくと思いますが，気が付くと`node_modules`内にものすごい数のパッケージがインストールされていて，それだけで数十MBのディスクを消費している．．．（まあ，昨今のハードディスク容量から考えると，数GB使っても大したことないのかもしれませんが）

このようなとき，私はどうしてもこう思ってしまうのです．

「すげーデカイんだけど．．．本当にこのサイズが必要なのか？」

もちろん，パッケージを使って別のプログラムを開発している人にとっての答えは明らかで，「必要です」が答えでしょう．その開発者が，あるパッケージのほんの一部の機能しか使っていなかったとしても，自分のプログラムを開発するために必要なのだから仕方ありません．

しかし，パッケージを提供する側は「提供する機能とサイズ」のバランスについて多少なりとも考えるべきだと私は思います．

個人の感想レベルにすぎませんが，Node.jsパッケージ開発者はパッケージサイズにあまり関心がなさそうに感じます．事実，自分が使っているNPMパッケージのサイズを集計してみようと思って手頃なツールを探してみたのですが，見つかるのはフロントエンド・ウェブアプリのバンドルファイルのサイズを解析することを目的としたツールが殆どでした．

* [package-size](https://www.npmjs.com/package/package-size)
* [webpack-bundle-analyzer](https://www.npmjs.com/package/webpack-bundle-analyzer)
* [bundlephobia.com](https://bundlephobia.com/)

上記がすべてではなく，探せば他にも見つかります（`vue ui`とか）．その中で使えそうだと感じたのは，以下のツールくらいでした（もちろん，私が見つけられなかっただけで，他にもある可能性は否定しません）．

* [cost-of-modules](https://github.com/siddharthkp/cost-of-modules)
* `du`コマンド
* 他に知っているツールがあれば教えてください．．

ただ，これらのツールの集計結果だけでは十分な情報が得られないので，さらなる加工や新たなメトリックスの導入が必要だと感じました．

そこで，[@masnagam/npm-diet](https://www.npmjs.com/package/@masnagam/npm-diet)を作りました．まだ，開発途中なので機能が足りなかったり，テーブル表示がいまいちだったり，helpの内容が変だったりしますが許してください．

`npm-diet`の概要についてはNPMのサイトに記載してあるので省略して，さっそくいろいろなパッケージのサイズの内訳を見ていきましょう．

なお，以降の記述は，調査の進行に応じて随時更新する予定です．

## 注意点

* `npm ddp`の効果により，複数パッケージの計測値は個々のパッケージの単体での計測値の合計値とはなりません
    * そのため，`npm-diet measure`は複数のパッケージを指定可能となっています
* `npm-diet summary`はインストールしたパッケージのバージョンや日付などを表示しないため，どのバージョンの結果なのかはっきりしません
    * 改善予定です

# コードカバレッジツール

[npm trends: istanbul vs nyc vs jscoverage](http://www.npmtrends.com/istanbul-vs-nyc-vs-jscoverage)

## istanbul

大抵の人が使っていたツールだと思いますが，nycに代替わりして，今ではメンテナンスも行われていないような印象を受けます．

```console
$ npm-diet measure istanbul | npm-diet summary
#PKGS  SIZE     #FILES  #DUPS  DUP      %DUP
-----  -------  ------  -----  -------  -------
   60  6.77 MB     775      6  1.25 MB  18.45 %
```

6.77MBと結構なサイズです．同一名パッケージ（以下，重複と呼びます）があり，全体サイズの18.45%を占めていることが分かります（細かい話ですが，どの同一名パッケージを重複とするかによって`DUP`と`%DUP`の値は変わります）．

次に，Top5を見てみましょう．

```console
$ npm-diet measure istanbul | npm-diet show measure --top=5
PACKAGE            SIZE       %SIZE    #FILES
-----------------  ---------  -------  ------
handlebars@4.0.11    2.71 MB  40.09 %     127
source-map@0.5.7   750.74 KB  10.84 %      19
uglify-js@2.8.29   605.62 KB   8.74 %      19
esprima@4.0.1      307.81 KB   4.44 %       7
istanbul@0.4.5     301.64 KB   4.35 %      56
-----------------  ---------  -------  ------
TOP 5                4.63 MB  68.46 %     228
TOTAL 60             6.77 MB              775
```

istanbul自体は300KBほどしかなく，全体の4.35%のサイズしか持たないことが分かります．また，一番大きいのはhandlebarsで40%を占めています．

続いて，何が重複しているのか見てみましょう．

```console
$ npm-diet measure istanbul | npm-diet show dup --package-path
PACKAGE           SIZE       %SIZE    #FILES  PATH
----------------  ---------  -------  ------  -----------------------------------------------
source-map@0.2.0  221.28 KB               40  node_modules/source-map
----------------  ---------  -------  ------  -----------------------------------------------
source-map@0.5.7  750.74 KB  58.73 %      19  node_modules/uglify-js/node_modules/source-map
source-map@0.4.4  125.48 KB   9.82 %      22  node_modules/handlebars/node_modules/source-map
----------------  ---------  -------  ------  -----------------------------------------------
TOTAL 2           876.22 KB  68.55 %      41

PACKAGE           SIZE       %SIZE    #FILES  PATH
----------------  ---------  -------  ------  -----------------------------------------------
esprima@2.7.3     214.46 KB                7  node_modules/esprima
----------------  ---------  -------  ------  -----------------------------------------------
esprima@4.0.1     307.81 KB  24.08 %       7  node_modules/js-yaml/node_modules/esprima
----------------  ---------  -------  ------  -----------------------------------------------
TOTAL 1           307.81 KB  24.08 %       7

PACKAGE           SIZE       %SIZE    #FILES  PATH
----------------  ---------  -------  ------  -----------------------------------------------
wordwrap@1.0.0     36.81 KB                9  node_modules/wordwrap
----------------  ---------  -------  ------  -----------------------------------------------
wordwrap@0.0.2     35.83 KB   2.80 %       9  node_modules/cliui/node_modules/wordwrap
wordwrap@0.0.3     36.87 KB   2.88 %       9  node_modules/optimist/node_modules/wordwrap
----------------  ---------  -------  ------  -----------------------------------------------
TOTAL 2            72.71 KB   5.69 %      18

PACKAGE           SIZE       %SIZE    #FILES  PATH
----------------  ---------  -------  ------  -----------------------------------------------
minimist@0.0.10    22.47 KB               16  node_modules/minimist
----------------  ---------  -------  ------  -----------------------------------------------
minimist@0.0.8     21.50 KB   1.68 %      14  node_modules/mkdirp/node_modules/minimist
----------------  ---------  -------  ------  -----------------------------------------------
TOTAL 1            21.50 KB   1.68 %      14
```

source-mapは

* istanbul
* uglify-js
* handlebars

のそれぞれに含まれており，重複の合計サイズは876KBです．重複サイズの半分以上がsource-mapだと分かります．

## nyc

istanbulの後継ツールです．正直，ホームページやGitHubを見ただけでは，追加された新規機能があるのかないのかはっきりしませんが，istanbulの５割増しであることが分かります．

```console
$ npm-diet measure nyc | npm-diet summary
#PKGS  SIZE      #FILES  #DUPS  DUP      %DUP
-----  --------  ------  -----  -------  -------
  289  12.53 MB    2967     68  2.63 MB  21.02 %
```

重複率は更に進んで21%です．

基本的に要領はistanbulのときと同じなので省略しますが，詳しく調査すると

* source-mapが４個（つまり重複３個）
    * 重複サイズの合計は1.63MB
* kind-ofが１０個
* debugが４個
* 他にもたくさん

自分の必要としている機能がすべてistanbulに含まれているなら，istanbulでもいいのかもしれません．

# テストフレームワーク

[npm trends: jest vs mocha vs ava vs jasmine vs qunit](http://www.npmtrends.com/jest-vs-mocha-vs-ava-vs-jasmine-vs-qunit)

## Jest

たくさんの機能が盛り込まれているだけあって，かなりデカイです．

```console
$ npm-diet measure jest | npm-diet summary
#PKGS  SIZE      #FILES  #DUPS  DUP      %DUP
-----  --------  ------  -----  -------  -------
  583  35.11 MB    8296    129  5.43 MB  15.45 %
```

35MBのテストフレームワークをパッケージ毎にインストールしていると，Jestのコピーだけでハードディスクを数百MB使ってしまいそうです．

* 人気のsource-mapが５個入ってます
* esprimaが２個（常連？）
* kind-ofが１２個

段々と重複の傾向が見えてきました．

## AVA

AVAはJestと違ってカバレッジツールやモックなどは含まれていません．

```console
$ npm-diet measure ava | npm-diet summary
#PKGS  SIZE      #FILES  #DUPS  DUP      %DUP
-----  --------  ------  -----  -------  -------
  470  14.52 MB    5694     87  1.88 MB  12.94 %
```

* source-mapが２個

## Mocha

MochaもAVA同様，もろもろ含まれていません．

```console
$ npm-diet measure mocha | npm-diet summary
#PKGS  SIZE     #FILES  #DUPS  DUP  %DUP
-----  -------  ------  -----  ---  ------
   24  1.86 MB     223      0  0 B  0.00 %
```

ついに出ました，重複なしです．

Top5で85%．mocha自身も41%で，寄せ集めではない感があります．

```console
$ npm-diet measure mocha | npm-diet show measure --top=5
PACKAGE           SIZE       %SIZE    #FILES
----------------  ---------  -------  ------
mocha@5.2.0       796.18 KB  41.88 %      49
diff@3.5.0        608.43 KB  32.01 %      27
he@1.1.1          106.33 KB   5.59 %       6
commander@2.15.1   59.37 KB   3.12 %       6
growl@1.10.5       58.90 KB   3.10 %       9
----------------  ---------  -------  ------
TOP 5               1.59 MB  85.70 %      97
TOTAL 24            1.86 MB              223
```

ちなみに，私が昔良く使っていた組み合わせについても計測してみました．

```console
$ npm-diet measure mocha chai sinon sinon-chai | npm-diet summary
#PKGS  SIZE     #FILES  #DUPS  DUP  %DUP
-----  -------  ------  -----  ---  ------
   43  8.66 MB     432      0  0 B  0.00 %
```

8MB超えか．．100KB以下のプログラムのテストにこれだけ使っていたのか．．

## Jasmine

昔は多くの人が使っていたJasmine．最近は選択肢が増えたこともあり，あまり活発に開発されていないように見えます．

```console
$ npm-diet measure jasmine | npm-diet summary
#PKGS  SIZE       #FILES  #DUPS  DUP  %DUP
-----  ---------  ------  -----  ---  ------
   13  462.74 KB     106      0  0 B  0.00 %
```

1MBを切りました．小さいです．個人的な感覚では，提供されている機能に対して460KBは大きすぎる気がしますが，まあ，スクリプト言語なのでこんなものなのでしょう．

spyなども含まれているので，正直これで十分な気がします．

# Transpiler & Bundler

[npm trends: babel-cli vs @babel/cli vs browserify vs webpack vs rollup](http://www.npmtrends.com/babel-cli-vs-@babel/cli-vs-browserify-vs-webpack-vs-rollup)

## Browserify

`require`を展開してくれる便利ツール．いくつかのNode.jsモジュールのshimもついてます．私もお世話になっています．

```console
$ npm-diet measure browserify | npm-diet summary
#PKGS  SIZE     #FILES  #DUPS  DUP        %DUP
-----  -------  ------  -----  ---------  ------
  136  5.50 MB    2043      6  139.40 KB  2.48 %
```

重複はありますが３％以下．ここにtranformを追加して使うので，10MB超えは確実か？

```console
$ npm-diet measure browserify | npm-diet show measure --top=5
PACKAGE            SIZE       %SIZE    #FILES
-----------------  ---------  -------  ------
pako@1.0.6         768.88 KB  13.65 %      27
source-map@0.5.7   750.77 KB  13.33 %      19
acorn@5.7.1        554.57 KB   9.85 %      16
JSONStream@1.3.3   400.06 KB   7.10 %      35
browserify@16.2.2  350.47 KB   6.22 %     426
-----------------  ---------  -------  ------
TOP 5                2.76 MB  50.16 %     523
TOTAL 136            5.50 MB             2043
```

pakoはJS製のzlibだそうで，それなりに大きいですね．macOSに入っていたlibz.dylibが180KBくらいなので，約４倍です．

## Babel

6 -> 7でほとんど変わらず（ちょっと減ってる）．

```console
$ npm-diet measure babel-cli babel-preset-env | npm-diet summary
#PKGS  SIZE      #FILES  #DUPS  DUP        %DUP
-----  --------  ------  -----  ---------  ------
  238  11.60 MB    5118     34  618.16 KB  5.21 %

$ npm-diet measure @babel/core @babel/cli @babel/preset-env | npm-diet summary
#PKGS  SIZE      #FILES  #DUPS  DUP         %DUP
-----  --------  ------  -----  ----------  ------
  322  11.34 MB    4330     69  1022.17 KB  8.80 %
```

```console
$ npm-diet measure @babel/core @babel/cli @babel/preset-env | npm-diet show measure --top=3
PACKAGE                    SIZE       %SIZE    #FILES
-------------------------  ---------  -------  ------
lodash@4.17.10               1.34 MB  11.79 %    1049
caniuse-lite@1.0.30000874    1.16 MB  10.21 %     752
source-map@0.5.7           750.79 KB   6.47 %      19
-------------------------  ---------  -------  ------
TOP 3                        3.23 MB  28.47 %    1820
TOTAL 322                   11.34 MB             4330
```

lodash大きいですね．分割されているのも納得です．

## webpack

もっと大きいかと思ったのですが，26MB弱でした．感覚が麻痺してきたのでしょうか．．

```console
$ npm-diet measure webpack webpack-cli | npm-diet summary
#PKGS  SIZE      #FILES  #DUPS  DUP      %DUP
-----  --------  ------  -----  -------  -------
  468  25.73 MB    8696    101  4.05 MB  15.73 %
```

source-mapが４個入っていても気にならなくなってきました．

```console
$ npm-diet measure webpack webpack-cli | npm-diet show measure --top=5
PACKAGE           SIZE       %SIZE    #FILES
----------------  ---------  -------  ------
rxjs@6.2.2          4.56 MB  17.71 %    3555
lodash@4.17.10      1.34 MB   5.19 %    1049
webpack@4.16.5      1.23 MB   4.78 %     327
ajv@6.5.2         872.00 KB   3.31 %      90
source-map@0.6.1  788.69 KB   2.99 %      20
----------------  ---------  -------  ------
TOP 5               8.74 MB  33.99 %    5041
TOTAL 468          25.73 MB             8696
```

rxjsは，reactive programming用のライブラリのようです．4MB強のサイズに見合った機能なのかは使ったことがないので分かりません．

## rollup.js

rollup.jsは，`import`をサポートしているバンドラーです．`require`は確かサポートしてなかったと思います（`node_modules`からの読み込みはプラグインでサポートしてたと思います）．

```console
$ npm-diet measure rollup | npm-diet summary
#PKGS  SIZE     #FILES  #DUPS  DUP  %DUP
-----  -------  ------  -----  ---  ------
    3  3.18 MB      18      0  0 B  0.00 %
```

圧倒的なパッケージ数の少なさに驚きます．Node.jsでは小さいパッケージを使って，大きなプログラムを作るみたいな文化を感じるので，これとは異なる思想の持ち主が作成したのかもしれません．

```console
$ npm-diet measure rollup | npm-diet show measure
PACKAGE               SIZE       %SIZE    #FILES
--------------------  ---------  -------  ------
rollup@0.64.1           2.67 MB  83.81 %       9
@types/node@10.5.7    509.50 KB  15.63 %       5
@types/estree@0.0.39   18.18 KB   0.56 %       4
--------------------  ---------  -------  ------
TOTAL 3                 3.18 MB               18
```

@types/nodeはNode.jsのTS用型定義．rollup.jsはTS製です．ですが，JSにコンパイル後は@types/nodeは不要な気がします．`devDependencies`にはできなかったのでしょうか？

ファイルも18個と少ないので，全部列挙してみます．

```console
$ npm-diet measure rollup | jq '.packages[].files[] | .path, .size / 1024.'
"CHANGELOG.md"
72.5615234375
"LICENSE.md"
1.1083984375
"README.md"
8.517578125
"bin/rollup"
65.4296875
"dist/rollup.browser.js"
822.5849609375
"dist/rollup.d.ts"
10.2373046875
"dist/rollup.es.js"
869.4365234375
"dist/rollup.js"
869.8125
"package.json"
5.3134765625
"LICENSE"
1.1552734375
"README.md"
0.486328125
"index.d.ts"
15.12890625
"package.json"
1.42578125
"LICENSE"
1.134765625
"README.md"
1.787109375
"index.d.ts"
403.46484375
"inspector.d.ts"
99.166015625
"package.json"
3.7021484375
```

TS用定義ファイルなど，rollupコマンドが実行できればいいだけなら，サイズは1MB以下になりそうな気がします．

# CLIフレームワーク

[npm trends: commander vs minimist vs nopt vs optimist vs optionator vs yargs vs meow](http://www.npmtrends.com/commander-vs-minimist-vs-nopt-vs-optimist-vs-optionator-vs-yargs-vs-meow)

## Commander.js

`npm-diet`でも使用しています．オプション解析機能に加えて，サブコマンドやヘルプ生成機能などもついています．

```console
$ npm-diet measure commander | npm-diet summary
#PKGS  SIZE      #FILES  #DUPS  DUP  %DUP
-----  --------  ------  -----  ---  ------
    1  60.67 KB       6      0  0 B  0.00 %
```

小さくていいです．このままの状態を維持してもらいたいです．

## Yargs

最もダウンロードされているだけあり，機能が豊富です．Commander.jsの機能に加えて，入力補完や設定ファイル，環境変数の処理なども含まれているようです．

```console
$ npm-diet measure yargs | npm-diet summary
#PKGS  SIZE     #FILES  #DUPS  DUP       %DUP
-----  -------  ------  -----  --------  ------
   50  1.23 MB     288      4  19.70 KB  1.57 %
```

多くの機能が盛り込まれているだけあって，サイズも大きく1.2MB超えです．

```console
$ npm-diet measure yargs | npm-diet show measure --top=3
PACKAGE              SIZE       %SIZE    #FILES
-------------------  ---------  -------  ------
xregexp@4.0.0        675.36 KB  53.65 %      22
yargs@12.0.1         211.16 KB  16.78 %      40
yargs-parser@10.1.0   48.33 KB   3.84 %       6
-------------------  ---------  -------  ------
TOP 3                934.85 KB  74.27 %      68
TOTAL 50               1.23 MB              288
```

一番大きいのはxregexpというライブラリです．Unicodeコードポイントの範囲でのマッチングや，正規表現だけでは難しい再帰構造に対するマッチングをサポートしているようです．

オプション解析機能だけ必要という人向けに，yargs-parserが用意されています．

## meow

以下はTop5のみですが，小さいものの寄せ集めで作られていることが分かります．yargs-parserとminimist-optionsが一緒に入っているところが面白いです．Node.jsの文化圏の人が作ったんだと思います．

```console
$ npm-diet measure meow | npm-diet show measure --top=5
PACKAGE                       SIZE       %SIZE    #FILES
----------------------------  ---------  -------  ------
semver@5.5.0                   57.09 KB  13.05 %       6
yargs-parser@10.1.0            48.33 KB  11.05 %       6
normalize-package-data@2.4.0   27.38 KB   6.26 %      11
graceful-fs@4.1.11             25.28 KB   5.78 %       7
spdx-correct@3.0.0             21.58 KB   4.94 %       4
----------------------------  ---------  -------  ------
TOP 5                         179.66 KB  41.08 %      34
TOTAL 47                      437.30 KB              220
```

## minimist

オプション解析機能だけなので小さいです．

```console
$ npm-diet measure minimist | npm-diet summary
#PKGS  SIZE      #FILES  #DUPS  DUP  %DUP
-----  --------  ------  -----  ---  ------
    1  30.47 KB      20      0  0 B  0.00 %
```

ちなみに

* yargs-parser: 53.50KB
* nopt: 54.75KB

と他と比べても小さいようです．

# ファイルシステム監視

[chokidar vs gaze vs fb-watchman vs sane vs watch](http://www.npmtrends.com/chokidar-vs-gaze-vs-fb-watchman-vs-sane-vs-watch)

## Chokidar

[昔のgulp.watchの問題](https://qiita.com/masnagam/items/33f4ae8a663539627b94)に遭遇以来，ずっと使っています．

```console
$ npm-diet measure chokidar | npm-diet summary
#PKGS  SIZE     #FILES  #DUPS  DUP        %DUP
-----  -------  ------  -----  ---------  -------
  207  5.49 MB    1325     58  705.14 KB  12.55 %
```

なぜかsource-mapが入っています．．

```console
$ npm-diet measure chokidar | npm-diet show measure --top=3
PACKAGE           SIZE       %SIZE    #FILES
----------------  ---------  -------  ------
source-map@0.5.7  750.73 KB  13.36 %      19
fsevents@1.2.4    657.94 KB  11.71 %      36
nan@2.10.0        401.64 KB   7.15 %      46
----------------  ---------  -------  ------
TOP 3               1.77 MB  32.23 %     101
TOTAL 207           5.49 MB             1325
```

どうやら，使っているパッケージが依存しているようです．

```console
$ npls chokidar -- source-map
npls-20397@1.0.0 $TMPDIR/npls-20397
└─┬ chokidar@2.0.4
  └─┬ braces@2.3.2
    └─┬ snapdragon@0.8.2
      └── source-map@0.5.7
```

bracesというのはBashの[Brace Expansion](https://www.gnu.org/software/bash/manual/html_node/Brace-Expansion.html)に似た機能を提供しているライブラリのようです．このパッケージがsnapdragonという構文解析器作成フレームワークに依存しています．詳しくは確認していませんが，恐らくコンパイル後の位置とそれを生成したhandlerの対応付けを行うのだと思われます．

あと，Top3には入っていませんが，tarも入っています．これはnode-pre-gypというaddon用のヘルパーがtarに，fseventsがnode-pre-gypに依存しているためです．

## gaze

Chokidarの1/3程度のサイズです．~~最新版では問題は修正されているはずなので，こっちを使ったほうがいいかも．~~少なくともmacOSでは，新規追加したファイルが通知されません．Chokidarの使用を推奨します．

```console
$ npm-diet measure gaze | npm-diet summary
#PKGS  SIZE     #FILES  #DUPS  DUP  %DUP
-----  -------  ------  -----  ---  ------
   14  1.52 MB    1111      0  0 B  0.00 %
```

## fb-watchman

パッケージ自身にはファイルシステム監視機能は入っていないため，小さいです．別途Watchmanをインストールする必要があります．

```console
$ npm-diet measure fb-watchman | npm-diet summary
#PKGS  SIZE      #FILES  #DUPS  DUP  %DUP
-----  --------  ------  -----  ---  ------
    3  46.52 KB      12      0  0 B  0.00 %
```

# Web Framework

[connect vs express vs koa](https://www.npmtrends.com/connect-vs-express-vs-koa)

## Connect

Express4からは削除されましたが，今でも現役です．240KB弱と大変小さいです．

```console
$ npm-diet measure connect | npm-diet summary
#PKGS  SIZE       #FILES  #DUPS  DUP  %DUP
-----  ---------  ------  -----  ---  ------
   12  233.08 KB      71      0  0 B  0.00 %
```

実用に耐えうるサーバーが必要な場合は，middlewareを追加することになるので，Expressと比べてもサイズメリットはなくなると思います．

ただ，フロントエンド開発時にちょっとしたサーバーが必要だというときに最適だと思います．例えば，live reload機能付きのサーバーはchokidarを入れても約6.7MBで済みます．Browser-Syncだと26MB強必要です．

```console
$ npm-diet measure connect connect-livereload serve-handler tiny-lr chokidar | \
    npm-diet summary
#PKGS  SIZE     #FILES  #DUPS  DUP        %DUP
-----  -------  ------  -----  ---------  -------
  247  6.74 MB    1661     62  779.73 KB  11.29 %

$ npm-diet measure browser-sync | npm-diet summary
#PKGS  SIZE      #FILES  #DUPS  DUP      %DUP
-----  --------  ------  -----  -------  -------
  290  26.05 MB    3441     43  3.05 MB  11.71 %
```

## Express

約1.5MBと小さいです．

```console
$ npm-diet measure express | npm-diet summary
#PKGS  SIZE     #FILES  #DUPS  DUP       %DUP
-----  -------  ------  -----  --------  ------
   50  1.54 MB     327      3  50.03 KB  3.18 %
```

３つの重複がありますが，どれもraw-bodyに関係しています．

```console
$ npm-diet measure express | npm-diet show dup --package-path
PACKAGE               SIZE      %SIZE    #FILES  PATH
--------------------  --------  -------  ------  -------------------------------------------------
depd@1.1.2            30.77 KB                9  node_modules/depd
--------------------  --------  -------  ------  -------------------------------------------------
depd@1.1.1            30.77 KB  61.50 %       9  node_modules/raw-body/node_modules/depd
--------------------  --------  -------  ------  -------------------------------------------------
TOTAL 1               30.77 KB  61.50 %       9

PACKAGE               SIZE      %SIZE    #FILES  PATH
--------------------  --------  -------  ------  -------------------------------------------------
http-errors@1.6.3     16.57 KB                5  node_modules/http-errors
--------------------  --------  -------  ------  -------------------------------------------------
http-errors@1.6.2     16.39 KB  32.77 %       5  node_modules/raw-body/node_modules/http-errors
--------------------  --------  -------  ------  -------------------------------------------------
TOTAL 1               16.39 KB  32.77 %       5

PACKAGE               SIZE      %SIZE    #FILES  PATH
--------------------  --------  -------  ------  -------------------------------------------------
setprototypeof@1.1.0   3.11 KB                5  node_modules/setprototypeof
--------------------  --------  -------  ------  -------------------------------------------------
setprototypeof@1.0.3   2.87 KB   5.73 %       4  node_modules/raw-body/node_modules/setprototypeof
--------------------  --------  -------  ------  -------------------------------------------------
TOTAL 1                2.87 KB   5.73 %       4
```

raw-bodyの更新がストップしているのが原因みたいです．

```console
$ npm v raw-body dependencies

{ bytes: '3.0.0',
  'http-errors': '1.6.3',
  'iconv-lite': '0.4.23',
  unpipe: '1.0.0' }

$ npm v http-errors version dependencies
version = '1.7.0'
dependencies =
{ depd: '~1.1.2',
  inherits: '2.0.3',
  setprototypeof: '1.1.0',
  statuses: '>= 1.5.0 < 2',
  toidentifier: '1.0.0' }
```

# WebSocket Server

[ws vs faye-websocket](https://www.npmtrends.com/ws-vs-faye-websocket)

## ws

faye-websocketよりも遥かに多くのパッケージ（4000以上）から使われています．

```console
$ npm-diet measure ws | npm-diet summary
#PKGS  SIZE       #FILES  #DUPS  DUP  %DUP
-----  ---------  ------  -----  ---  ------
    2  151.33 KB      30      0  0 B  0.00 %
```

## faye-websocket

wsとの差は26KB程度．tiny-lrが使っているので，併用するならwsではなくfaye-websocketを使ったほうが合計サイズが小さくなります．

```console
$ npm-diet measure faye-websocket | npm-diet summary
#PKGS  SIZE       #FILES  #DUPS  DUP  %DUP
-----  ---------  ------  -----  ---  ------
    4  177.43 KB      52      0  0 B  0.00 %
```

## engine.io

```console
$ npm-diet measure engine.io | npm-diet summary
#PKGS  SIZE       #FILES  #DUPS  DUP  %DUP
-----  ---------  ------  -----  ---  ------
   20  667.88 KB     148      0  0 B  0.00 %
```

wsを含んでいます．

```console
$ npm v engine.io dependencies

{ accepts: '~1.3.4',
  base64id: '1.0.0',
  debug: '~3.1.0',
  'engine.io-parser': '~2.1.0',
  ws: '~3.3.1',
  cookie: '0.3.1' }
```

## socket.io

```console
$ npm-diet measure socket.io | npm-diet summary
#PKGS  SIZE     #FILES  #DUPS  DUP  %DUP
-----  -------  ------  -----  ---  ------
   39  2.50 MB     299      0  0 B  0.00 %
```

engine.ioを含んでいます．

```console
$ npm v socket.io dependencies

{ debug: '~3.1.0',
  'engine.io': '~3.2.0',
  'has-binary2': '~1.0.2',
  'socket.io-adapter': '~1.1.0',
  'socket.io-client': '2.1.1',
  'socket.io-parser': '~3.2.0' }
```