JSON Web Token
JSON Web Token (JWT, МФА: [dʒɒt], вимовляється "джот"[1]) це стандарт токена доступу на основі JSON, стандартизованого в RFC 7519. Як правило, використовується для передачі даних для аутентифікації в клієнт-серверних програмах. Токени створюються сервером, підписуються секретним ключем і передаються клієнту, який надалі використовує цей токен для підтвердження своєї особи.
Токен JWT складається з трьох частин: заголовка (header), корисного навантаження (payload) та підпису або даних шифрування. Перші два елементи – це JSON об'єкти певної структури. Третій елемент обчислюється на основі перших і залежить від обраного алгоритму (у разі використання непідписаного JWT може бути опущений).
Заголовок (Header) це JSON елемент, що описує до якого типу належить даний токен і які методи шифрування використовувались.
Поле | Назва | Значення |
---|---|---|
typ | Type | Описує медіатип IANA Medientyp токену. В даному випадку JWT завжди мають медіатипapplication/jwt .
|
cty | Content Type | Це поле встановлюється коли JWT містить в собі інший JWT, в противному разі це поле пропускається. |
alg | Algorithm | Описує використаний алгоритм шифрування. Зазвичай використовують HMAC з SHA-256 (HS256 ) або RSA з SHA-256 (RS256 ). Можна також не використовувати жодного шифрування, вказавши none , але це не рекомендується. Можливі значення вказуються в стандарті JSON Web Encryption (JWE) RFC 7516.
|
Заголовок може наприклад виглядати так:
{
"alg": "HS256",
"typ": "JWT"
}
Вміст (англ. Payload) складається з елемента JSON, який описує твердження.
{
"sub": "1234567890",
"name": "John Doe",
"admin": true
}
Деякі твердження зарезервовані:
Поле | Назва | Значення |
---|---|---|
iss | Issuer | Той хто видав токен |
sub | Subject | Визначає якого суб'єкта стосуються твердження, тобто щодо кого або чого робляться твердження. |
aud | Audience | Цільова аудиторія токена. |
exp | Expiration Time | Час закінчення терміну дії токена в форматі Unix (кількість секунд що пройшли від 1970-01-01T00:00:00Z ).
|
nbf | Not Before | Час в форматі Unix до настання якого токен не дійсний. |
iat | Issued At | Коли токен був виданий (в форматі Unix) |
jti | JWT ID | Унікальна, чутлива до регістру послідовність символів, яка однозначно ідентифікує токен. Може застосовуватись для запобігання повторному використанню токена. Це можуть бути порядкові числа, GUID або Хеш. |
Решта - це Public Claims які визначаються IANA.[2] Крім того, той хто видає JWT може також додати Private Claim використавши URI, хоча це не є стандартизованим. Наприклад, тут може бути використана якась онтологія, на зразок Дублінського ядра або FOAF.
Структура підпису визначається стандартом JSON Web Signature (JWS, RFC 7515).
Щоб згенерувати підпис, заголовок та вміст кодуються в Base64, записуються в один рядок через крапку, а потім цей рядок хешується визначеним методом:
var encodedString = base64UrlEncode(header) + "." + base64UrlEncode(payload);
var hash = HMACSHA256(encodedString, secret);
Заголовок, вміст і підпис кожен кодуються в Base64 і розділяються в токені крапкою. JWT може виглядати так:
eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJzY290Y2guaW8iLCJleHAiOjEzMDA4MTkzdHJ1ZX0.03f329983b86f7d9a9f5fef85305880101d5e302afafa20154d094b229f75773
JWT передається в заголовках HTTP, зазвичай двома способами:
- в полі Authorization як Bearer-Token:
Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...
- в полі Cookie:
Cookie: token=eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...
Обидва методи мають різні переваги і недоліки:
Bearer-Token | Cookie | |
---|---|---|
Заголовок | Authorization: Bearer <JWT>
|
Cookie: token=<JWT>
|
CORS | Працює з CORS, проте необхідна реалізація на JavaScript. | Кукі зберігаються в браузері лише для конкретного домену, CORS неможливий. |
Зберігання | Можливі всі способи зберігання доступні для JavaScript, як наприклад WebStorage чи Cookie-Store. |
Cookie розміщуються в Cookie-Store. |
Захист від MITM | Наявність TLS повинна перевірятись в JavaScript. | Коли на кукі встановлюється прапорець secure , тоді примусово застосовується TLS.
|
Захист від XSS | Повинен реалізовуватись в JavaScript. | Неявний, якщо для кукі встановлено прапорець HttpOnly , для запобігання доступу через JavaScript.
|
Захист від CSRF | Неможливий. Необхідні інші заходи. | Повинен реалізовуватись в JavaScript |
Підписані JSON-токени описуються JWS специфікацією (RFC 7515).
Підпис заголовка та корисного навантаження виконується такими алгоритмами:
Обов'язковий для підтримки всіма реалізаціями алгоритм:
Рекомендовані алгоритми:
Також підтримуються варіації рекомендованих алгоритмів з використанням SHA-384 та SHA-512 відповідно:
- HS384, HS512
- RS384, RS512
- ES384, ES512
Абревіатури курсивом - назви, що використовуються в JSON-токенах, описані специфікацією JWA ([rfc:7519 RFC 7518])
У разі підписаного JWT до заголовка можуть бути додані додаткові ключі:
- jku: URI на набір відкритих ключів у JSON-форматі, що використовуються для підпису даного токена (JSON Web Key Set URL).
- jwk: Ключ, який використовується для підпису цього токена (JSON Web Key).
- kid: Унікальний ідентифікатор ключа для випадку, коли вказується набір ключів (Key ID).
- x5u: URI на набір сертифікатів X.509. Перший сертифікат у наборі повинен бути тим, який використовувався для підпису токена (X.509 URL).
- x5c: Масив сертифікатів X.509 у форматі JSON, використаних для підпису даного токена (X.509 certifcate chain).
- x5t: Цифровий відбиток сертифіката SHA1 X.509 (X.509 certificate SHA-1 fingerprint).
- crit: Масив рядків із назвами ключів даного заголовка, які мають оброблятися парсером JWT. Якщо мають бути оброблені всі ключі, то використовується (critical).[12]
Реалізації JWT доступні на безлічі платформ. Актуальний список можна знайти на сайті JWT.io[3]
Security Event Token (SET) розширює стандарт JWT твердженням events
, яке містить список подій що стосуються безпеки.[4] Ці токени містять відмітку часу і дійсні необмежений час. Вміст SET-токена може виглядати наступним чином:
{
"iss": "https://server.example.com",
"sub": "248289761001",
"aud": "s6BhdRkqt3",
"iat": 1471566154,
"jti": "bWJq",
"sid": "08a5019c-17e1-4977-8f42-65a12843ea02",
"events": {
"http://schemas.openid.net/event/backchannel-logout": {}
}
}
SET можуть використовуватись для аудиту[de]. На даний час (травень 2018) IETF поки що не створило для SET офіційного RFC.
- Security Assertion Markup Language (SAML)
- Simple Web Token (SWT)
- OAuth та OpenID
- ↑ Scalable Microservices with Kubernetes - Udacity
- ↑ JSON Web Token Claims. Архів оригіналу за 9 листопада 2017. Процитовано 20 жовтня 2017.
- ↑ JWT. Архів оригіналу за 25 жовтня 2017. Процитовано 20 жовтня 2017.
- ↑ Security Event Token (SET) Specification and IETF Security Events Working Group. Архів оригіналу за 21 жовтня 2017. Процитовано 20 жовтня 2017.