SpringBoot中的注解介绍

SpringBoot中的注解介绍1 Configuratio Bean 比 xml 配置而言类更好维护 分类和管理阅读 代理 1 1 Configuratio 的类就成为了 配置类 取代 application xml 文件 Configuratio proxyBeanMet true 默认单例 false 获取到对象每次不同 总结 Spring 会创建 CGLIB

大家好,我是讯享网,很高兴认识大家。这里提供最前沿的Ai技术和互联网信息。



1.@Configuration + @Bean

【比xml配置而言类更好维护、分类和管理阅读】 代理

1.1@Configuration的类就成为了"配置类",【取代application.xml文件】 @Configuration(proxyBeanMethods=true)默认单例,false获取到对象每次不同

总结:

Spring 会创建CGLIB 代理,保证 @Bean 方法互相调用时,永远返回同一个单例 Bean

1.2方法public User getName()上加上@Bean注解【@Bean(name="abc")】对象为abc,无name属性值,则对象为getName方法名 [取代application.xml中的 标签]

总结:

  1. 首选 namevalue 属性 :如果写了 @Bean(name="abc"),Bean 的唯一标识就是 abc
  2. 默认使用方法名 :如果没有指定 name,Spring 会直接取方法名 getName 作为 Bean 的 ID
  3. 用来替代传统的 配置

2.@Import() 导入组件

底层是一个接口 ()里面的参数是: Class [] value() 【把 普通类 / 配置类 / ImportSelector 导入到spring的IOC容器中去,导入之后我们就可以直接从容器中拿】

特点:常用于第三方类、自动配置

 
  
    
    
@Configuration 

@Import(User.class, OrderConfig.class) // 直接导入多个组件 public class AppConfig {}

 

3.@ImportResource()导入资源文件( 老xml配置文件 )

作用:把传统 xml 配置文件加载进 Spring

场景:兼容老项目、遗留 XML

 
  
    
    
@Configuration 

@ImportResource("classpath:spring-context.xml") public class XmlConfig {}

 

4.@ConditionalOnBean() 条件装配

作用: 容器里有某个 Bean 时,才创建当前 Bean

 
  
    
    
@Configuration 

public class ConditionConfig {

@Bean @ConditionalOnBean(User.class) // 有User才注册Order public Order order() { return new Order(); } 

}

 

5.前四个注解大致总结:

@Import / @ImportResource / @Conditional 系列注解

都属于「配置类专用注解」,必须标注在 @Configuration 类上才会生效!

6.@ConfigurationProperties

作用:配置绑定 [自动把 application.yml / application.properties 里的配置项批量注入到 JavaBeanJava 类的属性中。]

 
  
    
    
/ 
  • 简单粗暴理解:把当前类丢到Ioc容器中去 */ @Component //表明当前类是一个组件 {只有在容器中的组件,才会拥有SpringBoot提供的强大功能,加注解放入容器} 不代理 @ConfigurationProperties(prefix = "car1") // 这个car1就是properties中配置的car对象的键值对,如:car1.brand=BYD car1.price=123 // 这样car需要的属性会和properties中的自动对应 @Data // 没有手Setter 方法,@ConfigurationProperties 无法把配置文件里的值注入到成员变量中。 public class Car { private String brand; private Integer price; }
 

ConfigurationProperties 的底层逻辑是通过 Java 反射调用 Setter 方法 (如 setBrand)来完成赋值的。如果类中只有私有属性而没有对应的 Setter,Car对象中属性值null
注意 :@ConfigurationProperties(prefix = "test.test1") 若找不到prefix前缀时,对象Car创建时bean名称改为:test.test1-cn.stylefeng.guns.tenant.modular.Cat #



  • 类所在的包在 @SpringBootApplication 的扫描路径下,否则 @Component 不会生效。

7.@Confinguration @Commponent 不同

  • @Component :如果这个类只是一个纯粹的 POJO 数据载体,或者仅仅是用来承载配置属性,不涉及复杂的 Bean 组装 。每次调用都会 new 一个新对象 ,单例直接失效!
  • @Configuration :如果你打算在这个类里定义多个有依赖关系的 @Bean(例如 Bean A 的创建需要调用 Bean B 的方法),则必须使用它 。是配置类 ,Spring 会创建CGLIB 代理 ,保证 @Bean 方法互相调用时,永远返回同一个单例 Bean
    不要迷惑单例原因?从 Spring 容器中获取已创建好的 Bean




 
  
    
    
@Configuration 

public class MyConfig {

@Bean public User user() {

return new User(); 

}

@Bean public Order order() {

// 无论调用多少次 user(),永远返回同一个Bean return new Order(user()); 

} }

 

8.@EnableConfigurationProperties

理解: 当多个bean被@ConfigurationProperties()注解修饰,不愿再每个加@Component时,此注解就牛了
作用: 适合导入第三方配置,[第三方的配置没有用自动装配的相关注解,即没丢到IOC容器中,开发人员无法使用!此注解解决!!!]



1、开启属性配置绑定功能( 如:例子中的绑定Car类的属性 )使 @ConfigurationProperties 注解生效!

2、把组件自动注册到容器中( 如:例子中的Car,用了这个注解就可以把Car丢到Ioc容器中去 )

注意:@EnableConfigurationProperties 本身作用1.使@ConfigurationProperties修饰的po类与XXX.properties动态绑定2.将po类交由IOC容器管理!!!

但是要明白:@EnableConfigurationProperties 本身的类的前提是在IOC容器中,不然Spring如何读取。故【@Configuration 常用 @Component也可以但不多,@Service等也可以,很少用罢了,违背spring的设计语义】

 
  
    
    
@Configuration 

@EnableConfigurationProperties(Car.class) public class MyConfig {

private Integer price; 

}

 
  
    
    
@EnableConfigurationProperties(ThreadPoolConfigProperties.class) 

@Configuration public class ThreadPoolConfig

}

 

总结: @EnableConfigurationProperties 只关心所在的类是不是一个 Spring Bean(在 IOC 里)。但是呢 类似ThreadPoolConfig 内部有@Bean注解,会有调用出现。所以不可改为@Component 。

9.ImportSelector

Spring 中用于 动态、条件化导入配置类 的核心接口

Spring Boot 自动配置(@EnableAutoConfiguration) 的底层灵魂

与 @Import 对比

  • 静态 @Import(XXX.class):编译时就写死要导入的类。
  • ImportSelector运行时 通过代码逻辑(判断环境、配置、类存在与否)动态决定导入哪些类。
 
   
     
     
package org.springframework.context.annotation; 

public interface ImportSelector {

/ * 核心方法:返回需要导入的类的全限定名数组 * @param importingClassMetadata 被@Import标注的类的所有注解信息(可读取注解属性) * @return 要导入的@Configuration类/组件的全类名数组 */ String[] selectImports(AnnotationMetadata importingClassMetadata); 

}

 

执行时机(非常重要)

selectImports 方法在 Spring 容器启动、Bean 实例化之前 被调用。

  • 时机:早于 @Bean@ComponentScan
  • 作用:决定哪些类会被注册成 BeanDefinition ,进而实例化为 Bean
  • 当 Spring 解析到 @Import(YourSelector.class) 注解时,会立即 实例化 YourSelector 并调用其 selectImports() 方法。
  • 特点 :它的执行优先级非常高,发生在处理当前配置类中的 @Bean@ImportResource 等其他注解之前 。因此,在 selectImports() 方法中,你无法感知到由 @Bean 定义的 Bean。

DeferredImportSelector后执行 接口方式 【主要用于动态获取bean @Import注解场景】

两者区别:

特性 ImportSelector DeferredImportSelector 执行时机 立即执行,在解析配置类时触发。 延迟执行,在所有配置类处理完毕后触发。 感知范围 无法感知 @Bean 定义的 Bean。 可以感知所有已加载的 Bean 定义和配置。 主要用途 根据简单条件(如注解属性)动态导入配置。 根据完整的上下文信息(如某个 Bean 是否存在)进行更复杂的动态导入。 排序支持 不支持。 支持通过 @OrderOrdered 接口排序。
 
  
    
    
 3.1.//定义实现类实现接口ImportSelector 

public class MyImportSelector implements DeferredImportSelector ;

} 

}//注意:String[] selectImports 方法内可以根据开发者逻辑返回不同类的全限定名!!

 3.2//在配置类上导入实现类 

@Configuration @Import(MyImportSelector.class) public class MyConfiguration { @Bean

public Object test() { log.info("MyConfiguration create a object bean..."); return new Object(); } 

}

 3.3配置类样式 

@Slf4j public class MyConfiguration3 {

public MyConfiguration3() { log.info("MyConfiguration3 construct..."); } public void execute() { log.info("MyConfiguration3 execute..."); } 

} 3.4 调用 @SpringBootApplication public class XXApplication }

 
  
    
    

  • MyConfiguration create a object bean…
  • MyConfiguration1 construct…
  • MyConfiguration2 construct…
  • MyConfiguration3 construct…
  • MyConfiguration3 execute…

原因:Spring 首先解析 MyConfiguration 类。虽然发现了 @Import,但因为它是 DeferredImportSelector,Spring 会先搁置它,转而去注册当前类中定义的 test() Bean。因此,@Bean 方法会最先执行。

类似场景:ImportBeanDefinitionRegistrar 接口方式 [定义注册器]

#扩展:AnnotationMetadata这个类 [做一个分布式任务调度的框架,如果结合springboot,那么在做一些自定义配置的时候就好很多]

1.定义注解

@Target(ElementType.TYPE)

@Retention(RetentionPolicy.RUNTIME)

@Documented

@Inherited

@Import(MyHttpDeferredImportSelector.class)

public @interface MyHttp {

String name() default "";

String value() default "";

}

2.注解实现类

@Slf4j

public class MyHttpDeferredImportSelector implements DeferredImportSelector ,v:{}",k,String.valueOf(v));

});

return new String[0];

}//结果 MyConfiguration1全类名, name:myc1, MyConfiguration1全类名, value:myc1-value

}

3.使用注解

@Slf4j

@MyHttp(name = "myc1",value = "myc1-value")

public class MyConfiguration1

public void execute()

}

小讯
上一篇 2026-04-13 11:12
下一篇 2026-04-13 11:10

相关推荐

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容,请联系我们,一经查实,本站将立刻删除。
如需转载请保留出处:https://51itzy.com/kjqy/259934.html