Cross Site Request Forgery (CSRF) wird normalerweise mit einer der folgenden Methoden verhindert:
- Referer prüfen - RESTful aber unzuverlässig
- Token in Formular einfügen und Token in der Serversitzung speichern - nicht wirklich RESTful
- kryptische einmalige URIs - aus dem gleichen Grund wie Token nicht RESTful
- Kennwort manuell für diese Anforderung senden (nicht das zwischengespeicherte Kennwort, das bei der HTTP-Authentifizierung verwendet wird) - RESTful, aber nicht praktisch
Meine Idee ist es, ein Benutzergeheimnis, eine kryptische, aber statische Formular-ID und JavaScript zu verwenden, um Token zu generieren.
<form method="POST" action="/someresource" id="7099879082361234103">
<input type="hidden" name="token" value="generateToken(...)">
...
</form>
GET /usersecret/john_doe
vom JavaScript vom authentifizierten Benutzer abgerufen.- Antwort:
OK 89070135420357234586534346
Dieses Geheimnis ist konzeptionell statisch, kann aber jeden Tag / jede Stunde geändert werden, um die Sicherheit zu verbessern. Dies ist die einzige vertrauliche Sache. - Lesen Sie die kryptische (aber für alle Benutzer statische!) Formular-ID mit JavaScript und verarbeiten Sie sie zusammen mit dem Benutzergeheimnis:
generateToken(7099879082361234103, 89070135420357234586534346)
- Senden Sie das Formular zusammen mit dem generierten Token an den Server.
- Da der Server das Benutzergeheimnis und die Formular-ID kennt, kann vor dem Senden und Vergleichen der beiden Ergebnisse dieselbe generateToken-Funktion wie beim Client ausgeführt werden. Nur wenn beide Werte gleich sind, wird die Aktion autorisiert.
Stimmt etwas mit diesem Ansatz nicht, obwohl er ohne JavaScript nicht funktioniert?
Nachtrag: