ArgoCD: another operation is already in progress — operation deadlock
Fix the operation deadlock in ArgoCD when a stuck operation blocks all sync attempts with another operation is already in progress.
This runbook is part of a series on ArgoCD sync failures. See also: etcd request too large and HPA OutOfSync loop. For broader GitOps context, read our post on GitOps and ArgoCD.
Symptoms
ArgoCD refuses to sync — every attempt fails with:
# ArgoCD refuses to sync — operation lock is stuck
argocd app sync <APP_NAME>
# FATA[0001] rpc error: code = FailedPrecondition
# desc = another operation is already in progress
# Check the stuck operation
kubectl get application <APP_NAME> -n argocd \
-o jsonpath='{.status.operationState.phase}'
# Output: "Running" (but nothing is actually running)
The Application is locked — no new sync can be started, manually or automatically. ArgoCD UI shows a spinning icon with no actual progress.
Cause
ArgoCD implements pessimistic locking — one Application can have only one active sync operation at a time. Operation state is stored in .status.operationState in the Application CRD. If the controller crashes (pod restart, OOMKill, node preemption) during sync, the operation remains in Running state even though no process is handling it.
This is a deadlock — ArgoCD can’t start a new operation because the “old” operation never completed. The problem is common in clusters with aggressive node autoscaling or with limited resources for application-controller (too small memory limit leads to OOMKill).
Fix
A) Remove the operation state (fastest fix):
# Remove the operation state that's causing the lock
kubectl patch application <APP_NAME> -n argocd --type json -p '[
{"op": "remove", "path": "/status/operationState"}
]'
# Alternative: remove via annotation if patch fails
kubectl annotate application <APP_NAME> -n argocd \
argocd.argoproj.io/refresh- \
argocd.argoproj.io/operation-
B) Force-terminate the operation via ArgoCD CLI:
# Terminate the stuck operation
argocd app terminate-op <APP_NAME>
# Wait 10 seconds, then force a fresh sync
sleep 10
argocd app sync <APP_NAME> --force --replace
C) Restart application-controller (nuclear option):
If the problem affects multiple Applications simultaneously or the above solutions don’t work:
# If individual app fixes don't work, restart the controller
# This clears ALL in-flight operations across all Applications
kubectl rollout restart statefulset argocd-application-controller -n argocd
# Monitor controller startup
kubectl logs -f statefulset/argocd-application-controller -n argocd | \
grep -i "sync\|operation"
# Verify all apps recover
argocd app list --output json | \
jq '.[] | select(.status.sync.status != "Synced") | .metadata.name'
After restart, the controller will automatically run a reconciliation loop for all Applications and pick up stalled operations. Monitor logs for a few minutes to confirm no Application returns to deadlock state.
Prevention: To avoid deadlocks in the future, ensure application-controller has sufficient resources (recommended minimum: 512 Mi memory limit for clusters with <50 Applications, 1-2 Gi for larger ones). Consider also setting --operation-processors and --status-processors in the controller arguments to control the number of parallel sync operations.
Validation
# 1. Verify no stuck operations
argocd app get <APP_NAME> --output json | jq '.status.operationState.phase'
# Expected: "Succeeded" or null
# 2. Verify sync status is Synced
argocd app get <APP_NAME> --output json | jq '.status.sync.status'
# Expected: "Synced"
# 3. Verify health status
argocd app get <APP_NAME> --output json | jq '.status.health.status'
# Expected: "Healthy"
# 4. Try a manual sync to confirm lock is cleared
argocd app sync <APP_NAME>
# Expected: sync completes without "another operation" error
# 5. Check controller logs for recurring errors
kubectl logs statefulset/argocd-application-controller -n argocd \
--since=5m | grep -c "error"
# Expected: 0 or minimal
If sync completes without the “another operation is already in progress” error, the deadlock is resolved. Monitor for a few minutes to confirm the problem doesn’t recur (which could indicate repeated controller OOMKills).
CI/CD pipeline blocking your team?
Book a free 30-minute call. We'll review your ArgoCD configuration and pinpoint what to fix right away.