minitestのオススメ基本設定調べてみた

## はじめに

さて、みなさん、railsでテスト書いていらっしゃるでしょうか？
私は、普段、rspecでshouldを書いて地味なイライラが溜まっています。
rspec3の新文法expectも括弧地獄の辛みが凄くて、Kernel#shouldとかいう劇薬なモンキーパッチングでもこの方がマシと感じて移行しませんでした。

さて、そういう人間なもので***テストのためのシステムにメタプログラミングをするのはあまり好きではない***という理由でminitestを調べてみたのですが、正直関連するgemが本当にたくさんある割に情報が整理されていない感じがしたので、ちょっと全てのgemを調べてその***「まとめ」***を公開させて頂きます。

## 標準構成

結論から言うと、minitest自体は結構良く出来ているので、多くを求めないならminitest本体とminitest-railsだけでもそれなりに使えます。
ですが、やっぱり色分けだったり、rspec便利に使っていたのに、minitesで無いというモノは導入を行って、今は次の様な構成を基本にしています。

```rb
group :test do
  # 必須
  gem "minitest"
  gem "minitest-rails"
  gem "minitest-rails-capybara" # capybaraで結合テストできるようにする

  # レポートの書式を変更する
  gem "minitest-doc_reporter" # テスト結果の表示を整形

  # 機能追加系
  gem "minitest-stub_any_instance" # メソッドmockを追加できる様にする

  gem "minitest-bang" # let!文のサポートを追加

  gem "factory_girl" # DBのデータのモックを作成
end 
```

minitestがrspecと違う所は、それぞれのgemが小さな機能を提供しあって全体を構成する最小主義なので、上の構成を柱にしてから次の順番でカスタマイズをかけていくのが良いと思います。

1. テスト結果のフォーマッタを好きなものに取り変える
2. テストの書式を好きな様にカスタマイズを行う(慣れてからで良い)
3. 拡張機能の一覧から好きなものを選ぶ(慣れてからで良い)

ですのでここからは、用途別にgemとその選別結果を出させて頂きましょう。

あ、使い方に関しては他に良記事が

## テスト結果のフォーマッタ　

minitestで一番カスタマイズの効果が現れやすいのはコレでしょう。
結果表示のためのgemは次の３つです。

 * [minitest-reporters](https://github.com/kern/minitest-reporters)
 * [minitest-doc_reporter](https://github.com/jasonthompson/minitest-doc_reporter)
 * [minitest-documentation](https://github.com/teoljungberg/minitest-documentation)

これにそもそもカスタマイズを行わないで標準のままにしておく、という４択のうちで、気に入ったものを選んで使ってみるのが良いでしょう。


一応それぞれの結果を簡単に紹介させて頂きます。

### minitest-reporters

![minitest-reporters.png](https://qiita-image-store.s3.amazonaws.com/0/10715/ca02db05-c8f2-16bc-c0f3-cc70a1f1ff33.png)

テストの結果をプログレスバーでパーセント表示してくれます。
rspecでも[foobar](https://github.com/jeffkreeftmeijer/fuubar)の様に類似のgemがありますね

minitest標準の形式ではテストケースがとてつもない量になったときに、スクロールが発生してしまうので、一定して一画面内でテストを終わらせたい時に便利な表示形式だと思います。

### minitest-doc_reporter

![minitest_doc-reporter.png](https://qiita-image-store.s3.amazonaws.com/0/10715/584765dd-70a5-5daa-a50b-ebee94dbb9fe.png)

上記の通りrspecで

```
rspec spec --format documentation
```

のオプションで実行したときに近い表示形式です。
[RSpec ベストプラクティス](http://magazine.rubyist.net/?0032-TranslationArticle)でも推奨されている形式ですし、私はこれを好んで使っているので、今回はこれを標準にしました。
テストを実行中に何処で転んだのかを確認出来る形式なので、テスト実行終了を待たずに行動を開始できる等利点も多いフォーマットです。

欠点は表示される情報量が多いので一覧性に欠ける事でしょうか。

### minitest-documentation

![minitest-documentation.png](https://qiita-image-store.s3.amazonaws.com/0/10715/0b2c2b33-8988-6af3-e935-ce4dc05855ed.png)

minitest-doc_reporterと同じ様にドキュメント形式での表示になります。
少しだけ表示の感じが違いますが、どちらを選ぶかは好みでしょうか。

他にも表示周りのgemがありますので一応紹介しておきます。

| 名前 | 説明 |
|-----|------|
| [minitest-reporters](https://github.com/kern/minitest-reporters) | 上記３つの書式とほぼ同じものを設定で切り替えられます。他のgemと相性問題を起こしがちなので、あえて外しましたが使用感は悪くない感じです |
| [minitest-emoji](https://github.com/tenderlove/minitest-emoji) | 進捗を絵文字で表示してます、ネタ実装ですね |

## テスト書式変更

minitestは標準では、assert_equalでの書式しか用意していません。
そこからどの様にテストを書きたいのかをカスタマイズして行くのが、minitestの本領と言えると思います。

ですが分量が大きくなるので、別記事に切らせていただきました

[minitestのオススメ設定調べてみた(アサーション編)](http://qiita.com/baban@github/items/a43b66f29a7d1c52ab63)

## その他のgem

その他にもminitestには実に多様なgemが存在します。
rspecでもsporkやguard等のgemがそれぞれ愛されてきましたが、minitestの経済圏はrspecのそれを超えています。

それらを一通り分類して紹介させて頂きましょう。

### assetation文法追加

通常はassert_equalでチェックをすべきものですが、JSONの書式が想定通りか、想定したディレクトリにファイルが出来ているか等のチェックを簡潔に書くためのおすすめ書式があります。

必要に応じて導入しながら、minitestの世界の多様性を感じて頂くには一番良い用途だと思います。

| 名前 | 説明 |
|-----|------|
| [minitest-activemodel](https://github.com/frodsan/minitest-activemodel)   | active record のvalidationのチェックを簡潔に記述するためのassert関数の追加を行います |
| [minitest-ar-assertions](https://github.com/steventux/minitest-ar-assertions) | active recordのhas_many等の関連のチェックを簡潔に記述するためのassert関数の追加を行います |
| [minitest-filesystem](https://github.com/stefanozanella/minitest-filesystem)    | ファイルが意図した場所にあるかどうかをチェックするためのDSLを追加します |
| [minitest-mongoid](https://github.com/frodsan/mongoid-minitest) | active recordのチェックでは対応しきれないmongoidのフィールドチェックのためのgemです |
| [mongoid-minitest](https://github.com/frodsan/mongoid-minitest) | 上のminitest-mongoidと用途が同じです |
| [json_expressions](https://github.com/chancancode/json_expressions) | jsonの中の書式が意図通りかを非常に簡潔な書式でチェックできます。必ずしもminitest依存ではないですが、相性も良いですし紹介できないのが惜しいので掲載 |


### 通知周り

rspecではテストの実行が終了したときにgrowlで通知を行う仕掛けが存在しました、minitestではlinuxでも対応させる事が出来ます。
実は動作確認をとれていなかったりする所があるのですが、一応紹介させて頂きましょう。

| 名前 | 説明 |
|-----|------|
| [minitest-nc](https://github.com/stalcottsmith/minitest-nc) | Macの通知センター対応 |
|[minitest-growl](https://github.com/jnbt/minitest-growl) | MacのGrowl対応 |
| [minitest-libnotify](https://github.com/splattael/minitest-libnotify) | Linux(GNOME)の通知センター対応 |

### 対応環境追加

minitestの実行環境は当たり前ですがrailsだけに縛られません。
その間口の広さからcapistranoやmacrubyでも使えます。

* [minitest-capistrano](https://github.com/fnichol/minitest-capistrano)
* [minitest-macruby](https://github.com/seattlerb/minitest-macruby)

### Mock関連

開発初期に、役に立つモックは4種類ありましたが、これは個人的に「[minitest-stub_any_instance](https://github.com/codeodor/minitest-stub_any_instance)」一択で、コレ以外は特に検討する必要は無いのではないかと考えています。
理由はそれぞれのgemで提供している機能や書式がどれもそこまでは違わなかったので、インストールが一番楽なものが一番良いと考えたからです。
違う種類のgemを試すのは慣れてからで良いでしょう。

 * [minitest-stub_any_instance](https://github.com/codeodor/minitest-stub_any_instance)
 * [minitest-rspec_mocks](https://github.com/codeodor/minitest-rspec_mocks)
 * [minitest-stub-const](https://github.com/adammck/minitest-stub-const)
 * [minitest-firemock](https://github.com/cfcosta/minitest-firemock)

## 追記

minitestですが、実際に使ってみた感想としては
その最大の強みは、多様性からの環境適応能力の高さだと感じました
rspecと違って、地殻変動に追随しやすいので、今後新しいテストのパラダイムにが登場しても、無理なく適応できることでしょう
現状では、その多様性を使いこなせばrspecよりは確実に便利になりますが
現在溜まっているrspecの資産を全て書き直そうと思うだけのメリットまでは感じませんでした
新規案件であれば迷わずrspecを捨ててminitestで始めるという感じですね

正直、他にも紹介したいgemはあるのですが今回はここで一旦切らせて頂きましょう

[minitestのGitHubリポジトリ](https://github.com/seattlerb/minitest)にはまだまだ紹介できていないgemが記載されていますし、その中にはrspecで愛されてきたguardやsporkのminitest版も含まれていますし、それ以外のものも多数存在しています

ただ、minitestの経済圏もまだまだ安定しているとは言いがたい状態で、minitestの最新版に追随できていないgemも多い状態でしたし
gem同士が競合を起こして、挙動が意図しないものになるという経験もしました

※ 具体的にはminitest-aroundとminitest-reportersのgemが競合して、実行に失敗しました。また、minitest-doc_reporterを入れているとsimplecovでカバレッジを出したときの結果がおかしくなりました

こういう競合等を回避しつつ構成を作ったのが最初に紹介した標準構成です。
minitest自体はまだまだ変化と可能性を含んだフレームワークですので、一緒に発掘してくださる方を募集中です

※ この記事は、以下のスライドの拡張版です
http://www.slideshare.net/matsubaramasanao/minitest