对复杂Java POJO 字段赋值
背景
上周遇到了一个安全需求,要求外部接口不能返回手机号字段。难点在于,外部接口和内部接口调用的是同一个方法,所以只能在接口返回的地方做处理逻辑。当时为了快速上线,用的办法是把手机号字段取出,置为null,然后再set回去。因为接口返回的POJO比较复杂,嵌套层级多,所以这个办法不优雅。
问题来了,假设有一个复杂的POJO对象,如何快速给某个字段赋值,而不需要关心对象嵌套关系呢?
解决方法
使用了Java的反射
public static void setField(Object obj, String fieldName, Object target) throws IllegalAccessException {
// 取出所有字段,包括 public 和 private
var fields = obj.getClass().getDeclaredFields();
for (java.lang.reflect.Field field : fields) {
// 设置为可访问
field.setAccessible(true);
var o = field.get(obj);
// 如果是目标字段,则设置为目标值
if (field.getName().equals(fieldName)) {
field.set(obj, target);
return;
}
// 如果是基本数据类型,就直接跳过
if (o.getClass().getClassLoader() == null) {
continue;
} else {
// 如果是引用数据类型,就进行递归调用,直到遍历完所有字段或找到目标字段
setField(o, fieldName, target);
}
}
}