1. MyBatis-Plus入门
1.1 数据库准备
DROP TABLE IF EXISTS user;
CREATE TABLE user
(
id BIGINT(20) NOT NULL COMMENT '主键ID',
name VARCHAR(30) NULL DEFAULT NULL COMMENT '姓名',
age INT(11) NULL DEFAULT NULL COMMENT '年龄',
email VARCHAR(50) NULL DEFAULT NULL COMMENT '邮箱',
PRIMARY KEY (id)
);INSERT INTO user (id, name, age, email) VALUES
(1, 'Jone', 18, '[email protected]'),
(2, 'Jack', 20, '[email protected]'),
(3, 'Tom', 28, '[email protected]'),
(4, 'Sandy', 21, '[email protected]'),
(5, 'Billie', 24, '[email protected]');
1.2 导入依赖
<!-- 测试环境 快速启动SpringBoot项目-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
</dependency>
<!-- mybatis-plus -->
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-boot-starter</artifactId>
<version>3.5.3.1</version>
</dependency><!-- 数据库相关配置启动器 -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-jdbc</artifactId>
</dependency><!-- druid启动器的依赖 -->
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>druid-spring-boot-3-starter</artifactId>
<version>1.2.18</version>
</dependency><!-- 驱动类-->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>8.0.28</version>
</dependency>
1.3 准备配置文件和启动类
application.yaml
# 连接池配置
spring:
datasource:
type: com.alibaba.druid.pool.DruidDataSource
druid:
url: jdbc:mysql:///day01
username: root
password: root
driver-class-name: com.mysql.cj.jdbc.Driver
启动类(@MapperScan 注解,扫描Mapper层)
@MapperScan("com.xxx.mapper")
@SpringBootApplication
public class MainApplication {
public static void main(String[] args) {
SpringApplication.run(MainApplication.class,args);
}
}
1.4 功能编码
实体类
@Data
public class User {
private Long id;
private String name;
private Integer age;
private String email;
}
编写Mapper接口,继承mybatis-plus提供的基础Mapper接口,自带单表的crud方法!
public interface UserMapper extends BaseMapper<User> {
}
1.5 测试类
@SpringBootTest //springboot下测试环境注解
public class SampleTest {
@Autowired
private UserMapper userMapper;
@Test
public void testSelect() {
System.out.println(("----- selectAll method test ------"));
List<User> userList = userMapper.selectList(null);
userList.forEach(System.out::println);
}
}
通过以上几个简单的步骤,我们发现XML 文件都不用编写,就可以实现 User 表的 CRUD 功能,
集成MyBatis-Plus
非常的简单,只需要引入 starter 工程,并配置 mapper 扫描路径即可。
2. 基于Mapper接口的CRUD
Mapper Interface步骤:Mapper层接口继承BaseMapper(内部包含常见的单表操作!)
public interface UserMapper extends BaseMapper<User> {
//正常自定义方法!
//可以使用注解@Select或者mapper.xml实现
List<User> queryAll();
}
常见方法查看接口文档:Mapper Interface
为什么设计实体类时属性要用包装类修饰原因之一:当update()操作传入一个实体类对象时,如果对象的属性值为null,则不会修改此属性与之映射的字段!但是如果为基本数据类型,则会修改成为默认值。
3. 基于Service接口的CRUD
对比Mapper接口CRUD区别:
service添加了批量方法
service层的方法自动添加事务
步骤:接口需继承IService接口、实现类需继承ServiceImpl实现类
public interface UserService extends IService<User> {
}
@Service
public class UserServiceImpl extends ServiceImpl<UserMapper,User> implements UserService{
}
常见方法查看接口文档:Service Interface
4. 分页查询实现
1.在SpringBoot启动类中加入分页插件组件
@Bean
public MybatisPlusInterceptor mybatisPlusInterceptor() {
MybatisPlusInterceptor interceptor = new MybatisPlusInterceptor();
interceptor.addInnerInterceptor(new PaginationInnerInterceptor(DbType.MYSQL));
return interceptor;
}
2.使用分页查询
@Test
public void testPageQuery(){
//设置分页参数
Page<User> page = new Page<>(1, 5);
userMapper.selectPage(page, null);
//获取分页数据,分页查询的结果分装在了page对象中
List<User> list = page.getRecords();
list.forEach(System.out::println);
System.out.println("当前页:"+page.getCurrent());
System.out.println("每页显示的条数:"+page.getSize());
System.out.println("总记录数:"+page.getTotal());
System.out.println("总页数:"+page.getPages());
System.out.println("是否有上一页:"+page.hasPrevious());
System.out.println("是否有下一页:"+page.hasNext());
}
5. 条件构造器
条件构造器类结构(主要是四个实现类):
常用组装条件:
基于QueryWrapper 的组装:
@Test
public void test01(){
//查询用户名包含a,年龄在20到30之间,并且邮箱不为null的用户信息
//SELECT id,username AS name,age,email,is_deleted FROM t_user
// WHERE is_deleted=0 AND (username LIKE ? AND age BETWEEN ? AND ?
// AND email IS NOT NULL)
QueryWrapper<User> queryWrapper = new QueryWrapper<>();
queryWrapper.like("username", "a")
.between("age", 20, 30)
.isNotNull("email");
List<User> list = userMapper.selectList(queryWrapper);
list.forEach(System.out::println);
基于UpdateWapper 的组装:
@Test
public void testQuick2(){
UpdateWrapper<User> updateWrapper = new UpdateWrapper<>();
//将id = 3 的email设置为null, age = 18
updateWrapper.eq("id",3)
.set("email",null) // set 指定列和结果
.set("age",18);
//如果使用updateWrapper 实体对象写null即可!
int result = userMapper.update(null, updateWrapper);
System.out.println("result = " + result);
}
基于LambdaQueryWapper 的组装:
@Test
public void testQuick4(){
String name = "root";
int age = 18;
QueryWrapper<User> queryWrapper = new QueryWrapper<>();
//每个条件拼接方法都condition参数,这是一个比较运算,为true追加当前条件!
//eq(condition,列名,值)
queryWrapper.eq(!StringUtils.isEmpty(name),"name",name)
.eq(age>1,"age",age);
//TODO: 使用lambdaQueryWrapper
LambdaQueryWrapper<User> lambdaQueryWrapper = new LambdaQueryWrapper<>();
//注意: 需要使用方法引用
//技巧: 类名::方法名
lambdaQueryWrapper.eq(!StringUtils.isEmpty(name), User::getName,name);
List<User> users= userMapper.selectList(lambdaQueryWrapper);
System.out.println(users);
}
基于LambdaUpdateWrapper组装:
@Test
public void testQuick2(){
UpdateWrapper<User> updateWrapper = new UpdateWrapper<>();
//将id = 3 的email设置为null, age = 18
updateWrapper.eq("id",3)
.set("email",null) // set 指定列和结果
.set("age",18);
//使用lambdaUpdateWrapper
LambdaUpdateWrapper<User> updateWrapper1 = new LambdaUpdateWrapper<>();
updateWrapper1.eq(User::getId,3)
.set(User::getEmail,null)
.set(User::getAge,18);
//如果使用updateWrapper 实体对象写null即可!
int result = userMapper.update(null, updateWrapper);
System.out.println("result = " + result);
}
相比于 QueryWrapper,LambdaQueryWrapper 使用了实体类的属性引用(例如 User::getName
、User::getAge
),而不是字符串来表示字段名,提高了代码的可读性和可维护性。
6. 核心注解
@TableName注解
-
描述:表名注解,标识实体类对应的表
-
使用位置:实体类
特殊情况:如果表名和实体类名相同(忽略大小写)可以省略该注解!
其他解决方案:全局设置前缀
@TableId 注解
-
描述:主键注解
-
使用位置:实体类主键字段
@TableName("sys_user")
public class User {
@TableId(value="主键列名",type=主键策略)
private Long id;
private String name;
private Integer age;
private String email;
}
mybatis-plus:
configuration:
# 配置MyBatis日志
log-impl: org.apache.ibatis.logging.stdout.StdOutImpl
global-config:
db-config:
# 配置MyBatis-Plus操作表的默认前缀
table-prefix: t_
# 配置MyBatis-Plus的主键策略
id-type: auto
@TableField 注解
- 描述:字段注解(非主键)
- 位置:实体类非主键字段
@TableName("sys_user")
public class User {
@TableId
private Long id;
@TableField("nickname")
private String name;
private Integer age;
private String email;
}
@TableLogic 逻辑删除注解
@Data
public class User {
// @TableId
private Integer id;
private String name;
private Integer age;
private String email;
@TableLogic
//数据库中添加逻辑删除字段,实体类中添加逻辑删除属性
// mybatis-plus下,默认 逻辑删除值为1 未逻辑删除 0
private Integer deleted;
}
全局配置:
mybatis-plus:
global-config:
db-config:
logic-delete-field: deleted # 全局逻辑删除的实体字段名(since 3.3.0,配置后可以忽略不配置步骤2)
logic-delete-value: 1 # 逻辑已删除值(默认为 1)
logic-not-delete-value: 0 # 逻辑未删除值(默认为 0)
@Version 乐观锁实现注解
//添加乐观锁插件
@Bean
public MybatisPlusInterceptor mybatisPlusInterceptor() {
MybatisPlusInterceptor interceptor = new MybatisPlusInterceptor();
interceptor.addInnerInterceptor(new OptimisticLockerInnerInterceptor());
return interceptor;
}
//数据库中添加version字段,实体类中添加 版本号 属性
@Version
private Integer version;
//演示乐观锁生效场景
@Test
public void testQuick7(){
//步骤1: 先查询,在更新 获取version数据
//同时查询两条,但是version唯一,最后更新的失败
User user = userMapper.selectById(5);
User user1 = userMapper.selectById(5);
user.setAge(20);
user1.setAge(30);
userMapper.updateById(user);
//乐观锁生效,失败!
userMapper.updateById(user1);
}
防全表更新和删除实现:添加拦截器
@Bean
public MybatisPlusInterceptor mybatisPlusInterceptor() {
MybatisPlusInterceptor interceptor = new MybatisPlusInterceptor();
interceptor.addInnerInterceptor(new BlockAttackInnerInterceptor());
return interceptor;
}
}
标签:name,概括,age,private,println,Plus,MyBatis,new,public From: https://blog.csdn.net/qq_64784567/article/details/140095124