From 8891f4696254e5a2b37491daa62d027a54de82a5 Mon Sep 17 00:00:00 2001 From: Jan Ouwens Date: Mon, 16 Sep 2024 12:55:49 +0200 Subject: [PATCH] Removes FieldAccessor --- .../reflection/vintage/FieldAccessor.java | 103 ------------ .../reflection/vintage/FieldModifier.java | 7 +- .../reflection/vintage/ObjectAccessor.java | 3 +- .../architecture/ArchitectureTest.java | 4 - .../reflection/vintage/FieldAccessorTest.java | 154 ------------------ 5 files changed, 6 insertions(+), 265 deletions(-) delete mode 100644 equalsverifier-core/src/main/java/nl/jqno/equalsverifier/internal/reflection/vintage/FieldAccessor.java delete mode 100644 equalsverifier-core/src/test/java/nl/jqno/equalsverifier/internal/reflection/vintage/FieldAccessorTest.java diff --git a/equalsverifier-core/src/main/java/nl/jqno/equalsverifier/internal/reflection/vintage/FieldAccessor.java b/equalsverifier-core/src/main/java/nl/jqno/equalsverifier/internal/reflection/vintage/FieldAccessor.java deleted file mode 100644 index 6ee95b3b4..000000000 --- a/equalsverifier-core/src/main/java/nl/jqno/equalsverifier/internal/reflection/vintage/FieldAccessor.java +++ /dev/null @@ -1,103 +0,0 @@ -package nl.jqno.equalsverifier.internal.reflection.vintage; - -import static nl.jqno.equalsverifier.internal.util.Rethrow.rethrow; - -import edu.umd.cs.findbugs.annotations.SuppressFBWarnings; -import java.lang.reflect.Field; -import java.lang.reflect.Modifier; -import nl.jqno.equalsverifier.internal.exceptions.ReflectionException; - -/** Provides reflective access to one field of an object. */ -public final class FieldAccessor { - - private final Field field; - - /** Private constructor. Call {@link #of(Field)} to instantiate. */ - private FieldAccessor(Field field) { - this.field = field; - } - - /** - * Factory method. - * - * @param field The field to access. - * @return A {@link FieldAccessor} for {@link #field}. - */ - public static FieldAccessor of(Field field) { - return new FieldAccessor(field); - } - - /** @return The field itself. */ - @SuppressFBWarnings(value = "EI_EXPOSE_REP", justification = "Can't defensively copy a Field.") - public Field getField() { - return field; - } - - /** @return The field's type. */ - public Class getFieldType() { - return field.getType(); - } - - /** @return The field's name. */ - public String getFieldName() { - return field.getName(); - } - - /** @return Whether the field is of a primitive type. */ - public boolean fieldIsPrimitive() { - return getFieldType().isPrimitive(); - } - - /** @return Whether the field is marked with the final modifier. */ - public boolean fieldIsFinal() { - return Modifier.isFinal(field.getModifiers()); - } - - /** @return Whether the field is marked with the static modifier. */ - public boolean fieldIsStatic() { - return Modifier.isStatic(field.getModifiers()); - } - - /** @return Whether the field is marked with the transient modifier. */ - public boolean fieldIsTransient() { - return Modifier.isTransient(field.getModifiers()); - } - - /** @return Whether the field is an enum with a single value. */ - public boolean fieldIsEmptyOrSingleValueEnum() { - Class type = field.getType(); - return type.isEnum() && type.getEnumConstants().length <= 1; - } - - /** - * Tries to get the field's value. - * - * @param object The object that contains the field whose value we want to get. - * @return The field's value. - * @throws ReflectionException If the operation fails. - */ - @SuppressFBWarnings( - value = "DP_DO_INSIDE_DO_PRIVILEGED", - justification = "Only called in test code, not production." - ) - public Object get(Object object) { - field.setAccessible(true); - return rethrow(() -> field.get(object)); - } - - /** - * Determines whether the field can be modified using reflection. - * - * @return Whether or not the field can be modified reflectively. - */ - public boolean canBeModifiedReflectively() { - if (field.isSynthetic()) { - return false; - } - int modifiers = field.getModifiers(); - if (Modifier.isFinal(modifiers) && Modifier.isStatic(modifiers)) { - return false; - } - return true; - } -} diff --git a/equalsverifier-core/src/main/java/nl/jqno/equalsverifier/internal/reflection/vintage/FieldModifier.java b/equalsverifier-core/src/main/java/nl/jqno/equalsverifier/internal/reflection/vintage/FieldModifier.java index 343dc7edf..d2c632732 100644 --- a/equalsverifier-core/src/main/java/nl/jqno/equalsverifier/internal/reflection/vintage/FieldModifier.java +++ b/equalsverifier-core/src/main/java/nl/jqno/equalsverifier/internal/reflection/vintage/FieldModifier.java @@ -6,6 +6,7 @@ import java.util.LinkedHashSet; import nl.jqno.equalsverifier.internal.exceptions.ReflectionException; import nl.jqno.equalsverifier.internal.prefabvalues.TypeTag; +import nl.jqno.equalsverifier.internal.reflection.FieldProbe; import nl.jqno.equalsverifier.internal.util.PrimitiveMappers; public final class FieldModifier { @@ -122,11 +123,11 @@ public void changeField( } private void change(FieldChanger changer, boolean includeStatic) { - FieldAccessor accessor = FieldAccessor.of(field); - if (!accessor.canBeModifiedReflectively()) { + FieldProbe probe = FieldProbe.of(field); + if (!probe.canBeModifiedReflectively()) { return; } - if (!includeStatic && accessor.fieldIsStatic()) { + if (!includeStatic && probe.isStatic()) { return; } diff --git a/equalsverifier-core/src/main/java/nl/jqno/equalsverifier/internal/reflection/vintage/ObjectAccessor.java b/equalsverifier-core/src/main/java/nl/jqno/equalsverifier/internal/reflection/vintage/ObjectAccessor.java index 2445b1c70..aafe272e5 100644 --- a/equalsverifier-core/src/main/java/nl/jqno/equalsverifier/internal/reflection/vintage/ObjectAccessor.java +++ b/equalsverifier-core/src/main/java/nl/jqno/equalsverifier/internal/reflection/vintage/ObjectAccessor.java @@ -4,6 +4,7 @@ import java.util.LinkedHashSet; import java.util.function.Predicate; import nl.jqno.equalsverifier.internal.prefabvalues.TypeTag; +import nl.jqno.equalsverifier.internal.reflection.FieldProbe; import nl.jqno.equalsverifier.internal.reflection.RecordsHelper; /** @@ -77,7 +78,7 @@ public Class type() { */ @SuppressWarnings("unchecked") public T getField(Field field) { - return (T) FieldAccessor.of(field).get(object); + return (T) FieldProbe.of(field).getValue(object); } /** diff --git a/equalsverifier-core/src/test/java/nl/jqno/equalsverifier/internal/architecture/ArchitectureTest.java b/equalsverifier-core/src/test/java/nl/jqno/equalsverifier/internal/architecture/ArchitectureTest.java index 19656f580..c4f12e785 100644 --- a/equalsverifier-core/src/test/java/nl/jqno/equalsverifier/internal/architecture/ArchitectureTest.java +++ b/equalsverifier-core/src/test/java/nl/jqno/equalsverifier/internal/architecture/ArchitectureTest.java @@ -8,7 +8,6 @@ import nl.jqno.equalsverifier.internal.reflection.instantiation.VintageSubjectCreator; import nl.jqno.equalsverifier.internal.reflection.instantiation.VintageValueProvider; import nl.jqno.equalsverifier.internal.reflection.vintage.ClassAccessor; -import nl.jqno.equalsverifier.internal.reflection.vintage.FieldAccessor; import nl.jqno.equalsverifier.internal.reflection.vintage.FieldModifier; import nl.jqno.equalsverifier.internal.reflection.vintage.ObjectAccessor; import nl.jqno.equalsverifier.internal.reflection.vintage.PrefabValues; @@ -47,9 +46,6 @@ public final class ArchitectureTest { .areAssignableTo(ObjectAccessor.class) .orShould() .accessClassesThat() - .areAssignableTo(FieldAccessor.class) - .orShould() - .accessClassesThat() .areAssignableTo(FieldModifier.class) .orShould() .accessClassesThat() diff --git a/equalsverifier-core/src/test/java/nl/jqno/equalsverifier/internal/reflection/vintage/FieldAccessorTest.java b/equalsverifier-core/src/test/java/nl/jqno/equalsverifier/internal/reflection/vintage/FieldAccessorTest.java deleted file mode 100644 index e3157c23c..000000000 --- a/equalsverifier-core/src/test/java/nl/jqno/equalsverifier/internal/reflection/vintage/FieldAccessorTest.java +++ /dev/null @@ -1,154 +0,0 @@ -package nl.jqno.equalsverifier.internal.reflection.vintage; - -import static org.junit.jupiter.api.Assertions.*; - -import java.lang.reflect.Field; -import nl.jqno.equalsverifier.testhelpers.types.TypeHelper.*; -import org.junit.jupiter.api.Test; - -public class FieldAccessorTest { - - private static final String FIELD_NAME = "field"; - - @Test - public void getField() throws NoSuchFieldException { - ObjectContainer foo = new ObjectContainer(); - Field field = foo.getClass().getDeclaredField(FIELD_NAME); - FieldAccessor fieldAccessor = FieldAccessor.of(field); - assertSame(field, fieldAccessor.getField()); - } - - @Test - public void getFieldType() { - ObjectContainer foo = new ObjectContainer(); - FieldAccessor fieldAccessor = getAccessorFor(foo, FIELD_NAME); - assertEquals(Object.class, fieldAccessor.getFieldType()); - } - - @Test - public void getFieldName() { - ObjectContainer foo = new ObjectContainer(); - FieldAccessor fieldAccessor = getAccessorFor(foo, FIELD_NAME); - assertEquals(FIELD_NAME, fieldAccessor.getFieldName()); - } - - @Test - public void isNotPrimitive() { - ObjectContainer foo = new ObjectContainer(); - FieldAccessor fieldAccessor = getAccessorFor(foo, FIELD_NAME); - assertFalse(fieldAccessor.fieldIsPrimitive()); - } - - @Test - public void isPrimitive() { - PrimitiveContainer foo = new PrimitiveContainer(); - FieldAccessor fieldAccessor = getAccessorFor(foo, FIELD_NAME); - assertTrue(fieldAccessor.fieldIsPrimitive()); - } - - @Test - public void isNotFinal() { - ObjectContainer foo = new ObjectContainer(); - FieldAccessor fieldAccessor = getAccessorFor(foo, FIELD_NAME); - assertFalse(fieldAccessor.fieldIsFinal()); - } - - @Test - public void isFinal() { - FinalContainer foo = new FinalContainer(); - FieldAccessor fieldAccessor = getAccessorFor(foo, FIELD_NAME); - assertTrue(fieldAccessor.fieldIsFinal()); - } - - @Test - public void isNotStatic() { - ObjectContainer foo = new ObjectContainer(); - FieldAccessor fieldAccessor = getAccessorFor(foo, FIELD_NAME); - assertFalse(fieldAccessor.fieldIsStatic()); - } - - @Test - public void isStatic() { - StaticContainer foo = new StaticContainer(); - FieldAccessor fieldAccessor = getAccessorFor(foo, FIELD_NAME); - assertTrue(fieldAccessor.fieldIsStatic()); - } - - @Test - public void isNotTransient() { - ObjectContainer foo = new ObjectContainer(); - FieldAccessor fieldAccessor = getAccessorFor(foo, FIELD_NAME); - assertFalse(fieldAccessor.fieldIsTransient()); - } - - @Test - public void isTransient() { - TransientContainer foo = new TransientContainer(); - FieldAccessor fieldAccessor = getAccessorFor(foo, FIELD_NAME); - assertTrue(fieldAccessor.fieldIsTransient()); - } - - @Test - public void isNotEnum() { - PrimitiveContainer foo = new PrimitiveContainer(); - FieldAccessor fieldAccessor = getAccessorFor(foo, FIELD_NAME); - assertFalse(fieldAccessor.fieldIsEmptyOrSingleValueEnum()); - } - - @Test - public void isEnumButNotSingleValue() { - EnumContainer foo = new EnumContainer(); - FieldAccessor fieldAccessor = getAccessorFor(foo, "twoElementEnum"); - assertFalse(fieldAccessor.fieldIsEmptyOrSingleValueEnum()); - } - - @Test - public void isSingleValueEnum() { - EnumContainer foo = new EnumContainer(); - FieldAccessor fieldAccessor = getAccessorFor(foo, "oneElementEnum"); - assertTrue(fieldAccessor.fieldIsEmptyOrSingleValueEnum()); - } - - @Test - public void isEmptyEnum() { - EnumContainer foo = new EnumContainer(); - FieldAccessor fieldAccessor = getAccessorFor(foo, "emptyEnum"); - assertTrue(fieldAccessor.fieldIsEmptyOrSingleValueEnum()); - } - - @Test - public void getValuePrimitive() { - PrimitiveContainer foo = new PrimitiveContainer(); - foo.field = 10; - Object value = getValue(foo, "field"); - assertEquals(10, value); - } - - @Test - public void getValueObject() { - Object object = new Object(); - ObjectContainer foo = new ObjectContainer(); - foo.field = object; - Object value = getValue(foo, FIELD_NAME); - assertEquals(object, value); - } - - @Test - public void getPrivateValue() { - PrivateObjectContainer foo = new PrivateObjectContainer(); - getValue(foo, FIELD_NAME); - } - - private Object getValue(Object object, String fieldName) { - return getAccessorFor(object, fieldName).get(object); - } - - private FieldAccessor getAccessorFor(Object object, String fieldName) { - try { - Field field = object.getClass().getDeclaredField(fieldName); - return FieldAccessor.of(field); - } catch (NoSuchFieldException e) { - throw new IllegalArgumentException("fieldName: " + fieldName); - } - } -}