Netflix Eureka - Eureka Server 集群注册表同步以及高可用

125 阅读4分钟

本文已参与「新人创作礼」活动,一起开启掘金创作之路。


Netflix Eureka 目录汇总

  1. eureka server启动以及初始化

  2. eureka client启动以及初始化

  3. 服务注册

    3.1 可重入读写锁-读锁

  4. 服务发现

    4.1. 全量抓取注册表

    4.2. 注册表多级缓存机制

    4.3. 注册表多级缓存过期机制(主动、定时、被动)

    4.4. 增量抓取注册表

     4.4.1. 一致性Hash对比机制
    
     4.4.2. 可重入读写锁-写锁
    
  5. 服务续约

  6. 服务下线

  7. 服务故障自动感知及服务实例自动摘除

  8. 自我保护机制

  9. Eureka Server集群注册表同步及高可用


Netflix Eureka 时间间隔简要

服务注册(延迟40秒执行注册逻辑)

服务发现-

读写缓存-定时过期(180秒)

只读缓存-被动过期(30秒(整30秒))

定时抓取增量注册表(30秒)

定时删除超过3分钟的服务实例变更记录(30秒)

服务续约(30秒)

服务下线

服务故障自动感知及服务实例自动摘除(感知:90秒(BUG:90 * 2秒);摘除:60秒)

自我保护机制

每分钟期望的续约次数 & 每分钟期望的续约次数阈值(15分钟)

MeasuredRate renewsLastMin(60秒)

Eureka Server集群信息更新(10分钟)


注册表同步以及高可用

构造集群信息

初始化集群信息

同步集群注册表

服务注册、服务下线、服务续约状态同步

(1)构造及初始化集群信息

PeerEurekaNodes.start()

项目eureka core的EurekaBootStrap监听器构造PeerEurekaNodes实例,处理eureka server集群信息的初始化,serverContext.initialize()执行PeerEurekaNodes.start()方法启动 eureka-server 集群,10分钟一次定时调度updatePeerEurekaNodes()方法,更新eureka server 集群信息。

resolvePeerUrls()解析配置文件中的其他eureka server的url地址,基于url地址构造一个一个的PeerEurekaNode放入PeerEurekaNodes中,一个PeerEurekaNode就代表了一个eureka server。启动一个后台的线程,默认是每隔10分钟,会运行一个任务,就是基于配置文件中的url来刷新eureka server列表。

(2)同步注册表

registry.syncUp()

// 从相邻的一个eureka server节点拷贝注册表的信息,如果拷贝失败,就找下一个
// Copy registry from neighboring eureka node
此处的相邻节点说的是eurekaClient.getApplications()。
获取 eurekaClient.getApplications()时,是从EurekaServerConfig服务端地址配置项中取的第一个地址。相邻说的是这个地址。

当前这个eureka server会从任何一个其他的eureka server拉取注册表过来放在自己本地,作为初始的注册表。将自己作为一个eureka client,找任意一个eureka server来拉取注册表,将拉取到的注册表放到自己本地去。

eurekaClient.getApplications()

DiscoveryClient初始化时,调用getAndStoreFullRegistry()拉取全量注册表,放入remoteRegionsRef变量中,使用eurekaClient.getApplications()获取。

eureka server自己本身本来就是个eureka client,在初始化的时候,就会去找任意的一个eureka server拉取注册表到自己本地来,把这个注册表放到自己身上来,作为自己这个eureka server的注册表

(3)注册、下线、故障、心跳

如何从一台eureka server同步到另外一台eureka server上去的?(服务集群(A->B)之间对服务实例Action的同步)

replicateToPeers

isReplication = true :代表是同步节点,即eureka serverB节点。执行ActionType对应的操作(注册、下线、故障、心跳)关联的服务实例的操作,但是不继续执行同步操作。 peerEurekaNodes.getPeerEurekaNodes():遍历除自己以外其他的所有服务节点,执行ActionType对应的操作。

ApplicationResource.addInstance()方法,负责注册,先在自己本地完成一个注册register()(此时isReplication = false),然后对PeerEurekaNodes中的每个一个PeerEurekaNode调用replicateToPeers()(isReplication = false)方法,将这次注册请求,同步注册(此时restful请求头的isReplication = true,仅注册不同步)到其他所有的eureka server。

eureka client来找eureka server进行注册,isReplication是false,此时会给其他所有的配置的eureka server都同步这个注册请求,调用其他所有的eureka server的restful接口,去执行这个服务实例的注册的请求。

ReplicationHttpClient实现抽象方法addExtraHeaders()设置x-netflix-discovery-replication = true,此时同步注册请求给其他eureka server,其他eureka server接到这个同步的请求,仅仅在自己本地执行,不会再次向其他的eureka server去进行注册