URL-безопасное кодирование Base64: что это и почему это важно
Что такое URL-безопасное кодирование Base64?
URL-безопасное кодирование Base64 (также называемое Base64url) — это вариант стандартного Base64, который заменяет символы, имеющие специальное значение в URL и именах файлов, на безопасные альтернативы. Стандартный Base64 использует + и / в составе своего 64-символьного алфавита, а также = для дополнения, и все три проблематичны в URL, строках запросов и путях к файлам.
Base64url решает эту проблему двумя простыми заменами:
| Стандартный Base64 | URL-безопасный Base64 |
|-----------------|-----------------|
| + (плюс) | - (минус) |
| / (слеш) | _ (подчёркивание) |
| = (дополнение) | опускается (обычно) |
Почему стандартный Base64 ломает URL
Когда строка в формате Base64, содержащая + или /, появляется в URL, поведение браузера и сервера становится непредсказуемым.
Проблема с +
В строках запросов URL символ + интерпретируется как пробел. Это поведение происходит из спецификации application/x-www-form-urlencoded и приводит к тому, что декодированные данные содержат неожиданные пробелы.
Например, строка Base64 вида Pj4+Pz8/Pw== содержит символы +. Если она появляется в параметре URL ?token=Pj4+Pz8/Pw==, сервер увидит ?token=Pj4 Pz8/Pw== — + превращается в пробел.
Проблема с /
В путях URL символ / является разделителем пути. Строка Base64 вида ab/CD+Ef== содержит /, который будет интерпретирован как уровень директории. Если она появляется в сегменте URL, и клиент, и сервер могут неправильно интерпретировать структуру.
Проблема с =
Символ = используется для пар ключ-значение в строках запросов. Завершающий = в ?data=SGVsbG8= может быть неоднозначным — является ли = частью дополнения Base64 или синтаксисом параметра запроса?
Хотя процентное кодирование может исправить эти проблемы (+ превращается в %2B, / — в %2F), оно увеличивает длину строки и усложняет отладку. Base64url — более чистое решение.
Как работает Base64url
Base64url формально определён в RFC 4648 Section 5. Он использует точно такой же алгоритм, как и стандартный Base64 — 3 байта превращаются в 4 символа — но с заменой одного символа на позициях 62 и 63 алфавита:
- Индекс алфавита 62:
+→-(минус) - Индекс алфавита 63:
/→_(подчёркивание)
Дополнение (=) обычно удаляется, поскольку его можно вывести из длины строки при декодировании. Строка Base64url всегда является допустимым компонентом URL без дополнительного экранирования.
До и после
Вот как одни и те же бинарные данные выглядят в обоих форматах:
Стандартный: Pj4+Pz8/Pw==
URL-безопасный: Pj4-Pz8_Pw
Где используется Base64url
JSON Web Tokens (JWT)
JWT — самый заметный пользователь Base64url. Каждый JWT состоит из трёх частей — заголовка, полезной нагрузки и подписи — каждая из которых закодирована в URL-безопасном Base64 и разделена точками:
eyJhbGciOiJIUzI1NiJ9.eyJzdWIiOiIxMjM0NTY3ODkwIn0.dozjgNqP0m2iTgCjD0
Обратите внимание на дефисы и подчёркивания — никаких знаков плюса или слешей. Если бы JWT использовал стандартный Base64, токены ломались бы при передаче в качестве параметров URL, что является наиболее распространённым способом их использования в веб-приложениях.
OAuth и OpenID Connect
Как OAuth 2.0, так и OpenID Connect полагаются на JWT для токенов доступа и ID-токенов, что делает кодирование Base64url фундаментальным для современной аутентификации. Поток кода авторизации, неявный поток и поток клиентских учётных данных — все передают токены, использующие Base64url.
Веб-API и параметры запросов
Многие REST и GraphQL API принимают данные в формате Base64 в параметрах запросов для курсоров пагинации, фильтров или закодированных нагрузок. Base64url гарантирует, что эти параметры работают корректно без дополнительного URL-кодирования.
Реальный пример — курсорная пагинация API:
GET /api/users?cursor=MjAyNC0wMS0xNVQxMDozMDowMFo
API GitHub использует именно этот шаблон для пагинации больших наборов результатов.
Имена файлов и файловое хранилище
Строки Base64url образуют безопасные имена файлов, поскольку они не содержат разделителей пути (/), специальных символов, сбивающих с толку файловые системы, и символов, недопустимых в Windows (:, *, ? и т.д.).
Сети доставки контента и ключи кэша
CDN и слои кэширования часто используют значения в формате Base64url в качестве ключей кэша. Стандартный Base64 с / создавал бы ложные иерархии директорий в пространстве имён кэша, что приводило бы к неоднозначным ключам.
Преобразование между стандартным Base64 и Base64url
Преобразование между двумя вариантами просто реализуется на любом языке:
JavaScript
// Стандартный Base64 в URL-безопасный Base64
function base64ToBase64url(base64) {
return base64.replace(/\+/g, '-').replace(/\//g, '_').replace(/=+$/, '');
}
// URL-безопасный Base64 в стандартный Base64
function base64urlToBase64(base64url) {
let result = base64url.replace(/-/g, '+').replace(/_/g, '/');
// Восстановление дополнения
while (result.length % 4) {
result += '=';
}
return result;
}
Node.js
Node.js предоставляет нативную поддержку Base64url начиная с версии 15.7.0:
// Кодирование в Base64url
const encodedUrl = Buffer.from('Hello, world!').toString('base64url');
console.log(encodedUrl);
// Output: SGVsbG8sIHdvcmxkIQ
// Декодирование из Base64url
const decoded = Buffer.from(encodedUrl, 'base64url').toString('utf-8');
console.log(decoded);
// Output: Hello, world!
Python
import base64
# Кодирование в Base64url
encoded = base64.urlsafe_b64encode(b"Hello, world!")
print(encoded.decode())
# Output: SGVsbG8sIHdvcmxkIQ==
# Декодирование из Base64url
decoded = base64.urlsafe_b64decode(encoded)
print(decoded.decode())
# Output: Hello, world!
Когда использовать стандартный Base64, а когда Base64url
Используйте стандартный Base64 когда:
- Кодируете вложения электронной почты (этого требует стандарт MIME)
- Генерируете data URL для встраивания в HTML/CSS
- Храните данные в базах данных, где безопасность URL не важна
- Взаимодействуете с устаревшими системами, ожидающими стандартный Base64
Используйте Base64url когда:
- Создаёте или разбираете JWT-токены
- Передаёте закодированные данные в параметрах запросов URL или сегментах пути
- Генерируете имена файлов из бинарных данных
- Создаёте ключи кэша или идентификаторы
- Работаете с OAuth-токенами или OpenID Connect
Попробуйте URL-безопасное кодирование Base64 онлайн
Используйте наш бесплатный онлайн кодировщик и декодировщик Base64 для преобразования между стандартным Base64 и URL-безопасным форматом Base64. Вставьте свои данные, выберите вариант и мгновенно получите результат.