diff --git a/module/spring-boot-jms/src/main/java/org/springframework/boot/jms/health/JmsHealthIndicator.java b/module/spring-boot-jms/src/main/java/org/springframework/boot/jms/health/JmsHealthIndicator.java index 1c788f3086b..7be9a086d33 100644 --- a/module/spring-boot-jms/src/main/java/org/springframework/boot/jms/health/JmsHealthIndicator.java +++ b/module/spring-boot-jms/src/main/java/org/springframework/boot/jms/health/JmsHealthIndicator.java @@ -96,7 +96,7 @@ public class JmsHealthIndicator extends AbstractHealthIndicator { } void start() throws JMSException { - new Thread(() -> { + Thread watchdog = new Thread(() -> { try { Duration startTimeout1 = JmsHealthIndicator.this.startTimeout; if (!this.latch.await(startTimeout1.toNanos(), TimeUnit.NANOSECONDS)) { @@ -109,9 +109,15 @@ public class JmsHealthIndicator extends AbstractHealthIndicator { catch (InterruptedException ex) { Thread.currentThread().interrupt(); } - }, "jms-health-indicator").start(); - this.connection.start(); - this.latch.countDown(); + }, "jms-health-indicator"); + watchdog.setDaemon(true); + watchdog.start(); + try { + this.connection.start(); + } + finally { + this.latch.countDown(); + } } private void closeConnection() { diff --git a/module/spring-boot-jms/src/test/java/org/springframework/boot/jms/health/JmsHealthIndicatorTests.java b/module/spring-boot-jms/src/test/java/org/springframework/boot/jms/health/JmsHealthIndicatorTests.java index cf2a8ac069b..36cc2e85c6a 100644 --- a/module/spring-boot-jms/src/test/java/org/springframework/boot/jms/health/JmsHealthIndicatorTests.java +++ b/module/spring-boot-jms/src/test/java/org/springframework/boot/jms/health/JmsHealthIndicatorTests.java @@ -35,6 +35,7 @@ import static org.mockito.BDDMockito.given; import static org.mockito.BDDMockito.then; import static org.mockito.BDDMockito.willAnswer; import static org.mockito.BDDMockito.willThrow; +import static org.mockito.Mockito.after; import static org.mockito.Mockito.mock; /** @@ -123,6 +124,18 @@ class JmsHealthIndicatorTests { assertThat(health.getDetails()).doesNotContainKey("provider"); } + @Test + void whenConnectionStartThrowsWatchdogThreadDoesNotAlsoCloseConnection() throws JMSException { + Connection connection = mock(Connection.class); + willThrow(new JMSException("Could not start", "123")).given(connection).start(); + ConnectionFactory connectionFactory = mock(ConnectionFactory.class); + given(connectionFactory.createConnection()).willReturn(connection); + JmsHealthIndicator indicator = new JmsHealthIndicator(connectionFactory); + Health health = indicator.health(); + assertThat(health.getStatus()).isEqualTo(Status.DOWN); + then(connection).should(after(Duration.ofSeconds(5).plusMillis(500).toMillis()).times(1)).close(); + } + @Test void whenConnectionStartIsUnresponsiveStatusIsDown() throws JMSException { Health health = healthWhenConnectionStartIsUnresponsive(Duration.ofSeconds(5));