Javvano
Javvano

Reputation: 1059

Why Spock's Interactions doesn't work for Mock that built by other class

I'm trying to assemble all Mock building methods in one class. but when I use Mock object that built by building method on other groovy class . the stubbing of Mock seems work fine , but interactions check doesn't work. well ... how should I achieve this ?

MockTestingSpec.groovy

class MockTestingSpec extends Specification{

    def "use mock from other class"(){
        setup:"construct mock builder"
        def bldr = new MockBuilder()

        when:"build mock by MockBuilder"
        def mockObj = bldr.buildMock()

        and:"build mock by private method of this class"
        def builtAtThisClass = buildMock()

        then:"check stubbing are working. these conditions were satisfied"
        mockObj.getKey().equals("keyyyy")
        mockObj.getValue() == 12345
        builtAtThisClass.getKey().equals("keyyyy")
        builtAtThisClass.getValue() == 12345

        when:"put a mock to private method"
        callMockGetter(builtAtThisClass)

        then:"call each getter, these conditions were also satisfied"
        1 * builtAtThisClass.getKey()
        1 * builtAtThisClass.getValue()

        when:"puta a mock that built by builder"
        callMockGetter(mockObj)

        then:"these conditions were NOT satisfied... why?"
        1 * mockObj.getKey()
        1 * mockObj.getValue()
    }
    // completely same method on MockBuilder.
    private buildMock(String key = "keyyyy",Integer value = 12345){
        TestObject obj = Mock()
        obj.getKey() >> key
        obj.getValue() >> value
        return obj
    }

    private callMockGetter(TestObject obj){
        obj.getKey()
        obj.getValue()
    }
}

MockBuilder.groovy

class MockBuilder extends Specification{

    public buildMock(String key = "keyyyy",Integer value = 12345){
        TestObject obj = Mock()
        obj.getKey() >> key
        obj.getValue() >> value
        return obj
    }

    public static class TestObject{
        private String key
        public String getKey(){
            return key
        }
        private Integer value
        public Integer getValue(){
            return value
        }
    }
}

Upvotes: 0

Views: 595

Answers (1)

laenger
laenger

Reputation: 991

Moving mock creation to a superclass works instead. This way you can reuse complex mock creation across multiple Specs.

abstract class MockCreatingSpec extends Specification {
    createComplexMockInSuperClass() {
        return Mock()
    }
}
class MockTestingSpec extends MockCreatingSpec {
    def "use mock from superclass"() {
        given:
        def mock = createComplexMockInSuperClass()
        ...
    }
}

Upvotes: 1

Related Questions