Skip to content

Kubernetes Deployment

Deployment patterns

GOVERN Probe supports two Kubernetes deployment patterns:

PatternWhen to use
DaemonSetOne Probe per node. All pods on the node route through it.
SidecarOne Probe per pod. Tightest isolation, per-pod policies.

DaemonSet deployment

A DaemonSet runs one Probe replica on every node. Applications route to localhost:4020.

govern-probe-daemonset.yaml
apiVersion: apps/v1
kind: DaemonSet
metadata:
name: govern-probe
namespace: govern-system
labels:
app: govern-probe
spec:
selector:
matchLabels:
app: govern-probe
template:
metadata:
labels:
app: govern-probe
spec:
containers:
- name: govern-probe
image: archetypal/govern-probe:latest
ports:
- containerPort: 4020
hostPort: 4020
env:
- name: GOVERN_API_KEY
valueFrom:
secretKeyRef:
name: govern-secrets
key: api-key
- name: GOVERN_ORG_ID
valueFrom:
secretKeyRef:
name: govern-secrets
key: org-id
- name: UPSTREAM_URL
value: "https://api.anthropic.com"
- name: SCORING_MODE
value: "flag"
resources:
requests:
memory: "64Mi"
cpu: "100m"
limits:
memory: "256Mi"
cpu: "500m"
livenessProbe:
httpGet:
path: /healthz
port: 4020
initialDelaySeconds: 10
periodSeconds: 30
readinessProbe:
httpGet:
path: /readyz
port: 4020
initialDelaySeconds: 5
periodSeconds: 10
tolerations:
- key: node-role.kubernetes.io/control-plane
operator: Exists
effect: NoSchedule

Create the secret:

Terminal window
kubectl create namespace govern-system
kubectl create secret generic govern-secrets \
--namespace govern-system \
--from-literal=api-key=gvn_live_xxxx \
--from-literal=org-id=org_xxxx

Deploy:

Terminal window
kubectl apply -f govern-probe-daemonset.yaml
# Verify all nodes have a probe
kubectl get pods -n govern-system -o wide

Sidecar deployment

Inject the Probe as a sidecar container in your application pods.

my-app-deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
name: my-ai-app
spec:
replicas: 3
selector:
matchLabels:
app: my-ai-app
template:
spec:
containers:
# Your application container
- name: app
image: my-app:latest
env:
- name: ANTHROPIC_BASE_URL
value: "http://localhost:4020"
# GOVERN Probe sidecar
- name: govern-probe
image: archetypal/govern-probe:latest
ports:
- containerPort: 4020
env:
- name: GOVERN_API_KEY
valueFrom:
secretKeyRef:
name: govern-secrets
key: api-key
- name: GOVERN_ORG_ID
valueFrom:
secretKeyRef:
name: govern-secrets
key: org-id
- name: UPSTREAM_URL
value: "https://api.anthropic.com"
resources:
requests:
memory: "64Mi"
cpu: "50m"
limits:
memory: "128Mi"
cpu: "200m"

ConfigMap for YAML configuration

apiVersion: v1
kind: ConfigMap
metadata:
name: govern-probe-config
namespace: govern-system
data:
default.yaml: |
upstream:
url: https://api.anthropic.com
timeout_ms: 30000
scoring:
mode: flag
security:
enabled: true
threshold: 0.70
bias:
enabled: true
threshold: 0.60
telemetry:
flush_interval_ms: 5000
batch_size: 50

Mount in the DaemonSet:

volumeMounts:
- name: probe-config
mountPath: /app/config
readOnly: true
volumes:
- name: probe-config
configMap:
name: govern-probe-config

Horizontal Pod Autoscaler

For sidecar deployments, scale the application pod and the Probe scales with it automatically. For DaemonSet deployments, the Probe auto-scales with node count.

Network policies

Allow outbound from the Probe to the GOVERN telemetry API:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
name: govern-probe-egress
namespace: govern-system
spec:
podSelector:
matchLabels:
app: govern-probe
policyTypes:
- Egress
egress:
- to:
- ipBlock:
cidr: 0.0.0.0/0
ports:
- protocol: TCP
port: 443

Monitoring with Prometheus

The Probe exposes Prometheus metrics at /metrics. Scrape with a ServiceMonitor:

apiVersion: monitoring.coreos.com/v1
kind: ServiceMonitor
metadata:
name: govern-probe
namespace: govern-system
spec:
selector:
matchLabels:
app: govern-probe
endpoints:
- port: http
path: /metrics
interval: 15s