详细介绍:saveOrUpdate 有个缺点,不会把值赋值为null,解决办法

针对 MyBatis-Plus 的 saveOrUpdate 方法无法将字段更新为 null 的问题,这是因为 MyBatis-Plus 默认会忽略 null 值字段。以下是几种解决方案:

方案 1:使用 update(entity, wrapper) 手动指定更新条件

原理:通过 UpdateWrapper 明确指定需要更新为 null 的字段。

@Service
public
class UserServiceImpl
extends ServiceImpl<
UserMapper
, User>
implements UserService {
public
void updateWithNullValue(
) {
User user =
new User(
)
;
user.setId(1L
)
;
user.setUsername(
null
)
;
// 需要更新为 null 的字段
// 手动构建 UpdateWrapper,强制更新 null 值字段
UpdateWrapper<
User> wrapper =
new UpdateWrapper<
>(
)
;
wrapper.set("username"
,
null
) // 指定 username 字段更新为 null
.eq("id"
, user.getId(
)
)
;
// 更新条件:ID = 1
// 调用 update 方法,第一个参数可以为 null(因为条件已在 wrapper 中)
boolean success =
this.update(
null
, wrapper)
;
if (success) {
System.out.println("更新 null 值成功"
)
;
}
}
}

方案 2:配置全局字段策略(推荐)

原理:通过配置 FieldStrategy 让 MyBatis-Plus 不忽略 null 值。

方式 1:配置文件(application.yml)
mybatis-plus:
global-config:
db-config:
update-strategy: IGNORED # 更新策略:忽略判断,所有字段都更新(包括 null)
方式 2:Java 配置类
@Configuration
public
class MyBatisPlusConfig {
@Bean
public MybatisPlusInterceptor mybatisPlusInterceptor(
) {
MybatisPlusInterceptor interceptor =
new MybatisPlusInterceptor(
)
;
// 其他配置...
// 配置全局策略
GlobalConfig globalConfig =
new GlobalConfig(
)
;
GlobalConfig.DbConfig dbConfig =
new GlobalConfig.DbConfig(
)
;
dbConfig.setUpdateStrategy(FieldStrategy.IGNORED
)
;
// 更新时忽略字段非空判断
globalConfig.setDbConfig(dbConfig)
;
return interceptor;
}
}

方案 3:使用 @TableField 注解(细粒度控制)

原理:在实体类字段上指定更新策略为 IGNORED

@Data
@TableName("t_user"
)
public
class User {
@TableId
private Long id;
@TableField(updateStrategy = FieldStrategy.IGNORED
) // 该字段更新时忽略 null 判断
private String username;
private String phone;
@TableField(updateStrategy = FieldStrategy.IGNORED
) // 该字段更新时忽略 null 判断
private Integer age;
}

方案 4:自定义 SQL 方法

原理:在 Mapper 接口中自定义更新方法,使用 @Update 注解编写 SQL。

public
interface UserMapper
extends BaseMapper<
User> {
@Update("UPDATE t_user SET username = #{username}, age = #{age} WHERE id = #{id}"
)
boolean updateWithNull(@Param("id"
) Long id,
@Param("username"
) String username,
@Param("age"
) Integer age)
;
}

Service 层调用

@Service
public
class UserServiceImpl
extends ServiceImpl<
UserMapper
, User>
implements UserService {
public
void customUpdateWithNull(
) {
boolean success = baseMapper.updateWithNull(1L
,
null
, 25
)
;
if (success) {
System.out.println("自定义 SQL 更新 null 值成功"
)
;
}
}
}

总结

方案优点缺点适用场景
方案 1灵活,按需更新代码冗余少量需要更新 null 的场景
方案 2全局生效,无需修改代码影响所有实体项目中大量需要更新 null
方案 3细粒度控制,不影响其他字段需修改实体类部分字段需要更新 null
方案 4完全自定义 SQL维护成本高复杂更新逻辑或性能敏感场景

推荐顺序:方案 3(细粒度控制)→ 方案 2(全局配置)→ 方案 1(临时需求)→ 方案 4(特殊场景)。

posted @ 2025-10-08 17:40  wzzkaifa  阅读(35)  评论(0)    收藏  举报