Spring Cloud 配置中心应用集成
基于Spring Boot、Spring Cloud Alibaba、Maven和Nacos实现:
- Spring Boot
- Spring Cloud Alibaba Reference Documentation (spring-cloud-alibaba-group.github.io)
- Maven – Welcome to Apache Maven
- home (nacos.io)
1.Nacos dataId命名规则
dataId作为Nacos服务端和客户端配置交互的纽带,dataId在服务端和客户端必须遵循统一的命名规则和配置,方可实现配置中心的配置下发。
在 Nacos Spring Cloud 中,dataId
的完整格式如下:
${prefix}-${spring.profiles.active}.${file-extension}
-
prefix
默认为spring.application.name
的值,也可以通过配置项spring.cloud.nacos.config.prefix
来配置。 -
spring.profiles.active
即为当前环境对应的 profile,详情可以参考 Spring Boot文档。 注意:当spring.profiles.active
为空时,对应的连接符-
也将不存在,dataId 的拼接格式变成${prefix}.${file-extension}
-
file-exetension
为配置内容的数据格式,可以通过配置项spring.cloud.nacos.config.file-extension
来配置。目前只支持properties
和yaml
类型。
2.Spring Boot配置文件加载顺序
-
配置文件加载顺序
bootstrap.properties -> bootstrap.yml -> application.properties -> application.yml
例:如果在bootstrap.properties配置端口号:8080,bootstrap.yml文件中配置8081端口,此时启动时为8081端口号。先加载的配置文件中的配置,会被后加载文件中的配置选择性覆盖。
-
不同目录中
官方文档中给出指示,搜索位置如下:1. file:./config/ (当前目录的/config子目录 项目文件路径/config) 2. file:./ (当前目录 项目文件路径) 3. classpath:/config/ (classpath /config包 项目文件路径/src/main/resources/config) 4. classpath:/ (类路径根 项目文件路径/src/main/resources)
优先级由高至低,在列表中较高位置定义的属性将覆盖在较低位置中定义的属性。
注:classpath路径,没打包之前是…/resources路径,打包之后是在BOOT-INF/classes或者WEB-INF/classes文件夹中。
-
问题定位
1. 如果在项目中发现配置文件中的配置没有生效,检查下各个配置文件中是否有相同的内容配置,留下一个需要的配置,多余的去掉; 2. 如果项目是yml配置文件,还有可能是配置文件的格式有问题,检查下“:”后面是否加了空格; 3. 可能项目中采用的是配置中心管理配置文件,在本地修改配置文件并没有用。例如:nacos,需修改nacos中配置管理-配置列表中对应环境的配置文件。
3.Nacos配置及部署注意事项
打开参考网站:Spring Cloud Alibaba Reference Documentation (spring-cloud-alibaba-group.github.io),进入“Spring Cloud Alibaba Nacos Config”配置章节,参照指引进行配置,基于springboot +maven开发。
-
pom.xml文件增加依赖管理,用于统一管理spring cloud alibaba相关组件,不用多次重复声明version等元素。
<dependencyManagement> <dependencies> <dependency> <groupId>com.alibaba.cloud</groupId> <artifactId>spring-cloud-alibaba-dependencies</artifactId> <version>2.2.7.RELEASE</version> <type>pom</type> <scope>import</scope> </dependency> </dependencies> </dependencyManagement>
-
pom.xml文件增加nacos config启动类。
<dependency> <groupId>com.alibaba.cloud</groupId> <artifactId>spring-cloud-starter-alibaba-nacos-config</artifactId> </dependency>
-
Nacos的相关配置需要在bootstrap.properties或bootstrap.yml中进行,保证项目启动时优先与业务应用配置加载,否则可能会引发错误。此处使用yml格式,假设spring.profiles.active为“dev”,则此处生成的dataId为:application-dev.yml,在Nacos服务端的配置中心需配置对应的dataId进行适配。
spring: application: name: nacos-config-client cloud: nacos: config: server-addr: 127.0.0.1:8848 #Nacos服务地址和端口号 file-extension: yml #配置文件格式,对应dataId中的第三部分 prefix: application #配置文件前缀,对应dataId中的第一部分
-
Nacos端口
当Nacos客户端升级为2.x版本后,新增了gRPC的通信方式,新增了两个端口。这两个端口在Nacos原先的端口上(默认8848),进行一定偏移量自动生成.。
端口 与主端口偏移量 描述 9848 1000,主端口默认为8848 客户端gRPC请求服务端端口,用于客户端向服务端发起连接和请求 9849 1001,主端口默认为8848 服务端gRPC请求服务端端口,用于服务间同步等 因此客户端到服务端的访问,需要开放两个端口:8848,9848,否则客户端程序会报如下错误:
please check server X.X.X.X,port 9848 is available
-
Nacos server配置、启动及访问(单机模式)
-
JDK要求
Nacos Server如果运行在linux下,一定要使用oracle JDK不要使用系统自带的open JDK,open JDK由于缺少加密算法"HmacSHA256",会报如下错误:
jsonwebtoken.security.SignatureException: Unable to obtain JCA MAC algorithm 'HmacSHA256': Algorithm HmacSHA256 not available
-
JAVA_HOME配置
windows下会默认读取环境变量里面配置的JAVA_HOME设置。linux下如果未配置系统级别的JAVA_HOME,可在startup.sh文件中对JAVA_HOME进行配置:
export JAVA_HOME=/home/data/run/jdk1.8.0_202
-
启动
#进入nacos/bin目录,输入如下命令 startup.cmd -m standalone #单机模式启动,windows startup.sh -m standalone #单机模式启动,linux
-
默认访问地址:http://localhost:8848/nacos,默认用户名/密码:nacos/nacos。
-
4.Nacos配置中心业务实现
-
Nacos配置中心
dataid:application-dev.yml
dynamic-config: min-weight: 4.5
-
bootstrap.yml
spring: cloud: nacos: config: file-extension: yml #扩展名 server-addr: localhost:8848 #Nacos服务url prefix: application #前缀
-
配置类代码实现
@RefreshScope:Spring Cloud原生注解,实现配置自动更新,每30秒向服务器请求一次获取最新配置,如果获取失败则读取本机磁盘缓存。
@Configuration @RefreshScope @Data @NoArgsConstructor @AllArgsConstructor public class NacosConfig { @Value("${dynamic-config.min-weight}") private Double minWeight = 4.5; //最小过磅重量 }
-
Nacos健康检查代码
@Configuration public class NacosRegistryHealthyFilter implements ApplicationListener<InstancePreRegisteredEvent> { @Autowired HealthEndpoint healthEndpoint; @Autowired NacosDiscoveryProperties nacosDiscoveryProperties; public void onApplicationEvent(InstancePreRegisteredEvent event) { //健康检查代码 if (Status.UP.equals(healthEndpoint.health().getStatus())){ nacosDiscoveryProperties.setRegisterEnabled(true); System.out.println("healthy"); } else{ nacosDiscoveryProperties.setRegisterEnabled(false); System.out.println("no healthy"); } } }
-
Nacos配置读取示例
@RestController @RequestMapping("nacos/consumer") public class DemoController { @Autowired NacosConfig nacosConfig; @GetMapping("/test") public String test(){ System.out.println("从Nacos中获取配置minWeight=" + nacosConfig.getMinWeight()); return nacosConfig.getMinWeight().toString(); }