Prerequisites

  • A running Kubernetes cluster (minikube, kind, EKS, GKE, or AKS)
  • kubectl configured and pointing to your cluster
  • OpenClaw Docker image built and pushed to a registry
  • A Kubernetes secrets store or External Secrets Operator for API keys

Deployment Manifest

# openclaw-deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
  name: openclaw
  labels:
    app: openclaw
spec:
  replicas: 2
  selector:
    matchLabels:
      app: openclaw
  strategy:
    type: RollingUpdate
    rollingUpdate:
      maxSurge: 1
      maxUnavailable: 0        # Zero downtime
  template:
    metadata:
      labels:
        app: openclaw
    spec:
      securityContext:
        runAsNonRoot: true
        runAsUser: 1000
      containers:
        - name: openclaw
          image: ghcr.io/openclaw-ai/openclaw:1.5.2
          ports:
            - containerPort: 8080
          envFrom:
            - configMapRef:
                name: openclaw-config
          env:
            - name: OPENAI_API_KEY
              valueFrom:
                secretKeyRef:
                  name: openclaw-secrets
                  key: openai-api-key
          resources:
            requests:
              cpu: "250m"
              memory: "256Mi"
            limits:
              cpu: "1000m"
              memory: "1Gi"
          readinessProbe:
            httpGet:
              path: /health
              port: 8080
            initialDelaySeconds: 10
            periodSeconds: 10
          livenessProbe:
            httpGet:
              path: /health
              port: 8080
            initialDelaySeconds: 30
            periodSeconds: 30

ConfigMap and Secrets

# openclaw-config.yaml
apiVersion: v1
kind: ConfigMap
metadata:
  name: openclaw-config
data:
  OPENCLAW_ENV: "production"
  REDIS_URL: "redis://redis-service:6379/0"
  OPENCLAW_LOG_LEVEL: "INFO"
  OPENCLAW_MAX_WORKERS: "4"
---
# Create secret imperatively (never store secrets in YAML files in git)
# kubectl create secret generic openclaw-secrets #   --from-literal=openai-api-key="sk-..." #   --from-literal=db-password="$(openssl rand -base64 32)"
Never commit secrets to Git. Use kubectl create secret imperatively, or use External Secrets Operator to sync from Vault/AWS SM/GCP SM. See Secrets Management.

Service and Ingress

# openclaw-service.yaml
apiVersion: v1
kind: Service
metadata:
  name: openclaw-service
spec:
  selector:
    app: openclaw
  ports:
    - port: 80
      targetPort: 8080
  type: ClusterIP
---
# openclaw-ingress.yaml
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: openclaw-ingress
  annotations:
    cert-manager.io/cluster-issuer: letsencrypt-prod
    nginx.ingress.kubernetes.io/rate-limit: "100"  # 100 req/min per IP
spec:
  tls:
    - hosts: ["api.yourcompany.com"]
      secretName: openclaw-tls
  rules:
    - host: api.yourcompany.com
      http:
        paths:
          - path: /
            pathType: Prefix
            backend:
              service:
                name: openclaw-service
                port:
                  number: 80

Horizontal Pod Autoscaling

Automatically scale OpenClaw pods based on CPU utilization or custom metrics like queue depth:

apiVersion: autoscaling/v2
kind: HorizontalPodAutoscaler
metadata:
  name: openclaw-hpa
spec:
  scaleTargetRef:
    apiVersion: apps/v1
    kind: Deployment
    name: openclaw
  minReplicas: 2
  maxReplicas: 10
  metrics:
    - type: Resource
      resource:
        name: cpu
        target:
          type: Utilization
          averageUtilization: 70
# Apply all manifests
kubectl apply -f openclaw-deployment.yaml
kubectl apply -f openclaw-config.yaml
kubectl apply -f openclaw-service.yaml
kubectl apply -f openclaw-ingress.yaml
kubectl apply -f openclaw-hpa.yaml

# Watch rollout status
kubectl rollout status deployment/openclaw

# Check pods are running
kubectl get pods -l app=openclaw

Redis on Kubernetes

The recommended approach is to use a managed Redis (ElastiCache, Memorystore) rather than running Redis in K8s. If you need in-cluster Redis:

# Install Redis via Helm (Bitnami chart)
helm repo add bitnami https://charts.bitnami.com/bitnami
helm install redis bitnami/redis   --set auth.enabled=false   --set master.persistence.size=8Gi   --set replica.replicaCount=1

Troubleshooting K8s Deployments

# Pod is in CrashLoopBackOff — check logs
kubectl logs -l app=openclaw --previous

# Pod is Pending — check resource constraints
kubectl describe pod -l app=openclaw

# Check all events
kubectl get events --sort-by=.metadata.creationTimestamp

# Exec into a running pod for debugging
kubectl exec -it deployment/openclaw -- /bin/bash

Kubernetes Deployment Architecture

A production OpenClaw deployment on Kubernetes uses a Deployment resource with a defined replica count, resource requests and limits, a liveness probe to detect stuck processes, and a readiness probe to prevent traffic from reaching pods that haven't finished initializing. For batch or scheduled workloads, use a CronJob resource instead of a Deployment. Configure horizontal pod autoscaling (HPA) based on CPU utilization or custom metrics from your monitoring system — scale up when task queue depth grows, scale down during idle periods to conserve resources and costs.

Namespace isolation is important for multi-tenant deployments. Run each OpenClaw agent in its own namespace and use NetworkPolicies to restrict pod-to-pod communication — by default, allow no ingress from other namespaces and only the specific egress endpoints the agent needs. This prevents a compromised agent from laterally moving to other agents or infrastructure components in the cluster. Use RBAC to give each agent's service account only the Kubernetes API permissions it needs — most agents need no Kubernetes API access at all and should run with a service account that has zero cluster permissions.

Secrets Management in Kubernetes

Kubernetes Secrets are base64-encoded, not encrypted, by default. Enable encryption at rest for secrets in your cluster (using KMS-based encryption providers in EKS, GKE, and AKS). Better yet, use an external secrets operator (External Secrets Operator with AWS Secrets Manager, Vault Agent Injector, or Sealed Secrets) to pull credentials from a dedicated secrets management system rather than storing them as Kubernetes objects at all. External secrets management provides a central audit log, rotation support, and a security boundary between the secrets store and the Kubernetes cluster that protects credentials even if cluster credentials are compromised.

Rolling Updates and Rollbacks

Configure your Deployment's rolling update strategy to limit disruption during updates. Set maxUnavailable: 0 and maxSurge: 1 for zero-downtime deployments — Kubernetes brings up the new pod before terminating the old one, ensuring continuous availability. Test rollback procedures before you need them: kubectl rollout undo deployment/openclaw-agent reverts to the previous deployment configuration. For critical agents, set a deployment pause with kubectl rollout pause to canary test the new version with a fraction of traffic before completing the rollout. The combination of zero-downtime updates and tested rollback procedures makes production deployments far less stressful events.

Quick Start Manifests

Start with a minimal production manifest: a Deployment with 2 replicas, resource requests of 100m CPU and 256Mi memory, limits of 500m CPU and 512Mi memory, a liveness probe hitting the agent's health endpoint every 30 seconds, and a ConfigMap for non-secret configuration. Store the manifest in the same Git repository as your agent code so that deployment changes go through code review alongside code changes. Apply with kubectl apply -f deployment.yaml and monitor rollout status with kubectl rollout status deployment/openclaw-agent.