# Sicherheit

Rechnungen enthalten Namen, Anschriften, Beträge und Steuernummern deiner Kunden. Hier steht, wie BelegDock sie schützt, und auch, was ohne Schlüssel lesbar bleibt.

## Anmeldung

- **Zwei-Faktor-Anmeldung ist Pflicht.** Ohne Authenticator-App öffnet BelegDock keinen Arbeitsbereich. Für den Notfall gibt es acht Wiederherstellungscodes, jeder einmal verwendbar.
- **Sicherheitshinweise per E-Mail**, wenn dein Passwort geändert oder zurückgesetzt, die Zwei-Faktor-Anmeldung ausgeschaltet oder ein Wiederherstellungscode verwendet wird.
- Passwörter speichert BelegDock nur als Argon2id-Hash. Sitzungen, Links zum Zurücksetzen, Wiederherstellungscodes und API-Schlüssel liegen nur als Hash vor.
- Anmeldeversuche sind begrenzt, pro Konto und Absender. Fehlversuche aus dem Netz können dein Konto nicht sperren.
- Sitzungscookies sind `HttpOnly`, `Secure`, `SameSite` und an die Domain gebunden (`__Host-`). Jede Änderung muss von BelegDocks eigener Seite kommen.

## Verschlüsselung

BelegDock verschlüsselt mit AES-256-GCM, einem Verfahren, das jede Veränderung der Daten bemerkt. Verschlüsselt gespeichert sind:

- die Rechnungsdaten aus Stripe und aus der API, jede XRechnung, jede PDF und jeder Prüfbericht
- E-Mail-Adressen, Namen von Personen und Arbeitsbereichen, Unternehmensdaten, E-Mail-Vorlagen und Logos
- Zugangsdaten zu Stripe und Resend, Webhook-Geheimnisse und Zwei-Faktor-Schlüssel
- Supportanfragen, wartende Aufträge und jede ausgehende E-Mail samt Anhängen

Was BelegDock nachschlagen muss, etwa eine E-Mail-Adresse bei der Anmeldung oder die Bestellnummer einer API-Rechnung, liegt als Hash mit geheimem Schlüssel vor (HMAC). Wer nur die Datenbank hat, kann so nicht einmal prüfen, ob eine bestimmte Adresse ein Konto hat.

Der Schlüssel liegt nicht in der Datenbank. Eine Kopie der Datenbank oder ein Backup allein ist ohne ihn nutzlos.

**Ohne Schlüssel lesbar** bleiben nur Betriebsdaten, die BelegDock zum Arbeiten braucht: interne IDs, Zeitpunkte, Status, Rechnungsnummern, Rechnungsbeträge, Tarif und Zählerstände sowie die IDs von Stripe-Objekten.

## Trennung der Arbeitsbereiche

Jeder Arbeitsbereich ist schon in der Datenbank abgeschottet: PostgreSQL lässt jede Anfrage nur die Zeilen des Arbeitsbereichs sehen, für den sie läuft (Row-Level Security). Ein Fehler in einer einzelnen Abfrage kann so keine fremden Rechnungen liefern. Ein Stripe-Konto kann nur mit einem Arbeitsbereich verbunden sein.

## Stripe und API

- BelegDock hat auf dein Stripe-Konto **nur Lesezugriff**. Es ändert dort nichts, legt nichts an und löst keine Zahlungen aus.
- API-Schlüssel siehst du genau einmal, BelegDock speichert nur ihren Hash. Testschlüssel und Live-Schlüssel sind getrennt; jeder Schlüssel lässt sich sofort widerrufen.
- Webhooks von Stripe und Resend nimmt BelegDock nur mit gültiger Signatur an und verarbeitet jedes Ereignis genau einmal.

## Betrieb

- Alle Verbindungen laufen über HTTPS mit HSTS. Cloudflare steht vor dem Server und verwirft Anfragen an Adressen, die es bei BelegDock nicht gibt, bevor sie den Server erreichen.
- Strenge Content-Security-Policy, keine Skripte von Dritten in der App, kein Einbetten in fremde Seiten.
- Die Anwendung läuft in Containern ohne Root-Rechte mit schreibgeschütztem Dateisystem. Der Prüfdienst der KoSIT ist aus dem Internet nicht erreichbar.
- Ausgestellte API-Rechnungen sind in der Datenbank gegen Änderung und Löschung gesperrt.

## Dienstleister

Hetzner betreibt die Server, Cloudflare das Netzwerk davor, Resend versendet E-Mails, Stripe wickelt Zahlungen ab und liefert die Daten deiner Stripe-Rechnungen. Rechnungsdaten gehen nur an Resend für die E-Mails an die Empfänger, die du vorgibst, und über die Stripe-App in dein eigenes Stripe-Dashboard.

## Grenzen

Kein System ist unangreifbar. Wer den laufenden Server übernimmt, kommt auch an den Schlüssel; dagegen helfen getrennte Zugangsdaten, aktuelle Software und die Abschottung oben, aber keine Garantie. Eine Zertifizierung nach ISO 27001 oder ähnlich hat BelegDock nicht.
