All Downloads are FREE. Search and download functionalities are using the official Maven repository.
Please wait. This can take some minutes ...
Many resources are needed to download a project. Please understand that we have to compensate our server costs. Thank you in advance.
Project price only 1 $
You can buy this project and download/modify it how often you want.
cn.cliveyuan.robin.base.util.ReflectUtils Maven / Gradle / Ivy
/*
* Copyright (c) 2020 Clive Yuan ([email protected] ).
*/
package cn.cliveyuan.robin.base.util;
import cn.cliveyuan.robin.base.annotation.TableField;
import cn.cliveyuan.robin.base.annotation.TableId;
import cn.cliveyuan.robin.base.annotation.TableName;
import cn.cliveyuan.robin.base.support.ReflectEntity;
import cn.cliveyuan.robin.base.support.ReflectEntityHelper;
import cn.cliveyuan.robin.base.support.ReflectField;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.lang.reflect.Modifier;
import java.lang.reflect.ParameterizedType;
import java.lang.reflect.Type;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.Optional;
import java.util.concurrent.ConcurrentHashMap;
import java.util.function.Function;
import java.util.stream.Collectors;
/**
* 反射工具
*
* @author Clive Yuan
* @date 2020/10/29
*/
public class ReflectUtils {
private static final Logger LOGGER = LoggerFactory.getLogger(ReflectUtils.class);
private static final Map REFLECT_ENTITY_CACHE = new ConcurrentHashMap<>();
private static final String GET_METHOD_PREFIX = "get";
private static final String PRIMARY_KEY_NAME = "id";
public static Class> getSuperClassGenericType(final Class> clazz, final int index) {
return getClassGenericType(false, clazz, index);
}
public static Class> getClassGenericType(final boolean isInterface, final Class> clazz, final int index) {
Type genType = clazz.getGenericSuperclass();
if (isInterface) {
Type[] genericInterfaces = clazz.getGenericInterfaces();
if (genericInterfaces.length > 0) {
genType = genericInterfaces[0];
}
}
if (!(genType instanceof ParameterizedType)) {
LOGGER.warn(String.format("Warn: %s's superclass not ParameterizedType", clazz.getSimpleName()));
return Object.class;
}
Type[] params = ((ParameterizedType) genType).getActualTypeArguments();
if (index >= params.length || index < 0) {
LOGGER.warn(String.format("Warn: Index: %s, Size of %s's Parameterized Type: %s .", index,
clazz.getSimpleName(), params.length));
return Object.class;
}
if (!(params[index] instanceof Class)) {
LOGGER.warn(String.format("Warn: %s not set the actual class on superclass generic parameter",
clazz.getSimpleName()));
return Object.class;
}
return (Class>) params[index];
}
/**
* 解析反射实体
*
* @param clazz 实体类对象
* @return
*/
public static ReflectEntity resolveEntity(Class> clazz) {
String name = clazz.getName();
return Optional.ofNullable(REFLECT_ENTITY_CACHE.get(name))
.orElseGet(() -> {
ReflectEntity reflectEntity = doResolveEntity(clazz);
REFLECT_ENTITY_CACHE.put(name, reflectEntity);
return reflectEntity;
});
}
private static ReflectEntity doResolveEntity(Class> clazz) {
Objects.requireNonNull(clazz);
ReflectEntity reflectEntity = new ReflectEntity();
String simpleName = clazz.getSimpleName();
String tableName = simpleName;
// 读取类
TableName tableNameAnnotation = clazz.getAnnotation(TableName.class);
if (Objects.nonNull(tableNameAnnotation)) {
tableName = tableNameAnnotation.value();
}
reflectEntity.setTableName(tableName);
reflectEntity.setSimpleName(simpleName);
// 读取字段
List fields = new ArrayList<>();
reflectEntity.setFields(fields);
List declaredFields = getAllDeclaredFields(clazz);
for (Field declaredField : declaredFields) {
String name = declaredField.getName();
boolean primaryKey = false;
boolean ignoreSaving = false;
String fieldName = name;
TableId tableIdAnnotation = declaredField.getAnnotation(TableId.class);
if (Objects.nonNull(tableIdAnnotation)) {
if (RobinStrUtils.isNotBlank(tableIdAnnotation.value())) {
fieldName = tableIdAnnotation.value();
}
primaryKey = true;
ignoreSaving = true;
}
TableField tableFieldAnnotation = declaredField.getAnnotation(TableField.class);
if (Objects.nonNull(tableFieldAnnotation)) {
if (RobinStrUtils.isNotBlank(tableFieldAnnotation.value())) {
fieldName = tableFieldAnnotation.value();
}
ignoreSaving = tableFieldAnnotation.ignoreSaving();
}
ReflectField field = new ReflectField();
field.setName(name);
field.setFieldName(fieldName);
field.setIgnoreSaving(ignoreSaving);
field.setPrimaryKey(primaryKey);
fields.add(field);
}
reflectEntity.setReflectEntityHelper(ReflectEntityHelper.build(reflectEntity));
return reflectEntity;
}
public static boolean isIdNull(T entity) {
return isFieldNull(entity, PRIMARY_KEY_NAME);
}
public static boolean isFieldNull(T entity, String fieldName) {
Object value = methodInvoke(getMethod(entity.getClass(), fieldName), entity);
return Objects.isNull(value);
}
/**
* 获取实体字段和值
*
* @param entity 实体对象
* @param 实体对象类
* @return
*/
public static Map resolveEntityFieldAndValue(T entity) {
Map fieldValueMap = new HashMap<>();
Class> entityClass = entity.getClass();
List declaredFields = getAllDeclaredFields(entityClass);
List fieldNames = declaredFields.stream()
.map(Field::getName)
.collect(Collectors.toList());
Map fieldMap = declaredFields.stream().collect(Collectors.toMap(Field::getName, Function.identity()));
List declaredMethods = getAllMethods(entityClass);
Map getMethodMap = declaredMethods.stream().filter(x -> x.getName().startsWith(GET_METHOD_PREFIX))
.collect(Collectors.toMap(Method::getName, Function.identity()));
fieldNames.forEach(fieldName -> {
String columnName = fieldName;
Field field = fieldMap.get(fieldName);
TableField tableField = field.getAnnotation(TableField.class);
if (Objects.nonNull(tableField) && RobinStrUtils.isNotBlank(tableField.value())) {
columnName = tableField.value();
}
String methodName = GET_METHOD_PREFIX.concat(SqlUtils.firstToUpperCase(fieldName));
Method method = getMethodMap.get(methodName);
if (Objects.isNull(method)) {
return;
}
Object value = methodInvoke(method, entity);
if (Objects.nonNull(value)) {
fieldValueMap.put(columnName, value);
}
});
return fieldValueMap;
}
public static Object methodInvoke(Method method, Object obj, Object... args) {
try {
method.setAccessible(true);
return method.invoke(obj, args);
} catch (IllegalAccessException | InvocationTargetException e) {
LOGGER.error("methodInvoke error", e);
throw new RuntimeException(e);
}
}
public static Method getMethod(Class> entityClass, String fieldName) {
Method method = getMethodRecursion(entityClass, fieldName);
if (Objects.isNull(method)) {
String methodName = GET_METHOD_PREFIX.concat(SqlUtils.firstToUpperCase(fieldName));
throw new RuntimeException(String.format("NoSuchMethodException: %s.%s()", entityClass, methodName));
}
return method;
}
/**
* 递归获取对象get方法
*
* @param entityClass 对象类
* @param fieldName 字段名
* @return
*/
private static Method getMethodRecursion(Class> entityClass, String fieldName) {
String methodName = GET_METHOD_PREFIX.concat(SqlUtils.firstToUpperCase(fieldName));
if ("java.lang.Object".equalsIgnoreCase(entityClass.getName())) {
return null;
}
return Arrays.stream(entityClass.getDeclaredMethods())
.filter(x -> Objects.equals(x.getName(), methodName))
.findFirst()
.orElseGet(() -> getMethodRecursion(entityClass.getSuperclass(), fieldName));
}
public static List getAllMethods(Class> entityClass) {
List list = new ArrayList<>();
getMethodsRecursion(entityClass, list);
return list;
}
public static void getMethodsRecursion(Class> entityClass, List list) {
if ("java.lang.Object".equalsIgnoreCase(entityClass.getName())) {
return;
}
list.addAll(Arrays.stream(entityClass.getDeclaredMethods()).collect(Collectors.toList()));
getMethodsRecursion(entityClass.getSuperclass(), list);
}
/**
* 获取当前类声明字段,且非static修饰
*
* @param clazz 类对象
* @return
*/
public static List getDeclaredFields(Class> clazz) {
Field[] declaredFields = clazz.getDeclaredFields();
return Arrays.stream(declaredFields).filter(x -> !Modifier.isStatic(x.getModifiers()))
.collect(Collectors.toList());
}
/**
* 获取所有声明字段,且非static修饰 (包括父类)
*
* @param clazz 类对象
* @return
*/
public static List getAllDeclaredFields(Class> clazz) {
List list = new ArrayList<>();
getFieldsRecursion(clazz, list);
return list;
}
/**
* 递归获取对象字段
*
* @param entityClass 对象类
* @param fields 字段列表
* @return
*/
private static void getFieldsRecursion(Class> entityClass, List fields) {
if ("java.lang.Object".equalsIgnoreCase(entityClass.getName())) {
return;
}
Field[] declaredFields = entityClass.getDeclaredFields();
fields.addAll(Arrays.stream(declaredFields).filter(x -> !Modifier.isStatic(x.getModifiers()))
.collect(Collectors.toList()));
getFieldsRecursion(entityClass.getSuperclass(), fields);
}
}