代码地址

1. nacos 配置管理

1.1 什么是配置中心

1.1.1 什么是配置

应用程序在启动和运行的时候往往需要读取一些配置信息,配置基本上伴随着应用程序的整个生命周期,比如:数据库连接参数、启动参数等。
配置的特点:

  • 配置是独立于程序的只读变量
    • 同一份程序在不同的配置下会有不同的行为
    • 程序通过配置来改变自己的行为,但是程序不应该去改变配置
  • 配置伴随应用的整个生命周期
    • 应用在启动时通过读取配置来初始化,在运行时根据配置调整行为。比如: 启动时需要读取服务的端口号、系统在运行过程中需要读取定时策略指定定时任务等。
  • 配置可以多种加载方式
    • 常见的有程序内部硬编码,配置文件,环境变量,启动参数,基于数据库等
  • 配置需要治理

    • 权限控制: 由于配置能改变程序的行为,不正确的配置甚至能引起灾难,所以对配置的修改必须有比较完善的权限控制
    • 不同环境、集群配置管理: 同一份程序在不同的环境(开发、测试、生产)、不同的集群(如不同的数据中心)经常需要有不同的配置,所以需要有完善的环境、集群配置管理

      1.1.2 什么是配置中心

      在微服务架构中,当一个单体应用存在的时候,配置中心没有意义,在分布式系统中,一个个单体应用配置分散在各个应用中难以管理,这样配置不仅分散而且还存在冗余状态。
      配置冗余:
      image.png
      配置中心功能
      image.png

      1.2 nacos简介

  • 服务发现和服务健康监测

  • 动态配置服务
  • 动态 DNS 服务
  • 服务及其元数据管理

nacos: Dynamic Naming and Configuration Service nacos文档 github代码

与主流配置中心对比
cloud Alibaba(1)-nacos配置管理 - 图3

1.3 nacos快速入门

1.3.1 nacos server docker 单机安装

配置外部数据支持: 从官网下载解压后获取sql文件 在本地执行 nacos-db.sql
docker 安装说明

  1. docker run -d \
  2. -e MODE=standalone \
  3. -e NACOS_AUTH_ENABLE=true \
  4. -e SPRING_DATASOURCE_PLATFORM=mysql \
  5. -e MYSQL_SERVICE_HOST=192.168.19.128 \
  6. -e MYSQL_SERVICE_PORT=3306 \
  7. -e MYSQL_SERVICE_DB_NAME=nacos \
  8. -e MYSQL_SERVICE_USER=root \
  9. -e MYSQL_SERVICE_PASSWORD=123456 \
  10. -p 8848:8848 \
  11. --name nacos \
  12. nacos/nacos-server

访问 http://192.168.19.128:8848/nacos
image.png

1.3.2 配置说明

命名空间(Namespace)
命名空间( namespace )可用于进行不同环境的配置隔离不同的命名空间下,可以存在相同名称的配置分组(Group)或配置集。
配置分组(Group)
配置分组是对配置集进行分组,不同的配置分组下可以有相同的配置集( DataID)。当在Nacos上创建一个配置时 ,如果未填写配置分组的名称,则配置分组的名称默认采用DEFAULT. GROUP。
配置集(Data ID)
在系统中,一个配置文件通常就是一个配置集, 一个配置集可以包含了系统的各种配置信息,例如,一个配置集可能包含了数据源、线程池、日志级别等配置项。
配置项
就是我们的配置内容
cloud Alibaba(1)-nacos配置管理 - 图5

1.4 nacos配置管理基础应用

springboot版本: 2.4.2
nacos版本:2.0.2

1.4.1 springboot项目集成

目前 springboot注解配置 最高支持到2.3.X,2.4以下可以集成以下配置

  1. <dependency>
  2. <groupId>com.alibaba.boot</groupId>
  3. <artifactId>nacos-config-spring-boot-starter</artifactId>
  4. <version>0.2.8</version>
  5. </dependency>

2.4以上可以集成该配置

  1. <dependency>
  2. <groupId>com.alibaba.cloud</groupId>
  3. <artifactId>spring-cloud-starter-alibaba-nacos-config</artifactId>
  4. <version>2021.1</version>
  5. </dependency>
  6. # 一定要加这个配置 不然读取不到配置
  7. <dependency>
  8. <groupId>org.springframework.cloud</groupId>
  9. <artifactId>spring-cloud-starter-bootstrap</artifactId>
  10. <version>3.0.1</version>
  11. <exclusions>
  12. <exclusion>
  13. <artifactId>spring-cloud-context</artifactId>
  14. <groupId>org.springframework.cloud</groupId>
  15. </exclusion>
  16. <exclusion>
  17. <artifactId>spring-cloud-commons</artifactId>
  18. <groupId>org.springframework.cloud</groupId>
  19. </exclusion>
  20. </exclusions>
  21. </dependency>

1.4.2 springboot项目配置

nacos springboot 配置说明

application.yml

  1. spring:
  2. profiles:
  3. active: dev

bootstrap.yml

  1. spring:
  2. #配置了spring.cloud.nacos.config.name的情况下该配置无需配置,且spring.cloud.nacos.config.name优先级更高
  3. #application:
  4. # name: bootnacos
  5. cloud:
  6. nacos:
  7. config:
  8. namespace: 0c669785-19df-4df0-9fa8-6c6a7ce8c689
  9. #分组 不填就是默认分组 DEFAULT_GROUP
  10. group: MY_GROUP
  11. #必填 nacos地址和端口
  12. server-addr: 192.168.19.128:8848
  13. #配置项类型 默认 properties
  14. file-extension: yaml
  15. # dataId prefix名称
  16. name: bootnacos
  17. # 多个配置文件
  18. extension-configs[0]:
  19. data-id: nacosserver-dev.yaml
  20. refresh: true
  21. #完全开启/关闭配置
  22. enabled: true
  23. #nacos开启了权限管理 需要配置用户名密码
  24. username: nacos
  25. password: nacos

配置了spring.cloud.nacos.config.name的情况下不用配置spring.application.name,且spring.cloud.nacos.config.name优先级更高
配置上面spring.cloud.nacos.config.name是为了组成Data Id ( ${prefix}-${spring.profiles.active}.${fileextension}
在项目启动时会去加载 dataId 默认会去找三个,配置一个即可

  • bootnacos.yml
  • bootnacos-dev.yml (建议使用该配置,颗粒度更细)
  • bootnacos

配置一个配置类和一个控制类

  1. @Component
  2. @Data
  3. @ConfigurationProperties(prefix = "person")
  4. public class Person {
  5. private String userName;
  6. private Boolean boss;
  7. private Date birth;
  8. private Integer age;
  9. private Pet pet;
  10. private String[] interests;
  11. private List<String> animal;
  12. private Map<String, Object> score;
  13. private Set<Double> salarys;
  14. private Map<String, List<Pet>> allPets;
  15. @Data
  16. static class Pet {
  17. private String name;
  18. private Integer weight;
  19. }
  20. }
  1. @RestController
  2. @RequestMapping("/config")
  3. @RefreshScope
  4. public class ConfigController {
  5. @Autowired
  6. private Person person;
  7. @Value("${user.name}")
  8. private String name;
  9. @Value("${user.age}")
  10. private Integer age;
  11. @GetMapping("/getPerson")
  12. public Person getPerson() {
  13. return person;
  14. }
  15. @GetMapping("/getUserName")
  16. public String getUserName() {
  17. return name;
  18. }
  19. @GetMapping("/getUserAge")
  20. public Integer getUserAge() {
  21. return age;
  22. }
  23. }

nacosServer 配置:
bootnacos-dev.yaml

  1. server:
  2. port: 8888
  3. person:
  4. userName: wangwu
  5. boss: false
  6. birth: 2019/12/12 20:12:33
  7. age: 18
  8. pet:
  9. name: tomcat
  10. interests:
  11. - 游泳
  12. - 篮球
  13. animal: [jerry,mario]
  14. score:
  15. english:
  16. first: 30
  17. second: 30
  18. thrid: 30
  19. math:
  20. first: 70
  21. second: 71
  22. thrid: 72
  23. chinese: {first:28,second:89,thrid:78}
  24. salarys: [5979.3,45545]
  25. all-pets:
  26. sick:
  27. - {name: tom}
  28. - {name: 小黑, jerry, weight: 47}
  29. health: [{name: juccy, weight: 47},{name: juccy, weight: 47}]

nacosserver-dev.yaml

  1. user:
  2. name: 曹操
  3. age: 45

启动项目 访问 http://localhost:8888/config/getPerson 可以获取数据
image.png

实时修改 nacosserver-dev.yaml中的数据数据 可以在不重新启动项目的情况下 获取最新的数据 http://localhost:8888/config/getUserName
注意:实时获取最新数据需要加注解@RefreshScope

1.5 nacos 集群管理

官网配置
多台docker容器部署使用ip模式,单台docker构建容器使用hostname模式
本次使用hostname模式 外置挂载mysql

1.5.1 配置修改

  1. git clone --depth 1 https://github.com/nacos-group/nacos-docker.git

修改 cluster-hostname.yaml

  1. version: "3"
  2. services:
  3. nacos1:
  4. hostname: nacos1
  5. container_name: nacos1
  6. image: nacos/nacos-server:${NACOS_VERSION}
  7. volumes:
  8. - ./cluster-logs/nacos1:/home/nacos/logs
  9. - ./init.d/custom.properties:/home/nacos/init.d/custom.properties
  10. ports:
  11. - "8848:8848"
  12. - "9848:9848"
  13. - "9555:9555"
  14. env_file:
  15. - ../env/nacos-hostname.env
  16. restart: always
  17. nacos2:
  18. hostname: nacos2
  19. image: nacos/nacos-server:${NACOS_VERSION}
  20. container_name: nacos2
  21. volumes:
  22. - ./cluster-logs/nacos2:/home/nacos/logs
  23. - ./init.d/custom.properties:/home/nacos/init.d/custom.properties
  24. ports:
  25. - "8849:8848"
  26. - "9849:9848"
  27. env_file:
  28. - ../env/nacos-hostname.env
  29. restart: always
  30. nacos3:
  31. hostname: nacos3
  32. image: nacos/nacos-server:${NACOS_VERSION}
  33. container_name: nacos3
  34. volumes:
  35. - ./cluster-logs/nacos3:/home/nacos/logs
  36. - ./init.d/custom.properties:/home/nacos/init.d/custom.properties
  37. ports:
  38. - "8850:8848"
  39. - "9850:9848"
  40. env_file:
  41. - ../env/nacos-hostname.env
  42. restart: always

修改 nacos-hostname.env

  1. #nacos dev env
  2. PREFER_HOST_MODE=hostname
  3. NACOS_SERVERS=nacos1:8848 nacos2:8848 nacos3:8848
  4. MYSQL_SERVICE_HOST=192.168.19.128
  5. MYSQL_SERVICE_DB_NAME=nacos
  6. MYSQL_SERVICE_PORT=3306
  7. MYSQL_SERVICE_USER=root
  8. MYSQL_SERVICE_PASSWORD=123456
  9. #开启权限
  10. NACOS_AUTH_ENABLE=true

启动容器

  1. docker-compose -f cluster-hostname.yaml up -d

1.5.2配置nginx

  1. user nginx;
  2. worker_processes 1;
  3. error_log /var/log/nginx/error.log warn;
  4. pid /var/run/nginx.pid;
  5. events {
  6. worker_connections 1024;
  7. }
  8. http {
  9. include /etc/nginx/mime.types;
  10. default_type application/octet-stream;
  11. log_format main '$remote_addr - $remote_user [$time_local] "$request" '
  12. '$status $body_bytes_sent "$http_referer" '
  13. '"$http_user_agent" "$http_x_forwarded_for"';
  14. access_log /var/log/nginx/access.log main;
  15. sendfile on;
  16. keepalive_timeout 65;
  17. upstream cluster{
  18. server 192.168.19.128:8848 weight=1 max_fails=2 fail_timeout=30s;
  19. server 192.168.19.128:8849 weight=1 max_fails=2 fail_timeout=30s;
  20. server 192.168.19.128:8850 weight=1 max_fails=2 fail_timeout=30s;
  21. }
  22. server{
  23. listen 13306;
  24. server_name localhost;
  25. large_client_header_buffers 4 16k; # 读取大型客户端请求头的缓冲区的最大数量和大小
  26. client_max_body_size 300m; #设置nginx能处理的最大请求主体大小。
  27. client_body_buffer_size 128k; #请求主体的缓冲区大小。
  28. fastcgi_connect_timeout 300;
  29. fastcgi_send_timeout 300;
  30. fastcgi_read_timeout 300;
  31. fastcgi_buffer_size 64k;
  32. fastcgi_buffers 8 32k;
  33. fastcgi_busy_buffers_size 128k;
  34. fastcgi_temp_file_write_size 64k;
  35. location / {
  36. proxy_pass http://cluster;
  37. }
  38. }
  39. include /etc/nginx/conf.d/*.conf;
  40. }

访问 http://192.168.19.128:13306/nacos
image.png
在项目配置的时候就可以直接配置nginx的地址即可