MyBatis如何使用PageHelper实现分页查询

使用PageHelper实现分页查询

【实例】MyBatis使用PageHelper实现分页查询,并显示分页信息。执行效果如下图:

1、创建数据表

在MySQL数据库中创建用户信息表(tb_user),并添加数据。

-- 判断数据表是否存在,存在则删除

DROP TABLE IF EXISTS tb_user;

-- 创建“用户信息”数据表

CREATE TABLE IF NOT EXISTS tb_user

(

user_id INT AUTO_INCREMENT PRIMARY KEY COMMENT '用户编号',

user_name VARCHAR(50) NOT NULL COMMENT '用户姓名',

province VARCHAR(50) NOT NULL COMMENT '省份',

create_time TIMESTAMP DEFAULT CURRENT_TIMESTAMP COMMENT '注册时间'

) COMMENT = '用户信息表';

-- 添加数据

INSERT INTO tb_user(user_name,province) VALUES

('pan_junbiao的博客_01','广东省'),('pan_junbiao的博客_02','黑龙江省'),('pan_junbiao的博客_03','山东省'),('pan_junbiao的博客_04','安徽省'),('pan_junbiao的博客_05','黑龙江省'),

('pan_junbiao的博客_06','江苏省'),('pan_junbiao的博客_07','黑龙江省'),('pan_junbiao的博客_08','广东省'),('pan_junbiao的博客_09','陕西省'),('pan_junbiao的博客_10','广东省'),

('pan_junbiao的博客_11','广东省'),('pan_junbiao的博客_12','江苏省'),('pan_junbiao的博客_13','陕西省'),('pan_junbiao的博客_14','安徽省'),('pan_junbiao的博客_15','山东省'),

('pan_junbiao的博客_16','陕西省'),('pan_junbiao的博客_17','安徽省'),('pan_junbiao的博客_18','江苏省'),('pan_junbiao的博客_19','黑龙江省'),('pan_junbiao的博客_20','安徽省'),

('pan_junbiao的博客_21','江苏省'),('pan_junbiao的博客_22','广东省'),('pan_junbiao的博客_23','安徽省'),('pan_junbiao的博客_24','陕西省'),('pan_junbiao的博客_25','广东省'),

('pan_junbiao的博客_26','广东省'),('pan_junbiao的博客_27','安徽省'),('pan_junbiao的博客_28','山东省'),('pan_junbiao的博客_29','山东省'),('pan_junbiao的博客_30','黑龙江省'),

('pan_junbiao的博客_31','广东省'),('pan_junbiao的博客_32','江苏省'),('pan_junbiao的博客_33','陕西省'),('pan_junbiao的博客_34','安徽省'),('pan_junbiao的博客_35','山东省');

2、创建项目

(1)创建SpringBoot项目,项目结构如下图:

(2)添加pom.xml配置信息

在pom.xml配置文件中添加PageHelper、 MySQL的JDBC数据库驱动。

<!-- SpringBoot/MyBatis使用PageHelper分页控件 -->

<dependency>

<groupId>com.github.pagehelper</groupId>

<artifactId>pagehelper-spring-boot-starter</artifactId>

<version>1.2.13</version>

</dependency>

<!-- MySQL的JDBC数据库驱动 -->

<dependency>

<groupId>mysql</groupId>

<artifactId>mysql-connector-java</artifactId>

<version>8.0.20</version>

</dependency>

(3)配置相关信息

将默认的application.properties文件的后缀修改为“.yml”,即配置文件名称为:application.yml,并配置以下信息:

spring:

#DataSource数据源

datasource:

url: jdbc:mysql://localhost:3306/db_admin?useSSL=false&amp

username: root

password: 123456

driver-class-name: com.mysql.cj.jdbc.Driver

#MyBatis配置

mybatis:

type-aliases-package: com.pjb.entity #别名定义

configuration:

log-impl: org.apache.ibatis.logging.stdout.StdOutImpl #指定 MyBatis 所用日志的具体实现,未指定时将自动查找

map-underscore-to-camel-case: true #开启自动驼峰命名规则(camel case)映射

lazy-loading-enabled: true #开启延时加载开关

aggressive-lazy-loading: false #将积极加载改为消极加载(即按需加载),默认值就是false

lazy-load-trigger-methods: "" #阻挡不相干的操作触发,实现懒加载

cache-enabled: true #打开全局缓存开关(二级环境),默认值就是true

#MyBatis使用pageHelper分页

pagehelper:

helper-dialect: mysql

reasonable: true

support-methods-arguments: true

配置说明:

helper-dialect:配置使用哪种数据库语言,不配置的话pageHelper也会自动检测。

reasonable:在启用合理化时,如果 pageNum<1,则会查询第一页;如果 pageNum>pages,则会查询最后一页。

support-methods-arguments:支持通过Mapper接口参数来传递分页参数,默认值false,分页插件会从查询方法的参数值中,自动根据上面 params 配置的字段中取值,查找到合适的值时就会自动分页。

2.1 创建实体类(Entity层)

在com.pjb.entity包中,创建UserInfo类(用户信息实体类)。

package com.pjb.entity;

import org.springframework.stereotype.Component;

import java.util.Date;

/**

* 用户信息实体类

* @author pan_junbiao

**/

@Component

public class UserInfo

{

private int userId; //用户编号

private String userName; //用户姓名

private String province; //省份

private Date createTime; //注册时间

//省略getter与setter方法...

@Override

public String toString()

{

return "编号:" + this.getUserId() +" 姓名:" + this.getUserName() + " 省份:" + this.getProvince();

}

}

在com.pjb.entity包中,创建UserSearchParam类(用户查询条件类)。

package com.pjb.entity;

/**

* 用户查询条件类

* @author pan_junbiao

**/

public class UserSearchParam

{

private String userName; //用户姓名

private String province; //省份

//省略getter与setter方法...

}

2.2 数据库映射层(Mapper层)

在com.pjb.mapper包中,创建UserMapper接口(用户信息Mapper动态代理接口)。

package com.pjb.mapper;

import com.pjb.entity.UserInfo;

import com.pjb.entity.UserSearchParam;

import org.apache.ibatis.annotations.Mapper;

import org.apache.ibatis.annotations.SelectProvider;

import org.apache.ibatis.jdbc.SQL;

import org.springframework.stereotype.Repository;

import java.util.List;

/**

* 用户信息Mapper动态代理接口

* @author pan_junbiao

**/

@Mapper

@Repository

public interface UserMapper

{

/**

* 查询用户列表

*/

@SelectProvider(type = UserSqlBuilder.class, method = "searchUserList")

public List<UserInfo> searchUserList(UserSearchParam param);

//建议将SQL Builder以映射器接口内部类的形式进行定义

public class UserSqlBuilder

{

public String searchUserList(UserSearchParam param)

{

return new SQL()

{

{

SELECT("*");

FROM("tb_user");

WHERE("1 = 1");

if(param!=null)

{

//用户姓名

if(param.getUserName()!=null && param.getUserName().length()>0)

{

WHERE("user_name like '%${userName}%'");

}

//省份

if(param.getProvince()!=null && param.getProvince().length()>0)

{

WHERE("province = #{province}");

}

}

}

}.toString();

}

}

}

3、运行测试

【运行】查询第2页的用户数据,每页10条数据,并根据创建时间排序。

@Autowired

private UserMapper userMapper;

/**

* 分页查询用户列表

* @author pan_junbiao

*/

@Test

public void searchUserByParam()

{

int pageIndex = 2; ///获取第2页的数据

int pageSize = 10; //每页10条数据

String orderBy = "create_time ASC"; //排序

//分页信息

PageHelper.startPage(pageIndex, pageSize, orderBy);

//查询条件类

UserSearchParam userSearchParam = new UserSearchParam();

//userSearchParam.setUserName("pan_junbiao的博客"); //查询条件1

//userSearchParam.setProvince("广东省"); //查询条件2

//执行分页查询

PageInfo<UserInfo> userInfoPage = new PageInfo<UserInfo>(userMapper.searchUserList(userSearchParam));

//打印用户列表

System.out.println("\n");

List<UserInfo> userInfoList = userInfoPage.getList();

userInfoList.stream().forEach(System.out::println);

//打印分页信息

System.out.println("当前页码:第" + userInfoPage.getPageNum() + "页");

System.out.println("分页大小:每页" + userInfoPage.getPageSize() + "条");

System.out.println("数据总数:共" + userInfoPage.getTotal() + "条");

System.out.println("总页数:共" + userInfoPage.getPages() + "页");

}

PageInfo类提供的相关属性如下:

执行结果:

MyBatis PageHelper的使用

1、引入pagehelper的jar包

如果是maven项目,pom里添加依赖:

<dependency>

<groupId>com.github.pagehelper</groupId>

<artifactId>pagehelper</artifactId>

<version>4.1.4</version>

</dependency>

2、在mybatis的配置文件中配置拦截(也可以在spring配置文件中配置)

小编在mybatis配置文件SqlMapConfig.xml中配置的

<?xml version="1.0" encoding="UTF-8" ?>

<!DOCTYPE configuration

PUBLIC "-//mybatis.org//DTD Config 3.0//EN"

"http://mybatis.org/dtd/mybatis-3-config.dtd">

<configuration>

<plugins>

<plugin interceptor="com.github.pagehelper.PageHelper">

<!--设置数据可类型Oracle,Mysql,MariaDB,SQLite,Hsqldb,PostgreSQL六种数据库-->

<property name="dialect" value="mysql"/>

</plugin>

</plugins>

</configuration>

在spring中配置如下:

<!--配置SqlSessionFactory对象 -->

<bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">

<property name="dataSource" ref="dataSource" />

<property name="configLocation" value="classpath:mybatis-config.xml" />

<property name="typeAliasesPackage" value="com.aoChine.model.entity" />

<property name="mapperLocations" value="classpath:mapper/*.xml" />

<!-- 配置mybatis分页插件PageHelper -->

<property name="plugins">

<array>

<bean class="com.github.pagehelper.PageInterceptor">

<property name="properties">

<!-- 什么都不配,使用默认的配置 -->

<value></value>

</property>

</bean>

</array>

</property>

</bean>

3、代码中如何实现

Service中一个方法示例:

EasyUIDataGridResult是自己封装的一个pojo,如下:

public class EasyUIDataGridResult implements Serializable {

private long total;

private List rows;

public long getTotal() {

return total;

}

public void setTotal(long total) {

this.total = total;

}

public List getRows() {

return rows;

}

public void setRows(List rows) {

this.rows = rows;

}

}

如果不需要的话直接返回PageInfo就可以

4、注意事项 分页不安全的情况

分页不安全的情况

PageHelper 方法使用了静态的 ThreadLocal 参数,分页参数和线程是绑定的。

只要你可以保证在 PageHelper 方法调用后紧跟 MyBatis 查询方法,这就是安全的。因为 PageHelper 在 finally 代码段中自动清除了 ThreadLocal 存储的对象。

如下代码是不安全的:

PageHelper.startPage(1, 10);

List<Country> list;

if(param1 != null){

list = countryMapper.selectIf(param1);

} else {

list = new ArrayList<Country>();

}

这种情况下由于 param1 存在 null 的情况,就会导致 PageHelper 生产了一个分页参数,但是没有被消费,这个参数就会一直保留在这个线程上。当这个线程再次被使用时,就可能导致不该分页的方法去消费这个分页参数,这就产生了莫名其妙的分页。

写成如下便安全了:

List<Country> list;

if(param1 != null){

PageHelper.startPage(1, 10);

list = countryMapper.selectIf(param1);

} else {

list = new ArrayList<Country>();

}

另外也可以手动清理ThreadLocal存储的分页参数:

PageHelper.clearPage();

以上为个人经验,希望能给大家一个参考,也希望大家多多支持。

以上是 MyBatis如何使用PageHelper实现分页查询 的全部内容, 来源链接: utcz.com/p/251145.html

回到顶部