【译】Spring 4.0带来的@Conditional注解

稜镜实例化
• 阅读 6916

Spring 4.0带来的@Conditional注解

本文会接触spring 4的新功能:@Conditional注解。在之前的spring版本中,你处理conditions只有以下两个方法:

  • 在3.1版本之前,你需要使用spring expression language
  • 在3.1版本发布时,profiles被引入来处理conditions。

让我们分别看看以上两者,在来理解spring 4带来的@Conditional注解。

Spring Expression Language(SPeL)

SPeL的三元标识符(IF-THEN-ELSE)可以在spring配置文件中用来表达条件语句。

<bean id="flag">
   <constructor-arg value="#{systemProperties['system.propery.flag'] ?: false }" />
</bean>
<bean id="bean">
    <property name="property" value="#{ flag ? 'yes' : 'no' }"/>
</bean>

这个bean的属性依赖于flag的值,该值是使用外部属性注入的,这样bean就具有了动态的能力。

使用 Profiles

这是在spring 3.1引入的。像下面这样使用。

<!-- default configuration - will be loaded if no profile is specified -->
<!-- This will only work if it's put at the end of the configuration file -->
<!-- so no bean definitions after that -->
<beans profile="default">
     <import resource="classpath:default.xml" />
</beans>
<!-- some other profile -->
<beans profile="otherProfile">
    <import resource="classpath:other-profile.xml" />
</beans>

使用spring 4的@Conditional注解

现在介绍@Conditional注解。官方文档的说明是“只有当所有指定的条件都满足是,组件才可以注册”。主要的用处是在创建bean时增加一系列限制条件。

Conditional接口的声明如下:

@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.TYPE, ElementType.METHOD)
public @interface Conditional{
    Class <!--?extends Condition-->[] value();
}

所以@Conditional注解使用方法如下

  • 类型级别,可以在@Component 或是 @Configuration类上使用
  • 原型级别,可以用在其他自定义的注解上
  • 方法级别,可以用在@Bean的方法上

如果一个@Configuration类使用了@Conditional,会影响所有@Bean方法和@Import关联类

public interface Condition{
/** Determine if the condition matches.
* @param context the condition context
* @param metadata meta-data of the {@link AnnotationMetadata class} or
* {@link Method method} being checked.
* @return {@code true} if the condition matches and the component can be registered
* or {@code false} to veto registration.
*/
boolean matches(ConditionContext context, AnnotatedTypeMedata metadata);
}

下面是一个例子

public class SystemPropertyCondition implements Condition {
    @Override
    public boolean matches(ConditionContext context, AnnotatedTypeMetadata         metadata) {
        return (System.getProperty("flag") != null);
    }
}

class SystemPropertyAbsentCondition implements Condition {
    @Override
    public boolean matches(ConditionContext context, AnnotatedTypeMetadata metadata) {
        return (System.getProperty("flag") == null);
    }
}

这里我们有两个类:SystemPropertyCondition和SystemPropertyAbsentCondtion. 这两个类都实现了Condition接口.覆盖的方法基于属性flag返回一个布尔值。
现在我们定义两个类,一个是positive条件,一个是negative条件:

@Bean
@Conditional(SystemPropertyCondition.class)
public SampleService service1() {
    return new SampleServiceImpl1();
}

@Bean
@Conditional(SystemPropertyAbsentCondition.class)
public SampleService service2() {
    return new SampleServiceImpl2();
}

上面提到的profiles已经通过conditional原型注解进行了修改。

总结

本文介绍了spring 4的conditianal注解。注意condition注解是不会继承的。如果一个父类使用了conditional注解,其子类是不会拥有conditions的。如果你动手尝试以上的例子,会帮助你获得更好的理解。

点赞
收藏
评论区
推荐文章
Easter79 Easter79
3年前
spring注解
随着越来越多地使用Springboot敏捷开发,更多地使用注解配置Spring,而不是Spring的applicationContext.xml文件。Configuration注解:Spring解析为配置类,相当于spring配置文件Bean注解:容器注册Bean组件,默认id为方法名@Configurat
Wesley13 Wesley13
3年前
java面试中被问到的问题
 技术面1) Spring 的注解有哪些?2) 你如何理解 spring IOC 技术,如果不使用spring,你有哪些方式来加载 bean?3) spring aop 的原理是什么?它是怎样一个写法?关键配置项是什么?4) springmvc 的注解有哪些?@ModelAttribute 重点提及
Stella981 Stella981
3年前
Dubbo服务治理篇——改造低版本Dubbo,使其兼容Spring4或Spring5注解配置
!(https://oscimg.oschina.net/oscnet/9428b7690cb27befb3db0083017dc042723.gif)温馨提示:本文有点长,但是满满的干货,建议耐心看完!特别说明:由于很多网友留言自身使用的Dubbo框架版本比较低,无法兼容Spring4或Spring5的注解配置,故本文只针对
Stella981 Stella981
3年前
Spring 中使用 Hibernate
Hibernate在ORM领域具有广泛的影响,拥有广大的使用群体。它提供了ORM最完整、最丰富的实现,在Spring4.0中目前全面支持Hibernate5.0,不再支持Hibernate3.6 之前的版本。因为iBatis的升级版MyBatis自身已经提供了对Spring整合的支持,所以 Spring不再为MyBat
Wesley13 Wesley13
3年前
@Transactional注解失效的解决方案
一、前言  开发中我们经常使用@Transactional注解来启用Spring事务管理,但是如果使用方法不当,会遇到注解不生效该事务回滚的地方却没有回滚的问题。总结下一般是以下几个原因:1.@Transactional注解只能应用到public可见度的方法上。如果应用在protected、private或者p
Easter79 Easter79
3年前
Spring全解系列
本文基于Spring5.2.x@Import注解@Import是Spring基于Java注解配置的主要组成部分。@Import注解提供了@Bean注解的功能,同时还有原来Spring基于xml配置文件里的<import标签组织多个分散的xml文件的功能,当然在这里是组织多个分散的
Easter79 Easter79
3年前
Spring注解驱动开发之web
前言:现今SpringBoot、SpringCloud技术非常火热,作为Spring之上的框架,他们大量使用到了Spring的一些底层注解、原理,比如@Conditional、@Import、@EnableXXX等。如果掌握这些底层原理、注解,那么我们对这些高层框架就能做到高度定制,使用的游刃有余一、servlet3.0规范
Easter79 Easter79
3年前
Spring注解大全,汇总版
Spring使用的注解大全和解释注解解释@Controller组合注解(组合了@Component注解),应用在MVC层(控制层),DispatcherServlet会自动扫描注解了此注解的类,然后将web请求映射到注解了@RequestMapping的方法上。@Service组合注解(组合了@Component注解),应用在
Wesley13 Wesley13
3年前
0、Spring 注解驱动开发
0、Spring注解驱动开发0.1简介《Spring注解驱动开发》是一套帮助我们深入了解Spring原理机制的教程;现今SpringBoot、SpringCloud技术非常火热,作为Spring之上的框架,他们大量使用到了Spring的一些底层注解、原理,比如@Conditional、@Import、@
Wesley13 Wesley13
3年前
Spring学习总结(2)——Spring的常用注解
本文汇总了Spring的常用注解,以方便大家查询和使用,具体如下:使用注解之前要开启自动扫描功能其中basepackage为需要扫描的包(含子包)。?(https://www.oschina.net/action/GoToLink?urlhttp%3A%2F%2Fwww.jb51.net%2Farticle%2F53586.htm%23)
Stella981 Stella981
3年前
Spring Conditional原理与实例
1\.简介Spring4开始添加了一个Condition接口:@FunctionalInterfacepublicinterfaceCondition{booleanmatches(ConditionContextcontext,AnnotatedTypeMetadatametadata);
稜镜实例化
稜镜实例化
Lv1
门有车马客,驾言发故乡。
文章
4
粉丝
0
获赞
0