What's Actually Happening

ResourceQuota sets hard limits on resources a namespace can consume. When you try to create a pod, deployment, or other resource and the namespace has exceeded its quota, Kubernetes rejects the request.

The Error You'll See

bash
$ kubectl apply -f deployment.yaml
Error from server (Forbidden): error when creating "deployment.yaml": deployments.apps "my-app" is forbidden: exceeded quota: compute-quota, requested: requests.cpu=500m,requests.memory=512Mi, used: requests.cpu=4,requests.memory=8Gi, limited: requests.cpu=4,requests.memory=8Gi

Or for pods:

bash
$ kubectl run test --image=nginx
Error from server (Forbidden): pods "test" is forbidden: exceeded quota: compute-quota, requested: pods=1, used: pods=10, limited: pods=10

Why This Happens

  1. 1.CPU quota exhausted - Namespace used all allocated CPU
  2. 2.Memory quota exhausted - Namespace used all allocated memory
  3. 3.Pod count limit reached - Maximum pods count reached
  4. 4.Storage quota exceeded - PVC requests exceed storage quota
  5. 5.Object count limits - Too many deployments, services, secrets

Step 1: Check Current Quota

bash
kubectl get quota -n my-namespace
kubectl describe quota compute-quota -n my-namespace

Shows:

bash
Name:            compute-quota
Namespace:       my-namespace
Resource         Used    Hard
--------         ----    ----
cpu              4000m   4000m
memory           8Gi     8Gi
pods             10      10
requests.cpu     4000m   4000m
requests.memory  8Gi     8Gi
limits.cpu       8       8
limits.memory    16Gi    16Gi

Compare Used vs Hard - if equal, quota exhausted.

Step 2: List All ResourceQuotas in Namespace

bash
kubectl get quota -n my-namespace

Multiple quotas may exist:

bash
NAME              AGE
compute-quota     10d
storage-quota     10d
object-count      10d

Step 3: Check Resource Usage

```bash # See all pods and their resources kubectl get pods -n my-namespace -o custom-columns=NAME:.metadata.name,CPU:.spec.containers[*].resources.requests.cpu,MEMORY:.spec.containers[*].resources.requests.memory

# Top pods by resource usage kubectl top pods -n my-namespace ```

Step 4: Delete Unused Resources

Free up quota by removing unused resources:

```bash # List all resources kubectl get all -n my-namespace

# Delete failed or completed pods kubectl delete pod failed-pod -n my-namespace

# Delete unused deployments kubectl delete deployment old-app -n my-namespace

# Clean up completed jobs kubectl delete job completed-job -n my-namespace ```

Step 5: Reduce Pod Resource Requests

If pods request too many resources:

bash
kubectl get deployment my-app -n my-namespace -o yaml | grep -A10 resources

Shows:

yaml
resources:
  requests:
    cpu: "500m"    # Maybe too much
    memory: "512Mi"

Reduce requests:

yaml
resources:
  requests:
    cpu: "100m"    # Lower request
    memory: "256Mi"
  limits:
    cpu: "200m"
    memory: "512Mi"

Apply:

bash
kubectl apply -f deployment.yaml

Step 6: Increase Quota Limits

Edit the ResourceQuota to increase limits:

bash
kubectl edit quota compute-quota -n my-namespace

Increase values:

yaml
spec:
  hard:
    cpu: "8"            # Increase from 4
    memory: "16Gi"      # Increase from 8Gi
    pods: "20"          # Increase from 10
    requests.cpu: "8"
    requests.memory: "16Gi"

Or create updated quota:

yaml
apiVersion: v1
kind: ResourceQuota
metadata:
  name: compute-quota
  namespace: my-namespace
spec:
  hard:
    cpu: "8"
    memory: "16Gi"
    pods: "20"
bash
kubectl apply -f quota.yaml

Step 7: Check Cluster Resource Availability

Before increasing quota, verify cluster has capacity:

bash
kubectl describe nodes | grep -A5 "Allocated resources"
kubectl top nodes

If cluster is full, increasing quota won't help - pods will stay Pending.

Step 8: Create New Namespace with Quota

If namespace quota is permanently insufficient:

```bash # Create new namespace kubectl create namespace app-production

# Set appropriate quota kubectl create quota prod-quota --namespace=app-production --hard=cpu=16,memory=32Gi,pods=50

# Deploy to new namespace kubectl apply -f deployment.yaml -n app-production ```

Step 9: Check Object Count Quotas

For quotas limiting object counts:

bash
kubectl describe quota object-count -n my-namespace

Shows:

bash
Name:            object-count
Resource         Used  Hard
configmaps       15    20
secrets          10    20
services         5     10
replicationcontrollers 0  10

Clean up unused objects:

bash
kubectl delete configmap unused-config -n my-namespace
kubectl delete secret old-secret -n my-namespace

Verify the Fix

After reducing usage or increasing quota:

```bash # Check quota status kubectl describe quota compute-quota -n my-namespace

# Used should be less than Hard

# Create resource kubectl apply -f deployment.yaml # Should succeed

# Check pods running kubectl get pods -n my-namespace ```

Prevention Tips

When setting up quotas:

```yaml # Use realistic limits hard: cpu: "8" memory: "16Gi" pods: "20"

# Track usage kubectl top pods -n my-namespace

# Set up alerts for quota approaching limit # Prometheus: (kube_resourcequota_used / kube_resourcequota_hard) > 0.9 ```