
cn.featherfly.common.bean.BeanDescriptor Maven / Gradle / Ivy
package cn.featherfly.common.bean;
import java.lang.annotation.Annotation;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.util.ArrayList;
import java.util.Collection;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import org.apache.commons.collections.map.ListOrderedMap;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import cn.featherfly.common.bean.condition.BeanPropertyMatcher;
import cn.featherfly.common.lang.ClassUtils;
import cn.featherfly.common.lang.CollectionUtils;
import cn.featherfly.common.lang.ServiceLoaderUtils;
/**
*
* java bean 的描述信息
*
*
* @author 钟冀
* @param 描述的类型
*/
public class BeanDescriptor {
private static final Logger LOGGER = LoggerFactory.getLogger(BeanDescriptor.class);
private static final Map, BeanDescriptor>> BEAN_DESCRIPTORS =
new ConcurrentHashMap, BeanDescriptor>>();
private static final BeanPropertyFactory FACTORY = ServiceLoaderUtils.load(BeanPropertyFactory.class
, new ReflectionBeanPropertyFactory());
// private static BeanPropertyFactory factory = new ReflectionBeanPropertyFactory();
//
// static {
// ServiceLoader serviceLoader = ServiceLoader.load(BeanPropertyFactory.class);
// List factorys = new ArrayList();
// for (BeanPropertyFactory factory : serviceLoader) {
// factorys.add(factory);
// }
// if (factorys.size() > 1) {
// throw new IllegalArgumentException("找到多个BeanPropertyFactory实现 -> " + factorys) ;
// }
// if (factorys.isEmpty()) {
// factory = new ReflectionBeanPropertyFactory();
// } else {
// factory = factorys.get(0);
// }
// }
// private Map beanProperties = new HashMap(0);
private ListOrderedMap beanProperties = new ListOrderedMap();
/**
* 句号(.)
*/
protected static final String DOT = "." ;
/**
* @param type 类型
*/
protected BeanDescriptor(Class type) {
this.type = type;
this.initField(this.type);
}
//从field开始初始化
private void initField(Class> parent) {
// TODO 从field查找完成再查找set,get方法,单纯的设置、读取方法,没有field,用于动态读取、设置
if (null == parent || parent == Object.class) {
return ;
}
Field[] fields = parent.getDeclaredFields();
for (Field field : fields) {
Method getter = ClassUtils.getGetter(field, this.type);
Method setter = ClassUtils.getSetter(field, this.type);
if (getter != null || setter != null) {
BeanProperty> prop = FACTORY.create(this.type, field, setter, getter);
beanProperties.put(prop.getName(), prop);
if (LOGGER.isTraceEnabled() && parent != this.type) {
LOGGER.trace("类{}从父类{}中继承的属性:[{}]", new Object[]{this.type.getName()
, parent.getName(), prop.getName()});
}
}
}
//到父类中查找属性
initField(parent.getSuperclass());
}
// // 初始化动态set get方法
// private void initMethod() {
// for (Method method : this.type.getMethods()) {
// if (ClassUtils.isGetter(method) && beanProperties.containsKey(method.getName())) {
//
// }
// }
// for (Method method : this.type.getMethods()) {
// if (ClassUtils.isSetter(method)) {
//
// }
// }
// }
/**
* @return 返回beanProperties
*/
@SuppressWarnings("unchecked")
public Collection> getBeanProperties() {
return beanProperties.values();
}
/**
*
* 返回指定索引属性.
*
* @param index 索引
* @return 指定属性
*/
public BeanProperty> getBeanProperty(int index) {
return (BeanProperty>) beanProperties.getValue(index);
}
/**
*
* 返回指定属性.
* 如果没有则抛出NoSuchPropertyException异常
*
* @param name 属性名
* @return 指定属性
*/
public BeanProperty> getBeanProperty(String name) {
BeanProperty> property = (BeanProperty>) beanProperties.get(name);
if (property == null) {
throw new NoSuchPropertyException(type, name);
}
return property;
}
/**
*
* 返回指定子孙属性.
* 如果没有则抛出NoSuchPropertyException异常
*
* @param name 属性名
* @return 指定属性
*/
public BeanProperty> getChildBeanProperty(String name) {
if (name.contains(DOT)) {
String currentPropertyName = name.substring(0, name.indexOf(DOT));
String innerPropertyName = name.substring(name.indexOf(DOT) + 1);
BeanProperty> property = getBeanProperty(currentPropertyName);
BeanDescriptor> propertyDescriptor = getBeanDescriptor(property.getType());
return propertyDescriptor.getChildBeanProperty(innerPropertyName);
} else {
return getBeanProperty(name);
}
}
/**
*
* 查找并返回第一个符合条件BeanProperty.
* 如果没有则返回null.
*
* @param condition 条件判断
* @return 第一个符合条件BeanProperty
*/
public BeanProperty> findBeanProperty(BeanPropertyMatcher condition) {
for (BeanProperty> beanProperty : getBeanProperties()) {
if (condition.match(beanProperty)) {
return beanProperty;
}
}
return null;
}
/**
*
* 查找并返回所有符合条件BeanProperty的集合.
* 如果没有则返回一个长度为0的集合.
*
* @param condition 条件判断
* @return 所有符合条件BeanProperty的集合
*/
public Collection> findBeanPropertys(BeanPropertyMatcher condition) {
Collection> coll = new ArrayList<>();
for (BeanProperty> beanProperty : getBeanProperties()) {
if (condition.match(beanProperty)) {
coll.add(beanProperty);
}
}
return coll;
}
/**
*
* 设置属性
*
* @param obj 目标对象
* @param name 属性名称
* @param value 属性值
*/
@SuppressWarnings("unchecked")
public void setProperty(T obj, String name, Object value) {
if (name.contains(DOT)) {
String currentPropertyName = name.substring(0, name.indexOf(DOT));
String innerPropertyName = name.substring(name.indexOf(DOT) + 1);
BeanProperty> property = getBeanProperty(currentPropertyName);
@SuppressWarnings("rawtypes")
BeanDescriptor propertyDescriptor = getBeanDescriptor(property.getType());
Object propertyValue = property.getValue(obj);
//中间层次为空,使用默认构造函数生成一个空对象
if (propertyValue == null) {
try {
if (property.getType() == Map.class) {
LOGGER.trace("类{}的属性[{}]为空,对象为MAP接口,自动创建该属性对象[使用HashMap]", new Object[]
{property.getOwnerType().getName(), property.getName()});
propertyValue = new HashMap
© 2015 - 2025 Weber Informatics LLC | Privacy Policy