服务在不同环境启动,需要的运行参数可能会有差异,不同启动环境也可能公用同一份运行参,为了方便对这些不同环境相同和差异参数进行管理,springboot提供了文件配置化形式对这些参数进行管理,对于不同环境的差异化参数使用spring.profiles关键字进行了隔离。
示例文件分析
(文件中配置项纯属杜撰,只是为了为了方便分析环境参数家在生效顺序)
项目noodles-commerce-growth的backend模块中配置文件:application-backend.yaml
projectIdentity: noodles-commerce-growth
fdc.projectIdentity: noodles-commerce-growth
# ServiceInstanceMeta
serviceInstanceMeta:serviceName: noodles-commerce-growthlogging.level: INFOactuator:project: noodles-commerce-growthenabled: trueopenFalconEnabled: falselogging.access.directory: /home/shared/logspring.profiles.active: local,sg-testsecurity.filterOrder: 20---
spring:profiles: locallogging.access.enabled: false
zkServers: sh-zk1,sh-zk2,sh-zk3,sh-zk4,sh-zk5rpcServer.zkNode: false---
# 测试服务环境
spring:profiles: testlogging.config: classpath:log4j2.test.yaml
---
# 大兴测试机房
spring:profiles: sh-test# ZooKeeper 配置
zkServers: sh-zk1,sh-zk2,sh-zk3,sh-zk4,sh-zk5---
# 润泽测试机房
spring:profiles: rz-test# ZooKeeper 配置
zkServers: sh-zk1,sh-zk2,sh-zk3,sh-zk4,sh-zk5---
# 测试服务环境
spring:profiles: bj-test# MySQL 连接配置
db.datasource.noodlesCommerceGrowth:dynamicConfigEnabled: true # Optional,默认为 truedynamicConfigKey: noodles-mysql-noodles_commerce_growth-testdynamicConfigGroup: op-dba-mysql-confreadWriteSplit: true #开启读写分离需要指定,默认是false 关闭读写分离---
# 线上服务环境
spring:profiles: onlinelogging.config: classpath:log4j2.online.yaml
logging.access.directory: /home/shared/logsentry.dsn: https://6041205e545f455b96fda7d679a23c83@sentry-internal-noodles.zhuangzi.com/399---
# 线上服务环境
spring:profiles: bj-onlinedb.datasource.noodlesCommerceGrowth:dynamicConfigEnabled: true # Optional,默认为 truedynamicConfigKey: noodles-mysql-commerce_growth-onlinedynamicConfigGroup: op-dba-mysql-confreadWriteSplit: true #开启读写分离需要指定,默认是false 关闭读写分离---
# 大兴线上机房
spring:profiles: dx-onlinezkServers: dx-zk1,dx-zk2,dx-zk3,dx-zk4,dx-zk5---
# 廊坊线上机房
spring:profiles: lf-onlinezkServers: lf-zk1,lf-zk2,lf-zk3,lf-zk4,lf-zk5---
# alibj1 线上机房spring:profiles: alibj1-onlinezkServers: lf-zk1,lf-zk2,lf-zk3,lf-zk4,lf-zk5
文件分析:
1、不同环境下的差异化参数使用spring.profiles: local、spring.profiles: test、spring.profiles: soho-test、spring.profiles: bj-test、spring.profiles: rz-test、spring.profiles: online、spring.profiles: bj-online、spring.profiles: dx-online、spring.profiles: lf-online、spring.profiles: alibj1-online;从文件顶部到spring.profiles: local部分的配置信息为所有环境公用。
2、通过spring.profiles.active: local,sg-test指定服务启动时选择的环境参数。比如idea本地启动时默认选择的环境参数是就是配置文件中的spring.profiles.active: local,sg-test。首先可以指定服务运行时参数的地方有和生效次序为:命令行方式 > Java系统属性方式 > 系统变量方式 > 配置文件方式,在启动本地idea时,在前三种没有配置的情况下,就按照配置文件中spring.profiles.active指定环境选择对应的运行参数。
3、在spring.profiles.active中可以指定多个环境,多个环境的差异参数参数相同互补、形成一个全集对运行服务生效,不同环境的相同参数按照从左到右的顺序,以最右面的参数为准。
4、服务运行的环境通常分为本地(local)、测试(test)和生产(online)环境,为什么都是线上环境还有有多个呢,比如test和sg-test,online、bj-online、dx-onlne、lf-online和alibj1-online?针对这个问题,首先是sping.profiles的数据完全可以和真实服务运行环境数量保持一致,其中一个猜想是即使对同一种服务运行环境,配置对应的服务可能失效,多个备份可以起到容灾的目的。
常见的项目架构中,采用了模块化的思想对项目进行拆分以实现代码的复用和不同服务之间的解耦,这种模块化思想对配置文件同样适用。
noodles-commerce-growth的的某个服务中的配置文件application.yaml:
# tracing配置
tracing.enabled: true # tracing开关,所有环境默认开启,不用再配置
tracing.reporterConfig.enabled: true # tracing上报数据开关,测试环境默认关,线上环境默认开
serviceInstanceMeta.serviceName: noodles-commercee-growth # 在阿里云控制台展示的服务名# authFilter 配置
authFilter:internationalEnabled: truedefaultProductId: 503appKey: ApeescapePatterns:- /nooldes-commerce-growth/api/order/\d+- /nooldes-commerce-growth/api/order/share-info- /.*/swagger/.*# Web Server 配置
server:port: 8080tomcat:maxThreads: 500# multipart 配置
spring.http.multipart:max-file-size: 5MB # multipart单个文件大小限制max-request-size: 10MB # multipart整个request的大小限制file-size-threshold: 1MB # 大于fileSizeThreshold的在解析过程中会写磁盘, 否则是纯内存操作# sentinel 开关
spring.cloud.ahas.sentinel.web.enabled: false#海外http接口下发的域名替换
overseas:domain:replace: true# Actuator 配置
actuator:project: noodles-commerce-growth# Captain 配置
captain:serviceName: noodles-commerce-growth-webfdc.projectIdentity: noodles-commerce-growthcaptain.enabled: falsespring.datasource.initialize: falsespring.profiles.active: local,soho-test,bj-test# 本地环境
cache:local:song:capacity: 3000ttl-in-seconds: 60album:capacity: 1000ttl-in-seconds: 60type2albums:capacity: 1000ttl-in-seconds: 60springfox.documentation.swagger.v2.host: noodels.commerce.com# Redis 配置alimq.topics:---
spring:profiles: localrpcServer.zkNode: false
logging.access.enabled: false
actuator.enabled: false---
# 测试服务环境
spring:profiles: testlogging.config: classpath:log4j2.test.yaml
logging.access.directory: /home/shared/log---
# 线上服务环境
spring:profiles: onlinelogging.config: classpath:log4j2.online.yaml
logging.access.directory: /home/shared/log# Redis 配置alimq.topics:
---
# 大兴测试机房
spring:profiles: soho-test# ZooKeeper 配置
zkServers: soho-zk1,soho-zk2,soho-zk3,soho-zk4,soho-zk5---
# 润泽开发机房
spring:profiles: rz-devzkServers: noodles-zk1-dev,noodles-zk2-dev,noodles-zk3-dev---
# 大兴线上机房
spring:profiles: dx-onlinezkServers: dx-zk1,dx-zk2,dx-zk3,dx-zk4,dx-zk5---
# 廊坊线上机房
spring:profiles: lf-onlinezkServers: lf-zk1,lf-zk2,lf-zk3,lf-zk4,lf-zk5---
spring:profiles:include: backend
文件分析:
1、相比上一个文件,这个文件中多了spring.profiles.include配置项,服务启动时,会先加载backend中的profiles,然后和当前文件进行合并和覆盖,相同配置项当前文件会覆盖被引入的文件。
总结
相同配置项生效顺序遵循了就近原则,后加载覆盖之前加载的配置项。