Задать вопрос
@Galdar
Web, JS, PHP, NGINX, Linux

Как расшифровать JWT токен?

Вот есть пример на сайте
eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c

Пытаюсь его расшифровать и не получиться.
$jwt = 'eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c';
$key = "";

$decoded = JWT::decode($jwt, $key, array('HS256'));
$answer = $decoded;

Я так понимаю дело в ключе. Но какой ключ писать то? Читаю про JWT но не могу понять

ДОП:
Как я понял ключ указан в футере
secret
5f51eb66b58a9150260974.png

И правильно я понимаю, что JWT токен который я получаю у него нужно взять хвос и перевести его. Только вот как и из чего пока не разобрался.
  • Вопрос задан
  • 13329 просмотров
Подписаться 2 Простой Комментировать
Помогут разобраться в теме Все курсы
  • Skillbox
    Веб-разработчик на PHP
    9 месяцев
    Далее
  • Хекслет
    PHP-разработчик
    10 месяцев
    Далее
  • Нетология
    Веб-разработчик с нуля: профессия с выбором специализации
    14 месяцев
    Далее
Решения вопроса 2
Stalker_RED
@Stalker_RED
Токен состоит из трех частей разделенных точкой. Каждая часть кодируется немного модифицированным base64.
Первые две раскодируются вообще без ключа. В конце подпись, кодированная ключом. В вашем примере это
your-256-bit-secret (попробуйте там справа, где синенькое напечатать другой ключ и смотрите как меняется токен).

<?php
$key = 'your-256-bit-secret'; // ваш ключ
$jwtToken = 'eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c';
$jwtArr = array_combine(['header', 'payload', 'signature'], explode('.', $jwtToken));

var_export($jwtArr); /* -> разделяем по точкам
array (
  'header' => 'eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9',
  'payload' => 'eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ',
  'signature' => 'SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c',
) */

echo PHP_EOL . base64_decode($jwtArr['header']) . PHP_EOL; // декодированный заголовок
// -> {"alg":"HS256","typ":"JWT"}
echo base64_decode($jwtArr['payload']) . PHP_EOL; // декодированная нагрузка
// -> {"sub":"1234567890","name":"John Doe","iat":1516239022}

$calculatedHash = hash_hmac( // сами считаем хеш
	'sha256',
	$jwtArr['header'] . '.' . $jwtArr['payload'],
	$key,
	true);

echo base64_encode($calculatedHash) . PHP_EOL;
// -> SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV/adQssw5c=

echo $jwtArr['signature'] . PHP_EOL;
// -> SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c
// Похоже? Там слегка модифицированный base64


Третья часть - подпись. Если взять первые две части и получить sha265-хеш с использованием вашего ключа, то он должен совпасть с первой частью. Это подтвердит, что первые две части никто не изменял.

Хоть бы вики почитал, в самом деле :)
Ответ написан
Rsa97
@Rsa97
Для правильного вопроса надо знать половину ответа
JWT состоит из трёх частей, разделённых точками. Первая часть - заголовок, вторая - полезная нагрузка (payload), третья часть - подпись. Подпись представляет из себя шифрованный по ключу хэш от первых двух частей.

При выдаче токена сервер генерирует заголовок и полезную нагрузку, записывает их в JSON и кодирует в модифицированный BASE64. Получается две строки. Эти строки объединяются через точку и от полученной общей строки вычисляется подпись. Конкретный алгоритм вычисления указан в заголовке. Далее подпись через точку присоединяется к строке и получается полный токен.

При получении запроса с токеном сервер разделяет токен на части, распаковывает заголовок и находит алгоритм подписи. Затем он вычисляет контрольную подпись от первых двух частей токена и сравнивает её с полученной в токене. Если они совпадают, то токен признаётся правильным.

При использовании симметричного алгоритма один и тот же ключ знают как сервер, выдающий токен, так и сервер, проверяющий его. Асимметричное шифрование позволяет выдавать токен на одном сервере по закрытому ключу, а проверять на другом сервере по парному открытому ключу.
Ответ написан
Комментировать
Пригласить эксперта
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Похожие вопросы
FoodSoul Калининград
от 180 000 до 250 000 ₽
IT-Spirit Москва
от 230 000 до 320 000 ₽
от 200 000 до 290 000 ₽