Спецификация JWT позволяет токену самому указывать, какой алгоритм использовать. Это единственное дизайнерское решение стоит за большинством проблем с JWT в продакшене.
Вот что PASETO делает иначе.
1. Атака живёт в заголовке
JWT содержит поле
alg, которое указывает свой же алгоритм подписи. Вы можете установить его в "none", и некоторые библиотеки пропустят проверку.Или взять публичный RSA-ключ, использовать его как HMAC-секрет, подписать через HS256 — и сервер, доверяющий заголовку, примет поддельный токен.
Это атака RS256→HS256 confusion, и она до сих пор ломает реальные системы.
2. PASETO привязывает криптографию к версии
Токен PASETO имеет формат
version.purpose.payload. Версия фиксирует набор шифров — нечего согласовывать.v4.public — всегда Ed25519. v4.local — всегда XChaCha20 с BLAKE2b. Нет заголовка alg — нет атаки alg:none и confusion-атак.3. Вы выбираете назначение, а не алгоритм
Локальный токен (
local) зашифрован симметричным ключом. Публичный токен (public) подписан так, что любой с публичным ключом может его проверить.Стандартный JWT только подписан — payload читается как обычный base64, и секреты утекают, когда люди забывают об этом.
4. Для сессий не нужно ни то, ни другое
JWT безопасны только как короткоживущие токены — минуты, а не недели, на которые тянется сессия. Google делает именно так: JWT используется только для передачи логина между хостами, а сессия в браузере остаётся кукой.
PASETO — лучший выбор для короткоживущего подписанного токена: SSO-переходы, межсервисные вызовы, одноразовое использование.
Для сессий проще кука, подкреплённая Postgres или Redis, а отзыв одной сессии — это удаление одной строки.
Большинство логинов хватаются за токен там, где подошла бы сессия.
https://gist.github.com/samsch/0d1f3d3b4745d778f78b230cf6061452
👉 Java Portal
