问题背景
开发项目中,使用MyBatis-Plus 的updateById() 方法将查询结果中原本不为null的字段更新为null,该字段设置可为null。发现更新失败。
问题原因
mybatis-plus FieldStrategy 有三种策略:
- IGNORED:0 忽略
- NOT_NULL:1 非 NULL,默认策略
- NOT_EMPTY:2 非空
而默认更新策略是NOT_NULL:非 NULL;即通过接口更新数据时数据为NULL值时将不更新进数据库。
解决方案
1、写sql。直接在xml中写update sql语句。
2、设置全局的FieldStrategy
在配置文件中修改全局策略
#properties文件格式:
-strategy=ignored#yml文件格式:
mybatis-plus:
global-config:
#字段策略 0:"忽略判断",1:"非 NULL 判断",2:"非空判断"
field-strategy: 0
这样做是全局配置,会对所有字段忽略判断。如果一些字段没有传值过来,会被直接更新为null,可能会影响其他业务数据的准确性。 不推荐
3、对指定字段单独设置field-strategy
根据具体情况,在需要更新的字段中调整验证注解,如验证非空:
@TableField(strategy=FieldStrategy.NOT_EMPTY)
这样的话,我们只需要在需要更新为null的字段上,设置忽略策略,如下:
/**
*
*/
@TableField(updateStrategy = )
private Date patchedDate;
在更新代码中,我们直接使用mybatis-plus中的updateById方法便可以更新成功,如下:
DbPatchScheduleEntity schedule = (());
();
(null);
(schedule);
使用上述方法,如果需要这样处理的字段较多,那么就涉及到给各个字段加注解,这样弊端也就比较明显了。
4、使用UpdateWrapper方式更新
List<DbPatchScheduleRequestEntity> scheduleRequestList = (new QueryWrapper<DbPatchScheduleRequestEntity>().lambda().eq(DbPatchScheduleRequestEntity::getRequestId, requestId));
(scheduleRequest -> {
(scheduleRequest, new UpdateWrapper<DbPatchScheduleRequestEntity>().lambda()
.set(DbPatchScheduleRequestEntity::getScheduleStatus, )
.set(DbPatchScheduleRequestEntity::getPatchedDate, null)
.eq(DbPatchScheduleRequestEntity::getId, ()));
这种方式不影响其他方法,不需要修改全局配置,也不需要在字段上单独加注解,所以推荐使用该方式。