prole/monitoring/kps-values-k3s.yaml
chrisfu 885fa99a29 feat(auth): add Google Workspace OAuth (prole.org) for Grafana + Supabase Studio
- monitoring/kps-values-k3s.yaml: Grafana helm values for k3s homelab with
  dual auth (auth.proxy Kerberos + auth.google for prole.org Workspace)
- grafana-proxy-configmap.yaml: nginx passthrough for /grafana/login/google
  and /grafana/login to allow Google OAuth flow without knoe-auth redirect
- grafana-google-oidc-secret-prole.example.yaml: Secret template for Grafana
  Google OAuth client (svc.prole.org, Internal consent, prole.org Workspace)
- oauth2-proxy-google-oidc-secret-prole.example.yaml: Secret template for
  oauth2-proxy gating db.prole.org Studio
- oauth2-proxy-deployment-prole.yaml: k3s oauth2-proxy deployment for
  db.prole.org (prole.org domain, no BackendConfig)
- init_grafana_oauth_prole.sh: Bootstrap script for Grafana OAuth secret
- init_oauth2_proxy_prole.sh: Bootstrap script for Studio oauth2-proxy

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-06 16:22:49 -04:00

147 lines
4.4 KiB
YAML

# kube-prometheus-stack (kps) Helm values — k3s deploy mode (prole.org homelab).
#
# Apply with:
# helm upgrade kps prometheus-community/kube-prometheus-stack \
# --namespace monitoring \
# -f monitoring/kps-values-k3s.yaml
#
# Auth model:
# - Kerberos/knoe-auth users arrive via grafana-proxy nginx with X-WEBAUTH-USER
# header → Grafana auth.proxy auto-login (no password prompt).
# - Google Workspace users (chrisfu@prole.org etc.) use auth.google sign-in
# button on the Grafana login page. The grafana-proxy nginx passes login
# paths through unauthenticated so the OAuth flow can complete.
# - chrisfu@prole.org → Admin; all other @prole.org users → Editor.
# - Local break-glass login (adminPassword) remains available.
#
# Storage: uses local-path (k3s Rancher default). Override storageClassName if
# the homelab has a different provisioner (NFS, Longhorn, etc.).
---
alertmanager:
alertmanagerSpec:
nodeSelector:
prole.org/node-role: general
storage:
volumeClaimTemplate:
spec:
accessModes:
- ReadWriteOnce
resources:
requests:
storage: 5Gi
storageClassName: local-path
grafana:
enabled: true
# adminPassword is the local break-glass; primary auth is Google OAuth +
# knoe-auth proxy (below). Stored in the prole.org vault.
adminPassword: admin
nodeSelector:
prole.org/node-role: general
initChownData:
enabled: false
persistence:
accessModes:
- ReadWriteOnce
enabled: true
size: 10Gi
storageClassName: local-path
type: sts
service:
port: 80
targetPort: 3000
sidecar:
dashboards:
enabled: true
label: grafana_dashboard
labelValue: "1"
datasources:
enabled: true
label: grafana_datasource
labelValue: "1"
# Mount Google OAuth client credentials from the grafana-google-oidc Secret.
# Created by etc/init_grafana_oauth_prole.sh from
# etc/secrets/grafana-google-oidc-client-{id,secret}-prole.
# Provides GF_AUTH_GOOGLE_CLIENT_ID and GF_AUTH_GOOGLE_CLIENT_SECRET env vars.
envFromSecret: grafana-google-oidc
grafana.ini:
server:
domain: svc.prole.org
root_url: "https://svc.prole.org/grafana"
serve_from_sub_path: true
security:
cookie_secure: true
cookie_samesite: lax
csrf_trusted_origins: svc.prole.org
csrf_additional_headers: X-Forwarded-Host
"live":
allowed_origins: "https://svc.prole.org"
auth:
disable_login_form: false
token_rotation_interval_minutes: 1440
# Proxy auth: Kerberos/knoe-auth users arriving via grafana-proxy nginx.
# The nginx proxy injects X-WEBAUTH-USER after verifying with knoe-auth;
# Grafana trusts this header and auto-logs the user in without a password.
"auth.proxy":
enabled: true
header_name: X-WEBAUTH-USER
header_property: username
auto_sign_up: true
# Google OAuth: prole.org Workspace users sign in via the Google button on
# the Grafana login page. Requires grafana-proxy nginx to pass /grafana/login
# endpoints through unauthenticated (see grafana-proxy-configmap.yaml).
"auth.google":
enabled: true
allowed_domains: prole.org
scopes: "openid email profile"
auth_url: https://accounts.google.com/o/oauth2/v2/auth
token_url: https://oauth2.googleapis.com/token
api_url: https://openidconnect.googleapis.com/v1/userinfo
# JMESPath: chrisfu gets Admin; every other @prole.org user gets Editor.
role_attribute_path: "contains(['chrisfu@prole.org'], email) && 'Admin' || 'Editor'"
skip_org_role_sync: false
users:
auto_assign_org_role: Editor
kube-state-metrics:
nodeSelector:
prole.org/node-role: general
prometheus:
prometheusSpec:
nodeSelector:
prole.org/node-role: general
storageSpec:
volumeClaimTemplate:
spec:
accessModes:
- ReadWriteOnce
resources:
requests:
storage: 30Gi
storageClassName: local-path
prometheus-node-exporter:
affinity:
nodeAffinity:
requiredDuringSchedulingIgnoredDuringExecution:
nodeSelectorTerms:
- matchExpressions:
- key: kubernetes.io/hostname
operator: NotIn
values:
- pi.prole.org
nodeSelector:
prole.org/node-role: general
prometheusOperator:
nodeSelector:
prole.org/node-role: general