How can I do this using AssertJ (or Hamcrest)?

I want to unit test a method that returns a List<MyItem>, where MyItem has multiple properties, including name.

I only care that the list contains items with names "foo" and "bar", regardless of other properties. Ideally, I want a one-liner assertion.

I tried something like this in pseudo-code:

assert(listEntriesMatchInAnyOrder(myClass.getMyItems(), property("name"), new String[]{"foo", "bar"}));

How can I do this using AssertJ (or Hamcrest)? Specifically, is there a way to assert that the Iterable has elements with certain property values or use something like hasSize along with property checks in one line?

Using extracting with containsExactlyInAnyOrder

import static org.assertj.core.api.Assertions.assertThat;

List<MyItem> items = myClass.getMyItems();

assertThat(items)
    .extracting(MyItem::getName)             // extract the `name` property
    .containsExactlyInAnyOrder("foo", "bar"); // assert names match, any order

:white_check_mark: This ignores all other properties and checks only the name values.

Using extracting with contains

If you don’t care about exact size, just that “foo” and “bar” exist somewhere in the list:

assertThat(items)
    .extracting(MyItem::getName)
    .contains("foo", "bar");

If you want to assert that exactly these two items exist:

assertThat(items)
    .filteredOn(item -> Set.of("foo", "bar").contains(item.getName()))
    .hasSize(2);

This filters the list to only items with “foo” or “bar” and checks the count.