I am translating all my Junit Tests into Spock Tests and I don't want to use any "Assert methods". Therefore I have to translate the method isEqualToComparingFieldByFieldRecursively into my Groovy class. I am not sure, if I understood the function of the method correctly.
assertThat(validationMessage).isEqualToComparingFieldByFieldRecursively(provider.createValidationMessageDto());
In this case validationMessage is a DTO-Object and provider.createValidationMessageDto returns the same kind of DTO-Object. Does there already exist any similar method or do I have to code a new own method, which checks validationMessage? And if so, what should the method do?
Thanks for your answers. 😊
If the validation message DTO doesn't provide a proper equals methods, then sticking with isEqualToComparingFieldByFieldRecursively might be your best solution.
While Spock has great implicit assertion, something like reflective field-by-field compare isn't directly supported.
You could use Spock's support for Hamcrest and it's samePropertyValuesAs to write:
import static org.hamcrest.beans.SamePropertyValuesAs.samePropertyValuesAs
import static spock.util.matcher.HamcrestSupport.that
// ...
expect:
that validationMessage, samePropertyValuesAs(provider.createValidationMessageDto()
However, that does not do recursive comparison, for that you could use https://github.com/shazam/shazamcrest
Related
I want to test if method was invoked X times with one raw argument and other arguments from list. I found this method:
Mockito.verify(mock,Mockito.times(3)).myMethod(Mockito.eq("lastName"),
Mockito.argThat(Matchers.isOneOf("firstName","name","firstName"))));
However this complains that argThat method needs ArgumentMatcher but Matchers.isOneOf returns org.hamcrest.Matcher
Is there any other way that i could achieve this?
Thanks for help!
This changed in Mockito 2.1.0. On the Mockito web site, there is this migration advice.
All existing custom implementations of ArgumentMatcher will no longer
compile. All locations where hamcrest matchers are passed to argThat()
will no longer compile. There are 2 approaches to fix the problems:
a) Refactor the hamcrest matcher to Mockito matcher: Use implements
ArgumentMatcher instead of extends ArgumentMatcher. Then refactor
describeTo() method into toString() method.
b) Use org.mockito.hamcrest.MockitoHamcrest.argThat() instead of
Mockito.argThat(). Ensure that there is hamcrest dependency on
classpath (Mockito does not depend on hamcrest any more).
What option
is right for you? If you don't mind compile dependency to hamcrest
then option b) is probably right for you. Your choice should not have
big impact and is fully reversible - you can choose different option
in future (and refactor the code)
I have a code that I want to unit test. The code uses Collections.sort method providing it with our own sweet comparator something like :
List<Something> something = somethingService.doSomething(someParameter);
Collections.sort(something, somethingComparator);
Now while testing the function I am mocking the somethingService and stubbing the doSomething method like :
List<Something> mockList = Mockito.mock(List.class);
Mockito.when(somethingService.doSomething(anyInt())).thenReturn(mockList);
and I am mocking the Collections as :
PowerMockito.mockStatic(Collections.class);
PowerMockito.doNothing().when(Collections.class, "sort", anyListOf(Something.class), anyOf(Comparator.class));
But it is giving me :
org.mockito.exceptions.misusing.InvalidUseOfMatchersException:
Misplaced argument matcher detected
You cannot use argument matchers outside of verification or stubbing.
Now I do know that if we are using argument matchers in any param of a function we need to provide matchers to all the params. But here is it possible to do the same and if not then what is the existing workaround?
You are using PowerMock to mock a system class from the JDK, design wise it's really, really nasty. Seriously one should really think over his motivation to use Powermock as the author himself is.
Powermock cannot really mock directly static methods from system class, you have to create wrappers around the system calls, as documented in the wiki.
I would strongly advises you to extract some sorting strategy, that you could mock with just Mockito.
I'm Junit testing a class and had to create some Mockito mock objects. The line of code I'm interested in is this
Mockito.when(emailer.sendEmail(INPUT GOES HERE)).thenReturn(true);
the sendEmail() method of emailer takes in two parameters, and I'm not sure what they will be. Is there a sort of wild card that can be used there to replace the parameters without knowing what they will be?
As mentioned in the question comments.
Matchers.any(ClassName.class), which is usually what you want. In Mockito 1.x, this stands in for any object, regardless of its type, but by receiving a class it will typically avoid the need for a cast. (According to Mockito contributor Brice in an SO comment, this behavior will change in Mockito 2 and beyond, presumably to behave more like isA as any(MyClass.class) would suggest in English.)
Matchers.any(), which will usually require a cast, and isn't a good idea for primitives.
Matchers.anyInt() or Matchers.anyShort() (etc), which are good for primitives.
Matchers.anyString(), because Strings are a common use-case.
Because Mockito extends Matchers, most of these methods will be available on Mockito, but some IDEs have trouble finding static methods across subclasses. You can find all of them by using import static org.mockito.Matchers.*;.
Read more about all of the matchers available to you at the org.mockito.Matchers documentation.
If you run into trouble, or want to learn more about how these wildcards work under the surface, read more here.
I'm working on a Java project want to write a unit test for an .equals method I have in a DTO. In the .equals method, there is a .getClass() method called by both objects under test. I want to mock this, but I can't tell what type of object it wants. I tried,
when(mockRoomInv.getClass()).thenReturn(RoomInv.class);
but sure as heck didn't do anything. What is the return type of getClass, and how do I manipulate it?
As Object.getClass() is final, you cannot mock that method with Mockito. I would strongly advice you to refactor your code to inject the class in another way. If that's not possible, you could try out powermock, where you could mock any final method. Object.getClass() is a bit special, so be sure to set MockGateway.MOCK_GET_CLASS_METHOD = true in powermock.
Object.getClass() is a final method, so you cannot mock it with Mockito.
You can mock static and final methods (as this one) and even private methods with Powermock (it's a quite cool tool ;) available at https://github.com/powermock/powermock.
You can use it with Mockito as explained in the Mockito wiki article. There you will find some useful examples.
I'm using easymock, and I am mocking my UserService class.
My UserService has a few methods:
boolean canUserLogin(..);
boolean canUserJoinClass(...);
Now some of the methods call each other, and if I am testing method#1 I want to stub/mock methods #2 and methods# 3 that are called in method#1.
What I am confused is, how can I mock parts of a class and leave others to run the actual code?
So I want to actually test UserService.method#1, but mock UserService.method#2 and UserService.method#3 that method#1 calls internally.
By specifying return values for the methods you want mocked; see the easymock docs for examples.
The "Specifying Return Values" section discusses creating return values for mocked methods.
The "Partial mocking" section (towards the bottom) discusses mocking actual classes.
I agree with the docs (and other answers) that this may be an indication of sketchy design. Without further details, it's hard to say how sketchy it is, if it is at all.
You can check some library like Easymock, but I don't sure whether it can do this.
And here is my solution without third-party library. Create a subclass of UserService, and override the method you want to mock.
class SubUserService{
#override
boolean canUserJoinClass(...){
return false;
}
}
But notice the mock method can't be private.
And if this is one real problem you meet, you should refactor you methods to different classes.
I know Mockito supports "spy" on real objects. I could not find an equivalent in Easy Mock. So, I am not sure if you can do this.
Having said that, this is a smell to me. Why do you need to mock it? Is that an indication of the fact that your object is doing too much and hence you need to mock the other interactions?
Also, whenever you need to worry about the implementation of a method (method 1 in this case) i.e. the fact that it calls method2 and method3, especially of the same class, that sounds to me like a encapsulation leaking.
Mocking is intended to be used for dependencies, so you can test in isolation. In this case, you don't have any dependencies, since the methods you are calling are on one class. So I wouldn't use mocking here.
If methods 2 and 3 are so complicated that you want to mock them when testing method 1, then perhaps you should separate them out into their own class(es), so you can easily mock them.