フロントエンド片手間ンによる Laravel Elixir 入門

## この記事も若干古くなってきましたので…

[他のフレームワークでも使える Laravel-Elixir](http://localdisk.hatenablog.com/entry/2015/11/20/212236) という記事を書きました。入門から設定値の上書きの仕方まで。

この記事を書いた頃は `browserify` や `browserSync` できなかったですが、今はできますよ。！

## はじめに
この記事は、フロントエンド片手間ンである [@localdisk](http://twitter.com/localdisk) が `Laravel Elixir` を使ってみた記録です。頑張りました。

## 注意点
Laravel5 はおそらく来年のリリースになります。以下のコードは `Laravel Framework version 5.0-dev` で書かれました。
筆者の環境は

- Mac OS X 10.9.5
  - HomeBrew を使用している

当エントリに書かれたコードはすべて動作確認をしていますが、筆者はフロントエンド片手間ンなのでもっと効率のよい方法や勘違いがあるかもしれません。そういった記述がある場合はコメント等でご指摘いただければ幸いです。

## Laravel Elixir is 何
`Laravel Elixir` は Laravel 用に作られた `gulp` タスク群。フロントエンド(CSS/JS) と バックエンド(Laravel) をうまいこと繋いでくれます。

## で、何ができるの?
標準で用意されてるのは以下のとおり

- less コンパイル
- sass コンパイル
- CoffeeScript コンパイル
- CSS/JS minify & 結合
- CSS/JS のバージョニング
  - バージョニングされた CSS/JS を View に反映するヘルパー

いわゆるアセットパイプラインが実現できます。他にも

- PHPUnit/PHPSpec を自動的に実行
- route/event スキャンコマンドの実行
  - ここらへんは[昨日のエントリ](http://qiita.com/ytake/items/1c6eb4aae06aaad554aa)が詳しいぞ

といったことができます。もちろん gulp なので `gulp watch` も。便利。

もう少し機能はありますが割愛。興味のある人は [readme.md](https://github.com/laravel/elixir/blob/master/readme.md) を参照して下さい。

## 前準備
さて、それでは早速試してみましょう。まずは環境を整えます。

### Node.js

```sh:command
$ brew install node
$ npm -v
2.1.9
```

### gulp

```sh:command
$ npm install -g gulp
$ gulp -v
CLI version 3.8.10
```

### bower

```sh:command
$ npm install -g bower
$ bower -v
1.3.12
```

### Laravel5

```sh:command
$ composer create-project laravel/laravel laravel5 dev-develop --prefer-dist
```

### Laravel Elixir

```command
$ cd NetBeansProjects/laravel5
$ npm install
```

## 始めてみよう
おや、Laravel のホームディレクトリに `bower.json` がありますね。bower はフロントエンド専用のパッケージマネージャとのこと。

```js:bower.json
{
  "name": "Laravel Application",
  "dependencies": {
    "bootstrap-sass-official": "~3.3.1",
    "font-awesome": "~4.2.0"
  }
}

```

なるほど。bootstrap と font-awesome に依存すると書かれていますね。インストールしておきましょう

```sh:command
$ bower install
```

上記コマンドを実行すると `vendor/bower_components` 以下にインストールされます。標準ですと `components` にインストールされます(ですよね?)が `bowerrc` に以下のように定義されているためです。

```js:bowerrc
{
  "directory": "vendor/bower_components",
  "scripts": {
    "postinstall": "gulp publish"
  }
}

```

### gulpfile.js
`Laravel Elixir` の操作は `gulpfile.js` を編集 + コマンドを叩くことで行います。

```javascript:gulpfile.js
var elixir = require('laravel-elixir');

/*
 |--------------------------------------------------------------------------
 | Elixir Asset Management
 |--------------------------------------------------------------------------
 |
 | Elixir provides a clean, fluent API for defining some basic Gulp tasks
 | for your Laravel application. By default, we are compiling the Sass
 | file for our application, as well as publishing vendor resources.
 |
 */

elixir(function(mix) {
    mix.sass('app.scss')
       .publish(
            'jquery/dist/jquery.min.js',
            'public/js/vendor/jquery.js'
        )
       .publish(
            'bootstrap-sass-official/assets/javascripts/bootstrap.js',
            'public/js/vendor/bootstrap.js'
        )
       .publish(
            'font-awesome/css/font-awesome.min.css',
            'public/css/vendor/font-awesome.css'
        )
       .publish(
            'font-awesome/fonts',
            'public/css/fonts'
        );
});
```

なるほどなるほど。`resources/assets/sass/app.scss` をコンパイルして、bower でインストールした jQuery/Bootstrap/font-awewome を `public` 以下に publish しているようです。

```sh:command
$ gulp
```

してみると出力されましたね。では少し編集してみましょう。毎回 `gulp` コマンドを叩くのは面倒なので `gulp watch` しましょう。こうしておけば、編集されたら自動的にタスクが走ります。


### CSS/JS の minify


ちなみに `gulp` コマンドに `--production` オプションをつけると

```sh:command
$ gulp --production
```

CSS/JS が minify されます。


### CSS/JS の結合、バージョニング
各々、`styles`, `scripts` を使えば OK です。もしくは `scriptsIn` や `stylesIn` もありますが、結合順を制御できないようなきがするので `styles`, `scripts` を使いましょう。こんな感じです。結合すると all.js(css) というファイル名になるようです。

```javascript:gulpfile.js

var elixir = require('laravel-elixir');

/*
 |--------------------------------------------------------------------------
 | Elixir Asset Management
 |--------------------------------------------------------------------------
 |
 | Elixir provides a clean, fluent API for defining some basic Gulp tasks
 | for your Laravel application. By default, we are compiling the Sass
 | file for our application, as well as publishing vendor resources.
 |
 */

elixir(function(mix) {
    // 結合
    mix.styles([
            'public/app.css',
            'public/css/vendor/font-awesome.css'
        ])
        .scripts([
            'public/js/vendor/jquery.js',
            'public/js/vendor/bootstrap.js'
        ])
        // バージョニング
        .version([
            'css/all.css',
            'js/all.js'
        ]);

});
```

上に書いてますが `version` 関数を呼ぶと `all-{ハッシュ値}.js(css)` という名前のファイルが `public/build/` 以下に出力されます。ここには `rev-manifest.json` というファイルも出力されており、このファイルを参照して Laravel 本体の helper である `elixir` 関数がビルドされた js(css) のパスを出力します。

```php:index.php
<?= elixir('css/all.css') ?>
// -> /build/css/all-feda974a.css
<?= elixir('js/all.js') ?>
// -> /build/js/all-d1b9950f.js
```


## その他のタスク
その他便利タスク。特に PHP に関するもの。


### route scan

`route:scan` コマンドを `Laravel Elixir` から実行する。

```javascript:gulpfile.js
elixir(function(mix) {
    mix.routes();
});
```

### event scan

`event:scan` コマンドを `Laravel Elixir` から実行する。

```javascript:gulpfile.js
elixir(function(mix) {
    mix.events();
});
```

### PHPUnit

```javascript:gulpfile.js
elixir(function(mix) {
    mix.phpUnit();
});
```

### PHPSpec

```javascript:gulpfile.js
elixir(function(mix) {
    mix.phpSpec();
});
```


## おう機能が足らねーよ。どうなってんだあくしろよ
大丈夫だ。拡張できる

```js:index.js
var elixir = require("laravel-elixir");
var gulp   = require("gulp");
var shell  = require("gulp-shell");

elixir.extend("message", function(message) {

     gulp.task("say", function() {
         gulp.src("").pipe(shell("say " + message));
     });

     return this.queueTask("say");

 });
```

みたいな感じ作って `require` してやればよい。[npmjs.org から laravel-elixir を検索する](https://www.npmjs.org/search?q=laravel-elixir)と色々出てくるぞ。

## まとめ

駆け足だけど、`Laravel Elixir` の紹介をしてみました。いい感じにはかどるのでぜひ使ってみてください。

`Laravel Elixir` ですが、いくつか使えないタスク(routesやevents)を除けば Laravel4 でも動くと思います。そこらへんは後日ブログに書いてみようかと思います。

明日は [ytake](http://qiita.com/ytake) さんの [Laravel5 Testing, use Contracts](http://qiita.com/ytake/items/eab27f60e756f9a0abcd) です。お楽しみに！