Spring3 注解@ComponentScan、@Configuration、@Bean、@Scope

一、@ComponentScan注解

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
	xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
	xmlns:aop="http://www.springframework.org/schema/aop"
	xmlns:tx="http://www.springframework.org/schema/tx"
	xmlns:context="http://www.springframework.org/schema/context"
	xsi:schemaLocation="
   http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-2.5.xsd
   http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-2.5.xsd
   http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-2.5.xsd
   http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-2.5.xsd">
 
    <context:component-scan base-package=“com.mengma”/>
 
</beans>

前面在Spring2.5中了解了<context:component-scan>将遍历扫描com.mengma路径下的所有类型定义,寻找标注了相应注解的类,并添加到IoC容器。<context:component-scan>扫描注解类型是@Component以及细化的@Contoller、@Service和@Repository,而且<context:component-scan>,同时会将AutowiredAnnotationBeanPostProcessor和CommonAnnotationBeanPostProcessor一并注册到容器中,所以,@Autowired和@Resource也能满足依赖注入。 

  1. @ComponentScan("net.quickcodes.*")类似于配置文件中此行:<context:component-scan base-package=“com.mengma”/>
  2. @ComponentScan注解是什么?@ComponentScan主要就是定义扫描的路径,并从中找出标识了需要装配的类自动装配到spring的bean容器中;
  3. 做过web开发的同学一定都有用过@Controller,@Service,@Repository注解,查看其源码你会发现,他们中有一个共同的注解@Component,没错@ComponentScan注解默认就会装配标识了@Controller,@Service,@Repository,@Autowired,@Resource,@Component注解的类到spring容器中;
  4. @ComponentScan注解的参数:
  • value:扫描的路径;
  • basePackages: 与value属性一样;
  • basePackageClasses: 将指定数组中的多个class加入到spring容器中来;
  • includeFilters: 
  • excludeFilters:

   用法:   

  • 自动扫描路径下边带有@Controller,@Service,@Repository,@Component注解加入spring容器;

  • 通过includeFilters加入扫描路径下没有以上注解的类加入spring容器;

  • 通过excludeFilters过滤出不用加入spring容器的类;

  • 自定义增加了@Component注解的注解方式;

二、@Configuration注解 

       

  1. 从定义来看, @Configuration 注解本质上还是 @Component,因此 <context:component-scan/> 或者 @ComponentScan 都能处理@Configuration 注解的类。
  2. @Configuration 标记的类必须符合下面的要求:
  •           配置类必须以类的形式提供(不能是工厂方法返回的实例),允许通过生成子类在运行时增强(cglib 动态代理);
  •           配置类不能是 final 类(没法动态代理);
  •           @Configuration不可以是匿名类;
  •           配置注解通常为了通过 @Bean 注解生成 Spring 容器管理的类;
  •           配置类必须是非本地的(即不能在方法中声明,不能是 private);
  •           任何嵌套配置类都必须声明为static;
  •     @Bean 方法可能不会反过来创建进一步的配置类(也就是返回的 bean 如果带有 @Configuration,也不会被特殊处理,只会作为普通的 bean);

   3.@Configuration标注在类上,相当于把该类作为spring的xml配置文件中的<beans>,作用为:配置spring容器(应用上下文) 

package com.dxz.demo.configuration;
 
import org.springframework.context.annotation.Configuration;
 
@Configuration
public class TestConfiguration {
    public TestConfiguration() {
        System.out.println("TestConfiguration容器启动初始化。。。");
    }
}

相当于: 

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xmlns:context="http://www.springframework.org/schema/context" xmlns:jdbc="http://www.springframework.org/schema/jdbc"  
    xmlns:jee="http://www.springframework.org/schema/jee" xmlns:tx="http://www.springframework.org/schema/tx"
    xmlns:util="http://www.springframework.org/schema/util" xmlns:task="http://www.springframework.org/schema/task" xsi:schemaLocation="
        http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
        http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.0.xsd
        http://www.springframework.org/schema/jdbc http://www.springframework.org/schema/jdbc/spring-jdbc-3.0.xsd
        http://www.springframework.org/schema/jee http://www.springframework.org/schema/jee/spring-jee-3.0.xsd
        http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-3.0.xsd
        http://www.springframework.org/schema/util http://www.springframework.org/schema/util/spring-util-3.0.xsd
        http://www.springframework.org/schema/task http://www.springframework.org/schema/task/spring-task-3.0.xsd" default-lazy-init="false">
 
 
</beans>

一般来讲,在配置类中,@Configuration和@Bean同时使用; 

           

另外:

(1)在@configuration中引入扫描路径下的@ComponentScan 

 

(2)在@configuration中引入spring的xml配置文件 

    

 (3)在@configuration中引入spring的properties配置文件

     

(4)在@configuration中引入其它注解配置 

       

(5)@configuration嵌套(嵌套的Configuration必须是静态类)

       通过配置类嵌套的配置类,达到组合多个配置类的目的。但注意内部类必须是静态类。

        

三、@Bean注解 

   以前使用XML配置的方式,bean是这样的: 

<bean id="person" class="com.mengma.assembly.Person" />

而基于JavaConfig的配置形式是这样的: 

@Configuration
public class Appconfig{
    @Bean
    public Person person(){
        return new Person();
    }
}

在xml中,bean与bean的依赖关系,这样配置: 

<!--DAO配置-->
	<bean id="userDAO" class="com.hisu.daoImpl.UserDAOImpl" scope="singleton">
		...
	</bean>
	<!--service配置-->
	<bean id="userService" class="com.hisu.serviceImpl.UserServiceImpl">
		<property name="userDAO">
			<ref bean="userDAO"/>
		</property>
	</bean>

现在,基于JavaConfig的配置形式是这样的: 

@Configuration
public class Appconfig{
    @Bean
    public UserDAO userDAO(){
        return new UserDAO();
    }

    @Bean
    public UserService userService(){
        return new UserService(userDAO());
    }
}

说明:相信大多数人第一次看到上面 mockService() 中调用 dependencyService() 时,会认为这里的 DependencyService 和上面 @Bean 方法返回的 DependencyService 可能不是同一个对象,因此可能会通过下面的方式来替代这种方式: 

@Autowired
private DependencyService  dependencyService;

实际上不需要这么做,直接调用 dependencyService() 方法返回的是同一个实例。

  1. 使用范围:@Bean是一个方法级别上的注解(返回某个实例的方法),等价于spring的xml配置文件中的<bean>,作用为:注册bean对象,主要用在@Configuration注解的类里,也可以用在@Component注解的类里。
  2. @Bean不带参数:添加的bean的id为方法名,类型为方法返回值类型;
  3. @Bean(name=“testBean”)带上参数:添加的bean的id为testBean,类型为方法返回值类型;
  4. @Bean注解默认作用域为单例singleton作用域,可通过@Scope(“prototype”)设置为原型作用域; 
  5. 如果一个bean的定义依赖其他bean,则直接调用对应的JavaConfig类中依赖bean的创建方法就可以了。

四、@Scope:@Bean的属性支持

@Scope 设置Spring容器如何新建Bean实例(方法上,得有@Bean) 
其设置类型包括:

Singleton (单例,一个Spring容器中只有一个bean实例,默认模式), 
Protetype (每次调用新建一个bean)

发布了203 篇原创文章 · 获赞 6 · 访问量 4494

猜你喜欢

转载自blog.csdn.net/weixin_42073629/article/details/105400517