Skip to content

Commit 8dbd409

Browse files
committed
Reduce memory on RBD merge
** Probably not for Spring 4 M1 **
1 parent b197aed commit 8dbd409

File tree

2 files changed

+34
-9
lines changed

2 files changed

+34
-9
lines changed

spring-beans/src/main/java/org/springframework/beans/factory/support/AbstractBeanFactory.java

Lines changed: 33 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -169,7 +169,6 @@ public abstract class AbstractBeanFactory extends FactoryBeanRegistrySupport imp
169169
private final ThreadLocal<Object> prototypesCurrentlyInCreation =
170170
new NamedThreadLocal<Object>("Prototype beans currently in creation");
171171

172-
173172
/**
174173
* Create a new AbstractBeanFactory.
175174
*/
@@ -398,7 +397,7 @@ else if (containsSingleton(beanName)) {
398397
return parentBeanFactory.isSingleton(originalBeanName(name));
399398
}
400399

401-
RootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName);
400+
RootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName, true);
402401

403402
// In case of FactoryBean, return singleton status of created object if not a dereference.
404403
if (mbd.isSingleton()) {
@@ -428,7 +427,7 @@ public boolean isPrototype(String name) throws NoSuchBeanDefinitionException {
428427
return parentBeanFactory.isPrototype(originalBeanName(name));
429428
}
430429

431-
RootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName);
430+
RootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName, true);
432431
if (mbd.isPrototype()) {
433432
// In case of FactoryBean, return singleton status of created object if not a dereference.
434433
return (!BeanFactoryUtils.isFactoryDereference(name) || isFactoryBean(beanName, mbd));
@@ -495,7 +494,7 @@ else if (containsSingleton(beanName) && !containsBeanDefinition(beanName)) {
495494
}
496495

497496
// Retrieve corresponding bean definition.
498-
RootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName);
497+
RootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName, true);
499498

500499
Class[] typesToMatch = (FactoryBean.class.equals(typeToMatch) ?
501500
new Class[] {typeToMatch} : new Class[] {FactoryBean.class, typeToMatch});
@@ -560,13 +559,13 @@ else if (containsSingleton(beanName) && !containsBeanDefinition(beanName)) {
560559
return parentBeanFactory.getType(originalBeanName(name));
561560
}
562561

563-
RootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName);
562+
RootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName, true);
564563

565564
// Check decorated bean definition, if any: We assume it'll be easier
566565
// to determine the decorated bean's type than the proxy's type.
567566
BeanDefinitionHolder dbd = mbd.getDecoratedDefinition();
568567
if (dbd != null && !BeanFactoryUtils.isFactoryDereference(name)) {
569-
RootBeanDefinition tbd = getMergedBeanDefinition(dbd.getBeanName(), dbd.getBeanDefinition(), mbd);
568+
RootBeanDefinition tbd = getMergedBeanDefinition(dbd.getBeanName(), dbd.getBeanDefinition(), mbd, true);
570569
Class<?> targetClass = predictBeanType(dbd.getBeanName(), tbd);
571570
if (targetClass != null && !FactoryBean.class.isAssignableFrom(targetClass)) {
572571
return targetClass;
@@ -901,7 +900,7 @@ else if (containsSingleton(beanName)) {
901900
return ((ConfigurableBeanFactory) getParentBeanFactory()).isFactoryBean(name);
902901
}
903902

904-
return isFactoryBean(beanName, getMergedLocalBeanDefinition(beanName));
903+
return isFactoryBean(beanName, getMergedLocalBeanDefinition(beanName, true));
905904
}
906905

907906
@Override
@@ -1094,12 +1093,17 @@ protected void registerCustomEditors(PropertyEditorRegistry registry) {
10941093
* @throws BeanDefinitionStoreException in case of an invalid bean definition
10951094
*/
10961095
protected RootBeanDefinition getMergedLocalBeanDefinition(String beanName) throws BeansException {
1096+
return getMergedLocalBeanDefinition(beanName, false);
1097+
}
1098+
1099+
protected RootBeanDefinition getMergedLocalBeanDefinition(String beanName,
1100+
boolean forReadOnly) throws BeansException {
10971101
// Quick check on the concurrent map first, with minimal locking.
10981102
RootBeanDefinition mbd = this.mergedBeanDefinitions.get(beanName);
10991103
if (mbd != null) {
11001104
return mbd;
11011105
}
1102-
return getMergedBeanDefinition(beanName, getBeanDefinition(beanName));
1106+
return getMergedBeanDefinition(beanName, getBeanDefinition(beanName), null, forReadOnly);
11031107
}
11041108

11051109
/**
@@ -1129,6 +1133,27 @@ protected RootBeanDefinition getMergedBeanDefinition(String beanName, BeanDefini
11291133
protected RootBeanDefinition getMergedBeanDefinition(
11301134
String beanName, BeanDefinition bd, BeanDefinition containingBd)
11311135
throws BeanDefinitionStoreException {
1136+
return getMergedBeanDefinition(beanName, bd, containingBd, false);
1137+
}
1138+
1139+
/**
1140+
* Return a RootBeanDefinition for the given bean, by merging with the
1141+
* parent if the given bean's definition is a child bean definition.
1142+
* @param beanName the name of the bean definition
1143+
* @param bd the original bean definition (Root/ChildBeanDefinition)
1144+
* @param containingBd the containing bean definition in case of inner bean,
1145+
* or {@code null} in case of a top-level bean
1146+
* @return a (potentially merged) RootBeanDefinition for the given bean
1147+
* @throws BeanDefinitionStoreException in case of an invalid bean definition
1148+
*/
1149+
protected RootBeanDefinition getMergedBeanDefinition(
1150+
String beanName, BeanDefinition bd, BeanDefinition containingBd,
1151+
boolean forReadOnly)
1152+
throws BeanDefinitionStoreException {
1153+
1154+
if(forReadOnly && bd.getParentName() == null && bd instanceof RootBeanDefinition) {
1155+
return (RootBeanDefinition) bd;
1156+
}
11321157

11331158
synchronized (this.mergedBeanDefinitions) {
11341159
RootBeanDefinition mbd = null;

spring-beans/src/main/java/org/springframework/beans/factory/support/DefaultListableBeanFactory.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -347,7 +347,7 @@ private String[] doGetBeanNamesForType(Class<?> type, boolean includeNonSingleto
347347
// is not defined as alias for some other bean.
348348
if (!isAlias(beanName)) {
349349
try {
350-
RootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName);
350+
RootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName, true);
351351
// Only check bean definition if it is complete.
352352
if (!mbd.isAbstract() && (allowEagerInit ||
353353
((mbd.hasBeanClass() || !mbd.isLazyInit() || this.allowEagerClassLoading)) &&

0 commit comments

Comments
 (0)