千家信息网

@SpringBootApplication与@SpringBootTest的区别有哪些

发表于:2026-11-03 作者:千家信息网编辑
千家信息网最后更新 2026年11月03日,小编给大家分享一下@SpringBootApplication与@SpringBootTest的区别有哪些,希望大家阅读完这篇文章之后都有所收获,下面让我们一起去探讨吧!@SpringBootAppl
千家信息网最后更新 2026年11月03日@SpringBootApplication与@SpringBootTest的区别有哪些

小编给大家分享一下@SpringBootApplication与@SpringBootTest的区别有哪些,希望大家阅读完这篇文章之后都有所收获,下面让我们一起去探讨吧!

@SpringBootApplication与@SpringBootTest区别用法

1 @SpringBootApplication 注解的应用

一般情况我们使用 @SpringBootApplication 注解来启动 SpringBoot 项目

它其实只相当于 @Configuration、@EnableAutoConfiguration、@ComponentScan(包含了两个filter)

@SpringBootApplicationpublic class FrameworkUnitRealTestApp {    public static void main(String[] args) {        SpringApplication.run(FrameworkUnitRealTestApp.class, args);    }}

2 @SpringBootTest 注解的应用

一般情况我们使用 @SpringBootTest 和 @RunWith(SpringRunner.class) 注解来启动 SpringBoot 测试项目

@RunWith(SpringRunner.class) @SpringBootTestpublic class FrameworkUnitRealTestApp {    @Test    public void test() {}}

3 @SpringBootApplication 和 @SpringBootTest 的区别

这两个注解的区别的核心在于两个注解:@EnableAutoConfiguration、@ComponentScan(包含了两个filter)

@EnableAutoConfiguration 启动了所有的自动配置类

@ComponentScan(包含了两个filter):在扫描阶段过滤掉 @TestComponent 等专属于测试的类和过滤掉被 @Configuration 注解的自动配置类(使得自动配置类不会在扫描阶段就被注册 beanDefinition,因为 自动配置类的优先级应该是最低的)

可以看出 @SpringBootTest 并没有启用任何自动配置类,所以就不需要加 AutoConfigurationExcludeFilter 了

springboot 通过引入 @Test** 注解来在 测试环境下 引入不同的自动配置类!

4 @ComponentScan(包含了两个filter) 解析

详细的代码如下:添加了 TypeExcludeFilter 和 AutoConfigurationExcludeFilter 两个 excludeFilter

作用:扫描包的时候过滤掉被这两个 Filter 匹配的类!

@ComponentScan(excludeFilters = {        @Filter(type = FilterType.CUSTOM, classes = TypeExcludeFilter.class),        @Filter(type = FilterType.CUSTOM, classes = AutoConfigurationExcludeFilter.class) })

4.1 TypeExcludeFilter 解析

主要移除测试相关的类

public class TypeExcludeFilter implements TypeFilter, BeanFactoryAware {   @Override   public boolean match(MetadataReader metadataReader,         MetadataReaderFactory metadataReaderFactory) throws IOException {      if (this.beanFactory instanceof ListableBeanFactory            && getClass() == TypeExcludeFilter.class) {         Collection delegates = ((ListableBeanFactory) this.beanFactory)               .getBeansOfType(TypeExcludeFilter.class).values();         for (TypeExcludeFilter delegate : delegates) {            if (delegate.match(metadataReader, metadataReaderFactory)) {               return true;            }         }      }      return false;   }}//delegate.match 走这个类的 match 方法class TestTypeExcludeFilter extends TypeExcludeFilter {    private static final String[] CLASS_ANNOTATIONS = { "org.junit.runner.RunWith",            "org.junit.jupiter.api.extension.ExtendWith" };    private static final String[] METHOD_ANNOTATIONS = { "org.junit.Test",            "org.junit.platform.commons.annotation.Testable" };    @Override    public boolean match(MetadataReader metadataReader,            MetadataReaderFactory metadataReaderFactory) throws IOException {        //是否被 @TestComponent 及其父注解注释        if (isTestConfiguration(metadataReader)) {return true;}        //类上或类中方法上有没有 CLASS_ANNOTATIONS、METHOD_ANNOTATIONS 中的注解        if (isTestClass(metadataReader)) {return true;}        String enclosing = metadataReader.getClassMetadata().getEnclosingClassName();        if (enclosing != null) {            //递归内部类、父类            if (match(metadataReaderFactory.getMetadataReader(enclosing),                      metadataReaderFactory)) {                return true;            }        }        return false;    }}

4.2 AutoConfigurationExcludeFilter 解析

主要移除被 @Configuration 修饰的 自动配置类

public class AutoConfigurationExcludeFilter implements TypeFilter, BeanClassLoaderAware {    @Override    public boolean match(MetadataReader metadataReader,            MetadataReaderFactory metadataReaderFactory) throws IOException {        //如果被 @Configuration 注解,并且是 自动配置类就返回 true,即匹配成功         //注:被 @Component 等注解并不匹配        return isConfiguration(metadataReader) && isAutoConfiguration(metadataReader);    }}

5 @EnableAutoConfiguration 注解解析

作用:启用自动配置类

@AutoConfigurationPackage//启用 AutoConfigurationImportSelector 配置类:扫描得到所有自动配置类@Import(AutoConfigurationImportSelector.class)public @interface EnableAutoConfiguration {   String ENABLED_OVERRIDE_PROPERTY = "spring.boot.enableautoconfiguration";   //定义不启用的 自动配置类   Class[] exclude() default {};   //同上   String[] excludeName() default {};}//这个注解主要是向容器中注册 AutoConfigurationPackages.Registrar 类用来存储自动配置包@Import(AutoConfigurationPackages.Registrar.class)public @interface AutoConfigurationPackage {}//关键:这个类继承了 DeferredImportSelector 接口,所以是到最后才解析的!!public class AutoConfigurationImportSelector implements DeferredImportSelector{    @Override    public String[] selectImports(AnnotationMetadata annotationMetadata) {        if (!isEnabled(annotationMetadata)) {            return NO_IMPORTS;        }        AutoConfigurationMetadata autoConfigurationMetadata = AutoConfigurationMetadataLoader            .loadMetadata(this.beanClassLoader);        AutoConfigurationEntry autoConfigurationEntry = getAutoConfigurationEntry(            autoConfigurationMetadata, annotationMetadata);        return StringUtils.toStringArray(autoConfigurationEntry.getConfigurations());    }}

6 @…Test 注解

Spring Boot 中文文档 对每个 @…Test 注解导入的自动配置类做了详细的说明

SpringBootTest对比SpringBootApplication

SpringBootTest 是测试使用类的注解,标志这个类是测试用例。

具体看下源码分析

@Target({ElementType.TYPE})@Retention(RetentionPolicy.RUNTIME)@Documented@Inherited@BootstrapWith(SpringBootTestContextBootstrapper.class)@ExtendWith({SpringExtension.class})public @interface SpringBootTest {
@Target({ElementType.TYPE})@Retention(RetentionPolicy.RUNTIME)@Documented@Inherited@SpringBootConfiguration@EnableAutoConfiguration@ComponentScan(    excludeFilters = {@Filter(    type = FilterType.CUSTOM,    classes = {TypeExcludeFilter.class}), @Filter(    type = FilterType.CUSTOM,    classes = {AutoConfigurationExcludeFilter.class})})public @interface SpringBootApplication {

对比显示都是复合注解,并且前四个注解是一样的,后面区分BootstrapWith和ExtendWith这两个是测试中包含的

BootstrapWith这个注解中有一个参数为SpringBootTestContextBootstrapper

具体可以看下里面是什么

这里面申明了一些程序运行所在包的路径,在去查看继承的顶级类可以追溯到TestContextBootstrapper 这个接口 :

从里面的方法可以看到是在运行的时候设置上下文 以及如何获取上下文,来提供测试启动的必须值。

接下来看下 ExtendWith 这个注解类

这个主要看里面的SpringExtension这个参数

可以看出这个实现了很多接口,来处理测试需要的各种通知处理,以及在测试接口时可以提前处理请求参数。

SpringBootApplication中的复合注解则是扫描一些包和配置。虽然测试也是项目启动的一种,可以看到里面实现还是有些区别的。

看完了这篇文章,相信你对"@SpringBootApplication与@SpringBootTest的区别有哪些"有了一定的了解,如果想了解更多相关知识,欢迎关注行业资讯频道,感谢各位的阅读!

注解 配置 测试 两个 接口 参数 项目 处理 上下 上下文 作用 情况 方法 时候 篇文章 阶段 应用 运行 不同 最低 数据库的安全要保护哪些东西 数据库安全各自的含义是什么 生产安全数据库录入 数据库的安全性及管理 数据库安全策略包含哪些 海淀数据库安全审计系统 建立农村房屋安全信息数据库 易用的数据库客户端支持安全管理 连接数据库失败ssl安全错误 数据库的锁怎样保障安全 什么是科技互联网 互联网新科技 互联网佳科技有限公司 互联网公司 科技公司 互联网科技革命 中国互联网金融科技基金 互联网科技博主是什么意思 恒银科技与互联网金融 湖北码尼互联网科技有限公司电话 中国航天科技大学国际工业互联网 互联网与医疗科技 广州市恰铎互联网科技有限公司 华夏恒生互联网科技013171 威龙国际互联网科技公司 杭州披云加互联网科技有限公司 云鲸互联网络科技有限公司 互联网界的黑科技 互联网科技品牌 山东蛋芒互联网科技有限公司 广州全民伙伴互联网科技有限公司 互联网金融监管科技数据 互联网科技金融公司 碳银互联网科技 无线互联网科技 福州新华互联网科技学校 知乎 深圳市优智互联网科技有限公司 如何创新互联网科技 互联网科技实习生岗位 半导体行业属于互联网高科技类吗 张家口科技产业互联网平台
0