CodamAIDocs
Themafertig

Schutz der öffentlichen Endpunkte

Warum die Selbstregistrierung immer dieselbe Antwort liefert, warum ungültige Links gleich aussehen und wie die Drosselung funktioniert.

Ausprägungen
immer 202Link-Fehler 404, zweiter Klick 202Drosselung je AdresseDrosselung je Client429 ohne Retry-After

Worum es geht

Die Endpunkte unter /cias/registration/** sind ohne Anmeldung erreichbar. Jeder im Internet kann sie aufrufen, auch jemand, der herausfinden will, welche Adressen bei euch ein Konto haben, oder der massenhaft Mandanten anlegen will. Deshalb verraten diese Endpunkte so wenig wie möglich und sind gedrosselt.

Was ein Angreifer sieht

Gleiche Antwort, verschiedene Mail
neue Adresse
  • Antwort 202 accepted
  • Mail: „Bitte bestätigen Sie Ihre Adresse“
bekannte Adresse
  • Antwort 202 accepted
  • Mail: Einladung zum Beitritt oder „Sie haben bereits ein Konto“
gedrosselt
  • Antwort 429
  • keine Mail

Ein Angreifer sieht nur die Antworten, nicht die Mails. Für ihn sehen neue und bekannte Adressen gleich aus.

Die Antworten der öffentlichen Endpunkte

EndpunktAntwortWann
POST /self202 acceptedangenommen, egal ob die Adresse bekannt ist
400Adresse ungültig oder Anfrage kaputt
422Pflichtfeld fehlt, unbekanntes Feld, oder ein Hook lehnt ab
429gedrosselt
POST /verify, POST /invitations/accept202 acceptedeingelöst, oder schon früher eingelöst
404Link unbekannt, oder abgelaufen, solange der Vorgang noch wartet
GET /invitations/{token}/form200 oder 404offene Felder, oder Link unbekannt
GET /flows/{flow}/form200Feldbeschreibung eines Ablaufs

Alle Fehler haben dasselbe Format: { "error": "cias.registration.…", "message": "…" }.

Warum liefert ein zweiter Klick 202 und keinen Fehler? Viele Mailprogramme öffnen Links vorab, um sie auf Schadsoftware zu prüfen. Dabei wird das Token schon eingelöst, bevor die Person klickt. Ein Fehler beim echten Klick würde sie verwirren. Siehe E-Mail bestätigen.

Die Drosselung

Die Selbstregistrierung zählt Versuche in einem gleitenden Zeitfenster. Ist die Grenze erreicht, antwortet CIAS mit 429, bevor es irgendetwas prüft oder anlegt.

Zwei Zähler

Wann: immer

Höchstens rate-limit Versuche je Adresse in rate-limit-window. Standard und cias-runtime: 10 in 10 Minuten. Der Hub stellt 3 je Stunde ein.

Ergebnis: Schützt das Postfach einer Person davor, mit Mails geflutet zu werden.

Wann: Die Installation stellt client-ip-source auf REMOTE_ADDR oder HEADER.

Ein zweiter Zähler je Absender-IP. Die IP wird nie gespeichert, sondern mit einem Salz gehasht. Bei HEADER nimmt CIAS den ersten Eintrag des eingestellten Headers, etwa X-Forwarded-For. Der Hub stellt HEADER ein, mit 20 Versuchen in 10 Minuten. In cias-runtime ist dieser Zähler aus.

Ergebnis: Schützt davor, dass jemand von einem Rechner aus viele verschiedene Adressen durchprobiert.

Anfrage
POST /cias/registration/self   (11. Versuch in 10 Minuten)
Antwort
429
{ "error": "cias.registration.rate-limited", "message": "too many attempts" }

Die Antwort sagt absichtlich nicht, wann es wieder geht. Es gibt keinen Header Retry-After. Wer wartet, kommt wieder durch; wer es automatisch versucht, bekommt keinen Takt vorgegeben.

Die Verwaltungs-Endpunkte (Anlage durch Administratoren, Einladungen) sind nicht gedrosselt. Dort ist der Aufrufer angemeldet und bekannt.

Weiter

Quellen im Code und in der Wissensdatenbank
  • CIAS/cias-registration – RegistrationController, RegistrationExceptionHandler, RegistrationService (throttle), ClientKeyResolver, RateLimiterPort
  • CIAS/cias-spring-boot-starter – InMemoryRateLimiter, CiasProperties (rate-limit, rate-limits, client-ip-*)
  • CIAS/cias-runtime – application.yml; hub-backend – application.yaml
  • CIAS/cias-registration/docs/adr – ADR-012, ADR-014
Suchen