This is an automated email from the ASF dual-hosted git repository. jamesnetherton pushed a commit to branch 3.33.x in repository https://gitbox.apache.org/repos/asf/camel-quarkus.git
commit 601c9dc6563b3c3894f2cdb9d07c3ecb495399e5 Author: James Netherton <[email protected]> AuthorDate: Tue Jul 7 17:05:28 2026 +0100 Fix clustering integration test flakiness on Windows and slow CI - Align all Awaitility timeouts to 60s across master-file, master-openshift, master-infinispan, and quartz-clustered tests for consistent behavior on slow machines - Use FileUtils.deleteQuietly instead of deleteDirectory in cluster file cleanup to prevent Windows failures when FileLockClusterService holds OS-level file locks on cluster data files - Add destroyForcibly fallback in QuarkusProcessExecutor when graceful shutdown times out, preventing leaked processes and held file handles Co-Authored-By: Claude Opus 4.6 (1M context) <[email protected]> --- .../quarkus/test/support/process/QuarkusProcessExecutor.java | 3 ++- .../camel/quarkus/component/master/it/MasterFileTest.java | 10 +++++----- .../component/master/it/InfinispanClusterServiceTest.java | 10 +++++----- .../camel/quarkus/component/master/it/MasterOpenShiftTest.java | 10 +++++----- .../camel/quarkus/component/quartz/it/QuartzClusteredTest.java | 4 ++-- 5 files changed, 19 insertions(+), 18 deletions(-) diff --git a/integration-tests-support/process-executor-support/src/main/java/org/apache/camel/quarkus/test/support/process/QuarkusProcessExecutor.java b/integration-tests-support/process-executor-support/src/main/java/org/apache/camel/quarkus/test/support/process/QuarkusProcessExecutor.java index d027f441a4..012100ec50 100644 --- a/integration-tests-support/process-executor-support/src/main/java/org/apache/camel/quarkus/test/support/process/QuarkusProcessExecutor.java +++ b/integration-tests-support/process-executor-support/src/main/java/org/apache/camel/quarkus/test/support/process/QuarkusProcessExecutor.java @@ -90,7 +90,8 @@ public class QuarkusProcessExecutor { this.process.onExit().get(timeout, unit); LOGGER.infof("Process %d completed with exit code %d", this.process.pid(), this.process.exitValue()); } catch (TimeoutException e) { - LOGGER.warnf(e, "Timed out waiting to destroy process %d", this.process.pid()); + LOGGER.warnf("Timed out waiting to destroy process %d, forcing termination", this.process.pid()); + this.process.destroyForcibly(); } catch (ExecutionException | InterruptedException e) { LOGGER.warnf(e, "Error occurred destroying process %d", this.process.pid()); } finally { diff --git a/integration-tests/master-file/src/test/java/org/apache/camel/quarkus/component/master/it/MasterFileTest.java b/integration-tests/master-file/src/test/java/org/apache/camel/quarkus/component/master/it/MasterFileTest.java index 9864aa6483..f8b6d444d1 100644 --- a/integration-tests/master-file/src/test/java/org/apache/camel/quarkus/component/master/it/MasterFileTest.java +++ b/integration-tests/master-file/src/test/java/org/apache/camel/quarkus/component/master/it/MasterFileTest.java @@ -40,14 +40,14 @@ import static org.hamcrest.Matchers.emptyString; class MasterFileTest { @AfterEach - public void deleteClusterFiles() throws IOException { - FileUtils.deleteDirectory(Paths.get("target/cluster/").toFile()); + public void deleteClusterFiles() { + FileUtils.deleteQuietly(Paths.get("target/cluster/").toFile()); } @Test public void testFailover() throws IOException { // Verify that this process is the cluster leader - Awaitility.await().atMost(10, TimeUnit.SECONDS).with().until(() -> { + Awaitility.await().atMost(60, TimeUnit.SECONDS).with().until(() -> { return readLeaderFile("leader").equals("leader"); }); @@ -70,7 +70,7 @@ class MasterFileTest { // Verify that the secondary application has been elected as the // cluster leader - Awaitility.await().atMost(10, TimeUnit.SECONDS).until(() -> { + Awaitility.await().atMost(60, TimeUnit.SECONDS).until(() -> { return readLeaderFile("follower").equals("leader"); }); } finally { @@ -81,7 +81,7 @@ class MasterFileTest { } private void awaitStartup(QuarkusProcessExecutor quarkusProcessExecutor) { - Awaitility.await().atMost(10, TimeUnit.SECONDS).pollDelay(1, TimeUnit.SECONDS).until(() -> { + Awaitility.await().atMost(60, TimeUnit.SECONDS).pollDelay(1, TimeUnit.SECONDS).until(() -> { return isApplicationHealthy(quarkusProcessExecutor.getHttpPort()); }); } diff --git a/integration-tests/master-infinispan/src/test/java/org/apache/camel/quarkus/component/master/it/InfinispanClusterServiceTest.java b/integration-tests/master-infinispan/src/test/java/org/apache/camel/quarkus/component/master/it/InfinispanClusterServiceTest.java index 25f3600ffa..5502bd9926 100644 --- a/integration-tests/master-infinispan/src/test/java/org/apache/camel/quarkus/component/master/it/InfinispanClusterServiceTest.java +++ b/integration-tests/master-infinispan/src/test/java/org/apache/camel/quarkus/component/master/it/InfinispanClusterServiceTest.java @@ -43,14 +43,14 @@ import static org.hamcrest.Matchers.emptyString; @QuarkusTestResource(InfinispanClusterServiceTestResource.class) class InfinispanClusterServiceTest { @AfterEach - public void deleteClusterFiles() throws IOException { - FileUtils.deleteDirectory(Paths.get("target/cluster/").toFile()); + public void deleteClusterFiles() { + FileUtils.deleteQuietly(Paths.get("target/cluster/").toFile()); } @Test void testFailover() throws IOException { // Verify that this process is the cluster leader - Awaitility.await().atMost(10, TimeUnit.SECONDS).with().until(() -> { + Awaitility.await().atMost(60, TimeUnit.SECONDS).with().until(() -> { return readLeaderFile("leader").equals("leader"); }); @@ -82,7 +82,7 @@ class InfinispanClusterServiceTest { // Verify that the secondary application has been elected as the // cluster leader - Awaitility.await().atMost(10, TimeUnit.SECONDS).until(() -> { + Awaitility.await().atMost(60, TimeUnit.SECONDS).until(() -> { return readLeaderFile("follower").equals("leader"); }); } finally { @@ -93,7 +93,7 @@ class InfinispanClusterServiceTest { } private void awaitStartup(QuarkusProcessExecutor quarkusProcessExecutor) { - Awaitility.await().atMost(10, TimeUnit.SECONDS).pollDelay(1, TimeUnit.SECONDS).until(() -> { + Awaitility.await().atMost(60, TimeUnit.SECONDS).pollDelay(1, TimeUnit.SECONDS).until(() -> { return isApplicationHealthy(quarkusProcessExecutor.getHttpPort()); }); } diff --git a/integration-tests/master-openshift/src/test/java/org/apache/camel/quarkus/component/master/it/MasterOpenShiftTest.java b/integration-tests/master-openshift/src/test/java/org/apache/camel/quarkus/component/master/it/MasterOpenShiftTest.java index 4e83e18b28..f3b734b0db 100644 --- a/integration-tests/master-openshift/src/test/java/org/apache/camel/quarkus/component/master/it/MasterOpenShiftTest.java +++ b/integration-tests/master-openshift/src/test/java/org/apache/camel/quarkus/component/master/it/MasterOpenShiftTest.java @@ -55,8 +55,8 @@ class MasterOpenShiftTest { private KubernetesServer mockOpenShiftServer; @BeforeAll - public static void deleteClusterFiles() throws IOException { - FileUtils.deleteDirectory(Paths.get("target/cluster/").toFile()); + public static void deleteClusterFiles() { + FileUtils.deleteQuietly(Paths.get("target/cluster/").toFile()); } @Test @@ -86,7 +86,7 @@ class MasterOpenShiftTest { try { // Verify that this process is the cluster leader - Awaitility.await().atMost(10, TimeUnit.SECONDS).with().until(() -> { + Awaitility.await().atMost(60, TimeUnit.SECONDS).with().until(() -> { return readLeaderFile("leader").equals("leader"); }); @@ -103,7 +103,7 @@ class MasterOpenShiftTest { // Verify that the secondary application has been elected as the // cluster leader - Awaitility.await().atMost(10, TimeUnit.SECONDS).until(() -> { + Awaitility.await().atMost(60, TimeUnit.SECONDS).until(() -> { return readLeaderFile("follower").equals("leader"); }); } finally { @@ -119,7 +119,7 @@ class MasterOpenShiftTest { } private void awaitStartup(QuarkusProcessExecutor quarkusProcessExecutor) { - Awaitility.await().atMost(40, TimeUnit.SECONDS).pollDelay(1, TimeUnit.SECONDS).until(() -> { + Awaitility.await().atMost(60, TimeUnit.SECONDS).pollDelay(1, TimeUnit.SECONDS).until(() -> { return isApplicationHealthy(quarkusProcessExecutor.getHttpPort()); }); } diff --git a/integration-tests/quartz-clustered/src/test/java/org/apache/camel/quarkus/component/quartz/it/QuartzClusteredTest.java b/integration-tests/quartz-clustered/src/test/java/org/apache/camel/quarkus/component/quartz/it/QuartzClusteredTest.java index edb7314eb4..6bcd4fe73b 100644 --- a/integration-tests/quartz-clustered/src/test/java/org/apache/camel/quarkus/component/quartz/it/QuartzClusteredTest.java +++ b/integration-tests/quartz-clustered/src/test/java/org/apache/camel/quarkus/component/quartz/it/QuartzClusteredTest.java @@ -78,7 +78,7 @@ class QuartzClusteredTest { .statusCode(204); // Verify that the NodeB scheduler is running - Awaitility.await().atMost(10, TimeUnit.SECONDS).with().until(() -> { + Awaitility.await().atMost(60, TimeUnit.SECONDS).with().until(() -> { return Files.readAllLines(quarkusLog).stream().anyMatch(line -> line.contains("Hello from NodeB")); }); @@ -101,7 +101,7 @@ class QuartzClusteredTest { } private void awaitStartup(QuarkusProcessExecutor quarkusProcessExecutor) { - Awaitility.await().atMost(1, TimeUnit.MINUTES).pollDelay(1, TimeUnit.SECONDS).until(() -> { + Awaitility.await().atMost(60, TimeUnit.SECONDS).pollDelay(1, TimeUnit.SECONDS).until(() -> { return isApplicationHealthy(quarkusProcessExecutor.getHttpPort()); }); }
