Spring finally fixed a long known problem with the autowire (by type) performance, or generally spoken, with the performance of bean lookup by type. The background is, that determination of the actual type of a Spring bean is not done with a simple instanceof, because most beans might be proxies. A Spring bean could even have multiple proxies. So, to determine the type it is necessary to iterate through all PostProcessors and ask them for the original type:

protected Class predictBeanType(String beanName, RootBeanDefinition mbd, Class... typesToMatch) {
	Class beanClass;
	if (mbd.getFactoryMethodName() != null) {
		beanClass = getTypeForFactoryMethod(beanName, mbd, typesToMatch);
	}
	else {
		beanClass = resolveBeanClass(mbd, beanName, typesToMatch);
	}
	// Apply SmartInstantiationAwareBeanPostProcessors to predict the
	// eventual type after a before-instantiation shortcut.
	if (beanClass != null && !mbd.isSynthetic() && hasInstantiationAwareBeanPostProcessors()) {
		for (BeanPostProcessor bp : getBeanPostProcessors()) {
			if (bp instanceof SmartInstantiationAwareBeanPostProcessor) {
				SmartInstantiationAwareBeanPostProcessor ibp = (SmartInstantiationAwareBeanPostProcessor) bp;
				Class processedType = ibp.predictBeanType(beanClass, beanName);
				if (processedType != null) {
					return processedType;
				}
			}
		}
	}
	return beanClass;
}

This process can take astonishing long. And if you use autowiring in huge web-applications, with a lot of scoped beans, this can easily take a big part of the request time. Which has already been reported two years ago: SPR-6870

It was fixed now by simply caching all calls to DefaultListableBeanFactory.getBeansOfType(). See: SPR-9448

I recommend to update to Spring 3.1.2 if you’re using autowiring in scoped beans (especially request beans)!

Leave a Reply

Your email address will not be published. Required fields are marked *


*