W celu zabezpieczenia REST API za pomocą JWT, zgodnie z niektórymi materiałami (takimi jak ten przewodnik i to pytanie ), JWT może być przechowywany w localStorage lub Cookies . Na podstawie mojego zrozumienia:
- localStorage podlega XSS i generalnie nie zaleca się przechowywania w nim żadnych poufnych informacji.
- Za pomocą plików cookie możemy zastosować flagę „httpOnly”, która zmniejsza ryzyko XSS. Jeśli jednak mamy odczytać token JWT z plików cookie na zapleczu, wówczas podlegamy CSRF.
Opierając się więc na powyższej przesłance - najlepiej będzie, jeśli będziemy przechowywać JWT w plikach Cookies. Przy każdym żądaniu do serwera token JWT zostanie odczytany z plików Cookies i dodany w nagłówku Authorization za pomocą schematu Bearer. Serwer może następnie zweryfikować token JWT w nagłówku żądania (w przeciwieństwie do odczytywania go z plików cookie).
Czy moje rozumienie jest prawidłowe? Jeśli tak, czy powyższe podejście ma jakiekolwiek obawy dotyczące bezpieczeństwa? A może w pierwszej kolejności możemy po prostu uciec od używania localStorage?
Odpowiedzi:
Podoba mi się metoda XSRF Double Submit Cookies, o której wspomniano w artykule @ pkid169, ale jest jedna rzecz, której artykuł ci nie mówi. Nadal nie jesteś chroniony przed XSS, ponieważ atakujący może wstrzyknąć skrypt, który odczytuje plik cookie CSRF (który nie jest HttpOnly), a następnie wysyła żądanie do jednego z punktów końcowych interfejsu API za pomocą tego tokenu CSRF z plikiem cookie JWT wysyłanym automatycznie.
Tak więc w rzeczywistości nadal jesteś podatny na XSS, po prostu atakujący nie może ukraść Ci tokena JWT do późniejszego wykorzystania, ale nadal może wysyłać żądania w imieniu użytkowników za pomocą XSS.
Niezależnie od tego, czy przechowujesz swój token JWT w localStorage, czy też przechowujesz token XSRF w pliku cookie nie zawierającym tylko http, oba mogą być łatwo przechwycone przez XSS. Nawet twój JWT w pliku cookie HttpOnly może zostać przechwycony przez zaawansowany atak XSS.
Dlatego oprócz metody Double Submit Cookies, należy zawsze stosować najlepsze praktyki przeciwko XSS, w tym przed zawartością ucieczki. Oznacza to usunięcie każdego wykonywalnego kodu, który spowodowałby, że przeglądarka zrobiłaby coś, czego nie chcesz. Zwykle oznacza to usunięcie tagów // <! [CDATA [i atrybutów HTML, które powodują ocenę JavaScript.
źródło
Html.AntiForgeryToken()
w ASP.NET MVC używa pliku cookie HttpOnly dla tokenu CSRF. Myślę, że nadal jesteś podatny na niektóre XSS, ale pomyślałem, że warto o tym wspomnieć.W aktualnym poście ze Stormpath dość dużo rozwinąłem moje punkty i odpowiedziałem na moje pytanie.
TL; DR
Przechowuj token JWT w plikach cookie, a następnie przekazuj token JWT w nagłówku Authorization przy każdym żądaniu, o którym wspomniałem, lub jak sugeruje artykuł, polegaj na zapleczu, aby zapobiec CSRF (np. Używając
xsrfToken
w przypadku Angulara).źródło
Zamiast tego podczas logowania możesz dostarczyć dwa tokeny: token dostępu i token odświeżania. Token dostępu powinien być przechowywany w pamięci Javascript, a token odświeżania powinien być przechowywany w HttpOnly Cookie. Refresh token służy tylko i wyłącznie do tworzenia nowych tokenów dostępu - nic więcej.
Gdy użytkownik otworzy nową kartę lub odświeży stronę, należy wykonać żądanie utworzenia nowego tokena dostępu, na podstawie tokena odświeżania przechowywanego w Cookie.
Gorąco polecam również przeczytanie tego artykułu: https://hasura.io/blog/best-practices-of-using-jwt-with-graphql/
źródło
secure
,samesite: strict
,http-only
?Aby zapobiec atakom CSRF, które wykorzystują istniejące pliki cookie, możesz ustawić plik cookie za pomocą
SameSite
dyrektywy. Ustaw go nalax
lubstrict
.To wciąż jest wersja robocza i od 2019 roku nie jest w pełni obsługiwana przez wszystkie obecne przeglądarki , ale w zależności od wrażliwości danych i / lub kontroli nad przeglądarkami używanymi przez użytkowników może być realną opcją. Ustawienie dyrektywy na
SameSite=lax
pozwoli na „nawigację najwyższego poziomu, która używa„ bezpiecznej ”... metody HTTP”.źródło