読者です 読者をやめる 読者になる 読者になる

ikeike443のブログ

ソフトウェアビジネスに関心がある系のブログ

Play2 Scala + jacoco4sbt + jenkins でカバレッジを取る

Scala Play! CI Jenkins

Play2 Scalaで作ったプロジェクトをJenkins上で自動テストするのは簡単。フリースタイルジョブで作ってシェルの実行のところに下記のように書いてやれば普通に動く。JUnitスタイルのXMLを吐いてくれるので、テスト結果をJenkins上で綺麗に整形してみることができる。

play clean
play test


でもカバレッジとなると話は別で、Play1の時のようにCoberturaプラグインが用意されてるわけでもなく、上手い方法があるのかどうかよく分からない。

でもって、Scalaカバレッジ計測ができるツールないかなと探してたんだけど、メンテが止まってるのが数個見つかったくらいでいいのがなかった、んだけど、一個いい感じのを見つけた。

jacoco4sbt

https://bitbucket.org/jmhofer/jacoco4sbt/wiki/Home
jacocoの for sbt ということで、sbtプラグインとして書かれている。そこそこメンテもされてるよう。

jacoco4sbtをPlayで動かそう

そのままだと上手く動かないんだけど、下記の記事を参考にすると何とかなる。
http://ronalleva.com/2012/04/25/jacoco-and-play.html

記事の内容としては、jacocoというかsbtはデフォルトだとテストを並列に実行してしまう、けどもPlayは並列実行の設定をオフにしているため、jacocoだけ並列に動こうとして上手くいかないけどどうしたらいいのか、ってもの。

これを見ると、jacoco4sbtをPlayと共存させるための設定方法がよく分かる。(っていうかPeter Hausel*1に聞いた、って記事中にあるね。。)

詳しくは記事を見ればわかると思うけど、参考までに最終的に僕の設定がどうなったかを書いておく。

Build.scala
import sbt._
import Keys._
import PlayProject._
import de.johoop.jacoco4sbt.JacocoPlugin._
import de.johoop.jacoco4sbt.XMLReport
import de.johoop.jacoco4sbt.HTMLReport

object ApplicationBuild extends Build {

  val appName = "Hoge"
  val appVersion = "1.0-SNAPSHOT"

  lazy val s = Defaults.defaultSettings ++ Seq(jacoco.settings:_*)

  val appDependencies = Seq(
    // Add your project dependencies here,
  )

  val main = PlayProject(appName, appVersion, appDependencies, mainLang = SCALA, settings = s ).settings( 
    // Add your own project settings here
    // for jacoco
    parallelExecution in jacoco.Config := false,
    jacoco.reportFormats in jacoco.Config := Seq(XMLReport("utf-8"), HTMLReport("utf-8")),
    jacoco.outputDirectory in jacoco.Config := new File("target/coverage/")

    )

}


Build.scalaに上記のように書いてやれば、jacocoに対していろいろ設定できる。jacoco.settingsをsに追記してやって、そのsをPlayProjectの引数として渡してるね。こんなことできるんだ。。

ここでは記事と同じく parallelExecutionをオフにしたほか、カバレッジレポートのスタイルをXMLとHTMLの2本立てにして*2、レポートの出力先をtarget/coverage/に変更した。

plugins.sbt
// Comment to get more information during initialization
logLevel := Level.Warn

// The Typesafe repository 
resolvers += "Typesafe repository" at "http://repo.typesafe.com/typesafe/releases/"

// Use the Play sbt plugin for Play projects
addSbtPlugin("play" % "sbt-plugin" % "2.0.3")


// jacoco
resolvers += "Sonatype" at "https://oss.sonatype.org/content/groups/scala-tools/"

libraryDependencies ++= Seq(
  "org.jacoco" % "org.jacoco.core" % "0.5.9.201207300726" artifacts(Artifact("org.jacoco.core", "jar", "jar")),
  "org.jacoco" % "org.jacoco.report" % "0.5.9.201207300726" artifacts(Artifact("org.jacoco.report", "jar", "jar"))
)

addSbtPlugin("de.johoop" % "jacoco4sbt" % "1.2.3")

plugins.sbtに、上記のようにjacoco4sdbtの設定を追記。バージョンはこのブログを書いている時点のものなので、適当に読み替えてほしい。


それから、jacocoが吐き出すXMLをJenkinsに解釈させるために、Jenkinsのjacoco Pluginも入れた。

Jenkinsではシェルの実行に下記のような記述をした。

play test
play jacoco:cover

ちなみに、running(TestServer(xxx))を使ってHTTPスタックのテストを書いてカバレッジをとろうとすると上手くいかない。これは今調査中。


Enjoy!

Jenkins

Jenkins

Jenkins実践入門 ?ビルド・テスト・デプロイを自動化する技術 (WEB+DB PRESS plus)

Jenkins実践入門 ?ビルド・テスト・デプロイを自動化する技術 (WEB+DB PRESS plus)

*1:Playのコミッターの一人。

*2:jenkinsに読ませるにはXMLにしてやる必要がある