@Autowired-driven ObjectFactory/Provider resolution works in non-singleton beans as well

Issue: SPR-9181
This commit is contained in:
Juergen Hoeller
2012-08-31 15:58:41 +02:00
parent 26ee0c4842
commit fbe955ab28
4 changed files with 62 additions and 7 deletions

View File

@@ -121,6 +121,24 @@ public class DependencyDescriptor implements Serializable {
this.eager = eager;
}
/**
* Copy constructor.
* @param original the original descriptor to create a copy from
*/
public DependencyDescriptor(DependencyDescriptor original) {
this.methodParameter = original.methodParameter;
this.field = original.field;
this.declaringClass = original.declaringClass;
this.methodName = original.methodName;
this.parameterTypes = original.parameterTypes;
this.parameterIndex = original.parameterIndex;
this.fieldName = original.fieldName;
this.required = original.required;
this.eager = original.eager;
this.nestingLevel = original.nestingLevel;
this.fieldAnnotations = original.fieldAnnotations;
}
/**
* Return the wrapped MethodParameter, if any.
@@ -156,6 +174,10 @@ public class DependencyDescriptor implements Serializable {
}
/**
* Increase this descriptor's nesting level.
* @see MethodParameter#increaseNestingLevel()
*/
public void increaseNestingLevel() {
this.nestingLevel++;
if (this.methodParameter != null) {

View File

@@ -21,14 +21,11 @@ import java.io.NotSerializableException;
import java.io.ObjectInputStream;
import java.io.ObjectStreamException;
import java.io.Serializable;
import java.lang.annotation.Annotation;
import java.lang.ref.Reference;
import java.lang.ref.WeakReference;
import java.security.AccessController;
import java.security.PrivilegedAction;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
@@ -39,7 +36,6 @@ import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import javax.inject.Provider;
import org.springframework.beans.BeansException;
@@ -1031,9 +1027,9 @@ public class DefaultListableBeanFactory extends AbstractAutowireCapableBeanFacto
private final String beanName;
public DependencyObjectFactory(DependencyDescriptor descriptor, String beanName) {
this.descriptor = descriptor;
this.beanName = beanName;
this.descriptor = new DependencyDescriptor(descriptor);
this.descriptor.increaseNestingLevel();
this.beanName = beanName;
}
public Object getObject() throws BeansException {

View File

@@ -24,7 +24,6 @@ import java.lang.annotation.Target;
import java.util.List;
import java.util.Map;
import static org.junit.Assert.*;
import org.junit.Test;
import test.beans.ITestBean;
import test.beans.IndexedTestBean;
@@ -42,6 +41,8 @@ import org.springframework.beans.factory.support.GenericBeanDefinition;
import org.springframework.beans.factory.support.RootBeanDefinition;
import org.springframework.util.SerializationTestUtils;
import static org.junit.Assert.*;
/**
* Unit tests for {@link AutowiredAnnotationBeanPostProcessor}.
*
@@ -601,6 +602,22 @@ public final class AutowiredAnnotationBeanPostProcessorTests {
bf.destroySingletons();
}
@Test
public void testObjectFactoryInjectionIntoPrototypeBean() {
DefaultListableBeanFactory bf = new DefaultListableBeanFactory();
AutowiredAnnotationBeanPostProcessor bpp = new AutowiredAnnotationBeanPostProcessor();
bpp.setBeanFactory(bf);
bf.addBeanPostProcessor(bpp);
bf.registerBeanDefinition("annotatedBean", new RootBeanDefinition(ObjectFactoryInjectionBean.class, false));
bf.registerBeanDefinition("testBean", new RootBeanDefinition(TestBean.class));
ObjectFactoryInjectionBean bean = (ObjectFactoryInjectionBean) bf.getBean("annotatedBean");
assertSame(bf.getBean("testBean"), bean.getTestBean());
ObjectFactoryInjectionBean anotherBean = (ObjectFactoryInjectionBean) bf.getBean("annotatedBean");
assertNotSame(anotherBean, bean);
assertSame(bf.getBean("testBean"), anotherBean.getTestBean());
}
@Test
public void testObjectFactoryQualifierInjection() {
DefaultListableBeanFactory bf = new DefaultListableBeanFactory();

View File

@@ -383,6 +383,26 @@ public class InjectAnnotationBeanPostProcessorTests {
bf.destroySingletons();
}
@Test
public void testObjectFactoryInjectionIntoPrototypeBean() {
DefaultListableBeanFactory bf = new DefaultListableBeanFactory();
bf.setAutowireCandidateResolver(new QualifierAnnotationAutowireCandidateResolver());
AutowiredAnnotationBeanPostProcessor bpp = new AutowiredAnnotationBeanPostProcessor();
bpp.setBeanFactory(bf);
bf.addBeanPostProcessor(bpp);
bf.registerBeanDefinition("annotatedBean", new RootBeanDefinition(ObjectFactoryQualifierInjectionBean.class, false));
RootBeanDefinition bd = new RootBeanDefinition(TestBean.class);
bd.addQualifier(new AutowireCandidateQualifier(Qualifier.class, "testBean"));
bf.registerBeanDefinition("testBean", bd);
bf.registerBeanDefinition("testBean2", new RootBeanDefinition(TestBean.class));
ObjectFactoryQualifierInjectionBean bean = (ObjectFactoryQualifierInjectionBean) bf.getBean("annotatedBean");
assertSame(bf.getBean("testBean"), bean.getTestBean());
ObjectFactoryQualifierInjectionBean anotherBean = (ObjectFactoryQualifierInjectionBean) bf.getBean("annotatedBean");
assertNotSame(anotherBean, bean);
assertSame(bf.getBean("testBean"), bean.getTestBean());
}
@Test
public void testObjectFactoryQualifierInjection() {
DefaultListableBeanFactory bf = new DefaultListableBeanFactory();