From bfd4efcd94d09a38efe97a125d8f18cbae723e96 Mon Sep 17 00:00:00 2001 From: Spencer Gibb Date: Mon, 22 Feb 2016 17:01:57 -0700 Subject: [PATCH] Ignore EurekaHealthIndicator (boot) in EurekaHealthCheckHandler (eureka). See corresponding change in s-c-commons https://github.com/spring-cloud/spring-cloud-commons/commit/539a537abba58ed2261c4485d7f9426d2aa57453 fixes gh-643 --- spring-cloud-netflix-eureka-client/pom.xml | 5 ++ .../eureka/EurekaHealthCheckHandler.java | 27 ++++++-- .../eureka/EurekaHealthCheckHandlerTests.java | 68 +++++++++++++++---- 3 files changed, 81 insertions(+), 19 deletions(-) diff --git a/spring-cloud-netflix-eureka-client/pom.xml b/spring-cloud-netflix-eureka-client/pom.xml index c8e1224c..7e28f957 100644 --- a/spring-cloud-netflix-eureka-client/pom.xml +++ b/spring-cloud-netflix-eureka-client/pom.xml @@ -21,6 +21,11 @@ spring-boot-configuration-processor true + + org.springframework.boot + spring-boot-starter-actuator + true + org.springframework.cloud spring-cloud-netflix-core diff --git a/spring-cloud-netflix-eureka-client/src/main/java/org/springframework/cloud/netflix/eureka/EurekaHealthCheckHandler.java b/spring-cloud-netflix-eureka-client/src/main/java/org/springframework/cloud/netflix/eureka/EurekaHealthCheckHandler.java index ba337085..419ffd61 100644 --- a/spring-cloud-netflix-eureka-client/src/main/java/org/springframework/cloud/netflix/eureka/EurekaHealthCheckHandler.java +++ b/spring-cloud-netflix-eureka-client/src/main/java/org/springframework/cloud/netflix/eureka/EurekaHealthCheckHandler.java @@ -16,23 +16,24 @@ package org.springframework.cloud.netflix.eureka; -import static com.netflix.appinfo.InstanceInfo.InstanceStatus; - import java.util.HashMap; import java.util.Map; +import com.netflix.appinfo.HealthCheckHandler; +import com.netflix.appinfo.InstanceInfo; + import org.springframework.beans.BeansException; import org.springframework.beans.factory.InitializingBean; import org.springframework.boot.actuate.health.CompositeHealthIndicator; import org.springframework.boot.actuate.health.HealthAggregator; import org.springframework.boot.actuate.health.HealthIndicator; import org.springframework.boot.actuate.health.Status; +import org.springframework.cloud.client.discovery.health.DiscoveryCompositeHealthIndicator; import org.springframework.context.ApplicationContext; import org.springframework.context.ApplicationContextAware; import org.springframework.util.Assert; -import com.netflix.appinfo.HealthCheckHandler; -import com.netflix.appinfo.InstanceInfo; +import static com.netflix.appinfo.InstanceInfo.InstanceStatus; /** * A Eureka health checker, maps the application status into {@link InstanceStatus} @@ -72,10 +73,24 @@ public class EurekaHealthCheckHandler implements HealthCheckHandler, Application @Override public void afterPropertiesSet() throws Exception { - final Map healthIndicators = applicationContext.getBeansOfType(HealthIndicator.class); + for (Map.Entry entry : healthIndicators.entrySet()) { - healthIndicator.addHealthIndicator(entry.getKey(), entry.getValue()); + + //ignore EurekaHealthIndicator and flatten the rest of the composite + //otherwise there is a never ending cycle of down. See gh-643 + if (entry.getValue() instanceof DiscoveryCompositeHealthIndicator) { + DiscoveryCompositeHealthIndicator indicator = (DiscoveryCompositeHealthIndicator) entry.getValue(); + for (DiscoveryCompositeHealthIndicator.Holder holder : indicator.getHealthIndicators()) { + if (!(holder.getDelegate() instanceof EurekaHealthIndicator)) { + healthIndicator.addHealthIndicator(holder.getDelegate().getName(), holder); + } + } + + } + else { + healthIndicator.addHealthIndicator(entry.getKey(), entry.getValue()); + } } } diff --git a/spring-cloud-netflix-eureka-client/src/test/java/org/springframework/cloud/netflix/eureka/EurekaHealthCheckHandlerTests.java b/spring-cloud-netflix-eureka-client/src/test/java/org/springframework/cloud/netflix/eureka/EurekaHealthCheckHandlerTests.java index 6a40edbf..6b4c47f9 100644 --- a/spring-cloud-netflix-eureka-client/src/test/java/org/springframework/cloud/netflix/eureka/EurekaHealthCheckHandlerTests.java +++ b/spring-cloud-netflix-eureka-client/src/test/java/org/springframework/cloud/netflix/eureka/EurekaHealthCheckHandlerTests.java @@ -16,7 +16,9 @@ package org.springframework.cloud.netflix.eureka; -import static org.junit.Assert.assertEquals; +import java.util.List; + +import com.netflix.appinfo.InstanceInfo.InstanceStatus; import org.junit.Before; import org.junit.Test; @@ -24,11 +26,14 @@ import org.springframework.boot.actuate.health.AbstractHealthIndicator; import org.springframework.boot.actuate.health.Health; import org.springframework.boot.actuate.health.HealthIndicator; import org.springframework.boot.actuate.health.OrderedHealthAggregator; +import org.springframework.cloud.client.discovery.health.DiscoveryClientHealthIndicator; +import org.springframework.cloud.client.discovery.health.DiscoveryCompositeHealthIndicator; +import org.springframework.cloud.client.discovery.health.DiscoveryHealthIndicator; import org.springframework.context.ApplicationContext; import org.springframework.context.annotation.AnnotationConfigApplicationContext; import org.springframework.context.annotation.Bean; -import com.netflix.appinfo.InstanceInfo; +import static org.junit.Assert.assertEquals; /** * Tests the {@link EurekaHealthCheckHandler} with different health indicator registered. @@ -48,8 +53,8 @@ public class EurekaHealthCheckHandlerTests { @Test public void testNoHealthCheckRegistered() throws Exception { - InstanceInfo.InstanceStatus status = healthCheckHandler.getStatus(InstanceInfo.InstanceStatus.UNKNOWN); - assertEquals(InstanceInfo.InstanceStatus.UNKNOWN, status); + InstanceStatus status = healthCheckHandler.getStatus(InstanceStatus.UNKNOWN); + assertEquals(InstanceStatus.UNKNOWN, status); } @Test @@ -57,8 +62,8 @@ public class EurekaHealthCheckHandlerTests { initialize(UpHealthConfiguration.class); - InstanceInfo.InstanceStatus status = healthCheckHandler.getStatus(InstanceInfo.InstanceStatus.UNKNOWN); - assertEquals(InstanceInfo.InstanceStatus.UP, status); + InstanceStatus status = healthCheckHandler.getStatus(InstanceStatus.UNKNOWN); + assertEquals(InstanceStatus.UP, status); } @Test @@ -66,8 +71,8 @@ public class EurekaHealthCheckHandlerTests { initialize(UpHealthConfiguration.class, DownHealthConfiguration.class); - InstanceInfo.InstanceStatus status = healthCheckHandler.getStatus(InstanceInfo.InstanceStatus.UNKNOWN); - assertEquals(InstanceInfo.InstanceStatus.DOWN, status); + InstanceStatus status = healthCheckHandler.getStatus(InstanceStatus.UNKNOWN); + assertEquals(InstanceStatus.DOWN, status); } @Test @@ -75,10 +80,19 @@ public class EurekaHealthCheckHandlerTests { initialize(FatalHealthConfiguration.class); - InstanceInfo.InstanceStatus status = healthCheckHandler.getStatus(InstanceInfo.InstanceStatus.UNKNOWN); - assertEquals(InstanceInfo.InstanceStatus.UNKNOWN, status); + InstanceStatus status = healthCheckHandler.getStatus(InstanceStatus.UNKNOWN); + assertEquals(InstanceStatus.UNKNOWN, status); } + @Test + public void testEurekaIgnored() throws Exception { + + initialize(EurekaDownHealthConfiguration.class); + + InstanceStatus status = healthCheckHandler.getStatus(InstanceStatus.UP); + assertEquals(InstanceStatus.UP, status); + } + private void initialize(Class... configurations) throws Exception { ApplicationContext applicationContext = new AnnotationConfigApplicationContext(configurations); healthCheckHandler.setApplicationContext(applicationContext); @@ -88,7 +102,7 @@ public class EurekaHealthCheckHandlerTests { public static class UpHealthConfiguration { @Bean - public HealthIndicator upIndicator() { + public HealthIndicator healthIndicator() { return new AbstractHealthIndicator() { @Override protected void doHealthCheck(Health.Builder builder) throws Exception { @@ -101,7 +115,7 @@ public class EurekaHealthCheckHandlerTests { public static class DownHealthConfiguration { @Bean - public HealthIndicator upIndicator() { + public HealthIndicator healthIndicator() { return new AbstractHealthIndicator() { @Override protected void doHealthCheck(Health.Builder builder) throws Exception { @@ -114,7 +128,7 @@ public class EurekaHealthCheckHandlerTests { public static class FatalHealthConfiguration { @Bean - public HealthIndicator upIndicator() { + public HealthIndicator healthIndicator() { return new AbstractHealthIndicator() { @Override protected void doHealthCheck(Health.Builder builder) throws Exception { @@ -123,4 +137,32 @@ public class EurekaHealthCheckHandlerTests { }; } } + + + public static class EurekaDownHealthConfiguration { + @Bean + public DiscoveryHealthIndicator discoveryHealthIndicator() { + return new DiscoveryClientHealthIndicator(null) { + @Override + public Health health() { + return Health.up().build(); + } + }; + } + + @Bean + public DiscoveryHealthIndicator eurekaHealthIndicator() { + return new EurekaHealthIndicator(null, null, null) { + @Override + public Health health() { + return Health.down().build(); + } + }; + } + + @Bean + public DiscoveryCompositeHealthIndicator discoveryCompositeHealthIndicator(List indicators) { + return new DiscoveryCompositeHealthIndicator(new OrderedHealthAggregator(), indicators); + } + } } \ No newline at end of file