webpackの基本的な使い方(+Vue.js)

今まで自分で作ったプロジェクトは、ファイルは基本的な以下の3つで作成され、

ライブラリはVue.jsをインストールしているだけでした。 Vue.jsはBowerでインストールし、CSS,JavaScriptファイル(とVue.js)はHTMLから読み込んでいました。

実際にWeb開発をする、となった場合もっとたくさんのライブラリを使うだろうし、HTML,CSSコンパイルが必要なAltなんとかを使うこともあるでしょう。

今回のような単純なプロジェクトでは恩恵はあまりないかもしれませんが、モダンなWeb環境構築には慣れておかないといけないため、 webpack を利用してみることになりました。

やりたいこと

以下のような3つのファイルを用意します。Vue.jsを使って、p要素に赤文字の"hoge"が出力されるだけのページです。

<!DOCTYPE html>
<html lang="ja">
<head>
    <meta charset="utf-8">
    <title>webpack test</title>
</head>
<body>
  <div id="app">
    <p>{{text}}</p>
  </div>
  <script type="text/javascript" src="js/app.js"></script>
</body>
</html>
/** reset **/
html, body, div, form, fieldset, legend, label {
  margin: 0;
  padding: 0;
}

table {
  border-collapse: collapse;
  border-spacing: 0;
}

th, td {
  text-align: left;
  vertical-align: top;
}

h1, h2, h3, h4, h5, h6, th, td, caption {
  font-weight:normal;
}

img {
  border: 0;
}

/* style */
#app p {
  color: #d33;
}
var vm = new Vue({
  el: '#app',
  data: {
      text: "hoge"
  }
});

ディレクトリ構成はこのようになっています。

├── css
│   └── style.css
├── index.html
├── js
│   └── app.js
└── node_modules

上記の形から、vue.js部分を外出しして、以下のようにします。

  • app.htmlとapp.cssを追加
.
├── app.css
├── app.html
├── css
│   └── style.css
├── index.html
├── js
│   └── app.js
└── node_modules
  
  • app.html
<div id="app">
  <p>{{text}}</p>
</div>
/* style */
.test {
  color: #d33;
}

これから切り出したapp部分をwebpack側で読み込んで管理するようにします。 こうしておけばたとえHTMLやCSSが膨大になっても、機能単位で切り分けされてるので今後の開発がやりやすくなるでしょう!

webpackを使う前にpackage.jsonを作成してVue.jsをインストールしておきます。

npm init
npm install vue --save

インストール

webpackのインストールは、適当なプロジェクト用のディレクトリを作って、 npmコマンドでインストールします。

npm install webpack --save-dev

webpackのような開発用のツールは、本番環境では使わないので、-devオプションをつけて、package.jsonのdevDependenciesに追記されるようにします。

  "devDependencies": {
    "webpack": "^1.10.5"
  }

ひとまずwebpackコマンドが使えるようになりましたが、実際にあるファイルをパス指定してコマンド実行するのは面倒くさいので、グローバルにもインストールしておきます。

npm install webpack -g

webpackをプロジェクトで利用する準備

webpackは指定したJavascriptファイルをコンパイルして、そのコードをそのまま含むバンドルファイルを作成します。 このバンドルファイル、 bundle.jsによって依存関係などを気にせず開発ができるようなので、とりあえずindex.htmlで読み込むようにしておきましょう。 また、Vue.jsを読み込む部分と、app.jsの読み込む部分は今後webpackから読み込むので削除します。

<!DOCTYPE html>
<html lang="ja">
<head>
    <meta charset="utf-8">
    <!-- <script type="text/javascript" src="js/vue.min.js"></script> -->
    <link rel="stylesheet" type="text/css" href="css/style.css">
    <title>webpack test</title>
</head>
<body>
  <div id="app">
    <p>{{text}}</p>
  </div>
  <!-- <script type="text/javascript" src="js/app.js"></script> -->
  <script type="text/javascript" src="js/bundle.js"></script>
</body>
</html>

さらに、app.jsにVue.jsを読み込む記述を追加します。

var Vue = require('vue');

var vm = new Vue({
  el: '#app',
  data: {
      text: "hoge"
  }
});

とりあえず実行する

webpack js/app.js js/bundle.js

こちらを実行すると、webpackによってtodo.jsがコンパイルされてbundle.jsが作成されます。 成功すると以下のようなステータスが表示されます。

Hash: 49d346fa536be96181b6
Version: webpack 1.10.5
Time: 42ms
    Asset     Size  Chunks             Chunk Names
bundle.js  1.46 kB       0  [emitted]  main
   [0] ./js/app.js 70 bytes {0} [built]

ブラウザ上でもちゃんとvue.jsの処理も動いているのが確認できます。

設定ファイルの作成

webpackコマンドに引数でファイルを指定するのは面倒なので、 webpack.config.js を作って、webpackだけでコンパイル可能にしておきます。

module.exports = {
  entry: './js/app.js',
  output: {
    path: __dirname,
    filename: './js/bundle.js'
  }
};

これで、javascriptはとりあえずwebpackで管理されるようになりました。

HTML, CSSも管理する

やりたいこと で書いてあることと同様、app.htmlとapp.cssを作って、元ファイルから被るコードは削除しておきます。

  • index.html
<!DOCTYPE html>
<html lang="ja">
<head>
    <meta charset="utf-8">
    <script type="text/javascript" src="js/vue.min.js"></script>
    <link rel="stylesheet" type="text/css" href="css/style.css">
    <title>webpack test</title>
</head>
<body>
  <!--
  <div id="app">
    <p>{{text}}</p>
  </div>
  -->
  <!-- <script type="text/javascript" src="js/app.js"></script> -->
  <script type="text/javascript" src="js/bundle.js"></script>
</body>
</html>
/** reset **/
html, body, div, form, fieldset, legend, label {
  margin: 0;
  padding: 0;
}

table {
  border-collapse: collapse;
  border-spacing: 0;
}

th, td {
  text-align: left;
  vertical-align: top;
}

h1, h2, h3, h4, h5, h6, th, td, caption {
  font-weight:normal;
}

img {
  border: 0;
}

/* style */
/*
#app p {
  color: #d33;
}
*/

HTML, CSS用ローダーのインストール

webpackデフォルトではHTML, CSSを読み込めないので、専用のモジュールをインストールしておきます。 ここでも --save-devオプションは指定しておきます。

$ npm install --save-dev html-loader css-loader style-loader

設定ファイルでモジュールを読み込む

webpack.config.jsにモジュールを読み込む記述が必要です。

module.exports = {
  entry: './js/app.js',
  output: {
    path: __dirname,
    filename: './js/bundle.js'
  },
  module: {
    loaders: [
      { test: /\.html$/, loader: 'html?minimize' },
      { test: /\.css$/, loader: "style!css" }
    ]
  }
};

JavaScriptでHTML, CSSを読み込む

app.jsにHTMLとCSSを読み込む記述を追加します。 相対パスであることに注意してください。

var html = require('../app.html')
document.body.innerHTML = html;

require('../css/style.css');
require('../css/app.css');

var Vue = require('vue');

var vm = new Vue({
  el: '#app',
  data: {
      text: "hoge"
  }
});

webpackコマンド

これで、ファイルを切り分けても無事元と同じ画面が出力されるようになりました。 最後に、webpackコマンドは webpack —watch として実行することによって、ファイルの更新を監視することができます。そうしておけば、ファイルを更新してまたコマンドを打たなくても、webブラウザのリロードだけで確認できるようになります。

gitで管理する場合

webpack --watchしていると、bundle.jsはどんどん更新されていてgitでは面倒なことになるので、.gitignoreに記述しておきましょう。