Commit 259a6760 authored by Administrator's avatar Administrator

Improves the IsEqualToEntity abstract matcher

The IsEqualToEntity matcher (previously, IsEqualsToEntity) has been
improved to allow property comparison by functional reference to the
getter methods of the properties to compare. Specifically, the
"checkAttribute" methods added allow providing a Function<T, R> as a
getter, where T is the type of the entity to compare and R is the type
returned by the getter method.
parent 342bf501
package es.uvigo.esei.xcs.rest;
import static es.uvigo.esei.xcs.domain.entities.IsEqualsToOwner.containsOwnersInAnyOrder;
import static es.uvigo.esei.xcs.domain.entities.IsEqualsToOwner.equalsToOwner;
import static es.uvigo.esei.xcs.domain.entities.IsEqualToOwner.containsOwnersInAnyOrder;
import static es.uvigo.esei.xcs.domain.entities.IsEqualToOwner.equalToOwner;
import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.EXISTENT_LOGIN;
import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.NON_EXISTENT_LOGIN;
import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.OWNER_WITHOUT_PETS_LOGIN;
......@@ -89,7 +89,7 @@ public class OwnerResourceRestTest {
final Owner owner = response.readEntity(Owner.class);
final Owner expected = existentOwner();
assertThat(owner, is(equalsToOwner(expected)));
assertThat(owner, is(equalToOwner(expected)));
}
@Test @InSequence(3)
......@@ -202,7 +202,7 @@ public class OwnerResourceRestTest {
final Response responseGet = authorizedJsonRequestGet(location);
final Owner owner = responseGet.readEntity(Owner.class);
assertThat(owner, is(equalsToOwner(persistentOwner)));
assertThat(owner, is(equalToOwner(persistentOwner)));
}
......
package es.uvigo.esei.xcs.rest;
import static es.uvigo.esei.xcs.domain.entities.IsEqualsToOwner.containsOwnersInAnyOrder;
import static es.uvigo.esei.xcs.domain.entities.IsEqualsToOwner.equalsToOwner;
import static es.uvigo.esei.xcs.domain.entities.IsEqualToOwner.containsOwnersInAnyOrder;
import static es.uvigo.esei.xcs.domain.entities.IsEqualToOwner.equalToOwner;
import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.anyLogin;
import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.anyOwner;
import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.existentOwner;
......@@ -73,7 +73,7 @@ public class OwnerResourceUnitTest extends EasyMockSupport {
assertThat(response, hasHttpStatus(OK));
assertThat(response.getEntity(), is(instanceOf(Owner.class)));
assertThat((Owner) response.getEntity(), is(equalsToOwner(owner)));
assertThat((Owner) response.getEntity(), is(equalToOwner(owner)));
}
@Test(expected = IllegalArgumentException.class)
......
package es.uvigo.esei.xcs.service;
import static es.uvigo.esei.xcs.domain.entities.IsEqualsToOwner.containsOwnersInAnyOrder;
import static es.uvigo.esei.xcs.domain.entities.IsEqualsToOwner.equalsToOwner;
import static es.uvigo.esei.xcs.domain.entities.IsEqualsToPet.containsPetsInAnyOrder;
import static es.uvigo.esei.xcs.domain.entities.IsEqualToOwner.containsOwnersInAnyOrder;
import static es.uvigo.esei.xcs.domain.entities.IsEqualToOwner.equalToOwner;
import static es.uvigo.esei.xcs.domain.entities.IsEqualToPet.containsPetsInAnyOrder;
import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.existentLogin;
import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.existentOwner;
import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.newOwnerWithFreshPets;
......@@ -77,7 +77,7 @@ public class OwnerServiceIntegrationTest {
final Owner actual = asAdmin.call(() -> facade.get(login));
assertThat(actual, is(equalsToOwner(ownerWithLogin(login))));
assertThat(actual, is(equalToOwner(ownerWithLogin(login))));
}
@Test
......@@ -113,7 +113,7 @@ public class OwnerServiceIntegrationTest {
final List<Owner> owners = asAdmin.call(() -> facade.findByPetName(petName));
assertThat(owners, hasSize(1));
assertThat(owners.get(0), is(equalsToOwner(owner)));
assertThat(owners.get(0), is(equalToOwner(owner)));
}
@Test
......@@ -151,7 +151,7 @@ public class OwnerServiceIntegrationTest {
final Owner actual = asAdmin.call(() -> facade.create(newOwner));
assertThat(actual, is(equalsToOwner(newOwner)));
assertThat(actual, is(equalToOwner(newOwner)));
}
@Test
......@@ -159,7 +159,7 @@ public class OwnerServiceIntegrationTest {
public void testCreateWithPets() {
final Owner actual = asAdmin.call(() -> facade.create(newOwnerWithFreshPets()));
assertThat(actual, is(equalsToOwner(newOwnerWithPersistentPets())));
assertThat(actual, is(equalToOwner(newOwnerWithPersistentPets())));
}
@Test(expected = EJBTransactionRolledbackException.class)
......@@ -196,7 +196,7 @@ public class OwnerServiceIntegrationTest {
final Owner actual = asAdmin.call(() -> facade.update(newOwner));
assertThat(actual, is(equalsToOwner(newOwner)));
assertThat(actual, is(equalToOwner(newOwner)));
}
@Test
......@@ -204,7 +204,7 @@ public class OwnerServiceIntegrationTest {
public void testUpdateNewOwnerWithPets() {
final Owner actual = asAdmin.call(() -> facade.update(newOwnerWithFreshPets()));
assertThat(actual, is(equalsToOwner(newOwnerWithPersistentPets())));
assertThat(actual, is(equalToOwner(newOwnerWithPersistentPets())));
}
@Test
......
package es.uvigo.esei.xcs.service;
import static es.uvigo.esei.xcs.domain.entities.IsEqualsToPet.containsPetsInAnyOrder;
import static es.uvigo.esei.xcs.domain.entities.IsEqualsToPet.equalsToPet;
import static es.uvigo.esei.xcs.domain.entities.IsEqualToPet.containsPetsInAnyOrder;
import static es.uvigo.esei.xcs.domain.entities.IsEqualToPet.equalToPet;
import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.existentPetId;
import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.newPet;
import static es.uvigo.esei.xcs.domain.entities.OwnersDataset.newPetWithOwner;
......@@ -75,7 +75,7 @@ public class PetServiceIntegrationTest {
final Pet actual = asOwner.call(() -> facade.get(id));
assertThat(actual, equalsToPet(pet));
assertThat(actual, equalToPet(pet));
}
@Test
......
package es.uvigo.esei.xcs.domain.entities;
import static java.util.Arrays.asList;
import static java.util.Arrays.stream;
import static java.util.Objects.requireNonNull;
import static java.util.stream.Collectors.toList;
import static org.hamcrest.collection.IsIterableContainingInAnyOrder.containsInAnyOrder;
import static org.hamcrest.collection.IsIterableContainingInOrder.contains;
import java.util.Arrays;
import java.util.Collection;
import java.util.List;
import java.util.function.Consumer;
import java.util.function.Function;
import java.util.stream.StreamSupport;
import org.hamcrest.Description;
import org.hamcrest.Matcher;
import org.hamcrest.TypeSafeMatcher;
/**
* An abstract {@link Matcher} that can be used to create new matchers that
* compare entities by their attributes.
*
* @author Miguel Reboiro Jato
*
* @param <T> the type of the entities to be matched.
*/
public abstract class IsEqualToEntity<T> extends TypeSafeMatcher<T> {
/**
* The expected entity.
*/
protected final T expected;
private Consumer<Description> describeTo;
/**
* Constructs a new instance of {@link IsEqualToEntity}.
*
* @param entity the expected tentity.
*/
public IsEqualToEntity(final T entity) {
this.expected = requireNonNull(entity);
}
@Override
public void describeTo(final Description description) {
if (this.describeTo != null)
this.describeTo.accept(description);
}
/**
* Adds a new description using the template:
* <p>
* {@code <expected class> entity with value '<expected>' for <attribute>}
* </p>
*
* @param attribute the name of the attribute compared.
* @param expected the expected value.
*/
protected void addTemplatedDescription(final String attribute, final Object expected) {
this.describeTo = d -> d.appendText(String.format(
"%s entity with value '%s' for %s",
this.expected.getClass().getSimpleName(),
expected, attribute
));
}
/**
* Adds as the description of this matcher the
* {@link Matcher#describeTo(Description)} method of other matcher.
*
* @param matcher the matcher whose description will be used.
*/
protected void addMatcherDescription(final Matcher<?> matcher) {
this.describeTo = matcher::describeTo;
}
/**
* Cleans the current description.
*/
protected void clearDescribeTo() {
this.describeTo = null;
}
protected <R> boolean checkAttribute(
final String attribute,
final Function<T, R> getter, final T actual,
final Function<R, Matcher<R>> matcherFactory
) {
final R expectedValue = getter.apply(this.expected);
final R actualValue = getter.apply(actual);
if (expectedValue == null && actualValue == null) {
return true;
} else if (expectedValue == null || actualValue == null) {
this.addTemplatedDescription(attribute, expectedValue);
return false;
} else {
final Matcher<R> matcher = matcherFactory.apply(expectedValue);
if (matcher.matches(actualValue)) {
return true;
} else {
this.addMatcherDescription(matcher);
return false;
}
}
}
/**
* Compares the expected and the actual value of an array attribute. The
* elements of the attribute will be checked using a custom matcher.
* If the comparison fails, the description of the error will be updated.
*
* @param attribute the name of the attribute compared.
* @param getter the getter function of the attribute.
* @param actual the actual entity being compared to the expected entity.
* @param matcherFactory a function that creates a matcher for the expected
* array values.
* @param <R> type of the value returned by the getter.
* @return {@code true} if the value of the expected and actual attributes
* are equals and {@code false} otherwise. If the result is {@code false},
* the current description will be updated.
*/
protected <R> boolean checkArrayAttribute(
final String attribute,
final Function<T, R[]> getter, final T actual,
final Function<R[], Matcher<Iterable<? extends R>>> matcherFactory
) {
final R[] expectedValue = getter.apply(this.expected);
final R[] actualValue = getter.apply(actual);
if (expectedValue == null && actualValue == null) {
return true;
} else if (expectedValue == null || actualValue == null) {
this.addTemplatedDescription(attribute, expectedValue);
return false;
} else {
final Matcher<Iterable<? extends R>> matcher =
matcherFactory.apply(expectedValue);
if (matcher.matches(asList(actualValue))) {
return true;
} else {
this.addMatcherDescription(matcher);
return false;
}
}
}
/**
* Compares the expected and the actual value of an iterable attribute. The
* elements of the attribute will be checked using a custom matcher.
* If the comparison fails, the description of the error will be updated.
*
* @param attribute the name of the attribute compared.
* @param getter the getter function of the attribute.
* @param actual the actual entity being compared to the expected entity.
* @param matcherFactory a function that creates a matcher for the expected
* iterable values.
* @param <R> type of the value returned by the getter.
* @return {@code true} if the value of the expected and actual attributes
* are equals and {@code false} otherwise. If the result is {@code false},
* the current description will be updated.
*/
protected <R> boolean checkIterableAttribute(
final String attribute,
final Function<T, Iterable<R>> getter, final T actual,
final Function<Iterable<R>, Matcher<Iterable<? extends R>>> matcherFactory
) {
final Iterable<R> expectedValue = getter.apply(this.expected);
final Iterable<R> actualValue = getter.apply(actual);
if (expectedValue == null && actualValue == null) {
return true;
} else if (expectedValue == null || actualValue == null) {
this.addTemplatedDescription(attribute, expectedValue);
return false;
} else {
final Matcher<Iterable<? extends R>> matcher =
matcherFactory.apply(expectedValue);
if (matcher.matches(actualValue)) {
return true;
} else {
this.addMatcherDescription(matcher);
return false;
}
}
}
/**
* Compares the expected and the actual value of an attribute. If the
* comparison fails, the description of the error will be updated.
*
* @param attribute the name of the attribute compared.
* @param getter the getter function of the attribute.
* @param actual the actual entity being compared to the expected entity.
* @param <R> type of the value returned by the getter.
* @return {@code true} if the value of the expected and actual attributes
* are equals and {@code false} otherwise. If the result is {@code false},
* the current description will be updated.
*/
protected <R> boolean checkAttribute(
final String attribute, final Function<T, R> getter, final T actual
) {
final R expectedValue = getter.apply(this.expected);
final R actualValue = getter.apply(actual);
if (expectedValue == null && actualValue == null) {
return true;
} else if (expectedValue == null || !expectedValue.equals(actualValue)) {
this.addTemplatedDescription(attribute, expectedValue);
return false;
} else {
return true;
}
}
/**
* Compares the expected and the actual value of an array attribute. If the
* comparison fails, the description of the error will be updated.
*
* @param attribute the name of the attribute compared.
* @param getter the getter function of the attribute.
* @param actual the actual entity being compared to the expected entity.
* @param <R> type of the value returned by the getter.
* @return {@code true} if the value of the expected and actual attributes
* are equals and {@code false} otherwise. If the result is {@code false},
* the current description will be updated.
*/
protected <R> boolean checkArrayAttribute(
final String attribute, final Function<T, R[]> getter, final T actual
) {
final R[] expectedValue = getter.apply(this.expected);
final R[] actualValue = getter.apply(actual);
if (expectedValue == null && actualValue == null) {
return true;
} else if (expectedValue == null || actualValue == null) {
this.addTemplatedDescription(attribute, expectedValue == null ? "null" : Arrays.toString(expectedValue));
return false;
} else if (!Arrays.equals(expectedValue, actualValue)) {
this.addTemplatedDescription(attribute, Arrays.toString(expectedValue));
return false;
} else
return true;
}
/**
* Compares the expected and the actual value of an int array attribute. If
* the comparison fails, the description of the error will be updated.
*
* @param attribute the name of the attribute compared.
* @param getter the getter function of the attribute.
* @param actual the actual entity being compared to the expected entity.
* @return {@code true} if the value of the expected and actual attributes
* are equals and {@code false} otherwise. If the result is {@code false},
* the current description will be updated.
*/
protected boolean checkIntArrayAttribute(
final String attribute, final Function<T, int[]> getter, final T actual
) {
final int[] expectedValue = getter.apply(this.expected);
final int[] actualValue = getter.apply(actual);
if (expectedValue == null && actualValue == null) {
return true;
} else if (expectedValue == null || actualValue == null) {
this.addTemplatedDescription(attribute, expectedValue == null ? "null" : Arrays.toString(expectedValue));
return false;
} else if (!Arrays.equals(expectedValue, actualValue)) {
this.addTemplatedDescription(attribute, Arrays.toString(expectedValue));
return false;
} else
return true;
}
/**
* Utility method that generates a {@link Matcher} that compares several
* entities.
*
* @param converter a function to create a matcher for an entity.
* @param entities the entities to be used as the expected values.
* @param <T> type of the entity.
* @return a new {@link Matcher} that compares several entities.
*/
@SafeVarargs
protected static <T> Matcher<Iterable<? extends T>> containsEntityInAnyOrder(
final Function<T, Matcher<? super T>> converter, final T ... entities
) {
final Collection<Matcher<? super T>> entitiesMatchers = stream(entities)
.map(converter)
.collect(toList());
return containsInAnyOrder(entitiesMatchers);
}
/**
* Utility method that generates a {@link Matcher} that compares several
* entities.
*
* @param converter a function to create a matcher for an entity.
* @param entities the entities to be used as the expected values.
* @param <T> type of the entity.
* @return a new {@link Matcher} that compares several entities.
*/
protected static <T> Matcher<Iterable<? extends T>> containsEntityInAnyOrder(
final Function<T, Matcher<? super T>> converter, final Iterable<T> entities
) {
final Collection<Matcher<? super T>> entitiesMatchers =
StreamSupport.stream(entities.spliterator(), false)
.map(converter)
.collect(toList());
return containsInAnyOrder(entitiesMatchers);
}
/**
* Utility method that generates a {@link Matcher} that compares several
* entities in the same received order.
*
* @param converter A function to create a matcher for an entity.
* @param entities The entities to be used as the expected values, in the
* order to be compared.
* @param <T> The type of the entity.
*
* @return A new {@link Matcher} that compares several entities in the same
* received order.
*/
@SafeVarargs
protected static <T> Matcher<Iterable<? extends T>> containsEntityInOrder(
final Function<T, Matcher<? super T>> converter, final T ... entities
) {
return contains(stream(entities).map(converter).collect(toList()));
}
/**
* Utility method that generates a {@link Matcher} that compares several
* entities in the same received order.
*
* @param converter A function to create a matcher for an entity.
* @param entities The entities to be used as the expected values, in the
* order to be compared.
* @param <T> The type of the entity.
*
* @return A new {@link Matcher} that compares several entities in the same
* received order.
*/
protected static <T> Matcher<Iterable<? extends T>> containsEntityInOrder(
final Function<T, Matcher<? super T>> converter, final Iterable<T> entities
) {
final List<Matcher<? super T>> matchersList =
StreamSupport.stream(entities.spliterator(), false)
.map(converter)
.collect(toList());
return contains(matchersList);
}
}
package es.uvigo.esei.xcs.domain.entities;
import static es.uvigo.esei.xcs.domain.entities.IsEqualsToPet.containsPetsWithoutRelationsInAnyOrder;
import org.hamcrest.Factory;
import org.hamcrest.Matcher;
public class IsEqualsToOwner extends IsEqualsToEntity<Owner> {
public class IsEqualToOwner extends IsEqualToEntity<Owner> {
private final boolean checkRelations;
public IsEqualsToOwner(Owner owner, boolean checkRelations) {
public IsEqualToOwner(Owner owner, boolean checkRelations) {
super(owner);
this.checkRelations = checkRelations;
}
......@@ -18,48 +16,42 @@ public class IsEqualsToOwner extends IsEqualsToEntity<Owner> {
this.clearDescribeTo();
if (actual == null) {
this.addTemplatedDescription("owner", expected.toString());
return false;
} else if (!expected.getLogin().equals(actual.getLogin())) {
this.addTemplatedDescription("login", expected.getLogin());
return false;
} else if (!expected.getPassword().equals(actual.getPassword())) {
this.addTemplatedDescription("password", expected.getPassword());
return false;
} else if (this.checkRelations) {
final Matcher<Iterable<? extends Pet>> petsMatcher =
containsPetsWithoutRelationsInAnyOrder(
expected.getPets().toArray(new Pet[0]));
if (petsMatcher.matches(actual.getPets())) {
this.addMatcherDescription(petsMatcher);
return true;
} else {
this.addTemplatedDescription("actual", expected.toString());
return false;
}
} else {
return true;
return checkAttribute("login", Owner::getLogin, actual)
&& checkAttribute("password", Owner::getPassword, actual)
&& (!this.checkRelations || checkIterableAttribute("pets", Owner::getPets, actual, IsEqualToPet::containsPetsWithoutRelationsInAnyOrder));
}
}
@Factory
public static IsEqualsToOwner equalsToOwner(Owner owner) {
return new IsEqualsToOwner(owner, true);
public static IsEqualToOwner equalToOwner(Owner owner) {
return new IsEqualToOwner(owner, true);
}
@Factory
public static IsEqualsToOwner equalsToOwnerWithoutRelations(Owner owner) {
return new IsEqualsToOwner(owner, false);
public static IsEqualToOwner equalToOwnerWithoutRelations(Owner owner) {
return new IsEqualToOwner(owner, false);
}
@Factory
public static Matcher<Iterable<? extends Owner>> containsOwnersInAnyOrder(Owner ... owners) {
return containsEntityInAnyOrder(IsEqualsToOwner::equalsToOwner, owners);
return containsEntityInAnyOrder(IsEqualToOwner::equalToOwner, owners);
}
@Factory
public static Matcher<Iterable<? extends Owner>> containsOwnersWithoutRelationsInAnyOrder(Owner ... owners) {
return containsEntityInAnyOrder(IsEqualsToOwner::equalsToOwnerWithoutRelations, owners);
return containsEntityInAnyOrder(IsEqualToOwner::equalToOwnerWithoutRelations, owners);
}
@Factory
public static Matcher<Iterable<? extends Owner>> containsOwnersInAnyOrder(Iterable<Owner> owners) {
return containsEntityInAnyOrder(IsEqualToOwner::equalToOwner, owners);
}
@Factory
public static Matcher<Iterable<? extends Owner>> containsOwnersWithoutRelationsInAnyOrder(Iterable<Owner> owners) {
return containsEntityInAnyOrder(IsEqualToOwner::equalToOwnerWithoutRelations, owners);
}
}
package es.uvigo.esei.xcs.domain.entities;
import org.hamcrest.Factory;
import org.hamcrest.Matcher;
public class IsEqualToPet extends IsEqualToEntity<Pet> {
private final boolean checkRelations;
public IsEqualToPet(Pet pet, boolean checkRelations) {
super(pet);
this.checkRelations = checkRelations;
}
@Override
protected boolean matchesSafely(Pet actual) {
this.clearDescribeTo();
if (actual == null) {
this.addTemplatedDescription("actual", expected.toString());
return false;
} else {
return checkAttribute("id", Pet::getId, actual)
&& checkAttribute("name", Pet::getName, actual)
&& checkAttribute("animal", Pet::getAnimal, actual)
&& checkAttribute("birth", Pet::getBirth, actual)
&& (!this.checkRelations || checkAttribute("owner", Pet::getOwner, actual, IsEqualToOwner::equalToOwnerWithoutRelations));
}
}
@Factory
public static IsEqualToPet equalToPet(Pet pet) {
return new IsEqualToPet(pet, true);
}
@Factory
public static IsEqualToPet equalToPetWithoutRelations(Pet pet) {
return new IsEqualToPet(pet, false);
}
@Factory
public static Matcher<Iterable<? extends Pet>> containsPetsInAnyOrder(Pet ... pets) {
return containsEntityInAnyOrder(IsEqualToPet::equalToPet, pets);
}
@Factory
public static Matcher<Iterable<? extends Pet>> containsPetsWithoutRelationsInAnyOrder(Pet ... pets) {
return containsEntityInAnyOrder(IsEqualToPet::equalToPetWithoutRelations, pets);
}
@Factory
public static Matcher<Iterable<? extends Pet>> containsPetsInAnyOrder(Iterable<Pet> pets) {
return containsEntityInAnyOrder(IsEqualToPet::equalToPet, pets);
}
@Factory
public static Matcher<Iterable<? extends Pet>> containsPetsWithoutRelationsInAnyOrder(Iterable<Pet> pets) {
return containsEntityInAnyOrder(IsEqualToPet::equalToPetWithoutRelations, pets);
}
}
package es.uvigo.esei.xcs.domain.entities;
import static java.util.Arrays.stream;
import static java.util.stream.Collectors.toList;
import static org.hamcrest.collection.IsIterableContainingInAnyOrder.containsInAnyOrder;
import java.util.Collection;
import java.util.function.Consumer;
import java.util.function.Function;
import org.hamcrest.Description;
import org.hamcrest.Matcher;
import org.hamcrest.TypeSafeMatcher;
public abstract class IsEqualsToEntity<T> extends TypeSafeMatcher<T> {
protected final T expected;
private Consumer<Description> describeTo;
public IsEqualsToEntity(T entity) {
this.expected = entity;
}
@Override
public void describeTo(Description description) {
if (this.describeTo != null) {
this.describeTo.accept(description);
}
}
protected void addTemplatedDescription(String attribute, Object expected) {
this.describeTo = d -> d.appendText(String.format(
"%s entity with value '%s' for %s",
this.expected.getClass().getSimpleName(),
expected, attribute
));
}
protected void addMatcherDescription(Matcher<?> matcher) {
this.describeTo = matcher::describeTo;
}
protected void clearDescribeTo() {
this.describeTo = null;
}
@SafeVarargs
protected static <T> Matcher<Iterable<? extends T>> containsEntityInAnyOrder(
Function<T, Matcher<? super T>> converter, T ... entities
) {
final Collection<Matcher<? super T>> ownerMatchers = stream(entities)
.map(converter)
.collect(toList());
return containsInAnyOrder(ownerMatchers);
}
}
package es.uvigo.esei.xcs.domain.entities;
import static es.uvigo.esei.xcs.domain.entities.IsEqualsToOwner.equalsToOwnerWithoutRelations;
import org.hamcrest.Factory;
import org.hamcrest.Matcher;
public class IsEqualsToPet extends IsEqualsToEntity<Pet> {
private final boolean checkRelations;
public IsEqualsToPet(Pet pet, boolean checkRelations) {
super(pet);
this.checkRelations = checkRelations;
}
@Override
protected boolean matchesSafely(Pet actual) {
this.clearDescribeTo();
if (actual == null) {
this.addTemplatedDescription("pet", expected.toString());
return false;
} else if (this.expected.getId() != actual.getId()) {
this.addTemplatedDescription("id", expected.getId());
return false;
} else if (!this.expected.getName().equals(actual.getName())) {
this.addTemplatedDescription("name", expected.getName());
return false;
} else if (!this.expected.getAnimal().equals(actual.getAnimal())) {
this.addTemplatedDescription("animal", expected.getAnimal());
return false;
} else if (this.expected.getBirth().getTime() != actual.getBirth().getTime()) {
this.addTemplatedDescription("birth", expected.getBirth());
return false;
} else if (this.checkRelations) {
final IsEqualsToOwner equalsToOwner = equalsToOwnerWithoutRelations(this.expected.getOwner());
if (equalsToOwner.matchesSafely(actual.getOwner())) {
return true;
} else {
this.addMatcherDescription(equalsToOwner);
return false;
}
} else {
return true;
}
}
@Factory
public static IsEqualsToPet equalsToPet(Pet pet) {
return new IsEqualsToPet(pet, true);
}
@Factory
public static IsEqualsToPet equalsToPetWithoutRelations(Pet pet) {
return new IsEqualsToPet(pet, false);
}
@Factory
public static Matcher<Iterable<? extends Pet>> containsPetsInAnyOrder(Pet ... pets) {
return containsEntityInAnyOrder(IsEqualsToPet::equalsToPet, pets);
}
@Factory
public static Matcher<Iterable<? extends Pet>> containsPetsWithoutRelationsInAnyOrder(Pet ... pets) {
return containsEntityInAnyOrder(IsEqualsToPet::equalsToPetWithoutRelations, pets);
}
}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment