KOJIKA17

Web制作で面倒な作業を自動化するビルドツール、Grunt v0.4 入門

Webサイトの表示速度を気にすると、CSSやJavaScriptのminify、gzip、CSS Sprite、画像の最適化などの面倒な作業が発生します。
さらにメタ言語などを使用すると、複数のツールを使用しなければならないケースも出てきます。
それらの作業をまとめて自動化してしまう、Grunt.jsが面白かったので備忘録もかねて紹介します。

Grunt.jsとは?

Grunt.jsは、サーバーサイドJavaScriptのNode.jsを使用したCUIのビルドツールです。 タスクを設定しておき、それらを自動化します。
コマンドプロンプトやターミナルなど、いわゆる「黒い画面」を使います。

Grunt.jsののバージョンは0.4.1です。
バージョンが0.3から0.4になったことで、大きく仕様が変わりました。 Grunt.js v0.4ではgrunt-cliをインストールしてプロジェクトごとにGruntやプラグインをインストールして使用します。

プラグインをインストールすることによって、様々なタスクを行うことができます。 具体的に以下の例が挙げられます。

  • サーバーをたてる
  • 構文チェック
  • ファイルの結合
  • 特定のフォルダ、ファイルの複製、削除
  • メタ言語のコンパイル(Jade, CoffeeScript, TypeScript, Sass(Compass), Less, Stylusなど)
  • HTML, JS, CSSなどをminify
  • JS, CSSをgzipに圧縮
  • CSS Spriteの自動生成
  • 画像最適化
  • LiveReload(ファイルを保存すると勝手にブラウザが更新される)
  • スタイルガイドの生成

上記に挙げた例は一部です。
プラグインをインストールしたり、タスクを自分で書くことによって、自分にあった開発環境を整えることができたり、コマンドひとつで様々なタスクを自動化させることもできます。

インストール

grunt.jsをインストールする手順です。

Node.jsのインストール

まずはNode.jsがなければ始まりません。
Node.jsの公式サイトから、Windows, Mac, Linuxのインストーラーが提供されています。
CUIに慣れていない人は、まずはこちらからインストールすれば楽かもしれません。

Node.js

インストールすると、コマンドプロンプトやターミナルでNode.jsが使用できる状態になります。

grunt-cli のインストール

Node.jsがインストールできたら、ここから黒い画面といわれている、CUIを触ることになります。

Windowsは、キーボードで [win]+[r]を押して、「ファイル名を指定して実行」で cmd を入力。コマンドプロンプトが起動するはずです。

Macは、アプリケーション > ユーティリティからターミナルを起動します。
(デフォルトは黒くない)

コマンドプロンプトやターミナルから、grunt-cli をインストールします。

Win

npm install -g grunt-cli

Mac

sudo npm install -g grunt-cli

上のコマンドを記述したら、Enterを押してみてください。
Windowsは、そのままインストールが始まります。
Macの場合はパスワードが求められますのでMacのアカウントのパスワードを入力後、インストールが始まります。

黒い画面

grunt-cliのインストールが終わったら、黒い画面でプロジェクトのフォルダ(作業フォルダ)まで移動する必要があります。
黒い画面の使い方を復習します。

黒い画面でWinは、

cd C:\

Macは、

cd ~/

と入力してEnterを押してみてください。
Winは、Cドライブに移動。
Macは、ホームディレクトリに移動できます。

次にWinは

dir

Macは、

ls

と入力してください。
今いるディレクトリに含まれている、フォルダ、ファイルを表示します。
そこから、さらに移動したい場合

cd [移動したいフォルダ名]

また以下のコマンドを使用して、プロジェクトのディレクトリまで移動してください。

cd
カレントディレクトリの変更
dir | ls
ディレクトリのファイルの一覧表示
mkdir
ディレクトリの作成
矢印キー ↑↓
記述したコマンドの履歴を表示できます。地味に便利。

Grunt.jsを使ってみる

下準備ができましたので、ここからGrunt.jsの設定を行います。

Grunt.js v0.4にはまず基本となるファイル、package.json と Gruntfile.js(Gruntfile.coffee)が必要になります。

プロジェクトのディレクトリの構造は以下のように想定します。

project
├css
│├base.css
│└style.css
├package.json
└Gruntfile.js

package.json

黒い画面で作業フォルダまで移動したら、package.jsonを生成します。
黒い画面にて

npm init

と入力してください。
黒い画面のまま対話式に聞いてきますので、必要な情報を入力してください。
プロジェクトに必要な情報を記述するjsonファイルが生成されます。もしエラーになる場合は、package.jsonというファイルを空で用意して、再度コマンドを打ってみてください。

package.json

{
  "name": "test",
  "version": "0.0.0",
  "description": "test",
  "main": "Gruntfile.js",
  "scripts": {
    "test": "echo \"Error: no test specified\" && exit 1"
  },
  "repository": "",
  "author": "kojika17",
  "license": "BSD"
}

生成されたこのままの状態では、package.jsonを生かせません。

npm install grunt --save-dev

上記のコマンドを黒い画面に打ってください。
--save-devをつけると、package.jsonにインストールした情報が記述が追加されます。
なお npm install grunt は、gruntをインストールしろ、という指示です。node_modulesというフォルダが生成され、その中にgruntがインストールされます。

さらにプラグインも入れたいと思います。
プラグインは、grunt-contribを入れておけば色々ごにょごにょできます。
grunt-contribの内容は以下の通りです。

  • grunt-contrib-clean
  • grunt-contrib-coffee
  • grunt-contrib-compass
  • grunt-contrib-compress
  • grunt-contrib-concat
  • grunt-contrib-connect
  • grunt-contrib-copy
  • grunt-contrib-cssmin
  • grunt-contrib-csslint
  • grunt-contrib-handlebars
  • grunt-contrib-htmlmin
  • grunt-contrib-imagemin
  • grunt-contrib-jade
  • grunt-contrib-jasmine
  • grunt-contrib-jshint
  • grunt-contrib-jst
  • grunt-contrib-less
  • grunt-contrib-livereload
  • grunt-contrib-nodeunit
  • grunt-contrib-qunit
  • grunt-contrib-requirejs
  • grunt-contrib-sass
  • grunt-contrib-stylus
  • grunt-contrib-uglify
  • grunt-contrib-watch
  • grunt-contrib-yuidoc

数が多いので、ここでは細かく解説はしません。grunt-contribの概要

grunt-contribをインストールすれば色々使えるようになりますが、解説のために個別でインストールします。

ファイルが更新された自動感知して処理を実行する grunt-contrib-watch
cssファイルの改行やコメントを削除してファイルサイズを少なくする grunt-contrib-cssmin
この2つを個別にインストールします。
以下のコマンドを黒い画面に打ってください。

npm install grunt-contrib-watch grunt-contrib-cssmin --save-dev

node_modulesの中の上記のプラグインがインストールされ、package.jsonにはその情報が記述されているのが確認できるはずです。

package.json

{
  "name": "test",
  "version": "0.0.0",
  "description": "test",
  "main": "Gruntfile.js",
  "scripts": {
    "test": "echo \"Error: no test specified\" && exit 1"
  },
  "repository": "",
  "author": "kojika17",
  "license": "BSD",
  "devDependencies": {
    "grunt": "~0.4.1",
    "grunt-contrib-watch": "~0.3.1",
    "grunt-contrib-cssmin": "~0.4.2"
  }
}

このインストールしたnode_modulesは、プロジェクト毎に必要です。
プロジェクトがたつたびに、使用するプラグインを黒い画面で npm install grunt ~ などを1つ1つインストールするのは面倒です。

そこでpackage.jsonを使用します。
node_modulesフォルダを削除して、黒い画面で以下のコマンドを入力してください。

npm install

package.jsonのdevDependenciesにプラグインなどの情報が書かれていれば、必要なプラグインを一括でインストールできます。
インストールが終わったら、node_modulesのフォルダを見てみてください。
プラグインがインストールされているのが確認できると思います。

package.jsonに必要なプラグインを書いておけば、コマンド1つでインストールできるので、他のプロジェクトに使いまわす場合も楽になります。

Gruntfile.js

package.jsonの説明をしましたが、それだけでは動きません。
タスクを実行するGruntfile.jsが必要になります。

package.jsonと同じフォルダに、Gruntfile.jsというファイルを作成してください。

Gruntfile.jsを開いて、以下の記述してください。

module.exports = function(grunt) {
  grunt.initConfig({
  
  });
};

これが基本になります。

Gruntfile.jsの書き方

package.jsonに書かれている、grunt-contrib-cssminとgrunt-contrib-watchを使用します。
プラグインはインストールしたままでは動きません。

loadNpmTasksを使用して、プラグインを読み込みます。

module.exports = function(grunt) {
  grunt.initConfig({
    
  });

  grunt.loadNpmTasks('grunt-contrib-cssmin');
  grunt.loadNpmTasks('grunt-contrib-watch');
};

プラグインを読み込んだら、grunt.initConfigの中に設定を記述します。

module.exports = function(grunt) {
  grunt.initConfig({
    cssmin: {
      compress: {
        files: {
          './min.css': ['css/base.css', 'css/style.css']
        }
      }
    },
    watch: {
      files: ['css/*.css'],
      tasks: ['cssmin']
    }
  });

  grunt.loadNpmTasks('grunt-contrib-cssmin');
  grunt.loadNpmTasks('grunt-contrib-watch');
};

ここまでできたら、黒い画面にてGruntfile.jsのフォルダまで移動して、以下のコマンドを入力してください。

grunt cssmin

base.css と style.css は改行やコメントアウトが削除されて、なおかつmin.cssという1つのファイルに結合されるはずです。

次はcssフォルダの中のスタイルシートが保存されれば、自動的に [cssmin] というタスクが実行されるようにします。
黒い画面にて、以下のコマンドを入力してください。

grunt watch

cssファイルを一部変更して保存してみてください。
cssファイルが監視されているので、保存されると自動的にcssmin が実行されます。

今回は数が少ないですが、このやり方だと複数のタスクを順番に実行するのが面倒です。
よく使用するタスクをGruntfile.jsに登録しておきます。

module.exports = function(grunt) {
  grunt.initConfig({
    cssmin: {
      〜 省略 〜
    },
    watch {
      〜 省略 〜
    }
  });

  grunt.loadNpmTasks('grunt-contrib-cssmin');
  grunt.loadNpmTasks('grunt-contrib-watch');

  // 追記
  grunt.registerTask('default', ['cssmin', 'watch']);
};

下の方に、registerTaskを追加しました。
defaultと設定すると黒い画面で

grunt

上のコマンドだけで、登録しているタスクを順番に実行することができます。

プラグインの自動読み込み

Grunt.jsの簡単な説明しました。
ただプラグインを複数インストールして、Gruntfile.jsにloadNpmTasksを書かなければならないのは、非常に面倒です。

npm install grunt --save-dev などで、せっかくpackage.jsonにプラグインの情報が書き込まれているので、これを生かします。
module.exports = function(grunt) {

  // ここに追加
  var pkg = grunt.file.readJSON('package.json');

  grunt.initConfig({
    cssmin: {
      〜 省略 〜
    },
    watch {
      〜 省略 〜
    }
  });

  // loadNpmTasksを変更
  var taskName;
  for(taskName in pkg.devDependencies) {
    if(taskName.substring(0, 6) == 'grunt-') {
      grunt.loadNpmTasks(taskName);
    }
  }

  grunt.registerTask('default', ['cssmin', 'watch']);
};

grunt.file.readJSON()を使ってpackage.jsonを読み込み、loadNpmTasksをごにょごにょします。 こうしておけば、package.jsonのdevDependenciesに書かれているプラグインを勝手に読み取ってくれます。
プラグインを試したりする場合、こうしておくと便利です。

Gruntfile.coffee

Grunt v0.4では、GruntfileをCoffeeScriptで書くこともできます。
Gruntfile.coffeeで書くと、コンマなどを省略できるようになるので記述が楽になるかもしれません。

module.exports = (grunt) ->
  pkg = grunt.file.readJSON 'package.json'
  grunt.initConfig

  # config
    stylus:
      compile:
        src: 'stylus/style.styl'
        dest: './style.css' 
    
    cssmin:
      compile:
        src: '<%= stylus.compile.dest %>'
        dest: 'style.min.css'
		
    watch:
      files: ['stylus/*.{styl, stylus}']
      tasks: ['stylus', 'cssmin']
  
  # loadNpmTasks
  # package.jsonから読み込んでるもの
  # grunt-contrib-stylus, grunt-contrib-cssmin, grunt-contrib-watch
  for taskName of pkg.devDependencies when taskName.substring(0, 6) is 'grunt-'
    grunt.loadNpmTasks taskName
	  
  grunt.registerTask 'default', ['stylus', 'cssmin', 'watch']

気になること

2014-03-12 LiveReloadについて

grunt-contrib-livereloadは、非推奨になりました。
LiveReloadの機能は、grunt-contrib-watchに組み込まれましたので、optionsで設定して下さい。

サーバーについては、grunt-contrib-connectを利用することも可能ですが、MAMPなどもそのまま利用できます。

ただし、Google Chromeなどのエクテンションなどを入れた状態で利用して下さい。

module.exports = (grunt) ->
  pkg = grunt.file.readJSON 'package.json'
  grunt.initConfig
    
    watch:
      options:
        livereload: 35729
      html:
        files: ['./*.html']
        tasks: ['']

  for taskName of pkg.devDependencies when taskName.substring(0, 6) is 'grunt-'
    grunt.loadNpmTasks taskName
    
  grunt.registerTask 'default', ['watch']

最後

プラグインはGruntの公式サイトで探せます。
JSが書ける人なら、自分で書いたタスクを読み込ませることもできます。

Gruntは、CSS Preprocessorのコンパイルからgzip化、JSのminifyからブラウザをリロードまで、様々なものを自動化できます。
それだけ聞けば、「それなんてCodeKit」と言われそうですが、Grunt.jsの場合はOSを選ばずに環境を構築できるのが魅力です。

今回は入門っぽく書いたので、狭く浅い紹介になり、Gruntの凄さが伝わりにくいと思いますが、自動化できるのは大変便利です。
Sassなどで挫折した人も、黒い画面に再挑戦してみてはいかがでしょうか?
きっと制作の手法が広がると思います。