LimitedConcurrentExecutionsStrategy.java
package net.secodo.jcircuitbreaker.breakstrategy.impl;
import java.util.Collection;
import net.secodo.jcircuitbreaker.breaker.execution.ExecutedTask;
import net.secodo.jcircuitbreaker.breaker.execution.ExecutionContext;
import net.secodo.jcircuitbreaker.breakstrategy.BreakStrategy;
import net.secodo.jcircuitbreaker.task.Task;
/**
* An implementation of {@link BreakStrategy} which causes the circuit breaker to break (not execute the Task) in
* case all tasks currently running inside the circuit breaker reaches the allowed maximum (defined by
* maxSupportedExecutions constructor param).
*
* <p>In constructor you define maximum number of allowed concurrent executions of <i>real_method</i> .
*
* <p>For example this strategy:
*
* <p>new LimitedConcurrentExecutionsStrategy(10);
*
* <p>breaks (not allows execution of target-method) in there are currently 10 other threads that started execution
* of <i>target-method</i> and the method did not yet return a value. In this case circuit breaker would executed a
* break handler to provide fallback behaviour. If the number of task at the moment was less than 10, <i>Task</i>
* (<i>real-method</i>) would be executed normal.
*
* <p>NOTE: in above example, if the average was above 1000ms than this strategy would return false to circuit breaker
* and circuit breaker would execute {@link net.secodo.jcircuitbreaker.breakhandler.BreakHandler} to handle this
* situation
*
* @param <R> the return type of <i>real-method</i> that is executed by circuit breaker
*/
public class LimitedConcurrentExecutionsStrategy<R> implements BreakStrategy<R> {
/**
* Protected access to allow extending classes to dynamically change it,
* e.g. via MBean
*/
protected long maxSupportedExecutions;
public LimitedConcurrentExecutionsStrategy(long maxSupportedExecutions) {
this.maxSupportedExecutions = maxSupportedExecutions;
}
@Override
public boolean shouldBreak(Task<R> task, ExecutionContext<R> executionContext) {
final Collection<ExecutedTask<R>> executionsInProgress = executionContext.getExecutionsInProgress();
return executionsInProgress.size() >= maxSupportedExecutions;
}
}