文章目录
MyBatis-Plus 官方文档
1. MyBatis-Plus介绍
MyBatis-Plus(简称MP)是⼀个MyBatis的增强⼯具,在MyBatis的基础上只做增强不做改变,为简化开发、提高效率而生。
发
特性:
润物无声:只做增强不做改变,引入它不会对现有工程产生影响,如丝般顺滑。
效率至上:只需简单配置,即可快速进行单表 CRUD 操作,从而节省大量时间。
丰富功能:代码生成、自动分页、逻辑删除、自动填充、拦截器等功能一应俱全。
广泛认可:连续 5 年获得开源中国年度最佳开源项目殊荣,Github 累计 16K Star。
2.快速上手
2.1准备工作
数据准备
创建用户表user_info,并创建对应的实体类User
DROP TABLE IF EXISTS `user_info`;
CREATE TABLE `user_info` (
`id` int NOT NULL AUTO_INCREMENT,
`username` varchar(127) CHARACTER SET utf8mb4 COLLATE utf8mb4_0900_ai_ci NOT NULL,
`password` varchar(127) CHARACTER SET utf8mb4 COLLATE utf8mb4_0900_ai_ci NOT NULL,
`age` tinyint NOT NULL,
`gender` tinyint NULL DEFAULT 0 COMMENT '1-男 2-女 0-默认',
`phone` varchar(15) CHARACTER SET utf8mb4 COLLATE utf8mb4_0900_ai_ci NULL DEFAULT NULL,
`delete_flag` tinyint NULL DEFAULT 0 COMMENT '0-正常, 1-删除',
`create_time` datetime NULL DEFAULT CURRENT_TIMESTAMP,
`update_time` datetime NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
PRIMARY KEY (`id`) USING BTREE
) ENGINE = InnoDB AUTO_INCREMENT = 35 CHARACTER SET = utf8mb4 COLLATE = utf8mb4_0900_ai_ci ROW_FORMAT = Dynamic;
INSERT INTO `user_info` VALUES (1, 'admin', 'admin', 15, 1, '18612340001', 1, '2025-03-03 22:28:40', '2025-03-31 23:48:15');
INSERT INTO `user_info` VALUES (2, 'zhangsan', 'zhangsan', 15, 1, '18612340002', 1, '2025-03-03 22:28:40', '2025-03-31 23:48:15');
INSERT INTO `user_info` VALUES (3, 'lisi', 'lisi', 15, 1, '18612340003', 1, '2025-03-03 22:28:40', '2025-03-31 23:48:15');
INSERT INTO `user_info` VALUES (4, 'wangwu', 'wangwu', 18, 1, '18612340004', 0, '2025-03-03 22:28:40', '2025-03-03 22:28:40');
INSERT INTO `user_info` VALUES (5, '张三', '123456', 15, 0, NULL, 0, '2025-03-05 21:13:20', '2025-04-29 10:54:16');
SET FOREIGN_KEY_CHECKS = 1;
2.2添加依赖和配置
Spring Boot 3:
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-spring-boot3-starter</artifactId>
<version>3.5.5</version>
</dependency>
MySQL驱动:
<dependency>
<groupId>com.mysql</groupId>
<artifactId>mysql-connector-j</artifactId>
<scope>runtime</scope>
</dependency>
配置数据库和日志:
spring:
application:
name: demo
# 数据库连接配置
datasource:
url: jdbc:mysql://127.0.0.1:3306/java113?characterEncoding=utf8&useSSL=false
username: root
password: 123456
driver-class-name: com.mysql.cj.jdbc.Driver
mybatis-plus:
configuration: # 配置打印 MyBatis⽇志
log-impl: org.apache.ibatis.logging.stdout.StdOutImpl
2.3 创建实体类
public class UserInfo {
private Integer id;
private String username;
private String password;
private Integer age;
private Integer gender;
private String phone;
private Integer deleteFlag;
private Date createTime;
private Date updateTime;
}
Mapper接口:
MybatisPlus提供了⼀个基础的 BaseMapper 接口,已经实现了单表的CRUD,我们自定义的
Mapper只需要继承这个BaseMapper,就无需自己实现单表CRUD了
泛型指代要操作的实体类
@Mapper
public interface UserInfoMapper extends BaseMapper<UserInfo> {}
简单使用
在测试类中直接用调用方法
首先注入userInfoMapper类
@SpringBootTest
class UserInfoMapperTest {
@Autowired
private UserInfoMapper userInfoMapper;
}
增:
示例:
@Test
void insert() {
UserInfo userInfo = new UserInfo();
userInfo.setGender(1);
userInfo.setUsername("cyn");
userInfo.setPassword("123456");
userInfo.setDeleteFlag(1);
userInfo.setAge(12);
userInfoMapper.insert(userInfo);
}
查:根据具体需求传入参数
示例:查询id=35的数据
@Test
void selectById() {
UserInfo userInfo = userInfoMapper.selectById(35);
}
删:
可选择根据id删除,可以以map的形式传入数据
示例 删除id为35的数据
@Test
void delete() {
UserInfo userInfo = new UserInfo();
userInfo.setId(35);
userInfoMapper.deleteById(userInfo);
}
改:
示例:更改id为18的信息
@Test
void update(){
UserInfo userInfo = new UserInfo();
userInfo.setId(18);
userInfo.setGender(1);
userInfo.setUsername("cyn");
userInfo.setPassword("123456");
userInfo.setDeleteFlag(1);
userInfo.setAge(15);
userInfoMapper.updateById(userInfo);
}
可观察出来,更新成功
3.MyBatis-Plus复杂操作
如果我们的数据库设计是按照蛇形标准来设计数据库名以及字段名的话,驼峰方式命名类属性的话,MyBatis Plus会自动帮我们映射,但是如果实体类和数据库不是按照上述规则定义,就需要使用注解来帮我们映射。
3.1常见注解
@TableName
@TableName是类注解,用来表示当前类对应的数据库表名。
具体使用
mybatis-Plus是通过我们的类名去找表名的,当不符合规范就会找不到,但是加上@TableName注解讲明表名,就可以找到。
@TableFiled
@TableFiled注解这个是属性注解,跟@TableName作用一样,是用来对应当不符合规范命名时,对应类属性与数据库表字段的。
@TableId
@TableId注解,是用来对应主键的。
MyBatis - Plus默认主键是id,但是如果主键不是,就可以加上该注解表明这是主键对应的属性。还可以用 @TableId注解的type属性来设置当前是否是自增的。
@TableId(value = "id",type = IdType.AUTO)
private Integer userId;
如果属性名和字段名不⼀致,需要在 @TableId 指明对应的字段名
属性名和字段⼀致的情况下,直接加 @TableId 注解就可以.
3.2 条件构造器
MyBatis-Plus提供了⼀套强大的条件构造器(Wrapper),用于构建复杂的数据库查询条件.
Wrapper类允许开发者以链式调用的方式构造查询条件,无需编写繁琐的SQL语句,从而提高开发效率并减少SQL注入的风险.
以下是主要的Wrapper类及其功能:
• AbstractWrapper:这是⼀个抽象基类,提供了所有Wrapper类共有的方法和属性.
• QueryWrapper:用于构造查询条件,在AbstractWrapper的基础上拓展了⼀个select方法,允许指定查询字段.
• UpdateWrapper:用于构造更新条件,可以在更新数据时指定条件.
• LambdaQueryWrapper:基于Lambda表达式的查询条件构造器,它通过Lambda表达式来引用实体类的属性,从而避免了硬编码字段名
• LambdaUpdateWrapper:基于Lambda表达式的更新条件构造器,它允许你使用Lambda表达式来指定更新字段和条件,同样避免了硬编码字段名的问题.
方法介绍:
eq :用于设置单个字段的相等条件。
ne :设置单个字段的不相等条件。
gt:用于设置单个字段的大于条件。
ge:用于设置单个字段的大于等于条件。
lt:用于设置单个字段的小于条件。
le:设置单个字段的小于等于条件。
between:用于设置单个字段的 BETWEEN 条件。
like:用于设置单个字段的 LIKE 条件。
likeLeft:设置单个字段的右模糊匹配条件。
QueryWrapper
QueryWrapper并不只用于查询语句,修改, 删除, 查询,需要根据条件查询的时候都可以使用QueryWrapper来构建查询条件。
例如下面的sql语句:
SELECT id,username,password,age FROM user_info WHERE age = 16 AND username like "%name%"
测试类:
@Test
void selectByCondition() {
QueryWrapper<UserInfo> queryWrapper = new QueryWrapper<>();
queryWrapper.select("id, username, password, age, delete_flag")
.eq("age", 16)
.like("username", "name");
userInfoMapper.selectList(queryWrapper);
}
注意:
默认情况下Mybatis-Plus会根据 @TableFiled 生成别名,当指定了QueryWrapper的select属性后就仅仅是属性值而没有了别名.查询出来的结果会对应不上
解决办法:
- 写自定义SQL
- 实体类名和字段名保持⼀致
- 不指定QueryWrapper的select字段
- 使用LambdaQueryWrapper实现
UPDATE user_info SET username=“” WHERE (age < 15)
测试类
@Test
void updateByCondition(){
UpdateWrapper<UserInfo> updateWrapper=new UpdateWrapper<>();
updateWrapper.set("username","update")
.lt("age",15);
userInfoMapper.update(updateWrapper);
}
LambdaQueryWrapper
LambdaQueryWrapper是基于Lambda表达式的条件构造器,它通过 Lambda 表达式来引用实体类的属性,从而避免了硬编码字段名。也提高了代码的可读性和可维护性。
sql:
select id, username, password, age, delete_flag from user_info where age=5 and username like "%up%"
测试类
@Test
void selectByCondition2() {
// select id, username, password, age, delete_flag from user_info where age=5 and username like "%up%"
LambdaQueryWrapper<UserInfo> lambdaQueryWrapper= new LambdaQueryWrapper<>();
lambdaQueryWrapper.select(UserInfo::getId,UserInfo::getUsername,UserInfo::getPassword,UserInfo::getAge,UserInfo::getDeleteFlag)
.eq(UserInfo::getAge, 4)
.like(UserInfo::getUsername, "username");
userInfoMapper.selectList(lambdaQueryWrapper).forEach(x-> System.out.println(x));
}
LambdaUpdateWrapper
更新
sql:
UPDATE user_info SET delete_flag=0,password=“password5”,age=20,gender=1 WHERE (id IN (27,31))
@Test
void updateByCondition4(){
LambdaUpdateWrapper<UserInfo> lambdaUpdateWrapper=new LambdaUpdateWrapper<>();
lambdaUpdateWrapper.set(UserInfo::getDeleteFlag,0)
.set(UserInfo::getPassword,"password5").set(UserInfo::getAge,20).set(UserInfo::getGender,1).in(UserInfo::getId, List.of(27,31));
userInfoMapper.update(lambdaUpdateWrapper);
}
自定义sql
使用 Wrapper 自定义 SQL
注意事项
版本要求:确保你的项目中使用的MyBatis-Plus版本至少为 3.0.7,以支持自定义 SQL 功能。
参数命名:在自定义 SQL 时,传递 Wrapper 对象作为参数时,参数名必须为 ew
或者使用注解 @Param(Constants.WRAPPER) 明确指定参数为 Wrapper 对象。
使用 ${ew.customSqlSegment}:在 SQL 语句中,使用 ${ew.customSqlSegment} 来引用 Wrapper 对象生成的 SQL 片段。
不支持基于 entity 的 where 语句:自定义 SQL 时,Wrapper 对象不会基于实体类自动生成 where 子句,你需要手动编写完整的 SQL 语句。
示例
sql:
select id, username, password, age from user_info WHERE age < 20
UserInfoMapper:
@Mapper
public interface UserInfoMapper extends BaseMapper<UserInfo> {
@Select("select id, username, password, age from user_info ${ew.customSqlSegment}")
List<UserInfo> selectUserInfoByCondition(@Param(Constants.WRAPPER) Wrapper<UserInfo> queryWrapper);
}
测试类
@Test
void selectUserInfoByCondition() {
QueryWrapper<UserInfo> queryWrapper = new QueryWrapper<>();
queryWrapper.lt("age", 20);
userInfoMapper.selectUserInfoByCondition(queryWrapper).forEach(System.out::println);
}