Allied ArchitectsAllied ArchitectsEngineer Blog

Play Framework(Play2)(Scala)のTips Part2:Specs2とMockitoでテストを書く(Advent Calendar 8日目)

2014/12/8 Scala

この記事はアライドアーキテクツAdvent Calendar 8日目の記事です。

どうも。謎の刺客Tarou Yamadaさんにカレンダーを乗っ取られてしまった伊藤(係長)です。
気を取り直して、今回はSpecs2とMockitoを使ったユニットテストのお話を書きます。

■Specs2とは
Scala用のテスティングフレームワークです。BDD(振る舞い駆動開発)スタイルでテストケースを
記述する事ができます。
詳しくはこちらをご覧ください。

■Mockitoとは
簡単に言うとテスト時に邪魔になる(依存している)クラスをモック(ハリボテ)にして、
単体テストを書きやすくするモックフレームワークです。
詳しくはこちらをご覧ください。

■前提
こんな実装があったとして、HogeServiceのテストを書こうとします。

Fuga.scala

HogeService.scala

見ての通り、HogeService#doSomething()はFugaオブジェクトに依存しています。
そのままテストを書いて実行しようとすると、毎回DB接続が必要になってしまいます。
これではあまりよろしくないので、Fugaクラスをモックにします。

■モック化の準備
では早速Fugaをモックにしましょう、と行きたいところですが、
HogeServiceとFugaはobjectとして定義されています。
objectとは、Scalaで簡単にシングルトンを定義できるキーワードですね。
手軽にシングルトンを定義できるので、結構多用している方も多いのではないでしょうか。
このままではHogeServiceで使用しているFugaをモック化して差し込む事ができません。
(objectはモック化する事ができません。)
そこで、実装を次の通りに変更します。

Fuga.scala

HogeService.scala

実装の本体をclassで定義して、それを継承したobjectを定義しました。
HogeServiceでは、依存しているFugaをvalでフィールド定義します。
こうする事でFugaをモック化してHogeServiceに差し込む事が可能となります。
(※他にもやり方は何通りかあると思いますがその一例です。)

■テストコード
ここまででモックしてテストコードを書く準備が整いましたので、
実際にテストを書いてみます。

HogeServiceSpec.scala

これでOKです。
Fuga#findById()とFuga#update()はモック化されていますので、DB接続は行われません。
ここではFuga#update()が正しい引数で呼ばれている事を確認しています。

■spy
Mockitoにはspyというスバラシイ機能があります。
これは、テスト対象のクラスの一部分だけモック化できるというものです。
(パーシャルモックと言います)
実際のコードを見てみましょう。

Hoge.scala

isHogeの結果は、isFugaかisPiyoの結果で決まります。
そのままisHogeをテストしようとすると、設定ファイルとDBを見に行ってしまうので
あまりよろしくありません。

■テストコード
spyを使う事で次のように書く事ができます。
HogeSpec.scala

これで同一クラス内に定義されている関数をダマして、設定ファイルやDBを見に行かなくてもテストできるようになりました。

今回紹介したのはSpecs2、Mockitoの機能の内、ほん〜の一部だけですので、
実際触って見て色々試してみると良いと思います。

明日は、最近乗りに乗っているGit大佐こと大佐の番です!!!

  • cobonas
  • プログラマ
  • 元Javaプログラマ。現在はScala/PlayでWeb開発と、SwiftでiOSアプリ開発をしています。 Unitテストとか書いてる時が一番楽しかったりします。

RELATION ENTRY

Play Framework(Play2)(Scala)のTips Part3:Akkaを使った非同期/バッチ処理(Advent Calendar 20日目)

Play Framework(Play2...

2014/12/20 Scala

この記事はアライドアーキテクツAdvent Calendar 20日目の記事です。 どうも。伊藤(係長)です。 今日は他の方に乗っ取られる事もなく無事に書くことができます。 今回はAkkaを使った非同期処理やバッチ処理についてです。 通常、非同期処理をJavaとかで書こうと思ったら、ちょっとメン...

続きを読む

Play Framework(Play2)(Scala)のTips Part1:フォームのマッピングあれこれ

Play Framework(Play2...

2014/06/4 Scala

お久しぶりです。伊藤(係長)です。 最近、PHPでの開発を一旦休業しまして、ScalaでPlayFramework(Play2)を 使ったWebアプリの開発を始めました。 というわけで今後は主にPlay2とかScalaとかの記事を書いていこうと思います。 最初は初級編という事で、Co...

続きを読む

cobonasの記事一覧へ

ページTOPへ