Don't wrap resolver exceptions in InvocableHandlerMethod

Prior to this commit, exceptions thrown by the
`HandlerMethodArgumentResolver` would be wrapped into
`IllegalStateException`s.

This commit makes sure that a DEBUG log is written with the relevant
information and that the root cause is not wrapped into another
exception, so that the appropriate `ExceptionHandler` can be used to
deal with this error.

Issue: SPR-14618
master
Brian Clozel 8 years ago
parent e8530c917e
commit 960d335c35
  1. 21
      spring-web-reactive/src/main/java/org/springframework/web/reactive/result/method/InvocableHandlerMethod.java
  2. 22
      spring-web-reactive/src/test/java/org/springframework/web/reactive/result/method/InvocableHandlerMethodTests.java

@ -1,5 +1,5 @@
/*
* Copyright 2002-2015 the original author or authors.
* Copyright 2002-2016 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@ -129,7 +129,11 @@ public class InvocableHandlerMethod extends HandlerMethod {
try {
return resolver.resolveArgument(param, model, exchange)
.defaultIfEmpty(NO_VALUE)
.otherwise(ex -> Mono.error(getArgError("Error resolving ", param, ex)))
.doOnError(cause -> {
if(logger.isDebugEnabled()) {
logger.debug(getDetailedErrorMessage("Error resolving ", param), cause);
}
})
.log("reactor.unresolved");
}
catch (Exception ex) {
@ -148,10 +152,15 @@ public class InvocableHandlerMethod extends HandlerMethod {
}
private IllegalStateException getArgError(String message, MethodParameter param, Throwable cause) {
return new IllegalStateException(message +
"argument [" + param.getParameterIndex() + "] " +
"of type [" + param.getParameterType().getName() + "] " +
"on method [" + getBridgedMethod().toGenericString() + "]", cause);
return new IllegalStateException(getDetailedErrorMessage(message, param), cause);
}
private String getDetailedErrorMessage(String message, MethodParameter param) {
StringBuilder sb = new StringBuilder(message);
sb.append("argument [" + param.getParameterIndex() + "] ");
sb.append("of type [" + param.getParameterType().getName() + "] ");
sb.append("on method [" + getBridgedMethod().toGenericString() + "]");
return sb.toString();
}
private Object doInvoke(Object[] args) throws Exception {

@ -1,5 +1,5 @@
/*
* Copyright 2002-2015 the original author or authors.
* Copyright 2002-2016 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@ -32,6 +32,7 @@ import org.springframework.ui.ModelMap;
import org.springframework.web.reactive.HandlerResult;
import org.springframework.web.reactive.result.ResolvableMethod;
import org.springframework.web.server.ServerWebExchange;
import org.springframework.web.server.UnsupportedMediaTypeStatusException;
import org.springframework.web.server.adapter.DefaultServerWebExchange;
import org.springframework.web.server.session.MockWebSessionManager;
@ -102,25 +103,12 @@ public class InvocableHandlerMethodTests {
@Test
public void resolverThrowsException() throws Exception {
InvocableHandlerMethod hm = handlerMethod("singleArg");
addResolver(hm, Mono.error(new IllegalStateException("boo")));
addResolver(hm, Mono.error(new UnsupportedMediaTypeStatusException("boo")));
Mono<HandlerResult> mono = hm.invokeForRequest(this.exchange, this.model);
TestSubscriber.subscribe(mono)
.assertError(IllegalStateException.class)
.assertErrorMessage("Error resolving argument [0] of type [java.lang.String] " +
"on method [" + hm.getMethod().toGenericString() + "]");
}
@Test
public void resolverWithErrorSignal() throws Exception {
InvocableHandlerMethod hm = handlerMethod("singleArg");
addResolver(hm, Mono.error(new IllegalStateException("boo")));
Mono<HandlerResult> mono = hm.invokeForRequest(this.exchange, this.model);
TestSubscriber.subscribe(mono)
.assertError(IllegalStateException.class)
.assertErrorMessage("Error resolving argument [0] of type [java.lang.String] " +
"on method [" + hm.getMethod().toGenericString() + "]");
.assertError(UnsupportedMediaTypeStatusException.class)
.assertErrorMessage("Request failure [status: 415, reason: \"boo\"]");
}
@Test

Loading…
Cancel
Save