Let's assume we have third-party service implementation to mock. If service was designed well, it implements some kind of interface (or interfaces) so clients could call different methods using interface contracts.
1 2 3 4 5 6 7 8 | package com.example; import java.util.Collection; public interface SimpleService { Collection< String > getServiceProviders(); Collection< String > getServiceProviders( final String regex ); } |
package com.example import org.junit.Test class SimpleServiceTestCase extends GroovyTestCase { @Test void testGetServiceProvidersByPattern() { // Create implementation from a map, method name : implementation (closure) def simpleService = [ getServiceProviders : { String regex -> [ "Provider 1", "Provider 2" ] } ] as SimpleService assertEquals( [ "Provider 1", "Provider 2" ], simpleService.getServiceProviders( "Provider*" ) ) } }Awesome and easy! Let's consider another use case: service has implementation only, no interfaces. Could we mock and it as well? Yes!
1 2 3 4 5 6 7 8 9 10 11 | package com.example; public class SimpleServiceImpl { public Collection< String > getServiceProviders() { return null ; } public Collection< String > getServiceProviders( final String regex ) { return null ; } } |
package com.example import groovy.mock.interceptor.MockFor import org.junit.Test import com.example.impl.SimpleServiceImpl class SimpleServiceTestCase extends GroovyTestCase { @Test void testGetServiceProviders() { def context = new MockFor( SimpleServiceImpl ) context.demand.with { getServiceProviders() { -> [ "Provider 1", "Provider 2" ] } } context.use { def simpleService = new SimpleServiceImpl() assertEquals( [ "Provider 1", "Provider 2" ], simpleService.getServiceProviders() ) } } }Cool and easy! The obvious question is, what about mocking static methods? You will love Groovy after that (as I do). Let's complicate our service a bit with static method.
1 2 3 4 5 6 7 8 9 | package com.example; public class SimpleServiceImpl { public static Collection< String > getDefaultServiceProviders() { return null ; } // Other methods here } |
package com.example class SimpleServiceTestCase extends GroovyTestCase { @Test void testGetDefaultServiceProviders() { SimpleServiceImpl.metaClass.'static'.getDefaultServiceProviders = { -> [ "Provider 1", "Provider 2" ] } assertEquals( [ "Provider 1", "Provider 2" ], SimpleServiceImpl.getDefaultServiceProviders() ) } }And that's it!