我正在学习Spring 3,我似乎没有掌握<context:annotation-config>和<context:component-scan>背后的功能。

从我读到的内容来看,它们似乎处理不同的注释(@Required, @Autowired等vs @Component, @Repository, @Service等),但从我读到的内容来看,它们注册了相同的bean后处理器类。

更让我困惑的是,在<context:component-scan>上有一个annotation-config属性。

有人能解释一下这些标签吗?什么是相似的,什么是不同的,是一个被另一个取代,它们互相完善,我需要其中一个吗,还是两个?


当前回答

作为补充,您可以使用@ComponentScan以注释的方式使用<context:component-scan>。

在spring.io中也有描述

配置使用with的组件扫描指令 @ configuration类。提供与Spring XML并行的支持 元素。

需要注意的一点是,如果您正在使用SpringBoot, @Configuration和@ComponentScan可以通过使用@SpringBootApplication注释来暗示。

其他回答

<context:component-scan /> implicitly enables <context:annotation-config/>

try with <context:component-scan base-package="…" annotation-config="false"/>,在你的配置中@Service, @Repository, @Component工作正常,但是@Autowired,@Resource和@Inject不工作。

这意味着AutowiredAnnotationBeanPostProcessor将不会被启用,Spring容器将不会处理自动装配注释。

<context:component-scan/>自定义标记除了主要负责扫描java包和从类路径注册bean定义外,还注册了与by所做的相同的bean定义集。

如果出于某种原因要避免这种默认bean定义的注册,方法是在component-scan中指定一个额外的“annotation-config”属性,如下所示:

<context:component-scan basePackages="" annotation-config="false"/>

参考: http://www.java-allandsundry.com/2012/12/contextcomponent-scan-contextannotation.html

<context:component-scan base-package="package name" />:

这用于告诉容器在我的包中有bean类,扫描这些bean类。为了在bean的顶部通过容器扫描bean类,我们必须像下面这样编写一个立体类型注释。

@组件,@服务,@存储库,@控制器

<上下文:annotation-config / >:

如果我们不想显式地用XML写bean标签,那么容器如何知道bean中是否有自动连接。这可以通过使用@Autowired注释实现。我们必须通过上下文:annotation-config通知容器,在我的bean中有自动连接。

<context:annotation-config>

只解决@Autowired和@Qualifer注释,这就是所有的,它关于依赖注入,还有其他注释做同样的工作,我认为如何@Inject,但都是关于通过注释解决DI。

注意,即使声明了<context:annotation-config>元素,也必须声明类是Bean,记住我们有三个可用选项

XML: <憨豆先生> @注解:@组件,@服务,@存储库,@控制器 JavaConfig: @Configuration, @Bean

现在有了

<context:component-scan>

它做了两件事:

它扫描带有注释的所有类 @组件、@服务、@存储库、@控制器和@配置并创建一个Bean 它与<context:annotation-config>所做的工作相同。

因此,如果你声明<context:component-scan>,就没有必要再声明<context:annotation-config>了。

Thats所有

例如,一个常见的场景是仅通过XML声明bean,并通过注释解析DI

<bean id="serviceBeanA" class="com.something.CarServiceImpl" />
<bean id="serviceBeanB" class="com.something.PersonServiceImpl" />
<bean id="repositoryBeanA" class="com.something.CarRepository" />
<bean id="repositoryBeanB" class="com.something.PersonRepository" />

我们只声明了bean,没有关于<constructor-arg>和<property>, DI是通过@Autowired在它们自己的类中配置的。这意味着服务对它们的存储库组件使用@Autowired,而存储库对JdbcTemplate、DataSource等组件使用@Autowired

<context:annotation-config>标记告诉Spring扫描代码库,以自动解决包含@Autowired注释的类的依赖关系需求。

Spring 2.5还增加了对JSR-250注释的支持,比如@Resource、@PostConstruct和@PreDestroy。使用这些注释还要求在Spring容器中注册某些beanpostprocessor。与往常一样,这些可以注册为单独的bean定义,但也可以通过在spring配置中包含<context:annotation-config>标记来隐式注册。

摘自Spring文档中的基于注释的配置


Spring提供了自动检测“定型”类的功能,并在ApplicationContext中注册相应的BeanDefinitions。

根据org.springframework.stereotype的javadoc:

原型是表示类型或方法在整个体系结构中的角色的注释(在概念级别,而不是实现级别)。 例如:@控制器@服务@存储库等。 它们是供工具和方面使用的(成为切入点的理想目标)。

要自动检测这样的“原型”类,需要<context:component-scan>标记。

<context:component-scan>标记还告诉Spring在指定的包(及其所有子包)下扫描可注入bean的代码。