環境構築:webpackを拡張
まだまだ環境構築は続く・・・か。口癖になりそう・・・
昨日インストールしたwebpackを自分の環境に併せて拡張していきます。
ディレクトリ構造
自分の開発環境のディレクトリ構造は大体下記の感じです。
. # ドキュメント・ルート
└─ nananomae.xyz # バーチャルホストに設定したドキュメント・ルート
├─ dev
│ ├─ js
│ │ └─ # JavaScriptファイル群
│ └─ scss
│ └─ # SCSSファイル群
├─ node_modules
│ └─ # webpackが使用するモジュール群
├─ package.json
├─ public
│ ├─ index.html
│ └─ assets
│ ├─ js
│ │ └─ # 出力されるJavaScript群
│ └─ css
│ └─ # 出力されるCSS群
└─ webpack.config.js
実行環境
webpack.config.jsを編集
上記した通りの構造で開発を進めていくにあたって、webpack.config.js
を編集します。
重要なのは、エントリポイントを複数持つということです。
webpack.config.js
// output.pathに絶対パスを指定する必要があるため、pathモジュールを読み込む
const path = require('path');
module.exports = {
entry: {
index: './dev/js/index.js',
blog: './dev/js/blog.js',
...
},
output: {
path: path.join( __dirname, 'public/assets/js' ),
filename: '[name].js'
}
};
entry
エントリポイントとは、モジュール間の依存関係の解析を開始するポイントのこと。
output
出力するパスやファイル名を指定する。
※filename:
の値[name]
はエントリポイントで指定したオブジェクトのキーになります。
package.jsonを編集
$ webpack
コマンドを実行する際にモードを切り替えれるように設定します。
package.json
"scripts": {
"test": "echo "Error: no test specified" && exit 1",
- "build:dev": "webpack --mode=development",
+ "build": "webpack --mode=production",
+ "build:dev": "webpack --mode=development --watch"
},
$ npm run build
コマンドは公開モードとして実行し、$ npm run build:dev
コマンドは開発モードとして実行し、ターミナルを抜けるまで関連するファイルが変更されるたびに$ webpack
コマンドが実行されるようにします。
Loaderを導入
Babel Loader
ECMAScript 2015+を使えるようにするためBabel Loaderを下記のコマンドで必要なパッケージをインストールします。
$ npm install babel-loader @babel/core @babel/preset-env --save-dev
+ @babel/core@7.8.7
+ babel-loader@8.0.6
+ @babel/preset-env@7.8.7
added 126 packages from 40 contributors and audited 7137 packages in 6.675s
無事にインストールが完了したらwebpack.config.js
にBabel Loaderの設定を追加します。
webpack.conig.js
...
// ローダーの設定
module: {
rules: [
{
test: /¥.js$/,
exclude: /node_modules/,
use: [
loader: 'babel-loader',
options: {
presets: [
'@babel/preset-env'
]
}
]
},
]
}
上記の設定で、$ webpack
コマンドを実行すれば、ECMSScript2015+で書かれたJavaScriptをどのブラウザでも動作するように変換してくれます。
Sass Loader
中間言語Sassを使えるようにするためSass Loaderを下記のコマンドでインストールします。
$ npm install sass-loader sass style-loader css-loader --save-dev
+ css-loader@3.4.2
+ sass-loader@8.0.2
+ style-loader@1.1.3
+ sass@1.26.2
added 22 packages from 51 contributors and audited 9446 packages in 3.594s
無事にインストールが完了したらwebpack.config.js
にSass Loaderの設定を追加します。
webpack.conig.js
...
// ローダーの設定
module: {
rules: [
...
{
test: /¥.scss$/,
use: [
'style-loader',
{
loader: 'css-loader',
options: {
url: false,
importLoaders: 2
}
},
{
loader: 'sass-loader',
options: {
sourceMap: true,
}
}
]
},
]
}
上記の設定で.scss
ファイルに対して、use
配列で指定したLoaderが後ろから順番に適用されます。
Loaderを使用してSassを読み込むには、エントリポイント内でimport
文で下記のように記述します。
index.js
import '../scss/style.scss';
...
ただ、この状態で$ webpack
コマンドを実行しても、スタイルシートのベンダープレフィックスは付与されていません。
PostCSS Loader
AndroidやIE 11等への対応を考えると、ベンだープレフィックスは必須です。webpack単体で弁だープレフィックスを付与する機能はないため、PostCSS Loaderを下記のコマンドでインストールします。
$ npm install postcss-loader autoprefixer --save-dev
+ autoprefixer@9.7.4
+ postcss-loader@3.0.0
added 20 packages from 22 contributors and audited 9545 packages in 3.961s
無事にインストールが完了したらwebpack.config.js
にPostCSS Loaderの設定を追加します。
webpack.conig.js
...
devtool: "source-map",
// ローダーの設定
module: {
rules: [
...
{
test: /¥.scss$/,
use: [
...
{
loader: 'postcss-loader',
options: {
sourceMap: true,
plugins: [
require('autoprefixer')({})
]
}
},
...
]
},
]
}
上記の設定で、CSSにベンダープレフィックスが付与されるようになります。
ただ、この状態で$ webpack
コマンドを実行しても、出力されるファイルは.js
ファイルのみです。
Pluginを導入
MiniCssExtractPlugin
次に、出力されるファイルは.js
ファイルと.css
ファイルに分割したいので、MiniCssExtractPluginを下記コマンドでインストールします。
$ npm install mini-css-extract-plugin --save-dev
+ mini-css-extract-plugin@0.9.0
added 7 packages from 3 contributors and audited 9472 packages in 3.221s
無事にインストールが完了したらwebpack.config.js
にMiniCssExtractPluginの設定を追加/置き換えます。
webpack.conig.js
...
const MiniCssExtractPlugin = require('mini-css-extract-plugin');
...
// ローダーの設定
module: {
rules: [
...
{
test: /¥.(sa|sc|c)ss$/,
use: [
MiniCssExtractPlugin.loader,
{
loader: 'css-loader',
options: {
url: false,
importLoaders: 2
}
},
{
loader: 'postcss-loader',
options: {
sourceMap: true,
plugins: [
require('autoprefixer')({})
]
}
},
{
loader: 'sass-loader',
options: {
sourceMap: true,
}
}
]
},
]
},
plugins: [
new MiniCssExtractPlugin({
filename: '../css/styles.css'
})
]
上記の設定で.js
ファイルと.css
ファイルを別々に出力できるようになりました。
Vueの導入
Vue.js
の導入は別記事「Instagramの写真埋め込みスクリプトをVueにしてみました。」で説明済みなのでそちらを参考に。