一:Mybatis-Plus简介
Mybatis是一款优秀的持久层框架,主要用于JDBC的开发和SpringBoot搭配访问和处理数据库中的信息,Mybatis原名为iBatis,是由Apache的一个开源项目,后来迁移到了google code改名为Mybatis,并在2013年的11月份再次迁移到Github。MyBatis在继承了JDBC优点的同时解决了JDBC硬编码、代码繁琐、资源浪费和性能较低等问题,称为Java程序中操作数据库的首选。它操作数据库主要通过两种手段,第一种是在Mapper接口中的方法上方用注解注入SQL语句进行查询,第二种是通过XML映射文件写入复杂的语句,多用于动态SQL语句的拼接。MyBatis-Plus(简称mp)在继承了Mybatis功能的基础上新增了很多方法,它的出现是为了增强Mybatis的功能但不与之冲突,Mybatis程序在注入mp后依旧可以运行,但是mp中已经包含了Mybatis框架,所以无需第二次注入依赖。mp里封装了基础的增删改查方法,使用者可以自行调用,并且支持lambda表达式的使用,使代码更简洁,提升使用体验,mp中还优化了拦截器和分页等功能,需要时自行引入即可。MyBatis-Plus官方网址https://www.baomidou.com/pages/24112f/
二:快速入门案例
1:创建springboot项目
版本选3.0以下!!!
2:加载依赖
//mybatis-plus依赖
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-boot-starter</artifactId>
<version>3.5.1</version>
</dependency>
//mysql依赖(根据自己的mysql版本写哦,mysql5.7前后用的依赖和驱动不一样)
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>5.1.44</version>
</dependency>
//小白比较懒,不愿意写get、set有参无参那些,所以用了这个插件,看个人偏好吧
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
</dependency>
3:创建实体类(entily)和数据访问层(mapper)
UserMapper代码
@Mapper
public interface UserMapper extends BaseMapper<User> {
}
User代码
@Data
public class User {
private Long id;
private String name;
private String password;
private Integer age;
private String tel;
}
4:编写数据源(配置类)
这些属性就不用小白解释了叭,注意小白这里用的mysql5.1,所以写的是(com.mysql.jdbc.Driver),如果是5.7以上版本要写(com.mysql.cj.jdbc.Driver)
spring:
datasource:
driver-class-name: com.mysql.jdbc.Driver
url: jdbc:mysql://localhost:3306/mybatisplus_db?useUnicode=true&characterEncoding=utf8&useSSL=false&serverTimezone=Asia/Shanghai
username: root
password: root
这里小白送大家一个测试用的数据库叭
create database if not exists mybatisplus_db character set utf8;
use mybatisplus_db;
CREATE TABLE `user` (
`id` bigint(20) NOT NULL AUTO_INCREMENT COMMENT '编号' ,
`name` varchar(32) CHARACTER SET utf8 COLLATE utf8_general_ci NOT NULL COMMENT '用户名' ,
`password` varchar(32) CHARACTER SET utf8 COLLATE utf8_general_ci NOT NULL COMMENT '密码' ,
`age` int(3) NOT NULL COMMENT '龄年' ,
`tel` varchar(32) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL COMMENT '电话' ,
PRIMARY KEY (`id`)
);
insert into user values(null,'tom','123456',12,'12345678910');
insert into user values(null,'jack','123456',8,'12345678910');
insert into user values(null,'jerry','123456',15,'12345678910');
insert into user values(null,'tom','123456',9,'12345678910');
insert into user values(null,'snake','123456',28,'12345678910');
insert into user values(null,'张益达','123456',22,'12345678910');
insert into user values(null,'张大炮','123456',16,'12345678910');
4:mp常用方法展示
(1):我这里用的是junit进行测试,首先加载依赖项
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
(2):把UserMapper加载到测试类中
@Autowired
private UserMapper userMapper;
(3)常用方法展示
分页查询需要加载mp自带的分页拦截器,需要先创建拦截器对象再添加各种拦截器,创建mp拦截器(MybatisPlusConfig):
@Configuration
public class MybatisPlusConfig {
/**
* mybatisplus拦截器
*/
@Bean
public MybatisPlusInterceptor mybatisPlusInterceptor(){
MybatisPlusInterceptor mybatisPlusInterceptor = new MybatisPlusInterceptor();
//对分页操作进行拦截
mybatisPlusInterceptor.addInnerInterceptor( new PaginationInnerInterceptor(DbType.MYSQL));
return mybatisPlusInterceptor;
}
}
常用方法测试
/**
* 查询
*/
@Test
void test01() {
List<User> userList = userMapper.selectList(null);
System.out.println(userList);
}
/**
* 添加
*/
@Test
void test02(){
User user = new User();
user.setName("钱凯乐");
user.setPassword("qklwfm");
user.setAge(18);
user.setTel("15367788541");
userMapper.insert(user);
System.out.println("添加完毕");
}
/**
* 修改
*/
@Test
void test03(){
User user = new User();
user.setName("小白");
user.setId(8);
userMapper.updateById(user);
System.out.println("更新完毕");
}
/**
* 删除
*/
@Test
void test04(){
User user = new User();
user.setId(8);
userMapper.deleteById(user);
System.out.println("删除成功");
}
/**
* 通过id查找
*/
@Test
void test05(){
User user = new User();
user.setId(7);
User user1 = userMapper.selectById(user.getId());
System.out.println(user1);
}
/**
* 分页查询
*/
@Test
void test06(){
Page page = new Page(2,5);
userMapper.selectPage(page,null);
System.out.println("共几条:"+page.getTotal());
System.out.println("共几页:"+page.getPages());
System.out.println("第几页:"+page.getCurrent());
System.out.println("每页几条:"+page.getSize());
System.out.println(page.getRecords());//当前页面数据
}
/**
* 条件查询:QueryWrapper
*/
@Test
void test01(){
QueryWrapper queryWrapper = new QueryWrapper();
queryWrapper.eq("age",12);
List list = userMapper.selectList(queryWrapper);
System.out.println(list);
}
/**
* 条件查询:QueryWrapper.lambda()
*/
@Test
void test02(){
QueryWrapper<User> queryWrapper = new QueryWrapper<>();
queryWrapper.lambda().eq(User::getAge,12);
List list = userMapper.selectList(queryWrapper);
System.out.println(list);
}
/**
* 条件查询:LambdaQueryWrapper
*/
@Test
void test03(){
LambdaQueryWrapper<User> lambdaQueryWrapper = new LambdaQueryWrapper<>();
lambdaQueryWrapper.eq(User::getAge,16);
lambdaQueryWrapper.eq(User::getId,7);
List list = userMapper.selectList(lambdaQueryWrapper);
System.out.println(list);
}
/**
*组合查询:or
*/
@Test
void test4(){
LambdaQueryWrapper<User> lambdaQueryWrapper = new LambdaQueryWrapper<>();
lambdaQueryWrapper.eq(User::getAge,12).or().eq(User::getAge,15);//or查询
List<User> list = userMapper.selectList(lambdaQueryWrapper);
System.out.println(list);
}
/**
* 条件查询:null判断
*/
@Test
void test5(){
Integer age = 12;
LambdaQueryWrapper<User> lambdaQueryWrapper = new LambdaQueryWrapper<>();
lambdaQueryWrapper.eq(age != null,User::getAge,age);//判断(age!=null)成立才走此条件
List list = userMapper.selectList(lambdaQueryWrapper);
System.out.println(list);
}
/**
* LambdaQueryWrapper 查询部分字段投影
*/
@Test
void test6(){
LambdaQueryWrapper<User> lambdaQueryWrapper = new LambdaQueryWrapper<>();
lambdaQueryWrapper.select(User::getId,User::getName);//指定要查询的字段
List list = userMapper.selectList(lambdaQueryWrapper);
System.out.println(list);
}
/**
* QueryWrapper 查询部分字段(投影)
*/
@Test
void test7(){
QueryWrapper<User> queryWrapper = new QueryWrapper<>();
queryWrapper.select("id","name");
List<User> userList = userMapper.selectList(queryWrapper);
System.out.println(userList);
}
/**
* 查询部分字段(聚合查询)
*/
@Test
void test8(){
QueryWrapper<User> queryWrapper = new QueryWrapper<>();
queryWrapper.select("count(*) as ct");
List list = userMapper.selectMaps(queryWrapper);//要查询表中不存在的字段,使用selectMaps方法
System.out.println(list);
}
/**
* 查询部分字段(聚合查询+分组)
*/
@Test
void test9(){
QueryWrapper<User> queryWrapper = new QueryWrapper<>();
queryWrapper.select("count(*) as ct");//聚合查询(统计)
queryWrapper.groupBy("tel");
List list = userMapper.selectMaps(queryWrapper);
System.out.println(list);
}
/**
* 范围查询
* 模糊查询
*/
@Test
void test10(){
LambdaQueryWrapper<User> lambdaQueryWrapper = new LambdaQueryWrapper<>();
//between
lambdaQueryWrapper.between(User::getAge,20,30);
//模糊查询 name like 'j%';
lambdaQueryWrapper.likeRight(User::getName,"j");
//排序
lambdaQueryWrapper.orderByDesc(User::getAge);
List<User> userList = userMapper.selectList(lambdaQueryWrapper);
System.out.println(userList);
}
/**
* 1. 实体类名与表名不同 解决:@TableName("tbl_user")
* 2. 属性与表字段不同名, 解决: @TableField("password")
* 3. 表中不存在此字段, 解决: @TableField(exist = false)
* 4. 敏感字段不允许查询, 解决:@TableField(select = false)
*/
@Test
void testSelect() {
List list = userDao.selectList(null);
System.out.println(list);
}
/**
* ID生成策略
*
*/
@Test
void testInsert() {
User user = new User();
user.setName("黑马程序员");
user.setPwd("itheima");
user.setAge(12);
user.setTel("4006184000");
userDao.insert(user);
System.out.println("添加完毕");
}
/**
* 多数据操作(批量处理)
*/
@Test
void testBatchDelete() {
//批量删除
List<Long> idList = new ArrayList<>();
idList.add(1L);
idList.add(2L);
idList.add(3L);
userDao.deleteBatchIds(idList);
System.out.println("批量删除完毕");
}
/**
* 多数据操作(批量处理)
*/
@Test
void testBatchSelect() {
//批量查询
List<Long> idList = new ArrayList<>();
idList.add(4L);
idList.add(5L);
idList.add(6L);
List<User> userList = userDao.selectBatchIds(idList);
System.out.println(userList);
}
/**
* 逻辑删除
*/
@Test
void testDelete() {
userDao.deleteById(6L);
System.out.println("删除完毕");
}
/**
* 逻辑删除: 如果实体类指定了逻辑删除字段,则select查询时会排除掉被删除的数据(deleted=1)
*/
@Test
void testSelect2() {
List list = userDao.selectList(null);
System.out.println(list);
}
/**
* 乐观锁
*/
@Test
void testLock() {
User user1 = userDao.selectById(1L);
user1.setAge(11);
User user2 = userDao.selectById(1L);
user2.setAge(13);
userDao.updateById(user2);
int rows = userDao.updateById(user1);
System.out.println("更新的数据条数:" + rows);
if(rows==0){
//重新从头抢库存
}
}
/**
* 乐观锁: 必须先从数据库中获取旧数据,然后再更新,否则乐观锁不生效
*/
@Test
void testLock2() {
User user1 = new User();
user1.setId(1L);
user1.setAge(11);
User user2 = new User();
user2.setId(1L);
user2.setAge(13);
userDao.updateById(user2);
int rows = userDao.updateById(user1);
System.out.println("更新的数据条数:" + rows);
if(rows==0){
//重新从头抢库存
}
}