自我保护机制

当EurekaServer与EurekaClient网络不通的情况下,EurekaServer不会将EurekaClient服务剔除。

通过一个场景来了解一下:

有两个服务:用户服务app-user、订单服务app-order,用户服务做了集群,有两台机器,分别是8010和8011

keepalived心跳检查端口_keepalived心跳检查端口


现在order使用负载均衡的轮询机制,调用user的接口,可以看到是8010和8011轮询访问的。

keepalived心跳检查端口_微服务_02


那如果现在8010这台服务宕机了,会是什么情况?


keepalived心跳检查端口_java_03


当访问8010的时候,就报错了,我们再看一下Eureka的注册列表,宕机的8010还在列表之中

keepalived心跳检查端口_重启_04


自我保护机制说明:

keepalived心跳检查端口_微服务_05

默认情况下,“EurekaClient客户端”会定时(默认5秒)向“EurekaServer注册中心”发送心跳包,就是说EurekaClient会定时向EurekaServer发送一个请求,如果EurekaServer能收到,就知道当前这个EurekaClient是存活状态。

如果EurekaServer在一定时间内(一般默认是90秒),没有收到EurekaClient发送的心跳包,就会从服务列表中剔除该服务。但是如果在短时间内丢失了大量服务实例的心跳,这时候EurekaServer就会开启自我保护机制,不会剔除服务。

在什么环境下开启自我保护机制?
  • 本地环境
    建议关闭自我保护机制。因为在本地开发环境中,EurekaServer端相对来说重启频率不高,但是在EurekaClient端,可能改动代码之后需要重启,频率相对来说比较高;那么EurekaClient端重启之后就不会及时去向EurekaServer端发送心跳包,EurekaServer端就会认为是网络延迟或者其他原因,不会剔除服务,这样的话就会影响开发效率。
  • 生产环境
    建议开启自我保护机制。因为生产环境不会频繁重启服务器,并且EurekaClient端与EurekaServer端存在网络延迟的几率较高,所以需要开启自我保护机制避免误删服务。
如何关闭自我保护机制?
  • 在EurekaServer端的yml配置文件中加入如下配置:
eureka:
  server:
    # 服务自保机制,默认开启
    enable-self-preservation: true
    # 每隔多久触发一次服务剔除(单位ms毫秒)
    eviction-interval-timer-in-ms: 10000
  • 然后再在EurekaClient端的yml配置文件中添加如下配置:
eureka:
  client:
    service-url:
      defaultZone: http://localhost:20000/eureka/
  instance:
    # 每间隔5秒钟,向服务中心发送一条续约指令
    # 心跳检测与续约时间(开发环境可以将值设小一点,保证服务关闭后注册中心能及时剔除)
    lease-expiration-duration-in-seconds: 5
    # 如果30秒内,依然没有收到续约请求,判断服务过期
    lease-renewal-interval-in-seconds: 30

同样还是用之前的例子,把服务都打开,看一下注册列表:

keepalived心跳检查端口_keepalived心跳检查端口_06


user有两台,然后现在把8011这台服务关了,再刷新一下,8011就被剔除了。

keepalived心跳检查端口_java_07