2. MyBatis 插件
MyBatis 允许你在已映射语句执行过程中的某一点进行拦截调用。默认情况下,MyBatis 允许使用插件来拦截的方法调用包括:
- Executor (update, query, flushStatements, commit, rollback, getTransaction, close, isClosed)
- ParameterHandler (getParameterObject, setParameters)
- ResultSetHandler (handleResultSets, handleOutputParameters)
- StatementHandler (prepare, parameterize, batch, update, query)
这些类中方法的细节可以通过查看每个方法的签名来发现,或者直接查看 MyBatis 的发行包中的源代码。 假设你想做的不仅仅是监控方法的调用,那么你应该很好的了解正在重写的方法的行为。 因为如果在试图修改或重写已有方法的行为的时候,你很可能在破坏 MyBatis 的核心模块。 这些都是更低层的类和方法,所以使用插件的时候要特别当心。
测试
1.编写 Interceptor 实现类
2.使用 @Intercepts 注解完成插件签名
@Intercepts({
@Signature(type = StatementHandler.class,
method = "parameterize",
args = java.sql.Statement.class)})
public class MyFirstPlugin implements Interceptor{
/**
* intercept 拦截目标对象的目标方法的执行
*/
@Override
public Object intercept(Invocation invocation) throws Throwable {
System.out.println("MyFirstPlugin...intercept:"+invocation.getMethod());
return invocation.proceed();
}
/**
* 包装目标对象:为目标对象创建一个代理对象
*/
@Override
public Object plugin(Object target) {
System.out.println("MyFirstPlugin...plugin:包装对象 "+target);
//借助 Plugin 的 wrap 方法来使用 Interceptor 包装目标对象
return Plugin.wrap(target,this);
}
/**
* 将插件注册时的 property 属性设置进来
*/
@Override
public void setProperties(Properties properties) {
System.out.println(properties);
}
}
3.将该插件注册到全局配置文件中
<plugins>
<plugin interceptor="com.chen.dao.MyFirstInterceptor">
<property name="data" value="123"/>
</plugin>
</plugins>
mybatis 创建动态代理时候,是按照插件配置顺序创建层层代理对象;而执行目标方法后,是按照逆向顺序执行。
PageHelper 插件
官方文档:https://github.com/pagehelper/Mybatis-PageHelper/blob/master/wikis/zh/HowToUse.md
通过 maven 引入该插件
<dependency>
<groupId>com.github.pagehelper</groupId>
<artifactId>pagehelper</artifactId>
<version>最新版本</version>
</dependency>
配置拦截器插件
特别注意,新版拦截器是 com.github.pagehelper.PageInterceptor
。 com.github.pagehelper.PageHelper
现在是一个特殊的 dialect
实现类,是分页插件的默认实现类,提供了和以前相同的用法。
1.在 MyBatis 配置文件中配置拦截器插件
<plugins>
<!-- com.github.pagehelper为PageHelper类所在包名 -->
<plugin interceptor="com.github.pagehelper.PageInterceptor"/>
</plugins>
2.在 Spring 配置文件中配置拦截器插件
<bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">
<!-- 注意其他配置 -->
<property name="plugins">
<array>
<bean class="com.github.pagehelper.PageInterceptor">
<property name="properties">
<!--使用下面的方式配置参数,一行配置一个 -->
<value>
params=value1
</value>
</property>
</bean>
</array>
</property>
</bean>
测试
@Test
public void testPageHelper() throws IOException {
SqlSession sqlSession = getSqlSessionFactory().openSession(true);
try {
UserCrudMapper mapper = sqlSession.getMapper(UserCrudMapper.class);
/*Page<Object> page = PageHelper.startPage(2, 3);
List<User> users = mapper.getAllUsers();
System.out.println("当前页码:"+page.getPageNum());
System.out.println("总记录数:"+page.getTotal());
System.out.println("总页码:"+page.getPages());
System.out.println("每页的记录数:"+page.getPageSize());*/
Page<Object> page = PageHelper.startPage(2, 3);
List<User> users = mapper.getAllUsers();
//传入要连续显示多少页
PageInfo<User> info = new PageInfo<>(users,3);
System.out.println("当前页码:" + info.getPageNum());
System.out.println("总记录数:" + info.getTotal());
System.out.println("总页码:" + info.getPages());
System.out.println("每页的记录数:" + info.getPageSize());
System.out.println("是否为第一页:" + info.isIsFirstPage());
System.out.println(""+info.getNavigatepageNums().length);
} finally {
sqlSession.close();
}
}