|
34 | 34 | import org.springframework.beans.factory.config.DependencyDescriptor;
|
35 | 35 | import org.springframework.beans.factory.config.SmartInstantiationAwareBeanPostProcessor;
|
36 | 36 | import org.springframework.beans.factory.support.BeanDefinitionRegistry;
|
| 37 | +import org.springframework.beans.factory.support.BeanNameGenerator; |
| 38 | +import org.springframework.beans.factory.support.DefaultBeanNameGenerator; |
37 | 39 | import org.springframework.beans.factory.support.RootBeanDefinition;
|
38 | 40 | import org.springframework.core.Ordered;
|
39 | 41 | import org.springframework.core.PriorityOrdered;
|
@@ -63,6 +65,8 @@ class BeanOverrideBeanFactoryPostProcessor implements BeanFactoryPostProcessor,
|
63 | 65 |
|
64 | 66 | private final BeanOverrideRegistrar overrideRegistrar;
|
65 | 67 |
|
| 68 | + private final BeanNameGenerator beanNameGenerator = new DefaultBeanNameGenerator(); |
| 69 | + |
66 | 70 |
|
67 | 71 | /**
|
68 | 72 | * Create a new {@code BeanOverrideBeanFactoryPostProcessor} instance with
|
@@ -133,18 +137,11 @@ private void registerReplaceDefinition(ConfigurableListableBeanFactory beanFacto
|
133 | 137 | String beanNameIncludingFactory;
|
134 | 138 | BeanDefinition existingBeanDefinition = null;
|
135 | 139 | if (beanName == null) {
|
136 |
| - Set<String> candidateNames = getExistingBeanNamesByType(beanFactory, overrideMetadata, true); |
137 |
| - int candidateCount = candidateNames.size(); |
138 |
| - if (candidateCount != 1) { |
139 |
| - Field field = overrideMetadata.getField(); |
140 |
| - throw new IllegalStateException("Unable to select a bean definition to override: found " + |
141 |
| - candidateCount + " bean definitions of type " + overrideMetadata.getBeanType() + |
142 |
| - " (as required by annotated field '" + field.getDeclaringClass().getSimpleName() + |
143 |
| - "." + field.getName() + "')" + (candidateCount > 0 ? ": " + candidateNames : "")); |
144 |
| - } |
145 |
| - beanNameIncludingFactory = candidateNames.iterator().next(); |
| 140 | + beanNameIncludingFactory = getBeanNameForType(beanFactory, registry, overrideMetadata, beanDefinition, enforceExistingDefinition); |
146 | 141 | beanName = BeanFactoryUtils.transformedBeanName(beanNameIncludingFactory);
|
147 |
| - existingBeanDefinition = beanFactory.getBeanDefinition(beanName); |
| 142 | + if (registry.containsBeanDefinition(beanName)) { |
| 143 | + existingBeanDefinition = beanFactory.getBeanDefinition(beanName); |
| 144 | + } |
148 | 145 | }
|
149 | 146 | else {
|
150 | 147 | Set<String> candidates = getExistingBeanNamesByType(beanFactory, overrideMetadata, false);
|
@@ -176,6 +173,30 @@ else if (enforceExistingDefinition) {
|
176 | 173 | this.overrideRegistrar.registerNameForMetadata(overrideMetadata, beanNameIncludingFactory);
|
177 | 174 | }
|
178 | 175 |
|
| 176 | + private String getBeanNameForType(ConfigurableListableBeanFactory beanFactory, BeanDefinitionRegistry registry, |
| 177 | + OverrideMetadata overrideMetadata, RootBeanDefinition beanDefinition, boolean enforceExistingDefinition) { |
| 178 | + Set<String> candidateNames = getExistingBeanNamesByType(beanFactory, overrideMetadata, true); |
| 179 | + int candidateCount = candidateNames.size(); |
| 180 | + if (candidateCount == 1) { |
| 181 | + return candidateNames.iterator().next(); |
| 182 | + } |
| 183 | + else if (candidateCount == 0) { |
| 184 | + if (enforceExistingDefinition) { |
| 185 | + Field field = overrideMetadata.getField(); |
| 186 | + throw new IllegalStateException( |
| 187 | + "Unable to override bean: no bean definitions of type %s (as required by annotated field '%s.%s')" |
| 188 | + .formatted(overrideMetadata.getBeanType(), field.getDeclaringClass().getSimpleName(), field.getName())); |
| 189 | + } |
| 190 | + return this.beanNameGenerator.generateBeanName(beanDefinition, registry); |
| 191 | + } |
| 192 | + Field field = overrideMetadata.getField(); |
| 193 | + throw new IllegalStateException(String.format( |
| 194 | + "Unable to select a bean definition to override: found %s bean definitions of type %s " + |
| 195 | + "(as required by annotated field '%s.%s'): %s", |
| 196 | + candidateCount, overrideMetadata.getBeanType(), field.getDeclaringClass().getSimpleName(), |
| 197 | + field.getName(), candidateNames)); |
| 198 | + } |
| 199 | + |
179 | 200 | /**
|
180 | 201 | * Check that the expected bean name is registered and matches the type to override.
|
181 | 202 | * <p>If so, put the override metadata in the early tracking map.
|
@@ -209,7 +230,7 @@ private void registerWrapBean(ConfigurableListableBeanFactory beanFactory, Overr
|
209 | 230 | }
|
210 | 231 |
|
211 | 232 | RootBeanDefinition createBeanDefinition(OverrideMetadata metadata) {
|
212 |
| - RootBeanDefinition definition = new RootBeanDefinition(); |
| 233 | + RootBeanDefinition definition = new RootBeanDefinition(metadata.getBeanType().resolve()); |
213 | 234 | definition.setTargetType(metadata.getBeanType());
|
214 | 235 | definition.setQualifiedElement(metadata.getField());
|
215 | 236 | return definition;
|
|
0 commit comments