JavaEE SpringBoot配置文件详解

作者:技术拾光时间:2026-07-24 08:28:09浏览:638

SpringBoot通过application.properties和application.yml配置文件集中管理端口、数据库等参数,避免硬编码。properties采用键值对格式,yml采用树形层级结构,可读性更强且支持复杂数据类型。配置读取依赖@Value和@ConfigurationProperties注解,yml格式要求严格缩进。两种配置文件可共存

一、为什么需要配置文件?

写代码的时候,最怕什么?最怕改个端口号就得翻遍整个项目,重新打包部署。如果你把端口、数据库账号、第三方密钥这些变量直接写死在代码里——也就是所谓的硬编码——那维护起来可就真成了噩梦。具体来说,会面临三个绕不开的问题:

JavaEE SpringBoot配置文件详解

  1. 环境切换(本地/测试/生产)时,每次都得改代码、重新打包,效率极低;
  2. 敏感信息直接暴露在源码中,安全风险高,代码一旦泄露,后果严重;
  3. 想要统一修改某个参数,就得全局检索代码,费时费力且容易遗漏。

配置文件的用途,就是将那些经常变动的参数抽离出来,放到一个独立文件中。程序启动时,自动读取该文件,所有外部配置集中管理,一劳永逸。

SpringBoot 内置了两套主流的配置文件:application.properties 和 application.yml(yaml)。它们可以帮你维护端口、数据库、日志、自定义业务参数等几乎所有需要外部化的配置。

二、SpringBoot 两种配置文件

2.1 文件存放位置与加载规则

配置文件统一放在 src/main/resources 目录下,项目启动后自动加载。这里有两个默认选项:

  • application.properties:SpringBoot 创建项目时默认生成,采用经典的键值对格式;
  • application.yml/application.yaml:新式树形层级格式,可读性更强,是目前开发中的主流选择。

需注意:如果两个文件同时存在,配置会取并集,但 properties 优先级更高——同名配置会覆盖 yml 中的设置。实际项目中最好统一使用一种格式,同时维护两套配置容易造成混乱。

2.2 application.properties 键值对格式

1. 基础语法

格式简单:key=value,注释用 #,层级关系通过 . 分隔。

# 修改Tomcat端口
server.port = 9090
# MySQL数据库配置
spring.datasource.url = jdbc:mysql://127.0.0.1:3306/testdbcharacterEncoding = utf8&useSSL=false
spring.datasource.username = root
spring.datasource.password = root
# 自定义业务配置
my.test.key=demo123

2. 读取配置:@Value

使用 ${配置key} 直接读取参数,适用于零散、独立的配置——不过,只支持单个简单值。

@RestController
@RequestMapping("/prop")
public class PropController {
    // 读取properties自定义参数
    @Value("${my.test.key}")
    private String testKey;
    @RequestMapping("/get")
    public String getConfig() {
        return "读取properties配置:" + testKey;
    }
}

3. properties 的缺点

当配置层级变多时,重复前缀的问题就暴露出来了:

spring.datasource.url=xxx
spring.datasource.username=root
spring.datasource.password=root

每一行都要重复写 spring.datasource,层级越深,冗余越严重,维护起来很麻烦。

三、application.yml YAML 树形配置

YAML 的全称是 Yet Another Markup Language(另一种标记语言),采用树形缩进结构,可读性比 properties 强得多,而且原生支持对象、集合、Map 等复杂数据。

3.1 语法要点

  1. 基础格式:key: value,冒号后面必须加一个英文空格,缺少空格会导致解析报错,务必注意;
  2. 层级区分:使用缩进(2个空格)表示父子层级;
  3. 注释:# 单行注释;
  4. 行内写法:用大括号 {} 简化单层对象/Map,用短横线 - 表示集合元素。

拿数据库配置来对比一下:

# application.yml
spring:
  datasource:
    url: jdbc:mysql://127.0.0.1:3306/testdbcharacterEncoding=utf8&useSSL=false
    username: root
    password: root

和 properties 相比,yml 消除了重复前缀,层级关系一目了然。

3.2 yml 支持全类型数据配置

1. 基础数据类型

# 字符串
str: Hello SpringBoot
# 布尔值
bool: true
# 数字
num: 666
floatNum: 3.14
# null:~代表空值
empty: ~
# 空字符串
emptyStr: ''

2. 字符串单双引号的特殊规则

string:
  str1: Hello n Boot  # 无引号:n 原样输出,不会换行
  str2: 'Hello n Boot' # 单引号:转义所有特殊字符,n 仅作为文本
  str3: "Hello n Boot" # 双引号:保留转义字符,n 会自动换行

3. 配置对象

# 标准缩进写法
person:  
  id: 1  
  name: daisy  
  age: 10
# 行内简写,效果完全一致
person: {id: 1, name: daisy, age: 10}

重点提醒:对象不能用 @Value 读取,必须使用 @ConfigurationProperties 进行批量绑定。

@ConfigurationProperties(prefix = "person")  
@Configuration  
@Data  
public class Person {  
    private int id ;  
    private String name;  
    private int age;  
}

4. 配置 List & Map

  • List 集合
db-types:
  name:
    - mysql
    - sqlserver
    - db2

List 和数组的配置方式完全一样,既可以用 List 接收,也可以用数组接收。

  • Map 键值对集合
map-demo:
  map:
    k1: v1
    k2: v2
# 行内简写
map-demo: {map: {k1: v1, k2: v2}}
@Data  
@Component  
@ConfigurationProperties(prefix = "dbtypes")  
public class DBTypes {  
    private List name;  
    private Map ball;  
}

3.3 两种读取配置注解对比

特性@Value@ConfigurationProperties
适用场景单个简单参数、零散配置批量绑定一组配置、对象/List/Map
复杂类型不支持对象、集合、Map完美支持嵌套对象、List、Map
松散绑定严格匹配key名称支持驼峰、短横线、下划线自动映射

不论使用 application.properties 还是 application.yml,读取配置的方式都是通过这两个注解实现的,本质上没有区别。

3.4 yml 的优缺点

优点:

  1. 树形层级清晰,消除了重复前缀,可读性极高;
  2. 原生支持对象、数组、Map 等复杂数据结构;
  3. 跨语言通用,Java、Go、Python、前端都能用。

缺点:格式要求非常严苛,缩进、空格只要有一处错误,启动就会直接失败。

四、yml 配置 + Hutool 图形验证码案例

4.1 需求说明

  1. 访问接口返回图形验证码图片;
  2. 验证码存入 Session,有效期 1 分钟;
  3. 前端输入验证码提交,后端校验是否匹配、是否过期;
  4. 验证码的宽高、Session 键名全部抽离到 yml 配置中,统一管理。

4.2 引入 Hutool 验证码依赖

在 pom.xml 中添加依赖:


    cn.hutool
    hutool-captcha
    5.8.22

4.3 yml 配置验证码参数

captcha:  
  width: 150  
  height: 50  
  session:  
    key: CAPTCHA_SESSION_KEY  
    date: CAPTCHA_SESSION_DATE

4.4 创建配置映射实体 CaptchaProperties

@Data  
@Configuration  
@ConfigurationProperties(prefix = "captcha")  
public class CaptchaProperties {  
    private Integer width;  
    private Integer height;  
    private Session session;  
    @Data  
    public static class Session{  
        private String key;  
        private String date;  
    }  
}

注意: 普通的内部类不能交给 Spring 管理,因为它必须依托外部类存在。这里改成静态内部类,就不再依赖外部类,能被 Spring 正常管理。

4.5 后端 Controller 生成与校验验证码

@RestController  
@RequestMapping("/captcha")  
public class CaptchaController {  
    @Autowired  
    CaptchaProperties captchaProperties;  
    private final static Long VALID_TIME = 60*1000L;  
    @RequestMapping("/getCaptcha")  
    public void getCaptcha(HttpServletResponse response, HttpSession session) throws IOException {  
        response.setContentType("image/jpeg");  
        // 理论上由前端处理浏览器缓存问题  
        response.setHeader("Pragma", "No-cache");  
        // 生成验证码  
        ShearCaptcha shearCaptcha = CaptchaUtil.createShearCaptcha(captchaProperties.getWidth(), captchaProperties.getHeight());  
        String code = shearCaptcha.getCode();  
        session.setAttribute(captchaProperties.getSession().getKey(), code);  
        session.setAttribute(captchaProperties.getSession().getDate(), System.currentTimeMillis());  
        shearCaptcha.write(response.getOutputStream());  
        response.getOutputStream().close();  
    }  
    @RequestMapping("/check")  
    public boolean check(String captcha, HttpSession session){  
        // 判空  
        if(!StringUtils.hasLength(captcha))  
            return false;  
        // 验证  
        Object codeAttr = session.getAttribute(captchaProperties.getSession().getKey());  
        Object dateAttr = session.getAttribute(captchaProperties.getSession().getDate());  
        if(codeAttr == null || dateAttr == null)  
            return false;  
        String code = codeAttr.toString();  
        long date = (long) dateAttr;  
        boolean isValid = System.currentTimeMillis() - date <= VALID_TIME;  
        return captcha.equalsIgnoreCase(code) && isValid;  
    }  
}

4.6 前端页面

  • index.html 验证码输入页
  
  
  
    
  验证码  
    
  
  
  

输入验证码

JavaEE SpringBoot配置文件详解