graphify ist eingerichtet (786 Knoten, 1179 Kanten) und in CLAUDE.md als erster Griff bei Fragen zum Bestand festgehalten, statt Dateien durchzulesen. Mit der Stolperfalle dokumentiert: das `graphify` im PATH läuft nicht, weil es für Python 3.10 installiert ist und das System-python3 3.12 ist. Der Aufruf muss über python3.10 mit gesetztem PYTHONPATH laufen. graphify-out/ ist ein Bauartefakt und bleibt aus dem Repository. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
120 lines
5.9 KiB
Markdown
120 lines
5.9 KiB
Markdown
# AfiS-Aktensystem
|
|
|
|
Interne Web-Anwendung für die Abteilung für innere Sicherheit (AfiS) eines SCP-RP-Servers.
|
|
Verwaltet Fallakten, Personalakten und Ermittlungen mit einem mehrstufigen Klassifizierungssystem.
|
|
Anmeldung und Berechtigungen laufen vollständig über Discord.
|
|
|
|
Dies ist ein Rollenspiel-Werkzeug für eine geschlossene Gruppe von etwa 10 bis 50 Personen,
|
|
selbst gehostet auf einem Homeserver. Kein Multi-Tenant, keine öffentliche Registrierung.
|
|
|
|
## Stack
|
|
|
|
- Next.js 15, App Router, React 19, TypeScript strict
|
|
- Auth.js v5 (Discord Provider)
|
|
- Prisma + PostgreSQL 16
|
|
- Tailwind CSS, keine Komponentenbibliothek (siehe `docs/10-design-system.md`)
|
|
- Separater Node-Dienst `worker/` mit discord.js für Rollen-Abgleich
|
|
- ClamAV und Playwright als eigene Container
|
|
- Betrieb als **ein** Dockge-Stack, siehe `docs/11-betrieb.md`. Kein Reverse Proxy im Stack,
|
|
TLS und Kompression macht der Cloudflare Tunnel.
|
|
|
|
## Dokumentation
|
|
|
|
Vor dem Bau eines Bereichs immer das passende Dokument lesen:
|
|
|
|
| Datei | Inhalt |
|
|
|---|---|
|
|
| `docs/01-produkt.md` | Domäne, Glossar, Rollen der Nutzer |
|
|
| `docs/02-architektur.md` | Dienste, Datenflüsse, Verzeichnisstruktur |
|
|
| `docs/03-auth-und-rechte.md` | Discord-Login, Rollen-Mapping, Zugriffsprüfung |
|
|
| `docs/04-datenmodell.md` | Prisma-Schema, Indizes, Migrationen |
|
|
| `docs/05-akten-und-vorlagen.md` | Aktenaufbau, Vorlagen, Versionierung, Schwärzung |
|
|
| `docs/06-chat-und-realtime.md` | Aktenchat, SSE, Benachrichtigungen |
|
|
| `docs/07-dateien-und-sicherheit.md` | Upload-Prüfkette, Auslieferung |
|
|
| `docs/08-suche-und-export.md` | Volltextsuche, PDF-Export |
|
|
| `docs/09-performance-und-ux.md` | Ladezustände, optimistische Updates, Latenzbudgets |
|
|
| `docs/10-design-system.md` | Farben, Typografie, Komponentenregeln |
|
|
| `docs/11-betrieb.md` | Dockge-Stack, compose.yaml, Backups |
|
|
| `docs/13-entscheidungen.md` | Aufgelöste Widersprüche der Dokumente, getroffene Festlegungen |
|
|
|
|
`TASKS.md` enthält die Bauphasen. Arbeite sie in Reihenfolge ab und hake ab, was fertig ist.
|
|
|
|
## Wissensgraph (graphify)
|
|
|
|
Für Fragen zum Bestand **zuerst** den Graphen befragen, statt Dateien durchzulesen. Das
|
|
spart Kontext und zeigt Zusammenhänge über Dateigrenzen hinweg.
|
|
|
|
```bash
|
|
# Achtung: das `graphify` im PATH läuft nicht — es ist für Python 3.10
|
|
# installiert, das System-python3 ist 3.12. Deshalb immer so aufrufen:
|
|
export PYTHONPATH="$HOME/.local/lib/python3.10/site-packages"
|
|
python3.10 -m graphify query "<Frage>" --budget 2000
|
|
python3.10 -m graphify path "<A>" "<B>" # Zusammenhang zwischen zwei Knoten
|
|
python3.10 -m graphify explain "<Begriff>" # ein Knoten und seine Nachbarn
|
|
python3.10 -m graphify affected "<X>" # was hängt an X, rückwärts
|
|
python3.10 -m graphify god-nodes --top 10 # die am stärksten verdrahteten Stellen
|
|
```
|
|
|
|
**Nach jeder Änderung am Code** den Graphen nachziehen, das kostet nichts und braucht kein
|
|
LLM:
|
|
|
|
```bash
|
|
python3.10 -m graphify update . --no-cluster
|
|
```
|
|
|
|
`graphify-out/` ist ein Bauartefakt und liegt nicht im Repository.
|
|
|
|
## Harte Regeln
|
|
|
|
1. **Berechtigungsprüfung immer serverseitig und immer in der Datenbankabfrage.**
|
|
Niemals alle Datensätze laden und danach filtern. Siehe `docs/03-auth-und-rechte.md`.
|
|
2. **Verlaufseinträge dürfen nachträglich geändert werden, aber niemals unsichtbar.**
|
|
Jede Änderung erzeugt eine Version, jede Zurücknahme lässt einen Grabstein stehen,
|
|
beides ist für alle sichtbar, die den Eintrag sehen dürfen. Es gibt kein `DELETE`.
|
|
Welche Änderungen erlaubt sind, steuert die Änderungsrichtlinie in
|
|
`docs/05-akten-und-vorlagen.md`.
|
|
3. **Jede schreibende Aktion und jeder Lesezugriff auf Stufe 3+ erzeugt einen Audit-Eintrag.**
|
|
4. **Keine Dateiendungen als Typprüfung.** Immer Magic Bytes. Kein SVG, kein HTML, keine Archive.
|
|
5. **Keine Blockade-Spinner.** Jede Ansicht hat ein Skelett, jede Mutation eine sofortige
|
|
Reaktion. Siehe `docs/09-performance-und-ux.md`, das ist keine Kür.
|
|
6. **Existenz ist auch eine Information.** Akten oberhalb der Sichtstufe des Nutzers tauchen
|
|
weder in Listen noch in Trefferzahlen noch in Rückverweisen auf.
|
|
7. Keine Secrets im Repo. Alles über `.env`, Vorlage in `.env.example`.
|
|
8. **Keine Einmal-Container und keine Init-Container.** Der Betrieb läuft über Dockge, das
|
|
beendete Container nicht dauerhaft anzeigt. Migrationen gehören ins Startkommando von
|
|
`web`, wiederkehrende Aufgaben in Dauerläufer mit eigenem Cron. Jeder Dienst braucht
|
|
einen Healthcheck, weil das in Dockge die Statusanzeige ist.
|
|
|
|
## Sprachkonvention
|
|
|
|
- **Code, Datenbank, API**: Englisch. `Case`, `CaseEntry`, `PersonnelFile`, `ClearanceLevel`.
|
|
- **Oberfläche und Dokumentation**: Deutsch. Alle UI-Texte zentral in `lib/i18n/de.ts`,
|
|
nie hart im JSX. Das Glossar in `docs/01-produkt.md` legt die Übersetzungen fest.
|
|
- **Fachbegriffe der Domäne bleiben englisch**, so wie sie auf dem Discord heißen:
|
|
Rollennamen, Dienstgrade und die Bezeichnungen der Freigabestufen (`Sensitive Access`,
|
|
nicht `Geheim`). Die Oberfläche ist deutsch, die Begriffe darin sind es nicht. Nicht
|
|
eindeutschen. Diese Namen sind Daten, keine Oberflächentexte: sie stehen in der
|
|
Datenbank und sind im Adminbereich änderbar, nicht in `lib/i18n/de.ts`.
|
|
|
|
## Kommandos
|
|
|
|
```bash
|
|
pnpm dev # Next.js Dev-Server
|
|
pnpm worker:dev # Discord-Sync-Worker
|
|
pnpm db:migrate # Prisma Migration anwenden
|
|
pnpm db:seed # Testdaten inkl. Vorlagen
|
|
pnpm db:studio # Prisma Studio
|
|
pnpm test # Vitest
|
|
pnpm test:e2e # Playwright
|
|
pnpm lint && pnpm typecheck
|
|
pnpm build # Standalone-Build für das Container-Image
|
|
```
|
|
|
|
## Arbeitsweise
|
|
|
|
- Kleine Commits pro abgeschlossener Aufgabe aus `TASKS.md`.
|
|
- Für jede Zugriffsregel einen Test, der den **negativen** Fall prüft: Nutzer ohne Freigabe
|
|
sieht nichts, findet nichts, bekommt 404 statt 403.
|
|
- Bei Unklarheiten in der Fachlichkeit nicht raten, sondern nachfragen.
|
|
- Nach jeder Phase `pnpm lint && pnpm typecheck && pnpm test` laufen lassen.
|