How am I supposed to mock a nested Java class using scalamock, especially when said nested Java class is coming from a third party library?
Given the following sources:
src/main/java/Outer.java
/**
* Outer class that offers a Nested class inaccessible from Scala :(
*/
public class Outer {
public class Nested {
}
}
src/main/java/UseNestedJavaClassFromJava.java
public class UseNestedJavaClassFromJava {
private Outer.Nested nested;
}
src/main/scala/ImportNestedJavaClass.scala
// TODO uncomment the below line to break the build
//import Outer.Nested
Uncommenting the scala import line results in a compilation failure while compiling UseNestedJavaClassFromJava.java works just fine.
Full minimal example with gradle: https://github.com/billyjf/async-http-client-gradle-scala.
Apparently this was somewhat already addressed in the below question, but resorting to Java glue code or reflection trickery just for the sake of testing Scala code that leverages a Java library with nested Java classes seems a bit unreasonable to me, is there really no other solution?
While I did settle on the following solution, I lucked out in that all I needed currently was a mock.
I suppose reflection would still work in cases where constants need to be accessed in a third party libraries’ nested java class, but wow is that counterintuitive.
Where could I learn more about contributing to Scala’s Java interoperability?
Scalatest Mockito solution:
import org.mockito.Mockito
import org.scalamock.scalatest.MockFactory
import org.scalatest.mockito.MockitoSugar
import org.scalatest.{FlatSpec, Matchers}
class OuterNestedTest extends FlatSpec with MockFactory with Matchers with MockitoSugar {
"Nested Java class" should "be mockable using Mockito from within a scalatest" in {
val mockedNestedJavaClass = Mockito.mock(classOf[Outer#Nested])
Mockito.when(mockedNestedJavaClass.methodWithAParam("some value"))
.thenReturn("mocked", Nil: _*)
mockedNestedJavaClass.methodWithAParam("some value") shouldBe "mocked"
}
}