001package org.junit.runners.model;
002
003import java.lang.annotation.Annotation;
004import java.lang.reflect.Field;
005
006import org.junit.runners.BlockJUnit4ClassRunner;
007
008/**
009 * Represents a field on a test class (currently used only for Rules in
010 * {@link BlockJUnit4ClassRunner}, but custom runners can make other uses)
011 *
012 * @since 4.7
013 */
014public class FrameworkField extends FrameworkMember<FrameworkField> {
015    private final Field field;
016
017    /**
018     * Returns a new {@code FrameworkField} for {@code field}.
019     *
020     * <p>Access relaxed to {@code public} since version 4.13.1.
021     */
022    public FrameworkField(Field field) {
023        if (field == null) {
024            throw new NullPointerException(
025                    "FrameworkField cannot be created without an underlying field.");
026        }
027        this.field = field;
028
029        if (isPublic()) {
030            // This field could be a public field in a package-scope base class
031            try {
032                field.setAccessible(true);
033            } catch (SecurityException e) {
034                // We may get an IllegalAccessException when we try to access the field
035            }
036        }
037    }
038
039    @Override
040    public String getName() {
041        return getField().getName();
042    }
043
044    public Annotation[] getAnnotations() {
045        return field.getAnnotations();
046    }
047
048    public <T extends Annotation> T getAnnotation(Class<T> annotationType) {
049        return field.getAnnotation(annotationType);
050    }
051
052    @Override
053    public boolean isShadowedBy(FrameworkField otherMember) {
054        return otherMember.getName().equals(getName());
055    }
056
057    @Override
058    boolean isBridgeMethod() {
059        return false;
060    }
061
062    @Override
063    protected int getModifiers() {
064        return field.getModifiers();
065    }
066
067    /**
068     * @return the underlying java Field
069     */
070    public Field getField() {
071        return field;
072    }
073
074    /**
075     * @return the underlying Java Field type
076     * @see java.lang.reflect.Field#getType()
077     */
078    @Override
079    public Class<?> getType() {
080        return field.getType();
081    }
082    
083    @Override
084    public Class<?> getDeclaringClass() {
085        return field.getDeclaringClass();
086    }
087
088    /**
089     * Attempts to retrieve the value of this field on {@code target}
090     */
091    public Object get(Object target) throws IllegalArgumentException, IllegalAccessException {
092        return field.get(target);
093    }
094
095    @Override
096    public String toString() {
097        return field.toString();
098    }
099}