繁体   English   中英

Resilience4J 断路器启动特定的 HTTP 状态代码

[英]Resilience4J Circuit Breaker to kick-in on specific HTTP status code

我知道我们可以在构建CircuitBreakerConfig使用recordExceptions()来注册断路器应转换为OPEN状态的异常。

代码

我正在使用resilience4j-feign来装饰我的CircuitBreaker 如果您能指出我的代码示例,那将非常有帮助。

问题

如果出现特定的 HTTP 状态代码(例如,在503 Service Unavailable 上),如何使断路器启动?

来自自述文件( https://resilience4j.readme.io/docs/circuitbreaker#section-create-and-configure-a-circuitbreaker

// Create a custom configuration for a CircuitBreaker
CircuitBreakerConfig circuitBreakerConfig = CircuitBreakerConfig.custom()
  .recordExceptions(IOException.class, TimeoutException.class) // add you exceptions here!!!
  .ignoreExceptions(BusinessException.class, OtherBusinessException.class)
  .build();

记录为失败并因此增加失败率的异常列表。 任何匹配或从列表之一继承的异常都算作失败,除非通过 ignoreExceptions 显式忽略。

您需要为客户端的外部调用编写一个异常/响应处理程序,并根据收到的 http 状态抛出自定义异常。 然后将这些异常注册为断路器配置中的记录异常。 下面是一个小例子。 CB 将仅在 AbcException 时打开。 CB 配置是resilience4j.circuitbreaker.instances.bookService.record-exceptions=com.sk.example.cb.circuitbreakerr4j.AbcException

 @Service @Slf4j public class BookApiService { RestTemplate restTemplate = new RestTemplate(); @CircuitBreaker(name = "bookService", fallbackMethod = "getBookFallback") public String getBook(){ try { ResponseEntity<String> stringResponseEntity = restTemplate.getForEntity(new URI("http://localhost:8080/book"), String.class); if(null != stringResponseEntity){ if(stringResponseEntity.getStatusCode().is2xxSuccessful()){ return stringResponseEntity.getBody(); } } } catch (URISyntaxException e) { e.printStackTrace(); }catch (HttpServerErrorException e){ log.error("Service unavailable",e); if(e.getMessage().startsWith("503")) { throw new AbcException(); }else{ throw e; } } return ""; }

TL;DR:使用自定义异常将 HTTP 状态(例如 503)从 HTTP 客户端(例如 Feign)传送到 Resilience4J

  1. Feign:实现和配置一个ErrorDecoder以在 HTTP 状态上抛出一个自定义异常,如 503
  2. Resilience4J:使用断路器配置记录该自定义异常。

假装

Feign 默认抛出FeignException以防 HTTP 状态码错误。 您可以通过方法int status()获取状态代码编号。

要自定义您的 feign-clients 错误处理,请配置ErrorDecoder的(自定义)实现

如果您需要对处理意外响应进行更多控制,Feign 实例可以通过构建器注册自定义ErrorDecoder [..] 导致 HTTP 状态不在 2xx 范围内的所有响应都将触发ErrorDecoder的 decode 方法,允许您处理响应、将故障包装到自定义异常中或执行任何其他处理。 如果您想再次重试请求,请抛出RetryableException 这将调用注册的Retryer

自定义 Feign 错误处理

实现并配置自定义ErrorDecoder以在 HTTP 状态 503 的情况下引发异常。

@Component
@Slf4j
public class CustomErrorDecoder implements ErrorDecoder {
    
    @Override
    public Exception decode(String methodKey, Response response) {
        
        switch (response.status()) {
            case 400:
                log.error("Status code {} on methodKey '{}'", response.status(), methodKey);
            case 503:
                return new ServiceUnavailableException("HTTP status 503 when calling " methodKey);
            default:
                return new Exception(response.reason());
        } 
    }
    
}

这将抛出您的自定义异常ServiceUnavailableException

Resilienc4J 的断路器

默认情况下,断路器对异常做出反应。 它会记录它们,如果在太短的时间内太多,它会打开电路。

您可以在业务级别上按预期配置要记录哪些异常以及忽略哪些异常。

在特定异常上触发断路器

您可以配置 CiruitBreaker 来记录该异常 笑话的答案解释了如何做到这一点。

也可以看看

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM