I am trying to write units tests in Groovy/Spock and have to test the below code.
public class ClassA {
@Inject
private ClassB classB;
@Inject
private ClassC classC;
@Inject
private ClassD classD;
public void update(final int a, final Map<String, Object> b) {
classB.executeCommand(classC.callToMethodInClassC(), new InterfaceE<Void>() {
@Override
public Void execute() {
classD.update(a, b);
return null;
}
});
}
}
Now when I write test code I am unable to reach classD.update(a, b);
line. I know how to inject mocks/real object for ClassB, ClassC, ClassD, but unable to reach that statement. Please help.
Note: ClassA.update()
& ClassD.update()
have no relation between them except that their signatures match.
Make your classB mock like this:
Mock(ClassB) {
executeCommand(_, _) >> { c, e -> e.execute() }
}
I.e. provide a mock implementation for the executeCommand
method of ClassB that actually calls the execute
method of interfaceE.
EDIT: full working example:
import spock.lang.Specification
class TestMeSpec extends Specification {
def "my test"() {
def b = Mock( ClassB ) {
executeCommand( _, _ ) >> { c, e -> e.execute() }
}
def c = Mock( ClassC )
def d = Mock( ClassD )
def a = new ClassA( classB: b, classC: c, classD: d )
when:
a.update( 0, [ : ] )
then:
1 * d.update( 0, [ : ] )
}
}
class ClassA {
ClassB classB
ClassC classC
ClassD classD
void update( final int a, final Map<String, Object> b ) {
classB.executeCommand( classC.callToMethodInClassC(), new InterfaceE<Void>() {
@Override
Void execute() {
classD.update( a, b )
}
} )
}
}
class ClassB {
void executeCommand( c, InterfaceE e ) {
println "REAL CLASS B executCommand() METHOD RUNNING"
}
}
class ClassC {
def callToMethodInClassC() {}
}
class ClassD {
void update( a, b ) {
println "REAL CLASS D update() method called with $a and $b"
}
}
interface InterfaceE<T> {
T execute()
}
Collected from the Internet
Please contact [email protected] to delete if infringement.
Comments