argoproj/argo-workflows · error
invalid ConcurrencyPolicy: %s
Error message
invalid ConcurrencyPolicy: %s
What it means
enforceRuntimePolicy validates spec.concurrencyPolicy on a CronWorkflow. Only AllowConcurrent, ForbidConcurrent, and ReplaceConcurrent are valid; any other string hits the switch's default and aborts this cron evaluation with this error.
Source
Thrown at workflow/cron/operator.go:287
case v1alpha1.AllowConcurrent, "":
// Do nothing
case v1alpha1.ForbidConcurrent:
if len(woc.cronWf.Status.Active) > 0 {
woc.metrics.CronWfPolicy(ctx, woc.cronWf.Name, woc.cronWf.Namespace, v1alpha1.ForbidConcurrent)
woc.log.Info(ctx, "'ConcurrencyPolicy: Forbid' and has an active Workflow so it was not run")
return false, nil
}
case v1alpha1.ReplaceConcurrent:
if len(woc.cronWf.Status.Active) > 0 {
woc.metrics.CronWfPolicy(ctx, woc.cronWf.Name, woc.cronWf.Namespace, v1alpha1.ReplaceConcurrent)
woc.log.Info(ctx, "'ConcurrencyPolicy: Replace' and has active Workflows")
err := woc.terminateOutstandingWorkflows(ctx)
if err != nil {
return false, err
}
}
default:
return false, fmt.Errorf("invalid ConcurrencyPolicy: %s", woc.cronWf.Spec.ConcurrencyPolicy)
}
}
return true, nil
}
func (woc *cronWfOperationCtx) terminateOutstandingWorkflows(ctx context.Context) error {
for _, wfObjectRef := range woc.cronWf.Status.Active {
woc.log.WithField("name", wfObjectRef.Name).Info(ctx, "stopping")
err := util.TerminateWorkflow(ctx, woc.wfClient, wfObjectRef.Name)
if err != nil {
if apierrors.IsNotFound(err) {
woc.log.WithField("name", wfObjectRef.Name).Warn(ctx, "workflow not found when trying to terminate outstanding workflows")
continue
}
if alreadyShutdownErr, ok := errors.AsType[util.AlreadyShutdownError](err); ok {
woc.log.Warn(ctx, alreadyShutdownErr.Error())
continue
}View on GitHub (pinned to 35bff19146)
Solutions
- Set concurrencyPolicy to one of: Allow, Forbid, Replace (or omit it)
- Run argo lint on the CronWorkflow to catch invalid enum values before submitting
- Fix the field with kubectl edit cronworkflow <name> or update the manifest
- Check CRD/schema version mismatch if a previously-valid value is now rejected
Example fix
// before spec: concurrencyPolicy: AllowConcurrent // after spec: concurrencyPolicy: Allow
Defensive patterns
Strategy: validation
Validate before calling
# valid values: Allow | Forbid | Replace (or omit)
kubectl get cronworkflow <name> -o jsonpath='{.spec.concurrencyPolicy}' Type guard
var valid = map[string]bool{"": true, "Allow": true, "Forbid": true, "Replace": true}
if !valid[policy] {
return fmt.Errorf("invalid ConcurrencyPolicy: %s", policy)
} Try / catch
canProceed, err := enforceRuntimePolicy(ctx)
if err != nil {
// fix spec.concurrencyPolicy in the CronWorkflow, then re-run
return canProceed, err
} Prevention
- Only use Allow, Forbid, or Replace in cronworkflow specs
- Run argo lint on CronWorkflow manifests in CI
- Don't copy concurrencyPolicy semantics from k8s CronJobs blindly
When it happens
Trigger: A CronWorkflow is submitted or updated with concurrencyPolicy set to something other than "", Allow, Forbid, or Replace — enforcement happens when the cron operator runs (run -> enforceRuntimePolicy).
Common situations: Typos like "AllowConcurrent" vs "Allow"; YAML written against Kubernetes CronJob semantics ("Forbid" works, but misspellings like "allowconcurrent" or "forbidden" do not); tooling generating invalid values.
Understand the failure class
Background: Invalid enum value errors: "Unknown type", "Invalid scope", "must be one of" — when a string is not on the library's allowed list — this error's family across 23 libraries.
Related errors
- cron schedules must consist of 5 values only
- cron schedules must consist of 5 values only
- error stopping workflow %s: %w
AI-assisted analysis of argoproj/argo-workflows@35bff19146 (2026-09-03).
Data as JSON: /api/errors/4b955a7ed4fb9ce0.
Report an issue: GitHub.