项目:前端vue+后台java项目
数据库:默认是null,不是""
遇到的问题:使用elementUI的下拉框、treeSelect等控件删除一个对象的某些属性,之后无法成功更新“删除”掉这些数据
mybatis默认更新规则是不更新属性为null的属性的。
一般情况下遇到的一个问题就是:只能改属性,删不掉属性。
从安全、性能角度考虑确实需要这样,但是如果一张表有多重数据入口,比如可以在多个页面操作修改含有同一个表的数据,就必须得查出来所有字段,会影响一部分性能,另外项目迭代、连表查询时也容易丢失某些字段导致更新时update成null
公司同事建议用不同的dto,然后给这些dto设置成默认全部更新去解决,楼主认为这样又会产生大量dto+mapper文件,服务层也需要注入大量类似名称的mapper,不算一个通用的方法
经过测试发现前端的这些空间点击clear会将属性变成undefined,前端传给后台时如果该属性是undefined就不会传递,但是如果是null就会传递
楼主的解决方案:前端封装控件,传递属性为null的属性,后台用jsonObect接收参数,通过updateWrapper和class反射机制产生一个updatewapper对象,之后mapper用wrapper去更新。
这里以treeSelect为例,在它的外部又套了一层,在这里对undefined的情况下进行判断,设置成了null。
后台接口就这样写一下,更新部分用update方法代替了之前的
生成wrapper的部分大概就是这样的遍历就行了,这里只有一种date情况,到未来可能有很多类型需要判断,到时候可以再用设计模式优化一下。
public static <E> UpdateWrapper setUpdateWrapper(E e, JSONObject object) throws Exception{
UpdateWrapper<E> updateWrapper = new UpdateWrapper<E>();
List<Field> fields = ReflectUtils.getAllFields(e.getClass(), new ArrayList<>());
if (object != null) {
String name=null;//java字段名
String value=null;//数据库名
for (Field field : fields) {
boolean accessible = field.isAccessible();
field.setAccessible(true);
TableId tableId = field.getAnnotation(TableId.class);
TableField tableField = field.getAnnotation(TableField.class);
Class<?> type = field.getType();
if (tableId!=null){
name = field.getName();
value = tableId.value();
if (object.containsKey(name)&&StringUtils.isNotBlank(value)){
if (type== Date.class){
Object o = object.get(name);
Long aLong = new Long(object.get(name).toString());
Date date = new Date(aLong);
String dateStr = DateUtil.dateFormat(date);
updateWrapper.set(value,dateStr);
}
updateWrapper.eq(value,object.get(name));
}
}
if (tableField!=null){
name = field.getName();
value = tableField.value();
if (object.containsKey(name)&&StringUtils.isNotBlank(value)){
if (type== Date.class){
Object o = object.get(name);
Long aLong = new Long(object.get(name).toString());
Date date = new Date(aLong);
String dateStr = DateUtil.dateFormat(date);
updateWrapper.set(value,dateStr);
}else{
updateWrapper.set(value,object.get(name));
}
}
}
}
}
return updateWrapper;
}