MyBatis: 插件是怎么起作用的?

示例:
假如配置了PageHelper插件

public class MyBatisTest10 {
    public static void main(String[] args) throws IOException {
        SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(
                Resources.getResourceAsStream("mybatis-config.xml"));
        
        SqlSession sqlSession = sqlSessionFactory.openSession();
        List countries = sqlSession.getMapper(PersonMapper.class).selectCountry2(1, 2);
        System.out.println(countries.size());
        System.out.println(countries);
    }
}

执行sqlSessionFactory.openSession()时,进入openSession方法,代码如下:
在这里插入图片描述
其中调用的openSessionFromDataSource,其代码如下:
MyBatis: 插件是怎么起作用的?_第1张图片
其中调用了configuration对象的newExecutor方法,该方法代码如下:
MyBatis: 插件是怎么起作用的?_第2张图片
其中调用了interceptorChain对象的pluginAll方法,interceptorChain对象中为我们定义的所有实现了Interceptor接口的类,PageInterceptor就是其中之一。pluginAll方法代码如下:
MyBatis: 插件是怎么起作用的?_第3张图片
从上图可以看到,这个方法中会遍历所有interceptor,然后调用其plugin方法,PageInterceptor的plugin方法代码如下:
MyBatis: 插件是怎么起作用的?_第4张图片
其中调用的wrap方法代码如下:
MyBatis: 插件是怎么起作用的?_第5张图片
该方法位于Plugin类,我们可以看到,它使用了JDK动态代理生成了代理对象。
可见,所有的插件最后都是通过生成动态代理对象来实现其功能的。

调用的时候,会调用Plugin类的invoke方法,其代码如下:
MyBatis: 插件是怎么起作用的?_第6张图片
可以看到,其中调用了interceptor的intercept方法,如果我们配置了PageInterceptor,则会走到PageInterceptor的intercept方法进行执行,该方法代码如下:
MyBatis: 插件是怎么起作用的?_第7张图片
MyBatis: 插件是怎么起作用的?_第8张图片

该方法真正完成了分页查询。来到pageQuery的代码
MyBatis: 插件是怎么起作用的?_第9张图片
可以看到其中调用了dialect.getPageSql方法,该方法代码如下:
MyBatis: 插件是怎么起作用的?_第10张图片
如果我们的数据库是MySQL,则最后调用getPageSql将来到MySQLDialect类:
MyBatis: 插件是怎么起作用的?_第11张图片
在这里我们可以看到了添加limit的相关内容,也就是在原有SQL基础上加了分页功能

你可能感兴趣的:(MyBatis,mybatis,java,开发语言)