SpringBoot集成MyBatis-Plus快速入门Demo

目录

1. MyBatis-Plus概述

2. MyBatis-Plus框架结构

3. MyBatis-Plus快速入门

3.1 创建表

3.2 创建工程

3.3 导入依赖

3.4 添加配置文件application.yml,配置数据库信息

3.5 创建实体类(包括自动填充)

3.6 创建配置类(包括配置乐观锁、分页、逻辑删除等插件) 

3.7 编写自动填充handler类

3.8 编写mapper接口类

3.9 编写启动类,添加MapperScan

3.10 编写测试类,CRUD操作

3.11 编写多条件查询测试类

3.12 性能分析

3.12.1 配置文件中添加配置

3.12.2 配置类中添加插件 

4. Demo下载地址


1. MyBatis-Plus概述

        MyBatis-Plus(简称 MP)是一个MyBatis的增强工具,在MyBatis的基础上只做增强不做改变,为简化开发、提高效率而生。

        官网: https://baomidou.com/

2. MyBatis-Plus框架结构

MyBatis-Plus模块
序号模块功能
1

MyBatis-Plus Core

核心模块,提供了对MyBatis的增强和扩展,包括分页、动态SQL、对象映射等功能。

2

MyBatis-Plus JDBC

JDBC模块,提供了一些实用的方法,如获取数据库连接、执行SQL语句等。

3

MyBatis-Plus Meta

元数据模块,用于解析数据库的元数据信息,包括数据库表结构、字段信息等。

4

MyBatis-Plus PageHelper

分页模块,提供分页查询的功能

5

MyBatis-Plus Generator

代码生成模块,用于自动生成MyBatis的Mapper接口、XML文件和Java实体类。

6

MyBatis-Plus Annotations

注解模块,提供了一些自定义的注解,用于简化代码编写。

7

MyBatis-Plus Extensions

扩展模块,提供了一些实用的扩展功能,如缓存、事务管理等。

3. MyBatis-Plus快速入门

3.1 创建表

        创建数据库mybatis_db

        创建表user

CREATE TABLE user (
  id bigint(20) NOT NULL COMMENT '主键ID',
  name varchar(30) DEFAULT NULL COMMENT '姓名',
  age int(11) DEFAULT NULL COMMENT '年龄',
  email varchar(50) DEFAULT NULL COMMENT '邮箱',
  create_time datetime DEFAULT NULL COMMENT '创建时间',
  update_time datetime DEFAULT NULL COMMENT '修改时间',
  version int(11) DEFAULT NULL COMMENT '版本',
  deleted int(11) DEFAULT NULL COMMENT '删除标记',
  PRIMARY KEY (`id`)
);

        添加测试数据

INSERT INTO `user` VALUES
(1, '张三', 18, 'zs@qq.com', '2024-01-17 10:31:30', '2024-01-17 10:31:30', 1, 0),
(2, '李四', 20, 'ls@qq.com', '2024-01-17 10:31:30', '2024-01-17 10:31:30', 1, 0),
(3, '王五', 28, 'ww@qq.com', '2024-01-17 10:31:30', '2024-01-17 10:31:30', 1, 0),
(4, '赵六', 21, 'zl@qq.com', '2024-01-17 10:31:30', '2024-01-17 10:31:30', 1, 0),
(5, '周七', 24, 'zq@qq.com', '2024-01-17 10:31:30', '2024-01-17 10:31:30', 1, 0);

3.2 创建工程

        设置 Maven

        设置自动导入包 Auto Import

        设置启动注解 Annotation Processors

3.3 导入依赖

<!--引入springboot依赖-->
<parent>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-parent</artifactId>
    <version>2.3.4.RELEASE</version>
</parent>

<dependencies>
    <!--引入spring-boot启动器依赖, 添加启动器后web工程常用的依赖会自动帮你引入-->
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
    </dependency>
    <!--test-->
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-test</artifactId>
        <scope>test</scope>
    </dependency>
    <!--lombok-->
    <dependency>
        <groupId>org.projectlombok</groupId>
        <artifactId>lombok</artifactId>
    </dependency>
    <!--mybatis-plus-->
    <dependency>
        <groupId>com.baomidou</groupId>
        <artifactId>mybatis-plus-boot-starter</artifactId>
        <version>3.0.5</version>
    </dependency>
    <!--mysql-->
    <dependency>
        <groupId>mysql</groupId>
        <artifactId>mysql-connector-java</artifactId>
        <version>8.0.16</version>
    </dependency>
</dependencies>

<!--打包-->
<build>
    <plugins>
        <plugin>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-maven-plugin</artifactId>
        </plugin>
    </plugins>
</build>

3.4 添加配置文件application.yml,配置数据库信息

# 配置日志输出格式
logging:
  pattern:
    console: "%clr(%5p) %clr(-){faint} %clr(%-80.80logger{79}){cyan} %clr(:) %m%n"

spring:
  # 数据源配置
  datasource:
    username: root     #数据库用户名
    password: 163.com  #密码
    url: jdbc:mysql://localhost:3306/mybatis_db?serverTimezone=GMT%2B8
    driver-class-name: com.mysql.cj.jdbc.Driver

# sql输出日志配置
mybatis-plus:
  configuration:
    log-impl: org.apache.ibatis.logging.stdout.StdOutImpl

3.5 创建实体类(包括自动填充)

package com.miaxis.entity;

import com.baomidou.mybatisplus.annotation.*;
import lombok.Data;

import java.util.Date;

@Data
@TableName("user")
public class User {
    @TableId(type = IdType.ID_WORKER) //主键生成策略
    private Long id;
    private String name;
    private Integer age;
    private String email;
    @TableField(fill = FieldFill.INSERT)
    private Date createTime;  //自动填充
    @TableField(fill = FieldFill.INSERT_UPDATE)
    private Date updateTime;  //自动填充
    @TableField(fill = FieldFill.INSERT)
    @Version
    private Integer version;   //自动填充 当做更新时, version字段会自动加1
    @TableLogic   //逻辑删除
    @TableField(fill = FieldFill.INSERT) //自动填充
    private Integer deleted;
}

3.6 创建配置类(包括配置乐观锁、分页、逻辑删除等插件) 

package com.miaxis.config;

import com.baomidou.mybatisplus.core.injector.ISqlInjector;
import com.baomidou.mybatisplus.extension.injector.LogicSqlInjector;
import com.baomidou.mybatisplus.extension.plugins.OptimisticLockerInterceptor;
import com.baomidou.mybatisplus.extension.plugins.PaginationInterceptor;
import com.baomidou.mybatisplus.extension.plugins.PerformanceInterceptor;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Profile;

@Configuration
public class Config {
    /*配置乐观锁插件*/
    @Bean
    public OptimisticLockerInterceptor optimisticLockerInterceptor(){
        return  new OptimisticLockerInterceptor();
    }

    /*配置分页插件*/
    @Bean
    public PaginationInterceptor paginationInterceptor(){
        return new PaginationInterceptor();
    }

    /*逻辑删除配置*/
    @Bean
    public ISqlInjector sqlInjector() {
        return new LogicSqlInjector();
    }
}

乐观锁:一个人操作时,允许多人可以同时操作,但是同一时刻只能有一个操作。使用一个额外的字段Version,取出记录时,获取当前version,更新时,带上这个version,把version值+1。


逻辑删除(假删除),将对应数据中代表是否被删除字段状态修改为“被删除状态”,之后在数据库中仍旧能看到此条数据记录 。逻辑删除添加后,使用查询, 查询的内容只有标记为0的被查出来

3.7 编写自动填充handler类

添加注解 来去指明 哪些字段需要自动填充

package com.miaxis.handler;

import com.baomidou.mybatisplus.core.handlers.MetaObjectHandler;
import org.apache.ibatis.reflection.MetaObject;
import org.springframework.stereotype.Component;

import java.util.Date;
/* 1.编写handler 指定 填充的内容
 * 2.在实体类当中 添加注解 来去指明 哪些字段需要自动填充
 * */
@Component
public class UserMetaObjectHandler implements MetaObjectHandler {
    @Override
    public void insertFill(MetaObject metaObject) {
        this.setFieldValByName("createTime",new Date(),metaObject);
        this.setFieldValByName("updateTime",new Date(),metaObject);
        this.setFieldValByName("version",1,metaObject);
        this.setFieldValByName("deleted",0,metaObject);
    }

    @Override
    public void updateFill(MetaObject metaObject) {
        this.setFieldValByName("updateTime",new Date(),metaObject);
    }
}

3.8 编写mapper接口类

package com.miaxis.mapper;

import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.miaxis.entity.User;

public interface UserMapper extends BaseMapper<User> {
}

3.9 编写启动类,添加MapperScan

package com.miaxis;

import org.mybatis.spring.annotation.MapperScan;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;

@SpringBootApplication
@MapperScan("com.miaxis.mapper")
public class Application {
    public static void main(String[]   args  ) {
        SpringApplication.run(Application.class,  args  );
    }
}

3.10 编写测试类,CRUD操作

package com.miaxis;

import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.miaxis.entity.User;
import com.miaxis.mapper.UserMapper;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;

import java.util.Arrays;
import java.util.HashMap;
import java.util.List;

@SpringBootTest
public class ApplicationTests {
    @Autowired
    private UserMapper userMapper;

    @Test
	//查询所有内容
    public void getAll() {  /*如果添加了逻辑删除  默认查询只会查询出标记为0的选项*/
        /**查询所有内容*/
        List<User> users = userMapper.selectList(null);
        /** 打印集合中元素*/
        users.forEach(System.out::println);
    }

    @Test
	//create添加数据
    public void testInsert(){
        User user = new User();
        user.setName("fmjava");
        user.setAge(1);
        user.setEmail("fmjava.com@qq.com");
        int result = userMapper.insert(user);
        System.out.println(result);       //影响的行数
        System.out.println(user.getId()); //id自动回填
    }

    @Test
	//read读取数据
    public void testSelect(){
        //根据单个id查询
        User user = userMapper.selectById(2);
        System.out.println(user);
    }

    @Test
	//read读取数据
    public void testSelect2(){
        //多id批量查询
        List<User> users = userMapper.selectBatchIds(Arrays.asList(2, 3, 4));
        users.forEach(System.out::println);
    }

    @Test
	//read读取数据
    public void testSelect3(){
        //把需要查询的条件添加到map当中
        HashMap<String,Object> map = new HashMap<>();
        map.put("name","王五");
        map.put("age","28");
        List<User> users = userMapper.selectByMap(map);
        users.forEach(System.out::println);
    }

    @Test
	//分页查询
    public void selectByPage(){
        /*当前页,  一页查询多少条记录*/
        Page<User> page = new Page<>(2, 3);
        userMapper.selectPage(page,null);
        /*把查询出所有结果给封装到page对象当中*/
        System.out.println("当前页 : "+page.getCurrent());
        System.out.println("每页数据 : "+page.getRecords());
        System.out.println("每页显示多少条记录 :"+page.getSize());
        System.out.println("总记录数 : "+page.getTotal());
        System.out.println("总页数 : "+page.getPages());

        System.out.println("是否有下一页 : "+page.hasNext());
        System.out.println("是否有上一页 : "+page.hasPrevious());
    }

    @Test
	//update修改数据
    public void update(){
        //先查询
        User user = userMapper.selectById(1L);
        //修改数据
        user.setName("zs1");
        //执行更新
        int nRet = userMapper.updateById(user);
        if(nRet <= 0) {
            System.out.println("更新失败");
        }else {
            System.out.println("更新成功");
        }
    }

    @Test
	//update修改数据
    public void update2(){
        //先查询
        User user = userMapper.selectById(1L);
        //修改数据
        user.setName("zs2");
        //模拟取出数据后,数据库中version实际数据比取出的值大,即已被其它线程修改并更新了version
        //把版本给变小,发现代码能执行成功,但是没有修改成功
        user.setVersion(user.getVersion() -1);
        //执行更新
        int nRet = userMapper.updateById(user);
        if(nRet <= 0) {
            System.out.println("更新失败");
        }else {
            System.out.println("更新成功");
        }
    }

    @Test
	//delete删除数据
    public void deleteTest(){     /*逻辑删除*/
        int i = userMapper.deleteById(1L);
        System.out.println(i);
    }

    @Test
	//delete删除数据
    public void deleteTest2(){
        int i = userMapper.deleteBatchIds(Arrays.asList(2,3,4));
        System.out.println(i);
    }

    @Test
	//delete删除数据
    public void deleteTest3(){
        HashMap<String, Object> hashMap = new HashMap<>();
        hashMap.put("name","fmjava2");
        userMapper.deleteByMap(hashMap);
    }
}

3.11 编写多条件查询测试类

package com.miaxis;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.miaxis.entity.User;
import com.miaxis.mapper.UserMapper;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;

import java.util.HashMap;
import java.util.List;
import java.util.Map;

@SpringBootTest
public class ApplicationTests2 {
    @Autowired
    private UserMapper userMapper;

    @Test
    public void test1(){
        QueryWrapper<User> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("name","李四")
                .ne("age",10);
        List<User> users = userMapper.selectList(queryWrapper);
        System.out.println(users);
    }

    @Test
    public void test2(){
        QueryWrapper<User> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("name","李四")
                .ge("age",24)
                .isNotNull("email");
        userMapper.delete(queryWrapper);
    }

    @Test
    public void testSelectCount() {
        QueryWrapper<User> queryWrapper = new QueryWrapper<>();
        queryWrapper.between("age", 20, 30);
        Integer count = userMapper.selectCount(queryWrapper);
        System.out.println(count);
    }

    @Test
    public void testSelectList() {
        QueryWrapper<User> queryWrapper = new QueryWrapper<>();
        Map<String, Object> map = new HashMap<>();
        map.put("id", 3L);
        map.put("name", "王五");
        map.put("age", 28);

        queryWrapper.allEq(map);
        List<User> users = userMapper.selectList(queryWrapper);
        users.forEach(System.out::println);
    }

    @Test
    public void testSelectMaps() {
        QueryWrapper<User> queryWrapper = new QueryWrapper<>();
        queryWrapper
                .notLike("name", "fm")
                .likeRight("email", "l");
        List<User> maps = userMapper.selectList(queryWrapper);//返回值是Map列表
        maps.forEach(System.out::println);
    }

    @Test
    public void testSelectObjs() {
        QueryWrapper<User> queryWrapper = new QueryWrapper<>();
        //queryWrapper.in("id", 1, 2, 3);
        queryWrapper.inSql("id", "select id from user where id < 3");
        List<Object> objects = userMapper.selectObjs(queryWrapper);//返回值是Object列表
        objects.forEach(System.out::println);
    }

    @Test
    public void testUpdate1() {
        //修改值
        User user = new User();
        user.setAge(99);
        user.setName("gxq");
        //修改条件
        UpdateWrapper<User> userUpdateWrapper = new UpdateWrapper<>();
        userUpdateWrapper
                .like("name", "fm")
                .or()
                .between("age", 20, 30);
        int result = userMapper.update(user, userUpdateWrapper);
        System.out.println(result);
    }

    @Test
    public void testUpdate2() {
        //修改值
        User user = new User();
        user.setAge(10);
        user.setName("myxq");
        //修改条件
        UpdateWrapper<User> userUpdateWrapper = new UpdateWrapper<>();
        userUpdateWrapper
                .like("name", "A")
                .or(i -> i.eq("name", "gxq").ne("age", 20));
        int result = userMapper.update(user, userUpdateWrapper);
        System.out.println(result);
    }

    @Test
    public void testSelectListOrderBy() {
        QueryWrapper<User> queryWrapper = new QueryWrapper<>();
        queryWrapper.orderByDesc("id");
        List<User> users = userMapper.selectList(queryWrapper);
        users.forEach(System.out::println);
    }

    @Test
    public void testSelectListLast() {
        QueryWrapper<User> queryWrapper = new QueryWrapper<>();
        /**只能调用一次,多次调用以最后一次为准 有sql注入的风险,请谨慎使用*/
        queryWrapper.last("limit 1");
        List<User> users = userMapper.selectList(queryWrapper);
        users.forEach(System.out::println);
    }

    @Test
    public void testSelectListColumn() {
        QueryWrapper<User> queryWrapper = new QueryWrapper<>();
        queryWrapper.select("id", "name", "age");
        List<User> users = userMapper.selectList(queryWrapper);
        users.forEach(System.out::println);
    }
    
    @Test
    public void testUpdateSet() {
        //修改值
        User user = new User();
        user.setAge(10);
        //修改条件
        UpdateWrapper<User> userUpdateWrapper = new UpdateWrapper<>();
        userUpdateWrapper
                .like("name", "A")
                .set("name", "fmjava")//除了可以查询还可以使用set设置修改的字段
                .setSql(" email = 'fmjava@qq.com'");//可以有子查询
        int result = userMapper.update(user, userUpdateWrapper);
    }
}

3.12 性能分析

        概述:性能分析拦截器,用于输出每条 SQL 语句及其执行时间。SQL 性能执行分析,开发环境使用,超过指定时间,停止运行,有助于发现问题。

3.12.1 配置文件中添加配置

#环境设置:dev、test、prod
spring:
    profiles:
        active: test

3.12.2 配置类中添加插件 

/**
 * SQL 执行性能分析插件
 * 开发环境使用,线上不推荐。
 * 参数:maxTime: SQL 执行最大时长,超过自动停止运行,有助于发现问题。
 * 参数:format: SQL是否格式化,默认false。
 */
@Bean
@Profile({"test"})  // 设置 test 环境开启(可以设置多个 {"test","dev","prod"})
public PerformanceInterceptor performanceInterceptor(){
    PerformanceInterceptor performanceInterceptor = new PerformanceInterceptor();
    performanceInterceptor.setMaxTime(1000);//超过此处设置的ms sql不会执行
    performanceInterceptor.setFormat(true);//格式化sql
    return performanceInterceptor;
}

4. Demo下载地址

编译器版本:IntelliJ IDEA 2020.3.2 x64

JDK版本:java 1.8.0_111

下载地址:https://download.csdn.net/download/mickey2007/89059102

  • 76
    点赞
  • 13
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值