Как реализована проверка токенов?
Что проверяют
Понимаете ли вы, что именно сервер проверяет в токене и почему одна подпись без остальных проверок не защищает. Следом почти всегда спрашивают, как отозвать JWT до истечения срока и что можно кешировать.
Как отвечать
Начните с типа токена. JWT проверяется локально, без похода в базу; непрозрачный токен проверяется у сервера авторизации через introspection (RFC 7662) или по таблице сессий. Для JWT на Python (PyJWT или authlib) проверка состоит из нескольких шагов:
- подпись:
jwt.decode()с явным спискомalgorithms=["RS256"]. Алгоритм задаёт ваша настройка, а не заголовок токена; - ключ: для HS256 общий секрет, для RS256 и ES256 публичный ключ с JWKS-эндпоинта провайдера.
PyJWKClientкеширует ключи и выбирает нужный поkid; - сроки:
expиnbfпроверяются автоматически, небольшойleewayв несколько секунд спасает от расхождения часов. Обязательностьexpвключается черезoptions={"require": ["exp"]}; - адресат и издатель: параметры
audienceиissuer. Без них токен, выданный соседнему сервису того же провайдера, пройдёт и у вас; - права: после декодирования смотрят
scopeили роли, это уже авторизация, а не аутентификация.
В FastAPI это оформляется зависимостью через Depends и HTTPBearer: она возвращает текущего пользователя или отдаёт 401. В DRF есть готовый класс аутентификации из djangorestframework-simplejwt.
Про отзыв: подписанный JWT валиден до exp, поэтому access-токен делают коротким, в пределах 15 минут, а для экстренного отзыва держат denylist по jti в Redis с TTL до конца жизни токена. Кешировать уместно JWKS и ответы introspection, но не дольше срока жизни самого токена.
Где спотыкаются
Не фиксируют алгоритм. Старые библиотеки принимали alg: none или путали HS и RS, и подделать токен было нетрудно.
Путают кодирование с шифрованием. Payload JWT закодирован в base64url, его читает кто угодно, класть туда персональные данные нельзя.
Проверяют подпись и срок, но забывают aud. Или выписывают токен через datetime.utcnow(), который устарел с Python 3.12, вместо datetime.now(timezone.utc).