diff --git a/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/web/server/ManagementContextAutoConfiguration.java b/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/web/server/ManagementContextAutoConfiguration.java index 9599c42c644..d78c89168ca 100644 --- a/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/web/server/ManagementContextAutoConfiguration.java +++ b/spring-boot-project/spring-boot-actuator-autoconfigure/src/main/java/org/springframework/boot/actuate/autoconfigure/web/server/ManagementContextAutoConfiguration.java @@ -16,6 +16,9 @@ package org.springframework.boot.actuate.autoconfigure.web.server; +import org.apache.commons.logging.Log; +import org.apache.commons.logging.LogFactory; + import org.springframework.beans.factory.SmartInitializingSingleton; import org.springframework.boot.actuate.autoconfigure.endpoint.web.WebEndpointProperties; import org.springframework.boot.actuate.autoconfigure.web.ManagementContextFactory; @@ -26,6 +29,7 @@ import org.springframework.boot.autoconfigure.context.PropertyPlaceholderAutoCon import org.springframework.boot.context.event.ApplicationFailedEvent; import org.springframework.boot.context.properties.EnableConfigurationProperties; import org.springframework.boot.web.context.ConfigurableWebServerApplicationContext; +import org.springframework.boot.web.context.WebServerApplicationContext; import org.springframework.context.ApplicationContext; import org.springframework.context.ApplicationEvent; import org.springframework.context.ApplicationListener; @@ -55,6 +59,9 @@ import org.springframework.util.Assert; ManagementServerProperties.class }) public class ManagementContextAutoConfiguration { + private static final Log logger = LogFactory + .getLog(ManagementContextAutoConfiguration.class); + @Configuration @ConditionalOnManagementPort(ManagementPortType.SAME) static class SameManagementContextConfiguration @@ -129,16 +136,25 @@ public class ManagementContextAutoConfiguration { @Override public void afterSingletonsInstantiated() { - ConfigurableWebServerApplicationContext managementContext = this.managementContextFactory - .createManagementContext(this.applicationContext, - EnableChildManagementContextConfiguration.class, - PropertyPlaceholderAutoConfiguration.class); - managementContext.setServerNamespace("management"); - managementContext.setId(this.applicationContext.getId() + ":management"); - setClassLoaderIfPossible(managementContext); - CloseManagementContextListener.addIfPossible(this.applicationContext, - managementContext); - managementContext.refresh(); + if (this.applicationContext instanceof WebServerApplicationContext + && ((WebServerApplicationContext) this.applicationContext) + .getWebServer() != null) { + ConfigurableWebServerApplicationContext managementContext = this.managementContextFactory + .createManagementContext(this.applicationContext, + EnableChildManagementContextConfiguration.class, + PropertyPlaceholderAutoConfiguration.class); + managementContext.setServerNamespace("management"); + managementContext.setId(this.applicationContext.getId() + ":management"); + setClassLoaderIfPossible(managementContext); + CloseManagementContextListener.addIfPossible(this.applicationContext, + managementContext); + managementContext.refresh(); + } + else { + logger.warn("Could not start embedded management container on " + + "different port (management endpoints are still available " + + "through JMX)"); + } } private void setClassLoaderIfPossible(ConfigurableApplicationContext child) { diff --git a/spring-boot-project/spring-boot-actuator-autoconfigure/src/test/java/org/springframework/boot/actuate/autoconfigure/web/server/ManagementContextAutoConfigurationTests.java b/spring-boot-project/spring-boot-actuator-autoconfigure/src/test/java/org/springframework/boot/actuate/autoconfigure/web/server/ManagementContextAutoConfigurationTests.java new file mode 100644 index 00000000000..cb7322430c5 --- /dev/null +++ b/spring-boot-project/spring-boot-actuator-autoconfigure/src/test/java/org/springframework/boot/actuate/autoconfigure/web/server/ManagementContextAutoConfigurationTests.java @@ -0,0 +1,74 @@ +/* + * Copyright 2012-2018 the original author or authors. + * + * Licensed 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 + * + * http://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 org.springframework.boot.actuate.autoconfigure.web.server; + +import org.junit.Rule; +import org.junit.Test; + +import org.springframework.boot.actuate.autoconfigure.endpoint.EndpointAutoConfiguration; +import org.springframework.boot.actuate.autoconfigure.endpoint.web.WebEndpointAutoConfiguration; +import org.springframework.boot.actuate.autoconfigure.web.servlet.ServletManagementContextAutoConfiguration; +import org.springframework.boot.autoconfigure.AutoConfigurations; +import org.springframework.boot.autoconfigure.web.servlet.ServletWebServerFactoryAutoConfiguration; +import org.springframework.boot.test.context.runner.WebApplicationContextRunner; +import org.springframework.boot.test.rule.OutputCapture; +import org.springframework.boot.web.servlet.context.AnnotationConfigServletWebServerApplicationContext; + +import static org.assertj.core.api.Assertions.assertThat; + +/** + * Tests for {@link ManagementContextAutoConfiguration}. + * + * @author Madhura Bhave + */ +public class ManagementContextAutoConfigurationTests { + + private WebApplicationContextRunner contextRunner = new WebApplicationContextRunner() + .withConfiguration( + AutoConfigurations.of(ManagementContextAutoConfiguration.class, + ServletManagementContextAutoConfiguration.class)); + + @Rule + public OutputCapture output = new OutputCapture(); + + @Test + public void managementServerPortShouldBeIgnoredForNonEmbeddedServer() { + this.contextRunner.withPropertyValues("management.server.port=8081") + .run((context) -> { + assertThat(context.getStartupFailure()).isNull(); + assertThat(this.output.toString()) + .contains("Could not start embedded management container on " + + "different port (management endpoints are still available through JMX)"); + }); + } + + @Test + public void childManagementContextShouldStartForEmbeddedServer() { + WebApplicationContextRunner contextRunner = new WebApplicationContextRunner( + AnnotationConfigServletWebServerApplicationContext::new) + .withConfiguration(AutoConfigurations.of( + ManagementContextAutoConfiguration.class, + ServletWebServerFactoryAutoConfiguration.class, + ServletManagementContextAutoConfiguration.class, + WebEndpointAutoConfiguration.class, + EndpointAutoConfiguration.class)); + contextRunner.withPropertyValues("management.server.port=8081") + .run((context) -> assertThat(this.output.toString()).doesNotContain( + "Could not start embedded management container on " + + "different port (management endpoints are still available through JMX)")); + } + +}