gruntは、javascriptで書かれたタスクベースのコマンドラインツール。なぜgruntか?
すでにgruntをグローバルインストール済みの場合、
最初にnpm uninstall -g grunt
で削除しておく必要がある。
初めに、gruntのCLIをグローバルインストールする必要がある。windows以外ではsudoで、windowsでは管理者権限で以下のコマンドを実行する。
npm install -g grunt-cli
インストールされたら、grunt
のパスが通り、どこからでも実行可能になる。
grunt-cli
のインストールによってgruntのタスクランナーがインストールされるわけではないことに注意。
grunt-cliが行うことは単純にGruntfileの次にインストールされたバージョンのgruntを実行すること。
従って、複数のバージョンのgruntを同一マシーンにインストールできる。
grunt
を実行すると毎回、nodeのrequire()
によってローカルにインストールされたgruntを探す。
これは、プロジェクトの下層フォルダからでもgruntを実行できるようにするためである。
gruntが見つかったら、ローカルにインストールされたgruntのライブラリを読み込み、Gruntfileの設定を適用し、要求されたタスクを実行する。
実際に何が行われているかを理解するには、このコードを読むと良い。すぐに読める量だから。
一般的な準備は、package.jsonとGruntfileをプロジェクトに追加すること。
-
package.json: このjsonファイルは公開されたnpmモジュールのメタデータを保持してnpmから使うためによく用いられる。gruntやgruntのプラグインをdevDependenciesとして必要に応じてリストに加える。
-
The Gruntfile: Gruntのバージョンが
0.3.x
ならgrunt.js
かgrunt.coffee
、0.4.x+
ならGruntfile.js
かGruntfile.coffee
の名前でつくる。 このファイルは設定、タスクの定義およびプラグインの読み込みのために用いる。
package.json
はプロジェクトのルートに、Gruntfileと同じく配置し、プロジェクトのソースとしてコミットされるべき。
package.json
があるディレクトリでnpm install
を実行すると、package.json
に記述されたnpmがインストールされる。
package.jsonの生成方法はいくつかある。
{
"name": "my-project-name",
"version": "0.1.0",
"devDependencies": {
"grunt": "~0.4.0",
"grunt-contrib-jshint": "~0.1.0",
"grunt-contrib-nodeunit": "~0.1.0"
}
}
gruntとgruntのプラグインをpackage.json
に追加する最も単純な方法はnpm install <module> --save-dev
を実行すること。
ローカルにmodule
をインストールするだけでなく、tilde version rangeを用いてdevDependenciesセクションに追加する。
例えば、以下は最新のgruntをプロジェクトにインストールし、devDependenciesに追加する。
npm install grunt --save-dev
同様のことがgruntプラグインや他のnode moduleにも可能。package.jsonを更新したらプロジェクトと一緒にコミットすることを必ず行うべき。
Gruntfile.js
、もしくはGruntfile.coffee
はpackage.json同様にプロジェクトのルートに配置し、プロジェクトのソースと一緒にコミットすべき。0.4.0
以前のバージョンのgruntを使っている場合は、grunt.js
かgrunt.coffee
の名前でつくる。
Gruntfileは以下の要素から成る。
- ラッパー関数
- プロジェクト・タスクの設定
- プラグインとタスクの読み込み
- カスタマイズしたインラインのタスク
以下のGruntfileではプロジェクトのメタデータがpackage.jsonからgruntの設定にインポートされ、grunt-contrib-uglify pluginのuglify
コマンドがソースのミニファイとメタデータを用いて動的にbannerコメントを生成するように設定されている。
module.exports = function(grunt) {
// プロジェクトの設定
grunt.initConfig({
pkg: grunt.file.readJSON('package.json'),
uglify: {
options: {
banner: '/*! <%= pkg.name %> <%= grunt.template.today("yyyy-mm-dd") %> */\n'
},
dist: {
src: 'src/<%= pkg.name %>.js',
dest: 'dist/<%= pkg.name %>.min.js'
}
}
});
// uglify taskを提供するプラグインを読み込む
grunt.loadNpmTasks('grunt-contrib-uglify');
// デフォルトのタスク
grunt.registerTask('default', ['uglify']);
};
全てのGruntfile(とgruntのプラグイン)はこの形式を用いる。gruntのコードの記述はこの関数内でなければならない。
module.exports = function(grunt) {
// gruntに関するコードはこの中で
};
殆どのgruntのタスクはgrunt.initConfigに渡されたオブジェクトで定義された設定に依存する。
以下の例では、grunt.file.readJSON('package.json')
はpackage.jsonに保持されたJSONメタデータをgruntの設定にインポートしている。テンプレートの記述<% %>
は全ての設定を参照できるので、ファイルのパスやファイル群の設定を繰り返さずに済ませられる。
configuration Objectの中ではどのようなデータでも設定できる。タスクの設定値と競合した場合は無視される。
JavaScriptのファイルなのでJSONの形式に限定されることもない。正しいJavaScriptはいくらでも記述できる。必要ならプログラムで設定を生成も可能。
殆どのタスクのようにgrunt-contrib-uglify pluginのuglify
タスクは同じ名前で定義された設定を予期している。
以下のように、オプションbanner
は、ミニファイしたソースを記述する対象ファイルとuglifyの対象ファイルを定義したdist
とともに定義されている。
// プロジェクトの設定
grunt.initConfig({
pkg: grunt.file.readJSON('package.json'),
uglify: {
options: {
banner: '/*! <%= pkg.name %> <%= grunt.template.today("yyyy-mm-dd") %> */\n'
},
dist: {
src: 'src/<%= pkg.name %>.js',
dest: 'dist/<%= pkg.name %>.min.js'
}
}
});
minifyやconcat、lintといった共通してよく使われるタスクはgruntのプラグインとして存在する。
package.jsonにdependencyとして定義され、npm install
コマンドでインストールされたプラグインはGruntfileに簡単なコマンドを記述して使うことができる。
// uglifyタスクを提供するプラグインを読み込む
grunt.loadNpmTasks('grunt-contrib-uglify');
外部のJSファイルに定義されたタスクはgrunt.loadTasksで読み込み可能。
Note: `grunt --help'で利用可能なタスクの一覧を表示できる。
gruntのプラグインが提供するタスクのみを利用するプロジェクトの場合、カスタマイズしたタスクの定義は不要。
オプションを指定せずにgrunt
コマンドだけを実行した際に、デフォルトの挙動に加えて何か行いたい場合にデフォルトのタスクを設定する必要がある。
そのためには、alias taskを設定すればよい。以下のようにするとgrunt
もしくはgrunt default
を実行した際にuglifyタスクも実行される。これは機能上`grunt uglify'と同様のこと。
// デフォルトのタスク
grunt.registerTask('default', ['uglify']);
一つのコマンドで複数のタスクを続けて実行したい場合、必要ならオプションを指定して配列に追加すれば良い。
// プロジェクトをビルドする
grunt.registerTask('default', ['jshint', 'concat', 'uglify']);
事前に用意したタスクが不要な場合や外部のフォルダからカスタマイズしたタスクを読み込みたくない場合、Gruntfileの中で定義できる。 以下は、タスクの設定も利用しない単純なGruntfileの例。
module.exports = function(grunt) {
// かなり基本的なデフォルトのタスク
grunt.registerTask('default', 'Log some stuff.', function() {
grunt.log.write('Logging some stuff...').ok();
});
};
- Installing gruntは、開発中/公開されているgrunt/grunt-cliのインストールに関して詳細な情報が見られる。
- Configuring Tasksは、テンプレートの説明や幾つかのパターン、外部のデータ等を用いてGruntfileのタスク、対象、オプションに関する深い説明が見られる。
- Creating Tasksはタスクの形の違いを列挙し、タスクと設定のサンプルを数多く記述している。
- より多くのタスクのカスタマイズやプラグインについての情報は、developer documentationで確認できる。