【发布时间】:2017-02-03 19:04:02
【问题描述】:
我有在应用程序启动后运行一些初始化脚本的服务(使用ApplicationListener<ApplicationReadyEvent> 实现)。在这个脚本中,我需要使用RestTemplate 调用另一个服务,即@LoadBalanced。当调用服务时,没有关于远程服务实例的信息,因为当时没有联系发现服务器(我猜)。
java.lang.IllegalStateException: No instances available for api-service
at org.springframework.cloud.netflix.ribbon.RibbonLoadBalancerClient.execute(RibbonLoadBalancerClient.java:79)
那么在我的初始化脚本执行之前,有没有办法在应用程序启动时从发现服务器获取可用服务列表?
谢谢
编辑: 问题与事实更相关,即在当前环境(dev)中,所有服务都绑定在一个服务(api-service)中。所以从 api-service 我试图调用不了解自我的@LoadBalanced 客户端 api-service?我可以注册一些监听器或类似的东西来了解 api-service (self) 何时可用?
here 是示例应用程序。我主要感兴趣的是如何工作this method
edit2:
现在可能有创建 EurekaListener 的解决方案
public static class InitializerListener implements EurekaEventListener {
private EurekaClient eurekaClient;
private RestOperations restTemplate;
public InitializerListener(EurekaClient eurekaClient, RestOperations restTemplate) {
this.eurekaClient = eurekaClient;
this.restTemplate = restTemplate;
}
@Override
public void onEvent(EurekaEvent event) {
if (event instanceof StatusChangeEvent) {
if (((StatusChangeEvent) event).getStatus().equals(InstanceInfo.InstanceStatus.UP)) {
ResponseEntity<String> helloResponse = restTemplate.getForEntity("http://api-service/hello-controller/{name}", String.class, "my friend");
logger.debug("Response from controller is {}", helloResponse.getBody());
eurekaClient.unregisterEventListener(this);
}
}
}
}
然后像这样注册它:
EurekaEventListener initializerListener = new InitializerListener(discoveryClient, restTemplate);
discoveryClient.registerEventListener(initializerListener);
但是,这仅在应用程序第一次注册到发现服务时才会执行。下次我停止 api-service 并再次运行它时,不会发布事件。还有什么其他的事件我可以捕捉到吗?
【问题讨论】:
标签: spring-cloud netflix netflix-eureka spring-cloud-netflix netflix-ribbon