Platform setup
How to Deploy OpenClaw on Kubernetes
Browse more in Platform setup.
All platform setup guides →This guide walks you through how to deploy OpenClaw on Kubernetes using the official kustomize-based manifests and helper scripts. You’ll go from a bare cluster to a running OpenClaw gateway reachable via kubectl port-forward, with secrets and persistent storage wired up.
By the end, you’ll know how to customize agents, gateway config, providers, namespaces, and images for your own cluster.
Prerequisites
- ✓A running Kubernetes cluster (AKS, EKS, GKE, k3s, kind, OpenShift, etc.).
- ✓`kubectl` connected to your cluster.
- ✓An API key for at least one model provider (ANTHROPIC, GEMINI, OPENAI, or OPENROUTER).
Steps
- 1
Create a local Kind cluster for testing (optional)
If you don’t already have a Kubernetes cluster, you can spin up a local one with Kind using the helper script. This is useful to validate your OpenClaw manifests before touching a shared or production cluster.
bash./scripts/k8s/create-kind.sh # auto-detects docker or podman ./scripts/k8s/create-kind.sh --delete # tear down - 2
Export your model provider API key
OpenClaw needs at least one model provider key to start doing useful work. Export the provider-specific API key in your shell so the deploy script can create or update the Kubernetes Secret correctly.
bash# Replace with your provider: ANTHROPIC, GEMINI, OPENAI, or OPENROUTER export <PROVIDER>_API_KEY="..." - 3
Deploy OpenClaw with the helper script
Use the deploy script to create the namespace, secrets, and core resources via kustomize. Option A is the simplest path, while Option B gives you an explicit secret-creation step if you want more control over when secrets change.
bash# Option A — API key in environment (one step): # Replace with your provider: ANTHROPIC, GEMINI, OPENAI, or OPENROUTER export <PROVIDER>_API_KEY="..." ./scripts/k8s/deploy.sh # Option B — create the secret separately: export <PROVIDER>_API_KEY="..." ./scripts/k8s/deploy.sh --create-secret ./scripts/k8s/deploy.sh - 4
Retrieve the gateway token for the Control UI
The deploy script sets up token-based auth for the gateway by default, so you need the generated token to log into the Control UI. You can either print it directly during deploy for local debugging or read it from the Kubernetes Secret afterward.
bashkubectl get secret openclaw-secrets -n openclaw -o jsonpath='{.data.OPENCLAW_GATEWAY_TOKEN}' | base64 -d - 5
Access the OpenClaw gateway via port-forward
By default the gateway binds to loopback inside the pod, so you reach it using kubectl port-forward from your machine. This keeps the Control UI on a safer local-access path while you experiment.
bashkubectl port-forward svc/openclaw 18789:18789 -n openclaw open http://localhost:18789 - 6
Customize agents and gateway configuration
Once the base deployment works, you can edit the agent instructions and gateway config baked into the ConfigMap. json in the manifests, re-run the deploy script so Kubernetes picks up the new configuration.
bash## Edit AGENTS.md in scripts/k8s/manifests/configmap.yaml, then: ./scripts/k8s/deploy.sh - 7
Add additional model providers
You can enable multiple providers by exporting more API keys and recreating the secret. The script preserves existing provider keys unless you overwrite them, so you can safely add providers incrementally.
bashexport ANTHROPIC_API_KEY="..." export OPENAI_API_KEY="..." ./scripts/k8s/deploy.sh --create-secret ./scripts/k8s/deploy.sh - 8
Use a custom namespace or image when needed
If you don’t want to deploy into the default openclaw namespace or you need to pin a specific image, the manifests support both. Set OPENCLAW_NAMESPACE inline when running the deploy script, and edit the image field in the deployment manifest when you want to change the container image.
bashOPENCLAW_NAMESPACE=my-namespace ./scripts/k8s/deploy.sh # In scripts/k8s/manifests/deployment.yaml image: ghcr.io/openclaw/openclaw:latest # or pin to a specific version from https://github.com/openclaw/openclaw/releases - 9
Tear down the OpenClaw namespace when you’re done
When you want to remove OpenClaw from the cluster, use the delete flag on the deploy script. This cleans up the namespace and all resources in it, including the persistent volume claim.
bash./scripts/k8s/deploy.sh --delete
Configuration
| Option | Description | Example |
|---|---|---|
| <PROVIDER>_API_KEY | API key for a supported model provider such as ANTHROPIC, GEMINI, OPENAI, or OPENROUTER; used by the deploy script to populate the Kubernetes Secret. | ANTHROPIC_API_KEY |
| ANTHROPIC_API_KEY | Anthropic provider API key stored in the openclaw-secrets Secret for Anthropic-backed models. | ANTHROPIC_API_KEY="sk-ant-api03-..." |
| OPENAI_API_KEY | OpenAI provider API key stored in the openclaw-secrets Secret for OpenAI-backed models. | OPENAI_API_KEY="sk-openai-..." |
| OPENCLAW_NAMESPACE | Overrides the default Kubernetes namespace (openclaw) where all OpenClaw resources are created. | OPENCLAW_NAMESPACE=my-namespace |
| OPENCLAW_GATEWAY_TOKEN | Shared secret used for gateway token auth, stored in the openclaw-secrets Secret and required by the Control UI. | OPENCLAW_GATEWAY_TOKEN="long-random-token" |
Troubleshooting
You can’t reach the Control UI through a Service or Ingress even though the pod is running.
The gateway binds to loopback inside the pod by default, which only works with kubectl port-forward. yaml from loopback to a non-loopback bind that matches your deployment model, then redeploy and expose it through an Ingress or load balancer.
./scripts/k8s/deploy.shAfter adding a new provider API key, OpenClaw still behaves as if the provider is missing.
The running pod may still use the old Secret data. Re-run the deploy script with --create-secret to update the Secret, then redeploy so the pod picks up the new keys, or patch the Secret directly and restart the deployment.
kubectl patch secret openclaw-secrets -n openclaw \
-p '{"stringData":{"<PROVIDER>_API_KEY":"..."}}'
kubectl rollout restart deployment/openclaw -n openclawYou forgot the gateway token and can’t authenticate to the Control UI.
The deploy script stores the token in the openclaw-secrets Secret. Retrieve it by reading the OPENCLAW_GATEWAY_TOKEN field and decoding it from base64.
kubectl get secret openclaw-secrets -n openclaw -o jsonpath='{.data.OPENCLAW_GATEWAY_TOKEN}' | base64 -dYou want to reset everything, including persistent data, but resources still linger in the cluster.
Use the deploy script with the --delete flag to remove the namespace and all resources, including the PVC. This gives you a clean slate for a fresh deployment.
./scripts/k8s/deploy.sh --deleteFrequently asked questions
Powered by Mem0
Add persistent memory to OpenClaw
Official Mem0 plugin for OpenClaw keeps context across chats and tools. Smaller prompts, lower cost, better continuity for your agents.