@SpringBootApplication
@SpringBootApplication
其实是一个复合注解,简化标识 Spring Boot 应用程序的主类。
主要组合了 @SpringBootConfiguration
、@EnableAutoConfiguration
和@ComponentScan
@SpringBootConfiguration
是 @Configuration 注解的一个形式,表明该类是一个 Spring 配置类,用于定义 Bean。
@EnableAutoConfiguration
-
启用Spring Boot的自动配置机制。自动配置会根据应用程序的依赖项和类路径,自动配置各种常见的Spring配置和功能
-
如果应用中引入了
spring-boot-starter-web
依赖,Spring Boot 会自动为应用配置嵌入式 Tomcat 服务器、MVC 框架等。
SpringBoot 是如何实现自动配置的?
Spring Boot 的自动配置依赖于 META-INF/spring.factories
文件,该文件中列出了所有自动配置类路径。当 Spring Boot 启动时,它会根据 spring.factories
文件中指定的配置类加载相应的自动配置。
org.springframework.boot.autoconfigure.EnableAutoConfiguration=\ org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration,\ org.springframework.boot.autoconfigure.orm.jpa.HibernateJpaAutoConfiguration,\ org.springframework.boot.autoconfigure.web.servlet.WebMvcAutoConfiguration
不过3.0已经废除
-
条件注解(Conditional)
另外自动配置类通常使用 @ConditionalOnClass、@ConditionalOnMissingBean,@ConditionalOnProperty
等条件注解。它们控制自动配置的加载条件,例如仅在类路径中存在某个类时,才加载某些配置
@Configuration @ConditionalOnClass(DataSource.class) // 只有类路径中存在 DataSource 时才生效 public class DataSourceAutoConfiguration { @Bean @ConditionalOnMissingBean // 如果没有自定义 DataSource,则使用默认配置 public DataSource dataSource() { return new HikariDataSource(); } }
@ComponentScan
用于自动扫描并加载应用程序中的组件,例如Controller、Service、等。默认会扫描@SpringBootApplication
注解所在类的包及其子包中的组件,并将它们纳入Spring Boot应用程序的上下文中,使它们可被自动注入和使用
SpringBean相关
@Autowired和@Resource
@Autowired
是Spring框架的提供的,默认情况下是根据类型来查找匹配的Bean。如果应用上下文中存在多个相同类型的Bean,则需要使用 @Qualifier
注解来指定具体的Bean名称。否则会出现异常
@Resource
是JSR-250 提供的,它是Java 的标准的一部分,不仅仅局限于Spring项目中使用。默认按照名称来查找匹配的Bean。
如果指定了name属性,那么就会按照这个名称去寻找Bean,如果没有指定,则默认使用字段名或setter方法参数名作为Bean的名字。
@Component,@Repository,@Service, @Controller
这几个注解可以 把类标识成可用于 @Autowired
注解自动装配的 bean 的类。
-
@Component
:通用的注解,可标注任意类为Spring
组件。如果一个 Bean 不知道属于哪个层,可以使用@Component
注解标注。 -
@Controller
: 对应 Spring MVC 控制层,主要用于接受用户请求并调用 Service 层返回数据给前端页面。 -
@Service
: 对应服务层,主要涉及一些复杂的逻辑,需要用到 Dao 层。 -
@Repository
: 对应持久层即 Dao 层,主要用于数据库相关操作。
@Qualifier
@Qualifier
注解在 Spring 中的主要作用是在依赖注入时消除歧义。
当一个类型有多个实现时,@Qualifier
注解可以指定需要注入哪一个具体的 Bean。通常配合 @Autowired使用,实现按名称注入
@Component public class Client { private final Service service; @Autowired // 指定名称选择对应的实现 Bean public Client(@Qualifier("serviceImpl1") Service service) { this.service = service; } public void doSomething() { service.serve(); } }
@Primary
@Primary
注解用于指定当有多个候选 Bean 时默认注入哪个 Bean,也就是指定了第一顺位。
但@Qualifier 使用时,可以覆盖 @Primary 的默认行为,例如以下这样:
@Component @Primary public class DefaultService implements Service { ... } @Component @Qualifier("specificService") public class SpecificService implements Service { ... } @Component public class Client { private final Service service; @Autowired public Client(@Qualifier("specificService") Service service) { this.service = service; } } //即使 DefaultService 被标记为 @Primary,但由于 @Qualifier("specificService”),所以最终注入的仍然是 SpecificService!
@Bean
@Bean 是一个方法级别的注解,用于在配置类中声明方法,这些方法将返回一个对象,该对象将由 Spring 容器管理。
通过在配置类中使用 @Bean 注解,可以手动定义 Bean 的创建和初始化过程,可以指定 Bean 的作用域、初始化方法、销毁方法等。
适用范围:
-
主要用于Java配置方式,与 XML 配置相对应,通过 Java代码的方式来配置 Spring 应用上下文。
-
比如外部的JDBC Templete RedisTemplete,就可以通过配置类中@Bean写入,交由Spring容器去管理
@Configuration public class AppConfig { @Bean public MyService myService() { return new MyServiceImpl(); } }
@Primary
在 Spring 框架中,@Primary
注解用于标记当存在多个候选 Bean 时,应该优先注入哪一个
当一个接口有多个实现类,并且在注入时未明确指定要注入哪个实现类时Spring 会报错。这时可以使用@Primary
注解来指定一个首选实现类
public interface MyService { void performAction(); } @Component @Primary //使用@Primary public class MyServiceImpl1 implements MyService { @Override public void performAction() { ... } } @Component public class MyServiceImpl2 implements MyService { @Override public void performAction() { ... } }
@Component public class MyComponent { private final