Files
alva/felsokning/infra/terraform
Claude b147694e31 Härdning av hela TÜV-revisionen
Tio av tolv fynd stängda, två reducerade med skälen utskrivna. Varje
stängning prövas av integrationssviten mot riktig Postgres — 144
kontroller, upp från 100.

T-1  Händelsenyckeln är nu (arende_id, id). Det finns inget delat
     namnrum kvar att ockupera, så attacken saknar yta i stället för att
     vara mildrad. Inom ett ärende bedöms en kollision på klientens
     avtryck — en hash av det kanoniserade innehåll klienten skickade,
     taget före serverns egna fält och före krypteringen, eftersom
     varken raden eller nyttolasten går att jämföra. Identiskt innehåll
     är fortfarande idempotent; samma id med annat innehåll ger 409 och
     skriver ingenting alls, inte heller resten av satsen. Samma attack
     en nivå upp — ärende-id är lika förutsägbart — stängs separat: ett
     id som ägs av en annan organisation ger 409 i stället för att tyst
     låta bli, vilket tidigare lämnade offrets ärende oskapat och varje
     senare synk svarande 404.

T-2  Mätdonet slås upp i registret. Beteckning och kalibrering HÄRLEDS
     därifrån och skriver över det klienten skickade. Okänt mätdon ger
     400. Utgånget avvisas inte — mätningen gjordes — men registrets
     datum följer med, så graderingen faller på registrets uppgift. Ett
     mätvärde utan mätdon får sina påstådda uppgifter borttagna.

T-3  Reducerad, inte stängd. Personnycklarna kuverteras under en
     huvudnyckel utanför databasen. En återställd dump ger nycklar som
     inte öppnas — verifierat genom att starta om utan huvudnyckeln. Vad
     som återstår står utskrivet: en backup tagen FÖRE en radering, plus
     huvudnyckeln, återställer fortfarande uppgifterna.

Därtill: gallringen verkställs nu av ett eget jobb och grupperar på det
blindade fordonsindexet så att en delad nyckel inte gallras för tidigt
(T-4) · AI-avlästa mätvärden bär härkomst (T-5) · bcrypt kostnad 12
(T-6) · åtkomstloggen och raderingsregistret är append-only, med en
smalare regel för personnycklarna som måste kunna förstöras (T-7) ·
åtkomstloggen dokumenterad (T-8) · ett externt regelpaket utan signatur
spärrar avslut (T-9) · CORS faller inte längre öppet (T-10) · exp krävs
i token (T-11) · react-router 7 (T-12, med den kvarvarande avvikelsen
motiverad).

Den motspelande hyresgästen som revisionen efterlyste finns nu som
testform och körs i CI.

---- Vad härdningen själv avslöjade -----------------------------------

Två av rättelserna var kortvarigt fel på samma sätt som fynden, och
bägge fångades bara av att jag försökte bevisa dem:

  T-7-testet var grönt mot en TOM tabell. En radnivåtrigger har inga
  rader att fyra på, så delete lyckades och kontrollen mätte ingenting.

  T-6-testet påstod anropet, inte kostnaden. toContain("gen_salt('bf')")
  hade accepterat kostnad 6 för evigt — och gjorde det, så länge det
  fanns.

Bägge är mönstret revisionen namngav: en kontroll som är riktig i sina
egna termer och oprövad vid sin gräns. Det gäller tester lika mycket som
kod.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_012EQg3rJsrQ1ZNTvkzmQAtt
2026-08-06 13:05:16 +00:00
..

Infrastrukturen

Hela systemet i Terraform. Filerna är numrerade i den ordning de är begripliga att läsa:

Fil Vad
versions.tf Leverantörer och tillståndsbackend
variables.tf Allt som skiljer en installation från en annan
karta.tf Systemet som data — tjänster, portar, routing, hemligheter, dataflöden, gränser
10-namnrymd.tf Namnrymd, tjänstekonto med IRSA, hemligheter ur Secrets Manager
05-aws.tf Kopplingen till AWS-basen — allt den redan bestämt läses här
15-plattformstjanster.tf ALB-kontroller, External Secrets, metrics, CloudWatch
90-gitea.tf Självhostad git med egna byggrunners
30-plattform.tf Backend: auth, händelse-API, delning, integrationer
40-orkester.tf AI-orkestern
50-web.tf Klienten
60-ingress.tf ALB och DNS
70-natverk.tf Nätverkspolicyer — vem får prata med vem
outputs.tf Kartan utskriven

Börja i karta.tf. Den beskriver systemet en gång, som data; resten av filerna läser därifrån i stället för att upprepa portar och namn.

Kom igång

cp terraform.tfvars.exempel terraform.tfvars   # fyll i domän, register, nycklar
terraform init
terraform plan
terraform apply
terraform output karta                         # hela systemet i klartext

terraform output karta svarar på frågorna "vad kör var", "vem ser vilken hemlighet", "vad pratar med vad" och "vad ingår inte" — utan att någon behöver läsa .tf-filerna.

Kontroll utan kluster

terraform fmt -check -diff        # formatering
terraform init -backend=false     # hämtar leverantörer
terraform validate                # typer och referenser

terraform validate kräver att leverantörerna hämtats från registry.terraform.io.

Var saker ligger

Det här lagret bestämmer nästan ingenting själv. AWS-basen (felsokning/infra/aws) äger klustret, databasen, registret, hinken, rollerna, domänen och hemligheterna — och 05-aws.tf läser dess utdata. Ändras något där slår det igenom här utan att en rad ändras.

Vad Var
Händelseloggen Aurora PostgreSQL utanför klustret, med PITR
Bilagor S3, signerat med tjänstekontots roll — inga nycklar finns
Hemligheter Secrets Manager, speglade av External Secrets var timme
Bilder ECR med oföränderliga taggar
Trafik in ALB med ACM-certifikat
Git och bygge Gitea med egna runners i samma kluster

Terraform ser aldrig en hemlighets värde. Det är avsiktligt: en hemlighet som passerar Terraform hamnar i tillståndsfilen.

Driftsättning

Bilderna byggs av publicera.yml vid varje push till main och taggas med git-SHA:t. Driftsättningen är ett eget flöde, driftsatt.yml, som startas för hand med en tagg och kör mot GitHub-miljön produktion — den kan kräva godkännande. Rollback är att köra flödet igen med en tidigare tagg.

Kustomize- och Argo CD-vägen är borttagen. Den beskrev samma system en gång till och kunde inte köras samtidigt som Terraform utan att de motarbetade varandra (selfHeal återställde det Terraform ändrade, prune tog bort det Terraform skapade).

Det som medvetet inte ingår

Står också i terraform output karta under avgränsningar:

  • Objektlagring. Foton och video ligger som data-URL:er i händelseloggen. Det gör loggen till systemets enda sanningskälla, men också stor och tung att säkerhetskopiera.
  • Observability. Ingen metrikexport, ingen tracing.
  • Takt-begränsning på inloggning. Bara den publika beslutsvägen är begränsad, och bara per pod.
  • Återkallelse av JWT. En utfärdad token gäller sina 12 timmar ut även om användaren tagits bort.

Krav på klustret

  • En CNI som tillämpar NetworkPolicy (Cilium, Calico, Antrea). Utan det är 70-natverk.tf dokumentation, inte skydd.
  • ingress-nginx, med kontrollern i namnrymden var.ingress_namnrymd.
  • cert-manager med en ClusterIssuer.
  • En metrics-server för autoskalningen.
  • En StorageClass som klarar ReadWriteOnce.