diff --git a/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/autoconfigure/EndpointWebMvcAutoConfiguration.java b/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/autoconfigure/EndpointWebMvcAutoConfiguration.java index 73190530059..d5b20ff2c31 100644 --- a/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/autoconfigure/EndpointWebMvcAutoConfiguration.java +++ b/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/autoconfigure/EndpointWebMvcAutoConfiguration.java @@ -29,19 +29,26 @@ import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; import org.springframework.beans.BeansException; import org.springframework.beans.factory.BeanFactory; +import org.springframework.beans.factory.BeanFactoryUtils; import org.springframework.beans.factory.NoSuchBeanDefinitionException; import org.springframework.beans.factory.SmartInitializingSingleton; -import org.springframework.boot.actuate.condition.ConditionalOnManagementMvcContext; +import org.springframework.beans.factory.config.BeanDefinition; +import org.springframework.beans.factory.config.ConfigurableListableBeanFactory; +import org.springframework.beans.factory.support.DefaultListableBeanFactory; +import org.springframework.beans.factory.support.RootBeanDefinition; import org.springframework.boot.actuate.endpoint.Endpoint; import org.springframework.boot.autoconfigure.AutoConfigureAfter; import org.springframework.boot.autoconfigure.EnableAutoConfiguration; import org.springframework.boot.autoconfigure.PropertyPlaceholderAutoConfiguration; +import org.springframework.boot.autoconfigure.condition.ConditionOutcome; import org.springframework.boot.autoconfigure.condition.ConditionalOnClass; import org.springframework.boot.autoconfigure.condition.ConditionalOnWebApplication; +import org.springframework.boot.autoconfigure.condition.SpringBootCondition; import org.springframework.boot.autoconfigure.web.DispatcherServletAutoConfiguration; import org.springframework.boot.autoconfigure.web.EmbeddedServletContainerAutoConfiguration; import org.springframework.boot.autoconfigure.web.ServerProperties; import org.springframework.boot.autoconfigure.web.WebMvcAutoConfiguration; +import org.springframework.boot.bind.RelaxedPropertyResolver; import org.springframework.boot.context.embedded.AnnotationConfigEmbeddedWebApplicationContext; import org.springframework.boot.context.embedded.EmbeddedServletContainerException; import org.springframework.boot.context.embedded.EmbeddedWebApplicationContext; @@ -50,11 +57,14 @@ import org.springframework.context.ApplicationContextAware; import org.springframework.context.ApplicationListener; import org.springframework.context.ConfigurableApplicationContext; import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.ConditionContext; +import org.springframework.context.annotation.Conditional; import org.springframework.context.annotation.Configuration; import org.springframework.context.annotation.Import; import org.springframework.context.event.ContextClosedEvent; import org.springframework.core.env.ConfigurableEnvironment; import org.springframework.core.env.PropertySource; +import org.springframework.core.type.AnnotatedTypeMetadata; import org.springframework.web.context.WebApplicationContext; import org.springframework.web.filter.OncePerRequestFilter; import org.springframework.web.servlet.DispatcherServlet; @@ -76,10 +86,10 @@ import org.springframework.web.servlet.DispatcherServlet; @ConditionalOnClass({ Servlet.class, DispatcherServlet.class }) @ConditionalOnWebApplication @AutoConfigureAfter({ PropertyPlaceholderAutoConfiguration.class, - EmbeddedServletContainerAutoConfiguration.class, WebMvcAutoConfiguration.class, - ManagementServerPropertiesAutoConfiguration.class }) + EmbeddedServletContainerAutoConfiguration.class, WebMvcAutoConfiguration.class, + ManagementServerPropertiesAutoConfiguration.class }) public class EndpointWebMvcAutoConfiguration implements ApplicationContextAware, - SmartInitializingSingleton { +SmartInitializingSingleton { private static Log logger = LogFactory.getLog(EndpointWebMvcAutoConfiguration.class); @@ -91,7 +101,7 @@ public class EndpointWebMvcAutoConfiguration implements ApplicationContextAware, this.applicationContext = applicationContext; } - @ConditionalOnManagementMvcContext + @Conditional(OnManagementMvcCondition.class) @Configuration @Import(EndpointWebMvcImportSelector.class) protected static class EndpointWebMvcConfiguration { @@ -109,7 +119,7 @@ public class EndpointWebMvcAutoConfiguration implements ApplicationContextAware, if (managementPort == ManagementServerPort.DIFFERENT && this.applicationContext instanceof EmbeddedWebApplicationContext && ((EmbeddedWebApplicationContext) this.applicationContext) - .getEmbeddedServletContainer() != null) { + .getEmbeddedServletContainer() != null) { createChildManagementContext(); } if (managementPort == ManagementServerPort.SAME @@ -129,7 +139,7 @@ public class EndpointWebMvcAutoConfiguration implements ApplicationContextAware, EmbeddedServletContainerAutoConfiguration.class, DispatcherServletAutoConfiguration.class); CloseEventPropagationListener - .addIfPossible(this.applicationContext, childContext); + .addIfPossible(this.applicationContext, childContext); try { childContext.refresh(); managementContextResolver().setApplicationContext(childContext); @@ -195,7 +205,7 @@ public class EndpointWebMvcAutoConfiguration implements ApplicationContextAware, @Override protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain filterChain) - throws ServletException, IOException { + throws ServletException, IOException { if (this.properties == null) { this.properties = this.applicationContext .getBean(ManagementServerProperties.class); @@ -214,7 +224,7 @@ public class EndpointWebMvcAutoConfiguration implements ApplicationContextAware, * parent to a child. */ private static class CloseEventPropagationListener implements - ApplicationListener { + ApplicationListener { private final ApplicationContext parentContext; @@ -279,7 +289,89 @@ public class EndpointWebMvcAutoConfiguration implements ApplicationContextAware, return ((port == null) || (serverProperties.getPort() == null && port.equals(8080)) || (port != 0 && port.equals(serverProperties.getPort())) ? SAME - : DIFFERENT); + : DIFFERENT); + } + + } + + private static class OnManagementMvcCondition extends SpringBootCondition { + + @Override + public ConditionOutcome getMatchOutcome(ConditionContext context, + AnnotatedTypeMetadata metadata) { + RelaxedPropertyResolver management = new RelaxedPropertyResolver( + context.getEnvironment(), "management."); + RelaxedPropertyResolver server = new RelaxedPropertyResolver( + context.getEnvironment(), "server."); + Integer managementPort = management.getProperty("port", Integer.class); + if (managementPort == null) { + ManagementServerProperties managementServerProperties = getBeanCarefully( + context, ManagementServerProperties.class); + if (managementServerProperties != null) { + managementPort = managementServerProperties.getPort(); + } + } + if (managementPort != null && managementPort < 0) { + return new ConditionOutcome(false, "The mangagement port is disabled"); + } + if (!(context.getResourceLoader() instanceof WebApplicationContext)) { + // Current context is not a webapp + return new ConditionOutcome(false, "The context is not a webapp"); + } + Integer serverPort = server.getProperty("port", Integer.class); + if (serverPort == null) { + ServerProperties serverProperties = getBeanCarefully(context, + ServerProperties.class); + if (serverProperties != null) { + serverPort = serverProperties.getPort(); + } + } + if ((managementPort == null) + || (serverPort == null && managementPort.equals(8080)) + || (managementPort != 0 && managementPort.equals(serverPort))) { + return ConditionOutcome.match("The main context is the management context"); + } + return ConditionOutcome.noMatch("The main context is not the management context"); + } + + private T getBeanCarefully(ConditionContext context, Class type) { + String[] names = BeanFactoryUtils.beanNamesForTypeIncludingAncestors( + context.getBeanFactory(), type, false, false); + if (names.length == 1) { + BeanDefinition original = findBeanDefinition(context.getBeanFactory(), + names[0]); + if (original instanceof RootBeanDefinition) { + DefaultListableBeanFactory temp = new DefaultListableBeanFactory(); + temp.setParentBeanFactory(context.getBeanFactory()); + temp.registerBeanDefinition("bean", + ((RootBeanDefinition) original).cloneBeanDefinition()); + return temp.getBean(type); + } + return BeanFactoryUtils.beanOfType(context.getBeanFactory(), type, false, + false); + } + ; + return null; + } + + private BeanDefinition findBeanDefinition( + ConfigurableListableBeanFactory beanFactory, String name) { + BeanDefinition original = null; + while (beanFactory != null && original == null) { + if (beanFactory.containsLocalBean(name)) { + original = beanFactory.getBeanDefinition(name); + } + else { + BeanFactory parentBeanFactory = beanFactory.getParentBeanFactory(); + if (parentBeanFactory instanceof ConfigurableListableBeanFactory) { + beanFactory = (ConfigurableListableBeanFactory) parentBeanFactory; + } + else { + beanFactory = null; + } + } + } + return original; } } diff --git a/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/condition/ConditionalOnManagementMvcContext.java b/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/condition/ConditionalOnManagementMvcContext.java deleted file mode 100644 index e5a132165dc..00000000000 --- a/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/condition/ConditionalOnManagementMvcContext.java +++ /dev/null @@ -1,38 +0,0 @@ -/* - * Copyright 2012-2015 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.condition; - -import java.lang.annotation.ElementType; -import java.lang.annotation.Retention; -import java.lang.annotation.RetentionPolicy; -import java.lang.annotation.Target; - -import org.springframework.context.annotation.Conditional; - -/** - * {@link Conditional} that matches according to the way the management MVC endpoints are - * deployed. - * - * @author Dave Syer - * @since 1.3.0 - */ -@Conditional(OnManagementMvcCondition.class) -@Retention(RetentionPolicy.RUNTIME) -@Target({ ElementType.TYPE, ElementType.METHOD }) -public @interface ConditionalOnManagementMvcContext { - -} diff --git a/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/condition/OnManagementMvcCondition.java b/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/condition/OnManagementMvcCondition.java deleted file mode 100644 index 8fcf3cb9b1d..00000000000 --- a/spring-boot-actuator/src/main/java/org/springframework/boot/actuate/condition/OnManagementMvcCondition.java +++ /dev/null @@ -1,122 +0,0 @@ -/* - * Copyright 2012-2015 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.condition; - -import org.springframework.beans.factory.BeanFactory; -import org.springframework.beans.factory.BeanFactoryUtils; -import org.springframework.beans.factory.config.BeanDefinition; -import org.springframework.beans.factory.config.ConfigurableListableBeanFactory; -import org.springframework.beans.factory.support.DefaultListableBeanFactory; -import org.springframework.beans.factory.support.RootBeanDefinition; -import org.springframework.boot.actuate.autoconfigure.ManagementServerProperties; -import org.springframework.boot.autoconfigure.condition.ConditionOutcome; -import org.springframework.boot.autoconfigure.condition.SpringBootCondition; -import org.springframework.boot.autoconfigure.web.ServerProperties; -import org.springframework.boot.bind.RelaxedPropertyResolver; -import org.springframework.context.annotation.Condition; -import org.springframework.context.annotation.ConditionContext; -import org.springframework.core.type.AnnotatedTypeMetadata; -import org.springframework.web.context.WebApplicationContext; - -/** - * {@link Condition} that checks whether or not the management MVC endpoints are in the - * main context. - * - * @author Dave Syer - * @see ConditionalOnManagementMvcContext - */ -class OnManagementMvcCondition extends SpringBootCondition { - - @Override - public ConditionOutcome getMatchOutcome(ConditionContext context, - AnnotatedTypeMetadata metadata) { - RelaxedPropertyResolver management = new RelaxedPropertyResolver( - context.getEnvironment(), "management."); - RelaxedPropertyResolver server = new RelaxedPropertyResolver( - context.getEnvironment(), "server."); - Integer managementPort = management.getProperty("port", Integer.class); - if (managementPort == null) { - ManagementServerProperties managementServerProperties = getBeanCarefully( - context, ManagementServerProperties.class); - if (managementServerProperties != null) { - managementPort = managementServerProperties.getPort(); - } - } - if (managementPort != null && managementPort < 0) { - return new ConditionOutcome(false, "The mangagement port is disabled"); - } - if (!(context.getResourceLoader() instanceof WebApplicationContext)) { - // Current context is not a webapp - return new ConditionOutcome(false, "The context is not a webapp"); - } - Integer serverPort = server.getProperty("port", Integer.class); - if (serverPort == null) { - ServerProperties serverProperties = getBeanCarefully(context, - ServerProperties.class); - if (serverProperties != null) { - serverPort = serverProperties.getPort(); - } - } - if ((managementPort == null) - || (serverPort == null && managementPort.equals(8080)) - || (managementPort != 0 && managementPort.equals(serverPort))) { - return ConditionOutcome.match("The main context is the management context"); - } - return ConditionOutcome.noMatch("The main context is not the management context"); - } - - private T getBeanCarefully(ConditionContext context, Class type) { - String[] names = BeanFactoryUtils.beanNamesForTypeIncludingAncestors( - context.getBeanFactory(), type, false, false); - if (names.length == 1) { - BeanDefinition original = findBeanDefinition(context.getBeanFactory(), - names[0]); - if (original instanceof RootBeanDefinition) { - DefaultListableBeanFactory temp = new DefaultListableBeanFactory(); - temp.setParentBeanFactory(context.getBeanFactory()); - temp.registerBeanDefinition("bean", - ((RootBeanDefinition) original).cloneBeanDefinition()); - return temp.getBean(type); - } - return BeanFactoryUtils.beanOfType(context.getBeanFactory(), type, false, - false); - } - ; - return null; - } - - private BeanDefinition findBeanDefinition( - ConfigurableListableBeanFactory beanFactory, String name) { - BeanDefinition original = null; - while (beanFactory != null && original == null) { - if (beanFactory.containsLocalBean(name)) { - original = beanFactory.getBeanDefinition(name); - } - else { - BeanFactory parentBeanFactory = beanFactory.getParentBeanFactory(); - if (parentBeanFactory instanceof ConfigurableListableBeanFactory) { - beanFactory = (ConfigurableListableBeanFactory) parentBeanFactory; - } - else { - beanFactory = null; - } - } - } - return original; - } - -}