From a000801249ab9d71f94414be0335a960a335dd31 Mon Sep 17 00:00:00 2001 From: Seonghyeon Cho Date: Sat, 21 Jun 2025 00:48:31 +0900 Subject: [PATCH 1/7] Allow blocking call in kubernetes-client `WatchEventsListener` Motivation: Blockhound detects blocked thread after upgrading kubernetes-client 7.3.1 (#6271) Modification: - Remove `io.fabric8.kubernetes.client.http.StandardHttpRequest$Builder` from allow list, as it uses UUID created via AtomicLong now. - Add `io.fabric8.kubernetes.client.server.mock.WatchEventsListener` to allow list, because it is only used in the mock server. Result: Blockhound passes Signed-off-by: Seonghyeon Cho --- .../kubernetes/KubernetesBlockHoundIntegration.java | 8 ++------ 1 file changed, 2 insertions(+), 6 deletions(-) diff --git a/kubernetes/src/main/java/com/linecorp/armeria/client/kubernetes/KubernetesBlockHoundIntegration.java b/kubernetes/src/main/java/com/linecorp/armeria/client/kubernetes/KubernetesBlockHoundIntegration.java index 04e8f2d3c56..1e2ad58cd7e 100644 --- a/kubernetes/src/main/java/com/linecorp/armeria/client/kubernetes/KubernetesBlockHoundIntegration.java +++ b/kubernetes/src/main/java/com/linecorp/armeria/client/kubernetes/KubernetesBlockHoundIntegration.java @@ -32,12 +32,8 @@ public void applyTo(Builder builder) { // a fully readable ByteBuffer. builder.allowBlockingCallsInside( "io.fabric8.kubernetes.client.http.HttpClientReadableByteChannel", "doLockedAndSignal"); - // StandardHttpRequest creates UUIDs using java.util.UUID.randomUUID() that uses SecureRandom. - // The method is temporarily allowed until the problem is resolved in the upstream. - // See: https://github.com/fabric8io/kubernetes-client/issues/5735 - // TODO(ikhoon): Remove this once the issue is fixed. + // This only used in mock server. builder.allowBlockingCallsInside( - "io.fabric8.kubernetes.client.http.StandardHttpRequest$Builder", - "build"); + "io.fabric8.kubernetes.client.server.mock.WatchEventsListener", "onClosed"); } } From ea367c58672dbab203cd2193cd1afd8f7717411d Mon Sep 17 00:00:00 2001 From: Seonghyeon Cho Date: Tue, 1 Jul 2025 23:48:44 +0900 Subject: [PATCH 2/7] Add `KubernetesTestBlockHoundIntegration` Signed-off-by: Seonghyeon Cho --- .../KubernetesBlockHoundIntegration.java | 3 --- .../KubernetesTestBlockHoundIntegration.java | 15 +++++++++++++++ ...r.blockhound.integration.BlockHoundIntegration | 1 + 3 files changed, 16 insertions(+), 3 deletions(-) create mode 100644 kubernetes/src/test/java/com/linecorp/armeria/client/kubernetes/KubernetesTestBlockHoundIntegration.java create mode 100644 kubernetes/src/test/resources/META-INF/services/reactor.blockhound.integration.BlockHoundIntegration diff --git a/kubernetes/src/main/java/com/linecorp/armeria/client/kubernetes/KubernetesBlockHoundIntegration.java b/kubernetes/src/main/java/com/linecorp/armeria/client/kubernetes/KubernetesBlockHoundIntegration.java index 1e2ad58cd7e..a4153cf3c59 100644 --- a/kubernetes/src/main/java/com/linecorp/armeria/client/kubernetes/KubernetesBlockHoundIntegration.java +++ b/kubernetes/src/main/java/com/linecorp/armeria/client/kubernetes/KubernetesBlockHoundIntegration.java @@ -32,8 +32,5 @@ public void applyTo(Builder builder) { // a fully readable ByteBuffer. builder.allowBlockingCallsInside( "io.fabric8.kubernetes.client.http.HttpClientReadableByteChannel", "doLockedAndSignal"); - // This only used in mock server. - builder.allowBlockingCallsInside( - "io.fabric8.kubernetes.client.server.mock.WatchEventsListener", "onClosed"); } } diff --git a/kubernetes/src/test/java/com/linecorp/armeria/client/kubernetes/KubernetesTestBlockHoundIntegration.java b/kubernetes/src/test/java/com/linecorp/armeria/client/kubernetes/KubernetesTestBlockHoundIntegration.java new file mode 100644 index 00000000000..eefac745e43 --- /dev/null +++ b/kubernetes/src/test/java/com/linecorp/armeria/client/kubernetes/KubernetesTestBlockHoundIntegration.java @@ -0,0 +1,15 @@ +package com.linecorp.armeria.client.kubernetes; + +import reactor.blockhound.BlockHound.Builder; +import reactor.blockhound.integration.BlockHoundIntegration; + +/** + * A {@link BlockHoundIntegration} for the Fabric Kubernetes module in tests. + */ +public final class KubernetesTestBlockHoundIntegration implements BlockHoundIntegration { + @Override + public void applyTo(Builder builder) { + builder.allowBlockingCallsInside( + "io.fabric8.kubernetes.client.server.mock.WatchEventsListener", "onClosed"); + } +} diff --git a/kubernetes/src/test/resources/META-INF/services/reactor.blockhound.integration.BlockHoundIntegration b/kubernetes/src/test/resources/META-INF/services/reactor.blockhound.integration.BlockHoundIntegration new file mode 100644 index 00000000000..d592a790e22 --- /dev/null +++ b/kubernetes/src/test/resources/META-INF/services/reactor.blockhound.integration.BlockHoundIntegration @@ -0,0 +1 @@ +com.linecorp.armeria.client.kubernetes.KubernetesTestBlockHoundIntegration From ca2d85a70afa69aea1301543555253851dc14130 Mon Sep 17 00:00:00 2001 From: Seonghyeon Cho Date: Tue, 1 Jul 2025 23:59:34 +0900 Subject: [PATCH 3/7] Add license header Signed-off-by: Seonghyeon Cho --- .../KubernetesTestBlockHoundIntegration.java | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) diff --git a/kubernetes/src/test/java/com/linecorp/armeria/client/kubernetes/KubernetesTestBlockHoundIntegration.java b/kubernetes/src/test/java/com/linecorp/armeria/client/kubernetes/KubernetesTestBlockHoundIntegration.java index eefac745e43..4f38e030cd8 100644 --- a/kubernetes/src/test/java/com/linecorp/armeria/client/kubernetes/KubernetesTestBlockHoundIntegration.java +++ b/kubernetes/src/test/java/com/linecorp/armeria/client/kubernetes/KubernetesTestBlockHoundIntegration.java @@ -1,3 +1,19 @@ +/* + * Copyright 2025 LY Corporation + * + * LY Corporation licenses this file to you under the Apache License, + * version 2.0 (the "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at: + * + * https://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT + * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the + * License for the specific language governing permissions and limitations + * under the License. + */ + package com.linecorp.armeria.client.kubernetes; import reactor.blockhound.BlockHound.Builder; From d432271b4daa146d3a0e7d199d18c53f56b7a471 Mon Sep 17 00:00:00 2001 From: Seonghyeon Cho Date: Wed, 2 Jul 2025 00:38:21 +0900 Subject: [PATCH 4/7] Add allowing blocking call `onFailure` Signed-off-by: Seonghyeon Cho --- .../client/kubernetes/KubernetesTestBlockHoundIntegration.java | 2 ++ 1 file changed, 2 insertions(+) diff --git a/kubernetes/src/test/java/com/linecorp/armeria/client/kubernetes/KubernetesTestBlockHoundIntegration.java b/kubernetes/src/test/java/com/linecorp/armeria/client/kubernetes/KubernetesTestBlockHoundIntegration.java index 4f38e030cd8..67d512d0095 100644 --- a/kubernetes/src/test/java/com/linecorp/armeria/client/kubernetes/KubernetesTestBlockHoundIntegration.java +++ b/kubernetes/src/test/java/com/linecorp/armeria/client/kubernetes/KubernetesTestBlockHoundIntegration.java @@ -27,5 +27,7 @@ public final class KubernetesTestBlockHoundIntegration implements BlockHoundInte public void applyTo(Builder builder) { builder.allowBlockingCallsInside( "io.fabric8.kubernetes.client.server.mock.WatchEventsListener", "onClosed"); + builder.allowBlockingCallsInside( + "io.fabric8.kubernetes.client.server.mock.WatchEventsListener", "onFailure"); } } From 8c78e0b78e97081091b26e55c8e8ee5f36d74a2d Mon Sep 17 00:00:00 2001 From: minwoox Date: Thu, 3 Jul 2025 12:21:21 +0900 Subject: [PATCH 5/7] WIP --- .../KubernetesTestBlockHoundIntegration.java | 33 ------------------- ...ockhound.integration.BlockHoundIntegration | 1 - .../InternalTestingBlockHoundIntegration.java | 6 ++++ 3 files changed, 6 insertions(+), 34 deletions(-) delete mode 100644 kubernetes/src/test/java/com/linecorp/armeria/client/kubernetes/KubernetesTestBlockHoundIntegration.java delete mode 100644 kubernetes/src/test/resources/META-INF/services/reactor.blockhound.integration.BlockHoundIntegration diff --git a/kubernetes/src/test/java/com/linecorp/armeria/client/kubernetes/KubernetesTestBlockHoundIntegration.java b/kubernetes/src/test/java/com/linecorp/armeria/client/kubernetes/KubernetesTestBlockHoundIntegration.java deleted file mode 100644 index 67d512d0095..00000000000 --- a/kubernetes/src/test/java/com/linecorp/armeria/client/kubernetes/KubernetesTestBlockHoundIntegration.java +++ /dev/null @@ -1,33 +0,0 @@ -/* - * Copyright 2025 LY Corporation - * - * LY Corporation licenses this file to you under the Apache License, - * version 2.0 (the "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at: - * - * https://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT - * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the - * License for the specific language governing permissions and limitations - * under the License. - */ - -package com.linecorp.armeria.client.kubernetes; - -import reactor.blockhound.BlockHound.Builder; -import reactor.blockhound.integration.BlockHoundIntegration; - -/** - * A {@link BlockHoundIntegration} for the Fabric Kubernetes module in tests. - */ -public final class KubernetesTestBlockHoundIntegration implements BlockHoundIntegration { - @Override - public void applyTo(Builder builder) { - builder.allowBlockingCallsInside( - "io.fabric8.kubernetes.client.server.mock.WatchEventsListener", "onClosed"); - builder.allowBlockingCallsInside( - "io.fabric8.kubernetes.client.server.mock.WatchEventsListener", "onFailure"); - } -} diff --git a/kubernetes/src/test/resources/META-INF/services/reactor.blockhound.integration.BlockHoundIntegration b/kubernetes/src/test/resources/META-INF/services/reactor.blockhound.integration.BlockHoundIntegration deleted file mode 100644 index d592a790e22..00000000000 --- a/kubernetes/src/test/resources/META-INF/services/reactor.blockhound.integration.BlockHoundIntegration +++ /dev/null @@ -1 +0,0 @@ -com.linecorp.armeria.client.kubernetes.KubernetesTestBlockHoundIntegration diff --git a/testing-internal/src/main/java/com/linecorp/armeria/internal/testing/InternalTestingBlockHoundIntegration.java b/testing-internal/src/main/java/com/linecorp/armeria/internal/testing/InternalTestingBlockHoundIntegration.java index 3d62508a2b6..4382de92865 100644 --- a/testing-internal/src/main/java/com/linecorp/armeria/internal/testing/InternalTestingBlockHoundIntegration.java +++ b/testing-internal/src/main/java/com/linecorp/armeria/internal/testing/InternalTestingBlockHoundIntegration.java @@ -76,6 +76,12 @@ public void applyTo(Builder builder) { builder.allowBlockingCallsInside("com.linecorp.armeria.client.ClientFactory", "ofDefault"); builder.allowBlockingCallsInside("io.envoyproxy.controlplane.cache.SimpleCache", "createWatch"); builder.allowBlockingCallsInside("io.grpc.netty.shaded.io.netty.util.Version", "identify"); + builder.allowBlockingCallsInside( + "io.fabric8.kubernetes.client.server.mock.WatchEventsListener", "onClosed"); + builder.allowBlockingCallsInside( + "io.fabric8.kubernetes.client.server.mock.WatchEventsListener", "onFailure"); + builder.allowBlockingCallsInside( + "io.fabric8.mockwebserver.internal.WebSocketSession", "onOpen"); // prints the exception which makes it easier to debug issues builder.blockingMethodCallback(this::writeBlockingMethod); From a8fc287b4934f8ff3a2a71f372b685e80fa3a003 Mon Sep 17 00:00:00 2001 From: minwoox Date: Thu, 3 Jul 2025 13:16:57 +0900 Subject: [PATCH 6/7] WIP --- .../testing/InternalTestingBlockHoundIntegration.java | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/testing-internal/src/main/java/com/linecorp/armeria/internal/testing/InternalTestingBlockHoundIntegration.java b/testing-internal/src/main/java/com/linecorp/armeria/internal/testing/InternalTestingBlockHoundIntegration.java index 4382de92865..59365b2805b 100644 --- a/testing-internal/src/main/java/com/linecorp/armeria/internal/testing/InternalTestingBlockHoundIntegration.java +++ b/testing-internal/src/main/java/com/linecorp/armeria/internal/testing/InternalTestingBlockHoundIntegration.java @@ -80,8 +80,8 @@ public void applyTo(Builder builder) { "io.fabric8.kubernetes.client.server.mock.WatchEventsListener", "onClosed"); builder.allowBlockingCallsInside( "io.fabric8.kubernetes.client.server.mock.WatchEventsListener", "onFailure"); - builder.allowBlockingCallsInside( - "io.fabric8.mockwebserver.internal.WebSocketSession", "onOpen"); + builder.allowBlockingCallsInside("io.fabric8.mockwebserver.internal.WebSocketSession", "onOpen"); + builder.allowBlockingCallsInside("io.vertx.core.spi.tls.DefaultSslContextFactory", "createContext"); // prints the exception which makes it easier to debug issues builder.blockingMethodCallback(this::writeBlockingMethod); From 43cf4155369db6fb71042976d59a4d62b0b2f01a Mon Sep 17 00:00:00 2001 From: minwoox Date: Thu, 3 Jul 2025 18:35:37 +0900 Subject: [PATCH 7/7] Add vert.x-internal-blocking --- .../internal/testing/InternalTestingBlockHoundIntegration.java | 2 ++ 1 file changed, 2 insertions(+) diff --git a/testing-internal/src/main/java/com/linecorp/armeria/internal/testing/InternalTestingBlockHoundIntegration.java b/testing-internal/src/main/java/com/linecorp/armeria/internal/testing/InternalTestingBlockHoundIntegration.java index 59365b2805b..9fc2d90b760 100644 --- a/testing-internal/src/main/java/com/linecorp/armeria/internal/testing/InternalTestingBlockHoundIntegration.java +++ b/testing-internal/src/main/java/com/linecorp/armeria/internal/testing/InternalTestingBlockHoundIntegration.java @@ -52,6 +52,8 @@ public void write(int b) throws IOException { @Override public void applyTo(Builder builder) { + builder.nonBlockingThreadPredicate(predicate -> predicate.and( + thread -> !thread.getName().startsWith("vert.x-internal-blocking"))); // tests are allowed to block event loops builder.allowBlockingCallsInside("com.linecorp.armeria.internal.testing.BlockingUtils",