Spring提供了一系列名称以Enable *开头的注释,这些注释本质上使某些Spring管理的功能可以被激活。 这样的注释的一个很好的例子是EnableWebMvc ,它引入了在基于Spring的应用程序中支持MVC流所需的所有bean。 另一个很好的例子是EnableAsync注释,用于在基于Spring的应用程序中激活bean以支持异步功能。

我对这样的注释如何工作感到好奇,并希望记录下我的理解。 支持这些注释的方式可以视为SPI的一部分,因此,如果将来内部实现发生更改,则可能会中断。

简单的启用*注释

考虑这些自定义注释的一种方法是,它们将一组新bean添加到Spring的应用程序上下文中。 让我们首先定义一个这样的自定义注释:

@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.TYPE)
@interface EnableSomeBeans {}

并将此注释应用于Spring @Configuration类:

@Configuration
@EnableSomeBeans
public static class SpringConfig {}

因此,现在在应用此批注时引入一组bean就像添加通过@Import批注以这种方式引入的bean组一样简单:

@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.TYPE)
@Import(SomeBeanConfiguration.class)
@interface EnableSomeBeans {}

本质上就是这样,如果此导入的@Configuration类定义了任何bean,则它们现在将成为Application上下文的一部分:

@Configuration
class SomeBeanConfiguration {@Beanpublic String aBean1() {return "aBean1";}@Beanpublic String aBean2() {return "aBean2";}
}

这是一个具有工作样本的要点 。

使用选择器启用*注释

启用注释可能要复杂得多,它们可以根据周围的上下文来激活不同的Bean系列。 这样的注释的一个示例是EnableCaching ,它基于类路径中可用的不同缓存实现来激活配置。

与之前的简单示例相比,编写此类Enable *注释要花费更多的精力。 与之前一样,从一个自定义注释开始:

@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.TYPE)
@Import(SomeBeanConfigurationSelector.class)
public @interface EnableSomeBeansSelector {String criteria() default "default";
}

请注意,在这种情况下,自定义注释具有一个称为标准的示例字段,我要做的是根据此标准激活两组不同的bean。 这可以通过使用@Configuration选择器来实现,该选择器可以根据上下文返回不同的@Configuration文件(在此示例中,criteria字段的值)。 该选择器具有一个简单的签名,这是一个示例实现:

import org.springframework.context.annotation.ImportSelector;
import org.springframework.core.annotation.AnnotationAttributes;
import org.springframework.core.type.AnnotationMetadata;public class SomeBeanConfigurationSelector implements ImportSelector {@Overridepublic String[] selectImports(AnnotationMetadata importingClassMetadata) {AnnotationAttributes attributes =AnnotationAttributes.fromMap(importingClassMetadata.getAnnotationAttributes
(EnableSomeBeansSelector.class.getName(), false));String criteria = attributes.getString("criteria");if (criteria.equals("default")) {return new String[]{"enableannot.selector.SomeBeanConfigurationDefault"};}else {return new String[]{"enableannot.selector.SomeBeanConfigurationType1"};}}
}@Configuration
class SomeBeanConfigurationType1 {@Beanpublic String aBean() {return "Type1";}}@Configuration
class SomeBeanConfigurationDefault {@Beanpublic String aBean() {return "Default";}}

因此,如果条件字段为“默认”,则添加“ SomeBeanConfigurationDefault”中的bean,否则添加“ SomeBeanConfigurationType1”中的bean

  • 这是一个具有工作样本的要点 。

结论

我希望这能对Spring如何在内部实现@ Enable *注释有所了解,作为应用程序开发人员,您可能不需要自己创建此类注释,一种更简单的机制是使用@Configuration类和Spring Bean配置文件来组成应用程序。

翻译自: https://www.javacodegeeks.com/2015/04/spring-enable-annotation-writing-a-custom-enable-annotation.html

Spring Enable批注–编写自定义的Enable批注相关推荐

  1. Spring Enable annotation – writing a custom Enable annotation

    原文地址:https://www.javacodegeeks.com/2015/04/spring-enable-annotation-writing-a-custom-enable-annotati ...

  2. Spring MVC表单验证(带批注)

    这篇文章提供了一个简单HTML表单验证示例. 它基于带有注释的Spring MVC示例. 该代码可在GitHub的Spring-MVC-Form-Validation目录中找到. 数据 在此示例中,我 ...

  3. c++报错:引用了未定义标签_大牛带你解读Spring源码,编写自定义标签,您能学会吗?...

    Spring源码阅读之编写自定义标签 基于昨天的那篇文章,我们今天来聊一个比较简单轻松点的话题,今天我们来实现一个自定义的标签. (本文来自公众号:z小赵) 先明确下整个项目的结构,网上有很多关于自定 ...

  4. spock框架_Spock VW:编写自定义的Spock框架扩展

    spock框架 Spock框架具有多个内置扩展 ,这些扩展支持许多核心功能,例如@Ignore和@Timeout批注. 但更重要的是,鼓励开发人员编写自己的扩展. 例如, SpringExtensio ...

  5. Spock VW:编写自定义的Spock框架扩展

    Spock框架具有多个内置扩展 ,这些扩展支持许多核心功能,例如@Ignore和@Timeout批注. 但更重要的是,鼓励开发人员编写自己的扩展. 例如, SpringExtension很好地将Spo ...

  6. 通过SPANN方式将Spring&Quartz与自定义注释集成

    在上一篇文章中 ,我们演示了如何在Spring容器中创建和配置带批注的Quartz作业. 我们使用了一个类级别的注释将一些元数据添加到实现Quartz Job的bean中. 批注定义了作业的名称,组及 ...

  7. 使用SPANN方式将Spring&Quartz与自定义注释集成

    在上一篇文章中 ,我们演示了如何在Spring容器中创建和配置带批注的Quartz作业. 我们使用了一个类级别的注释将一些元数据添加到实现Quartz Job的bean中. 批注定义了作业的名称,组及 ...

  8. Spring Boot基础学习笔记04:Spring Boot加载自定义配置文件

    文章目录 零.学习目标 1.熟悉使用@PropertySource加载配置文件 2.熟悉使用@ImportResource加载XML配置文件 3.掌握使用@Configuration编写自定义配置类 ...

  9. Spring Cloud Gateway (六) 自定义 Global Filter

    Spring Cloud Gateway (六) 自定义 Global Filter 简介     在前面五篇的分析中,对 Spring Cloud Gateway 的 filter 组件有了一个大概 ...

最新文章

  1. 给.net程序打内存补丁-转
  2. 又一个 Java 面试神器!
  3. python pyside简单布局_python – pyside显示/隐藏布局
  4. scrapy框架对接seleniumpipeline数据持久化
  5. 【CV项目实战】纯新手如何从零开始完成一个工业级图像分割任务的整个流程?...
  6. 分支机构L2L *** 到总部再PAT通过专线到合作伙伴(SVTI建立***)
  7. 2016年春季计算机应用基础,东北师范2016年春季《计算机应用基础》期末考核
  8. Node.js 笔记 http服务器
  9. TCP/IP协议族之应用层协议(FTP、TFTP)
  10. BigDecimal保留两位小数,不足两位补0
  11. Python基础(五)
  12. vn.py开源量化交易程序开发框架
  13. 自动化框架应该具备的要点
  14. 软件工程第1次阅读作业
  15. ISO18000-6C 电子标签数据存储空间及数据加密说明
  16. C++:Sqlite调用之增、读、改
  17. 20190422每周精品之认知
  18. Python微信操控itchat定时发送消息
  19. antd select.option选项加入额外属性
  20. Web Framworks 的决斗

热门文章

  1. 2020蓝桥杯省赛---java---B---8(走方格)
  2. 2018蓝桥杯省赛---java---B---4(测试次数)
  3. python3 爬虫例子_如何让你写的爬虫速度像坐火箭一样快【并发请求】
  4. springboot创建项目2 开发环境的搭建
  5. 计算机应用基础期中上机考试,期中考试计算机应用基础试卷
  6. Object.hashCode()与Object.equals()
  7. thinking-in-java(21)并发2
  8. jpa避免n+1_JPA技巧:避免N + 1选择问题
  9. jax-ws和jax-rs_带有JAX-WS和Spring的Web服务应用程序
  10. vertx rest 跨域_在基于简单Vertx Rest的应用程序上为REST资源设置基本响应HTTP标头...