Package za.co.enerweb.toolbox.reflection

Source Code of za.co.enerweb.toolbox.reflection.PropertyUtils

package za.co.enerweb.toolbox.reflection;

import static java.lang.String.format;

import java.beans.BeanInfo;
import java.beans.IntrospectionException;
import java.beans.Introspector;
import java.beans.PropertyDescriptor;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;

import lombok.val;

import org.apache.commons.lang.StringUtils;

import za.co.enerweb.toolbox.objects.ObjectUtils;

/**
* Commons property utils does uses the plain Introspector which sometimes has
* weird capitilation of the first character of a field eg. it thinks iProperty
* should be IProperty ?!
*/
public class PropertyUtils {

    /**
     * @return all the properties that have getters and setters
     */
    public static List<String> getAllProperties(Class<?> type) {
        List<PropertyDescriptor> propertyDescriptors
            = getAllPropertyDescriptors(type);
        List<String> ret = new ArrayList<String>(propertyDescriptors.size());
        for (PropertyDescriptor propertyDescriptor : propertyDescriptors) {
            ret.add(propertyDescriptor.getName());
        }
        return ret;
    }

    public static List<PropertyDescriptor> getAllPropertyDescriptors(
        Class<?> type) {
        BeanInfo beanInfo = getBeanInfo(type);
        PropertyDescriptor[] propertyDescriptors = beanInfo
            .getPropertyDescriptors();
        List<PropertyDescriptor> ret = new ArrayList<PropertyDescriptor>(
            propertyDescriptors.length);
        for (PropertyDescriptor propertyDescriptor : propertyDescriptors) {
            if (propertyDescriptor.getWriteMethod() != null) {
                propertyDescriptor.setName(StringUtils
                    .uncapitalize(propertyDescriptor.getName()));
                ret.add(propertyDescriptor);
            }
        }
        return ret;
    }

    public static List<PropertyDescriptor> getAllReadablePropertyDescriptors(
        Class<?> type) {
        BeanInfo beanInfo = getBeanInfo(type);
        PropertyDescriptor[] propertyDescriptors = beanInfo
            .getPropertyDescriptors();
        List<PropertyDescriptor> ret = new ArrayList<PropertyDescriptor>(
            propertyDescriptors.length);
        for (PropertyDescriptor propertyDescriptor : propertyDescriptors) {
            propertyDescriptor.setName(StringUtils
                .uncapitalize(propertyDescriptor.getName()));
            ret.add(propertyDescriptor);
        }
        return ret;
    }

    private static BeanInfo getBeanInfo(Class<?> type) {
        try {
            BeanInfo beanInfo = Introspector.getBeanInfo(type);
            return beanInfo;
        } catch (IntrospectionException e) {
            throw new IllegalStateException("Could not introspect " + type, e);
        }
    }

    /**
     * Generic way to get a property on a object TODO: support isBoolean methods
     *
     * @throws InvalidPropertyException if then property could not be accessed
     */
    @SuppressWarnings("unchecked")
    public static <T> T getProperty(final Object bean, final String fieldName) {

        try {
            return (T) getPropertyDescriptor(bean, fieldName).getReadMethod()
                .invoke(bean);
        } catch (Exception e) {
            throw new InvalidPropertyException("Could not get "
                + bean.getClass().getSimpleName() + "." + fieldName, e);
        }
    }

    /**
     * Generic way to set a property on a object
     * @throws InvalidPropertyException if then property could not be accessed
     */
    public static void setProperty(final Object bean, final String fieldName,
        final Object value) {
        try {
            getPropertyDescriptor(bean, fieldName).getWriteMethod().invoke(
                bean, value);
        } catch (Exception e) {
            throw new InvalidPropertyException("Could not set "
                + bean.getClass().getSimpleName() + "." + fieldName + " to "
                + value, e);
        }
    }

    public static PropertyDescriptor getPropertyDescriptor(final Object object,
        final String fieldName) {
        BeanInfo beanInfo = getBeanInfo(object.getClass());
        PropertyDescriptor[] propertyDescriptors = beanInfo
            .getPropertyDescriptors();
        for (PropertyDescriptor propertyDescriptor : propertyDescriptors) {
            String name = StringUtils
                .uncapitalize(propertyDescriptor.getName());
            if (name.equals(fieldName)) {
                return propertyDescriptor;
                // } else {
                // System.out.println(fieldName + " != " + name);
            }
        }
        throw new InvalidPropertyException("Unknown property: " + fieldName);
    }

    /**
     * @param type
     * @return true if each property of b1 is equal to the corresponding
     *         property of b2
     */
    public static <T> boolean equalBeans(T b1, T b2,
        Class<T> type) {
        if (!ObjectUtils.equals(b1, b2)) {
            return false;
        }
        List<PropertyDescriptor> props = getAllPropertyDescriptors(type);
        for (PropertyDescriptor prop : props) {
            val readMethod = prop.getReadMethod();
            try {
                Object v1 = readMethod.invoke(b1);
                Object v2 = readMethod.invoke(b2);
                if (!ObjectUtils.equals(v1, v2)) {
                    return false;
                }
            } catch (Exception e) {
                new InvalidPropertyException("Could not compare beans of " +
                    "type " + type.getName(), e);
            }
        }
        return true;
    }

    public static <T> void assertEqualBeans(T b1, T b2,
        Class<T> type) throws AssertionError {
        if (!ObjectUtils.equals(b1, b2)) {
            throw new AssertionError(b1 + " != "
                + b2 + " (using Object.equals())");
        }
        List<PropertyDescriptor> props = getAllPropertyDescriptors(type);
        for (PropertyDescriptor prop : props) {
            val readMethod = prop.getReadMethod();
            try {
                Object v1 = readMethod.invoke(b1);
                Object v2 = readMethod.invoke(b2);
                if (!ObjectUtils.equals(v1, v2)) {
                    throw new AssertionError(format(
                        "%s.%s() = %s != %s.%s() = %s",
                        b1, readMethod.getName(), v1,
                        b2, readMethod.getName(), v2));
                }
            } catch (Exception e) {
                new InvalidPropertyException("Could not compare beans of " +
                    "type " + type.getName(), e);
            }
        }
    }

    // if you wanna make a Set<T> version of this, you'll have
    // to check that the sets contains each other
    public static <T> boolean equalBeans(List<T> bl1, List<T> bl2,
        Class<T> type) {
        if (bl1.size() != bl2.size()) {
            return false;
        }
        Iterator<T> i1 = bl1.iterator();
        Iterator<T> i2 = bl2.iterator();
        while (i1.hasNext() && i2.hasNext()) {
            if (!equalBeans(i1.next(), i2.next(), type)) {
                return false;
            }
        }
        return true;
    }

    public static <T> void assertEqualBeans(List<T> bl1, List<T> bl2,
        Class<T> type) throws AssertionError {
        if (bl1.size() != bl2.size()) {
            throw new AssertionError("Lists are not the same length.");
        }
        Iterator<T> i1 = bl1.iterator();
        Iterator<T> i2 = bl2.iterator();
        while (i1.hasNext() && i2.hasNext()) {
            assertEqualBeans(i1.next(), i2.next(), type);
        }
    }
}
TOP

Related Classes of za.co.enerweb.toolbox.reflection.PropertyUtils

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.