Открыть сервис

JSON Web Token

JSON Web Token (JWT) — это открытый стандарт (RFC 7519) для создания компактных и самодостаточных токенов доступа, предназначенных для передачи информации между двумя сторонами в виде JSON-объекта. JWT используется в системах аутентификации и авторизации, а также для безопасного обмена данными. Токен может быть проверен и доверен, поскольку он цифрово подписан (обычно с помощью HMAC или RSA/ECDSA). JWT компактен, что позволяет передавать его в URL, в HTTP-заголовках или в теле POST-запроса.

История

Стандарт JWT был разработан в 2010 году инженерами компании Atos, в частности, Джоном Брэдли и Натаниэлем Саком. В 2011 году он был принят как RFC 7519 под эгидой IETF (Internet Engineering Task Force). Изначально JWT создавался как расширение стандарта JSON Web Signature (JWS) и JSON Web Encryption (JWE), которые описывают подписание и шифрование данных в формате JSON. Основной целью JWT было создание простого и безопасного механизма для передачи утверждений (claims) между сторонами, который не требует хранения состояния на сервере (stateless). В 2015 году JWT стал частью спецификации OAuth 2.0 (RFC 7519) и получил широкое распространение в веб-разработке, особенно в микросервисной архитектуре и одностраничных приложениях (SPA). В России JWT активно используется в государственных информационных системах (например, в ЕСИА — Единой системе идентификации и аутентификации) и в коммерческих сервисах.

Структура токена

JWT состоит из трёх частей, разделённых точками (.), и имеет следующий формат: xxxxx.yyyyy.zzzzz. Каждая часть представляет собой Base64url-кодированный JSON-объект.

Заголовок (Header)

Заголовок содержит метаданные о токене: тип токена (обычно "typ": "JWT") и алгоритм подписи (например, "alg": "HS256" для HMAC-SHA256 или "alg": "RS256" для RSA). Пример заголовка:

``json { "alg": "HS256", "typ": "JWT" } ``

Полезная нагрузка (Payload)

Полезная нагрузка содержит утверждения (claims) — данные, которые передаются в токене. Утверждения делятся на три типа:

  • Зарегистрированные (registered): стандартные ключи, определённые в RFC 7519, такие как iss (issuer — издатель), sub (subject — субъект), aud (audience — аудитория), exp (expiration — время истечения), nbf (not before — не ранее), iat (issued at — время выдачи), jti (JWT ID — уникальный идентификатор токена).
  • Публичные (public): произвольные имена, которые могут быть зарегистрированы в реестре IANA, но обычно используются в рамках конкретной системы.
  • Частные (private): пользовательские утверждения, согласованные между сторонами (например, user_id, role).

Пример полезной нагрузки:

``json { "sub": "1234567890", "name": "Иван Иванов", "iat": 1516239022, "exp": 1516242622 } ``

Подпись (Signature)

Подпись создаётся путём кодирования заголовка и полезной нагрузки в Base64url, объединения их через точку и применения алгоритма подписи к полученной строке с использованием секретного ключа (для HMAC) или закрытого ключа (для RSA/ECDSA). Подпись позволяет проверить, что токен не был изменён после создания, и подтвердить его подлинность. Пример создания подписи для HMAC-SHA256:

`` HMACSHA256( base64UrlEncode(header) + "." + base64UrlEncode(payload), secret ) ``

Принцип работы

JWT используется в схемах аутентификации и авторизации, чаще всего в паре с протоколом OAuth 2.0. Процесс работы выглядит следующим образом:

  1. Аутентификация: Пользователь вводит логин и пароль на клиенте (например, веб-приложении). Клиент отправляет эти данные на сервер аутентификации.
  2. Выдача токена: Сервер проверяет учётные данные, и в случае успеха создаёт JWT, подписывает его и возвращает клиенту.
  3. Хранение токена: Клиент сохраняет JWT (обычно в localStorage, sessionStorage или в HTTP-куках с флагом HttpOnly).
  4. Отправка запросов: При каждом запросе к защищённому ресурсу клиент добавляет JWT в HTTP-заголовок Authorization в формате Bearer <token>.
  5. Верификация: Сервер ресурсов проверяет подпись JWT, срок действия и другие утверждения. Если токен валиден, сервер извлекает данные из полезной нагрузки и предоставляет доступ.

Основное преимущество JWT — отсутствие необходимости хранить сессию на сервере (stateless). Сервер может проверить токен автономно, без обращения к базе данных или кэшу.

Классификация алгоритмов подписи

JWT поддерживает два основных типа алгоритмов:

  • Симметричные (HMAC): Используется один секретный ключ как для создания, так и для проверки подписи. Примеры: HS256, HS384, HS512. Требуют, чтобы ключ был известен только серверу.
  • Асимметричные (RSA, ECDSA): Используется пара ключей — закрытый ключ для подписи и открытый ключ для проверки. Примеры: RS256, RS384, RS512, ES256, ES384, ES512. Позволяют разделять роли: сервер аутентификации подписывает токен закрытым ключом, а любой сервер ресурсов может проверить его открытым ключом.

Применение

JWT широко применяется в современных веб-приложениях и API:

  • Аутентификация пользователей: JWT используется в системах единого входа (SSO), например, в протоколах OpenID Connect (OIDC) и OAuth 2.0.
  • Авторизация в микросервисах: Каждый микросервис может проверить JWT без обращения к центральному серверу аутентификации, что упрощает архитектуру.
  • Обмен данными между системами: JWT используется для передачи утверждений между доверенными сторонами, например, между веб-приложением и API.
  • Мобильные приложения: JWT компактен и легко передаётся в HTTP-заголовках, что удобно для мобильных клиентов.
  • Государственные информационные системы: В России JWT применяется в ЕСИА (Единая система идентификации и аутентификации) для авторизации доступа к государственным услугам через портал «Госуслуги».

Критика и ограничения

Несмотря на популярность, JWT имеет ряд недостатков:

  • Неотзываемость: Поскольку JWT stateless, отозвать токен до истечения его срока сложно. Для решения этой проблемы используются чёрные списки (blacklist) или короткие сроки жизни токенов.
  • Размер: JWT может быть большим, если содержит много утверждений, что увеличивает размер HTTP-заголовков.
  • Безопасность хранения: Если JWT хранится в localStorage, он уязвим для XSS-атак. Рекомендуется использовать HttpOnly-куки.
  • Уязвимость к атакам с подменой алгоритма: Если сервер не проверяет алгоритм подписи, злоумышленник может изменить заголовок на none или на симметричный алгоритм, используя открытый ключ как секретный. Для защиты необходимо явно указывать допустимые алгоритмы и проверять подпись.
  • Сложность управления ключами: При использовании асимметричных алгоритмов требуется безопасное хранение и ротация ключей.

Интересные факты

  • JWT является основой для стандарта OpenID Connect (OIDC), который расширяет OAuth 2.0 для аутентификации.
  • В 2015 году JWT был включён в стандарт RFC 7519, который также описывает JSON Web Signature (JWS) и JSON Web Encryption (JWE).
  • JWT может быть зашифрован (JWE) для обеспечения конфиденциальности данных, а не только подписан.
  • В России JWT используется в системе «Московская электронная школа» для авторизации доступа к образовательным ресурсам.

Источники

  • RFC 7519 — JSON Web Token (JWT) (IETF, 2015).
  • RFC 7515 — JSON Web Signature (JWS) (IETF, 2015).
  • RFC 7516 — JSON Web Encryption (JWE) (IETF, 2015).
  • OpenID Connect Core 1.0 (OpenID Foundation, 2014).
  • Документация ЕСИА (Единая система идентификации и аутентификации), Министерство цифрового развития, связи и массовых коммуникаций РФ.
  • OAuth 2.0 Authorization Framework (RFC 6749, IETF, 2012).

BFOmetr — база данных и аналитика по компаниям России.

На главную BFOmetr →