diff --git a/dubbo-config/dubbo-config-api/src/main/java/org/apache/dubbo/config/ReferenceConfig.java b/dubbo-config/dubbo-config-api/src/main/java/org/apache/dubbo/config/ReferenceConfig.java index f38b80ba3e9..6445588c582 100644 --- a/dubbo-config/dubbo-config-api/src/main/java/org/apache/dubbo/config/ReferenceConfig.java +++ b/dubbo-config/dubbo-config-api/src/main/java/org/apache/dubbo/config/ReferenceConfig.java @@ -231,9 +231,10 @@ public synchronized void init() { return; } + if (bootstrap == null) { bootstrap = DubboBootstrap.getInstance(); - bootstrap.init(); + bootstrap.initialize(); } checkAndUpdateSubConfigs(); diff --git a/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/ReferenceBean.java b/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/ReferenceBean.java index be9cd718ce3..b7e470f296a 100644 --- a/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/ReferenceBean.java +++ b/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/ReferenceBean.java @@ -83,17 +83,20 @@ public boolean isSingleton() { * Initializes there Dubbo's Config Beans before @Reference bean autowiring */ private void prepareDubboConfigBeans() { - beansOfTypeIncludingAncestors(applicationContext, ApplicationConfig.class); - beansOfTypeIncludingAncestors(applicationContext, ModuleConfig.class); - beansOfTypeIncludingAncestors(applicationContext, RegistryConfig.class); - beansOfTypeIncludingAncestors(applicationContext, ProtocolConfig.class); - beansOfTypeIncludingAncestors(applicationContext, MonitorConfig.class); - beansOfTypeIncludingAncestors(applicationContext, ProviderConfig.class); - beansOfTypeIncludingAncestors(applicationContext, ConsumerConfig.class); - beansOfTypeIncludingAncestors(applicationContext, ConfigCenterBean.class); - beansOfTypeIncludingAncestors(applicationContext, MetadataReportConfig.class); - beansOfTypeIncludingAncestors(applicationContext, MetricsConfig.class); - beansOfTypeIncludingAncestors(applicationContext, SslConfig.class); + // Refactor 2.7.9 + final boolean includeNonSingletons = true; + final boolean allowEagerInit = false; + beansOfTypeIncludingAncestors(applicationContext, ApplicationConfig.class, includeNonSingletons, allowEagerInit); + beansOfTypeIncludingAncestors(applicationContext, ModuleConfig.class, includeNonSingletons, allowEagerInit); + beansOfTypeIncludingAncestors(applicationContext, RegistryConfig.class, includeNonSingletons, allowEagerInit); + beansOfTypeIncludingAncestors(applicationContext, ProtocolConfig.class, includeNonSingletons, allowEagerInit); + beansOfTypeIncludingAncestors(applicationContext, MonitorConfig.class, includeNonSingletons, allowEagerInit); + beansOfTypeIncludingAncestors(applicationContext, ProviderConfig.class, includeNonSingletons, allowEagerInit); + beansOfTypeIncludingAncestors(applicationContext, ConsumerConfig.class, includeNonSingletons, allowEagerInit); + beansOfTypeIncludingAncestors(applicationContext, ConfigCenterBean.class, includeNonSingletons, allowEagerInit); + beansOfTypeIncludingAncestors(applicationContext, MetadataReportConfig.class, includeNonSingletons, allowEagerInit); + beansOfTypeIncludingAncestors(applicationContext, MetricsConfig.class, includeNonSingletons, allowEagerInit); + beansOfTypeIncludingAncestors(applicationContext, SslConfig.class, includeNonSingletons, allowEagerInit); } @Override diff --git a/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/beans/factory/config/DubboConfigEarlyInitializationPostProcessor.java b/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/beans/factory/config/DubboConfigEarlyInitializationPostProcessor.java new file mode 100644 index 00000000000..7ec87cafbac --- /dev/null +++ b/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/beans/factory/config/DubboConfigEarlyInitializationPostProcessor.java @@ -0,0 +1,127 @@ +/* + * 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.beans.factory.config; + +import org.apache.dubbo.config.AbstractConfig; +import org.apache.dubbo.config.context.ConfigManager; + +import com.alibaba.spring.beans.factory.config.GenericBeanPostProcessorAdapter; +import org.apache.commons.logging.Log; +import org.apache.commons.logging.LogFactory; +import org.springframework.beans.BeansException; +import org.springframework.beans.factory.config.BeanPostProcessor; +import org.springframework.beans.factory.config.ConfigurableListableBeanFactory; +import org.springframework.beans.factory.support.BeanDefinitionRegistry; +import org.springframework.beans.factory.support.BeanDefinitionRegistryPostProcessor; +import org.springframework.beans.factory.support.DefaultListableBeanFactory; +import org.springframework.context.annotation.CommonAnnotationBeanPostProcessor; +import org.springframework.core.PriorityOrdered; + +import javax.annotation.PostConstruct; + +/** + * Generally, {@link AbstractConfig Dubbo Config} Bean will be added into {@link ConfigManager} on the bean initialization + * life cycle through {@link CommonAnnotationBeanPostProcessor} executing the callback of + * {@link PostConstruct @PostConstruct}. However, the instantiation and initialization of + * {@link AbstractConfig Dubbo Config} Bean could be too early before {@link CommonAnnotationBeanPostProcessor}, e.g, + * execution, thus it's required to register the current instance as a {@link BeanPostProcessor} into + * {@link DefaultListableBeanFactory the BeanFatory} using {@link BeanDefinitionRegistryPostProcessor} as early as + * possible. + * + * @see GenericBeanPostProcessorAdapter + * @since 2.7.9 + */ +public class DubboConfigEarlyInitializationPostProcessor extends GenericBeanPostProcessorAdapter + implements BeanDefinitionRegistryPostProcessor, PriorityOrdered { + + private static final Log logger = LogFactory.getLog(DubboConfigEarlyInitializationPostProcessor.class.getName()); + + public static final String BEAN_NAME = "dubboConfigEarlyInitializationPostProcessor"; + + private DefaultListableBeanFactory beanFactory; + + @Override + public void postProcessBeanDefinitionRegistry(BeanDefinitionRegistry registry) throws BeansException { + this.beanFactory = unwrap(registry); + initBeanFactory(); + } + + @Override + public void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) throws BeansException { + if (beanFactory == null) { // try again if postProcessBeanDefinitionRegistry method does not effect. + this.beanFactory = unwrap(beanFactory); + initBeanFactory(); + } + } + + protected void processBeforeInitialization(AbstractConfig config, String beanName) throws BeansException { + + if (this.beanFactory == null) { + if (logger.isErrorEnabled()) { + logger.error("Current Processor is not running in Spring container, next action will be skipped!"); + } + return; + } + + // If CommonAnnotationBeanPostProcessor is already registered, the method addIntoConfigManager() + // will be invoked in Bean life cycle. + if (!hasRegisteredCommonAnnotationBeanPostProcessor()) { + if (logger.isWarnEnabled()) { + logger.warn("CommonAnnotationBeanPostProcessor is not registered yet, " + + "the method addIntoConfigManager() will be invoked directly"); + } + config.addIntoConfigManager(); + } + } + + private DefaultListableBeanFactory unwrap(Object registry) { + if (registry instanceof DefaultListableBeanFactory) { + return (DefaultListableBeanFactory) registry; + } + return null; + } + + private void initBeanFactory() { + if (beanFactory != null) { + // Register itself + if (logger.isInfoEnabled()) { + logger.info("BeanFactory is about to be initialized, trying to resolve the Dubbo Config Beans early " + + "initialization"); + } + beanFactory.addBeanPostProcessor(this); + } + } + + /** + * {@link DefaultListableBeanFactory} has registered {@link CommonAnnotationBeanPostProcessor} or not? + * + * @return if registered, return true, or false + */ + private boolean hasRegisteredCommonAnnotationBeanPostProcessor() { + for (BeanPostProcessor beanPostProcessor : beanFactory.getBeanPostProcessors()) { + if (CommonAnnotationBeanPostProcessor.class.equals(beanPostProcessor.getClass())) { + return true; + } + } + return false; + } + + @Override + public int getOrder() { + return HIGHEST_PRECEDENCE; + } +} diff --git a/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/context/DubboApplicationListenerRegistrar.java b/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/context/DubboApplicationListenerRegistrar.java new file mode 100644 index 00000000000..cc45e1a326d --- /dev/null +++ b/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/context/DubboApplicationListenerRegistrar.java @@ -0,0 +1,59 @@ +/* + * 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.context; + +import org.springframework.beans.BeansException; +import org.springframework.context.ApplicationContext; +import org.springframework.context.ApplicationContextAware; +import org.springframework.context.ApplicationListener; +import org.springframework.context.ConfigurableApplicationContext; + +import static org.springframework.util.TypeUtils.isAssignable; + +/** + * Dubbo {@link ApplicationListener ApplicationListeners} Registrar + * + * @since 2.7.9 + */ +public class DubboApplicationListenerRegistrar implements ApplicationContextAware { + + /** + * The bean name of {@link DubboApplicationListenerRegistrar} + */ + public static final String BEAN_NAME = "dubboApplicationListenerRegister"; + + @Override + public void setApplicationContext(ApplicationContext applicationContext) throws BeansException { + if (!isAssignable(ConfigurableApplicationContext.class, applicationContext.getClass())) { + throw new IllegalArgumentException("The argument of ApplicationContext must be ConfigurableApplicationContext"); + } + addApplicationListeners((ConfigurableApplicationContext) applicationContext); + } + + private void addApplicationListeners(ConfigurableApplicationContext context) { + context.addApplicationListener(createDubboBootstrapApplicationListener(context)); + context.addApplicationListener(createDubboLifecycleComponentApplicationListener(context)); + } + + private ApplicationListener createDubboBootstrapApplicationListener(ConfigurableApplicationContext context) { + return new DubboBootstrapApplicationListener(context); + } + + private ApplicationListener createDubboLifecycleComponentApplicationListener(ConfigurableApplicationContext context) { + return new DubboLifecycleComponentApplicationListener(context); + } +} diff --git a/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/context/DubboBootstrapApplicationListener.java b/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/context/DubboBootstrapApplicationListener.java index 4a988804bf3..fcb72088f95 100644 --- a/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/context/DubboBootstrapApplicationListener.java +++ b/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/context/DubboBootstrapApplicationListener.java @@ -18,6 +18,8 @@ import org.apache.dubbo.config.bootstrap.DubboBootstrap; +import com.alibaba.spring.context.OnceApplicationContextEventListener; +import org.springframework.context.ApplicationContext; import org.springframework.context.ApplicationListener; import org.springframework.context.event.ApplicationContextEvent; import org.springframework.context.event.ContextClosedEvent; @@ -30,8 +32,7 @@ * * @since 2.7.5 */ -public class DubboBootstrapApplicationListener extends OneTimeExecutionApplicationContextEventListener - implements Ordered { +public class DubboBootstrapApplicationListener extends OnceApplicationContextEventListener implements Ordered { /** * The bean name of {@link DubboBootstrapApplicationListener} @@ -42,7 +43,8 @@ public class DubboBootstrapApplicationListener extends OneTimeExecutionApplicati private final DubboBootstrap dubboBootstrap; - public DubboBootstrapApplicationListener() { + public DubboBootstrapApplicationListener(ApplicationContext applicationContext) { + super(applicationContext); this.dubboBootstrap = DubboBootstrap.getInstance(); } diff --git a/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/context/DubboLifecycleComponentApplicationListener.java b/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/context/DubboLifecycleComponentApplicationListener.java index 7e7ae839711..353380467ed 100644 --- a/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/context/DubboLifecycleComponentApplicationListener.java +++ b/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/context/DubboLifecycleComponentApplicationListener.java @@ -19,6 +19,7 @@ import org.apache.dubbo.common.context.Lifecycle; +import com.alibaba.spring.context.OnceApplicationContextEventListener; import org.springframework.context.ApplicationContext; import org.springframework.context.ApplicationListener; import org.springframework.context.event.ApplicationContextEvent; @@ -39,7 +40,7 @@ * @see SmartApplicationListener * @since 2.7.5 */ -public class DubboLifecycleComponentApplicationListener extends OneTimeExecutionApplicationContextEventListener { +public class DubboLifecycleComponentApplicationListener extends OnceApplicationContextEventListener { /** * The bean name of {@link DubboLifecycleComponentApplicationListener} @@ -50,6 +51,10 @@ public class DubboLifecycleComponentApplicationListener extends OneTimeExecution private List lifecycleComponents = emptyList(); + public DubboLifecycleComponentApplicationListener(ApplicationContext applicationContext) { + super(applicationContext); + } + @Override protected void onApplicationContextEvent(ApplicationContextEvent event) { if (event instanceof ContextRefreshedEvent) { diff --git a/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/context/OneTimeExecutionApplicationContextEventListener.java b/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/context/OneTimeExecutionApplicationContextEventListener.java deleted file mode 100644 index 569a67ec7c4..00000000000 --- a/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/context/OneTimeExecutionApplicationContextEventListener.java +++ /dev/null @@ -1,71 +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.context; - -import org.springframework.beans.BeansException; -import org.springframework.context.ApplicationContext; -import org.springframework.context.ApplicationContextAware; -import org.springframework.context.ApplicationEvent; -import org.springframework.context.ApplicationListener; -import org.springframework.context.event.ApplicationContextEvent; - -import java.util.Objects; - -/** - * The abstract class {@link ApplicationListener} for {@link ApplicationContextEvent} guarantees just one-time execution - * and prevents the event propagation in the hierarchical {@link ApplicationContext ApplicationContexts} - * - * @since 2.7.5 - */ -abstract class OneTimeExecutionApplicationContextEventListener implements ApplicationListener, ApplicationContextAware { - - private ApplicationContext applicationContext; - - public final void onApplicationEvent(ApplicationEvent event) { - if (isOriginalEventSource(event) && event instanceof ApplicationContextEvent) { - onApplicationContextEvent((ApplicationContextEvent) event); - } - } - - /** - * The subclass overrides this method to handle {@link ApplicationContextEvent} - * - * @param event {@link ApplicationContextEvent} - */ - protected abstract void onApplicationContextEvent(ApplicationContextEvent event); - - /** - * Is original {@link ApplicationContext} as the event source - * - * @param event {@link ApplicationEvent} - * @return - */ - private boolean isOriginalEventSource(ApplicationEvent event) { - return (applicationContext == null) // Current ApplicationListener is not a Spring Bean, just was added - // into Spring's ConfigurableApplicationContext - || Objects.equals(applicationContext, event.getSource()); - } - - @Override - public final void setApplicationContext(ApplicationContext applicationContext) throws BeansException { - this.applicationContext = applicationContext; - } - - public ApplicationContext getApplicationContext() { - return applicationContext; - } -} diff --git a/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/context/annotation/DubboConfigConfigurationRegistrar.java b/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/context/annotation/DubboConfigConfigurationRegistrar.java index 5417acd54a2..1e99c4a61ed 100644 --- a/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/context/annotation/DubboConfigConfigurationRegistrar.java +++ b/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/context/annotation/DubboConfigConfigurationRegistrar.java @@ -18,7 +18,11 @@ import org.apache.dubbo.config.AbstractConfig; +import org.springframework.beans.BeansException; import org.springframework.beans.factory.support.BeanDefinitionRegistry; +import org.springframework.context.ApplicationContext; +import org.springframework.context.ApplicationContextAware; +import org.springframework.context.ConfigurableApplicationContext; import org.springframework.context.annotation.ImportBeanDefinitionRegistrar; import org.springframework.core.Ordered; import org.springframework.core.annotation.AnnotationAttributes; @@ -35,7 +39,9 @@ * @see Ordered * @since 2.5.8 */ -public class DubboConfigConfigurationRegistrar implements ImportBeanDefinitionRegistrar { +public class DubboConfigConfigurationRegistrar implements ImportBeanDefinitionRegistrar, ApplicationContextAware { + + private ConfigurableApplicationContext applicationContext; @Override public void registerBeanDefinitions(AnnotationMetadata importingClassMetadata, BeanDefinitionRegistry registry) { @@ -55,4 +61,12 @@ public void registerBeanDefinitions(AnnotationMetadata importingClassMetadata, B // Since 2.7.6 registerCommonBeans(registry); } + + @Override + public void setApplicationContext(ApplicationContext applicationContext) throws BeansException { + if (!(applicationContext instanceof ConfigurableApplicationContext)) { + throw new IllegalArgumentException("The argument of ApplicationContext must be ConfigurableApplicationContext"); + } + this.applicationContext = (ConfigurableApplicationContext) applicationContext; + } } diff --git a/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/util/DubboBeanUtils.java b/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/util/DubboBeanUtils.java index 3b2c31c9539..4a07e0ddbdf 100644 --- a/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/util/DubboBeanUtils.java +++ b/dubbo-config/dubbo-config-spring/src/main/java/org/apache/dubbo/config/spring/util/DubboBeanUtils.java @@ -19,6 +19,8 @@ import org.apache.dubbo.config.spring.beans.factory.annotation.DubboConfigAliasPostProcessor; import org.apache.dubbo.config.spring.beans.factory.annotation.ReferenceAnnotationBeanPostProcessor; import org.apache.dubbo.config.spring.beans.factory.config.DubboConfigDefaultPropertyValueBeanPostProcessor; +import org.apache.dubbo.config.spring.beans.factory.config.DubboConfigEarlyInitializationPostProcessor; +import org.apache.dubbo.config.spring.context.DubboApplicationListenerRegistrar; import org.apache.dubbo.config.spring.context.DubboBootstrapApplicationListener; import org.apache.dubbo.config.spring.context.DubboLifecycleComponentApplicationListener; @@ -53,16 +55,26 @@ static void registerCommonBeans(BeanDefinitionRegistry registry) { registerInfrastructureBean(registry, DubboConfigAliasPostProcessor.BEAN_NAME, DubboConfigAliasPostProcessor.class); + // Since 2.7.9 Register DubboApplicationListenerRegister as an infrastructure Bean + // https://github.com/apache/dubbo/issues/6559 + // Since 2.7.5 Register DubboLifecycleComponentApplicationListener as an infrastructure Bean - registerInfrastructureBean(registry, DubboLifecycleComponentApplicationListener.BEAN_NAME, - DubboLifecycleComponentApplicationListener.class); + // registerInfrastructureBean(registry, DubboLifecycleComponentApplicationListener.BEAN_NAME, + // DubboLifecycleComponentApplicationListener.class); // Since 2.7.4 Register DubboBootstrapApplicationListener as an infrastructure Bean - registerInfrastructureBean(registry, DubboBootstrapApplicationListener.BEAN_NAME, - DubboBootstrapApplicationListener.class); + // registerInfrastructureBean(registry, DubboBootstrapApplicationListener.BEAN_NAME, + // DubboBootstrapApplicationListener.class); + + registerInfrastructureBean(registry, DubboApplicationListenerRegistrar.BEAN_NAME, + DubboApplicationListenerRegistrar.class); // Since 2.7.6 Register DubboConfigDefaultPropertyValueBeanPostProcessor as an infrastructure Bean registerInfrastructureBean(registry, DubboConfigDefaultPropertyValueBeanPostProcessor.BEAN_NAME, DubboConfigDefaultPropertyValueBeanPostProcessor.class); + + // Since 2.7.9 Register DubboConfigEarlyInitializationPostProcessor as an infrastructure Bean + registerInfrastructureBean(registry, DubboConfigEarlyInitializationPostProcessor.BEAN_NAME, + DubboConfigEarlyInitializationPostProcessor.class); } } diff --git a/dubbo-config/dubbo-config-spring/src/test/java/org/apache/dubbo/config/spring/beans/factory/annotation/DubboReferenceGenericTest.java b/dubbo-config/dubbo-config-spring/src/test/java/org/apache/dubbo/config/spring/beans/factory/annotation/DubboReferenceGenericTest.java new file mode 100644 index 00000000000..7fb2d1bb63e --- /dev/null +++ b/dubbo-config/dubbo-config-spring/src/test/java/org/apache/dubbo/config/spring/beans/factory/annotation/DubboReferenceGenericTest.java @@ -0,0 +1,117 @@ +/* + * 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.beans.factory.annotation; + +import org.apache.dubbo.config.annotation.DubboReference; +import org.apache.dubbo.config.spring.api.HelloService; + +import org.junit.Test; +import org.junit.runner.RunWith; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.context.annotation.Bean; +import org.springframework.test.context.ContextConfiguration; +import org.springframework.test.context.TestPropertySource; +import org.springframework.test.context.junit4.SpringRunner; + +import static org.apache.dubbo.config.spring.beans.factory.annotation.ReferenceAnnotationBeanPostProcessor.BEAN_NAME; +import static org.junit.Assert.assertEquals; + +/** + * {@link DubboReference @DubboReference} of Generic injection test + * + * @see DubboReference + * @since 2.7.9 + */ +@RunWith(SpringRunner.class) +@ContextConfiguration( + classes = { + ServiceAnnotationTestConfiguration.class, + DubboReferenceGenericTest.class + }) +@TestPropertySource(properties = { + "packagesToScan = org.apache.dubbo.config.spring.context.annotation.provider", + "consumer.version = ${demo.service.version}", + "consumer.url = dubbo://127.0.0.1:12345?version=2.5.7", +}) +public class DubboReferenceGenericTest { + + @Bean + public HelloServiceManager helloServiceManager() { + return new HelloServiceManager(); + } + + @Bean(BEAN_NAME) + public ReferenceAnnotationBeanPostProcessor referenceAnnotationBeanPostProcessor() { + return new ReferenceAnnotationBeanPostProcessor(); + } + + @Bean + public String helloWorld() { + return "Hello,World"; + } + + @Bean + public StringService stringService() { + return new StringService(); + } + + @DubboReference + private HelloService helloService; + + @Autowired + private StringService stringService; + + @Autowired + private HelloServiceManager helloServiceManager; + + @Test + public void test() { + assertEquals("Hello,World", stringService.getS()); + HelloService helloService = helloServiceManager.getService(); + assertEquals("Greeting, Mercy", helloService.sayHello("Mercy")); + } + + + static abstract class AbstractServiceManager { + + @DubboReference + protected S service; + + public S getService() { + return service; + } + } + + static class HelloServiceManager extends AbstractServiceManager { + + } + + static abstract class AbstractService { + + @Autowired + private S s; + + public S getS() { + return s; + } + } + + static class StringService extends AbstractService { + + } + +} diff --git a/dubbo-dependencies-bom/pom.xml b/dubbo-dependencies-bom/pom.xml index e304361b861..df6dc65a0a2 100644 --- a/dubbo-dependencies-bom/pom.xml +++ b/dubbo-dependencies-bom/pom.xml @@ -149,7 +149,7 @@ 4.10.3 - 1.0.8 + 1.0.10 2.2.7 1.2.0