SpringBoot结合MyBatisPlus轻松实现分页功能超详细教程(附完整实现代码以及保姆级解释)

前言

本文旨在使用SpringBoot + MyBatisPlus + thymeleaf 模版引擎实现分页效果。目标功能实现如下:
SpringBoot结合MyBatisPlus轻松实现分页功能超详细教程(附完整实现代码以及保姆级解释)_第1张图片
在此案例中,表单数据从数据库拿到,可动态显示当前页,总页数以及记录数。并且实现分页按钮组,包括动态生成页码,前一页和后一页。


首先,需要引入MyBatisPlus以及thymleaf模版引擎相关starter

<dependency>
    <groupId>com.baomidougroupId>
    <artifactId>mybatis-plus-boot-starterartifactId>
    <version>3.4.1version>
dependency>

<dependency>
    <groupId>org.springframework.bootgroupId>
    <artifactId>spring-boot-starter-thymeleafartifactId>
dependency>

相关环境引入之后,本文以User表为案例进行测试

测试实体类

@Data
@AllArgsConstructor
@NoArgsConstructor
@ToString
//指定该entity映射到数据库中user_table这张表
@TableName("user_table")
public class User {
    private Long id;
    private String name;
    private Integer age;
    private String email;
}

数据库表及字段(案例参照mybatisPlus官方文档)

CREATE TABLE user_table
(
	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]');

增加SpringBoot配置类引入分页插件组件

@Configuration
public class MyBatisConfig {

    @Bean
    public MybatisPlusInterceptor paginationInterceptor(){
        //新建MybatisPlus拦截器
        MybatisPlusInterceptor mybatisPlusInterceptor = new MybatisPlusInterceptor();
        //新建分页拦截器paginationInnerInterceptor
        PaginationInnerInterceptor paginationInnerInterceptor = new PaginationInnerInterceptor();
        //设置分页拦截器的一些属性
        paginationInnerInterceptor.setOverflow(true);
        paginationInnerInterceptor.setMaxLimit(100L);
        //把分页拦截器添加到MybatisPlus拦截器中
        mybatisPlusInterceptor.addInnerInterceptor(paginationInnerInterceptor);
        //添加组件,大功告成!
        return mybatisPlusInterceptor;
    }
}
  • 这一步的主要目标是往Spring容器中mybatisPlus的分页插件拦截器

UserMapper接口

@Mapper
@Repository
public interface UserMapper extends BaseMapper<User> {

}
  • 实体类Mapper需要继承MybatisPlus的BaseMapper类,其中的范性为该目标实体User。该写法为MyBatisPlus的标准写法,继承BaseMapper后,可以给予CRUD功能

Service层

  • UserService接口:

    public interface UserService extends IService<User> {
    }
    
    • 直接实现MyBatisPlus中的顶级接口IService,其中的范型为目标实体
  • UserServiceImplUserService的真正实现类

    @Service
    public class UserServiceImpl extends ServiceImpl<UserMapper, User> implements UserService {
    }
    
    • 首先,肯定要实现其对应的接口:implements Userservice

    • 其次需要继承ServiceImpl,该类为mybatisPlus中的IService实现类,需要指定两个范性 。显而易见,第一个范性为User对应的Mybatis需要指定的的Mapper类,第二个范性为目标实体类User

Controller层

@Controller
public class TableController {		
    //自动注入userService
    @Autowired
    UserService userService;
  
    @GetMapping("/table")
    public String tableController(@RequestParam(value = "pn",defaultValue = "1") Integer pn, Model model){			
        //新建分页构造函数Page T为目标实体类
        Page<User> userPage = new Page<User>(pn, 2);
        //result为分页查询结果
        Page<User> result = userService.page(userPage);
        model.addAttribute("result",result);
        return "table";
    }
}

Controller层相对复杂,主要是以下几个方面:

  • 控制器参数部分 @RequestParam(value = "pn",defaultValue = "1") Integer pn :前端传入一个需要跳转到的页面值pn,默认为第一页

  • Page userPage = new Page(pn, 2):new一个分页构造函数类Page的实体userPage

    这个Page对象是所有分页功能最重要的一个类,强烈建议看看源码!!分页查询的结果与分页信息会全部包装在这个类中返回!!!

    其构造函数源代码如下:

    /**
     * 分页构造函数
     *
     * @param current 当前页
     * @param size    每页显示条数
     */
    public Page(long current, long size) {
        this(current, size, 0);
    }
    

    即:传入你想指定的当前页值,和每页显示条数(好像是废话。。。)

  • Page result = userService.page(userPage);:调用userService里面的page()方法,传入我们实例化好的userPage

    问题在这里userService没有定义任何方法,为什么会出现page()这个方法呢?

    这其实是userServiceImpl所继承的ServiceImpl提供的方法

    而这里的Page类型的result返回值,里面会包括所有我们查询到的结果以及分页信息!!

  • model.addAttribute("result",result);没什么好说的,把这个result直接丢进Model,返回到前端处理

前端页面

前端使用了thymeleaf模版引擎,具体引入请参照官方文档

https://www.thymeleaf.org/

样式截取关键代码

首先是表单区域:

<tbody>
  <tr class="gradeX" th:each="user,stat:${result.records}">
    <td th:text="${stat.count}">td>
    <td th:text="${user.id}">td>
    <td th:text="${user.name}">td>
    <td th:text="${user.age}">td>
    <td th:text="${user.email}">td>
  tr>
tbody>
  • th:each="user,stat:${result.records}":这里的result为之前controller放进model的Page result对象,我们可以通过result.records获得我们查询返回的结果,并且命名每一个结果为user进行循环输出,其中stat为每个user的状态(提供自thymeleaf模版),可以得到许多额外信息

显示分页信息区域

<div class="row-fluid">
  <div class="span6">
    <div class="dataTables_info" id="dynamic-table_info">
      当前第 [[${result.current}]]
      总计 [[${result.pages}]] 页
      共[[${result.total}]] 条记录div>
  div>
div>
  • 该区域动态显示其数据页面信息,如前文所解释,resultPage对象,里面包含了所有分页相关的信息,我们可以调用其属性动态显示当前页码,页码总数,记录总数等信息!!
  • [[${}]]该写法为thyemleaf取值的行内写法,具体请见相关文档

页码按钮栏区域

<ul>
  <li th:class="${result.current == 1}? 'prev disabled':'prve'" class="prev disabled">
    <a th:href="@{/table(pn=${result.current}-1)}">← Previousa>li>
  <li th:class="${num == result.current} ?'active':''"
      th:each="num:${#numbers.sequence(1,result.pages)}">
    <a th:href="@{/table(pn=${num})}">[[${num}]]a>
  li>
  <li class="next" th:class="${result.current == result.pages?'disabled next':'next'}">
    <a th:href="@{/table(pn=${result.current}+1)}">Next → a>li>
ul>

该区域看似比较复杂,实则结构十分简单,简化如下:

<ul>
  <li><a href="#">← Previousa>li>
  <li><a href="#">动态生成的页面数a>li>
  <li><a href="#">Next →a>li>
ul>

其中,Previous按钮与Next按钮的实现大同小异,以Previous按钮举例:

<li th:class="${result.current == 1}? 'prev disabled':'prve'" class="prev disabled">
  <a th:href="@{/table(pn=${result.current}-1)}">← Previousa>li>

动态生成页数区域:

<li th:class="${num == result.current} ?'active':''"
    th:each="num:${#numbers.sequence(1,result.pages)}">
  <a th:href="@{/table(pn=${num})}">[[${num}]]a>
li>

至此大功告成!

你可能感兴趣的:(java,html,mybatis,spring,boot,mysql)