Kliknięcie „Wyloguj” w systemie ERP klienta nie kończyło sesji. Aplikacja usuwała token JWT z przeglądarki, ale backend nie miał żadnego mechanizmu jego unieważniania, a czas życia tokena wynosił 24 godziny. Przechwycony token działał więc przez cały ten czas — niezależnie od tego, co robił prawowity użytkownik. Naprawa objęła skrócenie czasu życia tokena do 15 minut, wprowadzenie tokenów odświeżających i listę unieważnionych tokenów po stronie serwera.

Schemat powyżej: Po wdrożeniu deny listy backend sprawdza każdy token przed wykonaniem żądania i odrzuca ten, który został unieważniony — nawet jeśli kryptograficznie wciąż jest poprawny.

Kluczowe ustalenia

  • Wylogowanie działało wyłącznie po stronie przeglądarki — token znikał z Local Storage, ale pozostawał ważny na serwerze.
  • Czas życia tokena dostępowego wynosił 24 godziny, bez mechanizmu odświeżania.
  • Backend nie prowadził listy unieważnionych tokenów, więc nie miał jak odrzucić skradzionego.
  • Skutek: okno na wykorzystanie wykradzionego tokena było równe pełnej dobie, a nie sekundom.

Kontekst: „przecież kliknąłem wyloguj”

System ERP był sercem operacji klienta — zarządzał produkcją, magazynem i danymi kadrowymi. Zespół deweloperski wdrożył uwierzytelnianie oparte na JSON Web Tokens (JWT), żeby uzyskać bezstanowość i wydajność. Zabrakło jednej rzeczy: bezstanowość nie zwalnia z zarządzania cyklem życia sesji.

To rozróżnienie jest źródłem większości problemów z JWT, jakie spotykamy podczas testów penetracyjnych aplikacji webowych. Token, którego nie da się cofnąć, jest wygodny dla serwera i niebezpieczny dla organizacji.

Na czym polegał problem: tokeny wiecznie żywe

Aplikacja frontendowa poprawnie usuwała token z Local Storage po kliknięciu „Wyloguj”. Backend nie miał jednak żadnej listy unieważnionych tokenów, a ich czas życia ustawiono na 24 godziny. Z punktu widzenia serwera każdy podpisany, nieprzeterminowany token był dowodem tożsamości — bez względu na to, czy użytkownik uważał się za wylogowanego.

Jak pracowaliśmy: przechwycenie i ponowne użycie

W kontrolowanym środowisku odtworzyliśmy pełny scenariusz nadużycia.

  1. Użytkownik loguje się do systemu i otrzymuje token.
  2. Przechwytujemy token — symulując wyciek przez podatność XSS albo przez logi serwera proxy.
  3. Użytkownik klika „Wyloguj”.
  4. Wysyłamy żądanie do API z przechwyconym tokenem.

Backend zrealizował żądanie bez zastrzeżeń. Token był kryptograficznie poprawny, a jego czas życia jeszcze nie minął — z perspektywy serwera nic się nie wydarzyło.

Ryzyko biznesowe: dostęp z opóźnionym zapłonem

W razie wycieku tokena atakujący miał do 24 godzin swobodnego działania w systemie ERP, nawet jeśli użytkownik wylogował się minutę po kradzieży. W systemie tej klasy oznacza to możliwość odczytu i modyfikacji danych finansowych oraz dostęp do danych osobowych pracowników. Reakcja typu „natychmiast wyloguj wszystkich” nic by nie dała, bo nie było czego wylogowywać.

Co zaleciliśmy i co wdrożono

  1. Skrócenie czasu życia tokena dostępowego do 15 minut. Samo to zmniejsza okno nadużycia z doby do kwadransa.
  2. Wprowadzenie tokenów odświeżających (refresh tokens). Długo żyjący token trzymany jest po stronie serwera i można go w każdej chwili unieważnić.
  3. Lista unieważnionych tokenów (deny list) w pamięci podręcznej. Backend sprawdza w niej każdy token przed wykonaniem żądania; wpisy wygasają razem z tokenem, więc lista nie rośnie w nieskończoność.

Efekt: wylogowanie zaczęło działać

Po wdrożeniu poprawek kliknięcie „Wyloguj” faktycznie kończy sesję, a przechwycony token staje się bezużyteczny w tej samej sekundzie. Retest potwierdził, że żądanie z unieważnionym tokenem zwraca odpowiedź 401.

Jak zabezpieczyć się przed tym atakiem

Jeżeli wdrażasz uwierzytelnianie oparte na tokenach, pilnuj jednego: bezstanowość nie jest wymówką dla braku zarządzania sesją. Wymagaj mechanizmu unieważniania po stronie serwera. Czas życia dostępu licz w minutach, a długotrwałą sesję opieraj na mechanizmie odświeżania, który da się odciąć.

Warto też sprawdzić, co się dzieje przy zmianie hasła i przy odbieraniu uprawnień — w obu sytuacjach stare tokeny powinny przestać działać natychmiast, a nie po dobie.

Powiązane case studies

Jak Pentestica może pomóc

Mechanizmy uwierzytelniania i zarządzania sesją to obszar, w którym „działa” i „jest bezpieczne” to dwie różne rzeczy. Sprawdzamy je w ramach testów penetracyjnych aplikacji webowych, a szersza ocena procesów i konfiguracji należy do audytu bezpieczeństwa IT.

Zamów bezpłatną wycenę

Cyberbezpieczeństwo dla firm - Pentestica

Redakcja Pentestica to zespół pentesterów i konsultantów bezpieczeństwa, którzy na co dzień wykonują testy penetracyjne, testy TLPT wymagane przez DORA, red teaming i audyty bezpieczeństwa IT, a także prowadzą wdrożenia zgodności z NIS2, DORA i MiCA. Teksty na tym blogu piszemy z tej praktyki, a nie z opracowań. Każde twierdzenie o przepisie, terminie albo karze opieramy na źródle pierwotnym: dzienniku ustaw, tekście dyrektywy, komunikacie organu nadzoru. Jeśli czegoś nie da się potwierdzić, piszemy o tym wprost, zamiast powtarzać liczbę krążącą po branżowych portalach.

Bezpłatna wycena Napisz