Webpackのコンパイル速度改善HardSourcePlugin

##Webpackとは？

（今更ですが、）そもそもwebpackは、モジュール（js,sassなど）をひとつに束ねるツールです。
バンドル（bundle：束、束ねる）することで、様々なメリットを得ることができます。

メリット
・コードの可読性が上がる
・保守性を高められる
・コードを他プロジェクトに転用しやすくなる
・JSのみでなく、CSSや画像もバンドルできる
・包括的な開発環境が整う（開発作業分担やテストも容易になる）

大変わかりやすくまとめている方がいらしたので詳細は以下をご参照ください。
https://qiita.com/kamykn/items/45fb4690ace32216ca25


##コンパイル時間短縮プラグイン

コンパイルに時間を要するケースに直面し、改善する方法について調査したところ、
大幅な短縮結果を上げたという実例が多かったものを紹介します。
当方の開発環境でも実証済みです。

・HardSourcePlugin
中間キャッシュを生成し、それを再利用してビルド時間を短縮するプラグインです。
元記事によると70％もコンパイル時間を短縮できるとのこと。

以下2ステップで導入可能です。

①HardSourcePluginをインストール

```
npm install --save hard-source-webpack-plugin
```

②webpack.config.js に追記

```
// webpack.config.js

var HardSourceWebpackPlugin = require('hard-source-webpack-plugin');

module.exports = {
  context: // ...
  entry: // ...
  output: // ...
  plugins: [
    new HardSourceWebpackPlugin()
  ]
}
```

##元記事翻訳


以下、元記事を翻訳しました。
（若干直訳調なので読みにくかったらすみません）

0~100を2秒に-webpackを高速化

問題

ESアプリケーションが大きくなるほどbundleのビルドは長くなる。何も驚くことはない。

意外にも（少なくとも著者には）、webpackのキャッシュは期待しているほどうまく機能しない。ほとんど変更のないnode_modlesのバンドリングでさえも。
CommonsChunkPluginに分けたbundleを入れたとしても-単にnode_modulesがビルドされる。

下記で、ローカルの開発環境とCIのようなサードパーティを改善する方法を紹介する。


考えられる解決策

Webpack cache
https://webpack.github.io/docs/configuration.html#cache

インクリメンタルビルドの改善が目的なので、役に立たない。これはウォッチモードの更新を高速化するもので、起動を早くはしない。よって解決はしない。


HappyPack
https://github.com/amireh/happypack

ただのキャッシュでなく、デフォルトでキャッシュの選択肢をもっている。HappyPackはbuildプロセスを複数スレッドで立ち上げる。

かなりよさそうに見える。しかし、実際のところは、、、不適切にバリデートされたキャッシュの問題が発生する。
頻度はそれほどでないが、無視できないくらいには。。。

我々がコンフィグを十分いじれていなくて、他ではうまくいっている人もいるのは認める。HappyPackの内部の大きな仕組みがそれを裏付けるに違いない。でも、次紹介する２つでは、少ない設定でより良い結果を出すことができた。


DLL

https://github.com/webpack/docs/wiki/list-of-plugins#dllplugin

平均25%削減
DLLを使うと、node_modulesをたった一回ビルドすれば、node_modulesを変更するまでは忘れてOK。
次回からは、コンパイルされたdll-bundleからmodulesを再利用してWebpackがビルドされる。

node_modules意外にも機能するのが嬉しいところ。appのどこか一部をdll-bundleに入れてもいい。ほとんど変更のないコードやモジュールを見つけた？dll-bundleにぶち込もう。時間節約だ。

DllPluginを使う際、唯一注意すべきなのは、npm packageからimportする場合はpackage.json:mainが無視されinportされたファイルにフルパスを指定されることだ。これが意味するのは、dll-bundleがビルドされた後、manifest.jsonではreduxのようなインポートパスの変わりに/redux/es/index.js.ようなパスが発見できることだ。
これにより、アプリのインポートパスが破損する。
これを解消するためには、変更されたmanifest.jsonコンテンツをDLLReferencePluginに渡す必要がある。


HardSourcePlugin

騎兵隊がやってきた！

https://github.com/mzgoddard/hard-source-webpack-plugin


発端は、この [スレッド]
(https://github.com/webpack/webpack/issues/250#issuecomment-240643985p)でwebpackキャッシュの問題について議論が始ったことだ。そして、ビルドプロセスのパフォーマンスを大幅に向上させるキャッシングプラグイン作成へとつながった。この作者はWebpackソースに深く入り込み、生産的なキャッシングのソリューションを見つけた。必ずスレッドを読んだほうがいい。

ほとんどデフォルトの構成の状態でも、HardSourcePluginは大規模なアプリケーションでのビルドを40秒から10秒に短縮する。優れたハードウェアがを備え、同じアプリを2秒以内に構築する者もいる。そして、これまでのところ、HardSourcePluginに深刻な問題は見つかっていない。


解決策

DllPLuginとHardSourcePluginを組み合わせれば、長いビルドを忘れることができる。本当に。これは、ローカルの開発者環境でも、CIなどのサードパーティでも同様だ。

CIの問題は、ビルド間でアプリケーションコードが大幅に変更される可能性があるため、無効化の問題が発生する可能性が高くなる。
このような問題を解決すると、CIサーバーのキャッシュディレクトリがクリーンアップされ、キャッシュなしでビルドプロセスが再度開始される。これには時間がかかる。

CIでHardSourcePluginを実行した場合に無効化の問題にどの程度の頻度で出くわすかは不明だが、知りたいとは本気で思っている。実際の本番環境でテストし、良好な結果が得られた場合は、すべての一般的なCIのセットアップの説明記事に書き込むつもりだ。


参考：
https://qiita.com/kamykn/items/45fb4690ace32216ca25
https://medium.com/ottofellercom/0-100-in-two-seconds-speed-up-webpack-465de691ed4a