kestra-io/kestra · error · IllegalArgumentException
Invalid target state: {state}. Valid states are: {VALID_TARG
Error message
Invalid target state: {state}. Valid states are: {VALID_TARGET_STATES} What it means
The `ConcurrencyLimitService.unqueue()` method only allows transitions to three target states: `RUNNING`, `CANCELLED`, and `FAILED` (defined in `VALID_TARGET_STATES`). If any other `State.Type` is passed (e.g., `SUCCESS`, `PAUSED`, `KILLED`), an `IllegalArgumentException` is thrown. These states represent the valid outcomes of releasing a queued execution.
Source
Thrown at core/src/main/java/io/kestra/core/services/ConcurrencyLimitService.java:35
@Inject
private ExecutionQueuedStateStore executionQueuedStateStore;
/**
* Unqueue a queued execution.
*
* @throws IllegalArgumentException in case the execution is not queued or is transitioned to an unsupported state.
*/
public Execution unqueue(Execution execution, State.Type state) {
if (execution.getState().getCurrent() != State.Type.QUEUED) {
throw new IllegalArgumentException("Only QUEUED execution can be unqueued");
}
state = (state == null) ? State.Type.RUNNING : state;
// Validate the target state, throwing an exception if the state is invalid
if (!VALID_TARGET_STATES.contains(state)) {
throw new IllegalArgumentException("Invalid target state: " + state + ". Valid states are: " + VALID_TARGET_STATES);
}
executionQueuedStateStore.remove(execution);
return execution.withState(state);
}
}
View on GitHub (pinned to 823fada927)
Solutions
- Use one of the valid target states: RUNNING (start it), CANCELLED (cancel it), or FAILED (fail it).
- For SUCCESS, let the execution run and complete normally rather than forcing the state at unqueue time.
- If you need PAUSED, the execution must run first and then be paused, not transitioned directly from QUEUED.
Example fix
// before executionService.unqueue(execution, State.Type.SUCCESS); // after executionService.unqueue(execution, State.Type.RUNNING);
Defensive patterns
Strategy: validation
Validate before calling
// Validate target state before calling unqueue
import io.kestra.core.models.flows.State;
import java.util.EnumSet;
private static final Set<State.Type> VALID = EnumSet.of(State.Type.RUNNING, State.Type.CANCELLED, State.Type.FAILED);
public static State.Type validateUnqueueTargetState(State.Type state) {
if (state == null) return State.Type.RUNNING;
if (!VALID.contains(state)) {
throw new IllegalArgumentException("Invalid target state: " + state + ". Valid: " + VALID);
}
return state;
} Type guard
const VALID_UNQUEUE_STATES = new Set(['RUNNING', 'CANCELLED', 'FAILED']);
function isValidUnqueueState(state: string): boolean {
return VALID_UNQUEUE_STATES.has(state);
} Prevention
- Only pass RUNNING, CANCELLED, or FAILED as the target state for unqueue().
- Default to RUNNING when the intent is to start the execution.
- Do not try to force SUCCESS or PAUSED from QUEUED — these are not valid unqueue transitions.
When it happens
Trigger: Calling `unqueue(execution, State.Type.SUCCESS)` or `unqueue(execution, State.Type.PAUSED)`. Passing a state that is semantically inappropriate for an unqueue operation (SUCCESS must come from task completion, not from unqueuing).
Common situations: A developer assumes any terminal state is valid. A caller tries to mark a queued execution as SUCCESS to skip it, but SUCCESS is not a valid unqueue target.
Related errors
- Only QUEUED execution can be unqueued
- Execution '{executionId}' is not paused, can't resume it
- Execution must be terminated or paused and not killed to be
- Both `namespace` and `flowId` must be set when `executionId`
- `namespace` and `flowId` should only be set when `executionI
AI-assisted analysis of kestra-io/kestra@823fada927 (2026-08-14).
Data as JSON: /api/errors/5287926d765cc681.
Report an issue: GitHub.