avoid caching for expression results even when specified as TypedStringValue (SPR-6115)
This commit is contained in:
@@ -44,6 +44,8 @@ public class TypedStringValue implements BeanMetadataElement {
|
||||
|
||||
private String specifiedTypeName;
|
||||
|
||||
private volatile boolean dynamic;
|
||||
|
||||
|
||||
/**
|
||||
* Create a new {@link TypedStringValue} for the given String value.
|
||||
@@ -185,6 +187,21 @@ public class TypedStringValue implements BeanMetadataElement {
|
||||
return this.specifiedTypeName;
|
||||
}
|
||||
|
||||
/**
|
||||
* Mark this value as dynamic, i.e. as containing an expression
|
||||
* and hence not being subject to caching.
|
||||
*/
|
||||
public void setDynamic() {
|
||||
this.dynamic = true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return whether this value has been marked as dynamic.
|
||||
*/
|
||||
public boolean isDynamic() {
|
||||
return this.dynamic;
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public boolean equals(Object other) {
|
||||
|
||||
@@ -1311,7 +1311,8 @@ public abstract class AbstractAutowireCapableBeanFactory extends AbstractBeanFac
|
||||
}
|
||||
deepCopy.add(pv);
|
||||
}
|
||||
else if (originalValue instanceof TypedStringValue && convertible &&
|
||||
else if (convertible && originalValue instanceof TypedStringValue &&
|
||||
!((TypedStringValue) originalValue).isDynamic() &&
|
||||
!(convertedValue instanceof Collection || ObjectUtils.isArray(convertedValue))) {
|
||||
pv.setConvertedValue(convertedValue);
|
||||
deepCopy.add(pv);
|
||||
|
||||
@@ -167,10 +167,10 @@ class BeanDefinitionValueResolver {
|
||||
Object propKey = propEntry.getKey();
|
||||
Object propValue = propEntry.getValue();
|
||||
if (propKey instanceof TypedStringValue) {
|
||||
propKey = evaluate(((TypedStringValue) propKey).getValue());
|
||||
propKey = evaluate((TypedStringValue) propKey);
|
||||
}
|
||||
if (propValue instanceof TypedStringValue) {
|
||||
propValue = evaluate(((TypedStringValue) propValue).getValue());
|
||||
propValue = evaluate((TypedStringValue) propValue);
|
||||
}
|
||||
copy.put(propKey, propValue);
|
||||
}
|
||||
@@ -179,7 +179,7 @@ class BeanDefinitionValueResolver {
|
||||
else if (value instanceof TypedStringValue) {
|
||||
// Convert value to target type here.
|
||||
TypedStringValue typedStringValue = (TypedStringValue) value;
|
||||
Object valueObject = evaluate(typedStringValue.getValue());
|
||||
Object valueObject = evaluate(typedStringValue);
|
||||
try {
|
||||
Class<?> resolvedTargetType = resolveTargetType(typedStringValue);
|
||||
if (resolvedTargetType != null) {
|
||||
@@ -201,6 +201,19 @@ class BeanDefinitionValueResolver {
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate the given value as an expression, if necessary.
|
||||
* @param value the candidate value (may be an expression)
|
||||
* @return the resolved value
|
||||
*/
|
||||
protected Object evaluate(TypedStringValue value) {
|
||||
Object result = this.beanFactory.evaluateBeanDefinitionString(value.getValue(), this.beanDefinition);
|
||||
if (result != value.getValue()) {
|
||||
value.setDynamic();
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
/**
|
||||
* Evaluate the given value as an expression, if necessary.
|
||||
* @param value the candidate value (may be an expression)
|
||||
|
||||
Reference in New Issue
Block a user