2015-12-14 4 views
48

Ich versuche, für meine RESTful-APIs eine zustandslose Authentifizierung mit JWT zu implementieren.Was ist, wenn JWT gestohlen wird?

AFAIK, JWT ist im Grunde eine verschlüsselte Zeichenfolge, die während eines REST-Aufrufs als HTTP-Header übergeben wird.

Aber was ist, wenn es einen Lauscher gibt, der die Anfrage sieht und das Token stiehlt? Dann wird er in der Lage sein, eine Anfrage mit meiner Identität zu fälschen?

Eigentlich gilt diese Sorge für alle Token-basierte Authentifizierung .

Wie kann das verhindert werden? Ein sicherer Kanal wie HTTPS?

+0

Deshalb sind Token oft nur für kurze Zeit gültig. Und ja, Sie sollten HTTPS verwenden, wenn Sie Bedenken hinsichtlich der Vertraulichkeit Ihrer Daten haben. –

+2

@ JonathonReinhart Aber wenn ein Token bald abläuft, muss mein Client ein neues Token erhalten, indem er sich von Zeit zu Zeit erneut authentifiziert. Ist es nicht langweilig? – smwikipedia

+0

@ JonathonReinhart Ich denke, ich verstehe, warum Token kurzlebig ist.Auf diese Weise muss der Server den Ablauf eines Tokens nicht verfolgen und somit der Skalierbarkeit weichen. Es ist eine Art "Trade-Off" zwischen "feinere Kontrolle der Token-Ablauf" und "bessere Skalierbarkeit". – smwikipedia

Antwort

93

Ich bin der Autor einer Node-Bibliothek, die Authentifizierung in ziemlich viel Tiefe behandelt, express-stormpath, so werde ich hier mit ein paar Informationen einläuten.

Zunächst einmal sind JWTs in der Regel NICHT verschlüsselt. Während es eine Möglichkeit gibt, JWTs zu verschlüsseln (siehe:), ist dies in der Praxis aus vielen Gründen nicht sehr üblich.

Als Nächstes unterliegt jede Form der Authentifizierung (mit JWTs oder nicht) den Angriffen von MitM-Angriffen (Man-in-the-Middle). Diese Angriffe treten auf, wenn ein Angreifer Ihren Netzwerkverkehr anzeigen kann, wenn Sie Anforderungen über das Internet stellen. Dies ist, was Ihr ISP sehen kann, der NSA, etc.

Dies ist, was SSL hilft zu verhindern: durch die Verschlüsselung Ihres Netzwerkverkehrs von Ihrem Computer -> einige Server bei der Authentifizierung, eine dritte Partei, die Ihren Netzwerkverkehr überwachen kann NICHT Ihre Tokens, Passwörter oder Ähnliches sehen, es sei denn, sie sind irgendwie in der Lage, eine Kopie des privaten SSL-Schlüssels des Servers zu erhalten (unwahrscheinlich). Aus diesem Grund ist SSL für alle Arten der Authentifizierung obligatorisch.

Sagen wir aber, dass jemand in der Lage ist Ihre SSL zu nutzen und in der Lage, Ihr Token zu lesen: die Antwort auf Ihre Frage ist, dass JA, der Angreifer wird Lage sein, diese Token verwenden Sie zum Imitieren und stellen Sie Anfragen an Ihren Server.

Nun, dies ist, wo Protokolle kommen.

JWTs ist nur ein Standard für eine Authentifizierungs-Token. Sie können für so ziemlich alles verwendet werden. Der Grund, warum JWTs so cool sind, ist, dass Sie zusätzliche Informationen darin einbetten können, und Sie können bestätigen, dass niemand damit zu tun hat (Signieren).

JWTs selbst haben jedoch nichts mit Sicherheit zu tun. Für alle Absichten und Zwecke sind JWTs mehr oder weniger dasselbe wie API-Schlüssel: nur zufällige Zeichenfolgen, die Sie verwenden, um sich irgendwo gegen einen Server zu authentifizieren.

Was Ihre Frage interessanter macht, ist das verwendete Protokoll (höchstwahrscheinlich OAuth2).

Die Funktionsweise von OAuth2 besteht darin, dass es den Clients TEMPORARY-Token (wie JWTs!) Zur Authentifizierung für KURZE ZEITZEIT liefert!

Die Idee ist, dass der Angreifer das Token nur für einen kurzen Zeitraum benutzen kann, wenn es gestohlen wird.

Mit OAuth2 müssen Sie sich immer wieder mit dem Server authentifizieren, indem Sie Ihren Benutzernamen/Ihr Kennwort oder Ihre API-Anmeldeinformationen eingeben und dann ein Token zurückerhalten.

Da dieser Prozess hin und wieder passiert, werden sich Ihre Tokens häufig ändern, was es für Angreifer "härter" macht, Sie ständig zu imitieren, ohne große Probleme zu haben.

Hoffentlich hilft dies ^^

+0

Da Sie OAuth erwähnen, eine verwandte Frage: Was passiert, wenn Angreifer mein OAuth-Token stiehlt und das Token aktualisiert ... sie können theoretisch für immer Zugriff auf meine API erhalten (es sei denn, ich widerrufe den Zugriff auf dieses Token) richtig? – pratikm

+0

In der Regel haben Refresh-Tokens auch einen festgelegten Ablauf (obwohl dieser länger ist als ein Zugriffstoken). Aber ja, Sie haben Recht. – rdegges

+0

Der Autor des folgenden Artikels argumentiert, dass ein Nachteil von JWT darin besteht, dass die einzige Möglichkeit, sich von einem gestohlenen JWT zu erholen, darin besteht, ein neues Schlüsselpaar zu generieren und alle Benutzer effektiv zu protokollieren. Während Session-IDs in einer Datenbank gespeichert werden, kann die Website nur die Sitzungen des betroffenen Benutzers löschen und ihn von allen Geräten abmelden. Ich bin mir nicht sicher, wie OAuth2 hier ins Bild passt oder ob es hilft, die dargestellten Nachteile zu mildern. https://medium.com/@rahulgolwalkar/pros-and-cons-in-using-jwt-json-web-tokens-196ac6d41fb4 – Marcel

1

Ich weiß, dass dies eine alte Frage, aber ich glaube, ich meine $ 0.50 hier fallen kann, kann wahrscheinlich jemand verbessern oder ein Argument liefern, völlig mein Ansatz ablehnen. Ich verwende JWTs in einer RESTful API über HTTPS (Ofc).

Damit dies funktioniert, sollten Sie immer kurzlebige Token ausgeben (hängt von den meisten Fällen ab. In meiner App setze ich den Wert exp auf 30 Minuten und ttl auf 3 Tage, damit Sie dieses Token aktualisieren können solange seine ttl noch gültig ist und das Token wurde nicht die schwarze Liste)

Für die authentication service, um Token ungültig zu machen, Ich mag eine in-Memory-Cache-Schicht verwenden (redis in meinem Fall) wie ein JWT blacklist/ban-list vor, abhängig von einigen Kriterien: (Ich weiß, dass es bricht den RESTful ph ilosophy, aber die gespeicherten Dokumente sind wirklich kurzlebig, als ich für ihre verbleibende Zeit-to-live schwarze Liste - ttl claim-)

Hinweis: die schwarze Liste gesetzt Token nicht automatisch

aktualisiert werden können
  • Wenn user.password oder user.email aktualisiert wurde (erfordert eine Bestätigung des Passworts), gibt der Auth-Service ein aktualisertes Token zurück und macht vorherige (s) ungültig (schwarze Liste). Wenn Ihr Client also feststellt, dass die Identität des Benutzers gefährdet ist, können Sie diesen ändern sein Passwort. Wenn Sie die Blacklist nicht verwenden möchten, können Sie (aber ich ermutige Sie nicht) das iat (ausgegeben am) Claim gegen user.updated_at Feld validieren (wenn jwt.iat < user.updated_at dann JWT nicht gültig ist).
  • Benutzer absichtlich ausgeloggt.

Schließlich validieren Sie das Token normalerweise wie jeder tut.

Anmerkung 2: stattdessen das Token die Verwendung selbst (das ist wirklich lang ist) als der Schlüssel des Cache, schlage ich vor Erzeugen und eine UUID-Token für den jti Anspruch verwenden. Was ist gut und ich denke (nicht sicher, da es gerade in meinen Gedanken kam) Sie können diese UUID auch als das CSRF-Token verwenden, indem Sie ein secure/ Cookie mit ihm zurückgeben und den Header X-XSRF-TOKEN mit js ordnungsgemäß implementieren. Auf diese Weise vermeiden Sie die Rechenarbeit beim Erstellen eines weiteren Tokens für CSRF-Prüfungen.

+0

Es ist nie zu spät, um Ihre Idee zu bringen. Danke für deine Antwort. – smwikipedia

Verwandte Themen