Fluent Mybatis中Update语法怎么用

发布时间:2021-11-24 11:08:55 作者:小新
来源:亿速云 阅读:256
# Fluent Mybatis中Update语法详解

## 一、Fluent Mybatis简介

### 1.1 什么是Fluent Mybatis
Fluent Mybatis是一个基于Mybatis的增强工具,它通过流畅的API设计让Mybatis的使用更加简单直观。相比传统Mybatis需要编写XML或注解SQL的方式,Fluent Mybatis提供了Java链式调用的语法糖,使得代码更易读、更易维护。

### 1.2 核心特性
- **流畅的API**:通过方法链实现SQL构建
- **类型安全**:编译时检查SQL语法
- **动态SQL**:支持复杂的条件构造
- **代码生成**:自动生成Entity、Mapper等基础代码
- **减少样板代码**:简化CRUD操作

### 1.3 与传统Mybatis对比
| 特性                | 传统Mybatis       | Fluent Mybatis      |
|---------------------|------------------|---------------------|
| SQL编写方式         | XML/注解          | Java链式调用        |
| 可读性              | 中等              | 高                  |
| 类型安全            | 部分支持          | 完全支持            |
| 动态SQL复杂度       | 高                | 低                  |
| 学习曲线            | 陡峭              | 平缓                |

## 二、Update语法基础

### 2.1 基本Update操作
Fluent Mybatis提供了`update()`方法开启Update操作:

```java
public int updateBasic() {
    return new YourMapper()
        .update()
        .set(YourEntity.Column.name).is("newName")
        .set(YourEntity.Column.age).is(25)
        .where(YourEntity.Column.id).eq(1L)
        .execute();
}

2.2 链式方法说明

2.3 更新多个字段

可以通过连续调用set()方法更新多个字段:

public int updateMultiFields() {
    return new UserMapper()
        .update()
        .set(User.Column.userName).is("张三")
        .set(User.Column.age).is(30)
        .set(User.Column.gmtModified).is(new Date())
        .where(User.Column.id).eq(1L)
        .execute();
}

三、条件更新(Where子句)

3.1 基本条件表达式

Fluent Mybatis支持丰富的条件表达式:

.where(User.Column.age).gt(18)  // 大于
.where(User.Column.age).ge(18)  // 大于等于
.where(User.Column.age).lt(65)  // 小于
.where(User.Column.age).le(65)  // 小于等于
.where(User.Column.name).like("%张%")  // 模糊查询
.where(User.Column.name).notLike("%李%") // 非模糊匹配

3.2 多条件组合

使用andor连接多个条件:

public int updateWithMultiConditions() {
    return new UserMapper()
        .update()
        .set(User.Column.status).is("ACTIVE")
        .where(User.Column.age).gt(18)
        .and(User.Column.age).lt(65)
        .and(User.Column.status).eq("INACTIVE")
        .execute();
}

3.3 嵌套条件

通过apply方法实现复杂嵌套条件:

public int updateWithNestedConditions() {
    return new UserMapper()
        .update()
        .set(User.Column.remark).is("VIP")
        .where(User.Column.vipLevel).gt(3)
        .and(
            condition -> condition.where(User.Column.regTime).ge(LocalDate.now().minusYears(1))
                .or(User.Column.consumption).gt(10000)
        )
        .execute();
}

四、动态更新

4.1 条件判断更新

使用when实现条件判断更新:

public int dynamicUpdate(Long id, String newName, Integer newAge) {
    return new UserMapper()
        .update()
        .set(User.Column.userName).is(newName).when(Objects::nonNull)
        .set(User.Column.age).is(newAge).when(newAge != null)
        .where(User.Column.id).eq(id)
        .execute();
}

4.2 使用Lambda表达式

通过Lambda实现更灵活的条件:

public int updateWithLambda(User user) {
    return new UserMapper()
        .update()
        .set(User.Column.userName).is(user::getUserName).when(user::getUserName)
        .set(User.Column.age).is(user::getAge).when(user::getAge)
        .where(User.Column.id).eq(user::getId)
        .execute();
}

4.3 空值处理策略

配置全局空值处理:

@Configuration
public class FluentMybatisConfig {
    @Bean
    public FluentMybatisConfig config() {
        return new FluentMybatisConfig()
            .setGlobalUpdateIfNull(false); // 默认不更新null值
    }
}

五、批量更新

5.1 基于条件的批量更新

更新满足条件的所有记录:

public int batchUpdateByCondition() {
    return new UserMapper()
        .update()
        .set(User.Column.status).is("INACTIVE")
        .where(User.Column.lastLoginTime).lt(LocalDateTime.now().minusYears(1))
        .execute();
}

5.2 基于ID列表的批量更新

使用in条件批量更新:

public int batchUpdateByIds(List<Long> ids, String newStatus) {
    return new UserMapper()
        .update()
        .set(User.Column.status).is(newStatus)
        .where(User.Column.id).in(ids)
        .execute();
}

5.3 性能优化建议

  1. 合理设置批量大小(建议500-1000条/批)
  2. 考虑使用@BatchSize注解
  3. 必要时关闭自动提交

六、特殊更新场景

6.1 自增/自减操作

使用数学表达式实现:

public int incrementAge(Long userId) {
    return new UserMapper()
        .update()
        .set(User.Column.age).increase(1)  // 年龄+1
        .where(User.Column.id).eq(userId)
        .execute();
}

6.2 JSON字段更新

更新JSON类型字段:

public int updateJsonField(Long userId, String newExtInfo) {
    return new UserMapper()
        .update()
        .set(User.Column.extInfo).isJson(newExtInfo)
        .where(User.Column.id).eq(userId)
        .execute();
}

6.3 乐观锁实现

通过版本号实现乐观锁:

public int updateWithOptimisticLock(User user) {
    return new UserMapper()
        .update()
        .set(User.Column.userName).is(user.getUserName())
        .set(User.Column.version).increase(1) // 版本号+1
        .where(User.Column.id).eq(user.getId())
        .and(User.Column.version).eq(user.getVersion()) // 原始版本号条件
        .execute();
}

七、联表更新

7.1 简单联表更新

使用join实现联表更新:

public int updateWithJoin() {
    return new UserMapper()
        .update()
        .set(User.Column.status).is("VIP")
        .join(Order.class)
        .on(User.Column.id, Order.Column.userId)
        .where(Order.Column.amount).gt(10000)
        .execute();
}

7.2 复杂联表更新

多表关联更新:

public int multiTableUpdate() {
    return new UserMapper()
        .update()
        .set(User.Column.level).is("GOLD")
        .join(Order.class)
        .on(User.Column.id, Order.Column.userId)
        .join(Product.class)
        .on(Order.Column.productId, Product.Column.id)
        .where(Product.Column.category).eq("ELECTRONICS")
        .and(Order.Column.createTime).ge(LocalDate.now().minusMonths(3))
        .execute();
}

7.3 更新结果映射

获取更新后的实体:

public User updateAndReturn(User user) {
    return new UserMapper()
        .update()
        .set(User.Column.userName).is(user.getUserName())
        .set(User.Column.age).is(user.getAge())
        .where(User.Column.id).eq(user.getId())
        .executeAndFetch();
}

八、最佳实践与性能优化

8.1 索引使用建议

  1. 确保WHERE条件使用索引列
  2. 避免在更新列上使用函数
  3. 复合索引遵循最左前缀原则

8.2 事务管理

@Transactional
public void updateWithTransaction(User user1, User user2) {
    userMapper.updateById(user1);
    userMapper.updateById(user2);
    // 如果发生异常会自动回滚
}

8.3 监控与调优

  1. 使用@UpdateTime自动记录更新时间
  2. 通过explain分析复杂更新语句
  3. 监控慢SQL日志

九、常见问题排查

9.1 更新不生效的可能原因

  1. 条件不匹配导致0行更新
  2. 事务未提交
  3. 乐观锁版本冲突
  4. 字段值为null且配置了不更新null

9.2 性能问题排查

  1. 检查是否锁表(show processlist)
  2. 分析执行计划(explain)
  3. 检查索引使用情况

9.3 日志调试技巧

配置日志级别:

logging.level.tech.richard.vo.user.mapper=DEBUG

十、完整示例代码

10.1 用户状态批量更新

public int batchUpdateUserStatus(List<Long> ids, String newStatus) {
    return new UserMapper()
        .update()
        .set(User.Column.status).is(newStatus)
        .set(User.Column.gmtModified).is(new Date())
        .where(User.Column.id).in(ids)
        .and(User.Column.isDeleted).eq(false)
        .execute();
}

10.2 订单价格调整

public int adjustOrderPrices(String category, BigDecimal ratio) {
    return new OrderMapper()
        .update()
        .set(Order.Column.amount).math("amount * " + ratio)
        .join(Product.class)
        .on(Order.Column.productId, Product.Column.id)
        .where(Product.Column.category).eq(category)
        .and(Order.Column.status).eq("UNPD")
        .execute();
}

10.3 用户积分更新

public int updateUserPoints(Long userId, int pointsToAdd) {
    return new UserMapper()
        .update()
        .set(User.Column.points).increase(pointsToAdd)
        .set(User.Column.vipLevel).case()
            .when(User.Column.points).ge(10000).then(3)
            .when(User.Column.points).ge(5000).then(2)
            .elseThen(1)
        .end()
        .where(User.Column.id).eq(userId)
        .execute();
}

总结

Fluent Mybatis的Update语法通过流畅的API提供了强大的数据更新能力,从简单的单字段更新到复杂的联表更新都能优雅实现。关键要点包括:

  1. 掌握链式调用的基本模式
  2. 合理使用动态条件
  3. 批量更新注意性能优化
  4. 复杂场景使用联表更新
  5. 生产环境注意事务和锁机制

通过本文的全面介绍,相信您已经能够熟练运用Fluent Mybatis进行各种更新操作。建议结合官方文档和实际项目练习来巩固这些知识。 “`

推荐阅读:
  1. 使用update语法更新mysql
  2. 利用mybatis怎么实现多条update同时执行

免责声明:本站发布的内容(图片、视频和文字)以原创、转载和分享为主,文章观点不代表本网站立场,如果涉及侵权请联系站长邮箱:is@yisu.com进行举报,并提供相关证据,一经查实,将立刻删除涉嫌侵权内容。

fluent mybatis update

上一篇:Java排序算法之计数排序如何实现

下一篇:vue中install方法怎么用

相关阅读

您好,登录后才能下订单哦!

密码登录
登录注册
其他方式登录
点击 登录注册 即表示同意《亿速云用户服务条款》