Czy konieczne jest stosowanie ochrony CSRF, gdy aplikacja opiera się na uwierzytelnianiu bezstanowym (przy użyciu czegoś takiego jak HMAC)?
Przykład:
Mamy jedną aplikację, stronę (w przeciwnym razie mamy do dołączania żeton na każdym linku:
<a href="...?token=xyz">...</a>
.Użytkownik uwierzytelnia się za pomocą
POST /auth
. Po pomyślnym uwierzytelnieniu serwer zwróci pewien token.Token będzie przechowywany za pośrednictwem JavaScript w jakiejś zmiennej wewnątrz aplikacji pojedynczej strony.
Ten token będzie używany do uzyskiwania dostępu do ograniczonych adresów URL, takich jak
/admin
.Token będzie zawsze przesyłany w nagłówkach HTTP.
NIE ma sesji HTTP ani plików cookie.
O ile rozumiem, nie powinno być (?!) możliwości stosowania ataków między witrynami, ponieważ przeglądarka nie przechowuje tokena, a co za tym idzie, nie może automatycznie wysłać go na serwer (tak by się stało, gdybyśmy korzystali z Cookies / Sesja).
Czy coś mi brakuje?
Odpowiedzi:
Znalazłem informacje o tym, że CSRF + nie używa plików cookie do uwierzytelniania:
https://auth0.com/blog/2014/01/07/angularjs-authentication-with-cookies-vs-token/
„ponieważ nie korzystasz z plików cookie, nie musisz chronić się przed żądaniami z innych witryn”
http://angular-tips.com/blog/2014/05/json-web-tokens-introduction/
„Jeśli skorzystamy z plików cookie, naprawdę musisz wykonać CSRF, aby uniknąć żądań między witrynami. To jest coś, co możemy zapomnij o używaniu JWT, jak zobaczysz ”.
(JWT = Json Web Token, uwierzytelnianie oparte na tokenach dla aplikacji bezstanowych)
http://www.jamesward.com/2013/05/13/securing-single-page-apps-and-rest-services
„Najłatwiejszym sposobem na uwierzytelnienie bez ryzyka podatności CSRF jest unikanie używania plików cookie do identyfikacji użytkownika "
http://sitr.us/2011/08/26/cookies-are-bad-for-you.html
„Największym problemem związanym z CSRF jest to, że pliki cookie nie zapewniają absolutnie żadnej ochrony przed tego typu atakami. Jeśli używasz uwierzytelniania plików cookie musisz również zastosować dodatkowe środki w celu ochrony przed CSRF. Najbardziej podstawowym środkiem ostrożności, jaki możesz podjąć, jest upewnienie się, że aplikacja nigdy nie wywoła żadnych skutków ubocznych w odpowiedzi na żądania GET. "
Jest o wiele więcej stron, które stwierdzają, że nie potrzebujesz żadnej ochrony CSRF, jeśli nie używasz plików cookie do uwierzytelniania. Oczywiście nadal możesz używać plików cookie do wszystkiego innego, ale unikaj przechowywania czegoś takiego w
session_id
środku.Jeśli chcesz zapamiętać użytkownika, masz dwie możliwości:
localStorage
: Magazyn wartości klucza w przeglądarce. Zapisane dane będą dostępne nawet po zamknięciu przez użytkownika okna przeglądarki. Dane nie są dostępne dla innych stron internetowych, ponieważ każda witryna ma własne miejsce.sessionStorage
: Również magazyn danych w przeglądarce. Różnica polega na tym, że: dane są usuwane, gdy użytkownik zamyka okno przeglądarki. Jest to jednak przydatne, jeśli Twoja aplikacja internetowa składa się z wielu stron. Możesz więc wykonać następujące czynności:sessionStorage
sessionStorage
sessionStorage
lub poczekać, aż użytkownik zamknie okno przeglądarki, co spowoduje wyczyszczenie wszystkich zapisanych danych.(dla obu zajrzyj tutaj: http://www.w3schools.com/html/html5_webstorage.asp )
Czy są jakieś oficjalne standardy autoryzacji tokena?
JWT (Json Web Token): Myślę, że to wciąż szkic, ale jest już używany przez wiele osób, a koncepcja wygląda na prostą i bezpieczną. (IETF: http://tools.ietf.org/html/draft-ietf-oauth-json-web-token-25 )
Istnieją również biblioteki wielu dostępnych frameworków. Po prostu wygoogluj to!
źródło
http://.../someRestResource?method=POST
. Jest to więc w zasadzieGET
żądanie, ale aplikacja serwera interpretuje je jakoPOST
żądanie, ponieważ została skonfigurowana do używaniamethod
parametru zamiast nagłówka HTTP....
Jeśli chodzi o popularne przeglądarki internetowe, egzekwują one zasady tego samego pochodzenia i wykonująGET
żądania tylko do serwerów zagranicznych. Chociaż może być możliwe wykonywaniePOST
żądań, jeśli przeglądarka internetowa nie stosuje tych standardów sieciowych (błąd, złośliwe oprogramowanie).Server Side App
: Nadal nie jest możliwe wysłanie treści żądania, ponieważ popularne przeglądarki na to nie pozwalają. Jeśli jednak aplikacja serwera na to zezwalamethod=POST
, może również zezwolićbody={someJson}
na przesłonięcie domyślnej treści żądania. To naprawdę zły projekt API i niezwykle ryzykowny. Chociaż jeśli Twoja aplikacja serwerowa na to pozwalahttp://...?method=POST&body={someJson}
, powinieneś naprawdę przemyśleć, co tam zrobiłeś, dlaczego i czy w ogóle jest to konieczne. (Powiedziałbym, że w 99,9999% przypadków nie jest to konieczne). Ponadto przeglądarki mogą w ten sposób wysyłać tylko kilka kilobajtów.TL; DR
JWT, jeśli jest używany bez plików cookie, neguje potrzebę tokena CSRF - ALE! przechowując token JWT w session / localStorage, ujawniasz swój token JWT i tożsamość użytkownika, jeśli witryna ma lukę w zabezpieczeniach XSS (dość powszechną). Lepiej jest dodać
csrfToken
klucz do tokena JWT i przechowywać go w pliku cookie z ustawionymi atrybutamisecure
ihttp-only
.Przeczytaj ten artykuł z dobrym opisem, aby uzyskać więcej informacji https://stormpath.com/blog/where-to-store-your-jwts-cookies-vs-html5-web-storage
Będziesz więc musiał przechowywać csrfToken w localStorage / sessionStorage, a także w samym JWT (który jest przechowywany w bezpiecznym pliku cookie obsługującym tylko protokół http). Następnie w celu ochrony csrf sprawdź, czy token csrf w tokenie JWT jest zgodny z przesłanym nagłówkiem csrf-token.
źródło