@RestController @RequestMapping("/api") public class HealthController { @GetMapping("/health") public Map<String, String> health() { return Map.of("status", "ok"); } }@RestController、@RequestMapping、@GetMapping都是注解。Spring 看到不同注解,会决定怎么处理这个类或方法。
@RestController
它是在告诉 Spring:
这个类是一个 REST API Controller,请你管理它,并让它能够接收 HTTP 请求。
Spring Boot 启动时扫描到它,就知道这个类是一个Controller,可以用来接收前端发过来的请求。
@RequestMapping("/api")
意思是:
这个 Controller 里面所有接口,统一先加
/api。
与@GetMapping("/health")拼起来,构成了一个完整的URL:/api/health
@GetMapping("/health")
它告诉 Spring:
当收到一个GET 请求,地址是
/health的时候,就执行这个方法。
浏览器 / Vue
↓
GET /api/health
↓
Spring MVC
找到 HealthController
↓
找到 @GetMapping("/health")
↓
执行 health()
↓
返回 Java Map
↓
Spring 自动转 JSON
↓
{
"status": "ok"
}
以上就是现代 Spring Boot Controller 最基本的工作方式。
Spring MVC之所以能够正确匹配Controller,是因为在Spring Boot启动时,会扫描所有的带有@RestController注解的类,并将所有的类提前登记,就好比Spring MVC在启动时建立了一张“路由表”,当请求发过来的时候,会根据URL查询路由表,找到相同URL对应的类并执行。
Vue 前端
↓
GET /api/health
↓
Tomcat 收到 HTTP 请求
↓
DispatcherServlet
↓
Spring MVC 查“路由表”
↓
发现:
GET /api/health
对应
HealthController.health()
↓
执行 health()
↓
返回数据
这里涉及到一个关键的东西,叫做DispatcherServlet,可以把它理解为Spring MVC的总前台,它会根据额Spring启动时登记好的规则,根绝URL分发给不同的Controller。
GET/POST 叫做HTTP方法,URL 决定“找哪个资源”,HTTP 方法决定“要对这个资源干什么”。
比如:
GET /api/students= 查学生。
POST /api/students= 新增学生。
PUT /api/students/12= 修改 12 号学生。
DELETE /api/students/12= 删除 12 号学生。
前端按钮触发的前端代码决定了HTTP方法的发送。
function createStudent() { axios.post('/api/students', formData) }发送的时POST请求。
URI 是“资源标识符”的总称,URL 是 URI 的一种,专门用来说明资源在哪里、怎么访问。
URI
├─ URL
└─ 其他类型的标识符
比如:
https://example.com/api/students/12这是一个 URL,因为它告诉你:
- 协议:
https - 主机:
example.com - 路径:
/api/students/12
也就是:
这个资源在哪里,以及怎么访问它。
而像:
/api/students/12这种在 Spring 代码里经常写的东西,更准确地说是一个URI 路径,它并没有告诉你主机和协议。
真正开发时,URL、URI、path 这几个词经常被人不那么严格地混着说,只要你知道它们严格意义上不是完全一回事即可。
请求映射注解:
最常见的有 5 个:
| 注解 | HTTP 方法 | 常见含义 | 举例 |
|---|---|---|---|
@GetMapping | GET | 查询 | 查询学生列表 |
@PostMapping | POST | 新增 | 新建学生、提交反馈 |
@PutMapping | PUT | 整体修改 | 修改学生信息 |
@PatchMapping | PATCH | 部分修改 | 只修改学生备注 |
@DeleteMapping | DELETE | 删除 | 删除某条记录 |
例如学生接口:
@RestController @RequestMapping("/api/students") public class StudentController { @GetMapping public List<Student> list() { ... } @PostMapping public Student create() { ... } @PutMapping("/{id}") public Student update() { ... } @DeleteMapping("/{id}") public void delete() { ... } }那么对应关系就是:
GET /api/students → 查询学生 POST /api/students → 新增学生 PUT /api/students/12 → 修改 12 号学生 DELETE /api/students/12 → 删除 12 号学生这里还有一个“老大”:
@RequestMapping它更通用。
所以可以理解成:
@RequestMapping ↓ 简化出了 @GetMapping @PostMapping @PutMapping @PatchMapping @DeleteMapping现在 Spring Boot 项目里,一般优先用后面这些,因为更直观。
Spring 组件/Controller 注解
@RestController
是在告诉 Spring:
这个类是一个 Web Controller,而且它的方法返回的数据通常直接作为 HTTP 响应返回。
@Controller和@RestController有什么区别?
传统 Spring MVC:
@Controller public class StudentController { }@Controller最初主要用于:
返回网页。
比如:
@GetMapping("/students") public String students() { return "students"; }以前可能表示:去找 student.html 或JSP页面。
这在传统“前后端不分离”的 Java Web 项目里非常常见。
但在前后端分离的项目中,Spring Boot 后端基本不负责生成页面,而是返回JSON数据。
可以粗略的理解为@Controller + @ResponseBody = @RestController
@ResponseBody意思是不要把返回值当作网页名称,直接把返回的数据写进 HTTP 响应。
@Service、@Repository、@Compoent:
这些虽然和@RestController不完全属于同一种功能,但你会经常看到它们一起出现。
例如:
@RestController public class StudentController { }表示:
Web 接口层。
然后:
@Service public class StudentService { }表示:
业务逻辑层。
然后:
@Repository public class StudentRepository { }表示:
数据访问层。
还有一个更通用的:
@Component表示:
这是一个普通的 Spring 组件,请 Spring 创建和管理它。
可以暂时认为:
@Component ↑ │ ┌──────┼───────────┐ │ │ │ @Service @Repository @Controller它们本质上都在告诉 Spring:
“这个类你要管起来。”
但是它们表达的职责不同。
一般项目业务逻辑:
例如:
@RestController @RequestMapping("/api/students") public class StudentController { private final StudentService studentService; ... }然后:
@Service public class StudentService { private final StudentRepository studentRepository; ... }可以翻译成:
@RestController StudentController 负责接前端请求 ↓ @Service StudentService 负责业务逻辑 ↓ @Repository StudentRepository 负责数据库整个链路逻辑:
Vue │ │ GET /api/students ↓ @RestController StudentController │ │ @GetMapping ↓ list() │ ↓ @Service StudentService │ ↓ @Repository StudentRepository │ ↓ 数据库以上就是对于一个项目中出现的注解的认识。