URL-кодирование специальных символов: справочник для разработчиков
Подробный справочник по URL-кодированию специальных символов, включая пробелы, амперсанды, юникод и другие.
Специальные символы в URL
Синтаксис URL строго определён стандартом RFC 3986. Многие символы имеют специальное значение или недопустимы в определённых частях URL. Понимание того, как правильно кодировать эти символы, критически важно для создания надёжных веб-приложений и API.
Символ пробела
Пробел — самый часто кодируемый символ. Однако его можно закодировать двумя способами в зависимости от контекста:
%20— percent-encoding по RFC 3986, используется в путях URL и большинстве контекстов+— используется в форматеapplication/x-www-form-urlencoded(отправка HTML-форм)
При программном построении URL для единообразия отдавайте предпочтение %20. При формировании данных формы стандартом является нотация +.
Подробный разбор зарезервированных символов
Амперсанд (&)
Амперсанд разделяет параметры запроса. Когда амперсанд встречается в значении параметра, его необходимо закодировать как %26, чтобы он не был воспринят как разделитель. В HTML-контексте его также нужно кодировать сущностью как &.
Вопросительный знак (?)
Вопросительный знак отделяет путь от строки запроса. Если вопросительный знак встречается в значении параметра, его нужно закодировать как %3F. Обратите внимание, что encodeURI() НЕ кодирует вопросительные знаки, тогда как encodeURIComponent() кодирует.
Решётка (#)
Символ решётки начинает идентификатор фрагмента. В URL любой символ # в значении параметра запроса необходимо кодировать как %23, иначе браузер интерпретирует всё, что идёт после него, как идентификатор фрагмента и не отправит эту часть на сервер.
Прямой слеш (/)
Прямые слеши разделяют сегменты пути. Когда слеш встречается в значении сегмента пути (например, в имени файла, содержащем слеш), его нужно закодировать как %2F. Учтите, что некоторые серверы могут декодировать %2F и всё равно рассматривать его как разделитель пути.
Символы Unicode
Символы, не входящие в ASCII, кодируются путём предварительного преобразования их в последовательность байтов UTF-8, а затем percent-encoding каждого байта. Вот несколько примеров:
- Латинская e с акутом (é) → UTF-8: 0xC3 0xA9 →
%C3%A9 - Китайский иероглиф (中) → UTF-8: 0xE4 0xB8 0xAD →
%E4%B8%AD - Эмодзи (глобус) → UTF-8: 0xF0 0x9F 0x8C 0x8D →
%F0%9F%8C%8D
Кодирование в разных компонентах URL
| Компонент | Что нужно кодировать | Пример |
|---|---|---|
| Сегмент пути | Пробелы, ?, # и не-ASCII | /path/my%20file |
| Ключ запроса | =, &, #, +, пробелы | my%20key=value |
| Значение запроса | &, #, +, пробелы, = | key=hello%20world |
| Фрагмент | Пробелы и не-ASCII | #section%20one |
Распространённые ошибки
- Забыть закодировать
#в значениях запроса (остальная часть URL молча отбрасывается) - Двойное кодирование уже закодированных строк (приводит к
%2520вместо%20) - Использование
encodeURI()вместоencodeURIComponent()для значений параметров - Отсутствие кодирования
+в значениях запроса (он декодируется как пробел) - Предположение, что все серверы одинаково обрабатывают
%2Fв путях