1-4 项目结构
概念解析
标准项目结构
src/
├── main/
│ ├── java/
│ │ └── com/example/demo/
│ │ ├── DemoApplication.java # 启动类
│ │ ├── config/ # 配置类
│ │ ├── controller/ # 控制器
│ │ ├── service/ # 服务层
│ │ │ ├── impl/ # 服务实现
│ │ │ └── UserService.java
│ │ ├── repository/ # 数据访问层
│ │ ├── entity/ # 实体类
│ │ ├── dto/ # 数据传输对象
│ │ ├── vo/ # 视图对象
│ │ ├── mapper/ # MyBatis Mapper
│ │ ├── exception/ # 自定义异常
│ │ └── util/ # 工具类
│ └── resources/
│ ├── application.yml # 主配置文件
│ ├── application-dev.yml # 开发环境
│ ├── application-prod.yml # 生产环境
│ ├── static/ # 静态资源(CSS/JS/图片)
│ └── templates/ # 模板文件(Thymeleaf/Freemarker)
└── test/
└── java/
└── com/example/demo/ # 测试代码
配置文件优先级
Spring Boot 配置文件加载顺序(从高到低):
| 优先级 | 配置文件 | 说明 |
|---|---|---|
| 1 | 命令行参数 | --spring.config.location |
| 2 | OS 环境变量 | SPRING_CONFIG_ADDITIONAL_LOCATION |
| 3 | jar 包外配置文件 | ./config/application.yml |
| 4 | jar 包内配置文件 | classpath:application.yml |
多环境配置切换:
# 通过命令行指定
java -jar app.jar --spring.profiles.active=dev
代码示例
1. 多环境配置文件
application.yml(公共配置)
server:
port: 8080
# 公共配置
spring:
datasource:
driver-class-name: com.mysql.cj.jdbc.Driver
application-dev.yml(开发环境)
spring:
datasource:
url: jdbc:mysql://localhost:3306/dev_db
username: root
password: root
logging:
level:
com.example: DEBUG
application-prod.yml(生产环境)
spring:
datasource:
url: jdbc:mysql://prod-db-server:3306/prod_db
username: ${DB_USER}
password: ${DB_PASSWORD}
logging:
level:
com.example: INFO
2. YAML 配置示例
# 完整配置示例
spring:
application:
name: springboot-demo
profiles:
active: dev
datasource:
url: jdbc:mysql://localhost:3306/demo?useUnicode=true&characterEncoding=utf8
username: root
password: root
driver-class-name: com.mysql.cj.jdbc.Driver
hikari:
maximum-pool-size: 20
minimum-idle: 5
connection-timeout: 30000
jpa:
show-sql: true
hibernate:
ddl-auto: update
properties:
hibernate:
format_sql: true
redis:
host: localhost
port: 6379
password: ${REDIS_PASSWORD:}
database: 0
timeout: 3000
server:
port: 8080
servlet:
context-path: /api
tomcat:
threads:
max: 200
min-spare: 10
logging:
level:
root: INFO
com.example: DEBUG
pattern:
console: "%d{yyyy-MM-dd HH:mm:ss} [%thread] %-5level %logger{36} - %msg%n"
3. Properties 配置转换
YAML 转 Properties 示例:
# application.properties 等价于上面的 YAML
spring.application.name=springboot-demo
spring.profiles.active=dev
# 数据源配置
spring.datasource.url=jdbc:mysql://localhost:3306/demo
spring.datasource.username=root
spring.datasource.password=root
spring.datasource.driver-class-name=com.mysql.cj.jdbc.Driver
# JPA 配置
spring.jpa.show-sql=true
spring.jpa.hibernate.ddl-auto=update
spring.jpa.properties.hibernate.format_sql=true
# 端口
server.port=8080
4. 自定义配置文件
读取自定义配置:
# application.yml
app:
name: demo
version: 1.0.0
features:
- login
- register
// 方式一:@ConfigurationProperties(推荐)
@Component
@ConfigurationProperties(prefix = "app")
@Data
public class AppProperties {
private String name;
private String version;
private List<String> features;
}
// 方式二:@Value
@Value("${app.name}")
private String appName;
常见坑点
⚠️ 坑 1:配置文件乱码
问题:YAML 中中文乱码
解决:
- 确保 IDEA 设置为 UTF-8
- 或使用 Unicode 转义:
app.name: \u6D4B\u8BD5
⚠️ 坑 2:多环境激活失败
问题:application-dev.yml 没有被激活
排查:
# 检查启动日志中的 active profiles
# 应该显示:The following profiles are active: dev
常见错误:
# 错误写法
spring:
profile: dev # 应该是 profiles
# 正确写法
spring:
profiles:
active: dev
⚠️ 坑 3:@ConfigurationProperties 不生效
问题:注入的配置值为 null
解决:
// 1. 确保有 @EnableConfigurationProperties
@SpringBootApplication
@EnableConfigurationProperties(AppProperties.class)
public class SpringBootApplication { }
// 2. 或者添加 @Component
@Component
@ConfigurationProperties(prefix = "app")
public class AppProperties { }
⚠️ 坑 4:resources 下文件找不到
问题:classpath:mapper/UserMapper.xml 找不到
解决:确保 pom.xml 配置了资源打包
<build>
<resources>
<resource>
<directory>src/main/resources</directory>
</resource>
</resources>
</build>
面试题
Q1:Spring Boot 的配置加载顺序是什么?
参考答案:
从高到低:
- 命令行参数:
--spring.config.location=/path/to/config - OS 环境变量:
SPRING_CONFIG_ADDITIONAL_LOCATION - jar 包外部:
./config/application.yml - jar 包内部:
classpath:application.yml - @PropertySource:代码中指定的配置文件
相同配置项,高优先级覆盖低优先级
Q2:YAML 和 Properties 的区别?
参考答案:
| 特性 | YAML | Properties |
|---|---|---|
| 格式 | 缩进敏感 | key=value |
| 注释 | # | # 或 ! |
| 结构 | 支持嵌套 | 只能扁平 |
| 环境切换 | --- 分隔 | -dev 后缀 |
| 复杂度 | 简单配置更简洁 | 复杂配置更清晰 |
选择建议:
- 简单配置 → YAML
- 需要与 Spring Cloud 集成 → YAML
- 需要兼容 Java Properties API → Properties
Q3:如何实现配置热更新?
参考答案:
方案一:Spring Boot DevTools
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-devtools</artifactId>
</dependency>
方案二:Spring Cloud Config + Bus
# 启用 refresh 端点
management:
endpoints:
web:
exposure:
include: refresh
然后 POST 请求到 /actuator/refresh 触发刷新
方案三:Nacos/Apollo 配置中心
- 支持 Web UI 修改配置
- 自动推送到应用并刷新