当前位置: 首页 > news >正文

MyBatis Plus 核心功能与用法

目录

  • 一、 快速入门
    • 1. 创建工程与引入依赖
    • 2. 配置数据库连接
    • 3. 编写实体类
    • 4. 创建 Mapper 接口
    • 5. 测试 CRUD
  • 二、核心功能详解
    • 1. 条件构造器
      • 1. 常用 Wrapper 方法示例
      • 2. 使用示例:QueryWrapper
      • 3. 使用示例:UpdateWrapper
      • 4. 推荐使用:LambdaWrapper
    • 2. 常用注解
    • 3. 主键策略
  • 三、 Service 层封装
    • 1. 创建 Service 接口
    • 2. 创建 Service 实现类
    • 3. 使用 Service CRUD 方法
  • 四、 高级特性
    • 1. 代码生成器
    • 2. 分页查询
      • 1. 配置分页插件
      • 2. 进行分页查询
    • 3. 逻辑删除
      • 1. 数据库添加字段
      • 2. 实体类添加注解
      • 3. 配置(可选,新版 MP 可能不需要)
    • 4. 自动填充(审计)
      • 1. 实体类标记字段
      • 2. 实现 MetaObjectHandler 接口
    • 5. 乐观锁
      • 1. 数据库添加字段
      • 2. 实体类添加注解
      • 3. 配置乐观锁插件
  • 五、 总结

一、 快速入门

1. 创建工程与引入依赖

创建一个 Spring Boot 工程,并在 pom.xml 中引入 MyBatis Plus 的起步依赖。

<dependency><groupId>com.baomidou</groupId><artifactId>mybatis-plus-boot-starter</artifactId><version>3.5.3.1</version> <!-- 请注意使用最新版本 -->
</dependency>

2. 配置数据库连接

在 application.yml 中配置数据库连接等信息。如果需要查看 MP 执行的 SQL 语句,可以配置日志实现。

spring:datasource:url: jdbc:mysql://localhost:3306/mybatis-plus?useSSL=falseusername: rootpassword: 123456
mybatis-plus:configuration:log-impl: org.apache.ibatis.logging.stdout.StdOutImpl # 输出SQL日志到控制台

3. 编写实体类

创建实体类,并使用注解与数据库表进行映射。例如,对应 user 表的 User 类:

import lombok.Data;
import com.baomidou.mybatisplus.annotation.*;@Data // Lombok注解,自动生成getter/setter等方法
@TableName("user") // 指定关联的数据表名,如果类名与表名符合驼峰转下划线规则,可省略
public class User {@TableId(type = IdType.AUTO) // 指定主键及生成策略(AUTO-数据库自增)private Long id;private String name;private Integer age;private String email;// 如果实体类字段名与数据库列名不一致,可用 @TableField 指定// @TableField("user_name") // private String userName;// 如果实体类中存在非数据库字段,需要使用 @TableField(exist = false)// @TableField(exist = false)// private String nonDatabaseField;
}

4. 创建 Mapper 接口

创建 Mapper 接口,并使其继承 MyBatis Plus 提供的 BaseMapper 接口。继承后,无需编写 XML,即可获得大量单表 CRUD 方法。

import com.baomidou.mybatisplus.core.mapper.BaseMapper;@Repository // 可加注解,交由Spring管理
public interface UserMapper extends BaseMapper<User> {// 此时无需编写任何方法,就已具备了基本的增删改查功能
}

5. 测试 CRUD

在测试类中注入 UserMapper,即可测试基本的增删改查操作。

@SpringBootTest
class MybatisPlusDemoApplicationTests {@Autowiredprivate UserMapper userMapper;@Testvoid testSelect() {// 查询所有用户List<User> users = userMapper.selectList(null);users.forEach(System.out::println);// 根据ID查询User user = userMapper.selectById(1L);System.out.println(user);}@Testvoid testInsert() {User newUser = new User();newUser.setName("张三");newUser.setAge(30);newUser.setEmail("zhangsan@example.com");int result = userMapper.insert(newUser); // result是受影响的行数System.out.println("插入成功,受影响行数:" + result);}// 其他CRUD操作类似,可调用 deleteById, updateById 等方法
}

二、核心功能详解

1. 条件构造器

条件构造器(Wrapper)是 MP 中用于构建复杂查询条件的强大工具,你可以用它来替代手写 WHERE 子句。

1. 常用 Wrapper 方法示例

方法名说明示例
eq等于wrapper.eq(“name”, “张三”) // name = ‘张三’
ne不等于wrapper.ne(“age”, 20) // age <> 20
gt大于wrapper.gt(“age”, 18) // age > 18
ge大于等于wrapper.ge(“age”, 20) // age >= 20
lt小于wrapper.lt(“age”, 65) // age < 65
le小于等于wrapper.le(“age”, 65) // age <= 65
between介于wrapper.between(“age”, 18, 30) // age between 18 and 30
like模糊匹配wrapper.like(“name”, “张”) // name like ‘%张%’
likeLeft左模糊匹配wrapper.likeLeft(“name”, “三”) // name like ‘%三’
likeRight右模糊匹配wrapper.likeRight(“name”, “张”) // name like ‘张%’
isNull为NULLwrapper.isNull(“email”) // email is null
isNotNull不为NULLwrapper.isNotNull(“email”) // email is not null
in包含wrapper.in(“age”, Arrays.asList(18,20,22)) // age in (18,20,22)
andAND连接wrapper.and(w -> w.eq(“name”, “李四”).gt(“age”, 25))
orOR连接wrapper.or().eq(“name”, “张三”).or().eq(“name”, “李四”)
orderByAsc升序排序wrapper.orderByAsc(“age”)
orderByDesc降序排序wrapper.orderByDesc(“create_time”)
select指定查询列wrapper.select(“id”, “name”, “email”) // 只查询特定列

2. 使用示例:QueryWrapper

@Test
void testQueryWrapper() {// 构建查询条件:年龄大于20且姓名中包含"张"的用户,按年龄降序QueryWrapper<User> wrapper = new QueryWrapper<>();wrapper.gt("age", 20).like("name", "张").orderByDesc("age");List<User> users = userMapper.selectList(wrapper);users.forEach(System.out::println);
}

3. 使用示例:UpdateWrapper

@Test
void testUpdateWrapper() {// 构建更新条件:将年龄大于25的用户的邮箱更新为特定值UpdateWrapper<User> wrapper = new UpdateWrapper<>();wrapper.gt("age", 25).set("email", "senior@example.com"); // 直接设置值// 注意:这里传入的User实体可以为null,因为更新条件都在wrapper里int result = userMapper.update(null, wrapper);System.out.println("更新了 " + result + " 条记录");
}

4. 推荐使用:LambdaWrapper

使用 LambdaQueryWrapper 和 LambdaUpdateWrapper 可以通过方法引用来指定字段,避免硬编码字段名,从而在编译阶段就能发现错误,更加安全可靠。

@Test
void testLambdaQueryWrapper() {// 使用方法引用,避免拼写错误LambdaQueryWrapper<User> lambdaWrapper = new LambdaQueryWrapper<>();lambdaWrapper.gt(User::getAge, 20).like(User::getName, "张").orderByDesc(User::getAge);List<User> users = userMapper.selectList(lambdaWrapper);users.forEach(System.out::println);
}

2. 常用注解

MyBatis Plus 提供了一系列注解来简化实体类与数据库表之间的映射配置。

注解作用示例
@TableName指定实体类对应的数据库表名@TableName(“sys_user”)
@TableId指定主键字段,并可设置主键策略@TableId(value = “id”, type = IdType.AUTO)
@TableField指定普通字段映射@TableField(“user_name”) @TableField(exist = false) // 非表字段
@Version用于乐观锁(后续讲解)@Version private Integer version;
@TableLogic用于逻辑删除(后续讲解)@TableLogic private Integer deleted;

3. 主键策略

@TableId 注解的 type 属性用于指定主键生成策略。

public class User {@TableId(value = "id", type = IdType.AUTO) // 数据库自增private Long id;// ...
}

常见的 IdType 枚举:

  • AUTO:数据库ID自增
  • ASSIGN_ID:使用雪花算法生成Long类型的ID(默认策略)
  • INPUT:用户手动输入ID

三、 Service 层封装

MyBatis Plus 不仅增强了 Mapper 层,也对 Service 层提供了强大的支持。

1. 创建 Service 接口

创建接口并继承 MP 提供的 IService 接口。

public interface UserService extends IService<User> {// 可以在此定义自定义方法// User findUserByCustomMethod(String name);
}

2. 创建 Service 实现类

创建实现类,继承 MP 提供的 ServiceImpl,并实现自定义的 Service 接口。

@Service
public class UserServiceImpl extends ServiceImpl<UserMapper, User> implements UserService {// 如果 UserService 接口有自定义方法,需要在这里实现// @Override// public User findUserByCustomMethod(String name) { ... }
}

3. 使用 Service CRUD 方法

在 Controller 或其他地方注入你的 Service,即可使用其内置的大量方法。

@RestController
public class UserController {@Autowiredprivate UserService userService;@GetMapping("/users")public List<User> getAllUsers() {// 直接调用 IService 中提供的 list 方法return userService.list();}@GetMapping("/user/{id}")public User getUserById(@PathVariable Long id) {// 调用 getById 方法return userService.getById(id);}// 保存、更新、删除等方法调用类似// userService.save(user);// userService.updateById(user);// userService.removeById(id);
}

四、 高级特性

1. 代码生成器

MyBatis Plus 内置了代码生成器(MyBatis-Plus Generator),可以根据数据库表结构自动生成 Entity、Mapper、Service、Controller 等代码,极大提升开发效率。

// 示例代码片段,具体需参考官方文档配置
FastAutoGenerator.create("jdbc:mysql://localhost:3306/your_db", "username", "password").globalConfig(builder -> builder.outputDir("D://code")) // 指定输出目录.packageConfig(builder -> builder.parent("com.your.company")) // 指定父包名.strategyConfig(builder -> builder.addInclude("user", "order")) // 指定要生成的表.execute();

2. 分页查询

使用 MyBatis Plus 的分页功能需要先配置分页插件,然后即可使用其分页 API。

1. 配置分页插件

@Configuration
public class MybatisPlusConfig {@Beanpublic MybatisPlusInterceptor mybatisPlusInterceptor() {MybatisPlusInterceptor interceptor = new MybatisPlusInterceptor();// 添加分页插件interceptor.addInnerInterceptor(new PaginationInnerInterceptor());return interceptor;}
}

2. 进行分页查询

@Test
void testSelectPage() {// 创建分页对象,参数:当前页,每页大小Page<User> page = new Page<>(1, 5);// 执行分页查询,第二个参数是查询条件(Wrapper),为null则表示无条件userMapper.selectPage(page, null);// 从page对象获取分页数据System.out.println("总记录数: " + page.getTotal());System.out.println("当前页记录: " + page.getRecords());System.out.println("当前页码: " + page.getCurrent());System.out.println("总页数: " + page.getPages());System.out.println("每页大小: " + page.getSize());System.out.println("是否有下一页: " + page.hasNext());System.out.println("是否有上一页: " + page.hasPrevious());
}

3. 逻辑删除

逻辑删除并非真正物理删除数据,而是通过更新一个字段来标记数据已被删除。

1. 数据库添加字段

在表中增加一个 deleted(或自定义)字段,通常为 int 或 tinyint 类型。

2. 实体类添加注解

public class User {// ... 其他字段 ...@TableLogic// @TableField(fill = FieldFill.INSERT) // 可选,配合自动填充设置默认值private Integer deleted; // 0-未删除,1-已删除
}

3. 配置(可选,新版 MP 可能不需要)

在 application.yml 中配置逻辑删除的全局值(根据 MP 版本,有时可省略)。

mybatis-plus:global-config:db-config:logic-delete-value: 1 # 已删除的值logic-not-delete-value: 0 # 未删除的值

配置后,调用 userMapper.deleteById(id) 将会自动更新 deleted 字段为 1。查询时,MP 会自动带上 deleted = 0 的条件。

4. 自动填充(审计)

自动填充功能可用于自动处理一些通用字段的赋值,如数据的创建时间(create_time)和更新时间(update_time)。

1. 实体类标记字段

public class User {// ... 其他字段 ...@TableField(fill = FieldFill.INSERT) // 插入时填充private Date createTime;@TableField(fill = FieldFill.INSERT_UPDATE) // 插入和更新时填充private Date updateTime;
}

2. 实现 MetaObjectHandler 接口

创建一个处理器,实现插入和更新时的填充逻辑。

@Component // 记得声明为Spring组件
public class MyMetaObjectHandler implements MetaObjectHandler {@Overridepublic void insertFill(MetaObject metaObject) {// 插入时,为 createTime 和 updateTime 设置当前时间this.strictInsertFill(metaObject, "createTime", Date.class, new Date());this.strictInsertFill(metaObject, "updateTime", Date.class, new Date());}@Overridepublic void updateFill(MetaObject metaObject) {// 更新时,为 updateTime 设置当前时间this.strictUpdateFill(metaObject, "updateTime", Date.class, new Date());}
}

5. 乐观锁

乐观锁用于解决并发更新问题,通常通过一个版本号(version)字段实现。

1. 数据库添加字段

在表中增加一个 version 字段,通常为 int 类型。

2. 实体类添加注解

public class User {// ... 其他字段 ...@Version// @TableField(fill = FieldFill.INSERT) // 可选,配合自动填充设置默认值private Integer version;
}

3. 配置乐观锁插件

@Configuration
public class MybatisPlusConfig {@Beanpublic MybatisPlusInterceptor mybatisPlusInterceptor() {MybatisPlusInterceptor interceptor = new MybatisPlusInterceptor();// 添加乐观锁插件interceptor.addInnerInterceptor(new OptimisticLockerInnerInterceptor());return interceptor;}
}

使用流程:

  1. 查询数据时,获取当前的 version 值(例如 version=1)。
  2. 更新数据时,将 version 作为条件:UPDATE user SET …, version = 2 WHERE id = ? AND version = 1。
  3. 如果此时该数据已被其他线程修改(即数据库中的 version 已不为 1),则本次更新返回的影响行数为 0,可根据此结果判断更新是否成功。

五、 总结

MyBatis Plus 通过丰富的功能和简洁的 API,极大地提升了基于 MyBatis 的开发效率。核心在于:

  • 简单 CRUD:通过继承 BaseMapper 和 IService,无需编写 SQL 和 XML。
  • 复杂查询:利用强大的 Wrapper,特别是 LambdaWrapper,安全地构建查询条件。
  • 高效开发:利用代码生成器、分页、逻辑删除、自动填充、乐观锁等特性,处理常见开发场景。

希望这份详解能帮助你更好地理解和使用 MyBatis Plus。如果想深入了解某个特定功能,建议查阅其官方文档。

http://www.dtcms.com/a/456706.html

相关文章:

  • LNMP架构实践
  • 自己怎么建个网站赚钱吗外贸品牌推广公司
  • 在线咨询 1 网站宣传建立免费公司网站
  • 10-存储过程和存储函数
  • leetCode101:对称二叉树
  • 【Linux】网络部分——Socket编程 UDP实现网络云服务器与本地虚拟机的基本通信
  • 实战项目:鸿蒙多端协同智能家居控制 App 开发全流程
  • 个人用云计算学习笔记 --19 (MariaDB服务器)
  • Linux -- 信号【中】
  • Azure - 尝试创建并使用一下Azure AI Search
  • NtripShare GNSS接收机配置系统SPI读取村田SCL3300倾角数据
  • Python私教FastAPI+React构建Web应用02 什么是全栈Web应用
  • 开源安全管理平台wazuh-文件完整性监控FIM
  • 网站建设选超速云建站黄页88成立时间
  • 南通做网站ntwsd开发公司总工年终总结
  • VS Code文件监视排除设置详解
  • 3D坐标旋转公式
  • 《Git 从入门到进阶》教学大纲
  • linux网络服务+linux数据库5
  • 德山经济开发区建设局网站wordpress的数据库在哪里
  • P3808 AC 自动机(简单版)
  • C++----bitmap位图的使用
  • 单链表的应用02---算法中的暴力美学(第八讲)
  • 【RAG】优化query查询效果的几种处理
  • transformer详解(位置编码+attention+残差连接+全连接网络)
  • 已注册域名怎么做网站呢免费网站免费网站平台
  • 如何解决 pip install -r requirements.txt 约束文件 constraints.txt 仅允许固定版本(未锁定报错)问题
  • 【Camera】准备的一些Camera面试题——相机预览、拍照流程(经验尚欠,待补充)
  • CICD工具选型指南,GitLab cicd vs Arbess哪一款更好用?
  • 尉Lucene.Net 分词器选择指南:盘古分词 vs 结巴分词h