Files
alva/docs/DRIFT.md
T
Claude 03f1ef20f6 Allt i Kubernetes: containrar, manifest, orkestertjänst och CI
Målarkitekturen ur Master Prompt som kod:

- Webben containeriserad (flerstegs-Dockerfile → oprivilegierad nginx
  med SPA-fallback, hashade assets cachas hårt, säkerhetsheaders).
- AI-orkestern som egen tjänst (services/ai-orkester): samma routing
  och AI-regler som edge-funktionen men körbar som pod — egen
  HS256-JWT-verifiering (fail closed), /halsa, storleksgränser,
  read-only container som kör som node-användaren. Livetestad:
  hälsokontroll ok, 401 utan/med ogiltig token, 400-validering bakom
  giltig JWT.
- Kubernetes-manifest (infra/k8s, kustomize): namespace, Deployments
  med readiness/liveness och åtstramad securityContext, Services,
  HPA 2–10 pods på 70 % CPU, PodDisruptionBudgets, Ingress med TLS
  via cert-manager, secret-mall (riktiga värden skapas utanför git).
- Klienten väljer AI-väg vid bygget: VITE_AI_ORKESTER_URL → tjänsten
  i klustret, annars Supabase-edge-funktionen. Samma orkester i båda,
  låst av paritetstest.
- CI-arbetsflöde: tester + produktionsbygge + verifierande
  containerbyggen av båda bilderna på varje push/PR.
- docs/DRIFT.md: arkitekturdiagram, driftsättningssteg, skalning,
  och vad som återstår mot full självhostning.

Verifierat: 27 vitest-tester gröna, produktionsbygge ok, alla
K8s-manifest YAML-validerade, orkestertjänsten livetestad,
Playwright-röktest grönt.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_012EQg3rJsrQ1ZNTvkzmQAtt
2026-08-03 01:27:54 +00:00

3.4 KiB
Raw Blame History

Guidad Felsökning Drift i Kubernetes

Målarkitekturen ur Master Prompt som kod: allt körbart i kluster, med secrets för plattformsnycklarna och CI som verifierar både kod och containerbyggen.

Arkitektur

flowchart LR
    T[Tekniker] -->|HTTPS| I[Ingress + TLS]
    I -->|/| W[web\n210 pods, HPA]
    I -->|/api/ai| A[ai-orkester\n210 pods, HPA]
    A -->|Claude API| C[(Anthropic)]
    W & A -.->|auth + data| S[(Supabase\nPostgres · Auth)]
    K[Secret: felsokning-hemligheter] --> A
Komponent Vad Var
web SPA:n bakom oprivilegierad nginx (Dockerfile, docker/nginx.conf) Deployment + Service + HPA + PDB
ai-orkester AI-orkestern som egen tjänst (services/ai-orkester) — samma routing som edge-funktionen, med egen JWT-verifiering och /halsa Deployment + Service + HPA + PDB
Hemligheter ANTHROPIC_API_KEY + SUPABASE_JWT_SECRET Secret felsokning-hemligheter — aldrig i bilder eller manifest
Databas & auth Postgres (händelselogg, RLS, hamta_delat_arende) och inloggning Supabase — managerad, eller självhostad Supabase i klustret när det steget tas

Klienten väljer AI-väg vid byggtillfället: med VITE_AI_ORKESTER_URL satt går anropen till orkestertjänsten i klustret; utan den används Supabase-edge-funktionen. Samma orkester (modeller, systemprompter, scheman) i båda.

Driftsätta

# 1. Bygg och publicera bilderna (ersätt registry i infra/k8s/*.yaml)
docker build -t ghcr.io/ORG/guidad-felsokning-web \
  --build-arg VITE_SUPABASE_URL=\
  --build-arg VITE_SUPABASE_PUBLISHABLE_KEY=\
  --build-arg VITE_SUPABASE_PROJECT_ID=\
  --build-arg VITE_AI_ORKESTER_URL=https://app.exempel.se .
docker build -t ghcr.io/ORG/guidad-felsokning-ai-orkester services/ai-orkester
docker push ghcr.io/ORG/guidad-felsokning-web
docker push ghcr.io/ORG/guidad-felsokning-ai-orkester

# 2. Skapa secret:en (eller använd External Secrets/Sealed Secrets)
kubectl create namespace guidad-felsokning
kubectl -n guidad-felsokning create secret generic felsokning-hemligheter \
  --from-literal=anthropic-api-key='sk-ant-…' \
  --from-literal=supabase-jwt-secret='…'

# 3. Applicera manifesten
kubectl apply -k infra/k8s

# 4. Verifiera
kubectl -n guidad-felsokning get pods
curl https://app.exempel.se/halsa   # → {"status":"ok"}

Byt domän och cert-issuer i infra/k8s/ingress.yaml.

Skalning och robusthet

  • HPA 210 pods per tjänst på 70 % CPU; PDB håller minst en pod uppe vid noddränering.
  • Båda containrarna kör non-root utan capabilities; orkestern dessutom med read-only rotfilsystem.
  • Hälsokontroller: nginx svarar på /, orkestern på /halsa (readiness + liveness + Docker HEALTHCHECK).
  • Orkestern failar closed: utan nyckel/JWT-hemlighet svarar den 503, utan giltig JWT 401.

CI

.github/workflows/ci.yml kör tester + produktionsbygge och verifierar båda Dockerfilerna på varje push/PR. Publicering till registry och kubectl apply läggs i ett separat, behörighetsstyrt deploy-flöde (t.ex. environments med godkännande eller GitOps via Argo CD/Flux).

Kvar mot full självhostning

Synk, Live Share-funktionen och inloggningen går fortfarande mot Supabase (managerad Postgres + Auth). Nästa steg för "allt i kluster" är självhostad Supabase eller ett eget API-lager över Postgres i klustret — händelsemodellen är redan API-klar, så det bytet påverkar inte klienten.