package com.panzhihua.service_grid.model.helper.sensitive;
|
|
import java.lang.reflect.Field;
|
import java.sql.Statement;
|
import java.util.List;
|
import java.util.stream.Stream;
|
|
import org.apache.ibatis.executor.resultset.ResultSetHandler;
|
import org.apache.ibatis.plugin.Interceptor;
|
import org.apache.ibatis.plugin.Intercepts;
|
import org.apache.ibatis.plugin.Invocation;
|
import org.apache.ibatis.plugin.Signature;
|
import org.apache.ibatis.reflection.MetaObject;
|
import org.apache.ibatis.reflection.SystemMetaObject;
|
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
|
import org.springframework.core.annotation.Order;
|
import org.springframework.stereotype.Component;
|
|
import com.panzhihua.common.model.helper.sensitive.Sensitive;
|
import com.panzhihua.common.model.helper.sensitive.SensitiveStrategy;
|
|
import lombok.extern.slf4j.Slf4j;
|
|
/**
|
* 字段脱敏拦截器
|
*
|
* @author cedoo
|
* @since 2021-4-1 10:40:52
|
*/
|
@Intercepts(@Signature(type = ResultSetHandler.class, method = "handleResultSets", args = {Statement.class}))
|
@Slf4j
|
@ConditionalOnProperty(value = "domain.sensitive", havingValue = "true")
|
@Component
|
@Order(120)
|
public class SensitiveInterceptor implements Interceptor {
|
@SuppressWarnings("unchecked")
|
@Override
|
public Object intercept(Invocation invocation) throws Throwable {
|
// log.debug("脱敏拦截器");
|
List<Object> records = (List<Object>)invocation.proceed();
|
// 对结果集脱敏
|
records.forEach(this::sensitive);
|
return records;
|
}
|
|
private void sensitive(Object source) {
|
if (source != null) {
|
// 拿到返回值类型
|
Class<?> sourceClass = source.getClass();
|
// 初始化返回值类型的 MetaObject
|
MetaObject metaObject = SystemMetaObject.forObject(source);
|
// 捕捉到属性上的标记注解 @Sensitive 并进行对应的脱敏处理
|
Stream.of(sourceClass.getDeclaredFields()).filter(field -> field.isAnnotationPresent(Sensitive.class))
|
.forEach(field -> doSensitive(metaObject, field));
|
}
|
}
|
|
private void doSensitive(MetaObject metaObject, Field field) {
|
// 拿到属性名
|
String name = field.getName();
|
// 获取属性值
|
Object value = metaObject.getValue(name);
|
// 只有字符串类型才能脱敏 而且不能为null
|
if (String.class == metaObject.getGetterType(name) && value != null) {
|
Sensitive annotation = field.getAnnotation(Sensitive.class);
|
// 获取对应的脱敏策略 并进行脱敏
|
SensitiveStrategy type = annotation.strategy();
|
Object o = type.getDesensitizer().apply((String)value);
|
// 把脱敏后的值塞回去
|
metaObject.setValue(name, o);
|
}
|
}
|
}
|