Spring Cloud Consul 从入门到精通
Consul 介绍和安装
Consul 是什么
Consul 是一个支持多数据中心分布式高可用的服务发现和配置共享的服务软件,采用 Go 语言开发。Consul 支持健康检查,并允许 HTTP 和 DNS 协议调用 API 存储键值对。Consul 采用 Raft 一致性协议算法,来保证服务的高可用;使用 GOSSIP 协议管理成员和广播消息,并且支持 ACL 访问控制。
Consul 的使用场景
- Docker 实例的注册与配置共享
- 与 Consul template 服务集成,动态生成 Nginx 和 HAProxy 等配置文件
- Spring-Cloud-Consul 服务发现和配置文件存储
Consul 的优势
- 使用 Raft 算法来保证一致性, 比 ZooKeeper 的 Paxos 算法更简单直接。
- 支持多数据中心,内外网的服务采用不同的端口进行监听。 ZooKeeper 和 etcd 均不提供多数据中心功能的支持。
- 支持健康检查,etcd 不提供此功能。
- 支持 http 和 dns 协议接口。ZooKeeper 的集成较为复杂,etcd 只支持 http 协议。
- 官方提供 web 管理界面,etcd 无此功能。
- Consul 1.2 新增 Service Mesh 解决方案。
Consul、ZooKeeper、etcd、Eureka 比较
链接
官方网站:https://www.consul.io下载地址:https://www.consul.io/downloads.html启动
Consul 安装包解压完成之后就是一个可执行程序,直接运行即可。
Consul 默认启动为 dev 模式,重启后丢失数据,启动参数详解请见附录部分。
Windows
consul.exe agent -server -bootstrap -advertise 127.0.0.1 -data-dir ./data -ui
Linux
consul agent -server -bootstrap -advertise 127.0.0.1 -data-dir ./data -ui
Mac
- 安装
brew install consul
- 修改 Consul 启动参数:
vim /usr/local/opt/consul/homebrew.mxcl.consul.plist
- 修改 ProgramArguments 部分:
<key>ProgramArguments</key> <array> <string>/usr/local/opt/consul/bin/consul</string> <string>agent</string> <string>-server</string> <string>-bootstrap</string> <string>-advertise</string> <string>127.0.0.1</string> <string>-data-dir</string> <string>./data</string> <string>-ui</string> </array>
- 启动: bash brew services start consul
访问 Web 界面
我们为 Consul 添加了 -ui 启动参数,就会自动 Consul 的 Web 界面。端口默认为 8500,本地访问:http://localhost:8500/。
Spring Cloud Consul
Spring Cloud Consul 项目是 Spring Cloud 针对 Consul 服务治理的实现。
提供了服务发现(可替代Eureka)和配置管理(可替代Spring Cloud Config)的功能。
服务发现
1. 使用 IDEA Spring Initalizr 创建项目(consul-demo)
添加 Consul Discovery 和 Actuator (用于 Consul 服务监控检查)依赖:
注意:Spring Boot 2.0 的变化,2.0 actuator http 默认只开启了 health 和 info,全功能开放需要添加配置。
management: endpoints: web: exposure: include: '*'
2. 新建 bootstrap.yml 配置文件
spring: application: name: consul-demo cloud: consul: host: localhost port: 8500
3. 查看 Consul web 界面可以看到 consul-demo 服务已经注册
分布式配置
Consul 提供了用于存储配置和其他元数据的 [键/值存储]。是 Spring Cloud Consul Config 的替代方案。
默认情况下,配置存储在 /config 文件夹中。根据应用程序的名称和模拟 Spring Cloud Config 顺序解析属性的活动配置文件,创建多个 PropertySource 实例。
例如,名为“consul-demo”的应用程序和“dev”配置文件将创建以下属性源:
config/consul-demo,dev/ config/consul-demo/ config/application,dev/ config/application/
注意:application 为所有服务的通用配置。,dev 表示 dev 环境的配置。
更改依赖
想要使用 Spring Cloud Consul 的分布式配置功能,需要将 spring-cloud-starter-consul-discovery 依赖更改为 spring-cloud-starter-consul-all。
注:spring-cloud-starter-consul-all 中包含了下列依赖:
<!--消息总线,提供配置实时刷新,不再依赖中间件--> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-consul-bus</artifactId> </dependency> <!--consul的配置中心功能--> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-consul-config</artifactId> </dependency> <!--服务注册和发现功能--> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-consul-discovery</artifactId> </dependency>
在 Consul KEY/VALUE 中添加配置
首先,在 bootstrap.yml 中添加 Consul 配置:
key spring.cloud.consul.config.format value yaml spring: cloud: consul: host: localhost port: 8500 config: format: yaml
然后:打开 Consul UI 界面添加 key/value 配置:
添加 consul-demo 服务配置:config/consul-demo/data
server: port: 8100
添加通用配置:config/application/data
management: endpoints: web: exposure: include: '*'
配置的自动更新
Consul 中的 key/value 配置更改之后 Spring Cloud 服务端需要开启 Spring 的定时任务 watch Consul 中的配置,添加注解:@EnableScheduling 。
不同于 Spring cloud config 的配置更新机制(配置更新之后使用 bus 将配置变动推送给各个服务),Spring Cloud Consul 采用的是客户端定时 watch Consul 中的 key/value 变化,然后触发 Spring 的 RefreshEvent,刷新上下文。
Consul 集群搭建
Consul 集群搭建最方便的方式是采用 Docker compose。
集群说明
- 3 server 节点(consul-server1 ~ 3)和 2 node 节点(consul-node1 ~ 2)
- 映射本地 consul/data1 ~ 3/ 目录到 Docker 容器中,避免 Consul 集群重启后数据丢失。
- Consul web http 端口分别为 8501、8502、8503
新建 docker-compose.yml
version: '2.0' services: consul-server1: image: consul:latest hostname: "consul-server1" ports: - "8501:8500" volumes: - ./consul/data1:/consul/data command: "agent -server -bootstrap-expect 3 -ui -disable-host-node-id -client 0.0.0.0" consul-server2: image: consul:latest hostname: "consul-server2" ports: - "8502:8500" volumes: - ./consul/data2:/consul/data command: "agent -server -ui -join consul-server1 -disable-host-node-id -client 0.0.0.0" depends_on: - consul-server1 consul-server3: image: consul:latest hostname: "consul-server3" ports: - "8503:8500" volumes: - ./consul/data3:/consul/data command: "agent -server -ui -join consul-server1 -disable-host-node-id -client 0.0.0.0" depends_on: - consul-server1 consul-node1: image: consul:latest hostname: "consul-node1" command: "agent -join consul-server1 -disable-host-node-id" depends_on: - consul-server1 consul-node2: image: consul:latest hostname: "consul-node2" command: "agent -join consul-server1 -disable-host-node-id" depends_on: - consul-server1
集群启动时默认以 consul-server1 为 leader,然后 server2 ~ 3 和 node1 ~ 2 加入到该集群。当 server1 出现故障下线是,server2 ~ 3 则会进行选举选出新leader。
集群操作
- 创建并启动集群:docker-compose up -d
- 停止整个集群:docker-compose stop
- 启动集群:docker-compose start
- 清除整个集群:docker-compose rm(注意:需要先停止)
访问
- http://localhost:8501
- http://localhost:8502
- http://localhost:8503
Consul 负载均衡
Consul 可以使用 Ngxin 来做集群的负载均衡。
设定负载均衡的服务器列表
upstream consul { server 127.0.0.1:8501; server 127.0.0.1:8502; server 127.0.0.1:8503; }
服务配置
server { listen 80; server_name consul.test.com;#服务域名,需要填写你的服务域名 location / { proxy_pass http://consul;#请求转向consul服务器列表 proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; } }
Spring Cloud 服务中 Consul 的地址填写 http://consul.test.com (你的服务域名)即可,不需要像 Eureka 中需要填写各个服务的地址,Consul 的集群轻量高效。
总结
相较于 Eureka,Consul 有着更少的资源占用能支撑更大的规模集群。
相较于 Spring Cloud Config 配置中心,使用起来没有 Git 存储的配置管理版本追溯方便,需要自己采用用数据库管理配置并同步到 Consul 的方式。
但是 Spring Cloud Consul 的配置更新方式更加简单高效。