From c7a86fb899439ac104cfa77e57f4aba06015d2ae Mon Sep 17 00:00:00 2001 From: Nitish Goyal Date: Wed, 17 Jul 2019 13:08:12 +0530 Subject: [PATCH 1/8] Clojars integration --- hystrix-core/build.gradle | 36 ++++++++++++++++++++++++++++++++++++ 1 file changed, 36 insertions(+) diff --git a/hystrix-core/build.gradle b/hystrix-core/build.gradle index 8955c78e9..7fbafbf78 100644 --- a/hystrix-core/build.gradle +++ b/hystrix-core/build.gradle @@ -1,3 +1,22 @@ +buildscript { + repositories { + jcenter() + maven{ + name 'clojars' + url 'http://clojars.org/repo' + } + } + dependencies { + classpath 'com.netflix.nebula:nebula-clojure-plugin:4.0.1' + } +} +apply plugin: 'nebula.clojure' // this is a wrapper around clojuresque to make it behave well with other plugins + +repositories { + mavenCentral() + clojarsRepo() +} + apply plugin: 'osgi' apply plugin: 'me.champeau.gradle.jmh' @@ -11,6 +30,23 @@ dependencies { } +version = '1.5.0' +apply plugin: "groovy" +apply plugin: 'maven' + +uploadArchives { + repositories { + mavenDeployer { + repository(url: "https://clojars.org/repo"){ + authentication(userName: "", password: "") + } + pom.version = '1.5.11.1' + pom.groupId = 'org.hystrix' + pom.artifactId = 'hystrix-core' + } + } +} + javadoc { // the exclude isn't working, nor is there a subPackages options as docs suggest there should be // we do not want the com.netflix.hystrix.util package include From 3ce557e7a51674e24acc05c985799aa65146425c Mon Sep 17 00:00:00 2001 From: Nitish Goyal Date: Tue, 14 May 2019 07:59:46 +0530 Subject: [PATCH 2/8] Updated metrics and updated thread pool metrics at runtime --- .../hystrix/perf/CollapserPerfTest.java | 3 +- .../perf/CommandExecutionPerfTest.java | 2 +- .../netflix/hystrix/HystrixThreadPool.java | 32 ++++++++++++++++--- .../properties/HystrixPropertiesFactory.java | 19 +++++------ .../hystrix/HystrixThreadPoolTest.java | 4 +-- 5 files changed, 41 insertions(+), 19 deletions(-) diff --git a/hystrix-core/src/jmh/java/com/netflix/hystrix/perf/CollapserPerfTest.java b/hystrix-core/src/jmh/java/com/netflix/hystrix/perf/CollapserPerfTest.java index 3e155514b..2aafcd30d 100644 --- a/hystrix-core/src/jmh/java/com/netflix/hystrix/perf/CollapserPerfTest.java +++ b/hystrix-core/src/jmh/java/com/netflix/hystrix/perf/CollapserPerfTest.java @@ -36,7 +36,6 @@ import org.openjdk.jmh.annotations.TearDown; import org.openjdk.jmh.infra.Blackhole; import rx.Observable; -import rx.Subscription; import java.util.ArrayList; import java.util.Collection; @@ -52,7 +51,7 @@ public static class ThreadPoolState { public void setUp() { hystrixThreadPool = new HystrixThreadPool.HystrixThreadPoolDefault( HystrixThreadPoolKey.Factory.asKey("PERF") - , HystrixThreadPoolProperties.Setter().withCoreSize(100)); + , HystrixThreadPoolProperties.Setter().withCoreSize(100), false); } @TearDown diff --git a/hystrix-core/src/jmh/java/com/netflix/hystrix/perf/CommandExecutionPerfTest.java b/hystrix-core/src/jmh/java/com/netflix/hystrix/perf/CommandExecutionPerfTest.java index cc40587a7..56d93f696 100644 --- a/hystrix-core/src/jmh/java/com/netflix/hystrix/perf/CommandExecutionPerfTest.java +++ b/hystrix-core/src/jmh/java/com/netflix/hystrix/perf/CommandExecutionPerfTest.java @@ -227,7 +227,7 @@ public static class ThreadPoolState { public void setUp() { hystrixThreadPool = new HystrixThreadPool.HystrixThreadPoolDefault( HystrixThreadPoolKey.Factory.asKey("PERF") - , HystrixThreadPoolProperties.Setter().withCoreSize(100)); + , HystrixThreadPoolProperties.Setter().withCoreSize(100), false); } @TearDown diff --git a/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPool.java b/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPool.java index c68641dbf..1c5ff523d 100644 --- a/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPool.java +++ b/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPool.java @@ -92,6 +92,13 @@ public interface HystrixThreadPool { */ /* package */final static ConcurrentHashMap threadPools = new ConcurrentHashMap(); + /* + * Use the String from HystrixThreadPoolKey.name() instead of the HystrixThreadPoolKey instance as it's just an interface and we can't ensure the object + * we receive implements hashcode/equals correctly and do not want the default hashcode/equals which would create a new threadpool for every object we get even if the name is the same + */ + final static ConcurrentHashMap threadPoolProperties = + new ConcurrentHashMap(); + /** * Get the {@link HystrixThreadPool} instance for a given {@link HystrixThreadPoolKey}. *

@@ -102,17 +109,25 @@ public interface HystrixThreadPool { /* package */static HystrixThreadPool getInstance(HystrixThreadPoolKey threadPoolKey, HystrixThreadPoolProperties.Setter propertiesBuilder) { // get the key to use instead of using the object itself so that if people forget to implement equals/hashcode things will still work String key = threadPoolKey.name(); - + HystrixThreadPoolProperties.Setter oldPropertiesBuilder = threadPoolProperties.get(key); + boolean updated = oldPropertiesBuilder != null && !oldPropertiesBuilder.equals(propertiesBuilder); // this should find it for all but the first time HystrixThreadPool previouslyCached = threadPools.get(key); if (previouslyCached != null) { + if(updated && previouslyCached instanceof HystrixThreadPoolDefault){ + threadPoolProperties.put(key, propertiesBuilder); + ((HystrixThreadPoolDefault)previouslyCached).touchConfig(threadPoolKey, propertiesBuilder); + } return previouslyCached; } // if we get here this is the first time so we need to initialize synchronized (HystrixThreadPool.class) { if (!threadPools.containsKey(key)) { - threadPools.put(key, new HystrixThreadPoolDefault(threadPoolKey, propertiesBuilder)); + threadPools.put(key, new HystrixThreadPoolDefault(threadPoolKey, propertiesBuilder, updated)); + if(propertiesBuilder != null){ + threadPoolProperties.put(key, propertiesBuilder); + } } } return threadPools.get(key); @@ -162,14 +177,15 @@ public interface HystrixThreadPool { /* package */static class HystrixThreadPoolDefault implements HystrixThreadPool { private static final Logger logger = LoggerFactory.getLogger(HystrixThreadPoolDefault.class); - private final HystrixThreadPoolProperties properties; + private HystrixThreadPoolProperties properties; private final BlockingQueue queue; private final ThreadPoolExecutor threadPool; private final HystrixThreadPoolMetrics metrics; private final int queueSize; - public HystrixThreadPoolDefault(HystrixThreadPoolKey threadPoolKey, HystrixThreadPoolProperties.Setter propertiesDefaults) { - this.properties = HystrixPropertiesFactory.getThreadPoolProperties(threadPoolKey, propertiesDefaults); + public HystrixThreadPoolDefault(HystrixThreadPoolKey threadPoolKey, HystrixThreadPoolProperties.Setter propertiesDefaults, + boolean updated) { + this.properties = HystrixPropertiesFactory.getThreadPoolProperties(threadPoolKey, propertiesDefaults, updated); HystrixConcurrencyStrategy concurrencyStrategy = HystrixPlugins.getInstance().getConcurrencyStrategy(); this.queueSize = properties.maxQueueSize().get(); @@ -206,6 +222,12 @@ public Scheduler getScheduler(Func0 shouldInterruptThread) { return new HystrixContextScheduler(HystrixPlugins.getInstance().getConcurrencyStrategy(), this, shouldInterruptThread); } + private void touchConfig(HystrixThreadPoolKey threadPoolKey, HystrixThreadPoolProperties.Setter newProperties) { + this.properties = HystrixPropertiesFactory.getThreadPoolProperties(threadPoolKey, newProperties, + true); + touchConfig(); + } + // allow us to change things via fast-properties by setting it each time private void touchConfig() { final int dynamicCoreSize = properties.coreSize().get(); diff --git a/hystrix-core/src/main/java/com/netflix/hystrix/strategy/properties/HystrixPropertiesFactory.java b/hystrix-core/src/main/java/com/netflix/hystrix/strategy/properties/HystrixPropertiesFactory.java index 792d7ab09..190f61798 100644 --- a/hystrix-core/src/main/java/com/netflix/hystrix/strategy/properties/HystrixPropertiesFactory.java +++ b/hystrix-core/src/main/java/com/netflix/hystrix/strategy/properties/HystrixPropertiesFactory.java @@ -95,28 +95,29 @@ public static HystrixCommandProperties getCommandProperties(HystrixCommandKey ke * Pass-thru to {@link HystrixPropertiesStrategy#getThreadPoolProperties} implementation. * @param builder * Pass-thru to {@link HystrixPropertiesStrategy#getThreadPoolProperties} implementation. + * @param updated * @return {@link HystrixThreadPoolProperties} instance */ - public static HystrixThreadPoolProperties getThreadPoolProperties(HystrixThreadPoolKey key, HystrixThreadPoolProperties.Setter builder) { + public static HystrixThreadPoolProperties getThreadPoolProperties(HystrixThreadPoolKey key, HystrixThreadPoolProperties.Setter builder, + boolean updated) { HystrixPropertiesStrategy hystrixPropertiesStrategy = HystrixPlugins.getInstance().getPropertiesStrategy(); String cacheKey = hystrixPropertiesStrategy.getThreadPoolPropertiesCacheKey(key, builder); if (cacheKey != null) { HystrixThreadPoolProperties properties = threadPoolProperties.get(cacheKey); - if (properties != null) { + if (properties != null && !updated) { return properties; } else { if (builder == null) { builder = HystrixThreadPoolProperties.Setter(); } - // create new instance - properties = hystrixPropertiesStrategy.getThreadPoolProperties(key, builder); - // cache and return - HystrixThreadPoolProperties existing = threadPoolProperties.putIfAbsent(cacheKey, properties); - if (existing == null) { + synchronized (HystrixPropertiesFactory.class){ + // create new instance + properties = hystrixPropertiesStrategy.getThreadPoolProperties(key, builder); + // cache and return + threadPoolProperties.put(cacheKey, properties); return properties; - } else { - return existing; } + } } else { // no cacheKey so we generate it with caching diff --git a/hystrix-core/src/test/java/com/netflix/hystrix/HystrixThreadPoolTest.java b/hystrix-core/src/test/java/com/netflix/hystrix/HystrixThreadPoolTest.java index faf22f9be..7aec75dd6 100644 --- a/hystrix-core/src/test/java/com/netflix/hystrix/HystrixThreadPoolTest.java +++ b/hystrix-core/src/test/java/com/netflix/hystrix/HystrixThreadPoolTest.java @@ -105,9 +105,9 @@ public HystrixMetricsPublisherThreadPool getMetricsPublisherForThreadPool(Hystri }); HystrixThreadPoolKey threadPoolKey = HystrixThreadPoolKey.Factory.asKey("threadPoolFactoryConcurrencyTest"); HystrixThreadPool poolOne = new HystrixThreadPool.HystrixThreadPoolDefault( - threadPoolKey, HystrixThreadPoolPropertiesTest.getUnitTestPropertiesBuilder()); + threadPoolKey, HystrixThreadPoolPropertiesTest.getUnitTestPropertiesBuilder(), false); HystrixThreadPool poolTwo = new HystrixThreadPool.HystrixThreadPoolDefault( - threadPoolKey, HystrixThreadPoolPropertiesTest.getUnitTestPropertiesBuilder()); + threadPoolKey, HystrixThreadPoolPropertiesTest.getUnitTestPropertiesBuilder(), false); assertThat(poolOne.getExecutor(), is(poolTwo.getExecutor())); //Now that we get the threadPool from the metrics object, this will always be equal HystrixMetricsPublisherThreadPoolContainer hystrixMetricsPublisherThreadPool = From b50bdf3f0391b84d8d9c660a8aca8a4e4d6b4b9b Mon Sep 17 00:00:00 2001 From: Nitish Goyal Date: Tue, 20 Aug 2019 15:10:43 +0530 Subject: [PATCH 3/8] Java version upgrade --- build.gradle | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/build.gradle b/build.gradle index 15e60a933..455e95853 100644 --- a/build.gradle +++ b/build.gradle @@ -31,8 +31,8 @@ subprojects { apply plugin: 'nebula.provided-base' apply plugin: 'nebula.compile-api' - sourceCompatibility = 1.6 - targetCompatibility = 1.6 + sourceCompatibility = 1.8 + targetCompatibility = 1.8 From d05a263bcdd20454500bb994268e76036681868e Mon Sep 17 00:00:00 2001 From: Nitish Goyal Date: Thu, 5 Sep 2019 10:09:53 +0530 Subject: [PATCH 4/8] Updated metrics and updated thread pool metrics at runtime --- .../hystrix/HystrixThreadPoolProperties.java | 27 +++++++++++++++++-- .../properties/HystrixPropertiesFactory.java | 1 - 2 files changed, 25 insertions(+), 3 deletions(-) diff --git a/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPoolProperties.java b/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPoolProperties.java index 56f4e6307..edec0b656 100644 --- a/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPoolProperties.java +++ b/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPoolProperties.java @@ -321,8 +321,31 @@ public Setter withMetricsRollingStatisticalWindowBuckets(int value) { return this; } + @Override + public boolean equals(Object o) { + if(this == o) + return true; + if(!(o instanceof Setter)) + return false; + + Setter setter = (Setter)o; + + if(!coreSize.equals(setter.coreSize)) + return false; + if(!maximumSize.equals(setter.maximumSize)) + return false; + if(!keepAliveTimeMinutes.equals(setter.keepAliveTimeMinutes)) + return false; + return maxQueueSize.equals(setter.maxQueueSize); + } - - + @Override + public int hashCode() { + int result = coreSize.hashCode(); + result = 31 * result + maximumSize.hashCode(); + result = 31 * result + keepAliveTimeMinutes.hashCode(); + result = 31 * result + maxQueueSize.hashCode(); + return result; + } } } diff --git a/hystrix-core/src/main/java/com/netflix/hystrix/strategy/properties/HystrixPropertiesFactory.java b/hystrix-core/src/main/java/com/netflix/hystrix/strategy/properties/HystrixPropertiesFactory.java index 190f61798..aab542e5d 100644 --- a/hystrix-core/src/main/java/com/netflix/hystrix/strategy/properties/HystrixPropertiesFactory.java +++ b/hystrix-core/src/main/java/com/netflix/hystrix/strategy/properties/HystrixPropertiesFactory.java @@ -95,7 +95,6 @@ public static HystrixCommandProperties getCommandProperties(HystrixCommandKey ke * Pass-thru to {@link HystrixPropertiesStrategy#getThreadPoolProperties} implementation. * @param builder * Pass-thru to {@link HystrixPropertiesStrategy#getThreadPoolProperties} implementation. - * @param updated * @return {@link HystrixThreadPoolProperties} instance */ public static HystrixThreadPoolProperties getThreadPoolProperties(HystrixThreadPoolKey key, HystrixThreadPoolProperties.Setter builder, From aa6337840620c015b3e5c2d33ad8ec5eb31dbbe0 Mon Sep 17 00:00:00 2001 From: Nitish Goyal Date: Mon, 16 Sep 2019 12:54:36 +0530 Subject: [PATCH 5/8] 1. Added 95th percentiles 2. Updated codahale metrics publisher to publish updated metrics --- ...ystrixCodaHaleMetricsPublisherCommand.java | 12 +++++++ ...rixCodaHaleMetricsPublisherThreadPool.java | 14 ++++++-- .../netflix/hystrix/HystrixThreadPool.java | 5 +-- .../HystrixMetricsPublisherFactory.java | 32 ++++++++++--------- .../HystrixMetricsPublisherThreadPool.java | 4 +++ 5 files changed, 48 insertions(+), 19 deletions(-) diff --git a/hystrix-contrib/hystrix-codahale-metrics-publisher/src/main/java/com/netflix/hystrix/contrib/codahalemetricspublisher/HystrixCodaHaleMetricsPublisherCommand.java b/hystrix-contrib/hystrix-codahale-metrics-publisher/src/main/java/com/netflix/hystrix/contrib/codahalemetricspublisher/HystrixCodaHaleMetricsPublisherCommand.java index 88bbef9c3..e8542ea29 100644 --- a/hystrix-contrib/hystrix-codahale-metrics-publisher/src/main/java/com/netflix/hystrix/contrib/codahalemetricspublisher/HystrixCodaHaleMetricsPublisherCommand.java +++ b/hystrix-contrib/hystrix-codahale-metrics-publisher/src/main/java/com/netflix/hystrix/contrib/codahalemetricspublisher/HystrixCodaHaleMetricsPublisherCommand.java @@ -333,6 +333,12 @@ public Integer getValue() { return metrics.getExecutionTimePercentile(90); } }); + metricRegistry.register(createMetricName("latencyExecute_percentile_95"), new Gauge() { + @Override + public Integer getValue() { + return metrics.getExecutionTimePercentile(95); + } + }); metricRegistry.register(createMetricName("latencyExecute_percentile_99"), new Gauge() { @Override public Integer getValue() { @@ -382,6 +388,12 @@ public Integer getValue() { return metrics.getTotalTimePercentile(90); } }); + metricRegistry.register(createMetricName("latencyTotal_percentile_95"), new Gauge() { + @Override + public Integer getValue() { + return metrics.getTotalTimePercentile(95); + } + }); metricRegistry.register(createMetricName("latencyTotal_percentile_99"), new Gauge() { @Override public Integer getValue() { diff --git a/hystrix-contrib/hystrix-codahale-metrics-publisher/src/main/java/com/netflix/hystrix/contrib/codahalemetricspublisher/HystrixCodaHaleMetricsPublisherThreadPool.java b/hystrix-contrib/hystrix-codahale-metrics-publisher/src/main/java/com/netflix/hystrix/contrib/codahalemetricspublisher/HystrixCodaHaleMetricsPublisherThreadPool.java index 79fafcb4d..4f1a4332f 100644 --- a/hystrix-contrib/hystrix-codahale-metrics-publisher/src/main/java/com/netflix/hystrix/contrib/codahalemetricspublisher/HystrixCodaHaleMetricsPublisherThreadPool.java +++ b/hystrix-contrib/hystrix-codahale-metrics-publisher/src/main/java/com/netflix/hystrix/contrib/codahalemetricspublisher/HystrixCodaHaleMetricsPublisherThreadPool.java @@ -22,6 +22,8 @@ import com.netflix.hystrix.HystrixThreadPoolProperties; import com.netflix.hystrix.strategy.metrics.HystrixMetricsPublisherThreadPool; import com.netflix.hystrix.util.HystrixRollingNumberEvent; +import java.util.ArrayList; +import java.util.List; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -35,6 +37,7 @@ public class HystrixCodaHaleMetricsPublisherThreadPool implements HystrixMetrics private final MetricRegistry metricRegistry; private final String metricGroup; private final String metricType; + private List metricsList = new ArrayList<>(); static final Logger logger = LoggerFactory.getLogger(HystrixCodaHaleMetricsPublisherThreadPool.class); @@ -156,7 +159,7 @@ public Number getValue() { metricRegistry.register(createMetricName("propertyValue_actualMaximumSize"), new Gauge() { @Override public Number getValue() { - return properties.maximumSize().get(); + return properties.actualMaximumSize(); } }); @@ -182,7 +185,14 @@ public Number getValue() { }); } + @Override + public void tearDown() { + metricsList.forEach(metricRegistry::remove); + } + protected String createMetricName(String name) { - return MetricRegistry.name(metricGroup, metricType, name); + String metricName = MetricRegistry.name(metricGroup, metricType, name); + metricsList.add(metricName); + return metricName; } } diff --git a/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPool.java b/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPool.java index 1c5ff523d..64ae859e8 100644 --- a/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPool.java +++ b/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPool.java @@ -196,7 +196,7 @@ public HystrixThreadPoolDefault(HystrixThreadPoolKey threadPoolKey, HystrixThrea this.queue = this.threadPool.getQueue(); /* strategy: HystrixMetricsPublisherThreadPool */ - HystrixMetricsPublisherFactory.createOrRetrievePublisherForThreadPool(threadPoolKey, this.metrics, this.properties); + HystrixMetricsPublisherFactory.createOrRetrievePublisherForThreadPool(threadPoolKey, this.metrics, this.properties, updated); } @Override @@ -241,9 +241,10 @@ private void touchConfig() { dynamicMaximumSize = dynamicCoreSize; maxTooLow = true; } - // In JDK 6, setCorePoolSize and setMaximumPoolSize will execute a lock operation. Avoid them if the pool size is not changed. if (threadPool.getCorePoolSize() != dynamicCoreSize || (allowSizesToDiverge && threadPool.getMaximumPoolSize() != dynamicMaximumSize)) { + logger.info("Old core pool : {}, new core pool : {}, old max : {}, new max {}" , + threadPool.getCorePoolSize(), dynamicCoreSize, threadPool.getMaximumPoolSize(), dynamicMaximumSize); if (maxTooLow) { logger.error("Hystrix ThreadPool configuration for : " + metrics.getThreadPoolKey().name() + " is trying to set coreSize = " + dynamicCoreSize + " and maximumSize = " + configuredMaximumSize + ". Maximum size will be set to " + diff --git a/hystrix-core/src/main/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherFactory.java b/hystrix-core/src/main/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherFactory.java index 98c7813eb..51ba953e3 100644 --- a/hystrix-core/src/main/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherFactory.java +++ b/hystrix-core/src/main/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherFactory.java @@ -60,8 +60,11 @@ public class HystrixMetricsPublisherFactory { * Pass-thru to {@link HystrixMetricsPublisher#getMetricsPublisherForThreadPool} implementation * @return {@link HystrixMetricsPublisherThreadPool} instance */ - public static HystrixMetricsPublisherThreadPool createOrRetrievePublisherForThreadPool(HystrixThreadPoolKey threadPoolKey, HystrixThreadPoolMetrics metrics, HystrixThreadPoolProperties properties) { - return SINGLETON.getPublisherForThreadPool(threadPoolKey, metrics, properties); + public static HystrixMetricsPublisherThreadPool createOrRetrievePublisherForThreadPool(HystrixThreadPoolKey threadPoolKey, + HystrixThreadPoolMetrics metrics, + HystrixThreadPoolProperties properties, + boolean updated) { + return SINGLETON.getPublisherForThreadPool(threadPoolKey, metrics, properties, updated); } /** @@ -123,25 +126,24 @@ public static void reset() { // String is ThreadPoolKey.name() (we can't use ThreadPoolKey directly as we can't guarantee it implements hashcode/equals correctly) private final ConcurrentHashMap threadPoolPublishers = new ConcurrentHashMap(); - /* package */ HystrixMetricsPublisherThreadPool getPublisherForThreadPool(HystrixThreadPoolKey threadPoolKey, HystrixThreadPoolMetrics metrics, HystrixThreadPoolProperties properties) { + /* package */ HystrixMetricsPublisherThreadPool getPublisherForThreadPool(HystrixThreadPoolKey threadPoolKey, HystrixThreadPoolMetrics metrics, + HystrixThreadPoolProperties properties, boolean updated) { // attempt to retrieve from cache first HystrixMetricsPublisherThreadPool publisher = threadPoolPublishers.get(threadPoolKey.name()); - if (publisher != null) { + if (publisher != null && !updated) { return publisher; } + synchronized (HystrixMetricsPublisherFactory.class){ // it doesn't exist so we need to create it - publisher = HystrixPlugins.getInstance().getMetricsPublisher().getMetricsPublisherForThreadPool(threadPoolKey, metrics, properties); + HystrixMetricsPublisherThreadPool newPublisher = HystrixPlugins.getInstance().getMetricsPublisher() + .getMetricsPublisherForThreadPool(threadPoolKey, metrics, properties); // attempt to store it (race other threads) - HystrixMetricsPublisherThreadPool existing = threadPoolPublishers.putIfAbsent(threadPoolKey.name(), publisher); - if (existing == null) { - // we won the thread-race to store the instance we created so initialize it - publisher.initialize(); - // done registering, return instance that got cached - return publisher; - } else { - // we lost so return 'existing' and let the one we created be garbage collected - // without calling initialize() on it - return existing; + threadPoolPublishers.put(threadPoolKey.name(), newPublisher); + if(publisher != null){ + publisher.tearDown(); + } + newPublisher.initialize(); + return newPublisher; } } diff --git a/hystrix-core/src/main/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherThreadPool.java b/hystrix-core/src/main/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherThreadPool.java index ff3507a39..1ece086ce 100644 --- a/hystrix-core/src/main/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherThreadPool.java +++ b/hystrix-core/src/main/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherThreadPool.java @@ -33,4 +33,8 @@ public interface HystrixMetricsPublisherThreadPool { public void initialize(); + default void tearDown(){ + // Do Nothing + } + } From b144244b339522005d5f832a10a9de323e68f357 Mon Sep 17 00:00:00 2001 From: Nitish Goyal Date: Fri, 4 Oct 2019 11:09:51 +0530 Subject: [PATCH 6/8] Updated metrics and updated thread pool metrics at runtime --- .../HystrixCodaHaleMetricsPublisherThreadPool.java | 2 +- .../HystrixYammerMetricsPublisherThreadPool.java | 13 ++++++++++++- .../java/com/netflix/hystrix/HystrixThreadPool.java | 11 +++-------- .../netflix/hystrix/HystrixThreadPoolMetrics.java | 7 ++++--- .../metrics/HystrixMetricsPublisherThreadPool.java | 2 +- .../com/netflix/hystrix/HystrixThreadPoolTest.java | 2 +- .../metrics/HystrixMetricsPublisherFactoryTest.java | 2 +- 7 files changed, 23 insertions(+), 16 deletions(-) diff --git a/hystrix-contrib/hystrix-codahale-metrics-publisher/src/main/java/com/netflix/hystrix/contrib/codahalemetricspublisher/HystrixCodaHaleMetricsPublisherThreadPool.java b/hystrix-contrib/hystrix-codahale-metrics-publisher/src/main/java/com/netflix/hystrix/contrib/codahalemetricspublisher/HystrixCodaHaleMetricsPublisherThreadPool.java index 4f1a4332f..5fc7a8fa7 100644 --- a/hystrix-contrib/hystrix-codahale-metrics-publisher/src/main/java/com/netflix/hystrix/contrib/codahalemetricspublisher/HystrixCodaHaleMetricsPublisherThreadPool.java +++ b/hystrix-contrib/hystrix-codahale-metrics-publisher/src/main/java/com/netflix/hystrix/contrib/codahalemetricspublisher/HystrixCodaHaleMetricsPublisherThreadPool.java @@ -159,7 +159,7 @@ public Number getValue() { metricRegistry.register(createMetricName("propertyValue_actualMaximumSize"), new Gauge() { @Override public Number getValue() { - return properties.actualMaximumSize(); + return properties.maximumSize().get(); } }); diff --git a/hystrix-contrib/hystrix-yammer-metrics-publisher/src/main/java/com/netflix/hystrix/contrib/yammermetricspublisher/HystrixYammerMetricsPublisherThreadPool.java b/hystrix-contrib/hystrix-yammer-metrics-publisher/src/main/java/com/netflix/hystrix/contrib/yammermetricspublisher/HystrixYammerMetricsPublisherThreadPool.java index aa2b99654..1a960e95c 100644 --- a/hystrix-contrib/hystrix-yammer-metrics-publisher/src/main/java/com/netflix/hystrix/contrib/yammermetricspublisher/HystrixYammerMetricsPublisherThreadPool.java +++ b/hystrix-contrib/hystrix-yammer-metrics-publisher/src/main/java/com/netflix/hystrix/contrib/yammermetricspublisher/HystrixYammerMetricsPublisherThreadPool.java @@ -26,6 +26,9 @@ import org.slf4j.Logger; import org.slf4j.LoggerFactory; +import java.util.ArrayList; +import java.util.List; + /** * Implementation of {@link HystrixMetricsPublisherThreadPool} using Yammer Metrics (https://github.com/codahale/metrics) */ @@ -36,6 +39,7 @@ public class HystrixYammerMetricsPublisherThreadPool implements HystrixMetricsPu private final MetricsRegistry metricsRegistry; private final String metricGroup; private final String metricType; + private List metricsList = new ArrayList<>(); static final Logger logger = LoggerFactory.getLogger(HystrixYammerMetricsPublisherThreadPool.class); @@ -178,7 +182,14 @@ public Number value() { }); } + @Override + public void tearDown() { + metricsList.forEach(metricsRegistry::removeMetric); + } + protected MetricName createMetricName(String name) { - return new MetricName(metricGroup, metricType, name); + MetricName metricName = new MetricName(metricGroup, metricType, name); + metricsList.add(metricName); + return metricName; } } diff --git a/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPool.java b/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPool.java index 64ae859e8..809a18e20 100644 --- a/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPool.java +++ b/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPool.java @@ -116,7 +116,8 @@ public interface HystrixThreadPool { if (previouslyCached != null) { if(updated && previouslyCached instanceof HystrixThreadPoolDefault){ threadPoolProperties.put(key, propertiesBuilder); - ((HystrixThreadPoolDefault)previouslyCached).touchConfig(threadPoolKey, propertiesBuilder); + threadPools.put(key, new HystrixThreadPoolDefault(threadPoolKey, propertiesBuilder, true)); + ((HystrixThreadPoolDefault)previouslyCached).touchConfig(); } return previouslyCached; } @@ -191,7 +192,7 @@ public HystrixThreadPoolDefault(HystrixThreadPoolKey threadPoolKey, HystrixThrea this.metrics = HystrixThreadPoolMetrics.getInstance(threadPoolKey, concurrencyStrategy.getThreadPool(threadPoolKey, properties), - properties); + properties, updated); this.threadPool = this.metrics.getThreadPool(); this.queue = this.threadPool.getQueue(); @@ -222,12 +223,6 @@ public Scheduler getScheduler(Func0 shouldInterruptThread) { return new HystrixContextScheduler(HystrixPlugins.getInstance().getConcurrencyStrategy(), this, shouldInterruptThread); } - private void touchConfig(HystrixThreadPoolKey threadPoolKey, HystrixThreadPoolProperties.Setter newProperties) { - this.properties = HystrixPropertiesFactory.getThreadPoolProperties(threadPoolKey, newProperties, - true); - touchConfig(); - } - // allow us to change things via fast-properties by setting it each time private void touchConfig() { final int dynamicCoreSize = properties.coreSize().get(); diff --git a/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPoolMetrics.java b/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPoolMetrics.java index 22e978b1d..7e8285859 100644 --- a/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPoolMetrics.java +++ b/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPoolMetrics.java @@ -59,15 +59,16 @@ public class HystrixThreadPoolMetrics extends HystrixMetrics { * Pass-thru to {@link HystrixThreadPoolMetrics} instance on first time when constructed * @return {@link HystrixThreadPoolMetrics} */ - public static HystrixThreadPoolMetrics getInstance(HystrixThreadPoolKey key, ThreadPoolExecutor threadPool, HystrixThreadPoolProperties properties) { + public static HystrixThreadPoolMetrics getInstance(HystrixThreadPoolKey key, ThreadPoolExecutor threadPool, + HystrixThreadPoolProperties properties, boolean updated) { // attempt to retrieve from cache first HystrixThreadPoolMetrics threadPoolMetrics = metrics.get(key.name()); - if (threadPoolMetrics != null) { + if (threadPoolMetrics != null && !updated) { return threadPoolMetrics; } else { synchronized (HystrixThreadPoolMetrics.class) { HystrixThreadPoolMetrics existingMetrics = metrics.get(key.name()); - if (existingMetrics != null) { + if (existingMetrics != null && !updated) { return existingMetrics; } else { HystrixThreadPoolMetrics newThreadPoolMetrics = new HystrixThreadPoolMetrics(key, threadPool, properties); diff --git a/hystrix-core/src/main/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherThreadPool.java b/hystrix-core/src/main/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherThreadPool.java index 1ece086ce..91bb6d05a 100644 --- a/hystrix-core/src/main/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherThreadPool.java +++ b/hystrix-core/src/main/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherThreadPool.java @@ -31,7 +31,7 @@ public interface HystrixMetricsPublisherThreadPool { // TODO should the arguments be given via initialize rather than constructor so people can't accidentally do it wrong? - public void initialize(); + void initialize(); default void tearDown(){ // Do Nothing diff --git a/hystrix-core/src/test/java/com/netflix/hystrix/HystrixThreadPoolTest.java b/hystrix-core/src/test/java/com/netflix/hystrix/HystrixThreadPoolTest.java index 7aec75dd6..bcde16eb6 100644 --- a/hystrix-core/src/test/java/com/netflix/hystrix/HystrixThreadPoolTest.java +++ b/hystrix-core/src/test/java/com/netflix/hystrix/HystrixThreadPoolTest.java @@ -112,7 +112,7 @@ public HystrixMetricsPublisherThreadPool getMetricsPublisherForThreadPool(Hystri assertThat(poolOne.getExecutor(), is(poolTwo.getExecutor())); //Now that we get the threadPool from the metrics object, this will always be equal HystrixMetricsPublisherThreadPoolContainer hystrixMetricsPublisherThreadPool = (HystrixMetricsPublisherThreadPoolContainer)HystrixMetricsPublisherFactory - .createOrRetrievePublisherForThreadPool(threadPoolKey, null, null); + .createOrRetrievePublisherForThreadPool(threadPoolKey, null, null, false); ThreadPoolExecutor threadPoolExecutor = hystrixMetricsPublisherThreadPool.getHystrixThreadPoolMetrics().getThreadPool(); //assert that both HystrixThreadPools share the same ThreadPoolExecutor as the one in HystrixMetricsPublisherThreadPool diff --git a/hystrix-core/src/test/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherFactoryTest.java b/hystrix-core/src/test/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherFactoryTest.java index b1a7dde98..4380a8ec6 100644 --- a/hystrix-core/src/test/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherFactoryTest.java +++ b/hystrix-core/src/test/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherFactoryTest.java @@ -57,7 +57,7 @@ public void testSingleInitializePerKey() { public void run() { factory.getPublisherForCommand(TestCommandKey.TEST_A, null, null, null, null); factory.getPublisherForCommand(TestCommandKey.TEST_B, null, null, null, null); - factory.getPublisherForThreadPool(TestThreadPoolKey.TEST_A, null, null); + factory.getPublisherForThreadPool(TestThreadPoolKey.TEST_A, null, null, false); } })); From 65d3c4e0f0832c6c05133224c803affa33d1bae9 Mon Sep 17 00:00:00 2001 From: Nitish Goyal Date: Thu, 10 Oct 2019 10:33:38 +0530 Subject: [PATCH 7/8] Metrics publishing fix --- .../build.gradle | 15 +++++++++ ...rixCodaHaleMetricsPublisherThreadPool.java | 9 ++---- ...strixYammerMetricsPublisherThreadPool.java | 9 +----- hystrix-core/build.gradle | 4 +-- .../netflix/hystrix/HystrixThreadPool.java | 13 +++++--- .../hystrix/HystrixThreadPoolMetrics.java | 7 ++-- .../HystrixMetricsPublisherFactory.java | 32 +++++++++---------- .../HystrixMetricsPublisherThreadPool.java | 6 +--- .../properties/HystrixPropertiesFactory.java | 1 + .../hystrix/HystrixThreadPoolTest.java | 2 +- .../HystrixMetricsPublisherFactoryTest.java | 2 +- 11 files changed, 51 insertions(+), 49 deletions(-) diff --git a/hystrix-contrib/hystrix-codahale-metrics-publisher/build.gradle b/hystrix-contrib/hystrix-codahale-metrics-publisher/build.gradle index 7dc39e9f4..000f2ad0c 100644 --- a/hystrix-contrib/hystrix-codahale-metrics-publisher/build.gradle +++ b/hystrix-contrib/hystrix-codahale-metrics-publisher/build.gradle @@ -1,6 +1,21 @@ +apply plugin: 'maven' + dependencies { compileApi project(':hystrix-core') compileApi 'io.dropwizard.metrics:metrics-core:3.2.2' testCompile 'junit:junit-dep:4.10' testCompile 'org.mockito:mockito-all:1.9.5' } + +uploadArchives { + repositories { + mavenDeployer { + repository(url: "https://clojars.org/repo"){ + authentication(userName: "nitishgoyal13", password: "Shine12@") + } + pom.version = '1.5.11-22' + pom.groupId = 'org.hystrix' + pom.artifactId = 'hystrix-codahale-metrics-publisher' + } + } +} diff --git a/hystrix-contrib/hystrix-codahale-metrics-publisher/src/main/java/com/netflix/hystrix/contrib/codahalemetricspublisher/HystrixCodaHaleMetricsPublisherThreadPool.java b/hystrix-contrib/hystrix-codahale-metrics-publisher/src/main/java/com/netflix/hystrix/contrib/codahalemetricspublisher/HystrixCodaHaleMetricsPublisherThreadPool.java index 5fc7a8fa7..9ef28bdc8 100644 --- a/hystrix-contrib/hystrix-codahale-metrics-publisher/src/main/java/com/netflix/hystrix/contrib/codahalemetricspublisher/HystrixCodaHaleMetricsPublisherThreadPool.java +++ b/hystrix-contrib/hystrix-codahale-metrics-publisher/src/main/java/com/netflix/hystrix/contrib/codahalemetricspublisher/HystrixCodaHaleMetricsPublisherThreadPool.java @@ -145,14 +145,14 @@ public Number getValue() { metricRegistry.register(createMetricName("propertyValue_corePoolSize"), new Gauge() { @Override public Number getValue() { - return properties.coreSize().get(); + return metrics.getCurrentCorePoolSize(); } }); metricRegistry.register(createMetricName("propertyValue_maximumSize"), new Gauge() { @Override public Number getValue() { - return properties.maximumSize().get(); + return metrics.getCurrentMaximumPoolSize(); } }); @@ -185,11 +185,6 @@ public Number getValue() { }); } - @Override - public void tearDown() { - metricsList.forEach(metricRegistry::remove); - } - protected String createMetricName(String name) { String metricName = MetricRegistry.name(metricGroup, metricType, name); metricsList.add(metricName); diff --git a/hystrix-contrib/hystrix-yammer-metrics-publisher/src/main/java/com/netflix/hystrix/contrib/yammermetricspublisher/HystrixYammerMetricsPublisherThreadPool.java b/hystrix-contrib/hystrix-yammer-metrics-publisher/src/main/java/com/netflix/hystrix/contrib/yammermetricspublisher/HystrixYammerMetricsPublisherThreadPool.java index 1a960e95c..be2cec631 100644 --- a/hystrix-contrib/hystrix-yammer-metrics-publisher/src/main/java/com/netflix/hystrix/contrib/yammermetricspublisher/HystrixYammerMetricsPublisherThreadPool.java +++ b/hystrix-contrib/hystrix-yammer-metrics-publisher/src/main/java/com/netflix/hystrix/contrib/yammermetricspublisher/HystrixYammerMetricsPublisherThreadPool.java @@ -182,14 +182,7 @@ public Number value() { }); } - @Override - public void tearDown() { - metricsList.forEach(metricsRegistry::removeMetric); - } - protected MetricName createMetricName(String name) { - MetricName metricName = new MetricName(metricGroup, metricType, name); - metricsList.add(metricName); - return metricName; + return new MetricName(metricGroup, metricType, name); } } diff --git a/hystrix-core/build.gradle b/hystrix-core/build.gradle index 7fbafbf78..a522aae50 100644 --- a/hystrix-core/build.gradle +++ b/hystrix-core/build.gradle @@ -38,9 +38,9 @@ uploadArchives { repositories { mavenDeployer { repository(url: "https://clojars.org/repo"){ - authentication(userName: "", password: "") + authentication(userName: "nitishgoyal13", password: "Shine12@") } - pom.version = '1.5.11.1' + pom.version = '1.5.11-22' pom.groupId = 'org.hystrix' pom.artifactId = 'hystrix-core' } diff --git a/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPool.java b/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPool.java index 809a18e20..46c56c48b 100644 --- a/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPool.java +++ b/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPool.java @@ -116,8 +116,7 @@ public interface HystrixThreadPool { if (previouslyCached != null) { if(updated && previouslyCached instanceof HystrixThreadPoolDefault){ threadPoolProperties.put(key, propertiesBuilder); - threadPools.put(key, new HystrixThreadPoolDefault(threadPoolKey, propertiesBuilder, true)); - ((HystrixThreadPoolDefault)previouslyCached).touchConfig(); + ((HystrixThreadPoolDefault)previouslyCached).touchConfig(threadPoolKey, propertiesBuilder); } return previouslyCached; } @@ -192,12 +191,12 @@ public HystrixThreadPoolDefault(HystrixThreadPoolKey threadPoolKey, HystrixThrea this.metrics = HystrixThreadPoolMetrics.getInstance(threadPoolKey, concurrencyStrategy.getThreadPool(threadPoolKey, properties), - properties, updated); + properties); this.threadPool = this.metrics.getThreadPool(); this.queue = this.threadPool.getQueue(); /* strategy: HystrixMetricsPublisherThreadPool */ - HystrixMetricsPublisherFactory.createOrRetrievePublisherForThreadPool(threadPoolKey, this.metrics, this.properties, updated); + HystrixMetricsPublisherFactory.createOrRetrievePublisherForThreadPool(threadPoolKey, this.metrics, this.properties); } @Override @@ -223,6 +222,12 @@ public Scheduler getScheduler(Func0 shouldInterruptThread) { return new HystrixContextScheduler(HystrixPlugins.getInstance().getConcurrencyStrategy(), this, shouldInterruptThread); } + private void touchConfig(HystrixThreadPoolKey threadPoolKey, HystrixThreadPoolProperties.Setter newProperties) { + this.properties = HystrixPropertiesFactory.getThreadPoolProperties(threadPoolKey, newProperties, + true); + touchConfig(); + } + // allow us to change things via fast-properties by setting it each time private void touchConfig() { final int dynamicCoreSize = properties.coreSize().get(); diff --git a/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPoolMetrics.java b/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPoolMetrics.java index 7e8285859..22e978b1d 100644 --- a/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPoolMetrics.java +++ b/hystrix-core/src/main/java/com/netflix/hystrix/HystrixThreadPoolMetrics.java @@ -59,16 +59,15 @@ public class HystrixThreadPoolMetrics extends HystrixMetrics { * Pass-thru to {@link HystrixThreadPoolMetrics} instance on first time when constructed * @return {@link HystrixThreadPoolMetrics} */ - public static HystrixThreadPoolMetrics getInstance(HystrixThreadPoolKey key, ThreadPoolExecutor threadPool, - HystrixThreadPoolProperties properties, boolean updated) { + public static HystrixThreadPoolMetrics getInstance(HystrixThreadPoolKey key, ThreadPoolExecutor threadPool, HystrixThreadPoolProperties properties) { // attempt to retrieve from cache first HystrixThreadPoolMetrics threadPoolMetrics = metrics.get(key.name()); - if (threadPoolMetrics != null && !updated) { + if (threadPoolMetrics != null) { return threadPoolMetrics; } else { synchronized (HystrixThreadPoolMetrics.class) { HystrixThreadPoolMetrics existingMetrics = metrics.get(key.name()); - if (existingMetrics != null && !updated) { + if (existingMetrics != null) { return existingMetrics; } else { HystrixThreadPoolMetrics newThreadPoolMetrics = new HystrixThreadPoolMetrics(key, threadPool, properties); diff --git a/hystrix-core/src/main/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherFactory.java b/hystrix-core/src/main/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherFactory.java index 51ba953e3..98c7813eb 100644 --- a/hystrix-core/src/main/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherFactory.java +++ b/hystrix-core/src/main/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherFactory.java @@ -60,11 +60,8 @@ public class HystrixMetricsPublisherFactory { * Pass-thru to {@link HystrixMetricsPublisher#getMetricsPublisherForThreadPool} implementation * @return {@link HystrixMetricsPublisherThreadPool} instance */ - public static HystrixMetricsPublisherThreadPool createOrRetrievePublisherForThreadPool(HystrixThreadPoolKey threadPoolKey, - HystrixThreadPoolMetrics metrics, - HystrixThreadPoolProperties properties, - boolean updated) { - return SINGLETON.getPublisherForThreadPool(threadPoolKey, metrics, properties, updated); + public static HystrixMetricsPublisherThreadPool createOrRetrievePublisherForThreadPool(HystrixThreadPoolKey threadPoolKey, HystrixThreadPoolMetrics metrics, HystrixThreadPoolProperties properties) { + return SINGLETON.getPublisherForThreadPool(threadPoolKey, metrics, properties); } /** @@ -126,24 +123,25 @@ public static void reset() { // String is ThreadPoolKey.name() (we can't use ThreadPoolKey directly as we can't guarantee it implements hashcode/equals correctly) private final ConcurrentHashMap threadPoolPublishers = new ConcurrentHashMap(); - /* package */ HystrixMetricsPublisherThreadPool getPublisherForThreadPool(HystrixThreadPoolKey threadPoolKey, HystrixThreadPoolMetrics metrics, - HystrixThreadPoolProperties properties, boolean updated) { + /* package */ HystrixMetricsPublisherThreadPool getPublisherForThreadPool(HystrixThreadPoolKey threadPoolKey, HystrixThreadPoolMetrics metrics, HystrixThreadPoolProperties properties) { // attempt to retrieve from cache first HystrixMetricsPublisherThreadPool publisher = threadPoolPublishers.get(threadPoolKey.name()); - if (publisher != null && !updated) { + if (publisher != null) { return publisher; } - synchronized (HystrixMetricsPublisherFactory.class){ // it doesn't exist so we need to create it - HystrixMetricsPublisherThreadPool newPublisher = HystrixPlugins.getInstance().getMetricsPublisher() - .getMetricsPublisherForThreadPool(threadPoolKey, metrics, properties); + publisher = HystrixPlugins.getInstance().getMetricsPublisher().getMetricsPublisherForThreadPool(threadPoolKey, metrics, properties); // attempt to store it (race other threads) - threadPoolPublishers.put(threadPoolKey.name(), newPublisher); - if(publisher != null){ - publisher.tearDown(); - } - newPublisher.initialize(); - return newPublisher; + HystrixMetricsPublisherThreadPool existing = threadPoolPublishers.putIfAbsent(threadPoolKey.name(), publisher); + if (existing == null) { + // we won the thread-race to store the instance we created so initialize it + publisher.initialize(); + // done registering, return instance that got cached + return publisher; + } else { + // we lost so return 'existing' and let the one we created be garbage collected + // without calling initialize() on it + return existing; } } diff --git a/hystrix-core/src/main/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherThreadPool.java b/hystrix-core/src/main/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherThreadPool.java index 91bb6d05a..ff3507a39 100644 --- a/hystrix-core/src/main/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherThreadPool.java +++ b/hystrix-core/src/main/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherThreadPool.java @@ -31,10 +31,6 @@ public interface HystrixMetricsPublisherThreadPool { // TODO should the arguments be given via initialize rather than constructor so people can't accidentally do it wrong? - void initialize(); - - default void tearDown(){ - // Do Nothing - } + public void initialize(); } diff --git a/hystrix-core/src/main/java/com/netflix/hystrix/strategy/properties/HystrixPropertiesFactory.java b/hystrix-core/src/main/java/com/netflix/hystrix/strategy/properties/HystrixPropertiesFactory.java index aab542e5d..190f61798 100644 --- a/hystrix-core/src/main/java/com/netflix/hystrix/strategy/properties/HystrixPropertiesFactory.java +++ b/hystrix-core/src/main/java/com/netflix/hystrix/strategy/properties/HystrixPropertiesFactory.java @@ -95,6 +95,7 @@ public static HystrixCommandProperties getCommandProperties(HystrixCommandKey ke * Pass-thru to {@link HystrixPropertiesStrategy#getThreadPoolProperties} implementation. * @param builder * Pass-thru to {@link HystrixPropertiesStrategy#getThreadPoolProperties} implementation. + * @param updated * @return {@link HystrixThreadPoolProperties} instance */ public static HystrixThreadPoolProperties getThreadPoolProperties(HystrixThreadPoolKey key, HystrixThreadPoolProperties.Setter builder, diff --git a/hystrix-core/src/test/java/com/netflix/hystrix/HystrixThreadPoolTest.java b/hystrix-core/src/test/java/com/netflix/hystrix/HystrixThreadPoolTest.java index bcde16eb6..7aec75dd6 100644 --- a/hystrix-core/src/test/java/com/netflix/hystrix/HystrixThreadPoolTest.java +++ b/hystrix-core/src/test/java/com/netflix/hystrix/HystrixThreadPoolTest.java @@ -112,7 +112,7 @@ public HystrixMetricsPublisherThreadPool getMetricsPublisherForThreadPool(Hystri assertThat(poolOne.getExecutor(), is(poolTwo.getExecutor())); //Now that we get the threadPool from the metrics object, this will always be equal HystrixMetricsPublisherThreadPoolContainer hystrixMetricsPublisherThreadPool = (HystrixMetricsPublisherThreadPoolContainer)HystrixMetricsPublisherFactory - .createOrRetrievePublisherForThreadPool(threadPoolKey, null, null, false); + .createOrRetrievePublisherForThreadPool(threadPoolKey, null, null); ThreadPoolExecutor threadPoolExecutor = hystrixMetricsPublisherThreadPool.getHystrixThreadPoolMetrics().getThreadPool(); //assert that both HystrixThreadPools share the same ThreadPoolExecutor as the one in HystrixMetricsPublisherThreadPool diff --git a/hystrix-core/src/test/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherFactoryTest.java b/hystrix-core/src/test/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherFactoryTest.java index 4380a8ec6..b1a7dde98 100644 --- a/hystrix-core/src/test/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherFactoryTest.java +++ b/hystrix-core/src/test/java/com/netflix/hystrix/strategy/metrics/HystrixMetricsPublisherFactoryTest.java @@ -57,7 +57,7 @@ public void testSingleInitializePerKey() { public void run() { factory.getPublisherForCommand(TestCommandKey.TEST_A, null, null, null, null); factory.getPublisherForCommand(TestCommandKey.TEST_B, null, null, null, null); - factory.getPublisherForThreadPool(TestThreadPoolKey.TEST_A, null, null, false); + factory.getPublisherForThreadPool(TestThreadPoolKey.TEST_A, null, null); } })); From e566e7b1c37dda9cb81bbd81a36c5aaaa63567a3 Mon Sep 17 00:00:00 2001 From: Nitish Goyal Date: Wed, 6 Nov 2019 12:52:14 +0530 Subject: [PATCH 8/8] Commented username/password --- hystrix-contrib/hystrix-codahale-metrics-publisher/build.gradle | 2 +- hystrix-core/build.gradle | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/hystrix-contrib/hystrix-codahale-metrics-publisher/build.gradle b/hystrix-contrib/hystrix-codahale-metrics-publisher/build.gradle index 000f2ad0c..b3d20c3d0 100644 --- a/hystrix-contrib/hystrix-codahale-metrics-publisher/build.gradle +++ b/hystrix-contrib/hystrix-codahale-metrics-publisher/build.gradle @@ -11,7 +11,7 @@ uploadArchives { repositories { mavenDeployer { repository(url: "https://clojars.org/repo"){ - authentication(userName: "nitishgoyal13", password: "Shine12@") + authentication(userName: "", password: "") } pom.version = '1.5.11-22' pom.groupId = 'org.hystrix' diff --git a/hystrix-core/build.gradle b/hystrix-core/build.gradle index a522aae50..5ffcf17f5 100644 --- a/hystrix-core/build.gradle +++ b/hystrix-core/build.gradle @@ -38,7 +38,7 @@ uploadArchives { repositories { mavenDeployer { repository(url: "https://clojars.org/repo"){ - authentication(userName: "nitishgoyal13", password: "Shine12@") + authentication(userName: "", password: "") } pom.version = '1.5.11-22' pom.groupId = 'org.hystrix'