From 9fb9ff4a2003081b5db43578fa57cc2bdc71c67a Mon Sep 17 00:00:00 2001 From: Marc Nuri Date: Mon, 16 Dec 2024 10:33:17 +0100 Subject: [PATCH] fix(vertx): VertxHttpClientFactory reuses the same Vertx instance for each VertxHttpClient instance Signed-off-by: Marc Nuri --- CHANGELOG.md | 5 ++ .../client/vertx/VertxHttpClientFactory.java | 61 ++++++++++++------- 2 files changed, 43 insertions(+), 23 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 967a3902ee2..9fb629faa30 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -12,6 +12,11 @@ #### _**Note**_: Breaking changes +### 7.0.1 (TBD) + +#### Bugs + +* Fix #6709: VertxHttpClientFactory reuses the same Vertx instance for each VertxHttpClient instance ### 7.0.0 (2024-12-03) diff --git a/httpclient-vertx/src/main/java/io/fabric8/kubernetes/client/vertx/VertxHttpClientFactory.java b/httpclient-vertx/src/main/java/io/fabric8/kubernetes/client/vertx/VertxHttpClientFactory.java index c0e70a0e56f..c5d969aaf21 100644 --- a/httpclient-vertx/src/main/java/io/fabric8/kubernetes/client/vertx/VertxHttpClientFactory.java +++ b/httpclient-vertx/src/main/java/io/fabric8/kubernetes/client/vertx/VertxHttpClientFactory.java @@ -25,10 +25,47 @@ public class VertxHttpClientFactory implements io.fabric8.kubernetes.client.http.HttpClient.Factory { + private static final class VertxHolder { + + private static final Vertx INSTANCE = createVertxInstance(); + + private static synchronized Vertx createVertxInstance() { + // We must disable the async DNS resolver as it can cause issues when resolving the Vault instance. + // This is done using the DISABLE_DNS_RESOLVER_PROP_NAME system property. + // The DNS resolver used by vert.x is configured during the (synchronous) initialization. + // So, we just need to disable the async resolver around the Vert.x instance creation. + final String originalValue = System.getProperty(DISABLE_DNS_RESOLVER_PROP_NAME); + Vertx vertx; + try { + System.setProperty(DISABLE_DNS_RESOLVER_PROP_NAME, "true"); + vertx = Vertx.vertx(new VertxOptions() + .setFileSystemOptions(new FileSystemOptions().setFileCachingEnabled(false).setClassPathResolvingEnabled(false)) + .setUseDaemonThread(true)); + } finally { + // Restore the original value + if (originalValue == null) { + System.clearProperty(DISABLE_DNS_RESOLVER_PROP_NAME); + } else { + System.setProperty(DISABLE_DNS_RESOLVER_PROP_NAME, originalValue); + } + } + return vertx; + } + } + private final Vertx vertx; public VertxHttpClientFactory() { - this.vertx = createVertxInstance(); + this(VertxHolder.INSTANCE); + Runtime.getRuntime().addShutdownHook(new Thread(() -> { + if (vertx != null) { + vertx.close(); + } + })); + } + + public VertxHttpClientFactory(Vertx vertx) { + this.vertx = vertx; } @Override @@ -36,28 +73,6 @@ public VertxHttpClientBuilder newBuilder() { return new VertxHttpClientBuilder<>(this, vertx); } - private static synchronized Vertx createVertxInstance() { - // We must disable the async DNS resolver as it can cause issues when resolving the Vault instance. - // This is done using the DISABLE_DNS_RESOLVER_PROP_NAME system property. - // The DNS resolver used by vert.x is configured during the (synchronous) initialization. - // So, we just need to disable the async resolver around the Vert.x instance creation. - final String originalValue = System.getProperty(DISABLE_DNS_RESOLVER_PROP_NAME); - Vertx vertx; - try { - System.setProperty(DISABLE_DNS_RESOLVER_PROP_NAME, "true"); - vertx = Vertx.vertx(new VertxOptions() - .setFileSystemOptions(new FileSystemOptions().setFileCachingEnabled(false).setClassPathResolvingEnabled(false))); - } finally { - // Restore the original value - if (originalValue == null) { - System.clearProperty(DISABLE_DNS_RESOLVER_PROP_NAME); - } else { - System.setProperty(DISABLE_DNS_RESOLVER_PROP_NAME, originalValue); - } - } - return vertx; - } - /** * Additional configuration to be applied to the options after the {@link Config} has been processed. */