Name attributes in method argument annotations allow for placeholders and expressions
Issue: SPR-13952
This commit is contained in:
@@ -89,10 +89,16 @@ public abstract class AbstractNamedValueMethodArgumentResolver implements Handle
|
||||
NamedValueInfo namedValueInfo = getNamedValueInfo(parameter);
|
||||
MethodParameter nestedParameter = parameter.nestedIfOptional();
|
||||
|
||||
Object arg = resolveName(namedValueInfo.name, nestedParameter, webRequest);
|
||||
Object resolvedName = resolveStringValue(namedValueInfo.name);
|
||||
if (resolvedName == null) {
|
||||
throw new IllegalArgumentException(
|
||||
"Specified name must not resolve to null: [" + namedValueInfo.name + "]");
|
||||
}
|
||||
|
||||
Object arg = resolveName(resolvedName.toString(), nestedParameter, webRequest);
|
||||
if (arg == null) {
|
||||
if (namedValueInfo.defaultValue != null) {
|
||||
arg = resolveDefaultValue(namedValueInfo.defaultValue);
|
||||
arg = resolveStringValue(namedValueInfo.defaultValue);
|
||||
}
|
||||
else if (namedValueInfo.required && !nestedParameter.isOptional()) {
|
||||
handleMissingValue(namedValueInfo.name, nestedParameter, webRequest);
|
||||
@@ -100,7 +106,7 @@ public abstract class AbstractNamedValueMethodArgumentResolver implements Handle
|
||||
arg = handleNullValue(namedValueInfo.name, arg, nestedParameter.getNestedParameterType());
|
||||
}
|
||||
else if ("".equals(arg) && namedValueInfo.defaultValue != null) {
|
||||
arg = resolveDefaultValue(namedValueInfo.defaultValue);
|
||||
arg = resolveStringValue(namedValueInfo.defaultValue);
|
||||
}
|
||||
|
||||
if (binderFactory != null) {
|
||||
@@ -162,6 +168,22 @@ public abstract class AbstractNamedValueMethodArgumentResolver implements Handle
|
||||
return new NamedValueInfo(name, info.required, defaultValue);
|
||||
}
|
||||
|
||||
/**
|
||||
* Resolve the given annotation-specified value,
|
||||
* potentially containing placeholders and expressions.
|
||||
*/
|
||||
private Object resolveStringValue(String value) {
|
||||
if (this.configurableBeanFactory == null) {
|
||||
return value;
|
||||
}
|
||||
String placeholdersResolved = this.configurableBeanFactory.resolveEmbeddedValue(value);
|
||||
BeanExpressionResolver exprResolver = this.configurableBeanFactory.getBeanExpressionResolver();
|
||||
if (exprResolver == null) {
|
||||
return value;
|
||||
}
|
||||
return exprResolver.evaluate(placeholdersResolved, this.expressionContext);
|
||||
}
|
||||
|
||||
/**
|
||||
* Resolve the given parameter type and value name into an argument value.
|
||||
* @param name the name of the value being resolved
|
||||
@@ -174,21 +196,6 @@ public abstract class AbstractNamedValueMethodArgumentResolver implements Handle
|
||||
protected abstract Object resolveName(String name, MethodParameter parameter, NativeWebRequest request)
|
||||
throws Exception;
|
||||
|
||||
/**
|
||||
* Resolve the given default value into an argument value.
|
||||
*/
|
||||
private Object resolveDefaultValue(String defaultValue) {
|
||||
if (this.configurableBeanFactory == null) {
|
||||
return defaultValue;
|
||||
}
|
||||
String placeholdersResolved = this.configurableBeanFactory.resolveEmbeddedValue(defaultValue);
|
||||
BeanExpressionResolver exprResolver = this.configurableBeanFactory.getBeanExpressionResolver();
|
||||
if (exprResolver == null) {
|
||||
return defaultValue;
|
||||
}
|
||||
return exprResolver.evaluate(placeholdersResolved, this.expressionContext);
|
||||
}
|
||||
|
||||
/**
|
||||
* Invoked when a named value is required, but {@link #resolveName(String, MethodParameter, NativeWebRequest)}
|
||||
* returned {@code null} and there is no default value. Subclasses typically throw an exception in this case.
|
||||
|
||||
Reference in New Issue
Block a user