Throw the origin RuntimeException when invoke a restTemplate fallback method, it's helpful for a global handler with @ExceptionHandler.

Refined codes.
pull/1291/head
SoulSong 5 years ago
parent 3f534c8c33
commit 0a9f3eb6f9

@ -139,6 +139,9 @@ public class SentinelProtectInterceptor implements ClientHttpRequestInterceptor
throw new RuntimeException(e); throw new RuntimeException(e);
} }
catch (InvocationTargetException e) { catch (InvocationTargetException e) {
if (e.getTargetException() instanceof RuntimeException) {
throw (RuntimeException) e.getTargetException();
}
throw new RuntimeException(e); throw new RuntimeException(e);
} }
} }

@ -20,6 +20,8 @@ import com.alibaba.cloud.sentinel.annotation.SentinelRestTemplate;
import com.alibaba.cloud.sentinel.custom.SentinelBeanPostProcessor; import com.alibaba.cloud.sentinel.custom.SentinelBeanPostProcessor;
import com.alibaba.cloud.sentinel.rest.SentinelClientHttpResponse; import com.alibaba.cloud.sentinel.rest.SentinelClientHttpResponse;
import com.alibaba.csp.sentinel.slots.block.BlockException; import com.alibaba.csp.sentinel.slots.block.BlockException;
import com.alibaba.csp.sentinel.slots.block.degrade.DegradeException;
import com.alibaba.csp.sentinel.slots.block.flow.FlowException;
import org.junit.Test; import org.junit.Test;
@ -29,7 +31,11 @@ import org.springframework.context.annotation.AnnotationConfigApplicationContext
import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration; import org.springframework.context.annotation.Configuration;
import org.springframework.http.HttpRequest; import org.springframework.http.HttpRequest;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.http.client.ClientHttpRequestExecution; import org.springframework.http.client.ClientHttpRequestExecution;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.client.RestTemplate; import org.springframework.web.client.RestTemplate;
import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertEquals;
@ -112,6 +118,12 @@ public class SentinelRestTemplateTests {
new AnnotationConfigApplicationContext(TestConfig14.class); new AnnotationConfigApplicationContext(TestConfig14.class);
} }
@Test
public void testExceptionHandler4Fallback() {
new AnnotationConfigApplicationContext(TestConfig15.class);
}
@Configuration @Configuration
public static class TestConfig1 { public static class TestConfig1 {
@Bean @Bean
@ -328,6 +340,75 @@ public class SentinelRestTemplateTests {
} }
} }
@Configuration
public static class TestConfig15 {
@Bean
SentinelBeanPostProcessor sentinelBeanPostProcessor(
ApplicationContext applicationContext) {
return new SentinelBeanPostProcessor(applicationContext);
}
@Bean
@SentinelRestTemplate(fallbackClass = TestConfig15.class,
fallback = "fallbackHandler",
blockHandlerClass = TestConfig15.class,
blockHandler = "flowHandler")
RestTemplate restTemplate() {
return new RestTemplate();
}
@Bean
public SentinelRestTemplateExceptionHandler globalExceptionHandler() {
return new SentinelRestTemplateExceptionHandler();
}
public static SentinelClientHttpResponse flowHandler(HttpRequest request,
byte[] body,
ClientHttpRequestExecution execution,
BlockException exception) {
if (exception instanceof FlowException) {
throw new SentinelRestTemplateFlowException(exception.getMessage(), exception);
}
return new SentinelClientHttpResponse("Oops flowHandler");
}
public static SentinelClientHttpResponse fallbackHandler(HttpRequest request,
byte[] body,
ClientHttpRequestExecution execution,
BlockException exception) {
if (exception instanceof DegradeException) {
throw new SentinelRestTemplateDegradeException(exception.getMessage(), exception);
}
return new SentinelClientHttpResponse("Oops fallback");
}
public static class SentinelRestTemplateFlowException extends RuntimeException {
SentinelRestTemplateFlowException(String message, Throwable cause) {
super(message, cause);
}
}
public static class SentinelRestTemplateDegradeException extends RuntimeException {
SentinelRestTemplateDegradeException(String message, Throwable cause) {
super(message, cause);
}
}
@ControllerAdvice
public class SentinelRestTemplateExceptionHandler {
@ExceptionHandler(SentinelRestTemplateFlowException.class)
public ResponseEntity<String> restTemplateFlowExceptionHandler(SentinelRestTemplateFlowException exception) {
return ResponseEntity.status(HttpStatus.TOO_MANY_REQUESTS).body("PS: have a rest.");
}
@ExceptionHandler(SentinelRestTemplateDegradeException.class)
public ResponseEntity<String> restTemplateDegradeExceptionHandler(SentinelRestTemplateDegradeException exception) {
return ResponseEntity.status(HttpStatus.SERVICE_UNAVAILABLE).body("PS: " + HttpStatus.SERVICE_UNAVAILABLE.getReasonPhrase());
}
}
}
public static class ExceptionUtil { public static class ExceptionUtil {
public static SentinelClientHttpResponse handleException(HttpRequest request, public static SentinelClientHttpResponse handleException(HttpRequest request,
byte[] body, ClientHttpRequestExecution execution, BlockException ex) { byte[] body, ClientHttpRequestExecution execution, BlockException ex) {
@ -350,6 +431,7 @@ public class SentinelRestTemplateTests {
ClientHttpRequestExecution execution, BlockException ex) { ClientHttpRequestExecution execution, BlockException ex) {
System.out.println("Oops: " + ex.getClass().getCanonicalName()); System.out.println("Oops: " + ex.getClass().getCanonicalName());
} }
} }
public static class UrlCleanUtil { public static class UrlCleanUtil {
@ -361,4 +443,5 @@ public class SentinelRestTemplateTests {
} }
} }
} }

Loading…
Cancel
Save