leistungsbilanz-ts/.claude/skills/pre-release-gate/SKILL.md
Grovy311 ee117958b3 fix(security): stamp.py schreibt kein __pycache__ mehr
Ohne passende .gitignore machte der Cache den Arbeitsbaum unsauber, kein
Prüfstempel war gültig.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-17 11:10:44 +02:00

89 lines
5.6 KiB
Markdown

---
name: pre-release-gate
description: >
Release-Freigabe vor einem Deploy: übernimmt gültige Prüfstempel, lässt nur fehlende
Baseline-Prüfungen laufen, wertet die ASVS-light-Checkliste aus und liefert ein Urteil
Go / Go mit Auflagen / No-Go. Schreibt nach dem Deploy das Release-Protokoll und den Tag.
TRIGGER WENN der User sagt: "deployen", "Release", "live stellen", "ist das bereit",
"Go/No-Go", "Release-Check", "/pre-release-gate", oder bevor ein Agent einen Deploy anstößt.
Ergebnis: Urteil mit Begründung und den drei wichtigsten Befunden, nach dem Deploy
docs/releases/<datum>-<commit>.md und Tag release-<datum>.
---
# pre-release-gate
Ein Deploy ohne dieses Gate ist nicht freigegeben. Das Gate deployt **nicht** selbst; der Deploy
braucht danach die ausdrückliche Freigabe des Users.
Grundsatz: **Was für genau diesen Commit schon grün war, läuft nicht noch einmal.** Das belegen
die Prüfstempel der Baseline (`reports/stamps/`, `scripts/security/stamp.py`). Ein Stempel gilt nur,
wenn der Arbeitsbaum beim Lauf sauber war und der Commit derselbe ist (danach nur Doku-Commits
sind erlaubt).
## A. Vor dem Deploy (im App-Repo)
1. **Stand festhalten:** Branch, Commit, letzter Release-Tag (`git describe --tags --match 'release-*' --abbrev=0`),
Delta `git log --oneline <tag>..HEAD`. Kein Tag → erstes Release mit Gate, Delta = alles.
Arbeitsbaum muss sauber sein (`make stamp` zeigt es). Unsauber → erst committen, nicht weiter.
2. **Prüfungen:**
```bash
make release-checks # check + mutation, nur ohne gültigen Stempel
make release-checks IMAGE=<image:tag> # zusätzlich container, falls Container-Deploy
```
Ältere Baseline ohne `release-checks` → `make check`, `make mutation`, `make container` von Hand.
Ergebnis je Prüfung notieren: grün (frisch / aus Stempel von <commit>) | rot | **nicht anwendbar** + Grund
(kein `security-mutations.toml`, kein Container-Deploy). Nicht anwendbar ist kein „nicht ausgeführt“.
3. **Checkliste** `security-review/references/asvs-light.md`: jeder **K**-Punkt braucht einen Beleg
(Test, Scan, Konfiguration). Kein Beleg = offen. Ein K-Punkt ist nur dann **nicht anwendbar**, wenn
`docs/THREATMODEL.md` das als Design-Entscheidung festhält (z. B. B1/B2 bei bewusst teamweit geteilten
Objekten, im Test als `idorGap`/`idor_gap` sichtbar), mit Begründung und wer entschieden hat. Ohne
diesen Eintrag bleibt er offen; `idorGap` allein ist kein Beleg. Beim Folge-Release nur K-Punkte neu bewerten, die das
Delta aus Schritt 1 berührt; die übrigen Belege aus dem letzten Protokoll (`docs/releases/`) übernehmen
und darauf verweisen.
4. **Ausnahmen:** `docs/RELEASE-AUSNAHMEN.md` der App lesen. Ein H-/M-Punkt, der dort mit Begründung
steht und dessen „Prüfen bis“ nicht überschritten ist, ist **akzeptiert**: keine Auflage, im Urteil nur
als „akzeptiert (A<n>)“ nennen. Abgelaufen oder ohne Datum → wieder offen. K-Punkte nie als Ausnahme.
Datei fehlt → Vorlage `templates/docs/RELEASE-AUSNAHMEN.md` aus der Baseline vorschlagen, nicht
selbst Ausnahmen eintragen (Entscheidung Julian bzw. Christian).
5. **Deploy-Konfiguration:** App-Port nicht am Proxy vorbei erreichbar (Compose `ports:`), Debug aus,
Secrets aus Secret-Store/Env, Backup vor Migrationen.
6. Lag seit dem letzten Review ein größerer KI-Diff an Auth/Rollen? → `security-review` im frischen
Kontext, falls noch nicht geschehen.
## Urteil
- **No-Go**, wenn eins zutrifft: ein K-Punkt offen, Secrets gefunden, Tests rot, High/Critical in
Dependencies oder Image ohne dokumentierte Ausnahme, Mutation überlebt, Arbeitsbaum unsauber.
- **Go mit Auflagen**: neue oder abgelaufene H-/M-Punkte offen, jeder mit Entscheidung
(fixen/akzeptieren) und Termin, oder eine anwendbare Pflichtprüfung aus A.2 nicht ausgeführt.
Auflagen als Issues im Repo der App vorschlagen. Wird eine Auflage
akzeptiert, schlägt das Gate die Zeile für `docs/RELEASE-AUSNAHMEN.md` vor, damit sie beim nächsten
Release nicht wieder auftaucht.
- **Go**: alle anwendbaren Prüfungen aus A.2 grün (frisch oder per gültigem Stempel), alle K-Punkte
belegt, offene H-/M-Punkte nur als gültige Ausnahme.
- ZAP, Fuzzing und Playwright laufen **nach** dem Deploy (Teil B) und beeinflussen dieses Urteil nicht.
Ihr Ergebnis geht ins Protokoll; Funde werden Issues und Prüfpunkte fürs nächste Release.
## Ausgabe
```
Urteil: No-Go | Go mit Auflagen | Go
Stand: <branch>@<commit>, seit release-<datum>: <n> Commits
Prüfungen: check ✅ (Stempel 10:42) | mutation ✅ frisch 10/10 | container: nicht anwendbar (kein Image)
Akzeptiert: A1, A3 (docs/RELEASE-AUSNAHMEN.md)
Top-3-Befunde:
1. [K] ... (Datei:Zeile, Beleg)
2. ...
Auflagen / nächste Schritte: ...
```
## B. Nach dem Deploy (nur mit Freigabe deployt)
1. Gegen die eigene Live-Instanz, nie fremde Hosts:
`make zap TARGET=<url>` und, falls OpenAPI vorhanden, `make fuzz TARGET=<url>`.
Nicht möglich (z. B. Login vor allem) → „nicht ausgeführt, Grund“ ins Protokoll.
2. **Protokoll** nach Vorlage `templates/docs/release-protokoll.md` der Baseline:
`docs/releases/<YYYY-MM-DD>-<shortsha>.md`, Prüfungstabelle aus `make release-report`.
Als reiner Doku-Commit committen; der Stempel des deployten Commits bleibt dadurch gültig.
3. **Tag** auf den deployten Commit (nicht auf den Protokoll-Commit):
`git tag -a release-<YYYY-MM-DD> <commit> -m "Release <datum>, Urteil <...>"`, zweites Release am
selben Tag `release-<YYYY-MM-DD>-2`. Push von Tag und Protokoll nach `make prepush` (Doku → nur Secrets).
4. `AGENTS.md` der App: Abschnitt „Letztes Release“ mit Datum, Tag, Urteil, offenen Auflagen.