Webpackとはビルドツールの1つであり、モジュール管理ツールとしての側面も持っています。フロントエンドのビルドツールとしては、他にGulpとGruntなどがありますが、それらの仲間といった感じだと思います。Webpackは主にJavaScript用のビルドツールです。
WEBアプリケーションは、HTML、CSS、JavaScript、画像ファイル、webフォントなどのファイル(アセット)で構成されています。webpackはこれらのWEBアプリケーションを構成するファイルを「モジュール」単位で取り扱い、最適な形に集約するツールです。JavaScriptの言語仕様において、もともとモジュールを取り扱うための仕組みがないため、これまでにモジュールを取り扱うための様々な仕様が検討され、その仕様ごとにモジュール管理の仕組みが提供されてきた経過があります。代表的な仕様にCommonJS、AMD、ES2015等があり、その実装にはBrowserify、RequireJS、SystemJS(複数の仕様対応)などが存在しており、いずれも一長一短です。webpackは複数のモジュール仕様のメリットを採用しつつ、モジュールを簡潔に使用する仕組みがあります。
JavaScriptのモジュール管理は、最初、サーバサイドJavaScriptで使用されてきましたが、ブラウザではそのままで使用する事ができず、ブラウザが解釈できる形に変換する必要があります。そこで登場するのがwebbpackであり、JavaScriptモジュールをブラウザで扱える形に変換してくれます。webpackの設定はwebpack.config.jsというJavaScriptファイルを作成します。
また、webpackは、JavaScriptだけではなくスタイルシート、画像、webフォント、音声、動画などのあらゆるリソースファイルをモジュールとして集約して取り扱うことが可能です。JavaScriptファイル以外のファイルを扱うには、webpackのLoader機能を用いることで対応します。
webpackはあらゆるファイルを一つのファイルに結合することで、ファイルのリクエスト数が減少し、ページ読み込みの速度向上が見込めます。その他にも、webpackにはモジュール化したファイルのダウンロードを最適化する機能があります。
(1)モジュールの分割読み込みが可能(必要になったタイミングでモジュールを読み込むことができる)。
(2)バイナリファイルのbase64化を選択可能。
Webpackの基本機能
Webpackの要点をまとめてみると、以下の通りです。
- 主にJavaScriptをビルドするために使う。
- entryでコンパイル元を指定して、outputで出力先を指定する。
- Loaderという仕組みがあり、それでES6やReactをコンパイルできる。
- Pluginという仕組みがある。
「entryから読み込んでoutputへ出力する」がWebpackの基本的な流れです(それ以外は全てオプション項目)。Webpackが便利と言われるローダー(Loader)とプラグイン(Plugin)を用いることで様々なコンパイルを行うことが可能になります。
Webpackの処理の流れとしては、以下の通りです。
- entryに指定されたファイルを読み込む。
- 読み込む際にLoaderを経由して変換する(例:BabelLoaderでES6をES5に変換する)。
- 処理の前後でプラグインが実行される(実行タイミングなどはプラグインごとに異なります)。
- output先にビルド結果を出力する entry〜outputまでの間に色々と処理を行うための仕組みとして、LoaderとPluginが用意されています。
webpack.config.jsについて
webpack を使った JS/CSS のビルドを行う場合のJavaScriptの設定ファイルです。
(entry)
複数の定義が可能で、ビルドの起点となるファイルのパスを指定します。entry は文字列で単一のファイル名を指定することも、Array型またはObject型で複数のファイルを指定することもできます。複数指定する場合は、Object型だと出力ファイルも複数になりますが、Arrayだと出力されるファイルは1つに集約可能です。
(output)
output.path に出力先のパスを、output.filename に出力ファイル名を指定するのが一般的な設定方法です。entryにObject型を渡して複数のエントリーポイントを指定した場合、出力も複数のファイルになりますが、その場合、 filename に [id] や [name] などの変数を使用します。outputでその property名を使用して、動的に名前付けを行うことで問題解決できます。
1 2 3 4 5 6 7 8 |
entry: { main: './app/main.js', list: './app/list.js' }, output: { filename: '[name].bundle.js', path: '/dist' } |
上記のような設定をすることで main.bundle.jsとlist.bundle.jsの2ファイルが、destに指定したディレクトリに置かれることになります。
(module)
loadersの指定で、対象のファイルを変換するためにloaderを指定します(最も重要な機能であるLoadeです)。Loaderを用いて様々なコンパイルを行うことができます。Webpackの大きな特徴として、js以外のファイルでもloaderさえ使えば読み込むことができることです。modules.loadersはArray型になっており、Array型の要素は以下の項目を持った Objectになります。
- test : ビルド対象(Loader を適用するファイル)を指定します。正規表現が使えます。
- include, exclude : ビルド対象に含める/除外するファイルを指定します。正規表現が使えます。
- loader または loaders : 適用する loader の名前を指定します。xxx-loader の -loader 部分は省略可能です
(resolve)
extentionsの指定で、requireやimportを記述する時に拡張子を省略できるようになります。省略してビルド対象に含めたい(requireしている)ファイルの拡張子をArray型で指定します。例えば、foo.js を require('foo') というように拡張子なしで読み込みたい場合は、「'.js'」 を指定する必要があります。逆にデフォルト値以外の拡張子のファイルを require('myfile.ext') というように拡張子付きで読み込みたい場合、空文字列を指定する必要があります。※空文字列を指定するとエラーになるので指定していない。
rootの指定で、requireで読み込むときのルートpathを指定します。配列で複数の指定が可能になります。『webpack2でresolve.rootが使えなくなった』ようなので、注意が必要です。
(devtool)
デバッグのための SourceMap の出力を設定することができます。SourceMap とはビルド前後の JS ファイルの対応関係情報を持ったファイルで、これを出力するとブラウザの開発者ツールなどでビルド前のコードを参照することができます。デバッグ機能に使用されています(『Chromeを使ったAngular-cliのオンラインデバッグの方法についてhttp://www.ifelse.jp/blog/angular2-env-20』
(devServer)
webpack-dev-serverの設定を行います。contentBaseはWEBサーバのルートディレクトリを、portはHTTPのポート番号を指定します。