Skip to main content

Pod Configuration

Pod Security

KubeOpenCode applies a restricted security context by default to all agent containers, following the Kubernetes Pod Security Standards (Restricted profile).

Default Security Context

When no securityContext is specified in podSpec, the controller applies these defaults to all containers (init containers and the worker container):

  • allowPrivilegeEscalation: false
  • capabilities: drop: ["ALL"]
  • seccompProfile: type: RuntimeDefault

These defaults align with the Kubernetes Restricted Pod Security Standard and are suitable for most workloads.

Custom Container Security Context

Override the default security context for tighter or workload-specific settings using podSpec.securityContext:

apiVersion: kubeopencode.io/v1alpha1
kind: Agent
metadata:
name: hardened-agent
spec:
profile: "Security-hardened agent with strict container settings"
agentImage: ghcr.io/kubeopencode/kubeopencode-agent-opencode:latest
executorImage: ghcr.io/kubeopencode/kubeopencode-agent-devbox:latest
workspaceDir: /workspace
serviceAccountName: kubeopencode-agent
podSpec:
securityContext:
runAsNonRoot: true
allowPrivilegeEscalation: false
readOnlyRootFilesystem: true
capabilities:
drop:
- ALL
seccompProfile:
type: RuntimeDefault

Note: When using readOnlyRootFilesystem: true, ensure the agent image supports it. You may need to use emptyDir volumes for writable paths (e.g., /tmp, /home/agent).

Pod-Level Security Context

Use podSpec.podSecurityContext to configure security attributes that apply to the entire Pod (all containers):

apiVersion: kubeopencode.io/v1alpha1
kind: Agent
metadata:
name: uid-agent
spec:
profile: "Agent running as specific user and group"
agentImage: ghcr.io/kubeopencode/kubeopencode-agent-opencode:latest
executorImage: ghcr.io/kubeopencode/kubeopencode-agent-devbox:latest
workspaceDir: /workspace
serviceAccountName: kubeopencode-agent
podSpec:
podSecurityContext:
runAsUser: 1000
runAsGroup: 1000
fsGroup: 1000

podSecurityContext is useful for:

  • Enforcing a specific UID/GID for all containers
  • Setting fsGroup for shared volume permissions
  • Meeting namespace-level Pod Security Admission requirements

Advanced Pod Settings

Configure advanced Pod settings using podSpec:

apiVersion: kubeopencode.io/v1alpha1
kind: Agent
metadata:
name: advanced-agent
spec:
profile: "Advanced agent with gVisor isolation and GPU scheduling"
agentImage: ghcr.io/kubeopencode/kubeopencode-agent-opencode:latest
executorImage: ghcr.io/kubeopencode/kubeopencode-agent-devbox:latest
workspaceDir: /workspace
serviceAccountName: kubeopencode-agent
podSpec:
# Labels for NetworkPolicy, monitoring, etc.
labels:
network-policy: agent-restricted
# Enhanced isolation with gVisor or Kata
runtimeClassName: gvisor
# Scheduling configuration
scheduling:
nodeSelector:
node-type: ai-workload
tolerations:
- key: "dedicated"
operator: "Equal"
value: "ai-workload"
effect: "NoSchedule"

Extra Ports

Expose additional ports on the Agent's Service and Deployment using extraPorts. This is useful for Docker-in-Docker scenarios where containers inside the agent need to be accessible from outside — for example, web application UIs, VS Code server, or database ports.

apiVersion: kubeopencode.io/v1alpha1
kind: Agent
metadata:
name: dev-agent
spec:
profile: "Development agent with extra port exposure"
agentImage: ghcr.io/kubeopencode/kubeopencode-agent-opencode:latest
executorImage: ghcr.io/kubeopencode/kubeopencode-agent-devbox:latest
workspaceDir: /workspace
serviceAccountName: kubeopencode-agent
port: 4096
extraPorts:
- name: webapp
port: 3000
- name: vscode
port: 8080
- name: postgres
port: 5432
protocol: TCP

Each extra port is added to both the Deployment's container ports and the Agent's ClusterIP Service. Access them via:

# Port-forward individual ports
kubectl port-forward svc/dev-agent 3000:3000 8080:8080

# Open in browser
# http://localhost:3000 (webapp)
# http://localhost:8080 (vscode)

extraPorts can also be defined on AgentTemplate. When an Agent references a template, the Agent's extraPorts replaces the template's list (same merge strategy as credentials and contexts).

Extra Environment Variables

Inject custom environment variables into agent pod containers using podSpec.extraEnv (all containers) or podSpec.systemContainers (per-container-type targeting).

Global Extra Env (All Containers)

podSpec.extraEnv injects env vars into every container in the pod — all init containers and the executor container. These are appended after controller-managed env vars, so they can override controller defaults when necessary.

apiVersion: kubeopencode.io/v1alpha1
kind: Agent
metadata:
name: corp-agent
spec:
workspaceDir: /workspace
serviceAccountName: kubeopencode-agent
podSpec:
extraEnv:
# Plain value
- name: CORPORATE_REGISTRY
value: registry.corp.example.com
# From a Secret key
- name: NPM_TOKEN
valueFrom:
secretKeyRef:
name: npm-credentials
key: token
# From a ConfigMap key
- name: ENVIRONMENT
valueFrom:
configMapKeyRef:
name: cluster-config
key: environment

Per-Container-Type Overrides

podSpec.systemContainers provides fine-grained control over specific KubeOpenCode-managed containers. Use this when you need different env vars or volume mounts on specific container types.

Available container targets:

FieldContainerRole
openCodeInitopencode-initCopies OpenCode binary from agentImage to /tools
contextInitcontext-initCopies ConfigMap content into workspace
gitInitgit-init-*Clones Git repositories (all git-init containers)
gitSyncgit-sync-*Periodically syncs Git repos (HotReload policy sidecars)
pluginInitplugin-initInstalls OpenCode plugins via npm

OpenShift SCC Compatibility Fix

On OpenShift with restricted-v2 SCC, containers run with random UIDs that have no writable home directory in /etc/passwd. This caused git-init containers to crash with "failed to setup authentication: exit status 255" when trying to write ~/.gitconfig.

KubeOpenCode v0.1.2+ automatically sets HOME=/tmp and SHELL=/bin/bash on git-init and git-sync containers (the same fix already applied to the executor container since v0.1.0).

If you are running an older version or a custom system image, you can apply the fix via podSpec.systemContainers:

apiVersion: kubeopencode.io/v1alpha1
kind: AgentTemplate
metadata:
name: ocp-base
spec:
workspaceDir: /workspace
serviceAccountName: kubeopencode-agent
podSpec:
systemContainers:
gitInit:
extraEnv:
- name: HOME
value: /tmp
gitSync:
extraEnv:
- name: HOME
value: /tmp

Mounting Corporate CA Bundles into Git Containers

If your GitLab/GitHub uses a private CA that is not covered by caBundle (e.g., a different CA per container type), you can mount it specifically into git containers:

apiVersion: kubeopencode.io/v1alpha1
kind: Agent
metadata:
name: corp-git-agent
spec:
workspaceDir: /workspace
serviceAccountName: kubeopencode-agent
podSpec:
extraVolumes:
- name: corp-ca
configMap:
name: corp-ca-bundle
items:
- key: ca-certificates.crt
path: tls.crt
systemContainers:
gitInit:
extraEnv:
- name: HOME
value: /tmp
- name: GIT_SSL_CAINFO
value: /etc/ssl/corp/tls.crt
extraVolumeMounts:
- name: corp-ca
mountPath: /etc/ssl/corp
readOnly: true
gitSync:
extraEnv:
- name: HOME
value: /tmp
- name: GIT_SSL_CAINFO
value: /etc/ssl/corp/tls.crt
extraVolumeMounts:
- name: corp-ca
mountPath: /etc/ssl/corp
readOnly: true
# Also mount on the executor if needed
extraVolumeMounts:
- name: corp-ca
mountPath: /etc/ssl/corp
readOnly: true

Private npm Registry for Plugin Init

Inject npm authentication only into the plugin-init container without exposing it to the executor:

apiVersion: kubeopencode.io/v1alpha1
kind: Agent
metadata:
name: plugin-agent
spec:
workspaceDir: /workspace
serviceAccountName: kubeopencode-agent
plugins:
- name: "@corp/opencode-plugin@1.0.0"
podSpec:
systemContainers:
pluginInit:
extraEnv:
- name: NPM_TOKEN
valueFrom:
secretKeyRef:
name: npm-credentials
key: token
- name: NPM_CONFIG_REGISTRY
value: https://npm.corp.example.com

Merge Strategy with AgentTemplate

extraEnv and systemContainers live inside podSpec, which follows the same merge strategy as all other podSpec fields: Agent wins entirely if it defines a podSpec. If only the template defines podSpec, those values are inherited.

# Template defines base systemContainers
apiVersion: kubeopencode.io/v1alpha1
kind: AgentTemplate
metadata:
name: ocp-base
spec:
workspaceDir: /workspace
serviceAccountName: kubeopencode-agent
podSpec:
systemContainers:
gitInit:
extraEnv:
- name: HOME
value: /tmp

---
# Agent inherits the template's podSpec (including systemContainers)
# because Agent has no podSpec of its own
apiVersion: kubeopencode.io/v1alpha1
kind: Agent
metadata:
name: my-agent
spec:
templateRef:
name: ocp-base
# No podSpec here — template's podSpec is inherited in full

---
# Agent overrides podSpec entirely — must repeat systemContainers if needed
apiVersion: kubeopencode.io/v1alpha1
kind: Agent
metadata:
name: my-agent-custom
spec:
templateRef:
name: ocp-base
podSpec:
resources:
limits:
memory: "8Gi"
# Must re-declare systemContainers if template's values are still needed
systemContainers:
gitInit:
extraEnv:
- name: HOME
value: /tmp