3

最近、Specs2への依存関係をプロジェクトに追加しましたが、ScalaTestとMockitoで作成された既存のテストの一部が失敗したことに気付きました。Specs2が削除されると、これらのテストは再び合格しました。なぜこれが起こるのですか?

lazy val scalatestandspecscoexisting = Project(
  id = "scalatest-and-specs-coexisting",
  base = file("."),
  settings = Project.defaultSettings ++
    GraphPlugin.graphSettings ++
    Seq(
    name := "Scalatest-And-Specs-Coexisting",
    organization := "com.bifflabs",
    version := "0.1",
    scalaVersion := "2.9.2",
//  libraryDependencies ++= Seq(scalaTest, mockito)   //Tests Pass, no-specs2
    libraryDependencies ++= Seq(scalaTest, specs2, mockito)  //Tests Fail
  )
)

失敗したテストはすべてMockitoを使用し、すべてが2つの異なるパラメーターを使用してモックメソッドをセットアップしました。モックへの呼び出しの1つは、設定された値を返しません。以下の例は失敗します。さらなる要件は、タイプがFunction1である(またはapplyメソッドを持っている)必要があることでした。

import org.scalatest.FunSuite
import org.scalatest.mock.MockitoSugar
import org.mockito.Mockito.when

trait MockingBird {
  //Behavior only reproduces when input is Function1
  def sing(input: Set[String]): String
}

class MockSuite extends FunSuite with MockitoSugar {

  val iWannaRock = Set("I wanna Rock")
  val rock = "Rock!"

  val wereNotGonnaTakeIt = Set("We're not gonna take it")
  val no = "No! We ain't gonna take it"

  test("A mock should match on parameter but isn't") {

    val mockMockingBird = mock[MockingBird]
    when(mockMockingBird.sing(iWannaRock)).thenReturn(rock)
    //Appears to return this whenever any Set is passed to sing
    when(mockMockingBird.sing(wereNotGonnaTakeIt)).thenReturn(no)

    // Succeeds because it was set up last
    assert(mockMockingBird.sing(wereNotGonnaTakeIt) === no)
    // Fails because the mock returns "No! We ain't gonna take it"
    assert(mockMockingBird.sing(iWannaRock) === rock)
  }
}

出力:

 [info] MockSuite:
 [info] - A mock should match on parameter but isn't *** FAILED ***
 [info]   "[No! We ain't gonna take it]" did not equal "[Rock!]" (MockSuite.scala:38)
 [error] Failed: : Total 1, Failed 1, Errors 0, Passed 0, Skipped 0
4

1 に答える 1

2

編集-以下のEricのコメントによると、これはSpecs2≤1.12.2のバグです。1.12.3で修正する必要があります。

Specs2は、名前によるパラメーターを一致させるために、Mockitoの動作の一部を再定義していることがわかりました。

エリックは私の質問に答えました

「私はこれが好きではありませんが、それが名前によるパラメーターと一致することがわかった唯一の方法です: http ://bit.ly/UF9bVC 。あなたはそれを望むかもしれません。」

Specs2ドキュメントから

名前で

名前によるパラメーターは検証できますが、specs2 jarがクラスパスの最初に、mockito jarの前に配置されていない場合、これは機能しません。実際、specs2は、メソッド呼び出しをインターセプトするためにMockitoクラスを再定義して、bynameパラメーターが適切に処理されるようにします。

テストに再び合格するために、specs2のドキュメントで提案されているのとは逆のことを行い、Mockitoの後にSpecs2の依存関係を追加しました。試したことはありませんが、名前によるパラメータの一致は失敗すると思います。

lazy val scalatestandspecscoexisting = Project(
  id = "scalatest-and-specs-coexisting",
  base = file("."),
  settings = Project.defaultSettings ++
    GraphPlugin.graphSettings ++
    Seq(
    name := "Scalatest-And-Specs-Coexisting",
    organization := "com.bifflabs",
    version := "0.1",
    scalaVersion := "2.9.2",
//  libraryDependencies ++= Seq(scalaTest, mockito)   //Tests Pass
    libraryDependencies ++= Seq(scalaTest, mockito, specs2)  //Tests Pass
//  libraryDependencies ++= Seq(scalaTest, specs2, mockito)  //Tests Fail
  )
)

私のテストは合格しました

[info] MockSuite:
[info] - A mock should match on parameter but isn't
[info] Passed: : Total 1, Failed 0, Errors 0, Passed 1, Skipped 0
于 2012-11-01T02:58:07.060 に答える