# Langfuse v3 — minimal Kubernetes deployment for Langertha observability
#
# Deploys all required services in a single namespace.
# Pre-creates a project with known API keys so you can send data immediately.
#
# Usage:
# kubectl apply -f langfuse-k8s.yaml
# kubectl -n langfuse wait --for=condition=ready pod -l app=langfuse-web --timeout=300s
#
# Then use with Langertha:
# export LANGFUSE_PUBLIC_KEY=pk-lf-langertha
# export LANGFUSE_SECRET_KEY=sk-lf-langertha
# export LANGFUSE_URL=http://localhost:3000
# kubectl -n langfuse port-forward svc/langfuse-web 3000:3000 &
# perl ex/langfuse.pl
#
# With Cilium Gateway API (nip.io):
# export LANGFUSE_URL=http://langfuse.5.9.97.19.nip.io
#
# Dashboard: http://langfuse.5.9.97.19.nip.io (login: langertha@test.invalid / langertha)
---
apiVersion: v1
kind: Namespace
metadata:
name: langfuse
---
apiVersion: v1
kind: Secret
metadata:
name: langfuse-secrets
namespace: langfuse
stringData:
DATABASE_URL: "postgresql://postgres:langfuse@postgres:5432/langfuse"
POSTGRES_PASSWORD: "langfuse"
CLICKHOUSE_PASSWORD: "langfuse"
REDIS_AUTH: "langfuse"
MINIO_ROOT_USER: "minio"
MINIO_ROOT_PASSWORD: "miniosecret"
NEXTAUTH_SECRET: "langertha-nextauth-secret-change-in-production"
SALT: "langertha-salt-change-in-production"
ENCRYPTION_KEY: "0123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef"
# ============================================================
# PostgreSQL
# ============================================================
---
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
name: postgres-data
namespace: langfuse
spec:
storageClassName: local-path
accessModes: [ReadWriteOnce]
resources:
requests:
storage: 2Gi
---
apiVersion: apps/v1
kind: Deployment
metadata:
name: postgres
namespace: langfuse
spec:
replicas: 1
selector:
matchLabels:
app: postgres
template:
metadata:
labels:
app: postgres
spec:
containers:
- name: postgres
image: postgres:17
ports:
- containerPort: 5432
env:
- name: POSTGRES_USER
value: "postgres"
- name: POSTGRES_DB
value: "langfuse"
- name: POSTGRES_PASSWORD
valueFrom:
secretKeyRef:
name: langfuse-secrets
key: POSTGRES_PASSWORD
- name: TZ
value: "UTC"
- name: PGTZ
value: "UTC"
volumeMounts:
- name: data
mountPath: /var/lib/postgresql/data
readinessProbe:
exec:
command: ["pg_isready", "-U", "postgres"]
initialDelaySeconds: 5
periodSeconds: 5
resources:
requests:
memory: 256Mi
cpu: 100m
volumes:
- name: data
persistentVolumeClaim:
claimName: postgres-data
---
apiVersion: v1
kind: Service
metadata:
name: postgres
namespace: langfuse
spec:
selector:
app: postgres
ports:
- port: 5432
# ============================================================
# ClickHouse
# ============================================================
---
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
name: clickhouse-data
namespace: langfuse
spec:
storageClassName: local-path
accessModes: [ReadWriteOnce]
resources:
requests:
storage: 2Gi
---
apiVersion: apps/v1
kind: Deployment
metadata:
name: clickhouse
namespace: langfuse
spec:
replicas: 1
selector:
matchLabels:
app: clickhouse
template:
metadata:
labels:
app: clickhouse
spec:
containers:
- name: clickhouse
image: clickhouse/clickhouse-server
ports:
- containerPort: 8123
- containerPort: 9000
env:
- name: CLICKHOUSE_DB
value: "default"
- name: CLICKHOUSE_USER
value: "clickhouse"
- name: CLICKHOUSE_PASSWORD
valueFrom:
secretKeyRef:
name: langfuse-secrets
key: CLICKHOUSE_PASSWORD
volumeMounts:
- name: data
mountPath: /var/lib/clickhouse
readinessProbe:
httpGet:
path: /ping
port: 8123
initialDelaySeconds: 5
periodSeconds: 5
resources:
requests:
memory: 512Mi
cpu: 200m
volumes:
- name: data
persistentVolumeClaim:
claimName: clickhouse-data
---
apiVersion: v1
kind: Service
metadata:
name: clickhouse
namespace: langfuse
spec:
selector:
app: clickhouse
ports:
- name: http
port: 8123
- name: native
port: 9000
# ============================================================
# Redis
# ============================================================
---
apiVersion: apps/v1
kind: Deployment
metadata:
name: redis
namespace: langfuse
spec:
replicas: 1
selector:
matchLabels:
app: redis
template:
metadata:
labels:
app: redis
spec:
containers:
- name: redis
image: redis:7
command: ["redis-server", "--requirepass", "$(REDIS_AUTH)", "--maxmemory-policy", "noeviction"]
ports:
- containerPort: 6379
env:
- name: REDIS_AUTH
valueFrom:
secretKeyRef:
name: langfuse-secrets
key: REDIS_AUTH
readinessProbe:
exec:
command: ["redis-cli", "ping"]
initialDelaySeconds: 3
periodSeconds: 3
resources:
requests:
memory: 128Mi
cpu: 50m
---
apiVersion: v1
kind: Service
metadata:
name: redis
namespace: langfuse
spec:
selector:
app: redis
ports:
- port: 6379
# ============================================================
# MinIO (S3-compatible storage)
# ============================================================
---
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
name: minio-data
namespace: langfuse
spec:
storageClassName: local-path
accessModes: [ReadWriteOnce]
resources:
requests:
storage: 2Gi
---
apiVersion: apps/v1
kind: Deployment
metadata:
name: minio
namespace: langfuse
spec:
replicas: 1
selector:
matchLabels:
app: minio
template:
metadata:
labels:
app: minio
spec:
containers:
- name: minio
image: minio/minio
command: ["sh", "-c", "mkdir -p /data/langfuse && minio server --address :9000 --console-address :9001 /data"]
ports:
- containerPort: 9000
- containerPort: 9001
env:
- name: MINIO_ROOT_USER
valueFrom:
secretKeyRef:
name: langfuse-secrets
key: MINIO_ROOT_USER
- name: MINIO_ROOT_PASSWORD
valueFrom:
secretKeyRef:
name: langfuse-secrets
key: MINIO_ROOT_PASSWORD
volumeMounts:
- name: data
mountPath: /data
readinessProbe:
httpGet:
path: /minio/health/ready
port: 9000
initialDelaySeconds: 5
periodSeconds: 5
resources:
requests:
memory: 256Mi
cpu: 100m
volumes:
- name: data
persistentVolumeClaim:
claimName: minio-data
---
apiVersion: v1
kind: Service
metadata:
name: minio
namespace: langfuse
spec:
selector:
app: minio
ports:
- name: api
port: 9000
- name: console
port: 9001
# ============================================================
# Langfuse Worker
# ============================================================
---
apiVersion: apps/v1
kind: Deployment
metadata:
name: langfuse-worker
namespace: langfuse
spec:
replicas: 1
selector:
matchLabels:
app: langfuse-worker
template:
metadata:
labels:
app: langfuse-worker
spec:
containers:
- name: worker
image: langfuse/langfuse-worker:3
ports:
- containerPort: 3030
env:
- name: DATABASE_URL
valueFrom:
secretKeyRef:
name: langfuse-secrets
key: DATABASE_URL
- name: NEXTAUTH_URL
value: "http://langfuse-web:3000"
- name: SALT
valueFrom:
secretKeyRef:
name: langfuse-secrets
key: SALT
- name: ENCRYPTION_KEY
valueFrom:
secretKeyRef:
name: langfuse-secrets
key: ENCRYPTION_KEY
- name: CLICKHOUSE_MIGRATION_URL
value: "clickhouse://clickhouse:9000"
- name: CLICKHOUSE_URL
value: "http://clickhouse:8123"
- name: CLICKHOUSE_USER
value: "clickhouse"
- name: CLICKHOUSE_PASSWORD
valueFrom:
secretKeyRef:
name: langfuse-secrets
key: CLICKHOUSE_PASSWORD
- name: CLICKHOUSE_CLUSTER_ENABLED
value: "false"
- name: REDIS_HOST
value: "redis"
- name: REDIS_PORT
value: "6379"
- name: REDIS_AUTH
valueFrom:
secretKeyRef:
name: langfuse-secrets
key: REDIS_AUTH
- name: LANGFUSE_S3_EVENT_UPLOAD_BUCKET
value: "langfuse"
- name: LANGFUSE_S3_EVENT_UPLOAD_REGION
value: "auto"
- name: LANGFUSE_S3_EVENT_UPLOAD_ACCESS_KEY_ID
value: "minio"
- name: LANGFUSE_S3_EVENT_UPLOAD_SECRET_ACCESS_KEY
valueFrom:
secretKeyRef:
name: langfuse-secrets
key: MINIO_ROOT_PASSWORD
- name: LANGFUSE_S3_EVENT_UPLOAD_ENDPOINT
value: "http://minio:9000"
- name: LANGFUSE_S3_EVENT_UPLOAD_FORCE_PATH_STYLE
value: "true"
- name: LANGFUSE_S3_EVENT_UPLOAD_PREFIX
value: "events/"
- name: LANGFUSE_S3_MEDIA_UPLOAD_BUCKET
value: "langfuse"
- name: LANGFUSE_S3_MEDIA_UPLOAD_REGION
value: "auto"
- name: LANGFUSE_S3_MEDIA_UPLOAD_ACCESS_KEY_ID
value: "minio"
- name: LANGFUSE_S3_MEDIA_UPLOAD_SECRET_ACCESS_KEY
valueFrom:
secretKeyRef:
name: langfuse-secrets
key: MINIO_ROOT_PASSWORD
- name: LANGFUSE_S3_MEDIA_UPLOAD_ENDPOINT
value: "http://minio:9000"
- name: LANGFUSE_S3_MEDIA_UPLOAD_FORCE_PATH_STYLE
value: "true"
- name: LANGFUSE_S3_MEDIA_UPLOAD_PREFIX
value: "media/"
- name: LANGFUSE_S3_BATCH_EXPORT_ENABLED
value: "false"
- name: TELEMETRY_ENABLED
value: "false"
resources:
requests:
memory: 512Mi
cpu: 200m
---
apiVersion: v1
kind: Service
metadata:
name: langfuse-worker
namespace: langfuse
spec:
selector:
app: langfuse-worker
ports:
- port: 3030
# ============================================================
# Langfuse Web (with pre-configured project + API keys)
# ============================================================
---
apiVersion: apps/v1
kind: Deployment
metadata:
name: langfuse-web
namespace: langfuse
spec:
replicas: 1
selector:
matchLabels:
app: langfuse-web
template:
metadata:
labels:
app: langfuse-web
spec:
containers:
- name: web
image: langfuse/langfuse:3
ports:
- containerPort: 3000
env:
- name: DATABASE_URL
valueFrom:
secretKeyRef:
name: langfuse-secrets
key: DATABASE_URL
- name: NEXTAUTH_URL
value: "http://langfuse.5.9.97.19.nip.io"
- name: NEXTAUTH_SECRET
valueFrom:
secretKeyRef:
name: langfuse-secrets
key: NEXTAUTH_SECRET
- name: SALT
valueFrom:
secretKeyRef:
name: langfuse-secrets
key: SALT
- name: ENCRYPTION_KEY
valueFrom:
secretKeyRef:
name: langfuse-secrets
key: ENCRYPTION_KEY
- name: CLICKHOUSE_MIGRATION_URL
value: "clickhouse://clickhouse:9000"
- name: CLICKHOUSE_URL
value: "http://clickhouse:8123"
- name: CLICKHOUSE_USER
value: "clickhouse"
- name: CLICKHOUSE_PASSWORD
valueFrom:
secretKeyRef:
name: langfuse-secrets
key: CLICKHOUSE_PASSWORD
- name: CLICKHOUSE_CLUSTER_ENABLED
value: "false"
- name: REDIS_HOST
value: "redis"
- name: REDIS_PORT
value: "6379"
- name: REDIS_AUTH
valueFrom:
secretKeyRef:
name: langfuse-secrets
key: REDIS_AUTH
- name: LANGFUSE_S3_EVENT_UPLOAD_BUCKET
value: "langfuse"
- name: LANGFUSE_S3_EVENT_UPLOAD_REGION
value: "auto"
- name: LANGFUSE_S3_EVENT_UPLOAD_ACCESS_KEY_ID
value: "minio"
- name: LANGFUSE_S3_EVENT_UPLOAD_SECRET_ACCESS_KEY
valueFrom:
secretKeyRef:
name: langfuse-secrets
key: MINIO_ROOT_PASSWORD
- name: LANGFUSE_S3_EVENT_UPLOAD_ENDPOINT
value: "http://minio:9000"
- name: LANGFUSE_S3_EVENT_UPLOAD_FORCE_PATH_STYLE
value: "true"
- name: LANGFUSE_S3_EVENT_UPLOAD_PREFIX
value: "events/"
- name: LANGFUSE_S3_MEDIA_UPLOAD_BUCKET
value: "langfuse"
- name: LANGFUSE_S3_MEDIA_UPLOAD_REGION
value: "auto"
- name: LANGFUSE_S3_MEDIA_UPLOAD_ACCESS_KEY_ID
value: "minio"
- name: LANGFUSE_S3_MEDIA_UPLOAD_SECRET_ACCESS_KEY
valueFrom:
secretKeyRef:
name: langfuse-secrets
key: MINIO_ROOT_PASSWORD
- name: LANGFUSE_S3_MEDIA_UPLOAD_ENDPOINT
value: "http://minio:9000"
- name: LANGFUSE_S3_MEDIA_UPLOAD_FORCE_PATH_STYLE
value: "true"
- name: LANGFUSE_S3_MEDIA_UPLOAD_PREFIX
value: "media/"
- name: LANGFUSE_S3_BATCH_EXPORT_ENABLED
value: "false"
- name: TELEMETRY_ENABLED
value: "false"
# Pre-create project with known API keys — no UI setup needed
- name: LANGFUSE_INIT_ORG_ID
value: "langertha-org"
- name: LANGFUSE_INIT_ORG_NAME
value: "Langertha"
- name: LANGFUSE_INIT_PROJECT_ID
value: "langertha-project"
- name: LANGFUSE_INIT_PROJECT_NAME
value: "Langertha Dev"
- name: LANGFUSE_INIT_PROJECT_PUBLIC_KEY
value: "pk-lf-langertha"
- name: LANGFUSE_INIT_PROJECT_SECRET_KEY
value: "sk-lf-langertha"
- name: LANGFUSE_INIT_USER_EMAIL
value: "langertha@test.invalid"
- name: LANGFUSE_INIT_USER_NAME
value: "Langertha"
- name: LANGFUSE_INIT_USER_PASSWORD
value: "langertha"
readinessProbe:
httpGet:
path: /api/public/health
port: 3000
initialDelaySeconds: 30
periodSeconds: 10
resources:
requests:
memory: 512Mi
cpu: 200m
---
apiVersion: v1
kind: Service
metadata:
name: langfuse-web
namespace: langfuse
spec:
selector:
app: langfuse-web
ports:
- port: 3000
targetPort: 3000
# ============================================================
# Cilium Gateway API — HTTPRoute for langfuse.5.9.97.19.nip.io
# ============================================================
---
apiVersion: gateway.networking.k8s.io/v1
kind: HTTPRoute
metadata:
name: langfuse
namespace: langfuse
spec:
parentRefs:
- name: cilium-gateway
namespace: kube-system
hostnames:
- "langfuse.5.9.97.19.nip.io"
rules:
- matches:
- path:
type: PathPrefix
value: /
backendRefs:
- name: langfuse-web
port: 3000
---
apiVersion: gateway.networking.k8s.io/v1beta1
kind: ReferenceGrant
metadata:
name: allow-langfuse-gateway
namespace: kube-system
spec:
from:
- group: gateway.networking.k8s.io
kind: HTTPRoute
namespace: langfuse
to:
- group: ""
kind: Gateway