Zum Inhalt springen

Sicherheit

Du sicherst den tibi-server auf vier Ebenen: Tokens, CORS, Ratelimit und Dateipfade plus Prozess-Isolation. Quelle ist der Code (internal/config, internal/ratelimit, internal/suexec, internal/controller/setup.go).

X-Admin-Token X-Auth-Token Token Bearer
Art Header Wofür Scope-Syntax
Server-Admin-Token X-Admin-Token oder Authorization: Bearer Betrieb: Reload, Backup, Snapshots, Shutdown (server.shutdown nur für Stop) domain.action, Kurzform (project = project.*), * je Segment
Benutzer-JWT X-Auth-Token Anmeldung per /api/v1/login; Lebensdauer via API_ACCESS_TOKEN_LIFETIME (Standard 60m) Rollen + Collection-Rechte
Personal Access Token (PAT) X-Auth-Token (tibi_pat_…) Dauerhafte Maschinen-Tokens, immer aktiv gleiche Syntax wie Admin-Tokens; es gilt Token-Recht UND Besitzer-Recht
MCP X-Auth-Token (nur PAT) KI-Werkzeugzugriff über /api/v1/mcp PAT-Scopes, Admin-Aktionen nur mit mcp.allowAdminActions: true

Gültige Domänen: user, project (read/create/update/delete, reload, backup, regenerate-search, snapshot), team, org, audit.read, llm.chat, namespace.<ns>.<collection>.<aktion>.

Scope-Abgleich (Beispiel)
Anfrage-Recht: namespace.shop.artikel.read
Token-Scope: namespace.shop → passt (Kurzform)
Token-Scope: namespace.*.artikel.read → passt (Wildcard)
Besitzer darf es nicht → trotzdem verboten (UND-Regel)

Jeder Request bekommt genau eine CORS-Config — vom Spezifischen zum Allgemeinen:

CORS-Kaskade
/_actions/<name> → /<collection> → / → "" → keine (Browser blockt)
  • Die Kaskade steht pro Projekt (CORSMap), nicht global. Der cors:-Abschnitt der Server-Config ist die Basis, Projekt- und Collection-Werte mergen feldweise dazu (merge: true hängt an, merge: false ersetzt). Globales CORS ist auskommentiert — ohne Projekt-Kontext greift gar kein CORS.
  • Action-Endpunkte (/_actions/…) haben eigene Einträge — prüfe sie separat.
  • Preflight ohne echte Route antwortet 404 (kein offenes OPTIONS-Loch).

Der Login-Limiter bremst Fehlversuche mit exponentiellem Backoff — je IP und je Benutzername:

Schlüssel Standard Env
Erste Verzögerung 1s RATELIMIT_LOGIN_INITIAL_DELAY
Maximale Verzögerung 60s RATELIMIT_LOGIN_MAX_DELAY
Zähler-Reset nach Ruhe 15m RATELIMIT_LOGIN_RESET_AFTER
Ganz abschalten an (true) RATELIMIT_ENABLED=false (nur Notfall)

Erfolg setzt beide Zähler zurück. Gebremste Versuche antworten mit 429 plus Retry-After-Header (Sekunden) — warte sie ab statt zu hämmern. Das Limit gilt nur für Login, nicht global.

Schalter Wirkung
security.allowAbsolutePaths (SECURITY_ALLOWABSOLUTEPATHS) Absolute Dateipfade erlauben — sonst verboten
security.allowUpperPaths (SECURITY_ALLOWUPPERPATHS) ..-Pfade erlauben — sonst verboten
suexec (kein Schalter) Hooks und Jobs laufen unter der Projekt-UID/GID in eigenen Thread-Pools

Der Starter setzt beide Pfad-Schalter lokal auf "true". In Produktion lässt du sie aus, außer du weißt genau warum.

  1. jwtSecret gesetzt (lang, zufällig) und secureCookies: true (HTTPS).
  2. Admin-Tokens minimal vergeben: ein Token, ein Zweck, enge Scopes.
  3. RESPONSE_ERROR_STACK aus — keine Stacktraces an Clients.
  4. Pfad-Schalter aus, außer nötig. Ratelimit an.
  5. sentry.dsn gesetzt, /metrics nur intern erreichbar.
  6. CORS je Collection geprüft — keine *-Origins mit Credentials.

Config-Schlüssel stehen unter Server-Konfiguration. Laufende Kontrolle unter Betrieb und Beobachtung.

Verifiziert am 68b4278 2026-10-15 (tibi-server)