This critical error indicates your Kubernetes cluster's etcd database has exceeded its storage quota (default 2GB). etcd enters read-only mode, preventing any cluster modifications until space is reclaimed through compaction and defragmentation.
This error indicates that your Kubernetes cluster's etcd database has exceeded its configured storage quota limit, typically the default 2GB. etcd uses MVCC (Multi-Version Concurrent Control) to maintain a complete history of all key-value changes, never deleting old revisions automatically. When the database size reaches the quota, etcd enters a maintenance mode that only accepts read and delete operations, preventing any new writes to the cluster. The error occurs because etcd enforces a space quota to prevent the database from consuming unlimited disk space and degrading cluster performance. Without this quota, etcd would continue growing with every update to objects like Pods, Services, ConfigMaps, and Events, eventually exhausting your storage. Once the NOSPACE alarm is triggered, you cannot create or modify any Kubernetes objects—no deployments, no pods, no configuration changes—until the database space issue is resolved through compaction, defragmentation, and/or cleanup of accumulated objects.
Verify that the NOSPACE alarm is active. SSH into a control plane node and run:
ETCDCTL_API=3 etcdctl --endpoints=https://localhost:2379 \
--cacert=/etc/kubernetes/pki/etcd/ca.crt \
--cert=/etc/kubernetes/pki/etcd/server.crt \
--key=/etc/kubernetes/pki/etcd/server.key \
alarm listAlso check the etcd database size:
ETCDCTL_API=3 etcdctl --endpoints=https://localhost:2379 \
--cacert=/etc/kubernetes/pki/etcd/ca.crt \
--cert=/etc/kubernetes/pki/etcd/server.crt \
--key=/etc/kubernetes/pki/etcd/server.key \
endpoint status --write-out=json | jq '.[] | {endpoint, dbSize}'Compaction removes old versions of keys, freeing up logical space. First, get the current revision:
rev=$(ETCDCTL_API=3 etcdctl --endpoints=https://localhost:2379 \
--cacert=/etc/kubernetes/pki/etcd/ca.crt \
--cert=/etc/kubernetes/pki/etcd/server.crt \
--key=/etc/kubernetes/pki/etcd/server.key \
endpoint status --write-out="json" | jq '.[] | .revision')
echo "Current revision: $rev"Then compact to that revision:
ETCDCTL_API=3 etcdctl --endpoints=https://localhost:2379 \
--cacert=/etc/kubernetes/pki/etcd/ca.crt \
--cert=/etc/kubernetes/pki/etcd/server.crt \
--key=/etc/kubernetes/pki/etcd/server.key \
compact $revAfter compaction, defragment to return free space to the file system. For etcd v3.5.x, use etcdutl for offline defragmentation:
# Stop etcd pod first
kubectl -n kube-system delete pod etcd-<node-name> --ignore-not-found=true
# Perform offline defragmentation
ETCDCTL_API=3 etcdutl defrag --data-dir=/var/lib/etcdFor etcd v3.3 or v3.4, use online defragmentation:
ETCDCTL_API=3 etcdctl --endpoints=https://localhost:2379 \
--cacert=/etc/kubernetes/pki/etcd/ca.crt \
--cert=/etc/kubernetes/pki/etcd/server.crt \
--key=/etc/kubernetes/pki/etcd/server.key \
defrag --clusterAfter defragmentation, clear the NOSPACE alarm:
# Wait for etcd to be ready
sleep 30
# Disarm the alarm
ETCDCTL_API=3 etcdctl --endpoints=https://localhost:2379 \
--cacert=/etc/kubernetes/pki/etcd/ca.crt \
--cert=/etc/kubernetes/pki/etcd/server.crt \
--key=/etc/kubernetes/pki/etcd/server.key \
alarm disarmVerify alarms are cleared:
ETCDCTL_API=3 etcdctl --endpoints=https://localhost:2379 \
--cacert=/etc/kubernetes/pki/etcd/ca.crt \
--cert=/etc/kubernetes/pki/etcd/server.crt \
--key=/etc/kubernetes/pki/etcd/server.key \
alarm listThe output should be empty. Your cluster should now accept write operations.
Remove unnecessary objects that consume etcd space:
# Delete completed jobs
kubectl delete jobs --field-selector status.successful=1 -A
# Delete failed jobs
kubectl delete jobs --field-selector status.failed=1 -A
# Clean up evicted pods
kubectl get pods -A --field-selector=status.phase=Failed -o json | kubectl delete -f -
# Delete all events (use with caution)
kubectl delete event -A --allConfigure event TTL in the API server by editing /etc/kubernetes/manifests/kube-apiserver.yaml:
- --event-ttl=12hEdit /etc/kubernetes/manifests/etcd.yaml on each control plane node:
spec:
containers:
- name: etcd
command:
- etcd
- --auto-compaction-mode=periodic
- --auto-compaction-retention=1h
- --quota-backend-bytes=4294967296 # 4GBRestart etcd by deleting the static pod:
kubectl -n kube-system delete pod etcd-<node-name> --wait=falseThe --auto-compaction-retention=1h tells etcd to keep only 1 hour of history. Do not exceed 8GB for the quota—etcd performance degrades significantly above this threshold.
etcd's Multi-Version Concurrent Control mechanism stores every historical version of every key. This enables strong consistency guarantees but requires explicit cleanup through compaction. Deleting a key does not immediately free space; it only marks the key as deleted. Only compaction removes old revisions.
Recent etcd versions (v3.5.x) have data inconsistency bugs if defragmentation is interrupted. Use etcdutl for offline defragmentation instead of online defragmentation via etcdctl.
Monitor these Prometheus metrics to catch issues early:
- etcd_mvcc_db_total_size_in_use_in_bytes: Actual database size after compaction
- etcd_debugging_mvcc_db_total_size_in_bytes: Total size including fragmentation
- etcd_server_quota_backend_bytes: The configured quota
Set up alerts when the ratio of used space exceeds 70% of the quota.
The default 2GB quota is suitable for clusters with <5000 nodes. For larger clusters or high-churn environments, 4GB is recommended. Never exceed 8GB. If you regularly hit quota limits, investigate what's consuming space rather than just raising quotas.
Failed to connect to server: connection refused (HTTP/2)
How to fix "HTTP/2 connection refused" error in Kubernetes
No subnets found for EKS cluster
How to fix "eks subnet not found" in Kubernetes
missing request for cpu in container
How to fix "missing request for cpu in container" in Kubernetes HPA
unable to compute replica count
How to fix "unable to compute replica count" in Kubernetes HPA
error: context not found
How to fix "error: context not found" in Kubernetes