Merge branch '5.1.x'

This commit is contained in:
Juergen Hoeller
2019-02-07 16:01:14 +01:00
10 changed files with 196 additions and 82 deletions

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2018 the original author or authors.
* Copyright 2002-2019 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.
@@ -512,13 +512,19 @@ public class CommonAnnotationBeanPostProcessor extends InitDestroyAnnotationBean
Set<String> autowiredBeanNames;
String name = element.name;
if (this.fallbackToDefaultTypeMatch && element.isDefaultName &&
factory instanceof AutowireCapableBeanFactory && !factory.containsBean(name)) {
autowiredBeanNames = new LinkedHashSet<>();
resource = ((AutowireCapableBeanFactory) factory).resolveDependency(
element.getDependencyDescriptor(), requestingBeanName, autowiredBeanNames, null);
if (resource == null) {
throw new NoSuchBeanDefinitionException(element.getLookupType(), "No resolvable resource object");
if (factory instanceof AutowireCapableBeanFactory) {
AutowireCapableBeanFactory beanFactory = (AutowireCapableBeanFactory) factory;
DependencyDescriptor descriptor = element.getDependencyDescriptor();
if (this.fallbackToDefaultTypeMatch && element.isDefaultName && !factory.containsBean(name)) {
autowiredBeanNames = new LinkedHashSet<>();
resource = beanFactory.resolveDependency(descriptor, requestingBeanName, autowiredBeanNames, null);
if (resource == null) {
throw new NoSuchBeanDefinitionException(element.getLookupType(), "No resolvable resource object");
}
}
else {
resource = beanFactory.resolveBeanByName(name, descriptor);
autowiredBeanNames = Collections.singleton(name);
}
}
else {

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2018 the original author or authors.
* Copyright 2002-2019 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.
@@ -212,7 +212,11 @@ public abstract class AbstractApplicationContext extends DefaultResourceLoader
/** Statically specified listeners. */
private final Set<ApplicationListener<?>> applicationListeners = new LinkedHashSet<>();
/** ApplicationEvents published early. */
/** Local listeners registered before refresh. */
@Nullable
private Set<ApplicationListener<?>> earlyApplicationListeners;
/** ApplicationEvents published before the multicaster setup. */
@Nullable
private Set<ApplicationEvent> earlyApplicationEvents;
@@ -483,7 +487,6 @@ public abstract class AbstractApplicationContext extends DefaultResourceLoader
this.beanFactoryPostProcessors.add(postProcessor);
}
/**
* Return the list of BeanFactoryPostProcessors that will get applied
* to the internal BeanFactory.
@@ -578,6 +581,7 @@ public abstract class AbstractApplicationContext extends DefaultResourceLoader
* active flag as well as performing any initialization of property sources.
*/
protected void prepareRefresh() {
// Switch to active.
this.startupDate = System.currentTimeMillis();
this.closed.set(false);
this.active.set(true);
@@ -591,13 +595,23 @@ public abstract class AbstractApplicationContext extends DefaultResourceLoader
}
}
// Initialize any placeholder property sources in the context environment
// Initialize any placeholder property sources in the context environment.
initPropertySources();
// Validate that all properties marked as required are resolvable
// Validate that all properties marked as required are resolvable:
// see ConfigurablePropertyResolver#setRequiredProperties
getEnvironment().validateRequiredProperties();
// Store pre-refresh ApplicationListeners...
if (this.earlyApplicationListeners == null) {
this.earlyApplicationListeners = new LinkedHashSet<>(this.applicationListeners);
}
else {
// Reset local application listeners to pre-refresh state.
this.applicationListeners.clear();
this.applicationListeners.addAll(this.earlyApplicationListeners);
}
// Allow for the collection of early ApplicationEvents,
// to be published once the multicaster is available...
this.earlyApplicationEvents = new LinkedHashSet<>();
@@ -982,6 +996,7 @@ public abstract class AbstractApplicationContext extends DefaultResourceLoader
* @see #registerShutdownHook()
*/
protected void doClose() {
// Check whether an actual close attempt is necessary...
if (this.active.get() && this.closed.compareAndSet(false, true)) {
if (logger.isDebugEnabled()) {
logger.debug("Closing " + this);
@@ -1016,6 +1031,13 @@ public abstract class AbstractApplicationContext extends DefaultResourceLoader
// Let subclasses do some final clean-up if they wish...
onClose();
// Reset local application listeners to pre-refresh state.
if (this.earlyApplicationListeners != null) {
this.applicationListeners.clear();
this.applicationListeners.addAll(this.earlyApplicationListeners);
}
// Switch to inactive.
this.active.set(false);
}
}
@@ -1302,7 +1324,7 @@ public abstract class AbstractApplicationContext extends DefaultResourceLoader
@Nullable
protected MessageSource getInternalParentMessageSource() {
return (getParent() instanceof AbstractApplicationContext ?
((AbstractApplicationContext) getParent()).messageSource : getParent());
((AbstractApplicationContext) getParent()).messageSource : getParent());
}

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2018 the original author or authors.
* Copyright 2002-2019 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.
@@ -21,6 +21,7 @@ import java.util.Collections;
import java.util.List;
import java.util.Set;
import java.util.function.Supplier;
import javax.annotation.Resource;
import javax.inject.Provider;
import org.junit.Rule;
@@ -228,6 +229,22 @@ public class ConfigurationClassProcessingTests {
ctx.close();
}
@Test
public void configurationWithAdaptiveResourcePrototypes() {
AnnotationConfigApplicationContext ctx = new AnnotationConfigApplicationContext();
ctx.register(ConfigWithPrototypeBean.class, AdaptiveResourceInjectionPoints.class);
ctx.refresh();
AdaptiveResourceInjectionPoints adaptive = ctx.getBean(AdaptiveResourceInjectionPoints.class);
assertEquals("adaptiveInjectionPoint1", adaptive.adaptiveInjectionPoint1.getName());
assertEquals("setAdaptiveInjectionPoint2", adaptive.adaptiveInjectionPoint2.getName());
adaptive = ctx.getBean(AdaptiveResourceInjectionPoints.class);
assertEquals("adaptiveInjectionPoint1", adaptive.adaptiveInjectionPoint1.getName());
assertEquals("setAdaptiveInjectionPoint2", adaptive.adaptiveInjectionPoint2.getName());
ctx.close();
}
@Test
public void configurationWithPostProcessor() {
AnnotationConfigApplicationContext ctx = new AnnotationConfigApplicationContext();
@@ -444,6 +461,21 @@ public class ConfigurationClassProcessingTests {
}
@Scope("prototype")
static class AdaptiveResourceInjectionPoints {
@Resource(name = "adaptive1")
public TestBean adaptiveInjectionPoint1;
public TestBean adaptiveInjectionPoint2;
@Resource(name = "adaptive2")
public void setAdaptiveInjectionPoint2(TestBean adaptiveInjectionPoint2) {
this.adaptiveInjectionPoint2 = adaptiveInjectionPoint2;
}
}
static class ConfigWithPostProcessor extends ConfigWithPrototypeBean {
@Value("${myProp}")