关于SpingMVC的<context:component-scan>包扫描踩坑记录

 更新时间:2022年03月21日 10:43:16   作者:zeng1994  
这篇文章主要介绍了关于SpingMVC的<context:component-scan>包扫描踩坑记录,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教

<context:component-scan>包扫描的坑

公司项目配置的Spring项目的包扫描有点问题,出现了一个被Spring容器管理的Bean被创建了2次的现象。在此记录下解决的过程,方便后续查阅。

改动前

容器启动监听器中会扫描全部包,创建实例 

SpringMVC配置文件也会扫描全部包,创建实例

产生的问题:加了注解的类的实例都创建了2个

改动后

容器启动监听器里面负责非Controller层bean的创建

SpingMVC配置文件里只负责Controller层bean的创建

<context:component-scan>的使用说明

在xml配置了这个标签后,spring可以自动去扫描base-package下面或者子包下面的java文件,如果扫描到有@Component @Controller@Service等这些注解的类,则把这些类注册为bean

注意:如果配置了<context:component-scan>那么<context:annotation-config/>标签就可以不用再xml中配置了,因为前者包含了后者。

<context:annotation-config/>提供了两个子标签

<context:include-filter>
<context:exclude-filter>

再说明这两个子标签前,先说一下<context:component-scan>有一个use-default-filters属性,改属性默认为true,这就意味着会扫描指定包下的全部的标有@Component的类,并注册成bean.也就是@Component的子注解@Service,@Reposity等。所以如果仅仅是在配置文件中这么写

<context:component-scan base-package="tv.huan.weisp.web"/>

use-default-filter此时为true那么会对base-package包或者子包下的所有的进行java类进行扫描,并把匹配的java类注册成bean。

可以发现这种扫描的粒度有点太大,如果你只想扫描指定包下面的Controller,该怎么办?此时子标签context:incluce-filter就起到了用武之地。

如下所示

<context:component-scan base-package="tv.huan.weisp.web .controller">  
<context:include-filter type="annotation" expression="org.springframework.stereotype.Controller"/>   
</context:component-scan>  

这样就会只扫描base-package指定下的有@Controller下的java类,并注册成bean

但是因为use-dafault-filter在上面并没有指定,默认就为true,所以当把上面的配置改成如下所示的时候,就会产生与你期望相悖的结果(注意base-package包值得变化)

<context:component-scan base-package="tv.huan.weisp.web ">  
<context:include-filter type="annotation" expression="org.springframework.stereotype.Controller"/>   
</context:component-scan>  

此时,spring不仅扫描了@Controller,还扫描了指定包所在的子包service包下注解@Service的java类

此时指定的include-filter没有起到作用,只要把use-default-filter设置成false就可以了。这样就可以避免在base-packeage配置多个包名这种不是很优雅的方法来解决这个问题了。

另外在我参与的项目中可以发现在base-package指定的包中有的子包是不含有注解了,所以不用扫描,此时可以指定<context:exclude-filter>来进行过滤,说明此包不需要被扫描。综合以上说明

use-dafault-filters=”false”的情况下:

<context:exclude-filter>指定的不扫描,<context:include-filter>指定的扫描

定位问题原因* 根据原因思考问题解决方案* 实践验证方案有效性* 提交验证结果

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

相关文章

  • java利用JEXL实现动态表达式编译

    java利用JEXL实现动态表达式编译

    这篇文章主要介绍了java利用JEXL实现动态表达式编译,系统要获取多个数据源的数据,并进行处理,最后输出多个字段。字段的计算规则一般是简单的取值最多加一点条件判断,下面是具体的实现方法
    2021-04-04
  • Java中的动态代理使用

    Java中的动态代理使用

    这篇文章主要介绍了Java中的动态代理使用方式,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教
    2024-07-07
  • string boot 与 自定义interceptor的实例讲解

    string boot 与 自定义interceptor的实例讲解

    下面小编就为大家分享一篇string boot 与 自定义interceptor的实例讲解,具有很好的参考价值,希望对大家有所帮助。一起跟随小编过来看看吧
    2017-12-12
  • 关于junit测试需要的依赖

    关于junit测试需要的依赖

    这篇文章主要介绍了关于junit测试需要的依赖,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教
    2022-12-12
  • Gson中的TypeToken与泛型擦除详情

    Gson中的TypeToken与泛型擦除详情

    这篇文章主要介绍了Gson中的TypeToken与泛型擦除详情,其Gson类提供了toJson()与fromJson()方法,分别用来序列化与反序列化,更多相关内容需要的朋友可以参考一下
    2022-09-09
  • 自主配置数据源,mybatis/plus不打印sql日志问题

    自主配置数据源,mybatis/plus不打印sql日志问题

    这篇文章主要介绍了自主配置数据源,mybatis/plus不打印sql日志问题,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教
    2023-12-12
  • 浅谈JVM 底层解析 i++和 ++i 区别

    浅谈JVM 底层解析 i++和 ++i 区别

    这篇文章主要介绍了JVM 底层解析 i++和 ++i 区别,需要的朋友可以参考下面文章的具体内容
    2021-09-09
  • Spring Boot发送邮件详解

    Spring Boot发送邮件详解

    这篇文章主要为大家详细介绍了Spring Boot发送邮件的相关资料,文中示例代码介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2017-11-11
  • 基于jenkins实现发布node.js项目

    基于jenkins实现发布node.js项目

    这篇文章主要介绍了基于jenkins实现发布node.js项目,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下
    2020-07-07
  • Java多线程之彻底搞懂线程池

    Java多线程之彻底搞懂线程池

    熟悉 Java 多线程编程的同学都知道,当我们线程创建过多时,容易引发内存溢出,因此我们就有必要使用线程池的技术了。想要详细了解的同学可以参考阅读本文
    2023-03-03

最新评论