概述

在分布式系统中,由于服务数量巨多,为了方便服务配置文件统一管理,实时更新,所以需要分布式配置中心组件。

什么是 Nacos Config

Nacos 提供用于存储配置和其他元数据的 key/value 存储,为分布式系统中的外部化配置提供服务器端和客户端支持。使用 Spring Cloud Alibaba Nacos Config,您可以在 Nacos Server 集中管理你 Spring Cloud 应用的外部属性配置。

Spring Cloud Alibaba Nacos Config 是 Spring Cloud Config Server 和 Client 的替代方案,客户端和服务器上的概念与 Spring Environment 和 PropertySource 有着一致的抽象,在特殊的 bootstrap 阶段,配置被加载到 Spring 环境中。当应用程序通过部署管道从开发到测试再到生产时,您可以管理这些环境之间的配置,并确保应用程序具有迁移时需要运行的所有内容。

接入配置中心

需要在 Nacos Server 中创建配置文件,我们依然采用 YAML 的方式部署配置文件,操作流程如下:

image.png

  • 新建配置文件,此处我们以之前创建的 服务提供者 项目为例

image.png
image.png

  1. spring:
  2. application:
  3. name: nacos-consumer
  4. cloud:
  5. nacos:
  6. discovery:
  7. server-addr: 192.168.3.192:8848
  8. loadbalancer:
  9. ribbon:
  10. enabled: false
  11. server:
  12. port: 9091
  13. management:
  14. endpoints:
  15. web:
  16. exposure:
  17. include: "*"
  18. endpoint:
  19. health:
  20. show-details: always
  21. user:
  22. name: "造门炭治郎"

注意:Data ID 的默认扩展名为 .properties ,希望使用 YAML 配置,此处必须指明是 .yaml

  • 发布成功后在 “配置列表” 一栏即可看到刚才创建的配置项

image.png

Spring 配置文件加载优先级,由高到低

bootstrap.properties -> bootstrap.yml -> application.properties -> application.yml

修改配置文件

删除掉 com.funtl.hello.spring.cloud.alibaba.nacos.consumer 项目下的 application.yaml 配置文件,因为配置文件已经在 Nacos 里创建了,删除后创建 bootstrap.properties 配置文件,此文件是最高优先级,一定会执行

  1. # 这里的应用名对应 Nacos Config 中的 Data ID,实际应用名称以配置中心的配置为准
  2. spring.application.name=nacos-consumer-config
  3. # 指定查找名为 nacos-provider-config.yaml 的配置文件
  4. spring.cloud.nacos.config.file-extension=yaml
  5. # Nacos Server 的地址
  6. spring.cloud.nacos.config.server-addr=192.168.3.192:8848


Spring Boot 版本

Spring Boot 2.4版本开始,配置文件加载方式进行了重构,要引入高版本,如果你的版本是3以上,就不需要重新引入依赖

<!-- https://mvnrepository.com/artifact/org.springframework.cloud/spring-cloud-starter-bootstrap -->
<dependency>
    <groupId>org.springframework.cloud</groupId>
    <artifactId>spring-cloud-starter-bootstrap</artifactId>
    <version>3.1.1</version> <!-- 有版本管理,这个版本可以不用加 -->
</dependency>

Nacos 版本问题

Nacos2.0以后 有更新
在 Nacos Spring Cloud 中,dataId 的完整格式变更:
${prefix}-${spring.profiles.active}.${file-extension} --> ${name}-${spring.profiles.active}.${file-extension}
版本声明-SpringBoot-2.5.12 Nacos-2.0.3
配置文件的名字对应参数应为:
spring.cloud.nacos.config.name=${spring.application.name}
修改配置文件如下

spring.cloud.nacos.config.name=nacos-consumer-config
spring.cloud.nacos.config.server-addr=192.168.3.192:8848
spring.cloud.nacos.config.file-extension=yaml

记得在 pom.xml 文件中添加配置依赖

<dependency>
    <groupId>com.alibaba.cloud</groupId>
    <artifactId>spring-cloud-starter-alibaba-nacos-config</artifactId>
</dependency>

Controller

在 NacosConsumerFeignController.java 添加 @RefreshScope注解,并打印输出用户名

package com.funtl.hello.spring.cloud.alibaba.nacos.consumer.controller;

import com.funtl.hello.spring.cloud.alibaba.nacos.consumer.service.EchoService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.cloud.context.config.annotation.RefreshScope;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RestController;

@RefreshScope
@RestController
public class NacosConsumerFeignController {

    @Autowired
    private EchoService echoService;

    @Value("${user.name}")
    private String username;

    @GetMapping(value = "/feign/echo/{str}")
    public String echo(@PathVariable String str) {
        return echoService.echo(str);
    }

    @GetMapping(value = "/feign/echo")
    public String echo() {
        return echoService.echo(username);
    }

    @GetMapping(value = "/lb")
    public String lb(){

        return echoService.lb();
    }

}

通过代码获取 nacos 配置文件里的信息

package com.funtl.hello.spring.cloud.alibaba.nacos.consumer;

import com.alibaba.nacos.api.NacosFactory;
import com.alibaba.nacos.api.config.ConfigService;
import com.alibaba.nacos.api.exception.NacosException;

import java.util.Properties;

/**
 * Created with IntelliJ IDEA.
 *
 * @author: wuchang
 * @Date: 2022/5/5
 * @Time: 18:52
 * @BelongsProject hello-spring-cloud-alibaba
 * @BelongsPackage com.funtl.hello.spring.cloud.alibaba.nacos.consumer
 * @ClassName com.funtl.hello.spring.cloud.alibaba.nacos.consumer.Test
 * @Description: todo
 */
public class Test {

    public static void main(String[] args) throws NacosException {

        String serverAddr = "192.168.3.192:8848";

        String dataId = "nacos-consumer-config.yaml";

        String group  = "DEFAULT_GROUP";

        Properties properties = new Properties();
        properties.put("serverAddr",serverAddr);
        ConfigService configService = NacosFactory.createConfigService(properties);
        String config = configService.getConfig(dataId,group,5000);
        System.out.println(config);

    }
}

输出如下:
image.png

测试效果

访问:[http://192.168.3.191:9091/feign/echo](http://192.168.3.191:9091/feign/echo)
image.png
改修配置文件再次访问
image.png
image.png
配置文件能实时变更了