diff --git a/dubbo-config/dubbo-config-spring/pom.xml b/dubbo-config/dubbo-config-spring/pom.xml index dc333e7a8e4..995209db45e 100644 --- a/dubbo-config/dubbo-config-spring/pom.xml +++ b/dubbo-config/dubbo-config-spring/pom.xml @@ -112,18 +112,21 @@ javax.el test - org.springframework spring-tx test - org.springframework spring-test test + + org.apache.tomcat.embed + tomcat-embed-core + test + diff --git a/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/initializer/DubboApplicationContextInitializer.java b/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/initializer/DubboApplicationContextInitializer.java new file mode 100644 index 00000000000..36727e669f4 --- /dev/null +++ b/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/initializer/DubboApplicationContextInitializer.java @@ -0,0 +1,39 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF 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 + * + * 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.apache.dubbo.config.spring.initializer; + +import org.springframework.context.ApplicationContextInitializer; +import org.springframework.context.ConfigurableApplicationContext; + +/** + * Automatically register {@link DubboApplicationListener} to Spring context + * A {@link org.springframework.web.context.ContextLoaderListener} class is defined in + * src/main/resources/META-INF/web-fragment.xml + * In the web-fragment.xml, {@link DubboApplicationContextInitializer} is defined in context params. + * This file will be discovered if running under a servlet 3.0+ container. + * Even if user specifies {@link org.springframework.web.context.ContextLoaderListener} in web.xml, + * it will be merged to web.xml. + * If user specifies in web.xml, this will no take effect, + * unless user configures {@link DubboApplicationContextInitializer} explicitly in web.xml. + */ +public class DubboApplicationContextInitializer implements ApplicationContextInitializer { + + @Override + public void initialize(ConfigurableApplicationContext applicationContext) { + applicationContext.addApplicationListener(new DubboApplicationListener()); + } +} diff --git a/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/initializer/DubboWebApplicationInitializer.java b/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/initializer/DubboWebApplicationInitializer.java deleted file mode 100644 index 582535bb8bf..00000000000 --- a/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/initializer/DubboWebApplicationInitializer.java +++ /dev/null @@ -1,40 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright ownership. - * The ASF 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 - * - * 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.apache.dubbo.config.spring.initializer; - -import org.springframework.web.context.AbstractContextLoaderInitializer; -import org.springframework.web.context.WebApplicationContext; -import org.springframework.web.context.support.XmlWebApplicationContext; - -/** - * An initializer to register {@link DubboApplicationListener} - * to the ApplicationContext seamlessly. - */ -public class DubboWebApplicationInitializer extends AbstractContextLoaderInitializer { - - /** - * This method won't be triggered if running on spring-boot. - * It only works when running under a servlet container. - * @return a WebApplicationContext with DubboApplicationListener registered. - */ - @Override - protected WebApplicationContext createRootApplicationContext() { - XmlWebApplicationContext webApplicationContext = new XmlWebApplicationContext(); - webApplicationContext.addApplicationListener(new DubboApplicationListener()); - return webApplicationContext; - } -} diff --git a/dubbo-config/dubbo-config-spring/src/main/resources/META-INF/web-fragment.xml b/dubbo-config/dubbo-config-spring/src/main/resources/META-INF/web-fragment.xml new file mode 100644 index 00000000000..220874ab78c --- /dev/null +++ b/dubbo-config/dubbo-config-spring/src/main/resources/META-INF/web-fragment.xml @@ -0,0 +1,22 @@ + + + dubbo-fragment + + + + + + + + + contextInitializerClasses + org.apache.dubbo.config.spring.initializer.DubboApplicationContextInitializer + + + + org.springframework.web.context.ContextLoaderListener + + + \ No newline at end of file diff --git a/dubbo-config/dubbo-config-spring/src/test/java/org/apache/dubbo/config/spring/initializer/DubboApplicationContextInitializerTest.java b/dubbo-config/dubbo-config-spring/src/test/java/org/apache/dubbo/config/spring/initializer/DubboApplicationContextInitializerTest.java new file mode 100644 index 00000000000..2c84095f4e3 --- /dev/null +++ b/dubbo-config/dubbo-config-spring/src/test/java/org/apache/dubbo/config/spring/initializer/DubboApplicationContextInitializerTest.java @@ -0,0 +1,87 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF 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 + * + * 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.apache.dubbo.config.spring.initializer; + +import org.apache.catalina.core.StandardContext; +import org.apache.catalina.startup.ContextConfig; +import org.apache.catalina.startup.Tomcat; +import org.junit.Assert; +import org.junit.Test; +import org.springframework.web.context.ContextLoaderListener; + + +public class DubboApplicationContextInitializerTest { + + @Test + public void testSpringContextLoaderListenerInWebXml() throws Exception { + Tomcat tomcat = new Tomcat(); + tomcat.setBaseDir("src/test/resources"); + tomcat.setPort(12345); + StandardContext context = new StandardContext(); + context.setName("test"); + context.setDocBase("test"); + context.setPath("/test"); + context.addLifecycleListener(new ContextConfig()); + tomcat.getHost().addChild(context); + tomcat.start(); + // there should be 1 application listener + Assert.assertEquals(1, context.getApplicationLifecycleListeners().length); + // the first one should be Spring's built in ContextLoaderListener. + Assert.assertTrue(context.getApplicationLifecycleListeners()[0] instanceof ContextLoaderListener); + tomcat.stop(); + tomcat.destroy(); + } + + @Test + public void testNoListenerInWebXml() throws Exception { + Tomcat tomcat = new Tomcat(); + tomcat.setBaseDir("src/test/resources"); + tomcat.setPort(12345); + StandardContext context = new StandardContext(); + context.setName("test2"); + context.setDocBase("test2"); + context.setPath("/test2"); + context.addLifecycleListener(new ContextConfig()); + tomcat.getHost().addChild(context); + tomcat.start(); + // there should be 1 application listener + Assert.assertEquals(1, context.getApplicationLifecycleListeners().length); + // the first one should be Spring's built in ContextLoaderListener. + Assert.assertTrue(context.getApplicationLifecycleListeners()[0] instanceof ContextLoaderListener); + tomcat.stop(); + tomcat.destroy(); + } + + @Test + public void testMetadataComplete() throws Exception { + Tomcat tomcat = new Tomcat(); + tomcat.setBaseDir("src/test/resources"); + tomcat.setPort(12345); + StandardContext context = new StandardContext(); + context.setName("test3"); + context.setDocBase("test3"); + context.setPath("/test3"); + context.addLifecycleListener(new ContextConfig()); + tomcat.getHost().addChild(context); + tomcat.start(); + // there should be no application listeners + Assert.assertEquals(0, context.getApplicationLifecycleListeners().length); + tomcat.stop(); + tomcat.destroy(); + } + +} diff --git a/dubbo-config/dubbo-config-spring/src/test/resources/applicationContext.xml b/dubbo-config/dubbo-config-spring/src/test/resources/applicationContext.xml new file mode 100644 index 00000000000..977a8a43d05 --- /dev/null +++ b/dubbo-config/dubbo-config-spring/src/test/resources/applicationContext.xml @@ -0,0 +1,6 @@ + + + \ No newline at end of file diff --git a/dubbo-config/dubbo-config-spring/src/test/resources/webapps/test/WEB-INF/web.xml b/dubbo-config/dubbo-config-spring/src/test/resources/webapps/test/WEB-INF/web.xml new file mode 100644 index 00000000000..25214e23e35 --- /dev/null +++ b/dubbo-config/dubbo-config-spring/src/test/resources/webapps/test/WEB-INF/web.xml @@ -0,0 +1,14 @@ + + + dubbo-demo + + + contextConfigLocation + classpath:applicationContext.xml + + + + org.springframework.web.context.ContextLoaderListener + + + diff --git a/dubbo-config/dubbo-config-spring/src/test/resources/webapps/test2/WEB-INF/web.xml b/dubbo-config/dubbo-config-spring/src/test/resources/webapps/test2/WEB-INF/web.xml new file mode 100644 index 00000000000..0da8d8a5db2 --- /dev/null +++ b/dubbo-config/dubbo-config-spring/src/test/resources/webapps/test2/WEB-INF/web.xml @@ -0,0 +1,10 @@ + + + dubbo-demo + + + contextConfigLocation + classpath:applicationContext.xml + + + diff --git a/dubbo-config/dubbo-config-spring/src/test/resources/webapps/test3/WEB-INF/web.xml b/dubbo-config/dubbo-config-spring/src/test/resources/webapps/test3/WEB-INF/web.xml new file mode 100644 index 00000000000..81a5a13f9ed --- /dev/null +++ b/dubbo-config/dubbo-config-spring/src/test/resources/webapps/test3/WEB-INF/web.xml @@ -0,0 +1,10 @@ + + + dubbo-demo + + + contextConfigLocation + classpath:applicationContext.xml + + +