Khushboo
Khushboo

Reputation: 3163

CircuitBreaker Fallback method not working

I have the below code in Billing service microservice:

@RestController
@RequestMapping("/billing")
public class WebController {

    @Autowired
    private BillingService service;
    
    @GetMapping("/hi")
    @CircuitBreaker(name="BillingServiceCapture", fallbackMethod = "hiFallback")
    public String hi() {
        return "Hello Khushboo!";
    }
    
    public String hiFallback() {
        return "Hello Khushboo FallBack!";
    }

Application.Properties file:

server.port=9191
spring.h2.console.enable=true
spring.application.name=billing-service
eureka.client.serviceurl.defaultzone=http://localhost:8761/eureka   
eureka.instance.hostname=localhost

management.health.circuitbreakers.enabled=true
#actuator settings
management.endpoints.web.exposure.include=*
management.endpoint.health.show-details=always

resilience4j.circuitbreaker.instances.BillingServiceCapture.registerHealthIndicator=true
resilience4j.circuitbreaker.instances.BillingServiceCapture.eventConsumerBufferSize=10
resilience4j.circuitbreaker.instances.BillingServiceCapture.failureRateThreshold=20
resilience4j.circuitbreaker.instances.BillingServiceCapture.minimumNumberOfCalls=5
resilience4j.circuitbreaker.instances.BillingServiceCapture.automaticTransitionFromOpenToHalfOpenEnabled=true
resilience4j.circuitbreaker.instances.BillingServiceCapture.waitDurationInOpenState=5s
resilience4j.circuitbreaker.instances.BillingServiceCapture.permittedNumberOfCallsInHalfOpenState=3 
resilience4j.circuitbreaker.instances.BillingServiceCapture.slidingWindowSize=10
resilience4j.circuitbreaker.instances.BillingServiceCapture.slidingWindowType=COUNT_BASED

However, if I send a Get Request: localhost:8765/billing/hi I get Hello Khushboo message.

But when I stop the BillingService microservice and again send the same request, the circuit breaker method doesn't get invoked.

Also, while accessing the Actuator Health status, I do not see circuit breaker information in the status logs which I should see.

I even added the CircuitBreaker code in OrderService which actually calls the BillingService:

@CircuitBreaker(name="BillingServiceCapture", fallbackMethod = "getAllBillingDetails")
    public TransactionResponse saveOrder(TransactionRequest request) {
        
        Order order=request.getOrder();
        Billing billing=request.getBilling();
        
        billing.setOrderId(order.getId());
        billing.setAmount(order.getPrice());

        Order ordermade=orderRepo.save(order);
        
        Billing billingresponse=billingproxy.getBillingDone(billing);
        
        TransactionResponse response=null;
        
        String responseStr= billingresponse.getPaymentStatus().equals("success")?"Payment processing successful":"Payment failed";
        response=new TransactionResponse(order, billingresponse.getTransactionId(),billingresponse.getAmount(),responseStr);
        
        return response;
    }
    
    public Billing getAllBillingDetails(Billing bill,Exception e) {
        return new Billing(1000,"pass",101,102,1000);
    }

When I call http://localhost:8765/order/bookorder - this throws a 500 internal server exception but CircuitBreaker is not called. The error is:

[503] during [GET] to [http://billing-service/billing/preparebill] [BillingProxy#getBillingDone(Billing)]: [Load balancer does not contain an instance for the service billing-service]

Please note for testing purpose I'm not starting BillingService so the instance is not available for OrderService Feign to call.

Any insights will be appreciated.

Thanks.

Upvotes: 0

Views: 2002

Answers (1)

Saman KHATAEI
Saman KHATAEI

Reputation: 117

The fallback method should pass the Exception parameter and return the same type as the original method:

public String hiFallback(Exception e) {
    return "Hello Khushboo FallBack!";
}

Upvotes: 1

Related Questions