spring-cloud / spring-cloud-circuitbreaker

Spring Cloud Circuit Breaker API and Implementations
Apache License 2.0
328 stars 109 forks source link

Defining behavior for circuit breaker open state #177

Closed kyle-log closed 3 months ago

kyle-log commented 7 months ago

Problem describe I need to know the Resilience4j implementation to define the behavior of the CircuitBreaker when it is opened. Here's why

import io.github.resilience4j.circuitbreaker.CallNotPermittedException

factory.create(name).run(block) { e ->
    when(e) {
        is CallNotPermittedException -> // Open
        else -> // Not open
    }
}

I only want to know the Spring cloud circuit breaker interface, not the resilience4j implementation, because I want to be able to easily change to a different implementation in the future.

Solution

  1. When the circuit breaker is open, an exception specifically defined by Spring Cloud Circuit Breaker is thrown.
  2. The result of the CircuitBreaker's run function is encapsulated in a custom Response model, which will indicate whether the CircuitBreaker is open.
  3. The run function of the Circuitbreaker is given a function that is only executed when the CircuitBreaker is open.
  4. There is a way to check the current status of the circuit breaker.

Alternatives I'm currently using a custom exception to handle the situation when the circuit breaker is open. For more details, you can refer to this implementation: https://github.com/kyle-log/circuit-breaker-without-annotation"

ryanjbaxter commented 7 months ago

The exception that should be thrown when the circuit breaker is open is CallNotPermittedException.

spring-cloud-issues commented 7 months ago

If you would like us to look at this issue, please provide the requested information. If the information is not provided within the next 7 days this issue will be closed.

kyle-log commented 7 months ago

Thanks for the answer. It seems that CallNotPermittedException is a specific exception used in the Resilience4j framework.

// as is
import io.github.resilience4j.circuitbreaker.CallNotPermittedException;

factory.create(name).run(
    () -> { /* block */ },
    e -> {
        if (e instanceof CallNotPermittedException) {
            // Open
            return DefaultValue()
        } else {
            // Not open
            throw e
        }
    }
);

// to be, (example)
import org.springframework.cloud.client.CircuitOpenException

factory.create(name).run(
    () -> { /* block */ },
    e -> {
        if (e instanceof CircuitOpenException) {
            // Open
            return DefaultValue()
        } else {
            // Not open
            throw e
        }
    }
);

This is to provide flexibility in case the circuit breaker implementation Resilience4j changes to something else..

ryanjbaxter commented 7 months ago

Sorry I am not following what you are saying