@xxx叫"注解"(Annotation)它本身不是代码逻辑,而是一个"标签" 。你可以在类、方法、字段上贴标签,然后让别人(框架、编译器)根据标签做相应的事。
一个生活化的类比:
快递箱上贴着"易碎品🈲️倒置"的标签。标签本身不会保护箱子,但搬运工人(框架)看到标签就会轻拿轻放。注解就是贴在代码上的标签,框架就是看标签干活的工人。
本文把SpringBoot常用注解按启动入口、配置注入、Bean注册、AOP、Web、事务、条件装配、测试八大维度整理,采用多表格汇总,区分Spring原生注解与SpringBoot扩展注解,附带作用、使用场景与注意事项,便于查阅与面试复盘。
前言
SpringBoot本质是Spring + 自动配置 + starters ,大量注解是对Spring原生注解的封装增强。很多注解容易混淆:@Component / @Configuration / @Bean、@Value / @ConfigurationProperties、@Conditional系列。本文做结构化全景整理。
区分说明: ✅ Spring原生注解:Spring Core 自带 🚀 SpringBoot扩展注解:Boot新增,用于自动配置、条件装配
一、应用启动类注解(程序入口)
| 注解 | 归属 | 核心作用 | 使用场景 | 注意事项 |
|---|---|---|---|---|
@SpringBootApplication |
🚀 Boot | 启动类复合注解,组合 3 个注解 | main 启动类 | 等价 @Configuration + @EnableAutoConfiguration + @ComponentScan |
@Configuration |
✅ Spring | 标记当前类为配置类,内部可写 @Bean | 自定义 Bean 配置类 | 配置类会被 CGLIB 代理,方法调用会走容器单例 |
@EnableAutoConfiguration |
🚀 Boot | 开启 SpringBoot 自动装配,根据 classpath 自动创建 Bean | 嵌入在 @SpringBootApplication | 自动装配由 META-INF/spring.factories(Boot2)/ META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports(Boot3)驱动 |
@ComponentScan |
✅ Spring | 组件扫描,自动扫描@Component/@Service/@Repository/@Controller |
扫描指定包下 Bean | 默认扫描当前类所在包及子包;可通过 basePackages 自定义扫描路径 |
@EnableConfigurationProperties |
🚀 Boot | 开启配置属性绑定,把配置文件映射到 Properties 类 | 自定义配置属性类 | 需要配合@ConfigurationProperties使用 |
源码拆解:
@SpringBootApplication是复合注解,不是魔法注解,只是简化开发。
二、Bean注册与实例化注解(对象交给Spring容器管理)
| 注解 | 归属 | 核心作用 | 使用场景 | 注意事项 |
|---|---|---|---|---|
@Component |
✅ Spring | 通用组件,标记类交给Spring实例化 | 通用工具类、普通业务组件 | 元注解,@Service/@Controller/@Repository都是它的派生注解 |
@Service |
✅ Spring | 业务层组件,语义化@Component | Service业务逻辑层 | 仅语义区分,底层和@Component无差别 |
@Repository |
✅ Spring | 数据访问层组件 | Mapper、DAO层 | 额外开启异常转译:数据库异常转为Spring DataAccessException |
@Controller |
✅ Spring | MVC控制器,返回视图 | 传统Thymeleaf等页面控制器 | 返回页面,不直接返回JSON;返回JSON建议用RestController |
@RestController |
🚀 Boot | 复合注解 @Controller + @ResponseBody |
REST接口控制器 | 方法返回值直接序列化为JSON,不跳转页面 |
@Bean |
✅ Spring | 在配置类中,将方法返回对象注册为Bean | 第三方类(无法加@Component的类) | 默认方法名=beanName;可用@Bean("customName")指定名称;默认单例 |
@Scope |
✅ Spring | 指定Bean作用域 | 多实例场景 | singleton单例、prototype多例、request、session、application |
@Lazy |
✅ Spring | 延迟初始化Bean | 启动优化、解决循环依赖 | 默认启动时创建Bean;加@Lazy,第一次使用才实例化 |
@Primary |
✅ Spring | 多个同类型Bean冲突时,优先选用此Bean | 同接口多实现类 | 解决NoUniqueBeanDefinitionException |
@Qualifier |
✅ Spring | 根据Bean名称精准注入 | 同接口多个实现,配合@Autowired | 必须和@Autowired一起使用,指定beanName |
三、配置文件属性注入注解(yml/properties读取)
| 注解 | 归属 | 核心作用 | 使用场景 | 注意事项 |
|---|---|---|---|---|
@Value("${key}") |
✅ Spring | 读取单个配置项注入属性 | 少量零散配置 | 不支持复杂对象、不支持校验;SpEL支持#{} |
@ConfigurationProperties(prefix = "xxx") |
🚀 Boot | 批量绑定配置文件前缀,映射到实体类 | 一组相关配置(数据库、线程池) | 需要setter或者record(Boot3);支持JSR303校验 |
@Validated |
✅ Spring | 开启属性校验,配合JSR303注解 | 配置类参数合法性校验 | 需要引入validation依赖 |
@PropertySource |
✅ Spring | 加载外部properties配置文件 | 自定义配置文件 | 默认不加载yml,只能加载properties;Boot环境优先使用application.yml |
对比要点: 少量配置用
@Value;一组结构化配置优先@ConfigurationProperties,类型安全,IDE有配置提示。
四、依赖注入注解(Bean之间装配)
| 注解 | 归属 | 核心作用 | 使用场景 | 注意事项 |
|---|---|---|---|---|
@Autowired |
✅ Spring | 按类型自动注入Bean | 字段、构造器、setter注入 | Spring原生;默认required=true,找不到Bean直接报错;@Autowired(required=false)允许null |
@Inject |
✅ JSR规范 | JSR330标准注入注解,等价@Autowired | 规范兼容场景 | 需要额外引入javax.inject包 |
@Resource |
✅ JSR规范 | JSR250注解,默认按名称,找不到再按类型 | 名称优先注入 | Java原生规范,不是Spring注解 |
推荐最佳实践:构造器注入 ,Spring4.3之后,如果类只有一个构造器,
@Autowired可省略。
五、Web层SpringMVC核心注解(REST接口开发)
| 注解 | 归属 | 核心作用 | 使用场景 | 注意事项 |
|---|---|---|---|---|
@RequestMapping |
✅ SpringMVC | 通用请求映射,可指定method、path | 类/方法级别路由 | 派生注解:@Get/Post/Put/DeleteMapping |
@GetMapping |
✅ SpringMVC | GET请求映射 | 查询接口 | 仅接收GET |
@PostMapping |
✅ SpringMVC | POST请求映射 | 新增接口 | 提交表单/JSON |
@PutMapping |
✅ SpringMVC | PUT请求映射 | 全量更新接口 | 幂等更新 |
@DeleteMapping |
✅ SpringMVC | DELETE请求映射 | 删除接口 | 部分前端不支持DELETE,可考虑POST代理 |
@RequestParam |
✅ SpringMVC | 获取URL查询参数 ?name=xxx | 获取GET查询参数 | 对应url?后面参数;可设置required、defaultValue |
@PathVariable |
✅ SpringMVC | 获取路径占位符 /user/{id} | REST风格路径变量 | 路径中的变量 |
@RequestBody |
✅ SpringMVC | 将请求体JSON反序列化为Java对象 | POST提交JSON | POST请求体,GET无请求体 |
@RequestHeader |
✅ SpringMVC | 获取HTTP请求头 | 读取token、客户端信息 | 读取header字段 |
@RequestPart |
✅ SpringMVC | 文件上传 + JSON混合提交 | multipart/form-data | 文件上传场景,搭配MultipartFile |
@ResponseBody |
✅ SpringMVC | 返回对象序列化为JSON | 接口返回数据 | @RestController内置该注解 |
@CrossOrigin |
✅ SpringMVC | 解决跨域CORS | 前后端分离跨域 | 推荐网关统一配置,不建议每个Controller加注解 |
六、事务相关注解(Spring声明式事务)
| 注解 | 归属 | 核心作用 | 使用场景 | 注意事项 |
|---|---|---|---|---|
@Transactional |
✅ Spring | 开启声明式事务 | Service层数据库操作 | 底层AOP动态代理;仅public方法生效;内部方法调用事务失效 |
@EnableTransactionManagement |
✅ Spring | 开启事务管理 | Boot一般自动开启,自定义场景使用 | SpringBoot引入jdbc/MyBatis starter默认自动开启,无需手动写 |
事务失效高频坑:
- 非public方法;2. 同类内方法自调用;3. 异常被try-catch捕获不抛出;4. 数据库引擎不支持事务(MyISAM)。
七、条件装配注解(SpringBoot自动配置核心,🚀Boot)
这是SpringBoot最特色的一组注解,满足条件才创建Bean,自动装配底层就是大量Conditional注解。
| 注解 | 归属 | 核心作用 | 使用场景 |
|---|---|---|---|
@ConditionalOnClass |
🚀 Boot | classpath存在指定类,才实例化Bean | 存在某个依赖才启用配置 |
@ConditionalOnMissingClass |
🚀 Boot | classpath不存在指定类,才实例化Bean | 不存在依赖才启用 |
@ConditionalOnBean |
🚀 Boot | 容器存在指定Bean,才实例化 | 依赖容器中已有Bean |
@ConditionalOnMissingBean |
🚀 Boot | 容器没有该Bean,才实例化(用户自定义优先) | 自定义Bean覆盖Boot默认Bean,最常用 |
@ConditionalOnProperty |
🚀 Boot | 配置文件存在指定key,且匹配value | 通过开关控制组件启用 xxx.enable=true |
@ConditionalOnResource |
🚀 Boot | 类路径存在指定资源文件才生效 | 判断配置文件是否存在 |
@ConditionalOnWebApplication |
🚀 Boot | 当前是Web环境才生效 | Web相关自动配置 |
@ConditionalOnNotWebApplication |
🚀 Boot | 非Web环境生效 | 纯后台任务、客户端程序 |
重点:
@ConditionalOnMissingBean是扩展SpringBoot默认行为最核心注解,用户自己定义Bean会覆盖Boot默认Bean。
八、AOP切面注解(Spring AOP)
| 注解 | 归属 | 核心作用 | 使用场景 | 注意事项 |
|---|---|---|---|---|
@EnableAspectJAutoProxy |
✅ Spring | 开启AOP代理支持 | 使用切面功能 | SpringBoot默认开启,一般不用手动加;可设置proxyTargetClass=true强制CGLIB |
@Aspect |
✅ AspectJ | 标记当前类为切面类 | 日志、鉴权、埋点切面 | 类上标记,配合@Before/@After等通知 |
@Pointcut |
✅ AspectJ | 定义切点表达式,匹配拦截方法 | 复用切点表达式 | execution表达式常用 |
@Before |
✅ AspectJ | 前置通知,方法执行前执行 | 参数校验、日志前置 | |
@AfterReturning |
✅ AspectJ | 正常返回后执行 | 记录返回结果 | 异常时不会执行 |
@AfterThrowing |
✅ AspectJ | 抛出异常时执行 | 异常告警、错误日志 | |
@After |
✅ AspectJ | 最终通知,无论正常/异常都执行 | 资源释放 | |
@Around |
✅ AspectJ | 环绕通知,包裹目标方法,可控制执行 | 性能耗时统计、全链路鉴权 | 功能最强,需要手动调用proceed() |
九、测试相关注解(SpringBoot Test)
| 注解 | 归属 | 核心作用 | 使用场景 |
|---|---|---|---|
@SpringBootTest |
🚀 Boot | 加载完整Spring上下文做集成测试 | 完整服务集成测试,加载所有Bean |
@WebMvcTest |
🚀 Boot | 只加载Web层上下文,mock Controller | Controller单元测试,轻量 |
@MockBean |
🚀 Boot | Mock一个Bean,替换容器内真实Bean | Mock Service依赖,隔离测试 |
@AutoConfigureMockMvc |
🚀 Boot | 自动注入MockMvc,模拟http请求 | 接口单元测试 |
十、高频注解对比汇总表(面试高频)
| 对比项 | 注解1 | 注解2 | 核心差异 |
|---|---|---|---|
| Bean注册 | @Component |
@Bean |
@Component标记类;@Bean写在配置类方法,注册第三方类 |
| 配置注入 | @Value |
@ConfigurationProperties |
@Value单值;@ConfigurationProperties批量绑定前缀,支持对象、校验、IDE提示 |
| Controller | @Controller |
@RestController |
@Controller返回视图;@RestController自带ResponseBody直接返回JSON |
| 注入方式 | @Autowired |
@Resource |
@Autowired:按类型;@Resource:默认按名称(JSR规范) |
| 条件装配 | @ConditionalOnBean |
@ConditionalOnMissingBean |
存在Bean才创建 / 没有Bean才创建(自定义覆盖默认) |
十一、核心注解使用避坑总结
@SpringBootApplication只能放在启动类,扫描范围以当前包为根;业务配置类不要加这个注解。@Transactional只对public方法生效,同类内部调用事务失效。@ConfigurationProperties必须有setter(Boot2);Boot3使用record可以不用setter。@ConditionalOnMissingBean优先级:用户自定义Bean > SpringBoot自动配置Bean,这就是我们覆盖默认组件的原理。- AOP是动态代理,只能拦截Spring容器中的Bean的方法;静态方法、非Bean类方法无法被AOP拦截。
@Lazy延迟加载,只对容器Bean生效,解决启动耗时和循环依赖场景。
十二、一句话总结
SpringBoot注解体系分为两层:Spring原生注解(Bean管理、AOP、事务、MVC) + SpringBoot扩展注解(自动装配、条件注解、配置绑定)。 SpringBoot的核心魔力来自**@EnableAutoConfiguration + @Conditional系列注解**,实现按需装配;业务开发更多使用Bean注册、Web、属性注入注解完成业务编码。