跳到主内容
创建时间: 2026-09-16最后更新: 2026-09-16

上一章介绍的 Maven 配置决定项目使用哪些依赖、如何编译以及如何打包。应用启动以后,还需要另一类配置决定端口、日志级别和心跳接口返回的服务信息。

Spring Boot 的外部化配置让同一份代码和同一个 JAR 可以在不同环境中读取不同参数。本章先集中学习配置文件、占位符、Profile 和覆盖规则;配置怎样进入 Java 对象,将在理解 IoC 与 Spring Bean 后单独讲解。

1. 配置文件

Spring Initializr 通常会在 src/main/resources 中创建 application.properties。Maven 构建时把该目录复制到 classpath,Spring Boot 启动时自动读取其中的应用配置。

Spring Boot 也会检查 JAR 外的配置,常见位置包括应用当前目录及其 config/ 子目录。外部文件可以覆盖 JAR 内的默认值,同一个构建产物因此不必为每套环境重新编译。

常见的三个文件名是:

文件语法关系
application.propertiesJava Properties使用完整的点分隔键名
application.ymlYAML.yml 是 YAML 的常用扩展名
application.yamlYAML与 .yml 使用同一种语法

.yml 和 .yaml 不是两种配置语言,只是文件扩展名不同。一个项目应该选择 application.properties、application.yml 或 application.yaml 中的一种作为主配置,不要在同一位置同时维护多个同名配置来源。

为了让后续章节中的文件名保持一致,心跳项目从本章开始选择 application.yaml。如果项目由 Spring Initializr 生成了空的 application.properties,可以将它改名为 application.yaml,后面只维护这一份主配置。Properties 示例仍用于讲解该语法,不需要同时复制到项目中。

2. Properties

Properties 每一行使用 键=值 表达配置,层级直接写在完整键名中:

src/main/resources/application.properties
1
spring.application.name=spring
2
server.port=8080
3
4
app.health.status=UP
5
app.health.service=spring

spring.application.name、server.port 是 Spring Boot 提供的配置项,app.health.* 是当前项目定义的业务配置。自定义键应使用独立前缀,避免和框架或第三方库的配置重名。

Properties 中的空行可以分隔不同主题,注释使用 # 或 !:

src/main/resources/application.properties
1
# HTTP 服务
2
server.port=8080
3
4
# 心跳接口
5
app.health.status=UP

Properties 没有依靠缩进表示层级,因此移动行时不容易改变结构。配置不多或者希望一眼看到完整键名时,这种格式很直接。

3. YAML

YAML 使用缩进表示层级。下面两份文件内容等价,只应选择其中一个:

application.yml
application.yaml
01
spring:
02
application:
03
name: spring
04
05
server:
06
port: 8080
07
08
app:
09
health:
10
status: UP
11
service: spring

两格缩进表示下一层键,必须使用空格,不能混入 Tab。app.health.status 在 YAML 中被拆成 app、health、status 三层,但 Spring Environment 中的规范配置名仍然是 app.health.status。

YAML 适合层级较多的配置,也能清楚表示列表:

src/main/resources/application.yaml
1
app:
2
health:
3
targets:
4
- spring
5
- postgresql

冒号后的某些值可能被 YAML 解释成布尔值、数字或日期。明确需要字符串时可以加引号。缩进错误则可能把配置放到错误层级,修改后应先检查它是否仍位于预期父键下。

4. 配置项与占位符

项目当前使用下面几项配置:

配置项示例作用
spring.application.namespring标识应用名称
server.port8080设置 HTTP 监听端口
logging.level.rootINFO设置根日志级别
app.health.statusUP心跳检查的默认状态
app.health.servicespring心跳检查的默认服务

配置值可以使用 ${名称} 引用另一个配置,也可以用 ${名称:默认值} 提供回退值:

application.properties
application.yaml
1
spring.application.name=spring
2
server.port=${SERVER_PORT:8080}
3
app.health.status=UP
4
app.health.service=${spring.application.name}

SERVER_PORT 不存在时使用 8080,存在时使用环境提供的值。app.health.service 则复用应用名称,避免同一个值维护两份。

密码和令牌不应在仓库中提供可用默认值,可以只保留环境变量引用:

src/main/resources/application.properties
1
app.external-api-key=${APP_EXTERNAL_API_KEY}

Spring Boot 不会仅因为项目根目录存在 .env 就自动加载它。环境变量应由终端、IDE、容器或部署平台注入。

5. Profile

Profile 用来在公共配置之上叠加环境差异。心跳项目先保留公共文件:

src/main/resources/application.yaml
01
spring:
02
application:
03
name: spring
04
05
server:
06
port: "${SERVER_PORT:8080}"
07
08
app:
09
health:
10
status: UP
11
service: "${spring.application.name}"

然后在同一目录增加环境文件:

application-dev.yaml
application-prod.yaml
1
logging:
2
level:
3
cn.usehook.spring: DEBUG
4
5
app:
6
health:
7
service: spring-dev

激活 dev 时,Spring Boot 先加载公共文件,再使用 application-dev.yaml 中的同名配置覆盖它。Profile 文件应该与主文件保持同一种格式;如果项目选择 Properties,对应名称就是 application-dev.properties 和 application-prod.properties。

可以通过命令行或环境变量激活生产 Profile:

command-line.bash
environment.bash
1
java -jar target/spring-0.0.1-SNAPSHOT.jar --spring.profiles.active=prod

不要在公共配置中固定激活生产 Profile。当前运行环境应由启动命令或部署平台决定。

6. 覆盖顺序

同一个键可能来自多个位置。常见配置来源可以从低到高理解为:

优先级配置来源示例
低JAR 内的应用配置application.yaml
JAR 内的 Profile 配置application-prod.yaml
JAR 外的应用配置config/application.yaml
JAR 外的 Profile 配置config/application-prod.yaml
操作系统环境变量APP_HEALTH_SERVICE
Java 系统属性-Dapp.health.service=spring-system
高命令行参数--app.health.service=spring-command

环境变量名通常由规范键名转换而来:把点替换成下划线、移除连字符,再转换为大写。例如 app.health.service 对应 APP_HEALTH_SERVICE。

terminal.bash
1
java -jar target/spring-0.0.1-SNAPSHOT.jar \
2
--app.health.service=spring-command

排查配置没有生效时,应先确认激活的 Profile,再检查外部文件、环境变量、系统属性和命令行参数。不能只盯着 JAR 内的文件,因为最终值由所有属性来源共同决定。

7. 从配置值到 Java 对象

到这里,配置已经进入 Spring 的 Environment,但业务代码还没有直接读取它。本章有意停在这个边界:现在只需要理解配置来自哪里、怎样分环境以及哪个值最终生效。

下一篇先从变量、数据类型、流程控制和方法开始补齐 Java 语法,再学习类、IoC 和 Spring Bean。具备这些基础以后,「配置绑定」专章会使用 @Value 和 @ConfigurationProperties 把 app.health.* 转换成类型明确的 HealthProperties Bean,并注入 HealthService。这样配置文件语法与对象装配不会混在同一步中。