向Spring容器中註冊組件的方法彙總小結

一、經過xml定義
<bean class="">
    <property name="" value=""></property>
</bean>
二、經過註解

這種方式比較常見,一般用@Controller、@Component、@Service等等java

三、經過@Bean註解

好比下面的代碼往容器中註冊一個Person對象app

@Bean
public Person person(){
    return new Person("張三", 20);
}

默認狀況下,使用方法【person()】名person做爲Person對象的註冊id
也能夠經過修改方法名或者使用@Bean(「customBeanName」)ide

四、經過實現FactoryBean 接口
public interface FactoryBean<T> {
    T getObject() throws Exception;
    Class<?> getObjectType();
    boolean isSingleton();
}

// Sample
public class PersonFactoryBean implements FactoryBean<Person> {
    ....
}

實現上述接口的3個方法,並把PersonFactoryBean註冊到容器中,就能夠把Person也註冊到容器中。
具體建立Person過程的源碼能夠看FactoryBeanRegistrySupport#getObjectFromFactoryBean方法。code

// 以下代碼拿到的是Person對象
applicationContext.getBean("personFactoryBean")

// 若是想要拿到PersonFactoryBean對象,能夠再前面加&
applicationContext.getBean("&personFactoryBean")
五、經過@Import註解

先來看看源碼:component

@Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface Import {
    /**
    * {@link Configuration}, {@link ImportSelector}, {@link ImportBeanDefinitionRegistrar}
    * or regular component classes to import.
    */
    Class<?>[] value();
}

源碼註釋寫的也很清楚,能夠引入 配置類、ImportSelector、ImportBeanDefinitionRegistrar,甚至是普通class。 經過@Import,咱們可使用以下方式註冊組件:xml

@Import({Person.class, MyImportSelector.class,MyImportBeanDefinitionRegistrar.class})

其中:對象

  • MyImportSelector實現了ImportSelector接口,selectImports方法返回類全名的String[]都會被註冊到容器中接口

  • MyImportBeanDefinitionRegistrar實現了ImportBeanDefinitionRegistrar接口get

    // Sample
    public class MyImportBeanDefinitionRegistrar implements ImportBeanDefinitionRegistrar {
    @Override
    public void registerBeanDefinitions(AnnotationMetadata importingClassMetadata, BeanDefinitionRegistry registry) {
        // 指定Bean定義信息
        RootBeanDefinition beanDefinition = new RootBeanDefinition(Person.class);
        // 註冊一個Bean,指定bean名
        registry.registerBeanDefinition("person", beanDefinition);
      }
    }

這是一個很是重要的註解,在Spring源碼中,哪哪都能看到他的身影。源碼

  • 如 @EnableAspectJAutoProxy註解

    @Target(ElementType.TYPE)
    @Retention(RetentionPolicy.RUNTIME)
    @Documented
    @Import(AspectJAutoProxyRegistrar.class)
    public @interface EnableAspectJAutoProxy {
        ...
    }

    EnableAspectJAutoProxy經過@Import引入了AspectJAutoProxyRegistrar類[實現了 ImportBeanDefinitionRegistrar],這個Registrar裏面又會向Spring容器中註冊AnnotationAwareAspectJAutoProxyCreator(Spring aop註解實現的功臣)。

  • 如 @EnableWebMvc註解。經過Import引入的是一個配置類

    @Retention(RetentionPolicy.RUNTIME)
    @Target(ElementType.TYPE)
    @Documented
    @Import(DelegatingWebMvcConfiguration.class)
    public @interface EnableWebMvc {
    }
  • 如 @EnableAsync註解。經過Import引入的是AsyncConfigurationSelector[實現了ImportSelector接口]

    @Target(ElementType.TYPE)
    @Retention(RetentionPolicy.RUNTIME)
    @Documented
    @Import(AsyncConfigurationSelector.class)
    public @interface EnableAsync {
        ...
    }
相關文章
相關標籤/搜索