All MVC building methods accept controller type

Issue: SPR-13033
This commit is contained in:
Rossen Stoyanchev
2015-05-18 14:54:41 -04:00
parent e41877d64e
commit 85cf4e6999

View File

@@ -159,7 +159,9 @@ public class MvcUriComponentsBuilder {
* @param controllerType the controller to build a URI for * @param controllerType the controller to build a URI for
* @return a UriComponentsBuilder instance (never {@code null}) * @return a UriComponentsBuilder instance (never {@code null})
*/ */
public static UriComponentsBuilder fromController(UriComponentsBuilder builder, Class<?> controllerType) { public static UriComponentsBuilder fromController(UriComponentsBuilder builder,
Class<?> controllerType) {
builder = getBaseUrlToUse(builder); builder = getBaseUrlToUse(builder);
String mapping = getTypeRequestMapping(controllerType); String mapping = getTypeRequestMapping(controllerType);
return builder.path(mapping); return builder.path(mapping);
@@ -176,8 +178,11 @@ public class MvcUriComponentsBuilder {
* @throws IllegalArgumentException if there is no matching or * @throws IllegalArgumentException if there is no matching or
* if there is more than one matching method * if there is more than one matching method
*/ */
public static UriComponentsBuilder fromMethodName(Class<?> controllerType, String methodName, Object... args) { public static UriComponentsBuilder fromMethodName(Class<?> controllerType,
return fromMethodName(null, controllerType, methodName, args); String methodName, Object... args) {
Method method = getMethod(controllerType, methodName, args);
return fromMethodInternal(null, controllerType, method, args);
} }
/** /**
@@ -198,7 +203,7 @@ public class MvcUriComponentsBuilder {
Class<?> controllerType, String methodName, Object... args) { Class<?> controllerType, String methodName, Object... args) {
Method method = getMethod(controllerType, methodName, args); Method method = getMethod(controllerType, methodName, args);
return fromMethod(builder, method, args); return fromMethodInternal(builder, controllerType, method, args);
} }
/** /**
@@ -232,12 +237,17 @@ public class MvcUriComponentsBuilder {
* controller.getAddressesForCountry("US") * controller.getAddressesForCountry("US")
* builder = MvcUriComponentsBuilder.fromMethodCall(controller); * builder = MvcUriComponentsBuilder.fromMethodCall(controller);
* </pre> * </pre>
* @param invocationInfo either the value returned from a "mock" controller * @param info either the value returned from a "mock" controller
* invocation or the "mock" controller itself after an invocation * invocation or the "mock" controller itself after an invocation
* @return a UriComponents instance * @return a UriComponents instance
*/ */
public static UriComponentsBuilder fromMethodCall(Object invocationInfo) { public static UriComponentsBuilder fromMethodCall(Object info) {
return fromMethodCall(null, invocationInfo); Assert.isInstanceOf(MethodInvocationInfo.class, info);
MethodInvocationInfo invocationInfo = (MethodInvocationInfo) info;
Class<?> controllerType = invocationInfo.getControllerType();
Method method = invocationInfo.getControllerMethod();
Object[] arguments = invocationInfo.getArgumentValues();
return fromMethodInternal(null, controllerType, method, arguments);
} }
/** /**
@@ -247,14 +257,17 @@ public class MvcUriComponentsBuilder {
* request or to apply a custom baseUrl not matching the current request. * request or to apply a custom baseUrl not matching the current request.
* @param builder the builder for the base URL; the builder will be cloned * @param builder the builder for the base URL; the builder will be cloned
* and therefore not modified and may be re-used for further calls. * and therefore not modified and may be re-used for further calls.
* @param invocationInfo either the value returned from a "mock" controller * @param info either the value returned from a "mock" controller
* invocation or the "mock" controller itself after an invocation * invocation or the "mock" controller itself after an invocation
* @return a UriComponents instance * @return a UriComponents instance
*/ */
public static UriComponentsBuilder fromMethodCall(UriComponentsBuilder builder, Object invocationInfo) { public static UriComponentsBuilder fromMethodCall(UriComponentsBuilder builder, Object info) {
Assert.isInstanceOf(MethodInvocationInfo.class, invocationInfo); Assert.isInstanceOf(MethodInvocationInfo.class, info);
MethodInvocationInfo info = (MethodInvocationInfo) invocationInfo; MethodInvocationInfo invocationInfo = (MethodInvocationInfo) info;
return fromMethod(builder, info.getControllerType(), info.getControllerMethod(), info.getArgumentValues()); Class<?> controllerType = invocationInfo.getControllerType();
Method method = invocationInfo.getControllerMethod();
Object[] arguments = invocationInfo.getArgumentValues();
return fromMethodInternal(builder, controllerType, method, arguments);
} }
/** /**
@@ -330,7 +343,10 @@ public class MvcUriComponentsBuilder {
throw new IllegalArgumentException("No unique match for mapping mappingName " + throw new IllegalArgumentException("No unique match for mapping mappingName " +
name + ": " + handlerMethods); name + ": " + handlerMethods);
} }
return new MethodArgumentBuilder(builder, handlerMethods.get(0).getMethod()); HandlerMethod handlerMethod = handlerMethods.get(0);
Class<?> controllerType = handlerMethod.getBeanType();
Method method = handlerMethod.getMethod();
return new MethodArgumentBuilder(builder, controllerType, method);
} }
/** /**
@@ -341,12 +357,13 @@ public class MvcUriComponentsBuilder {
* {@link org.springframework.web.method.support.UriComponentsContributor * {@link org.springframework.web.method.support.UriComponentsContributor
* UriComponentsContributor}) while remaining argument values are ignored and * UriComponentsContributor}) while remaining argument values are ignored and
* can be {@code null}. * can be {@code null}.
* @param controllerType the controller type
* @param method the controller method * @param method the controller method
* @param args argument values for the controller method * @param args argument values for the controller method
* @return a UriComponentsBuilder instance, never {@code null} * @return a UriComponentsBuilder instance, never {@code null}
*/ */
public static UriComponentsBuilder fromMethod(Method method, Object... args) { public static UriComponentsBuilder fromMethod(Class<?> controllerType, Method method, Object... args) {
return fromMethod(null, method, args); return fromMethodInternal(null, controllerType, method, args);
} }
/** /**
@@ -357,15 +374,30 @@ public class MvcUriComponentsBuilder {
* current request. * current request.
* @param baseUrl the builder for the base URL; the builder will be cloned * @param baseUrl the builder for the base URL; the builder will be cloned
* and therefore not modified and may be re-used for further calls. * and therefore not modified and may be re-used for further calls.
* @param controllerType the controller type
* @param method the controller method * @param method the controller method
* @param args argument values for the controller method * @param args argument values for the controller method
* @return a UriComponentsBuilder instance, never {@code null} * @return a UriComponentsBuilder instance, never {@code null}
*/ */
public static UriComponentsBuilder fromMethod(UriComponentsBuilder baseUrl, Method method, Object... args) { public static UriComponentsBuilder fromMethod(UriComponentsBuilder baseUrl,
return fromMethod(baseUrl, method.getDeclaringClass(), method, args); Class<?> controllerType, Method method, Object... args) {
return fromMethodInternal(baseUrl, method.getDeclaringClass(), method, args);
} }
private static UriComponentsBuilder fromMethod(UriComponentsBuilder baseUrl, Class<?> controllerType, Method method, Object... args) { /**
* See {@link #fromMethod(Class, Method, Object...)}.
* @deprecated as of 4.2 this is deprecated in favor of the overloaded
* method that also accepts a controllerType.
*/
@Deprecated
public static UriComponentsBuilder fromMethod(Method method, Object... args) {
return fromMethodInternal(null, method.getDeclaringClass(), method, args);
}
private static UriComponentsBuilder fromMethodInternal(UriComponentsBuilder baseUrl,
Class<?> controllerType, Method method, Object... args) {
baseUrl = getBaseUrlToUse(baseUrl); baseUrl = getBaseUrlToUse(baseUrl);
String typePath = getTypeRequestMapping(controllerType); String typePath = getTypeRequestMapping(controllerType);
String methodPath = getMethodRequestMapping(method); String methodPath = getMethodRequestMapping(method);
@@ -621,11 +653,11 @@ public class MvcUriComponentsBuilder {
} }
/** /**
* An alternative to {@link #fromMethod(java.lang.reflect.Method, Object...)} * An alternative to {@link #fromMethod(Class, Method, Object...)}
* for use with an instance of this class created via {@link #relativeTo}. * for use with an instance of this class created via {@link #relativeTo}.
*/ */
public UriComponentsBuilder withMethod(Method method, Object... args) { public UriComponentsBuilder withMethod(Class<?> controllerType, Method method, Object... args) {
return fromMethod(this.baseUrl, method, args); return fromMethod(this.baseUrl, controllerType, method, args);
} }
@@ -692,6 +724,8 @@ public class MvcUriComponentsBuilder {
public static class MethodArgumentBuilder { public static class MethodArgumentBuilder {
private final Class<?> controllerType;
private final Method method; private final Method method;
private final Object[] argumentValues; private final Object[] argumentValues;
@@ -699,13 +733,15 @@ public class MvcUriComponentsBuilder {
private final UriComponentsBuilder baseUrl; private final UriComponentsBuilder baseUrl;
public MethodArgumentBuilder(Method method) { public MethodArgumentBuilder(Class<?> controllerType, Method method) {
this(null, method); this(null, controllerType, method);
} }
public MethodArgumentBuilder(UriComponentsBuilder baseUrl, Method method) { public MethodArgumentBuilder(UriComponentsBuilder baseUrl, Class<?> controllerType, Method method) {
Assert.notNull(controllerType, "'controllerType' is required");
Assert.notNull(method, "'method' is required"); Assert.notNull(method, "'method' is required");
this.baseUrl = baseUrl; this.baseUrl = baseUrl;
this.controllerType = controllerType;
this.method = method; this.method = method;
this.argumentValues = new Object[method.getParameterTypes().length]; this.argumentValues = new Object[method.getParameterTypes().length];
for (int i = 0; i < this.argumentValues.length; i++) { for (int i = 0; i < this.argumentValues.length; i++) {
@@ -713,6 +749,14 @@ public class MvcUriComponentsBuilder {
} }
} }
/**
* @deprecated as of 4.2 deprecated in favor of alternative constructors
* that accept the controllerType.
*/
@Deprecated
public MethodArgumentBuilder(Method method) {
this(method.getDeclaringClass(), method);
}
public MethodArgumentBuilder arg(int index, Object value) { public MethodArgumentBuilder arg(int index, Object value) {
@@ -721,13 +765,13 @@ public class MvcUriComponentsBuilder {
} }
public String build() { public String build() {
return MvcUriComponentsBuilder.fromMethod(this.baseUrl, this.method, this.argumentValues) return fromMethodInternal(this.baseUrl, this.controllerType, this.method,
.build(false).encode().toUriString(); this.argumentValues).build(false).encode().toUriString();
} }
public String buildAndExpand(Object... uriVariables) { public String buildAndExpand(Object... uriVars) {
return MvcUriComponentsBuilder.fromMethod(this.baseUrl, this.method, this.argumentValues) return fromMethodInternal(this.baseUrl, this.controllerType, this.method,
.build(false).expand(uriVariables).encode().toString(); this.argumentValues).build(false).expand(uriVars).encode().toString();
} }
} }