PowerMockito not able to mock final class - unit-testing

I wanted to use PowerMockito to mock couple of final class related to cloudwatch.
I am able to mock a non final class
CloudWatchLogsClient cloudWatchLogsClient = PowerMockito.mock(CloudWatchLogsClient.class);
But when i try to mock these final classes
LogGroup logGroup = PowerMockito.mock(LogGroup.class);
DescribeLogGroupsResponse describeLogGroupsResponse = PowerMockito.mock(DescribeLogGroupsResponse.class);
it gives error
MethodSource [className = 'util.LogUtilTest', methodName = 'testLogGroupPresent', methodParameterTypes = '']
[java] => org.mockito.exceptions.base.MockitoException:
[java] Cannot mock/spy class software.amazon.awssdk.services.cloudwatchlogs.model.LogGroup
[java] Mockito cannot mock/spy because :
[java] - final class
I am using
#RunWith(PowerMockRunner.class)
#PrepareForTest({CreateLogStreamRequest.class, LogGroup.class, DescribeLogGroupsResponse.class, DescribeLogGroupsRequest.class})
but still i am getting the error, anyone knows why is this happening ?

Related

#WebMvcTest No qualifying bean of type repository

I'm writing a controller test where controller looks like
#RestController
public class VehicleController {
#Autowired
private VehicleService vehicleService = null;
...
}
While the test class looks like
#RunWith(SpringRunner.class)
#WebMvcTest(VehicleController.class)
public class VehicleControllerTest {
#Autowired
private MockMvc mockMvc = null;
#MockBean
private VehicleService vehicleServie = null;
#Test
public void test() {
...
}
}
When I run this test it fails with the following error
Caused by: org.springframework.beans.factory.NoSuchBeanDefinitionException: No qualifying bean of type 'com.example.database.repositories.SomeOtherRepository' available: expected at least 1 bean which qualifies as autowire candidate. Dependency annotations: {#org.springframework.beans.factory.annotation.Autowired(required=true)}
Here, SomeOtherRepository is not used in a given controller or service.
If I do #MockBean for SomeOtherRepository the test works but the same problem occurs for the rest of the repositories.
#MockBean private SomeOtherRepository someOtherRepository = null
...
# Bunch of other repositories
Ideally I should not be concerned about all the repositories except the one's I'm using. What am I missing here? How can I avoid writing bunch of #MockBeans?
You have specified
#WebMvcTest(VehicleController.class)
which is fine, however you might find some beans from other dependencies, such as a custom UserDetailsService, some custom validation, or #ControllerAdvice that are also being brought in.
You can exclude these beans by using exclude filters.
#WebMvcTest(controllers = VehicleController.class, excludeFilters = #Filter(type = FilterType.ASSIGNABLE_TYPE, classes = CustomUserDetailsService.class)
Your VehicleService depends on SomeOtherRepository, so you have to mock it too in your test class. Try adding:
#MockBean private SomeOtherRepository someOtherRepository
in your VehicleControllerTest class.

Mock is giving missing method exception in spock framewrok

I am running my Junit test cases for my groovy class using spock framework I am using Mock to invoke my class. but it is giving me MissingMethodException but if I invoke the same method by normal creating object def obj = new MyClass() way it is working. please let me know am I missing something? below is my stacktrace
Expected no exception to be thrown, but got 'groovy.lang.MissingMethodException'
at spock.lang.Specification.noExceptionThrown(Specification.java:119)
at .AsplTest.fetchXmlTest(AsplTest.groovy:35)
Caused by: groovy.lang.MissingMethodException: No signature of method: com.webservice.Service.fetchAsplXml() is applicable for argument types: (java.lang.String, groovy.net.xmlrpc.XMLRPCServerProxy, java.lang.String) values: [3c98fa0dd1b5d92af599779bfb7be655, groovy.net.xmlrpc.XMLRPCServerProxy#797b0699, ...]
Possible solutions: getFetchAsplXml()
at .AsplTest.fetchXmlTest(AsplTest.groovy:33)
below is my test code
public void fetchXmlTest() {
given:
def asplObject=Mock(Service);
when:
asplObject.fetchXml(sessionId, serverProxy, "https://serverproxy")
then:
noExceptionThrown()
}
FYI:
my groovy version is 2.4.12 and spock version 1.1-groovy-2.4
It seems to me that you are doing things backwards.
Mocks are not test subjects. They are used to control the interactions of your test subjects with other objects. It looks, from the code you posted, that you want to test the invocation of method fetchXml on your Service object.
To do this, you need to create an instance of Service, and call the method. If your Service has collaborating objects, then you can Mock them, and add interactions, like this:
given:
def service = new Service()
and:
service.collaboratingObject = Mock(CollaboratingObjectClass)
when:
service.getFetchAsplXml()
then:
1 * service.collaboratingObject.someMethodReturningAString(_ as String) >> {String input-> "mockedResult from $input" as String }

Unit testing service returns a 'cannot add service class' error message

in my services folder, i have this file
abstract class AsyncUploadedFileService<T> {
def grailsApplication
def jesqueService
String jobName
String workerPool
String _queueName
AsyncUploadedFileService (Class<T> job, String workerPool) {
jobName = job.simpleName
this.workerPool = workerPool
}
}
and I have a unit test
#Build(UploadedFile)
#TestMixin(GrailsUnitTestMixin)
#TestFor(AsyncUploadedFileService)
class AsyncUploadedFileServiceSpec extends Specification {
def setup() {
User.metaClass.encodePassword = {-> }
}
void "add to the worker pool"() {
when:
UploadedFile uploadedFile = UploadedFile.build()
then:
service.perform(uploadedFile)
}
}
when I run my test, I get the following error
Cannot add Service class [class com.example.AsyncUploadedFileService]. It is not a Service!
org.codehaus.groovy.grails.exceptions.GrailsConfigurationException: Cannot add Service class [class com.example.AsyncUploadedFileService]. It is not a Service!
at grails.test.mixin.services.ServiceUnitTestMixin.mockService(ServiceUnitTestMixin.groovy:46)
at org.spockframework.util.ReflectionUtil.invokeMethod(ReflectionUtil.java:138)
at org.spockframework.runtime.extension.builtin.JUnitFixtureMethodsExtension$FixtureType$FixtureMethodInterceptor.intercept(JUnitFixtureMethodsExtension.java:145)
at org.spockframework.runtime.extension.MethodInvocation.proceed(MethodInvocation.java:84)
at org.spockframework.util.ReflectionUtil.invokeMethod(ReflectionUtil.java:138)
at org.spockframework.util.ReflectionUtil.invokeMethod(ReflectionUtil.java:138)
at org.spockframework.util.ReflectionUtil.invokeMethod(ReflectionUtil.java:138)
Is this error because I'm using the service.perform() syntax? If so, what other way is there of testing the AsynchUploadedFileService function?
You can't instantiate an abstract class, so you can't create one to test with. Make it non-abstract, or create a concrete subclass and test that.
Also, since you have a constructor with arguments, there is no default (no-arg) constructor. If you have no constructors, the compiler adds one for you (in both Java and Groovy) and in Grails since services are auto-registered, you must have a no-arg constructor (you can have others, but I can't see why you would) so Spring can create the instance. You can always manually wire up a class as a Spring bean and provide constructor args in resources.groovy, but then it wouldn't be a Grails service, so it would be better to put it in src/groovy.

JUnit Testing FacesContext.getExternalContext

I have the following code in a Java EE managed bean:
FacesContext context = facesContextProvider.getCurrentInstance();
HttpServletResponse response = (HttpServletResponse) context.getExternalContext();
Where facesContextProvider is a custom class for returning the faces context (useful for mock testing).
I'm wondering how to test this in JUnit using mockito. I am trying a combination of:
FacesContextProvider mockFacesContextProvider = mock(FacesContextProvider.class);
when(mockFacesContextProvider.getCurrentInstance()).thenReturn(mockFacesContext);
// this line is wrong ~> when(mockFacesContext.getExternalContext()).thenReturn((ExternalContext) new MockHttpServletResponse());
How can I inject some sort of mock or custom HttpServletResponse into my external context?
Thanks for the help.
ANSWER
My controller code is wrong. You can work with the ExternalContext to do whatever you need. So in the controller, it should actually be:
FacesContext facesContext = facesContextProvider.getCurrentInstance();
ExternalContext externalContext = facesContext.getExternalContext();
externalContext.responseReset();
If you still wanted the response, you could get it from:
HttpResponse response = externalContext.getResponse();
Then the unit test harness would be:
mockFacesContextProvider = mock(FacesContextProvider.class);
mockFacesContext = mock(FacesContext.class);
mockExternalContext = mock(ExternalContext.class);
mockHttpSession = mock(HttpSession.class);
when(mockFacesContextProvider.getCurrentInstance()).thenReturn(mockFacesContext);
when(mockFacesContext.getExternalContext()).thenReturn(mockExternalContext);
when(mockExternalContext.getSession(true)).thenReturn(mockHttpSession);
And then the Unit Test code would be:
verify(mockExternalContext).responseReset();
FacesContextProvider mockFacesContextProvider = mock(FacesContextProvider.class);
HttpServletResponse mockResponse = mock(HttpServletResponse.class);
when(mockFacesContextProvider.getCurrentInstance()).thenReturn(mockFacesContext);
when(mockFacesContext.getExternalContext()).thenReturn(mockResponse);

How to mock a java class inside a Grails unit test?

I have a java class, which I've added to my resources.groovy like this:
import persistentrep.ReasoningXMLLoader;
// Place your Spring DSL code here
beans = {
reasoningXMLLoader(ReasoningXMLLoader)
}
I then use this class in my GrailsService:
class XMLService
{
def reasoningXMLLoader
def someMethod()
{
reasoningXMLLoader.doSomething()
}
}
Obviously, I want to write a unit test that mocks reasoningXMLLoader and injects it into the service.
I tried using #Mock, MockFor and mockFor and I keep getting org.codehaus.groovy.grails.exceptions.GrailsConfigurationException: Cannot add Domain class [class persistentrep.ReasoningXMLLoader]. It is not a Domain! error :
org.codehaus.groovy.grails.exceptions.GrailsConfigurationException: Cannot add Domain class [class persistentrep.ReasoningXMLLoader]. It is not a Domain!
at org.codehaus.groovy.grails.commons.DefaultGrailsApplication.addArtefact(DefaultGrailsApplication.java:916)
at org.codehaus.groovy.grails.commons.DefaultGrailsApplication.addArtefact(DefaultGrailsApplication.java:615)
at org.codehaus.groovy.grails.commons.GrailsApplication$addArtefact.call(Unknown Source)
at org.codehaus.groovy.runtime.callsite.CallSiteArray.defaultCall(CallSiteArray.java:42)
at org.codehaus.groovy.runtime.callsite.AbstractCallSite.call(AbstractCallSite.java:108)
at org.codehaus.groovy.runtime.callsite.AbstractCallSite.call(AbstractCallSite.java:120)
at grails.test.mixin.domain.DomainClassUnitTestMixin.mockDomain(DomainClassUnitTestMixin.groovy:131)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:601)
at org.codehaus.groovy.runtime.callsite.PogoMetaMethodSite$PogoCachedMethodSite.invoke(PogoMetaMethodSite.java:226)
at org.codehaus.groovy.runtime.callsite.PogoMetaMethodSite.callCurrent(PogoMetaMethodSite.java:52)
at org.codehaus.groovy.runtime.callsite.CallSiteArray.defaultCallCurrent(CallSiteArray.java:46)
at org.codehaus.groovy.runtime.callsite.AbstractCallSite.callCurrent(AbstractCallSite.java:133)
at org.codehaus.groovy.runtime.callsite.AbstractCallSite.callCurrent(AbstractCallSite.java:145)
at grails.test.mixin.domain.DomainClassUnitTestMixin.mockDomain(DomainClassUnitTestMixin.groovy:128)
at com.vpundit.www.XMLServiceTests.mockDomain(XMLServiceTests.groovy)
at com.vpundit.www.XMLServiceTests.setUp(XMLServiceTests.groovy)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:601)
at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:45)
at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:15)
at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:42)
at org.junit.internal.runners.statements.RunBefores.evaluate(RunBefores.java:27)
at org.junit.internal.runners.statements.RunAfters.evaluate(RunAfters.java:30)
at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:263)
at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:68)
at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:47)
at org.junit.runners.ParentRunner$3.run(ParentRunner.java:231)
at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:60)
at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:229)
at org.junit.runners.ParentRunner.access$000(ParentRunner.java:50)
at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:222)
at org.junit.internal.runners.statements.RunBefores.evaluate(RunBefores.java:28)
at org.junit.internal.runners.statements.RunAfters.evaluate(RunAfters.java:30)
at org.junit.runners.ParentRunner.run(ParentRunner.java:300)
at org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run(JUnit4TestReference.java:50)
at org.eclipse.jdt.internal.junit.runner.TestExecution.run(TestExecution.java:38)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:467)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:683)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:390)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:197)
Is there a way to mock this using the Grails built-in mocking framework, or do I need to use something like Mockito?
What is the best way to inject the mock? Is there some Grails magic that can do it for me, or do I just use the exposed property -
service.reasoningXMLLoader = mock?
I finally managed to figure out how to do this. I was getting the exception, because I was trying to use the #Mock() attribute, which apparently cannot be used for what I was trying to do.
The task is actually pretty straight forward after reading the Groovy documentation for mocking with closures and with MockFor. I should have realized earlier that Groovy's documentation is better suited for this type of information that Grails'
So here is how to accomplish what I wanted to do, using closures. It's very neat actually:
void testParseXml() {
String xml = "test string"
def mockReturnObject = {create your object to be returned here}
def loader = [parseString:{ mockReturnObject }] as ReasoningXMLLoader
service.reasoningXMLLoader = loader
def result = service.parseXML(xml)
do assertions here
}
Here is how to do the same with mocks:
void testParseXml() {
String xml = "test string"
def mockReturnObject = {create your object to be returned here}
def loader = new MockFor(ReasoningXMLLoader)
loader.demand.parseString{mockReturnObject}
service.reasoningXMLLoader = loader.proxyInstance()
def result = service.parseXML(xml)
do assertions here
}
I hope this helps someone who is new to Grails and Groovy.