java spring required,Spring @Resource 忽略 required

在使用spring 自动注入对象通常会用到@Autowired (spring 自定义注解)、@Resource (JSR-250规范定义的注解) 两个注解,在使用中@Autowired 支持 required = false 的设置可以允许注入对象为null,而@Resource 不支持该特性 (王侯将相宁有种乎?), 手动扩展spring使其支持null对象注入。

探究源码

// @Resource注解使用的是CommonAnnotationBeanPostProcessor处理器

public class CommonAnnotationBeanPostProcessor extends InitDestroyAnnotationBeanPostProcessor

implements InstantiationAwareBeanPostProcessor, BeanFactoryAware, Serializable {

/**

* 通过注入对象的名称从BeanFactory提取bean 对象

*/

protected Object autowireResource(BeanFactory factory, LookupElement element, String requestingBeanName)

throws BeansException {

Object resource;

Set autowiredBeanNames;

String name = element.name;

if (this.fallbackToDefaultTypeMatch && element.isDefaultName &&

factory instanceof AutowireCapableBeanFactory && !factory.containsBean(name)) {

autowiredBeanNames = new LinkedHashSet();

resource = ((AutowireCapableBeanFactory) factory).resolveDependency(

element.getDependencyDescriptor(), requestingBeanName, autowiredBeanNames, null);

}

else {

resource = factory.getBean(name, element.lookupType);

autowiredBeanNames = Collections.singleton(name);

}

if (factory instanceof ConfigurableBeanFactory) {

ConfigurableBeanFactory beanFactory = (ConfigurableBeanFactory) factory;

for (String autowiredBeanName : autowiredBeanNames) {

if (beanFactory.containsBean(autowiredBeanName)) {

beanFactory.registerDependentBean(autowiredBeanName, requestingBeanName);

}

}

}

return resource;

}

}

扩展BeanPostProcessor

/**

* 直接继承CommonAnnotationBeanPostProcessor

* 作为BeanPostProcessor组件加载

*/

@Component

public class AutoResourceNull extends CommonAnnotationBeanPostProcessor {

/**

* 重写autowireResource方法。

* 在获取注入对象是如果为null捕获异常从而返回null对象,不影响spring 容器加载

*/

@Override

protected Object autowireResource(BeanFactory factory, LookupElement element, String requestingBeanName) throws BeansException {

Object obj = null;

try {

obj = super.autowireResource(factory, element, requestingBeanName);

} catch (Exception e) {

System.err.println(e.getMessage());

}

return obj;

}

}

通过重写CommonAnnotationBeanPostProcessor在对象注入前,重写该类中autowireResource 方法,在BeanFactory中找不到该对象是默认返回null对象给到引用方,从而不影响这个spring容器的加载,多数情况下用于单元测试阶段 (因为不想因为不相干的bean对象找不到从而影响整个spring容器的加载)。有一个缺点就是不能像@Autowired那样细粒度控制到具体某个对象允许为null,这里相当于给@Resource加了个全局开关。

实现@Autowired的全局允许为null的扩展

/**

* @Autowired 和 @Inject 使用的是 AutowiredAnnotationBeanPostProcessor 处理器

*/

@Component

public class AppTest extends AutowiredAnnotationBeanPostProcessor {

/**

* 同理,在获取bean对象时捕获异常返回null对象

*/

@Override

public PropertyValues postProcessPropertyValues(PropertyValues pvs, PropertyDescriptor[] pds, Object bean, String beanName) throws BeanCreationException {

try {

pvs = super.postProcessPropertyValues(pvs, pds, bean, beanName);

} catch (BeanCreationException e) {

System.err.println(e.getMessage());

}

return pvs;

}

}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
### 回答1: @Autowired 是 Spring 容器提供的注解,可以用来根据类型自动装配bean,而 @Resource 则是 Java 提供的注解,可以根据 bean 的名称进行装配。@Autowired 默认按类型装配,默认情况下必须要求依赖对象必须存在,如果要允许 null 值,可以设置它的 required 属性为 false。@Resource 默认按照 bean 的名称进行装配,名称可以通过 name 属性进行指定,如果没有指定 name 属性,当注解写在字段上时,默认取字段名作为 bean 的名称。 ### 回答2: 在Spring框架中,@Autowired和@Resource都是用于依赖注入的注解,它们的作用是从容器中获取指定类型的实例并自动注入到相应的属性中。它们之间的区别如下: 1. @Autowired注解属于Spring注解,而@Resource注解JavaEE的注解。因此,如果我们使用的是纯粹的Spring框架,可以选择使用@Autowired注解;如果是使用的是JavaEE容器,可以选择使用@Resource注解。 2. 默认情况下,@Autowired注解按照类型进行依赖注入。即,它会根据属性的类型在容器中查找相应的实例进行注入。而@Resource注解默认按照名称进行依赖注入。即,它会根据属性的名称在容器中查找相应的实例进行注入。当然,@Resource注解也可以通过name属性指定注入的名称。 3. 在@Autowired注解中,可以使用required属性来指定是否必须注入成功。如果将required属性设置为true,但容器中找不到相应的实例,会抛出异常;如果设置为false,在找不到实例时,则会将属性设置为null。而@Resource注解则没有类似的属性,它的行为是非强制性的,也就是说,如果找不到相应的实例,则不会抛出异常,属性会保持不变。 4. @Autowired注解可以应用于构造方法、属性和方法上,而@Resource注解则主要应用于属性上。 综上所述,@Autowired和@Resource注解的区别在于注解本身的来源、注入方式、是否强制注入以及适用范围。根据具体的需求和使用场景,可以选择合适的注解来进行依赖注入。 ### 回答3: 在Spring框架中,@Autowired和@Resource注解都用于依赖注入,但有一些细微的区别。 首先,@Autowired是Spring提供的注解,而@Resource是由Java EE(JSR-250)提供的注解。这意味着如果只使用Spring框架,则可以使用@Autowired,而@Resource也可以在任何Java EE环境中使用。 其次,@Autowired默认按照类型进行依赖注入。它会去查找与属性类型匹配的Bean,并将其注入。如果存在多个匹配的Bean,Spring会抛出异常。要解决这个歧义,可以使用@Autowired的required属性进行控制。另外,还可以使用@Qualifier注解来指定具体的Bean名称。 而@Resource默认按照属性名称进行依赖注入。它会先按照属性名称查找对应的Bean,如果找不到再按照类型查找。通过@Resource的name属性,可以指定具体的Bean名称。 此外,@Autowired可以用于构造方法、参数、属性和方法上,而@Resource只能用于属性和方法上。 最后,@Autowired是Spring的特定功能注解,它提供更多的功能和灵活性,可以实现更复杂的依赖注入。而@ResourceJava EE提供的注解,它更简单,功能相对较少。 综上所述,两者的主要区别在于来源、注入方式和功能灵活性。对于只使用Spring框架的项目来说,@Autowired是首选,而@Resource可以在Java EE环境中使用。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值