Eureka Client无法反映OUT_OF_SERVICE的手动状态

时间:2018-09-04 20:46:18

标签: spring-cloud netflix-eureka

我有一个使用Eureka来发现工作程序的管理程序。两者都使用Spring Cloud Netflix及其提供的自动配置来进行服务注册和发现。

有时候,经理将一个实例标记为OUT_OF_SERVICE,然后在一段时间(以分钟为单位)上将该实例标记为UP

管理器使用CloudEurekaClient发现实例,然后设置其状态:

@Autowired
private CloudEurekaClient cloudEurekaClient;

...

InstanceInfo instance = cloudEurekaClient.getNextServerFromEureka(WORKER_SERVICE_NAME, false);
cloudEurekaClient.setStatus(InstanceInfo.InstanceStatus.OUT_OF_SERVICE, instance);
// do some work
cloudEurekaClient.setStatus(InstanceInfo.InstanceStatus.UP, instance);

这似乎很好。 Eureka服务器状态页面显示我的实例从UPOUT_OF_SERVICE

enter image description here

但是,CloudEurekaClient似乎并不知道实例是OUT_OF_SERVICE。相反,使用调试器,我发现实例的状态为UP,而overridenStatus的状态为UNKNOWN

enter image description here

注意:如果我调用cloudEurekaClient.getApplication("worker").getInstances(),它将显示4个UP实例,但没有提及OUT_OF_SERVICE实例。

这是预期的吗?我以为eureka客户知道实例是OUT_OF_SERVICE,但这不是我所看到的行为。这会给我使用CloudEurekaClient来显示UPOUT_OF_SERVICE实例数的运行状况指示器带来问题。

1 个答案:

答案 0 :(得分:0)

经过一番挖掘,问题似乎在于设置实例状态立即调用Eureka Server,这就是服务器状态UI实时显示正确状态的原因:

public void setStatus(InstanceStatus newStatus, InstanceInfo info) {
    getEurekaHttpClient().statusUpdate(info.getAppName(), info.getId(), newStatus, info);
}

但是,调用CloudEurekaServer.getNextServerFromEureka()使用的本地缓存仅由EurekaClientConfig.getRegistryFetchIntervalSeconds()定义的计时器定期更新。

所以我处于竞争状态,如果我将实例状态设置为OUT_OF_SERVICE并尝试在刷新缓存之前向发现客户端查询应用程序,则客户端和服务器对实例的视图不同。如果我在等待 registryRefreshInterval 秒之后再向客户端询问下一个服务器,它将正确地忽略我手动进入OUT_OF_SERVICE状态的实例。