我的环境
- Windows10
- JDK8
- SpringCloud:Hoxton.SR9
- SpringBoot:2.3.9.RELEASE
- spring-cloud-alibaba-dependencies:2.2.3.RELEASE
- Nacos-server:2.0.3
场景描述
一个项目中服务数量增加后,配置文件相应增加,多个配置文件中会存在相同的配置,那么我们可以将相同的配置独立出来,作为该项目中各个服务的共享配置文件,每个服务都可以通过Nacos进行共享配置的读取
下面用一个demo演示下,是否可行
demo工程:nacos-config-share
配置文件:nacos-config-share.yml
共享配置文件:shareconfig1.yml,shareconfig2.yml
创建项目
创建聚合工程springcloud-nacos, pom文件:
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.cloud</groupId>
<artifactId>springcloud-nacos</artifactId>
<packaging>pom</packaging>
<version>1.0-SNAPSHOT</version>
<modules>
<module>nacos-config-share</module>
</modules>
<properties>
<maven.compiler.source>1.8</maven.compiler.source>
<maven.compiler.target>1.8</maven.compiler.target>
<worldskills.version>1.1.0</worldskills.version>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
<java.version>1.8</java.version>
<spring-boot.version>2.3.9.RELEASE</spring-boot.version>
<spring-cloud.version>Hoxton.SR9</spring-cloud.version>
<spring-cloud-alibaba.version>2.2.3.RELEASE</spring-cloud-alibaba.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
<version>${spring-boot.version}</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
</dependencies>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>${spring-cloud.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-dependencies</artifactId>
<version>${spring-boot.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-alibaba-dependencies</artifactId>
<version>${spring-cloud-alibaba.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
</project>
创建子工程nacos-config-share, maven坐标:
<dependencies>
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
</dependency>
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-nacos-config</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-configuration-processor</artifactId>
<optional>true</optional>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
创建配置类:NacosShareConfig
@Data
@RefreshScope
@Configuration
@ConfigurationProperties(prefix = "nacos.config")
public class NacosShareConfig {
private String nacosConfigShare;
/**
* 共享配置
*/
private String shareConfig1;
private String shareConfig2;
/**
* 扩展共享配置
*/
private String shareConfig3;
private String shareConfig4;
}
控制器:NacosConfigShareController
@RestController
@RequestMapping("/share")
public class NacosConfigShareController {
@Autowired
private NacosShareConfig nacosShareConfig;
@RequestMapping("/getConfigShare")
public String getConfigShare() {
return nacosShareConfig.getNacosConfigShare();
}
@RequestMapping("/getShareConfig1")
public String getShareConfig1() {
return nacosShareConfig.getShareConfig1();
}
@RequestMapping("/getShareConfig2")
public String getShareConfig2() {
return nacosShareConfig.getShareConfig2();
}
@RequestMapping("/getShareConfig3")
public String getShareConfig3() {
return nacosShareConfig.getShareConfig3();
}
@RequestMapping("/getShareConfig4")
public String getShareConfig4() {
return nacosShareConfig.getShareConfig4();
}
}
配置文件:bootstrap.yml
spring:
application:
name: nacos-config-share
cloud:
nacos:
discovery:
server-addr: 192.168.194.128:8848
config:
server-addr: 192.168.194.128:8848
prefix: ${spring.application.name}
file-extension: yml
#旧共享配置方式+动态刷新
# shared-dataids: shareconfig1.yml,shareconfig2.yml
# refreshable-dataids: shareconfig1.yml,shareconfig2.yml
#新的共享配置+动态刷新
shared-configs:
- data-id: shareconfig1.yml
group: DEFAULT_GROUP
refresh: true #动态刷新配置开启
- data-id: shareconfig2.yml
group: DEFAULT_GROUP
refresh: false #动态刷新配置关闭
从配置文件可以看出,通过
shared-dataids
属性来指定要读取共享配置文件的DataID
,多个文件用,
分隔使用refreshable-dataids
指定共享配置文件支持自动刷新shared-dataids/refreshable-dataids官方标记废弃了
Nacos新建配置文件
这里我们作为演示,暂不加入Namespace,直接在公共空间中创建及测试
创建配置文件nacos-config-share.yml,详细如下:
- DataId:nacos-config-share.yml
- 配置格式:YAML
- 配置内容:
server:
port: 9984
nacos:
config:
nacosConfigShare: nacos-config-share
创建共享配置文件1shareconfig1.yml,详细如下:
- DataId:shareconfig1.yml
- 配置格式:YAML
- 配置内容:
nacos:
config:
shareConfig1: 这里是共享配置文件1
创建共享配置文件1shareconfig2.yml,详细如下:
- DataId:shareconfig2.yml
- 配置格式:YAML
- 配置内容:
nacos:
config:
shareConfig2: 这里是共享配置文件2
创建成功后,配置列表如下图:
启动测试
访问控制器提供的接口
http://localhost:9984/share/getConfigShare #nacos-config-share
http://localhost:9984/share/getShareConfig1 #这里是共享配置文件1
http://localhost:9984/share/getShareConfig2 #这里是共享配置文件2
再测试下共享配置的自动刷新是否生效,shareconfig1.yml的refresh:true 预期会生效,shareconfig2.yml的refresh:false不生效
在Nacos控制台中修改共享配置文件shareconfig1.yml的值为:这里是共享配置文件1-测试动态刷新是否生效
编辑保存后,重新请求 http://localhost:9984/share/getShareConfig1 ,观察返回结果如下:
这里是共享配置文件1-测试动态刷新是否生效
重新请求 http://localhost:9984/share/getShareConfig2 ,观察返回结果如下:
这里是共享配置文件2
需求变更
假设现在要读取shareconfig3.yml和shareconfig4.yml文件但是它的Group为SHARE3_GROUP和SHARE4_GROUP, 即共享配置文件与项目自身配置文件不在同一Group中(上边的例子是全都在DEFAULT_GROUP分组) 那如果继续用上边的方法,就无法读取共享配置文件
这时可以使用另一个配置ext-config
,它可以由用户自定义指定需要加载的配置DataID、Group以及是否自动刷新
并且ext-config
是一个集合(List
),支持多个配置文件的指定。
注:ext-config官方标记废弃;取而代之的是extension-configs
新建共享配置文件
先创建配置配置文件shareconfig3.yml
和shareconfig4.yml
,注意他们的Group属性
- DataId:shareconfig3.yml
- Group:SHARE3_GROUP
- 配置格式:YAML
- 配置内容:
nacos:
config:
shareConfig3: 这里是共享配置文件3,Group:SHARE3_GROUP
- DataId:shareconfig4.yml
- Group:SHARE4_GROUP
- 配置格式:YAML
- 配置内容:
nacos:
config:
shareConfig4: 这里是共享配置文件4,Group:SHARE4_GROUP
创建成功页面如下:
修改项目配置文件bootstrap.yml
,增加ext-config(旧),
extension-configs(新)
配置
spring:
application:
name: nacos-config-share
cloud:
nacos:
discovery:
server-addr: 192.168.194.128:8848
config:
server-addr: 192.168.194.128:8848
prefix: ${spring.application.name}
file-extension: yml
#旧共享配置方式+动态刷新
# shared-dataids: shareconfig1.yml,shareconfig2.yml
# refreshable-dataids: shareconfig1.yml,shareconfig2.yml
#新的共享配置+动态刷新
shared-configs:
- data-id: shareconfig1.yml
group: DEFAULT_GROUP
refresh: true #动态刷新配置开启
- data-id: shareconfig2.yml
group: DEFAULT_GROUP
refresh: false #动态刷新配置关闭
#旧扩展配置方式+动态刷新 + 不同组获取共享配置数据
# ext-config:
# - data-id: shareconfig3.yml
# group: SHARE3_GROUP
# refresh: true
# - data-id: shareconfig4.yml
# group: SHARE4_GROUP
# refresh: true
#新的扩展配置方式 + 动态刷新 + 不同组获取共享配置数据
extension-configs:
- data-id: shareconfig3.yml
group: SHARE3_GROUP
refresh: true #动态刷新配置开启
- data-id: shareconfig4.yml
group: SHARE4_GROUP
refresh: false #动态刷新配置关闭
启动进行测试
项目经过修改后,可以看到
- 项目自身的nacos配置文件属于DEFAULT_GROUP下,默认读取
- shareconfig1.yml,shareconfig2.yml 都属于DEFAULT_GROUP下,通过shared-dataids(旧)/shared-configs(新)指定进行读取
- shareconfig3.yml,shareconfig4.yml 都属于非DEFAULT_GROUP下,通过ext-config(旧)/extension-configs(新)配置属性进行自定义读取
启动项目,测试所有的配置文件是否可以正常读取
http://localhost:9984/share/getConfigShare #nacos-config-share
http://localhost:9984/share/getShareConfig1 #这里是共享配置文件1
http://localhost:9984/share/getShareConfig2 #这里是共享配置文件2
http://localhost:9984/share/getShareConfig3 #这里是共享配置文件3,Group:SHARE3_GROUP
http://localhost:9984/share/getShareConfig4 #这里是共享配置文件4,Group:SHARE4_GROUP
修改shareconfig3.yml
的配置内容为:这里是共享配置文件3,Group:SHARE3_GROUP
- 测试扩展配置是否支持动态刷新,保存后,再次调用http://localhost:9984/share/getShareConfig3,返回如下:
这里是共享配置文件3,Group:SHARE3_GROUP - 测试扩展配置是否支持动态刷新
调用接口后发现,两种共享配置的加载方式都可以正常读取,并且可以一起使用。extension-configs的方式实现了用户自定义配置共享配置文件。
总结
上面的demo已经演示Nacos共享配置的两种实现方式,两种方式针对不同的场景,总结如下:
- shared-configs方式:
- 适合于共享配置文件与项目默认配置文件处于相同Group时,直接两条命令就可以搞定
- 优点:配置方便
- 缺点:只能在同一Group中
- ext-config方式: 它可以由开发者自定义要读取的共享配置文件的DataId、Group、refresh属性,这样刚好解决了shared-dataids存在的局限性。 优点:可以与shared-dataids方案结合使用,用户自定义配置。灵活性强 缺点:配置容易出错,要熟悉YAML语法