mybatis-插件开发

  在Executor、StatementHandler、parameterHandler、resultSetHandler创建的时候都有一步这样的操作xxxHandler=interceptorChain.pluginAll(xxxHandler);而这个方法会获取到所有的Interceptor(拦截器),调用interceptor.plugin(target),返回target包装后的对象

 

插件实现

编写Interceptor的实现类,使用@Intercepts拦截对象的方法

复制代码
@Intercepts(
        {
            @Signature(type=StatementHandler.class,method="parameterize",args=java.sql.Statement.class)
        })
public class MyFirstPlugin implements Interceptor{

    /**
     *  拦截目标对象的目标方法的执行
     */
    @Override
    public Object intercept(Invocation invocation) throws Throwable {
        System.out.println("MyFirstPlugin...intercept:"+invocation.getMethod());
        Object target = invocation.getTarget();
        System.out.println("当前拦截到的对象:"+target);//拿到target的元数据
        MetaObject metaObject = SystemMetaObject.forObject(target);
        Object value = metaObject.getValue("parameterHandler.parameterObject");
        System.out.println("sql语句用的参数是:"+value);
        //修改完sql语句要用的参数
        metaObject.setValue("parameterHandler.parameterObject", 11);
        //执行目标方法
        Object proceed = invocation.proceed();
        //返回执行后的返回值
        return proceed;
    }

    /**
     *  包装目标对象:为目标对象创建一个代理对象
     */
    @Override
    public Object plugin(Object target) {
        // TODO Auto-generated method stub
        //我们可以借助Plugin的wrap方法来使用当前Interceptor包装我们目标对象
        System.out.println("MyFirstPlugin...plugin:mybatis将要包装的对象"+target);
        Object wrap = Plugin.wrap(target, this);
        //返回为当前target创建的动态代理
        return wrap;
    }

    /**
     *  将插件注册时 的property属性设置进来
     */
    @Override
    public void setProperties(Properties properties) {
        // TODO Auto-generated method stub
        System.out.println("插件配置的信息:"+properties);
    }
复制代码

 

将写好的插件注册到全局配置文件中

复制代码
<!--plugins:注册插件  -->
    <plugins>
        <plugin interceptor="com.mybatis.dao.MyFirstPlugin">
            <property name="username" value="root"/>
            <property name="password" value="123456"/>
        </plugin>
        <plugin interceptor="com.mybatis.dao.MySecondPlugin"></plugin>
    </plugins>
复制代码

 

多个插件对同一对象的包装

复制代码
@Intercepts(
        {
            @Signature(type=StatementHandler.class,method="parameterize",args=java.sql.Statement.class)
        })
public class MySecondPlugin implements Interceptor{

    @Override
    public Object intercept(Invocation invocation) throws Throwable {
        System.out.println("MySecondPlugin...intercept:"+invocation.getMethod());
        return invocation.proceed();
    }

    @Override
    public Object plugin(Object target) {
        // TODO Auto-generated method stub
        System.out.println("MySecondPlugin...plugin:"+target);
        return Plugin.wrap(target, this);
    }

    @Override
    public void setProperties(Properties properties) {
        // TODO Auto-generated method stub
    }
复制代码

 

 总结

  我们可以使用插件为目标对象创建一个代理对象,根据@Signature定义的规则拦截方法的每一个执行。

posted @   edda_huang  阅读(102)  评论(0编辑  收藏  举报
编辑推荐:
· 记一次.NET内存居高不下排查解决与启示
· 探究高空视频全景AR技术的实现原理
· 理解Rust引用及其生命周期标识(上)
· 浏览器原生「磁吸」效果!Anchor Positioning 锚点定位神器解析
· 没有源码,如何修改代码逻辑?
阅读排行:
· 全程不用写代码,我用AI程序员写了一个飞机大战
· MongoDB 8.0这个新功能碉堡了,比商业数据库还牛
· 记一次.NET内存居高不下排查解决与启示
· DeepSeek 开源周回顾「GitHub 热点速览」
· 白话解读 Dapr 1.15:你的「微服务管家」又秀新绝活了
点击右上角即可分享
微信分享提示

目录导航