- Only carry context in tryPass/onComplete method (this might be generic in upcoming versions) Signed-off-by: Eric Zhao <sczyh16@gmail.com>master
@@ -50,7 +50,7 @@ public class DegradeSlot extends AbstractLinkedProcessorSlot<DefaultNode> { | |||
return; | |||
} | |||
for (CircuitBreaker cb : circuitBreakers) { | |||
if (!cb.tryPass(context, r)) { | |||
if (!cb.tryPass(context)) { | |||
throw new DegradeException(cb.getRule().getLimitApp(), cb.getRule()); | |||
} | |||
} | |||
@@ -72,7 +72,7 @@ public class DegradeSlot extends AbstractLinkedProcessorSlot<DefaultNode> { | |||
if (curEntry.getBlockError() == null) { | |||
// passed request | |||
for (CircuitBreaker circuitBreaker : circuitBreakers) { | |||
circuitBreaker.onRequestComplete(context, r); | |||
circuitBreaker.onRequestComplete(context); | |||
} | |||
} | |||
@@ -65,13 +65,13 @@ public abstract class AbstractCircuitBreaker implements CircuitBreaker { | |||
} | |||
@Override | |||
public boolean tryPass(Context context, ResourceWrapper r) { | |||
public boolean tryPass(Context context) { | |||
// Template implementation. | |||
if (currentState.get() == State.CLOSED) { | |||
return true; | |||
} | |||
if (currentState.get() == State.OPEN) { | |||
// For half-open state we allow a request for trial. | |||
// For half-open state we allow a request for probing. | |||
return retryTimeoutArrived() && fromOpenToHalfOpen(context); | |||
} | |||
return false; | |||
@@ -106,16 +106,16 @@ public abstract class AbstractCircuitBreaker implements CircuitBreaker { | |||
notifyObservers(State.OPEN, State.HALF_OPEN, null); | |||
Entry entry = context.getCurEntry(); | |||
entry.whenComplete(new BiConsumer<Context, Entry>() { | |||
@Override | |||
public void accept(Context context, Entry entry) { | |||
// Note: This works as a temporary workaround for https://github.com/alibaba/Sentinel/issues/1638 | |||
// Without the hook, the circuit breaker won't recover from half-open state in some circumstances | |||
// when the request is actually blocked by upcoming rules (not only degrade rules). | |||
if (entry.getBlockError() != null) { | |||
// Fallback to OPEN due to detecting request is blocked | |||
currentState.compareAndSet(State.HALF_OPEN, State.OPEN); | |||
notifyObservers(State.HALF_OPEN, State.OPEN, 1.0d); | |||
return; | |||
} | |||
} | |||
}); | |||
return true; | |||
@@ -36,11 +36,10 @@ public interface CircuitBreaker { | |||
/** | |||
* Acquires permission of an invocation only if it is available at the time of invoking. | |||
* | |||
* @param context | |||
* @param r | |||
* @param context context of current invocation | |||
* @return {@code true} if permission was acquired and {@code false} otherwise | |||
*/ | |||
boolean tryPass(Context context, ResourceWrapper r); | |||
boolean tryPass(Context context); | |||
/** | |||
* Get current state of the circuit breaker. | |||
@@ -50,12 +49,12 @@ public interface CircuitBreaker { | |||
State currentState(); | |||
/** | |||
* Called when a `passed` invocation finished. | |||
* <p>Record a completed request with the context and handle state transformation of the circuit breaker.</p> | |||
* <p>Called when a <strong>passed</strong> invocation finished.</p> | |||
* | |||
* @param context context of current invocation | |||
* @param wrapper current resource | |||
*/ | |||
void onRequestComplete(Context context, ResourceWrapper wrapper); | |||
void onRequestComplete(Context context); | |||
/** | |||
* Circuit breaker state. | |||
@@ -63,7 +63,7 @@ public class ExceptionCircuitBreaker extends AbstractCircuitBreaker { | |||
} | |||
@Override | |||
public void onRequestComplete(Context context, ResourceWrapper r) { | |||
public void onRequestComplete(Context context) { | |||
Entry entry = context.getCurEntry(); | |||
if (entry == null) { | |||
return; | |||
@@ -61,7 +61,7 @@ public class ResponseTimeCircuitBreaker extends AbstractCircuitBreaker { | |||
} | |||
@Override | |||
public void onRequestComplete(Context context, ResourceWrapper wrapper) { | |||
public void onRequestComplete(Context context) { | |||
SlowRequestCounter counter = slidingCounter.currentWindow().value(); | |||
Entry entry = context.getCurEntry(); | |||
if (entry == null) { | |||