I am learning Hamcrest 1.3 and I want to come up with an example for each Hamcrest static method in Matchers. The Javadoc helpfully already has examples for some methods. I tested the following contains code snippet with Java 8 and it passed:
assertThat(Arrays.asList("foo", "bar"),
contains(Arrays.asList(equalTo("foo"), equalTo("bar"))));
However, my team is currently using Java 7 so I wanted to make sure all the examples work in that version. The above code snippet produces the following error in Java 7:
no suitable method found for assertThat(java.util.List,org.hamcrest.Matcher>>>) method org.junit.Assert.assertThat(T,org.hamcrest.Matcher) is not applicable (actual argument org.hamcrest.Matcher>>> cannot be converted to org.hamcrest.Matcher> by method invocation conversion) method org.junit.Assert.assertThat(java.lang.String,T,org.hamcrest.Matcher) is not applicable (cannot instantiate from arguments because actual and formal argument lists differ in length)
I know that Java 8 added new implicit typing features for static methods and I think this is likely related. I have attempted to refactor out parameters and casting them to the expected arguments, but that results in the same error:
List<String> actual = Arrays.asList("foo", "bar");
List<Matcher<String>> expected = Arrays.asList(equalTo("foo"),
equalTo("bar"));
assertThat(actual, contains(expected));
What is the proper way to call static <E> Matcher<java.lang.Iterable<? extends E>> contains(java.util.List<Matcher<? super E>> itemMatchers)
in Java 7?
In the Hamcrest Javadoc, the method signature for the contains()
that you're targeting is:
public static <E> Matcher<Iterable<? extends E>> contains(List<Matcher<? super E>> itemMatchers);
The important bit to note in the above signature is the List<Matcher<? super E>>
. Java 7 cannot infer List<Matcher<? super E>>
from List<Matcher<String>>
. The contains()
is additionally overloaded, so the signature of the method that Java 7 targets is:
public static <E> Matcher<Iterable<? extends E>> contains(E... items);
And this is the reason you're getting the cryptic compilation error message!
Fortunately, the fix is pretty straightforward:
List<String> actual = Arrays.asList("foo", "bar");
List<Matcher<? super String>> expected = Arrays.<Matcher<? super String>>asList(equalTo("foo"),
equalTo("bar"));
assertThat(actual, contains(expected));
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With