Spring Boot 入门
Spring Boot 介绍
Spring Boot 是 Java 世界中最流行的应用程序构建框架。Spring Boot 是一种基于约定而非配置的方法,用于构建基于 Spring 框架的应用程序。
使用 Spring Boot,你可以构建单体应用程序、微服务、serverless 应用程序、批处理应用程序等不同类型的应用程序。
让我们快速了解一下 Spring Boot 有哪些关键功能使其如此受欢迎。
Spring Boot 关键特性
自动配置
Spring Boot 对应用程序有自己的约定,它会根据默认约定自动配置组件(又称 Bean),而不需要你显式配置所有内容。不过,如果需要,你可以通过各种方式自定义或覆盖 Bean 配置。
例如,如果添加 spring-boot-starter-data-jpa
依赖,它将添加 Hibernate 作为 JPA 实现,因为它是最常用的 JPA 提供程序。此外,Spring Boot 还会自动配置使用 Spring Data Jpa 所需的组件,如 DataSource
、EntityManagerFactory
、PlatformTransactionManager
等。如果 classpath 中存在内存 JDBC 驱动程序(如 H2
或 HSQL
),那么 Spring Boot 将自动配置基于内存的数据源。
如果要使用 MySQL
、Postgresql
等非内存数据库,可以添加相应的 JDBC 驱动程序 jar,并在 application.properties
文件中配置 JDBC 连接参数。然后,Spring Boot 将使用这些属性来配置 DataSource
Bean,而不是使用默认的内存数据库。你甚至可以使用 @Bean
注解自行配置 DataSource
Bean,然后 Spring Boot 将回退并使用你配置的 DataSource
Bean,而不是自动配置。
有了 Spring Boot 的自动配置功能,对 Spring 应用程序配置的需求就大大减少了。
约定大于配置
Spring Boot 依靠各种默认约定来自动配置应用程序。
例如,在大多数基于 Spring(不是基于 Spring Boot)的应用程序中,我们使用配置属性并注册 PropertySourcesPlaceholderConfigurer
Bean。在 Spring Boot 中,你可以将配置属性放在 src/main/resources/application.properties
文件中,Spring Boot 将自动注册 PropertySourcesPlaceholderConfigurer
Bean,并加载该文件中的属性。你不必明确指定属性文件名。
同样,你可能希望根据环境(dev
、qa
、staging
、prod
)为属性配置不同的值。你可以在 application-{profile}.properties
中配置配置文件属性,其中配置文件可以是 dev
、qa
、staging
和 prod
。然后,只需启用所需的配置文件,Spring Boot 就能从特定的配置文件属性文件中读取值。
Spring Boot 非常灵活,可以根据项目或团队的偏好自定义这些约定。
依赖的版本管理
通常情况下,Spring Boot 应用程序继承自 spring-boot-starter-parent
,而 spring-boot-starter-parent
已配置了所有兼容的依赖的版本,因此你不必再检查哪个依赖的版本与哪个版本的 Spring 兼容。你可以查看 org.springframework.boot:spring-boot-dependencies
模块的 pom.xml
,了解预先配置的所有依赖。
生产准备就绪的监控功能
监控是任何在生产中运行的应用程序的一个重要方面。Spring Boot 通过 Actuator
提供了生产就绪监控功能。你可以通过 Actuator REST 端点获取内存使用情况、磁盘空间、各种组件的健康检查等应用程序运行时信息。Actuator 在运行状态下使用 Micrometer
,你可以使用它将所有这些应用程序指标导出到各种监控服务,如 Prometheus
、Datadog
、Influx
等。
嵌入式服务器的支持
传统上,基于 Java 的 web 应用程序是以 war 文件的形式构建的,然后部署到 servlet 容器或 Tomcat、Wildfly、WebSphere 等应用服务器上。更现代的方法是将服务器运行时嵌入到应用程序本身,这样就可以直接运行应用程序,而无需从外部安装和配置服务器。
Spring Boot 支持嵌入 Tomcat、Jetty、Undertow 等 servlet 容器,你可以,以独立于服务器的方式定制各种服务器属性。Spring Boot 还提供各种特定于服务器的自定义属性。
Spring 生态
Spring Boot 拥有庞大的项目生态系统,可支持各种类型的应用程序。
- SpringMVC 和 Spring WebFlux:你可以使用 SpringMVC 或 Spring WebFlux 构建传统的 web 应用程序和 REST API。
- Spring Data:Spring Data 为 ORM 和 NoSQL 数据访问库提供了高级抽象,因此你无需重复实现模板化的 CRUD 操作。
- Spring Security:你可以使用 Spring Security 实现身份验证和授权。它还支持实现基于 OAuth 2.0 的认证和授权。
- Spring Batch:你可以使用 SpringBatch 构建强大的批处理应用程序
- Spring Integration:Spring Integration 实现了许多企业集成模式,可用于与第三方服务集成。
- Spring Cloud:Spring Cloud 支持按照 12 要素应用程序 原则构建云原生应用程序。
- Spring Cloud Streams:你可以构建数据管道,处理 Kafka 等基于流的数据源。
还有更多有趣的项目。更多 Spring 生态系统项目,请参见 https://spring.io/projects。
让我们使用 Spring Boot 构建一个简单的 REST API 应用程序,并探索它的一些功能。
创建 Spring Boot 应用
可以使用 Spring Initializr 或 Spring Tool 或带有 Spring Boot Plugin 的 IntelliJ IDEA 或 NetBeans IDE 创建 Spring Boot 应用程序。
我们将使用 Spring Initializr 并提供以下项目元数据。
- Project: Maven Project
- Language: Java
- Spring Boot: 3.1.2
- Project Metadata:
- Group: com.sivalabs
- Artifact: spring-boot-helloworld
- Name: spring-boot-helloworld
- Description: Spring Boot HelloWorld
- Package name: com.sivalabs.helloworld
- Packaging: jar
- Java: 17
- 点击 ADD DEPENDENCIES,添加 Spring Web, Lombok starter。
- 点击 GENERATE。
生成的 Spring Boot 应用程序将被下载到本地。你可以解压缩并将项目导入你的 IDE。我将使用 IntelliJ IDEA,但你也可以使用任何你喜欢的 IDE。
使用 Spring Boot 开发简单的 REST API
我们要构建的是一个简单的 REST API,其中有一个端点 GET /api/hello?name={name}
,返回 JSON 响应 { "greeting" : "Hello {name}"}
。我们不想硬编码问候语前缀 "Hello"
,而是希望它是可配置的。
让我们从创建响应 model 类 GreetingResponse
开始,如下所示:
// src/main/java/com/sivalabs/helloworld/GreetingResponse.java
record GreetingResponse(String greeting){}
接下来,创建 ApplicationProperties
类来绑定应用程序配置参数。
// src/main/java/com/sivalabs/helloworld/ApplicationProperties.java
import lombok.Getter;
import lombok.Setter;
import org.springframework.boot.context.properties.ConfigurationProperties;
@ConfigurationProperties(prefix = "app") // (1)
@Setter
@Getter
public class ApplicationProperties {
private String greeting = "Hello";
private String defaultName = "World";
}
- 我们将
application.properties
文件中带有通用前缀app.
的属性绑定到ApplicationProperties
类字段中。
创建 GreetingService
并实现 sayHello(String name)
方法如下:
// src/main/java/com/sivalabs/helloworld/GreetingService.java
import lombok.RequiredArgsConstructor;
import org.springframework.stereotype.Service;
@Service // (1)
@RequiredArgsConstructor // (2)
public class GreetingService {
private final ApplicationProperties properties; // (3)
public String sayHello(String name) {
String s = name == null ? properties.getDefaultName(): name;
return String.format("%s %s", properties.getGreeting(), s);
}
}
- 使用
@Service
注解将GreetingService
声明为 Spring Bean。 - Lombok 的
@RequiredArgsConstructor
注解将生成一个包含所有final
属性的构造函数。在本例中,它将生成一个带有ApplicationProperties
参数的构造函数。 - 注入
ApplicationProperties
实例作为GreetingService
Bean 的依赖。
创建 HelloWorldController
并实现 GET /api/hello
API 端点,如下所示:
// src/main/java/com/sivalabs/helloworld/HelloWorldController.java
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
@RestController // (1)
@RequiredArgsConstructor
@Slf4j // (2)
public class HelloWorldController {
private final GreetingService greetingService;
@GetMapping("/api/hello") // (3)
public GreetingResponse sayHello(
@RequestParam(name = "name", required = false) String name) {
log.info("Say Hello to Name: {}", name);
String greeting = greetingService.sayHello(name);
return new GreetingResponse(greeting);
}
}
- 将类声明为 Spring Controller,并带有 request handler 方法。
- 使用 Lomkok 的
@Slf4j
注解自动创建 SLF4J Logger 实例,而不是手动创建private static final Logger log = LoggerFactory.getLogger(HelloWorldController.class);
sayHello()
方法被注解为@GetMapping("/api/hello")
,表示它是HTTP GET /api/hello
URL 的请求处理方法。
让我们在 src/main/resources/application.properties
中配置如下属性:
app.greeting=Hello
app.default-name=World
最后,我们需要使用 @EnableConfigurationProperties
启用配置属性绑定,如下所示:
// src/main/java/com/sivalabs/helloworld/SpringBootHelloWorldApplication.java
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
@SpringBootApplication
@EnableConfigurationProperties({ApplicationProperties.class}) // (1)
//@ConfigurationPropertiesScan // (2)
public class SpringBootHelloWorldApplication {
public static void main(String[] args) {
SpringApplication.run(SpringBootHelloWorldApplication.class, args);
}
}
- 明确启用
ApplicationProperties
类的配置属性绑定。如果有更多这样的配置绑定类,我们可以一一列出。 - 我们可以使用
@ConfigurationPropertiesScan
注解来扫描所有带有@ConfigurationProperties
注解的类,而不是显式地指定所有配置绑定类。
我们只需运行 SpringBootHelloWorldApplication
中的 main()
方法,就能在 IDE 中运行应用程序。
使用 Maven 和 Gradle 运行程序
Spring Boot Maven 和 Gradle 插件提供了无需构建构件(jar 或 war)即可运行应用程序的功能。
Maven:
./mvnw spring-boot:run
Gradle:
./gradlew bootRun
以 FatJar 方式运行程序
我们可以将 Spring Boot 应用程序构建为 fat-jar,然后使用 java -jar
命令运行它。
Maven:
$ ./mvnw clean package
$ java -jar target/spring-boot-helloworld-0.0.1-SNAPSHOT.jar
Gradle:
$ ./gradlew clean build
$ java -jar build/libs/spring-boot-helloworld-0.0.1-SNAPSHOT.jar
我们可以使用 cURL 对 API 端点进行如下验证:
$ curl http://localhost:8080/api/hello
{"greeting":"Hello World"}
$ curl http://localhost:8080/api/hello?name=Siva
{"greeting":"Hello Siva"}
总结
我们已经了解了 Spring Boot、其生态系统和一些核心功能,并且使用 Spring Boot 创建了一个简单的 REST API,并使用 cURL 进行了测试。
参考:https://www.sivalabs.in/getting-started-with-spring-boot/