Browse Source

Log warning for single optional constructor when no default constructor to fall back to

Issue: SPR-12161
(cherry picked from commit 80cec01)
pull/689/head
Juergen Hoeller 12 years ago
parent
commit
5cf452463e
  1. 12
      spring-beans/src/main/java/org/springframework/beans/factory/annotation/AutowiredAnnotationBeanPostProcessor.java
  2. 34
      spring-beans/src/test/java/org/springframework/beans/factory/annotation/AutowiredAnnotationBeanPostProcessorTests.java

12
spring-beans/src/main/java/org/springframework/beans/factory/annotation/AutowiredAnnotationBeanPostProcessor.java

@ -263,8 +263,16 @@ public class AutowiredAnnotationBeanPostProcessor extends InstantiationAwareBean @@ -263,8 +263,16 @@ public class AutowiredAnnotationBeanPostProcessor extends InstantiationAwareBean
}
if (!candidates.isEmpty()) {
// Add default constructor to list of optional constructors, as fallback.
if (requiredConstructor == null && defaultConstructor != null) {
candidates.add(defaultConstructor);
if (requiredConstructor == null) {
if (defaultConstructor != null) {
candidates.add(defaultConstructor);
}
else if (candidates.size() == 1 && logger.isWarnEnabled()) {
logger.warn("Inconsistent constructor declaration on bean with name '" + beanName +
"': single autowire-marked constructor flagged as optional - this constructor " +
"is effectively required since there is no default constructor to fall back to: " +
candidates.get(0));
}
}
candidateConstructors = candidates.toArray(new Constructor<?>[candidates.size()]);
}

34
spring-beans/src/test/java/org/springframework/beans/factory/annotation/AutowiredAnnotationBeanPostProcessorTests.java

@ -30,6 +30,7 @@ import org.springframework.beans.factory.BeanCreationException; @@ -30,6 +30,7 @@ import org.springframework.beans.factory.BeanCreationException;
import org.springframework.beans.factory.BeanFactory;
import org.springframework.beans.factory.FactoryBean;
import org.springframework.beans.factory.ObjectFactory;
import org.springframework.beans.factory.UnsatisfiedDependencyException;
import org.springframework.beans.factory.config.BeanDefinition;
import org.springframework.beans.factory.config.ConfigurableListableBeanFactory;
import org.springframework.beans.factory.support.AutowireCandidateQualifier;
@ -395,6 +396,23 @@ public class AutowiredAnnotationBeanPostProcessorTests { @@ -395,6 +396,23 @@ public class AutowiredAnnotationBeanPostProcessorTests {
bf.destroySingletons();
}
@Test
public void testConstructorResourceInjectionWithNoCandidatesAndNoFallback() {
DefaultListableBeanFactory bf = new DefaultListableBeanFactory();
AutowiredAnnotationBeanPostProcessor bpp = new AutowiredAnnotationBeanPostProcessor();
bpp.setBeanFactory(bf);
bf.addBeanPostProcessor(bpp);
bf.registerBeanDefinition("annotatedBean", new RootBeanDefinition(ConstructorWithoutFallbackBean.class));
try {
bf.getBean("annotatedBean");
fail("Should have thrown UnsatisfiedDependencyException");
}
catch (UnsatisfiedDependencyException ex) {
// expected
}
}
@Test
public void testConstructorResourceInjectionWithMultipleCandidatesAsCollection() {
DefaultListableBeanFactory bf = new DefaultListableBeanFactory();
@ -1256,6 +1274,21 @@ public class AutowiredAnnotationBeanPostProcessorTests { @@ -1256,6 +1274,21 @@ public class AutowiredAnnotationBeanPostProcessorTests {
}
public static class ConstructorWithoutFallbackBean {
protected ITestBean testBean3;
@Autowired(required = false)
public ConstructorWithoutFallbackBean(ITestBean testBean3) {
this.testBean3 = testBean3;
}
public ITestBean getTestBean3() {
return this.testBean3;
}
}
public static class ConstructorsCollectionResourceInjectionBean {
protected ITestBean testBean3;
@ -1321,7 +1354,6 @@ public class AutowiredAnnotationBeanPostProcessorTests { @@ -1321,7 +1354,6 @@ public class AutowiredAnnotationBeanPostProcessorTests {
@Autowired
private Map<String, TestBean> testBeanMap;
public Map<String, TestBean> getTestBeanMap() {
return this.testBeanMap;
}

Loading…
Cancel
Save