001/*
002 * Copyright 2002-2020 the original author or authors.
003 *
004 * Licensed under the Apache License, Version 2.0 (the "License");
005 * you may not use this file except in compliance with the License.
006 * You may obtain a copy of the License at
007 *
008 *      https://www.apache.org/licenses/LICENSE-2.0
009 *
010 * Unless required by applicable law or agreed to in writing, software
011 * distributed under the License is distributed on an "AS IS" BASIS,
012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013 * See the License for the specific language governing permissions and
014 * limitations under the License.
015 */
016
017package org.springframework.beans.factory.support;
018
019import java.beans.PropertyDescriptor;
020import java.lang.reflect.Constructor;
021import java.lang.reflect.InvocationTargetException;
022import java.lang.reflect.Method;
023import java.lang.reflect.Modifier;
024import java.security.AccessController;
025import java.security.PrivilegedAction;
026import java.security.PrivilegedActionException;
027import java.security.PrivilegedExceptionAction;
028import java.util.ArrayList;
029import java.util.Arrays;
030import java.util.Collection;
031import java.util.HashSet;
032import java.util.LinkedHashSet;
033import java.util.List;
034import java.util.Set;
035import java.util.TreeSet;
036import java.util.concurrent.ConcurrentHashMap;
037import java.util.concurrent.ConcurrentMap;
038import java.util.function.Supplier;
039
040import org.apache.commons.logging.Log;
041
042import org.springframework.beans.BeanUtils;
043import org.springframework.beans.BeanWrapper;
044import org.springframework.beans.BeanWrapperImpl;
045import org.springframework.beans.BeansException;
046import org.springframework.beans.MutablePropertyValues;
047import org.springframework.beans.PropertyAccessorUtils;
048import org.springframework.beans.PropertyValue;
049import org.springframework.beans.PropertyValues;
050import org.springframework.beans.TypeConverter;
051import org.springframework.beans.factory.Aware;
052import org.springframework.beans.factory.BeanClassLoaderAware;
053import org.springframework.beans.factory.BeanCreationException;
054import org.springframework.beans.factory.BeanCurrentlyInCreationException;
055import org.springframework.beans.factory.BeanDefinitionStoreException;
056import org.springframework.beans.factory.BeanFactory;
057import org.springframework.beans.factory.BeanFactoryAware;
058import org.springframework.beans.factory.BeanNameAware;
059import org.springframework.beans.factory.FactoryBean;
060import org.springframework.beans.factory.InitializingBean;
061import org.springframework.beans.factory.InjectionPoint;
062import org.springframework.beans.factory.UnsatisfiedDependencyException;
063import org.springframework.beans.factory.config.AutowireCapableBeanFactory;
064import org.springframework.beans.factory.config.AutowiredPropertyMarker;
065import org.springframework.beans.factory.config.BeanDefinition;
066import org.springframework.beans.factory.config.BeanPostProcessor;
067import org.springframework.beans.factory.config.ConfigurableBeanFactory;
068import org.springframework.beans.factory.config.ConstructorArgumentValues;
069import org.springframework.beans.factory.config.DependencyDescriptor;
070import org.springframework.beans.factory.config.InstantiationAwareBeanPostProcessor;
071import org.springframework.beans.factory.config.SmartInstantiationAwareBeanPostProcessor;
072import org.springframework.beans.factory.config.TypedStringValue;
073import org.springframework.core.DefaultParameterNameDiscoverer;
074import org.springframework.core.MethodParameter;
075import org.springframework.core.NamedThreadLocal;
076import org.springframework.core.ParameterNameDiscoverer;
077import org.springframework.core.PriorityOrdered;
078import org.springframework.core.ResolvableType;
079import org.springframework.lang.Nullable;
080import org.springframework.util.Assert;
081import org.springframework.util.ClassUtils;
082import org.springframework.util.ObjectUtils;
083import org.springframework.util.ReflectionUtils;
084import org.springframework.util.ReflectionUtils.MethodCallback;
085import org.springframework.util.StringUtils;
086
087/**
088 * Abstract bean factory superclass that implements default bean creation,
089 * with the full capabilities specified by the {@link RootBeanDefinition} class.
090 * Implements the {@link org.springframework.beans.factory.config.AutowireCapableBeanFactory}
091 * interface in addition to AbstractBeanFactory's {@link #createBean} method.
092 *
093 * <p>Provides bean creation (with constructor resolution), property population,
094 * wiring (including autowiring), and initialization. Handles runtime bean
095 * references, resolves managed collections, calls initialization methods, etc.
096 * Supports autowiring constructors, properties by name, and properties by type.
097 *
098 * <p>The main template method to be implemented by subclasses is
099 * {@link #resolveDependency(DependencyDescriptor, String, Set, TypeConverter)},
100 * used for autowiring by type. In case of a factory which is capable of searching
101 * its bean definitions, matching beans will typically be implemented through such
102 * a search. For other factory styles, simplified matching algorithms can be implemented.
103 *
104 * <p>Note that this class does <i>not</i> assume or implement bean definition
105 * registry capabilities. See {@link DefaultListableBeanFactory} for an implementation
106 * of the {@link org.springframework.beans.factory.ListableBeanFactory} and
107 * {@link BeanDefinitionRegistry} interfaces, which represent the API and SPI
108 * view of such a factory, respectively.
109 *
110 * @author Rod Johnson
111 * @author Juergen Hoeller
112 * @author Rob Harrop
113 * @author Mark Fisher
114 * @author Costin Leau
115 * @author Chris Beams
116 * @author Sam Brannen
117 * @author Phillip Webb
118 * @since 13.02.2004
119 * @see RootBeanDefinition
120 * @see DefaultListableBeanFactory
121 * @see BeanDefinitionRegistry
122 */
123public abstract class AbstractAutowireCapableBeanFactory extends AbstractBeanFactory
124                implements AutowireCapableBeanFactory {
125
126        /** Strategy for creating bean instances. */
127        private InstantiationStrategy instantiationStrategy = new CglibSubclassingInstantiationStrategy();
128
129        /** Resolver strategy for method parameter names. */
130        @Nullable
131        private ParameterNameDiscoverer parameterNameDiscoverer = new DefaultParameterNameDiscoverer();
132
133        /** Whether to automatically try to resolve circular references between beans. */
134        private boolean allowCircularReferences = true;
135
136        /**
137         * Whether to resort to injecting a raw bean instance in case of circular reference,
138         * even if the injected bean eventually got wrapped.
139         */
140        private boolean allowRawInjectionDespiteWrapping = false;
141
142        /**
143         * Dependency types to ignore on dependency check and autowire, as Set of
144         * Class objects: for example, String. Default is none.
145         */
146        private final Set<Class<?>> ignoredDependencyTypes = new HashSet<>();
147
148        /**
149         * Dependency interfaces to ignore on dependency check and autowire, as Set of
150         * Class objects. By default, only the BeanFactory interface is ignored.
151         */
152        private final Set<Class<?>> ignoredDependencyInterfaces = new HashSet<>();
153
154        /**
155         * The name of the currently created bean, for implicit dependency registration
156         * on getBean etc invocations triggered from a user-specified Supplier callback.
157         */
158        private final NamedThreadLocal<String> currentlyCreatedBean = new NamedThreadLocal<>("Currently created bean");
159
160        /** Cache of unfinished FactoryBean instances: FactoryBean name to BeanWrapper. */
161        private final ConcurrentMap<String, BeanWrapper> factoryBeanInstanceCache = new ConcurrentHashMap<>();
162
163        /** Cache of candidate factory methods per factory class. */
164        private final ConcurrentMap<Class<?>, Method[]> factoryMethodCandidateCache = new ConcurrentHashMap<>();
165
166        /** Cache of filtered PropertyDescriptors: bean Class to PropertyDescriptor array. */
167        private final ConcurrentMap<Class<?>, PropertyDescriptor[]> filteredPropertyDescriptorsCache =
168                        new ConcurrentHashMap<>();
169
170
171        /**
172         * Create a new AbstractAutowireCapableBeanFactory.
173         */
174        public AbstractAutowireCapableBeanFactory() {
175                super();
176                ignoreDependencyInterface(BeanNameAware.class);
177                ignoreDependencyInterface(BeanFactoryAware.class);
178                ignoreDependencyInterface(BeanClassLoaderAware.class);
179        }
180
181        /**
182         * Create a new AbstractAutowireCapableBeanFactory with the given parent.
183         * @param parentBeanFactory parent bean factory, or {@code null} if none
184         */
185        public AbstractAutowireCapableBeanFactory(@Nullable BeanFactory parentBeanFactory) {
186                this();
187                setParentBeanFactory(parentBeanFactory);
188        }
189
190
191        /**
192         * Set the instantiation strategy to use for creating bean instances.
193         * Default is CglibSubclassingInstantiationStrategy.
194         * @see CglibSubclassingInstantiationStrategy
195         */
196        public void setInstantiationStrategy(InstantiationStrategy instantiationStrategy) {
197                this.instantiationStrategy = instantiationStrategy;
198        }
199
200        /**
201         * Return the instantiation strategy to use for creating bean instances.
202         */
203        protected InstantiationStrategy getInstantiationStrategy() {
204                return this.instantiationStrategy;
205        }
206
207        /**
208         * Set the ParameterNameDiscoverer to use for resolving method parameter
209         * names if needed (e.g. for constructor names).
210         * <p>Default is a {@link DefaultParameterNameDiscoverer}.
211         */
212        public void setParameterNameDiscoverer(@Nullable ParameterNameDiscoverer parameterNameDiscoverer) {
213                this.parameterNameDiscoverer = parameterNameDiscoverer;
214        }
215
216        /**
217         * Return the ParameterNameDiscoverer to use for resolving method parameter
218         * names if needed.
219         */
220        @Nullable
221        protected ParameterNameDiscoverer getParameterNameDiscoverer() {
222                return this.parameterNameDiscoverer;
223        }
224
225        /**
226         * Set whether to allow circular references between beans - and automatically
227         * try to resolve them.
228         * <p>Note that circular reference resolution means that one of the involved beans
229         * will receive a reference to another bean that is not fully initialized yet.
230         * This can lead to subtle and not-so-subtle side effects on initialization;
231         * it does work fine for many scenarios, though.
232         * <p>Default is "true". Turn this off to throw an exception when encountering
233         * a circular reference, disallowing them completely.
234         * <p><b>NOTE:</b> It is generally recommended to not rely on circular references
235         * between your beans. Refactor your application logic to have the two beans
236         * involved delegate to a third bean that encapsulates their common logic.
237         */
238        public void setAllowCircularReferences(boolean allowCircularReferences) {
239                this.allowCircularReferences = allowCircularReferences;
240        }
241
242        /**
243         * Set whether to allow the raw injection of a bean instance into some other
244         * bean's property, despite the injected bean eventually getting wrapped
245         * (for example, through AOP auto-proxying).
246         * <p>This will only be used as a last resort in case of a circular reference
247         * that cannot be resolved otherwise: essentially, preferring a raw instance
248         * getting injected over a failure of the entire bean wiring process.
249         * <p>Default is "false", as of Spring 2.0. Turn this on to allow for non-wrapped
250         * raw beans injected into some of your references, which was Spring 1.2's
251         * (arguably unclean) default behavior.
252         * <p><b>NOTE:</b> It is generally recommended to not rely on circular references
253         * between your beans, in particular with auto-proxying involved.
254         * @see #setAllowCircularReferences
255         */
256        public void setAllowRawInjectionDespiteWrapping(boolean allowRawInjectionDespiteWrapping) {
257                this.allowRawInjectionDespiteWrapping = allowRawInjectionDespiteWrapping;
258        }
259
260        /**
261         * Ignore the given dependency type for autowiring:
262         * for example, String. Default is none.
263         */
264        public void ignoreDependencyType(Class<?> type) {
265                this.ignoredDependencyTypes.add(type);
266        }
267
268        /**
269         * Ignore the given dependency interface for autowiring.
270         * <p>This will typically be used by application contexts to register
271         * dependencies that are resolved in other ways, like BeanFactory through
272         * BeanFactoryAware or ApplicationContext through ApplicationContextAware.
273         * <p>By default, only the BeanFactoryAware interface is ignored.
274         * For further types to ignore, invoke this method for each type.
275         * @see org.springframework.beans.factory.BeanFactoryAware
276         * @see org.springframework.context.ApplicationContextAware
277         */
278        public void ignoreDependencyInterface(Class<?> ifc) {
279                this.ignoredDependencyInterfaces.add(ifc);
280        }
281
282        @Override
283        public void copyConfigurationFrom(ConfigurableBeanFactory otherFactory) {
284                super.copyConfigurationFrom(otherFactory);
285                if (otherFactory instanceof AbstractAutowireCapableBeanFactory) {
286                        AbstractAutowireCapableBeanFactory otherAutowireFactory =
287                                        (AbstractAutowireCapableBeanFactory) otherFactory;
288                        this.instantiationStrategy = otherAutowireFactory.instantiationStrategy;
289                        this.allowCircularReferences = otherAutowireFactory.allowCircularReferences;
290                        this.ignoredDependencyTypes.addAll(otherAutowireFactory.ignoredDependencyTypes);
291                        this.ignoredDependencyInterfaces.addAll(otherAutowireFactory.ignoredDependencyInterfaces);
292                }
293        }
294
295
296        //-------------------------------------------------------------------------
297        // Typical methods for creating and populating external bean instances
298        //-------------------------------------------------------------------------
299
300        @Override
301        @SuppressWarnings("unchecked")
302        public <T> T createBean(Class<T> beanClass) throws BeansException {
303                // Use prototype bean definition, to avoid registering bean as dependent bean.
304                RootBeanDefinition bd = new RootBeanDefinition(beanClass);
305                bd.setScope(SCOPE_PROTOTYPE);
306                bd.allowCaching = ClassUtils.isCacheSafe(beanClass, getBeanClassLoader());
307                return (T) createBean(beanClass.getName(), bd, null);
308        }
309
310        @Override
311        public void autowireBean(Object existingBean) {
312                // Use non-singleton bean definition, to avoid registering bean as dependent bean.
313                RootBeanDefinition bd = new RootBeanDefinition(ClassUtils.getUserClass(existingBean));
314                bd.setScope(SCOPE_PROTOTYPE);
315                bd.allowCaching = ClassUtils.isCacheSafe(bd.getBeanClass(), getBeanClassLoader());
316                BeanWrapper bw = new BeanWrapperImpl(existingBean);
317                initBeanWrapper(bw);
318                populateBean(bd.getBeanClass().getName(), bd, bw);
319        }
320
321        @Override
322        public Object configureBean(Object existingBean, String beanName) throws BeansException {
323                markBeanAsCreated(beanName);
324                BeanDefinition mbd = getMergedBeanDefinition(beanName);
325                RootBeanDefinition bd = null;
326                if (mbd instanceof RootBeanDefinition) {
327                        RootBeanDefinition rbd = (RootBeanDefinition) mbd;
328                        bd = (rbd.isPrototype() ? rbd : rbd.cloneBeanDefinition());
329                }
330                if (bd == null) {
331                        bd = new RootBeanDefinition(mbd);
332                }
333                if (!bd.isPrototype()) {
334                        bd.setScope(SCOPE_PROTOTYPE);
335                        bd.allowCaching = ClassUtils.isCacheSafe(ClassUtils.getUserClass(existingBean), getBeanClassLoader());
336                }
337                BeanWrapper bw = new BeanWrapperImpl(existingBean);
338                initBeanWrapper(bw);
339                populateBean(beanName, bd, bw);
340                return initializeBean(beanName, existingBean, bd);
341        }
342
343
344        //-------------------------------------------------------------------------
345        // Specialized methods for fine-grained control over the bean lifecycle
346        //-------------------------------------------------------------------------
347
348        @Override
349        public Object createBean(Class<?> beanClass, int autowireMode, boolean dependencyCheck) throws BeansException {
350                // Use non-singleton bean definition, to avoid registering bean as dependent bean.
351                RootBeanDefinition bd = new RootBeanDefinition(beanClass, autowireMode, dependencyCheck);
352                bd.setScope(SCOPE_PROTOTYPE);
353                return createBean(beanClass.getName(), bd, null);
354        }
355
356        @Override
357        public Object autowire(Class<?> beanClass, int autowireMode, boolean dependencyCheck) throws BeansException {
358                // Use non-singleton bean definition, to avoid registering bean as dependent bean.
359                RootBeanDefinition bd = new RootBeanDefinition(beanClass, autowireMode, dependencyCheck);
360                bd.setScope(SCOPE_PROTOTYPE);
361                if (bd.getResolvedAutowireMode() == AUTOWIRE_CONSTRUCTOR) {
362                        return autowireConstructor(beanClass.getName(), bd, null, null).getWrappedInstance();
363                }
364                else {
365                        Object bean;
366                        if (System.getSecurityManager() != null) {
367                                bean = AccessController.doPrivileged(
368                                                (PrivilegedAction<Object>) () -> getInstantiationStrategy().instantiate(bd, null, this),
369                                                getAccessControlContext());
370                        }
371                        else {
372                                bean = getInstantiationStrategy().instantiate(bd, null, this);
373                        }
374                        populateBean(beanClass.getName(), bd, new BeanWrapperImpl(bean));
375                        return bean;
376                }
377        }
378
379        @Override
380        public void autowireBeanProperties(Object existingBean, int autowireMode, boolean dependencyCheck)
381                        throws BeansException {
382
383                if (autowireMode == AUTOWIRE_CONSTRUCTOR) {
384                        throw new IllegalArgumentException("AUTOWIRE_CONSTRUCTOR not supported for existing bean instance");
385                }
386                // Use non-singleton bean definition, to avoid registering bean as dependent bean.
387                RootBeanDefinition bd =
388                                new RootBeanDefinition(ClassUtils.getUserClass(existingBean), autowireMode, dependencyCheck);
389                bd.setScope(SCOPE_PROTOTYPE);
390                BeanWrapper bw = new BeanWrapperImpl(existingBean);
391                initBeanWrapper(bw);
392                populateBean(bd.getBeanClass().getName(), bd, bw);
393        }
394
395        @Override
396        public void applyBeanPropertyValues(Object existingBean, String beanName) throws BeansException {
397                markBeanAsCreated(beanName);
398                BeanDefinition bd = getMergedBeanDefinition(beanName);
399                BeanWrapper bw = new BeanWrapperImpl(existingBean);
400                initBeanWrapper(bw);
401                applyPropertyValues(beanName, bd, bw, bd.getPropertyValues());
402        }
403
404        @Override
405        public Object initializeBean(Object existingBean, String beanName) {
406                return initializeBean(beanName, existingBean, null);
407        }
408
409        @Override
410        public Object applyBeanPostProcessorsBeforeInitialization(Object existingBean, String beanName)
411                        throws BeansException {
412
413                Object result = existingBean;
414                for (BeanPostProcessor processor : getBeanPostProcessors()) {
415                        Object current = processor.postProcessBeforeInitialization(result, beanName);
416                        if (current == null) {
417                                return result;
418                        }
419                        result = current;
420                }
421                return result;
422        }
423
424        @Override
425        public Object applyBeanPostProcessorsAfterInitialization(Object existingBean, String beanName)
426                        throws BeansException {
427
428                Object result = existingBean;
429                for (BeanPostProcessor processor : getBeanPostProcessors()) {
430                        Object current = processor.postProcessAfterInitialization(result, beanName);
431                        if (current == null) {
432                                return result;
433                        }
434                        result = current;
435                }
436                return result;
437        }
438
439        @Override
440        public void destroyBean(Object existingBean) {
441                new DisposableBeanAdapter(existingBean, getBeanPostProcessors(), getAccessControlContext()).destroy();
442        }
443
444
445        //-------------------------------------------------------------------------
446        // Delegate methods for resolving injection points
447        //-------------------------------------------------------------------------
448
449        @Override
450        public Object resolveBeanByName(String name, DependencyDescriptor descriptor) {
451                InjectionPoint previousInjectionPoint = ConstructorResolver.setCurrentInjectionPoint(descriptor);
452                try {
453                        return getBean(name, descriptor.getDependencyType());
454                }
455                finally {
456                        ConstructorResolver.setCurrentInjectionPoint(previousInjectionPoint);
457                }
458        }
459
460        @Override
461        @Nullable
462        public Object resolveDependency(DependencyDescriptor descriptor, @Nullable String requestingBeanName) throws BeansException {
463                return resolveDependency(descriptor, requestingBeanName, null, null);
464        }
465
466
467        //---------------------------------------------------------------------
468        // Implementation of relevant AbstractBeanFactory template methods
469        //---------------------------------------------------------------------
470
471        /**
472         * Central method of this class: creates a bean instance,
473         * populates the bean instance, applies post-processors, etc.
474         * @see #doCreateBean
475         */
476        @Override
477        protected Object createBean(String beanName, RootBeanDefinition mbd, @Nullable Object[] args)
478                        throws BeanCreationException {
479
480                if (logger.isTraceEnabled()) {
481                        logger.trace("Creating instance of bean '" + beanName + "'");
482                }
483                RootBeanDefinition mbdToUse = mbd;
484
485                // Make sure bean class is actually resolved at this point, and
486                // clone the bean definition in case of a dynamically resolved Class
487                // which cannot be stored in the shared merged bean definition.
488                Class<?> resolvedClass = resolveBeanClass(mbd, beanName);
489                if (resolvedClass != null && !mbd.hasBeanClass() && mbd.getBeanClassName() != null) {
490                        mbdToUse = new RootBeanDefinition(mbd);
491                        mbdToUse.setBeanClass(resolvedClass);
492                }
493
494                // Prepare method overrides.
495                try {
496                        mbdToUse.prepareMethodOverrides();
497                }
498                catch (BeanDefinitionValidationException ex) {
499                        throw new BeanDefinitionStoreException(mbdToUse.getResourceDescription(),
500                                        beanName, "Validation of method overrides failed", ex);
501                }
502
503                try {
504                        // Give BeanPostProcessors a chance to return a proxy instead of the target bean instance.
505                        Object bean = resolveBeforeInstantiation(beanName, mbdToUse);
506                        if (bean != null) {
507                                return bean;
508                        }
509                }
510                catch (Throwable ex) {
511                        throw new BeanCreationException(mbdToUse.getResourceDescription(), beanName,
512                                        "BeanPostProcessor before instantiation of bean failed", ex);
513                }
514
515                try {
516                        Object beanInstance = doCreateBean(beanName, mbdToUse, args);
517                        if (logger.isTraceEnabled()) {
518                                logger.trace("Finished creating instance of bean '" + beanName + "'");
519                        }
520                        return beanInstance;
521                }
522                catch (BeanCreationException | ImplicitlyAppearedSingletonException ex) {
523                        // A previously detected exception with proper bean creation context already,
524                        // or illegal singleton state to be communicated up to DefaultSingletonBeanRegistry.
525                        throw ex;
526                }
527                catch (Throwable ex) {
528                        throw new BeanCreationException(
529                                        mbdToUse.getResourceDescription(), beanName, "Unexpected exception during bean creation", ex);
530                }
531        }
532
533        /**
534         * Actually create the specified bean. Pre-creation processing has already happened
535         * at this point, e.g. checking {@code postProcessBeforeInstantiation} callbacks.
536         * <p>Differentiates between default bean instantiation, use of a
537         * factory method, and autowiring a constructor.
538         * @param beanName the name of the bean
539         * @param mbd the merged bean definition for the bean
540         * @param args explicit arguments to use for constructor or factory method invocation
541         * @return a new instance of the bean
542         * @throws BeanCreationException if the bean could not be created
543         * @see #instantiateBean
544         * @see #instantiateUsingFactoryMethod
545         * @see #autowireConstructor
546         */
547        protected Object doCreateBean(String beanName, RootBeanDefinition mbd, @Nullable Object[] args)
548                        throws BeanCreationException {
549
550                // Instantiate the bean.
551                BeanWrapper instanceWrapper = null;
552                if (mbd.isSingleton()) {
553                        instanceWrapper = this.factoryBeanInstanceCache.remove(beanName);
554                }
555                if (instanceWrapper == null) {
556                        instanceWrapper = createBeanInstance(beanName, mbd, args);
557                }
558                Object bean = instanceWrapper.getWrappedInstance();
559                Class<?> beanType = instanceWrapper.getWrappedClass();
560                if (beanType != NullBean.class) {
561                        mbd.resolvedTargetType = beanType;
562                }
563
564                // Allow post-processors to modify the merged bean definition.
565                synchronized (mbd.postProcessingLock) {
566                        if (!mbd.postProcessed) {
567                                try {
568                                        applyMergedBeanDefinitionPostProcessors(mbd, beanType, beanName);
569                                }
570                                catch (Throwable ex) {
571                                        throw new BeanCreationException(mbd.getResourceDescription(), beanName,
572                                                        "Post-processing of merged bean definition failed", ex);
573                                }
574                                mbd.postProcessed = true;
575                        }
576                }
577
578                // Eagerly cache singletons to be able to resolve circular references
579                // even when triggered by lifecycle interfaces like BeanFactoryAware.
580                boolean earlySingletonExposure = (mbd.isSingleton() && this.allowCircularReferences &&
581                                isSingletonCurrentlyInCreation(beanName));
582                if (earlySingletonExposure) {
583                        if (logger.isTraceEnabled()) {
584                                logger.trace("Eagerly caching bean '" + beanName +
585                                                "' to allow for resolving potential circular references");
586                        }
587                        addSingletonFactory(beanName, () -> getEarlyBeanReference(beanName, mbd, bean));
588                }
589
590                // Initialize the bean instance.
591                Object exposedObject = bean;
592                try {
593                        populateBean(beanName, mbd, instanceWrapper);
594                        exposedObject = initializeBean(beanName, exposedObject, mbd);
595                }
596                catch (Throwable ex) {
597                        if (ex instanceof BeanCreationException && beanName.equals(((BeanCreationException) ex).getBeanName())) {
598                                throw (BeanCreationException) ex;
599                        }
600                        else {
601                                throw new BeanCreationException(
602                                                mbd.getResourceDescription(), beanName, "Initialization of bean failed", ex);
603                        }
604                }
605
606                if (earlySingletonExposure) {
607                        Object earlySingletonReference = getSingleton(beanName, false);
608                        if (earlySingletonReference != null) {
609                                if (exposedObject == bean) {
610                                        exposedObject = earlySingletonReference;
611                                }
612                                else if (!this.allowRawInjectionDespiteWrapping && hasDependentBean(beanName)) {
613                                        String[] dependentBeans = getDependentBeans(beanName);
614                                        Set<String> actualDependentBeans = new LinkedHashSet<>(dependentBeans.length);
615                                        for (String dependentBean : dependentBeans) {
616                                                if (!removeSingletonIfCreatedForTypeCheckOnly(dependentBean)) {
617                                                        actualDependentBeans.add(dependentBean);
618                                                }
619                                        }
620                                        if (!actualDependentBeans.isEmpty()) {
621                                                throw new BeanCurrentlyInCreationException(beanName,
622                                                                "Bean with name '" + beanName + "' has been injected into other beans [" +
623                                                                StringUtils.collectionToCommaDelimitedString(actualDependentBeans) +
624                                                                "] in its raw version as part of a circular reference, but has eventually been " +
625                                                                "wrapped. This means that said other beans do not use the final version of the " +
626                                                                "bean. This is often the result of over-eager type matching - consider using " +
627                                                                "'getBeanNamesForType' with the 'allowEagerInit' flag turned off, for example.");
628                                        }
629                                }
630                        }
631                }
632
633                // Register bean as disposable.
634                try {
635                        registerDisposableBeanIfNecessary(beanName, bean, mbd);
636                }
637                catch (BeanDefinitionValidationException ex) {
638                        throw new BeanCreationException(
639                                        mbd.getResourceDescription(), beanName, "Invalid destruction signature", ex);
640                }
641
642                return exposedObject;
643        }
644
645        @Override
646        @Nullable
647        protected Class<?> predictBeanType(String beanName, RootBeanDefinition mbd, Class<?>... typesToMatch) {
648                Class<?> targetType = determineTargetType(beanName, mbd, typesToMatch);
649                // Apply SmartInstantiationAwareBeanPostProcessors to predict the
650                // eventual type after a before-instantiation shortcut.
651                if (targetType != null && !mbd.isSynthetic() && hasInstantiationAwareBeanPostProcessors()) {
652                        boolean matchingOnlyFactoryBean = typesToMatch.length == 1 && typesToMatch[0] == FactoryBean.class;
653                        for (BeanPostProcessor bp : getBeanPostProcessors()) {
654                                if (bp instanceof SmartInstantiationAwareBeanPostProcessor) {
655                                        SmartInstantiationAwareBeanPostProcessor ibp = (SmartInstantiationAwareBeanPostProcessor) bp;
656                                        Class<?> predicted = ibp.predictBeanType(targetType, beanName);
657                                        if (predicted != null &&
658                                                        (!matchingOnlyFactoryBean || FactoryBean.class.isAssignableFrom(predicted))) {
659                                                return predicted;
660                                        }
661                                }
662                        }
663                }
664                return targetType;
665        }
666
667        /**
668         * Determine the target type for the given bean definition.
669         * @param beanName the name of the bean (for error handling purposes)
670         * @param mbd the merged bean definition for the bean
671         * @param typesToMatch the types to match in case of internal type matching purposes
672         * (also signals that the returned {@code Class} will never be exposed to application code)
673         * @return the type for the bean if determinable, or {@code null} otherwise
674         */
675        @Nullable
676        protected Class<?> determineTargetType(String beanName, RootBeanDefinition mbd, Class<?>... typesToMatch) {
677                Class<?> targetType = mbd.getTargetType();
678                if (targetType == null) {
679                        targetType = (mbd.getFactoryMethodName() != null ?
680                                        getTypeForFactoryMethod(beanName, mbd, typesToMatch) :
681                                        resolveBeanClass(mbd, beanName, typesToMatch));
682                        if (ObjectUtils.isEmpty(typesToMatch) || getTempClassLoader() == null) {
683                                mbd.resolvedTargetType = targetType;
684                        }
685                }
686                return targetType;
687        }
688
689        /**
690         * Determine the target type for the given bean definition which is based on
691         * a factory method. Only called if there is no singleton instance registered
692         * for the target bean already.
693         * <p>This implementation determines the type matching {@link #createBean}'s
694         * different creation strategies. As far as possible, we'll perform static
695         * type checking to avoid creation of the target bean.
696         * @param beanName the name of the bean (for error handling purposes)
697         * @param mbd the merged bean definition for the bean
698         * @param typesToMatch the types to match in case of internal type matching purposes
699         * (also signals that the returned {@code Class} will never be exposed to application code)
700         * @return the type for the bean if determinable, or {@code null} otherwise
701         * @see #createBean
702         */
703        @Nullable
704        protected Class<?> getTypeForFactoryMethod(String beanName, RootBeanDefinition mbd, Class<?>... typesToMatch) {
705                ResolvableType cachedReturnType = mbd.factoryMethodReturnType;
706                if (cachedReturnType != null) {
707                        return cachedReturnType.resolve();
708                }
709
710                Class<?> commonType = null;
711                Method uniqueCandidate = mbd.factoryMethodToIntrospect;
712
713                if (uniqueCandidate == null) {
714                        Class<?> factoryClass;
715                        boolean isStatic = true;
716
717                        String factoryBeanName = mbd.getFactoryBeanName();
718                        if (factoryBeanName != null) {
719                                if (factoryBeanName.equals(beanName)) {
720                                        throw new BeanDefinitionStoreException(mbd.getResourceDescription(), beanName,
721                                                        "factory-bean reference points back to the same bean definition");
722                                }
723                                // Check declared factory method return type on factory class.
724                                factoryClass = getType(factoryBeanName);
725                                isStatic = false;
726                        }
727                        else {
728                                // Check declared factory method return type on bean class.
729                                factoryClass = resolveBeanClass(mbd, beanName, typesToMatch);
730                        }
731
732                        if (factoryClass == null) {
733                                return null;
734                        }
735                        factoryClass = ClassUtils.getUserClass(factoryClass);
736
737                        // If all factory methods have the same return type, return that type.
738                        // Can't clearly figure out exact method due to type converting / autowiring!
739                        int minNrOfArgs =
740                                        (mbd.hasConstructorArgumentValues() ? mbd.getConstructorArgumentValues().getArgumentCount() : 0);
741                        Method[] candidates = this.factoryMethodCandidateCache.computeIfAbsent(factoryClass,
742                                        clazz -> ReflectionUtils.getUniqueDeclaredMethods(clazz, ReflectionUtils.USER_DECLARED_METHODS));
743
744                        for (Method candidate : candidates) {
745                                if (Modifier.isStatic(candidate.getModifiers()) == isStatic && mbd.isFactoryMethod(candidate) &&
746                                                candidate.getParameterCount() >= minNrOfArgs) {
747                                        // Declared type variables to inspect?
748                                        if (candidate.getTypeParameters().length > 0) {
749                                                try {
750                                                        // Fully resolve parameter names and argument values.
751                                                        Class<?>[] paramTypes = candidate.getParameterTypes();
752                                                        String[] paramNames = null;
753                                                        ParameterNameDiscoverer pnd = getParameterNameDiscoverer();
754                                                        if (pnd != null) {
755                                                                paramNames = pnd.getParameterNames(candidate);
756                                                        }
757                                                        ConstructorArgumentValues cav = mbd.getConstructorArgumentValues();
758                                                        Set<ConstructorArgumentValues.ValueHolder> usedValueHolders = new HashSet<>(paramTypes.length);
759                                                        Object[] args = new Object[paramTypes.length];
760                                                        for (int i = 0; i < args.length; i++) {
761                                                                ConstructorArgumentValues.ValueHolder valueHolder = cav.getArgumentValue(
762                                                                                i, paramTypes[i], (paramNames != null ? paramNames[i] : null), usedValueHolders);
763                                                                if (valueHolder == null) {
764                                                                        valueHolder = cav.getGenericArgumentValue(null, null, usedValueHolders);
765                                                                }
766                                                                if (valueHolder != null) {
767                                                                        args[i] = valueHolder.getValue();
768                                                                        usedValueHolders.add(valueHolder);
769                                                                }
770                                                        }
771                                                        Class<?> returnType = AutowireUtils.resolveReturnTypeForFactoryMethod(
772                                                                        candidate, args, getBeanClassLoader());
773                                                        uniqueCandidate = (commonType == null && returnType == candidate.getReturnType() ?
774                                                                        candidate : null);
775                                                        commonType = ClassUtils.determineCommonAncestor(returnType, commonType);
776                                                        if (commonType == null) {
777                                                                // Ambiguous return types found: return null to indicate "not determinable".
778                                                                return null;
779                                                        }
780                                                }
781                                                catch (Throwable ex) {
782                                                        if (logger.isDebugEnabled()) {
783                                                                logger.debug("Failed to resolve generic return type for factory method: " + ex);
784                                                        }
785                                                }
786                                        }
787                                        else {
788                                                uniqueCandidate = (commonType == null ? candidate : null);
789                                                commonType = ClassUtils.determineCommonAncestor(candidate.getReturnType(), commonType);
790                                                if (commonType == null) {
791                                                        // Ambiguous return types found: return null to indicate "not determinable".
792                                                        return null;
793                                                }
794                                        }
795                                }
796                        }
797
798                        mbd.factoryMethodToIntrospect = uniqueCandidate;
799                        if (commonType == null) {
800                                return null;
801                        }
802                }
803
804                // Common return type found: all factory methods return same type. For a non-parameterized
805                // unique candidate, cache the full type declaration context of the target factory method.
806                cachedReturnType = (uniqueCandidate != null ?
807                                ResolvableType.forMethodReturnType(uniqueCandidate) : ResolvableType.forClass(commonType));
808                mbd.factoryMethodReturnType = cachedReturnType;
809                return cachedReturnType.resolve();
810        }
811
812        /**
813         * This implementation attempts to query the FactoryBean's generic parameter metadata
814         * if present to determine the object type. If not present, i.e. the FactoryBean is
815         * declared as a raw type, checks the FactoryBean's {@code getObjectType} method
816         * on a plain instance of the FactoryBean, without bean properties applied yet.
817         * If this doesn't return a type yet, and {@code allowInit} is {@code true} a
818         * full creation of the FactoryBean is used as fallback (through delegation to the
819         * superclass's implementation).
820         * <p>The shortcut check for a FactoryBean is only applied in case of a singleton
821         * FactoryBean. If the FactoryBean instance itself is not kept as singleton,
822         * it will be fully created to check the type of its exposed object.
823         */
824        @Override
825        protected ResolvableType getTypeForFactoryBean(String beanName, RootBeanDefinition mbd, boolean allowInit) {
826                // Check if the bean definition itself has defined the type with an attribute
827                ResolvableType result = getTypeForFactoryBeanFromAttributes(mbd);
828                if (result != ResolvableType.NONE) {
829                        return result;
830                }
831
832                ResolvableType beanType =
833                                (mbd.hasBeanClass() ? ResolvableType.forClass(mbd.getBeanClass()) : ResolvableType.NONE);
834
835                // For instance supplied beans try the target type and bean class
836                if (mbd.getInstanceSupplier() != null) {
837                        result = getFactoryBeanGeneric(mbd.targetType);
838                        if (result.resolve() != null) {
839                                return result;
840                        }
841                        result = getFactoryBeanGeneric(beanType);
842                        if (result.resolve() != null) {
843                                return result;
844                        }
845                }
846
847                // Consider factory methods
848                String factoryBeanName = mbd.getFactoryBeanName();
849                String factoryMethodName = mbd.getFactoryMethodName();
850
851                // Scan the factory bean methods
852                if (factoryBeanName != null) {
853                        if (factoryMethodName != null) {
854                                // Try to obtain the FactoryBean's object type from its factory method
855                                // declaration without instantiating the containing bean at all.
856                                BeanDefinition factoryBeanDefinition = getBeanDefinition(factoryBeanName);
857                                Class<?> factoryBeanClass;
858                                if (factoryBeanDefinition instanceof AbstractBeanDefinition &&
859                                                ((AbstractBeanDefinition) factoryBeanDefinition).hasBeanClass()) {
860                                        factoryBeanClass = ((AbstractBeanDefinition) factoryBeanDefinition).getBeanClass();
861                                }
862                                else {
863                                        RootBeanDefinition fbmbd = getMergedBeanDefinition(factoryBeanName, factoryBeanDefinition);
864                                        factoryBeanClass = determineTargetType(factoryBeanName, fbmbd);
865                                }
866                                if (factoryBeanClass != null) {
867                                        result = getTypeForFactoryBeanFromMethod(factoryBeanClass, factoryMethodName);
868                                        if (result.resolve() != null) {
869                                                return result;
870                                        }
871                                }
872                        }
873                        // If not resolvable above and the referenced factory bean doesn't exist yet,
874                        // exit here - we don't want to force the creation of another bean just to
875                        // obtain a FactoryBean's object type...
876                        if (!isBeanEligibleForMetadataCaching(factoryBeanName)) {
877                                return ResolvableType.NONE;
878                        }
879                }
880
881                // If we're allowed, we can create the factory bean and call getObjectType() early
882                if (allowInit) {
883                        FactoryBean<?> factoryBean = (mbd.isSingleton() ?
884                                        getSingletonFactoryBeanForTypeCheck(beanName, mbd) :
885                                        getNonSingletonFactoryBeanForTypeCheck(beanName, mbd));
886                        if (factoryBean != null) {
887                                // Try to obtain the FactoryBean's object type from this early stage of the instance.
888                                Class<?> type = getTypeForFactoryBean(factoryBean);
889                                if (type != null) {
890                                        return ResolvableType.forClass(type);
891                                }
892                                // No type found for shortcut FactoryBean instance:
893                                // fall back to full creation of the FactoryBean instance.
894                                return super.getTypeForFactoryBean(beanName, mbd, true);
895                        }
896                }
897
898                if (factoryBeanName == null && mbd.hasBeanClass() && factoryMethodName != null) {
899                        // No early bean instantiation possible: determine FactoryBean's type from
900                        // static factory method signature or from class inheritance hierarchy...
901                        return getTypeForFactoryBeanFromMethod(mbd.getBeanClass(), factoryMethodName);
902                }
903                result = getFactoryBeanGeneric(beanType);
904                if (result.resolve() != null) {
905                        return result;
906                }
907                return ResolvableType.NONE;
908        }
909
910        private ResolvableType getFactoryBeanGeneric(@Nullable ResolvableType type) {
911                if (type == null) {
912                        return ResolvableType.NONE;
913                }
914                return type.as(FactoryBean.class).getGeneric();
915        }
916
917        /**
918         * Introspect the factory method signatures on the given bean class,
919         * trying to find a common {@code FactoryBean} object type declared there.
920         * @param beanClass the bean class to find the factory method on
921         * @param factoryMethodName the name of the factory method
922         * @return the common {@code FactoryBean} object type, or {@code null} if none
923         */
924        private ResolvableType getTypeForFactoryBeanFromMethod(Class<?> beanClass, String factoryMethodName) {
925                // CGLIB subclass methods hide generic parameters; look at the original user class.
926                Class<?> factoryBeanClass = ClassUtils.getUserClass(beanClass);
927                FactoryBeanMethodTypeFinder finder = new FactoryBeanMethodTypeFinder(factoryMethodName);
928                ReflectionUtils.doWithMethods(factoryBeanClass, finder, ReflectionUtils.USER_DECLARED_METHODS);
929                return finder.getResult();
930        }
931
932        /**
933         * This implementation attempts to query the FactoryBean's generic parameter metadata
934         * if present to determine the object type. If not present, i.e. the FactoryBean is
935         * declared as a raw type, checks the FactoryBean's {@code getObjectType} method
936         * on a plain instance of the FactoryBean, without bean properties applied yet.
937         * If this doesn't return a type yet, a full creation of the FactoryBean is
938         * used as fallback (through delegation to the superclass's implementation).
939         * <p>The shortcut check for a FactoryBean is only applied in case of a singleton
940         * FactoryBean. If the FactoryBean instance itself is not kept as singleton,
941         * it will be fully created to check the type of its exposed object.
942         */
943        @Override
944        @Deprecated
945        @Nullable
946        protected Class<?> getTypeForFactoryBean(String beanName, RootBeanDefinition mbd) {
947                return getTypeForFactoryBean(beanName, mbd, true).resolve();
948        }
949
950        /**
951         * Obtain a reference for early access to the specified bean,
952         * typically for the purpose of resolving a circular reference.
953         * @param beanName the name of the bean (for error handling purposes)
954         * @param mbd the merged bean definition for the bean
955         * @param bean the raw bean instance
956         * @return the object to expose as bean reference
957         */
958        protected Object getEarlyBeanReference(String beanName, RootBeanDefinition mbd, Object bean) {
959                Object exposedObject = bean;
960                if (!mbd.isSynthetic() && hasInstantiationAwareBeanPostProcessors()) {
961                        for (BeanPostProcessor bp : getBeanPostProcessors()) {
962                                if (bp instanceof SmartInstantiationAwareBeanPostProcessor) {
963                                        SmartInstantiationAwareBeanPostProcessor ibp = (SmartInstantiationAwareBeanPostProcessor) bp;
964                                        exposedObject = ibp.getEarlyBeanReference(exposedObject, beanName);
965                                }
966                        }
967                }
968                return exposedObject;
969        }
970
971
972        //---------------------------------------------------------------------
973        // Implementation methods
974        //---------------------------------------------------------------------
975
976        /**
977         * Obtain a "shortcut" singleton FactoryBean instance to use for a
978         * {@code getObjectType()} call, without full initialization of the FactoryBean.
979         * @param beanName the name of the bean
980         * @param mbd the bean definition for the bean
981         * @return the FactoryBean instance, or {@code null} to indicate
982         * that we couldn't obtain a shortcut FactoryBean instance
983         */
984        @Nullable
985        private FactoryBean<?> getSingletonFactoryBeanForTypeCheck(String beanName, RootBeanDefinition mbd) {
986                synchronized (getSingletonMutex()) {
987                        BeanWrapper bw = this.factoryBeanInstanceCache.get(beanName);
988                        if (bw != null) {
989                                return (FactoryBean<?>) bw.getWrappedInstance();
990                        }
991                        Object beanInstance = getSingleton(beanName, false);
992                        if (beanInstance instanceof FactoryBean) {
993                                return (FactoryBean<?>) beanInstance;
994                        }
995                        if (isSingletonCurrentlyInCreation(beanName) ||
996                                        (mbd.getFactoryBeanName() != null && isSingletonCurrentlyInCreation(mbd.getFactoryBeanName()))) {
997                                return null;
998                        }
999
1000                        Object instance;
1001                        try {
1002                                // Mark this bean as currently in creation, even if just partially.
1003                                beforeSingletonCreation(beanName);
1004                                // Give BeanPostProcessors a chance to return a proxy instead of the target bean instance.
1005                                instance = resolveBeforeInstantiation(beanName, mbd);
1006                                if (instance == null) {
1007                                        bw = createBeanInstance(beanName, mbd, null);
1008                                        instance = bw.getWrappedInstance();
1009                                }
1010                        }
1011                        catch (UnsatisfiedDependencyException ex) {
1012                                // Don't swallow, probably misconfiguration...
1013                                throw ex;
1014                        }
1015                        catch (BeanCreationException ex) {
1016                                // Instantiation failure, maybe too early...
1017                                if (logger.isDebugEnabled()) {
1018                                        logger.debug("Bean creation exception on singleton FactoryBean type check: " + ex);
1019                                }
1020                                onSuppressedException(ex);
1021                                return null;
1022                        }
1023                        finally {
1024                                // Finished partial creation of this bean.
1025                                afterSingletonCreation(beanName);
1026                        }
1027
1028                        FactoryBean<?> fb = getFactoryBean(beanName, instance);
1029                        if (bw != null) {
1030                                this.factoryBeanInstanceCache.put(beanName, bw);
1031                        }
1032                        return fb;
1033                }
1034        }
1035
1036        /**
1037         * Obtain a "shortcut" non-singleton FactoryBean instance to use for a
1038         * {@code getObjectType()} call, without full initialization of the FactoryBean.
1039         * @param beanName the name of the bean
1040         * @param mbd the bean definition for the bean
1041         * @return the FactoryBean instance, or {@code null} to indicate
1042         * that we couldn't obtain a shortcut FactoryBean instance
1043         */
1044        @Nullable
1045        private FactoryBean<?> getNonSingletonFactoryBeanForTypeCheck(String beanName, RootBeanDefinition mbd) {
1046                if (isPrototypeCurrentlyInCreation(beanName)) {
1047                        return null;
1048                }
1049
1050                Object instance;
1051                try {
1052                        // Mark this bean as currently in creation, even if just partially.
1053                        beforePrototypeCreation(beanName);
1054                        // Give BeanPostProcessors a chance to return a proxy instead of the target bean instance.
1055                        instance = resolveBeforeInstantiation(beanName, mbd);
1056                        if (instance == null) {
1057                                BeanWrapper bw = createBeanInstance(beanName, mbd, null);
1058                                instance = bw.getWrappedInstance();
1059                        }
1060                }
1061                catch (UnsatisfiedDependencyException ex) {
1062                        // Don't swallow, probably misconfiguration...
1063                        throw ex;
1064                }
1065                catch (BeanCreationException ex) {
1066                        // Instantiation failure, maybe too early...
1067                        if (logger.isDebugEnabled()) {
1068                                logger.debug("Bean creation exception on non-singleton FactoryBean type check: " + ex);
1069                        }
1070                        onSuppressedException(ex);
1071                        return null;
1072                }
1073                finally {
1074                        // Finished partial creation of this bean.
1075                        afterPrototypeCreation(beanName);
1076                }
1077
1078                return getFactoryBean(beanName, instance);
1079        }
1080
1081        /**
1082         * Apply MergedBeanDefinitionPostProcessors to the specified bean definition,
1083         * invoking their {@code postProcessMergedBeanDefinition} methods.
1084         * @param mbd the merged bean definition for the bean
1085         * @param beanType the actual type of the managed bean instance
1086         * @param beanName the name of the bean
1087         * @see MergedBeanDefinitionPostProcessor#postProcessMergedBeanDefinition
1088         */
1089        protected void applyMergedBeanDefinitionPostProcessors(RootBeanDefinition mbd, Class<?> beanType, String beanName) {
1090                for (BeanPostProcessor bp : getBeanPostProcessors()) {
1091                        if (bp instanceof MergedBeanDefinitionPostProcessor) {
1092                                MergedBeanDefinitionPostProcessor bdp = (MergedBeanDefinitionPostProcessor) bp;
1093                                bdp.postProcessMergedBeanDefinition(mbd, beanType, beanName);
1094                        }
1095                }
1096        }
1097
1098        /**
1099         * Apply before-instantiation post-processors, resolving whether there is a
1100         * before-instantiation shortcut for the specified bean.
1101         * @param beanName the name of the bean
1102         * @param mbd the bean definition for the bean
1103         * @return the shortcut-determined bean instance, or {@code null} if none
1104         */
1105        @Nullable
1106        protected Object resolveBeforeInstantiation(String beanName, RootBeanDefinition mbd) {
1107                Object bean = null;
1108                if (!Boolean.FALSE.equals(mbd.beforeInstantiationResolved)) {
1109                        // Make sure bean class is actually resolved at this point.
1110                        if (!mbd.isSynthetic() && hasInstantiationAwareBeanPostProcessors()) {
1111                                Class<?> targetType = determineTargetType(beanName, mbd);
1112                                if (targetType != null) {
1113                                        bean = applyBeanPostProcessorsBeforeInstantiation(targetType, beanName);
1114                                        if (bean != null) {
1115                                                bean = applyBeanPostProcessorsAfterInitialization(bean, beanName);
1116                                        }
1117                                }
1118                        }
1119                        mbd.beforeInstantiationResolved = (bean != null);
1120                }
1121                return bean;
1122        }
1123
1124        /**
1125         * Apply InstantiationAwareBeanPostProcessors to the specified bean definition
1126         * (by class and name), invoking their {@code postProcessBeforeInstantiation} methods.
1127         * <p>Any returned object will be used as the bean instead of actually instantiating
1128         * the target bean. A {@code null} return value from the post-processor will
1129         * result in the target bean being instantiated.
1130         * @param beanClass the class of the bean to be instantiated
1131         * @param beanName the name of the bean
1132         * @return the bean object to use instead of a default instance of the target bean, or {@code null}
1133         * @see InstantiationAwareBeanPostProcessor#postProcessBeforeInstantiation
1134         */
1135        @Nullable
1136        protected Object applyBeanPostProcessorsBeforeInstantiation(Class<?> beanClass, String beanName) {
1137                for (BeanPostProcessor bp : getBeanPostProcessors()) {
1138                        if (bp instanceof InstantiationAwareBeanPostProcessor) {
1139                                InstantiationAwareBeanPostProcessor ibp = (InstantiationAwareBeanPostProcessor) bp;
1140                                Object result = ibp.postProcessBeforeInstantiation(beanClass, beanName);
1141                                if (result != null) {
1142                                        return result;
1143                                }
1144                        }
1145                }
1146                return null;
1147        }
1148
1149        /**
1150         * Create a new instance for the specified bean, using an appropriate instantiation strategy:
1151         * factory method, constructor autowiring, or simple instantiation.
1152         * @param beanName the name of the bean
1153         * @param mbd the bean definition for the bean
1154         * @param args explicit arguments to use for constructor or factory method invocation
1155         * @return a BeanWrapper for the new instance
1156         * @see #obtainFromSupplier
1157         * @see #instantiateUsingFactoryMethod
1158         * @see #autowireConstructor
1159         * @see #instantiateBean
1160         */
1161        protected BeanWrapper createBeanInstance(String beanName, RootBeanDefinition mbd, @Nullable Object[] args) {
1162                // Make sure bean class is actually resolved at this point.
1163                Class<?> beanClass = resolveBeanClass(mbd, beanName);
1164
1165                if (beanClass != null && !Modifier.isPublic(beanClass.getModifiers()) && !mbd.isNonPublicAccessAllowed()) {
1166                        throw new BeanCreationException(mbd.getResourceDescription(), beanName,
1167                                        "Bean class isn't public, and non-public access not allowed: " + beanClass.getName());
1168                }
1169
1170                Supplier<?> instanceSupplier = mbd.getInstanceSupplier();
1171                if (instanceSupplier != null) {
1172                        return obtainFromSupplier(instanceSupplier, beanName);
1173                }
1174
1175                if (mbd.getFactoryMethodName() != null) {
1176                        return instantiateUsingFactoryMethod(beanName, mbd, args);
1177                }
1178
1179                // Shortcut when re-creating the same bean...
1180                boolean resolved = false;
1181                boolean autowireNecessary = false;
1182                if (args == null) {
1183                        synchronized (mbd.constructorArgumentLock) {
1184                                if (mbd.resolvedConstructorOrFactoryMethod != null) {
1185                                        resolved = true;
1186                                        autowireNecessary = mbd.constructorArgumentsResolved;
1187                                }
1188                        }
1189                }
1190                if (resolved) {
1191                        if (autowireNecessary) {
1192                                return autowireConstructor(beanName, mbd, null, null);
1193                        }
1194                        else {
1195                                return instantiateBean(beanName, mbd);
1196                        }
1197                }
1198
1199                // Candidate constructors for autowiring?
1200                Constructor<?>[] ctors = determineConstructorsFromBeanPostProcessors(beanClass, beanName);
1201                if (ctors != null || mbd.getResolvedAutowireMode() == AUTOWIRE_CONSTRUCTOR ||
1202                                mbd.hasConstructorArgumentValues() || !ObjectUtils.isEmpty(args)) {
1203                        return autowireConstructor(beanName, mbd, ctors, args);
1204                }
1205
1206                // Preferred constructors for default construction?
1207                ctors = mbd.getPreferredConstructors();
1208                if (ctors != null) {
1209                        return autowireConstructor(beanName, mbd, ctors, null);
1210                }
1211
1212                // No special handling: simply use no-arg constructor.
1213                return instantiateBean(beanName, mbd);
1214        }
1215
1216        /**
1217         * Obtain a bean instance from the given supplier.
1218         * @param instanceSupplier the configured supplier
1219         * @param beanName the corresponding bean name
1220         * @return a BeanWrapper for the new instance
1221         * @since 5.0
1222         * @see #getObjectForBeanInstance
1223         */
1224        protected BeanWrapper obtainFromSupplier(Supplier<?> instanceSupplier, String beanName) {
1225                Object instance;
1226
1227                String outerBean = this.currentlyCreatedBean.get();
1228                this.currentlyCreatedBean.set(beanName);
1229                try {
1230                        instance = instanceSupplier.get();
1231                }
1232                finally {
1233                        if (outerBean != null) {
1234                                this.currentlyCreatedBean.set(outerBean);
1235                        }
1236                        else {
1237                                this.currentlyCreatedBean.remove();
1238                        }
1239                }
1240
1241                if (instance == null) {
1242                        instance = new NullBean();
1243                }
1244                BeanWrapper bw = new BeanWrapperImpl(instance);
1245                initBeanWrapper(bw);
1246                return bw;
1247        }
1248
1249        /**
1250         * Overridden in order to implicitly register the currently created bean as
1251         * dependent on further beans getting programmatically retrieved during a
1252         * {@link Supplier} callback.
1253         * @since 5.0
1254         * @see #obtainFromSupplier
1255         */
1256        @Override
1257        protected Object getObjectForBeanInstance(
1258                        Object beanInstance, String name, String beanName, @Nullable RootBeanDefinition mbd) {
1259
1260                String currentlyCreatedBean = this.currentlyCreatedBean.get();
1261                if (currentlyCreatedBean != null) {
1262                        registerDependentBean(beanName, currentlyCreatedBean);
1263                }
1264
1265                return super.getObjectForBeanInstance(beanInstance, name, beanName, mbd);
1266        }
1267
1268        /**
1269         * Determine candidate constructors to use for the given bean, checking all registered
1270         * {@link SmartInstantiationAwareBeanPostProcessor SmartInstantiationAwareBeanPostProcessors}.
1271         * @param beanClass the raw class of the bean
1272         * @param beanName the name of the bean
1273         * @return the candidate constructors, or {@code null} if none specified
1274         * @throws org.springframework.beans.BeansException in case of errors
1275         * @see org.springframework.beans.factory.config.SmartInstantiationAwareBeanPostProcessor#determineCandidateConstructors
1276         */
1277        @Nullable
1278        protected Constructor<?>[] determineConstructorsFromBeanPostProcessors(@Nullable Class<?> beanClass, String beanName)
1279                        throws BeansException {
1280
1281                if (beanClass != null && hasInstantiationAwareBeanPostProcessors()) {
1282                        for (BeanPostProcessor bp : getBeanPostProcessors()) {
1283                                if (bp instanceof SmartInstantiationAwareBeanPostProcessor) {
1284                                        SmartInstantiationAwareBeanPostProcessor ibp = (SmartInstantiationAwareBeanPostProcessor) bp;
1285                                        Constructor<?>[] ctors = ibp.determineCandidateConstructors(beanClass, beanName);
1286                                        if (ctors != null) {
1287                                                return ctors;
1288                                        }
1289                                }
1290                        }
1291                }
1292                return null;
1293        }
1294
1295        /**
1296         * Instantiate the given bean using its default constructor.
1297         * @param beanName the name of the bean
1298         * @param mbd the bean definition for the bean
1299         * @return a BeanWrapper for the new instance
1300         */
1301        protected BeanWrapper instantiateBean(String beanName, RootBeanDefinition mbd) {
1302                try {
1303                        Object beanInstance;
1304                        if (System.getSecurityManager() != null) {
1305                                beanInstance = AccessController.doPrivileged(
1306                                                (PrivilegedAction<Object>) () -> getInstantiationStrategy().instantiate(mbd, beanName, this),
1307                                                getAccessControlContext());
1308                        }
1309                        else {
1310                                beanInstance = getInstantiationStrategy().instantiate(mbd, beanName, this);
1311                        }
1312                        BeanWrapper bw = new BeanWrapperImpl(beanInstance);
1313                        initBeanWrapper(bw);
1314                        return bw;
1315                }
1316                catch (Throwable ex) {
1317                        throw new BeanCreationException(
1318                                        mbd.getResourceDescription(), beanName, "Instantiation of bean failed", ex);
1319                }
1320        }
1321
1322        /**
1323         * Instantiate the bean using a named factory method. The method may be static, if the
1324         * mbd parameter specifies a class, rather than a factoryBean, or an instance variable
1325         * on a factory object itself configured using Dependency Injection.
1326         * @param beanName the name of the bean
1327         * @param mbd the bean definition for the bean
1328         * @param explicitArgs argument values passed in programmatically via the getBean method,
1329         * or {@code null} if none (-> use constructor argument values from bean definition)
1330         * @return a BeanWrapper for the new instance
1331         * @see #getBean(String, Object[])
1332         */
1333        protected BeanWrapper instantiateUsingFactoryMethod(
1334                        String beanName, RootBeanDefinition mbd, @Nullable Object[] explicitArgs) {
1335
1336                return new ConstructorResolver(this).instantiateUsingFactoryMethod(beanName, mbd, explicitArgs);
1337        }
1338
1339        /**
1340         * "autowire constructor" (with constructor arguments by type) behavior.
1341         * Also applied if explicit constructor argument values are specified,
1342         * matching all remaining arguments with beans from the bean factory.
1343         * <p>This corresponds to constructor injection: In this mode, a Spring
1344         * bean factory is able to host components that expect constructor-based
1345         * dependency resolution.
1346         * @param beanName the name of the bean
1347         * @param mbd the bean definition for the bean
1348         * @param ctors the chosen candidate constructors
1349         * @param explicitArgs argument values passed in programmatically via the getBean method,
1350         * or {@code null} if none (-> use constructor argument values from bean definition)
1351         * @return a BeanWrapper for the new instance
1352         */
1353        protected BeanWrapper autowireConstructor(
1354                        String beanName, RootBeanDefinition mbd, @Nullable Constructor<?>[] ctors, @Nullable Object[] explicitArgs) {
1355
1356                return new ConstructorResolver(this).autowireConstructor(beanName, mbd, ctors, explicitArgs);
1357        }
1358
1359        /**
1360         * Populate the bean instance in the given BeanWrapper with the property values
1361         * from the bean definition.
1362         * @param beanName the name of the bean
1363         * @param mbd the bean definition for the bean
1364         * @param bw the BeanWrapper with bean instance
1365         */
1366        @SuppressWarnings("deprecation")  // for postProcessPropertyValues
1367        protected void populateBean(String beanName, RootBeanDefinition mbd, @Nullable BeanWrapper bw) {
1368                if (bw == null) {
1369                        if (mbd.hasPropertyValues()) {
1370                                throw new BeanCreationException(
1371                                                mbd.getResourceDescription(), beanName, "Cannot apply property values to null instance");
1372                        }
1373                        else {
1374                                // Skip property population phase for null instance.
1375                                return;
1376                        }
1377                }
1378
1379                // Give any InstantiationAwareBeanPostProcessors the opportunity to modify the
1380                // state of the bean before properties are set. This can be used, for example,
1381                // to support styles of field injection.
1382                if (!mbd.isSynthetic() && hasInstantiationAwareBeanPostProcessors()) {
1383                        for (BeanPostProcessor bp : getBeanPostProcessors()) {
1384                                if (bp instanceof InstantiationAwareBeanPostProcessor) {
1385                                        InstantiationAwareBeanPostProcessor ibp = (InstantiationAwareBeanPostProcessor) bp;
1386                                        if (!ibp.postProcessAfterInstantiation(bw.getWrappedInstance(), beanName)) {
1387                                                return;
1388                                        }
1389                                }
1390                        }
1391                }
1392
1393                PropertyValues pvs = (mbd.hasPropertyValues() ? mbd.getPropertyValues() : null);
1394
1395                int resolvedAutowireMode = mbd.getResolvedAutowireMode();
1396                if (resolvedAutowireMode == AUTOWIRE_BY_NAME || resolvedAutowireMode == AUTOWIRE_BY_TYPE) {
1397                        MutablePropertyValues newPvs = new MutablePropertyValues(pvs);
1398                        // Add property values based on autowire by name if applicable.
1399                        if (resolvedAutowireMode == AUTOWIRE_BY_NAME) {
1400                                autowireByName(beanName, mbd, bw, newPvs);
1401                        }
1402                        // Add property values based on autowire by type if applicable.
1403                        if (resolvedAutowireMode == AUTOWIRE_BY_TYPE) {
1404                                autowireByType(beanName, mbd, bw, newPvs);
1405                        }
1406                        pvs = newPvs;
1407                }
1408
1409                boolean hasInstAwareBpps = hasInstantiationAwareBeanPostProcessors();
1410                boolean needsDepCheck = (mbd.getDependencyCheck() != AbstractBeanDefinition.DEPENDENCY_CHECK_NONE);
1411
1412                PropertyDescriptor[] filteredPds = null;
1413                if (hasInstAwareBpps) {
1414                        if (pvs == null) {
1415                                pvs = mbd.getPropertyValues();
1416                        }
1417                        for (BeanPostProcessor bp : getBeanPostProcessors()) {
1418                                if (bp instanceof InstantiationAwareBeanPostProcessor) {
1419                                        InstantiationAwareBeanPostProcessor ibp = (InstantiationAwareBeanPostProcessor) bp;
1420                                        PropertyValues pvsToUse = ibp.postProcessProperties(pvs, bw.getWrappedInstance(), beanName);
1421                                        if (pvsToUse == null) {
1422                                                if (filteredPds == null) {
1423                                                        filteredPds = filterPropertyDescriptorsForDependencyCheck(bw, mbd.allowCaching);
1424                                                }
1425                                                pvsToUse = ibp.postProcessPropertyValues(pvs, filteredPds, bw.getWrappedInstance(), beanName);
1426                                                if (pvsToUse == null) {
1427                                                        return;
1428                                                }
1429                                        }
1430                                        pvs = pvsToUse;
1431                                }
1432                        }
1433                }
1434                if (needsDepCheck) {
1435                        if (filteredPds == null) {
1436                                filteredPds = filterPropertyDescriptorsForDependencyCheck(bw, mbd.allowCaching);
1437                        }
1438                        checkDependencies(beanName, mbd, filteredPds, pvs);
1439                }
1440
1441                if (pvs != null) {
1442                        applyPropertyValues(beanName, mbd, bw, pvs);
1443                }
1444        }
1445
1446        /**
1447         * Fill in any missing property values with references to
1448         * other beans in this factory if autowire is set to "byName".
1449         * @param beanName the name of the bean we're wiring up.
1450         * Useful for debugging messages; not used functionally.
1451         * @param mbd bean definition to update through autowiring
1452         * @param bw the BeanWrapper from which we can obtain information about the bean
1453         * @param pvs the PropertyValues to register wired objects with
1454         */
1455        protected void autowireByName(
1456                        String beanName, AbstractBeanDefinition mbd, BeanWrapper bw, MutablePropertyValues pvs) {
1457
1458                String[] propertyNames = unsatisfiedNonSimpleProperties(mbd, bw);
1459                for (String propertyName : propertyNames) {
1460                        if (containsBean(propertyName)) {
1461                                Object bean = getBean(propertyName);
1462                                pvs.add(propertyName, bean);
1463                                registerDependentBean(propertyName, beanName);
1464                                if (logger.isTraceEnabled()) {
1465                                        logger.trace("Added autowiring by name from bean name '" + beanName +
1466                                                        "' via property '" + propertyName + "' to bean named '" + propertyName + "'");
1467                                }
1468                        }
1469                        else {
1470                                if (logger.isTraceEnabled()) {
1471                                        logger.trace("Not autowiring property '" + propertyName + "' of bean '" + beanName +
1472                                                        "' by name: no matching bean found");
1473                                }
1474                        }
1475                }
1476        }
1477
1478        /**
1479         * Abstract method defining "autowire by type" (bean properties by type) behavior.
1480         * <p>This is like PicoContainer default, in which there must be exactly one bean
1481         * of the property type in the bean factory. This makes bean factories simple to
1482         * configure for small namespaces, but doesn't work as well as standard Spring
1483         * behavior for bigger applications.
1484         * @param beanName the name of the bean to autowire by type
1485         * @param mbd the merged bean definition to update through autowiring
1486         * @param bw the BeanWrapper from which we can obtain information about the bean
1487         * @param pvs the PropertyValues to register wired objects with
1488         */
1489        protected void autowireByType(
1490                        String beanName, AbstractBeanDefinition mbd, BeanWrapper bw, MutablePropertyValues pvs) {
1491
1492                TypeConverter converter = getCustomTypeConverter();
1493                if (converter == null) {
1494                        converter = bw;
1495                }
1496
1497                Set<String> autowiredBeanNames = new LinkedHashSet<>(4);
1498                String[] propertyNames = unsatisfiedNonSimpleProperties(mbd, bw);
1499                for (String propertyName : propertyNames) {
1500                        try {
1501                                PropertyDescriptor pd = bw.getPropertyDescriptor(propertyName);
1502                                // Don't try autowiring by type for type Object: never makes sense,
1503                                // even if it technically is a unsatisfied, non-simple property.
1504                                if (Object.class != pd.getPropertyType()) {
1505                                        MethodParameter methodParam = BeanUtils.getWriteMethodParameter(pd);
1506                                        // Do not allow eager init for type matching in case of a prioritized post-processor.
1507                                        boolean eager = !(bw.getWrappedInstance() instanceof PriorityOrdered);
1508                                        DependencyDescriptor desc = new AutowireByTypeDependencyDescriptor(methodParam, eager);
1509                                        Object autowiredArgument = resolveDependency(desc, beanName, autowiredBeanNames, converter);
1510                                        if (autowiredArgument != null) {
1511                                                pvs.add(propertyName, autowiredArgument);
1512                                        }
1513                                        for (String autowiredBeanName : autowiredBeanNames) {
1514                                                registerDependentBean(autowiredBeanName, beanName);
1515                                                if (logger.isTraceEnabled()) {
1516                                                        logger.trace("Autowiring by type from bean name '" + beanName + "' via property '" +
1517                                                                        propertyName + "' to bean named '" + autowiredBeanName + "'");
1518                                                }
1519                                        }
1520                                        autowiredBeanNames.clear();
1521                                }
1522                        }
1523                        catch (BeansException ex) {
1524                                throw new UnsatisfiedDependencyException(mbd.getResourceDescription(), beanName, propertyName, ex);
1525                        }
1526                }
1527        }
1528
1529
1530        /**
1531         * Return an array of non-simple bean properties that are unsatisfied.
1532         * These are probably unsatisfied references to other beans in the
1533         * factory. Does not include simple properties like primitives or Strings.
1534         * @param mbd the merged bean definition the bean was created with
1535         * @param bw the BeanWrapper the bean was created with
1536         * @return an array of bean property names
1537         * @see org.springframework.beans.BeanUtils#isSimpleProperty
1538         */
1539        protected String[] unsatisfiedNonSimpleProperties(AbstractBeanDefinition mbd, BeanWrapper bw) {
1540                Set<String> result = new TreeSet<>();
1541                PropertyValues pvs = mbd.getPropertyValues();
1542                PropertyDescriptor[] pds = bw.getPropertyDescriptors();
1543                for (PropertyDescriptor pd : pds) {
1544                        if (pd.getWriteMethod() != null && !isExcludedFromDependencyCheck(pd) && !pvs.contains(pd.getName()) &&
1545                                        !BeanUtils.isSimpleProperty(pd.getPropertyType())) {
1546                                result.add(pd.getName());
1547                        }
1548                }
1549                return StringUtils.toStringArray(result);
1550        }
1551
1552        /**
1553         * Extract a filtered set of PropertyDescriptors from the given BeanWrapper,
1554         * excluding ignored dependency types or properties defined on ignored dependency interfaces.
1555         * @param bw the BeanWrapper the bean was created with
1556         * @param cache whether to cache filtered PropertyDescriptors for the given bean Class
1557         * @return the filtered PropertyDescriptors
1558         * @see #isExcludedFromDependencyCheck
1559         * @see #filterPropertyDescriptorsForDependencyCheck(org.springframework.beans.BeanWrapper)
1560         */
1561        protected PropertyDescriptor[] filterPropertyDescriptorsForDependencyCheck(BeanWrapper bw, boolean cache) {
1562                PropertyDescriptor[] filtered = this.filteredPropertyDescriptorsCache.get(bw.getWrappedClass());
1563                if (filtered == null) {
1564                        filtered = filterPropertyDescriptorsForDependencyCheck(bw);
1565                        if (cache) {
1566                                PropertyDescriptor[] existing =
1567                                                this.filteredPropertyDescriptorsCache.putIfAbsent(bw.getWrappedClass(), filtered);
1568                                if (existing != null) {
1569                                        filtered = existing;
1570                                }
1571                        }
1572                }
1573                return filtered;
1574        }
1575
1576        /**
1577         * Extract a filtered set of PropertyDescriptors from the given BeanWrapper,
1578         * excluding ignored dependency types or properties defined on ignored dependency interfaces.
1579         * @param bw the BeanWrapper the bean was created with
1580         * @return the filtered PropertyDescriptors
1581         * @see #isExcludedFromDependencyCheck
1582         */
1583        protected PropertyDescriptor[] filterPropertyDescriptorsForDependencyCheck(BeanWrapper bw) {
1584                List<PropertyDescriptor> pds = new ArrayList<>(Arrays.asList(bw.getPropertyDescriptors()));
1585                pds.removeIf(this::isExcludedFromDependencyCheck);
1586                return pds.toArray(new PropertyDescriptor[0]);
1587        }
1588
1589        /**
1590         * Determine whether the given bean property is excluded from dependency checks.
1591         * <p>This implementation excludes properties defined by CGLIB and
1592         * properties whose type matches an ignored dependency type or which
1593         * are defined by an ignored dependency interface.
1594         * @param pd the PropertyDescriptor of the bean property
1595         * @return whether the bean property is excluded
1596         * @see #ignoreDependencyType(Class)
1597         * @see #ignoreDependencyInterface(Class)
1598         */
1599        protected boolean isExcludedFromDependencyCheck(PropertyDescriptor pd) {
1600                return (AutowireUtils.isExcludedFromDependencyCheck(pd) ||
1601                                this.ignoredDependencyTypes.contains(pd.getPropertyType()) ||
1602                                AutowireUtils.isSetterDefinedInInterface(pd, this.ignoredDependencyInterfaces));
1603        }
1604
1605        /**
1606         * Perform a dependency check that all properties exposed have been set,
1607         * if desired. Dependency checks can be objects (collaborating beans),
1608         * simple (primitives and String), or all (both).
1609         * @param beanName the name of the bean
1610         * @param mbd the merged bean definition the bean was created with
1611         * @param pds the relevant property descriptors for the target bean
1612         * @param pvs the property values to be applied to the bean
1613         * @see #isExcludedFromDependencyCheck(java.beans.PropertyDescriptor)
1614         */
1615        protected void checkDependencies(
1616                        String beanName, AbstractBeanDefinition mbd, PropertyDescriptor[] pds, @Nullable PropertyValues pvs)
1617                        throws UnsatisfiedDependencyException {
1618
1619                int dependencyCheck = mbd.getDependencyCheck();
1620                for (PropertyDescriptor pd : pds) {
1621                        if (pd.getWriteMethod() != null && (pvs == null || !pvs.contains(pd.getName()))) {
1622                                boolean isSimple = BeanUtils.isSimpleProperty(pd.getPropertyType());
1623                                boolean unsatisfied = (dependencyCheck == AbstractBeanDefinition.DEPENDENCY_CHECK_ALL) ||
1624                                                (isSimple && dependencyCheck == AbstractBeanDefinition.DEPENDENCY_CHECK_SIMPLE) ||
1625                                                (!isSimple && dependencyCheck == AbstractBeanDefinition.DEPENDENCY_CHECK_OBJECTS);
1626                                if (unsatisfied) {
1627                                        throw new UnsatisfiedDependencyException(mbd.getResourceDescription(), beanName, pd.getName(),
1628                                                        "Set this property value or disable dependency checking for this bean.");
1629                                }
1630                        }
1631                }
1632        }
1633
1634        /**
1635         * Apply the given property values, resolving any runtime references
1636         * to other beans in this bean factory. Must use deep copy, so we
1637         * don't permanently modify this property.
1638         * @param beanName the bean name passed for better exception information
1639         * @param mbd the merged bean definition
1640         * @param bw the BeanWrapper wrapping the target object
1641         * @param pvs the new property values
1642         */
1643        protected void applyPropertyValues(String beanName, BeanDefinition mbd, BeanWrapper bw, PropertyValues pvs) {
1644                if (pvs.isEmpty()) {
1645                        return;
1646                }
1647
1648                if (System.getSecurityManager() != null && bw instanceof BeanWrapperImpl) {
1649                        ((BeanWrapperImpl) bw).setSecurityContext(getAccessControlContext());
1650                }
1651
1652                MutablePropertyValues mpvs = null;
1653                List<PropertyValue> original;
1654
1655                if (pvs instanceof MutablePropertyValues) {
1656                        mpvs = (MutablePropertyValues) pvs;
1657                        if (mpvs.isConverted()) {
1658                                // Shortcut: use the pre-converted values as-is.
1659                                try {
1660                                        bw.setPropertyValues(mpvs);
1661                                        return;
1662                                }
1663                                catch (BeansException ex) {
1664                                        throw new BeanCreationException(
1665                                                        mbd.getResourceDescription(), beanName, "Error setting property values", ex);
1666                                }
1667                        }
1668                        original = mpvs.getPropertyValueList();
1669                }
1670                else {
1671                        original = Arrays.asList(pvs.getPropertyValues());
1672                }
1673
1674                TypeConverter converter = getCustomTypeConverter();
1675                if (converter == null) {
1676                        converter = bw;
1677                }
1678                BeanDefinitionValueResolver valueResolver = new BeanDefinitionValueResolver(this, beanName, mbd, converter);
1679
1680                // Create a deep copy, resolving any references for values.
1681                List<PropertyValue> deepCopy = new ArrayList<>(original.size());
1682                boolean resolveNecessary = false;
1683                for (PropertyValue pv : original) {
1684                        if (pv.isConverted()) {
1685                                deepCopy.add(pv);
1686                        }
1687                        else {
1688                                String propertyName = pv.getName();
1689                                Object originalValue = pv.getValue();
1690                                if (originalValue == AutowiredPropertyMarker.INSTANCE) {
1691                                        Method writeMethod = bw.getPropertyDescriptor(propertyName).getWriteMethod();
1692                                        if (writeMethod == null) {
1693                                                throw new IllegalArgumentException("Autowire marker for property without write method: " + pv);
1694                                        }
1695                                        originalValue = new DependencyDescriptor(new MethodParameter(writeMethod, 0), true);
1696                                }
1697                                Object resolvedValue = valueResolver.resolveValueIfNecessary(pv, originalValue);
1698                                Object convertedValue = resolvedValue;
1699                                boolean convertible = bw.isWritableProperty(propertyName) &&
1700                                                !PropertyAccessorUtils.isNestedOrIndexedProperty(propertyName);
1701                                if (convertible) {
1702                                        convertedValue = convertForProperty(resolvedValue, propertyName, bw, converter);
1703                                }
1704                                // Possibly store converted value in merged bean definition,
1705                                // in order to avoid re-conversion for every created bean instance.
1706                                if (resolvedValue == originalValue) {
1707                                        if (convertible) {
1708                                                pv.setConvertedValue(convertedValue);
1709                                        }
1710                                        deepCopy.add(pv);
1711                                }
1712                                else if (convertible && originalValue instanceof TypedStringValue &&
1713                                                !((TypedStringValue) originalValue).isDynamic() &&
1714                                                !(convertedValue instanceof Collection || ObjectUtils.isArray(convertedValue))) {
1715                                        pv.setConvertedValue(convertedValue);
1716                                        deepCopy.add(pv);
1717                                }
1718                                else {
1719                                        resolveNecessary = true;
1720                                        deepCopy.add(new PropertyValue(pv, convertedValue));
1721                                }
1722                        }
1723                }
1724                if (mpvs != null && !resolveNecessary) {
1725                        mpvs.setConverted();
1726                }
1727
1728                // Set our (possibly massaged) deep copy.
1729                try {
1730                        bw.setPropertyValues(new MutablePropertyValues(deepCopy));
1731                }
1732                catch (BeansException ex) {
1733                        throw new BeanCreationException(
1734                                        mbd.getResourceDescription(), beanName, "Error setting property values", ex);
1735                }
1736        }
1737
1738        /**
1739         * Convert the given value for the specified target property.
1740         */
1741        @Nullable
1742        private Object convertForProperty(
1743                        @Nullable Object value, String propertyName, BeanWrapper bw, TypeConverter converter) {
1744
1745                if (converter instanceof BeanWrapperImpl) {
1746                        return ((BeanWrapperImpl) converter).convertForProperty(value, propertyName);
1747                }
1748                else {
1749                        PropertyDescriptor pd = bw.getPropertyDescriptor(propertyName);
1750                        MethodParameter methodParam = BeanUtils.getWriteMethodParameter(pd);
1751                        return converter.convertIfNecessary(value, pd.getPropertyType(), methodParam);
1752                }
1753        }
1754
1755
1756        /**
1757         * Initialize the given bean instance, applying factory callbacks
1758         * as well as init methods and bean post processors.
1759         * <p>Called from {@link #createBean} for traditionally defined beans,
1760         * and from {@link #initializeBean} for existing bean instances.
1761         * @param beanName the bean name in the factory (for debugging purposes)
1762         * @param bean the new bean instance we may need to initialize
1763         * @param mbd the bean definition that the bean was created with
1764         * (can also be {@code null}, if given an existing bean instance)
1765         * @return the initialized bean instance (potentially wrapped)
1766         * @see BeanNameAware
1767         * @see BeanClassLoaderAware
1768         * @see BeanFactoryAware
1769         * @see #applyBeanPostProcessorsBeforeInitialization
1770         * @see #invokeInitMethods
1771         * @see #applyBeanPostProcessorsAfterInitialization
1772         */
1773        protected Object initializeBean(String beanName, Object bean, @Nullable RootBeanDefinition mbd) {
1774                if (System.getSecurityManager() != null) {
1775                        AccessController.doPrivileged((PrivilegedAction<Object>) () -> {
1776                                invokeAwareMethods(beanName, bean);
1777                                return null;
1778                        }, getAccessControlContext());
1779                }
1780                else {
1781                        invokeAwareMethods(beanName, bean);
1782                }
1783
1784                Object wrappedBean = bean;
1785                if (mbd == null || !mbd.isSynthetic()) {
1786                        wrappedBean = applyBeanPostProcessorsBeforeInitialization(wrappedBean, beanName);
1787                }
1788
1789                try {
1790                        invokeInitMethods(beanName, wrappedBean, mbd);
1791                }
1792                catch (Throwable ex) {
1793                        throw new BeanCreationException(
1794                                        (mbd != null ? mbd.getResourceDescription() : null),
1795                                        beanName, "Invocation of init method failed", ex);
1796                }
1797                if (mbd == null || !mbd.isSynthetic()) {
1798                        wrappedBean = applyBeanPostProcessorsAfterInitialization(wrappedBean, beanName);
1799                }
1800
1801                return wrappedBean;
1802        }
1803
1804        private void invokeAwareMethods(String beanName, Object bean) {
1805                if (bean instanceof Aware) {
1806                        if (bean instanceof BeanNameAware) {
1807                                ((BeanNameAware) bean).setBeanName(beanName);
1808                        }
1809                        if (bean instanceof BeanClassLoaderAware) {
1810                                ClassLoader bcl = getBeanClassLoader();
1811                                if (bcl != null) {
1812                                        ((BeanClassLoaderAware) bean).setBeanClassLoader(bcl);
1813                                }
1814                        }
1815                        if (bean instanceof BeanFactoryAware) {
1816                                ((BeanFactoryAware) bean).setBeanFactory(AbstractAutowireCapableBeanFactory.this);
1817                        }
1818                }
1819        }
1820
1821        /**
1822         * Give a bean a chance to react now all its properties are set,
1823         * and a chance to know about its owning bean factory (this object).
1824         * This means checking whether the bean implements InitializingBean or defines
1825         * a custom init method, and invoking the necessary callback(s) if it does.
1826         * @param beanName the bean name in the factory (for debugging purposes)
1827         * @param bean the new bean instance we may need to initialize
1828         * @param mbd the merged bean definition that the bean was created with
1829         * (can also be {@code null}, if given an existing bean instance)
1830         * @throws Throwable if thrown by init methods or by the invocation process
1831         * @see #invokeCustomInitMethod
1832         */
1833        protected void invokeInitMethods(String beanName, Object bean, @Nullable RootBeanDefinition mbd)
1834                        throws Throwable {
1835
1836                boolean isInitializingBean = (bean instanceof InitializingBean);
1837                if (isInitializingBean && (mbd == null || !mbd.isExternallyManagedInitMethod("afterPropertiesSet"))) {
1838                        if (logger.isTraceEnabled()) {
1839                                logger.trace("Invoking afterPropertiesSet() on bean with name '" + beanName + "'");
1840                        }
1841                        if (System.getSecurityManager() != null) {
1842                                try {
1843                                        AccessController.doPrivileged((PrivilegedExceptionAction<Object>) () -> {
1844                                                ((InitializingBean) bean).afterPropertiesSet();
1845                                                return null;
1846                                        }, getAccessControlContext());
1847                                }
1848                                catch (PrivilegedActionException pae) {
1849                                        throw pae.getException();
1850                                }
1851                        }
1852                        else {
1853                                ((InitializingBean) bean).afterPropertiesSet();
1854                        }
1855                }
1856
1857                if (mbd != null && bean.getClass() != NullBean.class) {
1858                        String initMethodName = mbd.getInitMethodName();
1859                        if (StringUtils.hasLength(initMethodName) &&
1860                                        !(isInitializingBean && "afterPropertiesSet".equals(initMethodName)) &&
1861                                        !mbd.isExternallyManagedInitMethod(initMethodName)) {
1862                                invokeCustomInitMethod(beanName, bean, mbd);
1863                        }
1864                }
1865        }
1866
1867        /**
1868         * Invoke the specified custom init method on the given bean.
1869         * Called by invokeInitMethods.
1870         * <p>Can be overridden in subclasses for custom resolution of init
1871         * methods with arguments.
1872         * @see #invokeInitMethods
1873         */
1874        protected void invokeCustomInitMethod(String beanName, Object bean, RootBeanDefinition mbd)
1875                        throws Throwable {
1876
1877                String initMethodName = mbd.getInitMethodName();
1878                Assert.state(initMethodName != null, "No init method set");
1879                Method initMethod = (mbd.isNonPublicAccessAllowed() ?
1880                                BeanUtils.findMethod(bean.getClass(), initMethodName) :
1881                                ClassUtils.getMethodIfAvailable(bean.getClass(), initMethodName));
1882
1883                if (initMethod == null) {
1884                        if (mbd.isEnforceInitMethod()) {
1885                                throw new BeanDefinitionValidationException("Could not find an init method named '" +
1886                                                initMethodName + "' on bean with name '" + beanName + "'");
1887                        }
1888                        else {
1889                                if (logger.isTraceEnabled()) {
1890                                        logger.trace("No default init method named '" + initMethodName +
1891                                                        "' found on bean with name '" + beanName + "'");
1892                                }
1893                                // Ignore non-existent default lifecycle methods.
1894                                return;
1895                        }
1896                }
1897
1898                if (logger.isTraceEnabled()) {
1899                        logger.trace("Invoking init method  '" + initMethodName + "' on bean with name '" + beanName + "'");
1900                }
1901                Method methodToInvoke = ClassUtils.getInterfaceMethodIfPossible(initMethod);
1902
1903                if (System.getSecurityManager() != null) {
1904                        AccessController.doPrivileged((PrivilegedAction<Object>) () -> {
1905                                ReflectionUtils.makeAccessible(methodToInvoke);
1906                                return null;
1907                        });
1908                        try {
1909                                AccessController.doPrivileged((PrivilegedExceptionAction<Object>)
1910                                                () -> methodToInvoke.invoke(bean), getAccessControlContext());
1911                        }
1912                        catch (PrivilegedActionException pae) {
1913                                InvocationTargetException ex = (InvocationTargetException) pae.getException();
1914                                throw ex.getTargetException();
1915                        }
1916                }
1917                else {
1918                        try {
1919                                ReflectionUtils.makeAccessible(methodToInvoke);
1920                                methodToInvoke.invoke(bean);
1921                        }
1922                        catch (InvocationTargetException ex) {
1923                                throw ex.getTargetException();
1924                        }
1925                }
1926        }
1927
1928
1929        /**
1930         * Applies the {@code postProcessAfterInitialization} callback of all
1931         * registered BeanPostProcessors, giving them a chance to post-process the
1932         * object obtained from FactoryBeans (for example, to auto-proxy them).
1933         * @see #applyBeanPostProcessorsAfterInitialization
1934         */
1935        @Override
1936        protected Object postProcessObjectFromFactoryBean(Object object, String beanName) {
1937                return applyBeanPostProcessorsAfterInitialization(object, beanName);
1938        }
1939
1940        /**
1941         * Overridden to clear FactoryBean instance cache as well.
1942         */
1943        @Override
1944        protected void removeSingleton(String beanName) {
1945                synchronized (getSingletonMutex()) {
1946                        super.removeSingleton(beanName);
1947                        this.factoryBeanInstanceCache.remove(beanName);
1948                }
1949        }
1950
1951        /**
1952         * Overridden to clear FactoryBean instance cache as well.
1953         */
1954        @Override
1955        protected void clearSingletonCache() {
1956                synchronized (getSingletonMutex()) {
1957                        super.clearSingletonCache();
1958                        this.factoryBeanInstanceCache.clear();
1959                }
1960        }
1961
1962        /**
1963         * Expose the logger to collaborating delegates.
1964         * @since 5.0.7
1965         */
1966        Log getLogger() {
1967                return logger;
1968        }
1969
1970
1971        /**
1972         * Special DependencyDescriptor variant for Spring's good old autowire="byType" mode.
1973         * Always optional; never considering the parameter name for choosing a primary candidate.
1974         */
1975        @SuppressWarnings("serial")
1976        private static class AutowireByTypeDependencyDescriptor extends DependencyDescriptor {
1977
1978                public AutowireByTypeDependencyDescriptor(MethodParameter methodParameter, boolean eager) {
1979                        super(methodParameter, false, eager);
1980                }
1981
1982                @Override
1983                public String getDependencyName() {
1984                        return null;
1985                }
1986        }
1987
1988
1989        /**
1990         * {@link MethodCallback} used to find {@link FactoryBean} type information.
1991         */
1992        private static class FactoryBeanMethodTypeFinder implements MethodCallback {
1993
1994                private final String factoryMethodName;
1995
1996                private ResolvableType result = ResolvableType.NONE;
1997
1998                FactoryBeanMethodTypeFinder(String factoryMethodName) {
1999                        this.factoryMethodName = factoryMethodName;
2000                }
2001
2002                @Override
2003                public void doWith(Method method) throws IllegalArgumentException, IllegalAccessException {
2004                        if (isFactoryBeanMethod(method)) {
2005                                ResolvableType returnType = ResolvableType.forMethodReturnType(method);
2006                                ResolvableType candidate = returnType.as(FactoryBean.class).getGeneric();
2007                                if (this.result == ResolvableType.NONE) {
2008                                        this.result = candidate;
2009                                }
2010                                else {
2011                                        Class<?> resolvedResult = this.result.resolve();
2012                                        Class<?> commonAncestor = ClassUtils.determineCommonAncestor(candidate.resolve(), resolvedResult);
2013                                        if (!ObjectUtils.nullSafeEquals(resolvedResult, commonAncestor)) {
2014                                                this.result = ResolvableType.forClass(commonAncestor);
2015                                        }
2016                                }
2017                        }
2018                }
2019
2020                private boolean isFactoryBeanMethod(Method method) {
2021                        return (method.getName().equals(this.factoryMethodName) &&
2022                                        FactoryBean.class.isAssignableFrom(method.getReturnType()));
2023                }
2024
2025                ResolvableType getResult() {
2026                        Class<?> resolved = this.result.resolve();
2027                        boolean foundResult = resolved != null && resolved != Object.class;
2028                        return (foundResult ? this.result : ResolvableType.NONE);
2029                }
2030        }
2031
2032}