Spring5.0学习之路(二)
一、@Condition条件注册bean的使用;
编写Condition测试类:
public class ConditionTest implements Condition {
/**
*
* @param conditionContext 获取当前环境的上下文
* @param annotatedTypeMetadata 获取当前注解的信息
* @return
*/
@Override
public boolean matches(ConditionContext conditionContext, AnnotatedTypeMetadata annotatedTypeMetadata) {
// 1.获取当前环境
Environment environment = conditionContext.getEnvironment();
// 2.获取当前系统名称,例如Windows 7 10 Mac linux等
String property = environment.getProperty("os.name");
if (property.equals("Windows 10")){
System.out.println("注册该bean到Windows10系统成功!");
// 可以注册该bean
return true;
}
// 不可以注册该bean
return false;
}
}
注意:ConditionContext对象,获取当前环境的上下文;
AnnotatedTypeMetadata 对象,获取当前注解的信息。
在配置类上,Car对象上加上@Condition该注解;
测试:
注:我当前笔记本系统为Windows 10。
若判断条件修改,注入失败。运行结果如下:
@Condition注解用法总结:
- 编写某类,实现Condition类,重写matches方法;
- 配置类注入bean时,加上该注解,并指明实现类;
二、@Import使用,和@Bean区别;
配置类中使用@Import注解注入Car
注意:使用该注解,获取bean时,需要加上全路径,否则会找不到该bean对象。
测试:
@Import注解使用总结:
- 使用该注解相比于@Bean注解方便,可以减少代码冗余;
- 和@Bean注解使用场景:注入第三方jar包。
三、@Enable~~~功能性注解实现原理
例:自定义一个注解:
@Target({ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Inherited
@Import(Dog.class)
public @interface EnableDog {
}
注:Dog.class是一个实体类。
注解介绍:
@Target({ElementType.TYPE})表示该注解可以使用在类、方法上;
@Retention(RetentionPolicy.RUNTIME)表示会在class字节码文件中存在,在运行时可以通过反射获取到;
@Document表示该注解将被包含在javadoc中;
@Inherited:说明子类可以继承父类中的该注解。
配置类上加上该注解
启动测试:(如图说明Dog.class注入到容器中了)
@Enable~~注解原理总结:
@Enable~~注解,大致是通过@import将对象注入到IOC容器中使用。
四、实现ImportSelector注入bean对象;
编写类实现ImportSelector接口:
public class ImportSelectorTest implements ImportSelector {
@Override
public String[] selectImports(AnnotationMetadata annotationMetadata) {
return new String[]{"com.ls.entity.Car","com.ls.entity.Dog"};
}
}
在配置文件注入该类,并测试:
总结:可以使用类实现ImportSelector接口,在数组上加入需要注入类的全路径,则可以注入到IOC容器中;
五、使用ImportBeanDefinitionRegistrar注册bean对象;
编写类实现ImportBeanDefinitionRegistrar接口:
public class ImportBeanDefinitionRegistrarTest implements ImportBeanDefinitionRegistrar {
@Override
public void registerBeanDefinitions(AnnotationMetadata annotationMetadata, BeanDefinitionRegistry beanDefinitionRegistry) {
RootBeanDefinition rootBeanDefinition = new RootBeanDefinition(Car.class);
beanDefinitionRegistry.registerBeanDefinition("Car",rootBeanDefinition);
}
}
将该类注入IOC中,测试:
总结:实现该接口,可以实现手动注入bean对象到IOC容器中。
六、使用FactoryBean注册bean对象;
FactoryBean和BeanFactory区别:
- FactoryBean表示注册bean对象的工厂,可以将bean对象注入到IOC容器中;
- BeanFactory表示获取bean对象的工厂,可以在该工厂中获取bean对象;
实现FactoryBean接口,重写一下方法,注入Car对象:
public class FactoryBeanTest implements FactoryBean<Car> {
@Override
public Car getObject() throws Exception {
return new Car();
}
@Override
public Class<?> getObjectType() {
return Car.class;
}
@Override
public boolean isSingleton() {
// 返回true表示单例,返回false表示为多例
return true;
}
}
将FactoryBeanTest注入到IOC容器中:
测试,打印bean对象并验证是否是单例:
使用FactoryBean注册bean总结:
- 实现FactoryBean接口,重写接口中的方法;
- isSingleton方法返回true表示为单例,返回false表示为多例。
注:该例子是学习蚂蚁课堂Spring5.0的学习笔记。