Eureka 学习之高可用多节点注册中心 (四)
Eureka Server
注册中心可以实现高可用的多节点配置。具体实现方式是多个Eureka Server
互相注册,形成链路,此时Client
注册到任何一个节点,Server
链路会保证服务被同步到所有的注册中心节点上。从而实现高可用的注册中心。哪怕你配置的注册地址eureka.client.service-url.defaultZone
已经宕机了,其它已经被同步的注册中心一样可以提供服务。当然通常情况下我们的服务注册地址也可以是多个的,用逗号分隔。
1. 本地环境配置多节点 Eureka Server
- 通过 Idea 的
Spring Initializr
插件创建项目
- 添加
Eureka Server
依赖
- 启动类中添加注解
@EnableEurekaServer
@SpringBootApplication
@EnableEurekaServer
public class SpringCloudEurekaServerApplication {
public static void main(String[] args) {
SpringApplication.run(SpringCloudEurekaServerApplication.class, args);
}
}
resource
下添加2个配置文件,分别为application-node1.properties
,application-node2.properties
,它们的配置如下。配置本地的hostname
在mac上可以通过/etc/hosts
文件配置,添加如下代码即可,保存退出即可生效,可以试试ping
一下。
127.0.0.1 node1
127.0.0.1 node2
# application-node1.properties
# Eureka 服务端口号
server.port=10001
# 应用名
spring.application.name=spring-cloud-eureka-server
# Eureka 相关配置
# 1.主机名
eureka.instance.hostname=node1
# 2.注册地址 注册到node2节点
eureka.client.service-url.defaultZone=http://node2:10002/eureka/
# application-node2.properties
# Eureka 服务端口号
server.port=10002
# 应用名
spring.application.name=spring-cloud-eureka-server
# Eureka 相关配置
# 1.主机名
eureka.instance.hostname=node2
# 2.注册地址 注册到node1节点
eureka.client.service-url.defaultZone=http://node1:10001/eureka/
这样,它们直接就形成了互相注册的链路关系。
- 在Idea中新增一个
Spring Boot
启动实例,分别命名为eureka-server-node1
和eureka-server-node2
。添加VM option
启动参数-Dspring.profiles.active=node1
以及-Dspring.profiles.active=node2
。
- 启动后通过
http://node1:10001
和http://node2:10002
访问,如下图。此时已经完成了最简单的双节点Eureka Server
的配置。
2. 向多节点的 Eureka Server 注册服务
Eureka Client
基础的创建和服务注册就不写了,以前学习记录过,可以翻看以前的文章。
- 直接上
Client
端的配置文件。
# Eureka 客户端口号
server.port=20001
# 应用名
spring.application.name=service-provider
# Eureka 相关配置
# 1.注册地址 注册到 Eureka Server 服务 同时注册到 node1和node2
eureka.client.service-url.defaultZone=http://node1:10001/eureka/,http://node2:10002/eureka/
- 启动类 添加注释
@EnableDiscoveryClient
@SpringBootApplication
@EnableDiscoveryClient
public class SpringCloudEurekaProviderApplication {
public static void main(String[] args) {
SpringApplication.run(SpringCloudEurekaProviderApplication.class, args);
}
}
- 启动
service-provider
服务
访问 http://node1:10001
和 http://node2:10002
可以看到 service-provider
已在两个节点分别注册。
3.高可用
前面介绍了2个 Eureka Server
注册中心互相注册实现高可用,并且 Eureka Client
也分别注册到了2个Server
中去。可能这样看不出高可用在哪里。因为不管任何一个注册中心节点出故障宕机,另一个节点总有UP的服务存在,毕竟服务是分别注册到了2个节点上。那如果我们只注册到其中1个节点,试试会怎么样。
修改 Client
端的配置文件然后启动
# Eureka 客户端 port
server.port=20001
# 应用名
spring.application.name=service-provider
# Eureka 相关配置
# 1.注册地址 注册到 Eureka Server 服务
eureka.client.service-url.defaultZone=http://node1:10001/eureka/
这时候发现服务同样被分别注册到2个注册中心,这个很好理解,因为两个注册中心是互相注册到对方的,所以node1
会向node2
同步服务。如果此时,关闭 node1
注册中心,会发现node2
的注册中心service-provider
还是UP
状态,并且该服务是可以被调用并且正确响应的(我试过,大家有兴趣也可以试试)。这就有点意思了,明明注册到了node1
节点,同步到了node2
,然后node1
挂了,node2
还是可以继续提供服务。我们知道服务端判断服务健康状态的方式是接收客户端的心跳Ping,那么客户端是注册到node1
上的,为什么还会和node2
保持心跳Ping呢,这个可能就要分析源码了。今后慢慢深入学习时再介绍。
下面看个简单的图:
Client
同时注册到2个Server
而两个Server
也是同步的任何一个Server
故障都能保证Client
的可用。哪怕Client
只注册到一个Server
,只要2个注册中心之间保证链路,即可能保证服务可用。
那如果假设是下面这种情况呢:
经过试验,此时注册到node2
的服务将不会同步到node1
,注册中心之间没有形成环形链路。这种就不是高可用的注册中心集群了。假设你有3个,4个或者更多的注册中心,则必须让他们形成环形链路的注册配置。
4. 总结
通过运行多个实例并要求它们相互注册,可以使Eureka
更具可用性。必须至少形成一个链路连接。不然可能形成分裂故障(官网解释),通俗的理解就是假设多个节点没有形成双向链路,则会形成某些服务不能逆向同步到前一个节点。