https://www.jianshu.com/p/23f504713b94

核心注解

打开上面任意一个AutoConfiguration文件,一般都有下面的条件注解,在spring-boot-autoconfigure-1.5.3.RELEASE.jar的org.springframework.boot.autoconfigure.condition包下条件注解如下:

  • @ConditionalOnBean:当前容器有指定Bean的条件下。
  • @ConditionalOnClass:当前类路径下有指定的类的条件下。
  • @ConditionalOnExpression:基于SpEL表达式作为判断条件。
  • @ConditionalOnJava:基于JVM版本作为判断条件。
  • @ConditionalOnJndi:在JNDI存在的条件下查找指定的位置。
  • @ConditionalOnMissingBean:当容器里没有指定Bean的情况下。
  • @ConditionalOnMissingClass:当类路径下没有指定的类的条件下。
  • @ConditionalOnNotWebApplication:当前项目不是WEB项目的条件下。
  • @ConditionalOnProperty:指定属性是否有指定的值。
  • @ConditionalOnResource:类路径是否有指定的值。
  • @ConditionalOnSingleCandidate:当指定Bean在容器中只有一个,或者虽然有多个但 是指定首选的Bean。
  • @ConditionalOnWebApplication:当前项目是WEB项目的条件下。

这些注解都组合了@Conditional元注解,只是使用了不同的条件(Conditional),Spring 条件注解(@Conditional)我们介绍过根据不同条件创建不同Bean。

简单分析一下@ConditionalOnWebApplication注解:

package org.springframework.boot.autoconfigure.condition;

import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target; import org.springframework.context.annotation.Conditional; @Target({ ElementType.TYPE, ElementType.METHOD })
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Conditional(OnWebApplicationCondition.class)
public @interface ConditionalOnWebApplication {
}

从源码我们可以看出,此注解使用的条件是OnWebApplicationCondition类,下面我们看看这个类是怎么构造的:

package org.springframework.boot.autoconfigure.condition;

import org.springframework.context.annotation.Condition;
import org.springframework.context.annotation.ConditionContext;
import org.springframework.core.Ordered;
import org.springframework.core.annotation.Order;
import org.springframework.core.type.AnnotatedTypeMetadata;
import org.springframework.util.ClassUtils;
import org.springframework.util.ObjectUtils;
import org.springframework.web.context.WebApplicationContext;
import org.springframework.web.context.support.StandardServletEnvironment; @Order(Ordered.HIGHEST_PRECEDENCE + 20)
class OnWebApplicationCondition extends SpringBootCondition { private static final String WEB_CONTEXT_CLASS = "org.springframework.web.context."
+ "support.GenericWebApplicationContext"; @Override
public ConditionOutcome getMatchOutcome(ConditionContext context,
AnnotatedTypeMetadata metadata) {
boolean webApplicationRequired = metadata
.isAnnotated(ConditionalOnWebApplication.class.getName());
ConditionOutcome webApplication = isWebApplication(context, metadata); if (webApplicationRequired && !webApplication.isMatch()) {
return ConditionOutcome.noMatch(webApplication.getMessage());
} if (!webApplicationRequired && webApplication.isMatch()) {
return ConditionOutcome.noMatch(webApplication.getMessage());
} return ConditionOutcome.match(webApplication.getMessage());
} private ConditionOutcome isWebApplication(ConditionContext context,
AnnotatedTypeMetadata metadata) { if (!ClassUtils.isPresent(WEB_CONTEXT_CLASS, context.getClassLoader())) {
return ConditionOutcome.noMatch("web application classes not found");
} if (context.getBeanFactory() != null) {
String[] scopes = context.getBeanFactory().getRegisteredScopeNames();
if (ObjectUtils.containsElement(scopes, "session")) {
return ConditionOutcome.match("found web application 'session' scope");
}
} if (context.getEnvironment() instanceof StandardServletEnvironment) {
return ConditionOutcome
.match("found web application StandardServletEnvironment");
} if (context.getResourceLoader() instanceof WebApplicationContext) {
return ConditionOutcome.match("found web application WebApplicationContext");
} return ConditionOutcome.noMatch("not a web application");
} }

从isWebApplication方法可以看出,判断条件是:

  1. GenericWebApplicationContext是否在类路径中;
  2. 容器中是否有名为session的scope;
  3. 当前容器的Enviroment是否为StandardServletEnvironment;
  4. 当前的ResourceLoader是否是WebApplicationContext(ResourceLoader是ApplicationContext的顶级接口之一);
  5. 我们需要构建ConditionOutcome类的对象来帮助我们,最终通过ConditionOutcome.isMatch方法返回值来确定条件。

Spring Boot 运行原理 - 核心注解的更多相关文章

  1. Spring Boot运行原理

    概述 本文主要写了下Spring Boot运行原理,还有一个小例子. Spring4.x提供了基于条件来配置Bean的能力,而Spring Boot的实现也是基于这一原理的. Spring Boot关 ...

  2. Spring boot运行原理-自定义自动配置类

    在前面SpringBoot的文章中介绍了SpringBoot的基本配置,今天我们将给大家讲一讲SpringBoot的运行原理,然后根据原理我们自定义一个starter pom. 本章对于后续继续学习S ...

  3. Spring Boot 运行原理

    Spring Boot并没有任何新的技术,全都是基于Spring4提供的技术,用优秀的设计,为Web开发提供了一套新的方式. 在HelloWorld中,我们没有进行任何显示的配置,但是程序还是运行起来 ...

  4. Spring Boot的27个注解【核心】

    导读[约定大于配置] Spring Boot方式的项目开发已经逐步成为Java应用开发领域的主流框架,它不仅可以方便地创建生产级的Spring应用程序,还能轻松地通过一些注解配置与目前比较火热的微服务 ...

  5. Spring Boot 运作原理

    Spring Boot 运作原理 1.Spring Boot 简介 SpringBoot是由Pivotal团队提供的全新框架,其设计目的是用来简化新Spring应用的初始搭建以及开发过程.该框架使用了 ...

  6. Spring Boot启动原理解析

    Spring Boot启动原理解析http://www.cnblogs.com/moonandstar08/p/6550758.html 前言 前面几章我们见识了SpringBoot为我们做的自动配置 ...

  7. spring boot启动原理步骤分析

    spring boot最重要的三个文件:1.启动类 2.pom.xml 3.application.yml配置文件 一.启动类->main方法 spring boot启动原理步骤分析 1.spr ...

  8. struts1,struts2,hibernate,spring的运行原理结构图

    一.struts1运行原理 1.初始化:struts框架的总控制器ActionServlet是一个Servlet,它在web.xml中配置成自动启动的Servlet,在启动时总控制器会读取配置文件(s ...

  9. spring boot 运行提示:Process finished with exit code 1

    spring boot 运行提示:Process finished with exit code 1 经检查发现是由于在application.properties配置文件中将某些自定义配置项移除了, ...

随机推荐

  1. Java基础回顾一

    1.JDK和JRE的区别: JDK:java开发工具包,提供java的开发环境和运行环境 JRE:java运行环境,为java的运行提供所需要的环境 2. ==和qruals的区别: == 基本类型: ...

  2. odoo10学习笔记十七:controller

    转载请注明原文地址:https://www.cnblogs.com/ygj0930/p/11189391.html 一:controller简述 odoo里面的controller相似于springM ...

  3. if语句编写Mysql备份脚本

    #!/bin/bash #auto bakcup mysql db #by authors zgh #define backup path BAK_DIR=/data/backup/`date +%Y ...

  4. 使用hutool工具类进行导出

    引入依赖为: <dependency> <groupId>cn.hutool</groupId> <artifactId>hutool-all</ ...

  5. 1.python进行if条件相等时候的条件

    在我们进行 if == 判断的时候!其中判断的条件: 1:其值是不是一样 3:其类型是否是一样 ###二者少了任何一个都不可以 >>> pwd = 23>>> cc ...

  6. XSS-DOM

    DOM型XSS是基于DOM文档对象模型的一种漏洞 通过 HTML DOM,树中的所有节点均可通过 JavaScript 进行访问.所有 HTML 元素(节点)均可被修改,也可以创建或删除节点.(引用W ...

  7. day23_7.29 多态和类的内置方法

    一.多态 在现实生活中,多态也会体现.如对于水这种物质,有固态:冰,液态:常态,气态:水蒸气, 在程序中,其官方定义是:多个不同对象可以相应同一方法,产生不同的结果. 而在python中,多态不是一个 ...

  8. 【Spring AOP】AOP的实现(三)

    一.Spring 对AOP的支持 Spring中AOP代理由Spring的IOC容器负责生成.管理,其依赖关系也由IOC容器负责管理.因此,AOP代理可以直接使用容器中的其它bean实例作为目标,这种 ...

  9. 循环控制语句if 、for、case、while

    if 循环控制(单分支与多分支) (1)单个判断(单分支循环): if [ 条件判断 ]; then 执行动作 fi if [ 条件判断 ]; then 执行动作 else 执行动作 fi 写入tes ...

  10. 创建vector<T>容器

    vector<T> 容器是包含 T 类型元素的序列容器,和 array<T,N> 容器相似,不同的是 vector<T> 容器的大小可以自动增长,从而可以包含任意数 ...