Testing Spring Controllers Using Powermock

I have a class that validates a specific controller and it works great

@RunWith(SpringJUnit4ClassRunner.class) @ContextConfiguration(locations = "classpath:config/test-applicationContext-config.xml") @TestExecutionListeners({ WebContextTestExecutionListener.class, DependencyInjectionTestExecutionListener.class, DirtiesContextTestExecutionListener.class }) public class TestAdminController { //..... } 

I used the Google Mockito library from mockito.org there to mock my base beans.

Now my question is this: I have some classes that need to be taunted too, but they have final methods, and Google mockito does not seem to solve this problem. One of my colleagues suggested using Powermock from powermock.org . But this requires annotating the tester class using the @RunWith(PowerMockRunner.class) annotation @RunWith(PowerMockRunner.class) . If I use this, I need to remove the @RunWith(SpringJUnit4ClassRunner.class) annotation @RunWith(SpringJUnit4ClassRunner.class) and this will give me problems because the Spring test context will not be created. How can I avoid this situation?

After the suggestion, I configured to use PowerMockRule instead of @RunWith annotations

My Maven project dependencies are as follows

 <dependency> <groupId>org.powermock</groupId> <artifactId>powermock-mockito-release-full</artifactId> <version>1.5</version> <type>pom</type> </dependency> <dependency> <groupId>org.powermock</groupId> <artifactId>powermock-module-junit4-rule</artifactId> <version>1.5</version> <scope>test</scope> </dependency> <dependency> <groupId>org.powermock</groupId> <artifactId>powermock-classloading-xstream</artifactId> <version>1.5</version> <scope>test</scope> </dependency> 

Now my class looks like this (another controller test)

 @RunWith(SpringJUnit4ClassRunner.class) @ContextConfiguration(locations = "classpath:config/test-applicationContext-config.xml") @TestExecutionListeners({ WebContextTestExecutionListener.class, DependencyInjectionTestExecutionListener.class, DirtiesContextTestExecutionListener.class }) @PrepareForTest(ADSynchronizationImpl.class) public class ThirdPartyLoginControllerTest { @Rule public PowerMockRule rule = new PowerMockRule(); @Autowired private ThirdPartyLoginController thirtPartyLoginController; @Autowired private MockFactoryForControllers mockFactory; @Test public void testLoginActiveDirectory(){ } } 

But after running my test, I get the following exception trace

com.thoughtworks.xstream.converters.ConversionException: javassist.NotFoundException: com.somecompany.analytics.manager.db.api.MlDao $$ EnhancerByMockitoWithCGLIB $$ b86d7415: javassist.NotFoundException: com.somecompany.analy. MlDao $$ EnhancerByMockitoWithCGLIB $$ b86d7415 ---- Debug information ---- message: javassist.NotFoundException: com.somecompany.analytics.manager.db.api.MlDao $$ EnhancerByMockitoWithCGLIB $$ b86d7415 jang.lang: RuntimeException reason-message: javassist.NotFoundException: com.somecompany.analytics.manager.db.api.MlDao $$ EnhancerByMockitoWithCGLIB $$ b86d7415 class: com.somecompany.ui.controllers.ThirdPartyLoginController required-type: com .ThirdPartyLoginController converter-type: com.thoughtworks.xstream.converters.reflection.ReflectionConverter track: /org.powermock.modules.junit4.rule.PowerMockStat ement $ 1 / outer-class / fNext / fTarget / thirtPartyLoginController / mlDao line number: 14 class 1 : com.somecompany.ui.controllers.ThirdPartyLoginControllerTest class 2 : org.junit.internal.runners.statements.InvokeMethod class [3]
: org.powermock.modules.junit4.rule.PowerMockStatement class [4]
: org.powermock.modules.junit4.rule.PowerMockStatement $ 1 version
: zero ------------------------------- on com.thoughtworks.xstream.core.TreeUnmarshaller.convert (TreeUnmarshaller.java: 79) in com.thoughtworks.xstream.core.AbstractReferenceUnmarshaller.convert (AbstractReferenceUnmarshaller.java:65) in com.thoughtworks.xstream.core.TreeUnmarshaller.convertAnother (TreeUnmarshaller.java:66) in com.thoughtworks.xstream.converters.relection .AbstractReflectionConverter.unmarshallField (AbstractReflectionConverter.javahaps55) in com.thoughtworks.xstream.converters.reflection.AbstractReflectionConverter.doUnmarshal (AbstractReflectionConverter.java:306) in com.thoughtworks.xstream.converters.reflection.refleflection.refleflection.refleflection.refleflection.refleflection.refleflection.reflefreleflefreleflefreleflefreflefle : 234) in com.thoughtworks.xstream.core.TreeUnmarshaller.convert (TreeUnmarshaller.java:72) in com.thoughtworks.xstream.core.AbstractReferenceUnmarshaller.convert (AbstractReferenceUnmarshaller.java:65) in com.thoughtworks.xstream.core. TreeUnmarshaller.convertAnother (TreeUnmar shaller. .thoughtworks.xstream.converters.reflection.AbstractReflectionConverter.unmarshal (AbstractReflectionConverter.java:234) in com.thoughtworks.xstream.core.TreeUnmarshaller.convert (TreeUnmarshaller.java:72) in com.thoughtworks.xstream.core.AbstractReference (AbstractReferenceUnmarshaller.java:65) in com.thoughtworks.xstream.core.TreeUnmarshaller.convertAnother (TreeUnmarshaller.java:66) in com.thoughtworks.xstream.converters.reflection.AbstractReflectionConverter.unmarshallField (AbstractReflectionConverter.ava. thoughtworks.xstream.converters.reflection.AbstractReflectionConverter.doUnmarshal (AbstractReflectionConverter.java:306) in com.thoughtworks.xstream.conver ters.reflection.AbstractReflectionConverter.unmarshal (AbstractReflectionConverter.java:234) in com.thoughtworks.xstream.core.TreeUnmarshaller.convert (TreeUnmarshaller.java:72) in com.thoughtworks.xstream.core.AbstractReferenceUnmarshaller.avavert (abstract) 65) in com.thoughtworks.xstream.core.TreeUnmarshaller.convertAnother (TreeUnmarshaller.java:66) in com.thoughtworks.xstream.converters.reflection.AbstractReflectionConverter.unmarshallField (AbstractReflectionConverter.javahaps55) in com.thoughtverworksxstream .reflection.AbstractReflectionConverter.doUnmarshal (AbstractReflectionConverter.java:306) at com.thoughtworks.xstream.converters.reflection.AbstractReflectionConverter.unmarshal (AbstractReflectionConverter.java:234) in com.thoughtworks.xstream.core.treen : 72) in com.thoughtworks.xstream.core.AbstractReferenceUnmarshaller.convert (AbstractReferenceUnmarshaller.java:65) in com.thoughtworks.xstre am.core.TreeUnmarshaller.convertAnother (TreeUnmarshaller.java:66) at com.thoughtworks.xstream.core.TreeUnmarshaller.convertAnother (TreeUnmarshaller.java:50) at com.thoughtworks.xstream.core.TreeUnmarshaller.start (TreeUavamarshaller 134) at com.thoughtworks.xstream.XStream.unmarshal (XStream.java:1052) at com.thoughtworks.xstream.XStream.unmarshal (Xtream.xStream.unmarshal (X). .java: 1036) at com.thoughtworks.xstream.XStream.fromXML (XStream.java:912) at com.thoughtworks.xstream.XStream.fromXML (XStream.java:903) in org.powermock.classloading.DeepCloner.clone ( DeepCloner.java:54) at org.powermock.classloading.ClassloaderExecutor.execute (ClassloaderExecutor.java:89) at org.powermock.classloading.ClassloaderExecutor.execute (ClassloaderExecutor.java:78) at org.powermock.modules.junit4 .PowerMockStatement.evaluate (PowerMockRule.java:49) in org.springframework.test.context.junit4.stat ements.RunBeforeTestMethodCallbacks.evaluate (RunBeforeTestMethodCallbacks.java:74) in org.springframework.test.context.junit4.statements.RunAfterTestMethodCallbacks.evaluate (RunAfterTestMethodCallbacks.jprt.. evaluate (SpringRepeat.java:72) in org.springframework.test.context.junit4.SpringJUnit4ClassRunner.runChild (SpringJUnit4ClassRunner.java:240) in org.junit.runners.BlockJUnit4ClassRunner.runnjj.jun.runnjjj.jpg .runners.ParentRunner $ 3.run (ParentRunner.java:238) at org.junit.runners.ParentRunner $ 1.schedule (ParentRunner.java:63) at org.junit.runners.ParentRunner.runChildren (ParentRunner.java:236) org.junit.runners.ParentRunner.access $ 000 (ParentRunner.java:53) at org.junit.runners.ParentRunner $ 2.valuation (ParentRunner.java:229) at org.springframework.test.context.junit4.statements.RunBeforeTestClass evaluate (RunBeforeTestClassCallbacks.java:61) in org.spr ingframework.test.context.junit4.statements.RunAfterTestClassCallbacks.evaluate (RunAfterTestClassCallbacks.java:70) at org.junit.runners.ParentRunner.run (ParentRunner.java.309) in org.springframework.testJnprlass.testRun.class.r run (SpringJUnit4ClassRunner.java:180) in org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run (JUnit4TestReference.java:50) in org.eclipse.jdt.internal.junit.runner.TestecExececExecution java: 38) in org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests (RemoteTestRunner.java:467) in org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests (RemoteTestRunner) in org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run (RemoteTestRunner.javahaps90) in org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main (RemoteTestRunner.java:197). Called: lang.RuntimeException: javassist.NotFoundException: com.somecompany.idm.analytics.manager.db.api.MlDao $$ EnhancerByMockitoWithCGLI B $$ b86d7415 in org.powermock.core.classloader.MockClassLoader.loadUnmockedClass (MockClassLoader.java:199) in org.powermock.core.classloader.MockClassLoader.loadModifiedClass (MockClassLoader.java:assass1414) .DeferSupportingClassLoader.loadClass (DeferSupportingClassLoader.java:67) in java.lang.ClassLoader.loadClass (ClassLoader.javahaps56) in com.thoughtworks.xstream.core.util.ClassLoaderReference.loadClass (ClassLoaderReference.j:31 thoughtworks.xstream.mapper.DefaultMapper.realClass (DefaultMapper.java:49) at com.thoughtworks.xstream.mapper.MapperWrapper.realClass (MapperWrapper.java:30) at com.thoughtworks.xstream.mapper.DynamicProxyMapper.realClass (DynamicProxyMapper. java: 55) in com.thoughtworks.xstream.mapper.MapperWrapper.realClass (MapperWrapper.java:30) in com.thoughtworks.xstream.mapper.PackageAliasingMapper.realClass (PackageAliasingMapper.java:88) in com.thoughtworks.xstream.mapper .MapperWrapper.realClass (MapperWrapper.java data 0) in com.thoughtworks.xstream.mapper.ClassAliasingMapper.realClass (ClassAliasingMapper.java:79) in com.thoughtworks.xstream.mapper.MapperWrapper.realClass (MapperWrapper.java:30) in com.thoughtworks.xstream.mapper.MapperWrapper .realClass (MapperWrapper.java:30) at com.thoughtworks.xstream.mapper.MapperWrapper.realClass (MapperWrapper.java:30) at com.thoughtworks.xstream.mapper.MapperWrapper.realClass (MapperWrapper.java:30) at com. thoughtworks.xstream.mapper.MapperWrapper.realClass (MapperWrapper.java:30) at com.thoughtworks.xstream.mapper.MapperWrapper.realClass (MapperWrapper.java:30) at com.thoughtworks.xstream.mapper.ArrayMapper.realClass (ArrayMapper. java: 74) in com.thoughtworks.xstream.mapper.MapperWrapper.realClass (MapperWrapper.java:30) in com.thoughtworks.xstream.mapper.MapperWrapper.realClass (MapperWrapper.java:30) in com.thoughtworks.xstream.mapper .MapperWrapper.realClass (MapperWrapper.java:30) at com.thoughtworks.xstream.mapper.MapperWrapper.realClass (Mapp erWrapper.java:30) at com.thoughtworks.xstream.mapper.MapperWrapper.realClass (MapperWrapper.java:30) at com.thoughtworks.xstream.mapper.MapperWrapper.realClass (MapperWrapper.java:30) at com.thoughtworks.xstream .mapper.MapperWrapper.realClass (MapperWrapper.java:30) at com.thoughtworks.xstream.mapper.CachingMapper.realClass (CachingMapper.java:45) at com.thoughtworks.xstream.converters.reflection.AbstractReflectionConverter.determineTypeon Abstract : 458) in com.thoughtworks.xstream.converters.reflection.AbstractReflectionConverter.doUnmarshal (AbstractReflectionConverter.java:294) in com.thoughtworks.xstream.converters.reflection.AbstractReflectionConverter.unmarshal (AbstractReflectionConverter.java23. xstream.core.TreeUnmarshaller.convert (TreeUnmarshaller.java:72) ... 57 more Caused by: javassist.NotFoundException: com.somecompany.analytics.manager.db.api.MlDao $$ EnhancerByMockitoWithCGLIB $$ b86d7415 in javassis t.ClassPool.get (ClassPool.java:450) in org.powermock.core.classloader.MockClassLoader.loadUnmockedClass (MockClassLoader.java:192) ... 87 more

+4
source share
3 answers

Check out this article that explains how to use PowerMock and SpringJUnit4ClassRunner . Basically, you just need to use the special PowerMockRule rule :

 @RunWith(SpringJUnit4ClassRunner.class) @ContextConfiguration(locations = "classpath:config/test-applicationContext-config.xml") @TestExecutionListeners({ WebContextTestExecutionListener.class, DependencyInjectionTestExecutionListener.class, DirtiesContextTestExecutionListener.class }) public class SpringExampleTest { @Rule public PowerMockRule rule = new PowerMockRule(); } 

Edit: It seems that other people had the same issue as you regarding @PowerMockRule . Using PowerMockAgent instead, you can solve your case. See also this anwer on SO.

+6
source

You can use JMockit instead of Powermock. It can do whatever Powermock can do, and it does not need the @RunWith clause to prevent it from interfering with your test running Spring. I found that PowerMockRule presented more problems than it solved ...

+3
source

You can also try to annotate your test class.

 @PowerMockRunnerDelegate(SpringJUnit4ClassRunner.class) 

See an example here .

+3
source

All Articles