Spring Boot 用来快速创建可以独立运行的 Spring 应用。它负责整理依赖、自动配置常用组件,并内置 Web 服务器,让我们不必先搭建一套复杂的 Java Web 运行环境。
这篇文章从一台没有 Java 开发环境的电脑开始,创建一个 Maven 项目,运行应用,再完成一个返回 JSON 的心跳检测接口。
1. 环境准备
Spring Boot 本身通常不需要全局安装。开发时真正需要安装的是 JDK,Spring Boot 则作为项目依赖写入 pom.xml,由构建工具下载和管理。
本文使用 Java 21。Spring Boot 4.1.1 至少需要 Java 17,并支持到 Java 26;Java 21 是长期支持版本,适合作为学习和项目开发环境。版本要求可以在 Spring Boot System Requirements 中确认。
根据你的操作系统选择一种 JDK 安装方式:
1brew install --cask temurin@21
安装完成后,重新打开终端并检查 Java 运行器与编译器:
1java -version2javac -version
两条命令都应该显示 21。java 用来运行编译后的程序,javac 用来编译 Java 源码;如果只有 java 而没有 javac,通常说明安装的是 JRE,而不是开发所需的完整 JDK。
编辑器可以使用 IntelliJ IDEA,也可以使用安装了 Java 与 Spring 扩展的 Visual Studio Code。编辑器只负责提高编码体验,不影响下面的命令行操作。
2. 创建项目
打开 Spring Initializr,按照下面的配置创建项目:
| 配置项 | 选择或填写的值 | 作用 |
|---|---|---|
| Project | Maven | 使用 Maven 管理依赖和构建任务 |
| Language | Java | 使用 Java 编写项目 |
| Spring Boot | 默认稳定版 | 本文核对时为 4.1.1 |
| Group | cn.usehook | 项目组织标识,也是包名的一部分 |
| Artifact | spring | 项目和构建产物的名称 |
| Packaging | Jar | 生成可以独立运行的 JAR 文件 |
| Java | 21 | 与刚刚安装的 JDK 保持一致 |
| Dependencies | Spring Web | 提供 Spring MVC、JSON 转换与内嵌 Tomcat |
点击 Generate 下载 spring.zip,然后解压并进入项目目录:
1unzip spring.zip2cd spring
Initializr 已经把 Spring Boot 版本和 Web 依赖写入 pom.xml。其中最关键的部分如下:
01<parent>02<groupId>org.springframework.boot</groupId>03<artifactId>spring-boot-starter-parent</artifactId>04<version>4.1.1</version>05<relativePath />06</parent>0708<groupId>cn.usehook</groupId>09<artifactId>spring</artifactId>10<version>0.0.1-SNAPSHOT</version>1112<properties>13<java.version>21</java.version>14</properties>1516<dependencies>17<dependency>18<groupId>org.springframework.boot</groupId>19<artifactId>spring-boot-starter-webmvc</artifactId>20</dependency>21<dependency>22<groupId>org.springframework.boot</groupId>23<artifactId>spring-boot-starter-webmvc-test</artifactId>24<scope>test</scope>25</dependency>26</dependencies>
spring-boot-starter-parent 统一管理常用依赖和插件版本,因此两个 Starter 都不需要再单独填写版本。spring-boot-starter-webmvc 提供应用运行所需的 Spring MVC、JSON 序列化和默认内嵌 Tomcat;spring-boot-starter-webmvc-test 只在测试阶段使用。Starter 不是一个完整框架副本,而是一组经过协调的依赖集合。
3. 项目结构
在编写接口之前,先看清 Initializr 生成的关键目录。下面额外列出了稍后要创建的 HealthController.java:
入口文件 Application.java 已经由 Initializr 创建:
01package cn.usehook.spring;0203import org.springframework.boot.SpringApplication;04import org.springframework.boot.autoconfigure.SpringBootApplication;0506@SpringBootApplication07public class Application {0809public static void main(String[] args) {10SpringApplication.run(Application.class, args);11}12}
@SpringBootApplication 是应用的核心注解。它会启用自动配置,并从 cn.usehook.spring 包开始扫描 Spring 组件。因此,后面创建的 controller 子包也会被自动发现,不需要手动注册。
4. 启动应用
项目自带 Maven Wrapper,所以不需要在电脑上额外安装 Maven。Wrapper 会读取项目固定的 Maven 配置,并在第一次运行时下载所需版本。
1./mvnw spring-boot:run
当终端中出现类似下面的信息时,应用已经启动:
1Tomcat started on port 8080 (http)2Started Application
Spring Boot 默认在 http://localhost:8080 启动内嵌 Tomcat。此时访问根路径会得到 404,这是正常现象,因为项目里还没有定义任何请求路径。需要停止应用时,在终端按 Ctrl + C。
5. 心跳检测接口
心跳检测接口用来确认应用是否正在运行,以及浏览器能否连接到它。在 src/main/java/cn/usehook/spring 下创建 controller 目录,再创建 HealthController.java:
01package cn.usehook.spring.controller;0203import org.springframework.web.bind.annotation.CrossOrigin;04import org.springframework.web.bind.annotation.GetMapping;05import org.springframework.web.bind.annotation.RequestMapping;06import org.springframework.web.bind.annotation.RestController;0708@RestController09@RequestMapping("/api/v1")10@CrossOrigin(origins = "*")11public class HealthController {1213@GetMapping("/health")14public HealthResponse health() {15HealthData data = new HealthData("UP", "spring");16return new HealthResponse(0, "success", data);17}1819public record HealthResponse(int code, String message, HealthData data) {}2021public record HealthData(String status, String service) {}22}
这段代码完成了从请求路径到 JSON 响应的完整映射:
@RestController把类注册为 Web 控制器,方法返回值会直接写入响应体。@RequestMapping("/api/v1")为这个类中的接口添加统一前缀。@CrossOrigin(origins = "*")允许本文的网页案例跨域请求本地接口。这个接口只返回公开的运行状态,因此示例中允许所有来源。@GetMapping("/health")表示health()处理GET /api/v1/health请求。HealthResponse和HealthData是只保存响应数据的 Javarecord,Spring 会通过 Jackson 将它们转换为 JSON。
最终路径由类上的 /api/v1 与方法上的 /health 拼接而成。status 使用 UP 表示服务正在运行,service 用来标识当前应用。
控制器位于入口类包的子包中,这一点很重要。默认组件扫描以 Application 所在包为起点;如果把控制器放到完全无关的包中,Spring 就不会自动发现它。
6. 访问接口
保存代码后重新启动应用,然后在浏览器访问:
1http://localhost:8080/api/v1/health
接口会返回:
1{2"code": 0,3"message": "success",4"data": {5"status": "UP",6"service": "spring"7}8}
本文页面与本地 Spring Boot 应用使用不同的来源:页面来自课程站点,接口来自 localhost:8080。浏览器默认禁止跨来源读取响应,所以控制器中的 @CrossOrigin 不能省略。完成代码并启动 Spring Boot 后,可以通过下面的案例发起真实请求:
案例顶部会每隔一段时间检测本地接口是否可用。显示“心跳正常”后,点击“发送请求”,下方响应区域就会显示 Spring Boot 返回的 JSON 和本次请求耗时。
也可以在终端中发起请求:
1curl http://localhost:8080/api/v1/health
一次请求会依次经过内嵌 Tomcat、Spring MVC 的路由匹配、health() 方法和 Jackson JSON 序列化,最后成为客户端收到的 HTTP 响应。我们只编写了控制器,其他环节由 Spring Boot 根据 Starter 自动配置完成。
7. 打包运行
开发阶段可以使用 spring-boot:run,准备交付时则把项目打包成可执行 JAR:
1./mvnw clean package2java -jar target/spring-0.0.1-SNAPSHOT.jar
clean package 会编译源码、运行测试,并在 target 目录生成 JAR。这个文件已经包含应用依赖和内嵌服务器,只要目标机器装有兼容的 Java,就可以使用 java -jar 启动,不需要另外部署 Tomcat。