Add docs for circuit breaker new feature #22596
This commit is contained in:
parent
626d07edca
commit
d3de9d40cd
3 changed files with 106 additions and 4 deletions
|
|
@ -32,9 +32,9 @@ appropriate while the breaker is open.
|
||||||
The Akka library provides an implementation of a circuit breaker called
|
The Akka library provides an implementation of a circuit breaker called
|
||||||
:class:`akka.pattern.CircuitBreaker` which has the behavior described below.
|
:class:`akka.pattern.CircuitBreaker` which has the behavior described below.
|
||||||
|
|
||||||
=================
|
================
|
||||||
What do they do?
|
What do they do?
|
||||||
=================
|
================
|
||||||
* During normal operation, a circuit breaker is in the `Closed` state:
|
* During normal operation, a circuit breaker is in the `Closed` state:
|
||||||
* Exceptions or calls exceeding the configured `callTimeout` increment a failure counter
|
* Exceptions or calls exceeding the configured `callTimeout` increment a failure counter
|
||||||
* Successes reset the failure count to zero
|
* Successes reset the failure count to zero
|
||||||
|
|
@ -119,6 +119,48 @@ Java
|
||||||
There is also a :class:`CircuitBreakerProxy` actor that you can use, which is an alternative implementation of the pattern.
|
There is also a :class:`CircuitBreakerProxy` actor that you can use, which is an alternative implementation of the pattern.
|
||||||
The main difference is that it is intended to be used only for request-reply interactions with another actor. See :ref:`Circuit Breaker Actor <circuit-breaker-proxy>`
|
The main difference is that it is intended to be used only for request-reply interactions with another actor. See :ref:`Circuit Breaker Actor <circuit-breaker-proxy>`
|
||||||
|
|
||||||
|
--------------------------------
|
||||||
|
Control failure count explicitly
|
||||||
|
--------------------------------
|
||||||
|
|
||||||
|
By default, the circuit breaker treat :class:`Exception` as failure in synchronized API, or failed :class:`Future` as failure in future based API.
|
||||||
|
Failure will increment failure count, when failure count reach the `maxFailures`, circuit breaker will be opened.
|
||||||
|
However, some applications might requires certain exception to not increase failure count, or vice versa,
|
||||||
|
sometime we want to increase the failure count even if the call succeeded.
|
||||||
|
Akka circuit breaker provides a way to achieve such use case:
|
||||||
|
|
||||||
|
* `withCircuitBreaker`
|
||||||
|
* `withSyncCircuitBreaker`
|
||||||
|
|
||||||
|
* `callWithCircuitBreaker`
|
||||||
|
* `callWithCircuitBreakerCS`
|
||||||
|
* `callWithSyncCircuitBreaker`
|
||||||
|
|
||||||
|
All methods above accepts an argument ``defineFailureFn``
|
||||||
|
|
||||||
|
~~~~~
|
||||||
|
Scala
|
||||||
|
~~~~~
|
||||||
|
|
||||||
|
Type of ``defineFailureFn``: ``Try[T] ⇒ Boolean``
|
||||||
|
|
||||||
|
This is a function which takes in a :class:`Try[T]` and return a :class:`Boolean`. The :class:`Try[T]` correspond to the :class:`Future[T]` of the protected call. This function should return ``true`` if the call should increase failure count, else false.
|
||||||
|
|
||||||
|
.. includecode:: code/docs/circuitbreaker/CircuitBreakerDocSpec.scala
|
||||||
|
:include: even-no-as-failure
|
||||||
|
|
||||||
|
~~~~
|
||||||
|
Java
|
||||||
|
~~~~
|
||||||
|
|
||||||
|
Type of ``defineFailureFn``: :class:`BiFunction[Optional[T], Optional[Throwable], java.lang.Boolean]`
|
||||||
|
|
||||||
|
For Java Api, the signature is a bit different as there's no :class:`Try` in Java, so the response of protected call is modelled using :class:`Optional[T]` for succeeded return value and :class:`Optional[Throwable]` for exception, and the rules of return type is the same.
|
||||||
|
Ie. this function should return ``true`` if the call should increase failure count, else false.
|
||||||
|
|
||||||
|
.. includecode:: code/docs/circuitbreaker/EvenNoFailureJavaExample.java
|
||||||
|
:include: even-no-as-failure
|
||||||
|
|
||||||
-------------
|
-------------
|
||||||
Low level API
|
Low level API
|
||||||
-------------
|
-------------
|
||||||
|
|
@ -140,9 +182,9 @@ Scala
|
||||||
:include: circuit-breaker-tell-pattern
|
:include: circuit-breaker-tell-pattern
|
||||||
|
|
||||||
|
|
||||||
~~~~~
|
~~~~
|
||||||
Java
|
Java
|
||||||
~~~~~
|
~~~~
|
||||||
|
|
||||||
.. includecode:: code/docs/circuitbreaker/TellPatternJavaActor.java
|
.. includecode:: code/docs/circuitbreaker/TellPatternJavaActor.java
|
||||||
:include: circuit-breaker-tell-pattern
|
:include: circuit-breaker-tell-pattern
|
||||||
|
|
|
||||||
|
|
@ -11,6 +11,7 @@ import akka.pattern.pipe
|
||||||
import akka.actor.{ Actor, ActorLogging, ActorRef }
|
import akka.actor.{ Actor, ActorLogging, ActorRef }
|
||||||
|
|
||||||
import scala.concurrent.Future
|
import scala.concurrent.Future
|
||||||
|
import scala.util.{ Failure, Success, Try }
|
||||||
|
|
||||||
//#imports1
|
//#imports1
|
||||||
|
|
||||||
|
|
@ -76,3 +77,29 @@ class TellPatternActor(recipient: ActorRef) extends Actor with ActorLogging {
|
||||||
}
|
}
|
||||||
//#circuit-breaker-tell-pattern
|
//#circuit-breaker-tell-pattern
|
||||||
}
|
}
|
||||||
|
|
||||||
|
class EvenNoFailureActor extends Actor {
|
||||||
|
import context.dispatcher
|
||||||
|
//#even-no-as-failure
|
||||||
|
def luckyNumber(): Future[Int] = {
|
||||||
|
val evenNumberAsFailure: Try[Int] => Boolean = {
|
||||||
|
case Success(n) => n % 2 == 0
|
||||||
|
case Failure(_) => true
|
||||||
|
}
|
||||||
|
|
||||||
|
val breaker =
|
||||||
|
new CircuitBreaker(
|
||||||
|
context.system.scheduler,
|
||||||
|
maxFailures = 5,
|
||||||
|
callTimeout = 10.seconds,
|
||||||
|
resetTimeout = 1.minute)
|
||||||
|
|
||||||
|
// this call will return 8888 and increase failure count at the same time
|
||||||
|
breaker.withCircuitBreaker(Future(8888), evenNumberAsFailure)
|
||||||
|
}
|
||||||
|
//#even-no-as-failure
|
||||||
|
|
||||||
|
override def receive = {
|
||||||
|
case x: Int =>
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,33 @@
|
||||||
|
package docs.circuitbreaker;
|
||||||
|
|
||||||
|
import akka.actor.AbstractActor;
|
||||||
|
import akka.pattern.CircuitBreaker;
|
||||||
|
import scala.concurrent.duration.Duration;
|
||||||
|
|
||||||
|
import java.util.Optional;
|
||||||
|
import java.util.function.BiFunction;
|
||||||
|
|
||||||
|
public class EvenNoFailureJavaExample extends AbstractActor {
|
||||||
|
//#even-no-as-failure
|
||||||
|
private final CircuitBreaker breaker;
|
||||||
|
|
||||||
|
public EvenNoFailureJavaExample() {
|
||||||
|
this.breaker = new CircuitBreaker(
|
||||||
|
getContext().dispatcher(), getContext().system().scheduler(),
|
||||||
|
5, Duration.create(10, "s"), Duration.create(1, "m"));
|
||||||
|
}
|
||||||
|
|
||||||
|
public int luckyNumber() {
|
||||||
|
BiFunction<Optional<Integer>, Optional<Throwable>, Boolean> evenNoAsFailure =
|
||||||
|
(result, err) -> (result.isPresent() && result.get() % 2 == 0);
|
||||||
|
|
||||||
|
// this will return 8888 and increase failure count at the same time
|
||||||
|
return this.breaker.callWithSyncCircuitBreaker(() -> 8888, evenNoAsFailure);
|
||||||
|
}
|
||||||
|
|
||||||
|
//#even-no-as-failure
|
||||||
|
@Override
|
||||||
|
public Receive createReceive() {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
}
|
||||||
Loading…
Add table
Add a link
Reference in a new issue