quarkus依赖注入之十二:禁用类级别拦截器

2023年 7月 16日 15.5k 0

欢迎访问我的GitHub

这里分类和汇总了欣宸的全部原创(含配套源码):github.com/zq2599/blog…

本篇概览

  • 本篇是《quarkus依赖注入》系列的第十二篇,继续学习拦截器的另一个高级特性:禁用类级别拦截器
  • 本篇由以下内容构成
  • 编码验证类拦截器和方法拦截器的叠加效果
  • 用注解NoClassInterceptors使类拦截器失效
    • 总的来说,本篇内容非常简单,就是说清楚NoClassInterceptors注解用在哪里,怎么用,可以轻松愉快的阅读

    类拦截器和方法拦截器的叠加效果

    • 接下来进行编码,看看作用在类上和方法上的两个拦截器的叠加效果,要新建的文件清单如下
  • TrackClass.java:定义类级别的拦截器
  • TrackClassInterceptor.java:拦截器TrackClass的功能实现
  • TrackMethod.java:方法级别的拦截器
  • TrackMethodInterceptor.java:拦截器TrackMethod的功能实现
  • ExcludeInterceptorDemo.java:普通的bean,用TrackClass修饰其类,用TrackMethod修饰其test1方法
  • ExcludeInterceptorTest.java:单元测试类,运行ExcludeInterceptorDemo的方法,观察拦截效果
    • 以下是每个文件的详细内容
  • 第一个拦截器TrackClass,用来修饰类,对类的每个方法都有拦截效果
  • @InterceptorBinding
    @Target({ElementType.TYPE, ElementType.METHOD})
    @Retention(RetentionPolicy.RUNTIME)
    public @interface TrackClass {
    }
    
  • TrackClass的拦截功能实现类TrackClassInterceptor
  • @TrackClass
    @Interceptor
    public class TrackClassInterceptor {
    
        @AroundInvoke
        Object execute(InvocationContext context) throws Exception {
            Log.info("from TrackClass");
            return context.proceed();
        }
    }
    
  • 第二个拦截器TrackMethod,用来修饰方法,只对被修饰的方法有拦截效果
  • @InterceptorBinding
    @Target({ElementType.TYPE, ElementType.METHOD})
    @Retention(RetentionPolicy.RUNTIME)
    public @interface TrackMethod {
    }
    
  • TrackMethod的拦截功能实现类TrackMethodInterceptor
  • @TrackMethod
    @Interceptor
    public class TrackMethodInterceptor {
    
        @AroundInvoke
        Object execute(InvocationContext context) throws Exception {
            Log.info("from TrackMethod");
            return context.proceed();
        }
    }
    
  • 为了演示拦截器的效果,创建一个bean,如下所示,TrackClass修饰在类上面,所以test0和test1方法都会被TrackClassInterceptor拦截,另外,test1方法还会被TrackMethodInterceptor,也就是说两个拦截器都会拦截test1方法
  • @ApplicationScoped
    @TrackClass
    public class ExcludeInterceptorDemo {
    
        public void test0() {
            Log.info("from test0");
        }
    
        @TrackMethod
        public void test1() {
            Log.info("from test1");
        }
    }
    
  • 用单元测试类验证效果
  • @QuarkusTest
    public class ExcludeInterceptorTest {
       
        @Inject
        ExcludeInterceptorDemo excludeInterceptorDemo;
    
        @Test
        public void test() {
            excludeInterceptorDemo.test0();
            Log.info("*****************************");
            excludeInterceptorDemo.test1();
        }
    }
    
    • 运行效果如下,可见test0被类拦截器拦截,而test1先后被类拦截器和方法拦截器拦截

    image-20220502180545876

    • 当然了,以上一切都是符合预期的,并没有什么问题

    用注解NoClassInterceptors使类拦截器失效

    • 假设遇到了某些冲突(例如和数据库、IO相关等),导致TrackClassInterceptor和TrackMethodInterceptor两个拦截器不能同时对test1方法进行拦截,只能保留TrackMethodInterceptor
    • 此时,可以用注解NoClassInterceptors修饰test1方法,如下图红框所示,这样类拦截器TrackClassInterceptor就会失效,只剩下TrackMethodInterceptor可以正常工作

    image-20220502192040472

    • 再次执行单元测试,效果如下图,可见类拦截器TrackClassInterceptor不再拦截被NoClassInterceptors修饰的test1方法

    image-20220502192714034

    NoClassInterceptors的影响范围

    • 回顾类拦截器TrackClassInterceptor,如下图红框,可见其拦截方法有注解AroundInvoke修饰

    image-20220502193918403

    • 而NoClassInterceptors的作用,就是针对有注解AroundInvoke修饰的方法,使他们失效
    • 除了AroundInvoke,NoClassInterceptors还针对AroundConstruct修饰的方法,使他们失效
    • 至此,拦截器的高级特性已经全部学习和实践完成,希望能给您提供一些参考,助您设计出更完善的拦截器

    源码下载

    • 本篇实战的完整源码可在GitHub下载到,地址和链接信息如下表所示(github.com/zq2599/blog…)
    名称 链接 备注
    项目主页 github.com/zq2599/blog… 该项目在GitHub上的主页
    git仓库地址(https) github.com/zq2599/blog… 该项目源码的仓库地址,https协议
    git仓库地址(ssh) git@github.com:zq2599/blog_demos.git 该项目源码的仓库地址,ssh协议
    • 这个git项目中有多个文件夹,本次实战的源码在quarkus-tutorials文件夹下,如下图红框 image-20220312091203116
    • quarkus-tutorials是个父工程,里面有多个module,本篇实战的module是basic-di,如下图红框 image-20220312091404031

    欢迎关注掘金:程序员欣宸

    学习路上,你不孤单,欣宸原创一路相伴...

    相关文章

    JavaScript2024新功能:Object.groupBy、正则表达式v标志
    PHP trim 函数对多字节字符的使用和限制
    新函数 json_validate() 、randomizer 类扩展…20 个PHP 8.3 新特性全面解析
    使用HTMX为WordPress增效:如何在不使用复杂框架的情况下增强平台功能
    为React 19做准备:WordPress 6.6用户指南
    如何删除WordPress中的所有评论

    发布评论