JavaScript7 мин чтения

В чём разница между encodeURI и encodeURIComponent?

encodeURI кодирует URL целиком, сохраняя структурные символы вроде /, ? и #. encodeURIComponent кодирует отдельный компонент URI, экранируя все специальные символы, включая /, ? и &. Используйте encodeURIComponent для значений параметров запроса, а encodeURI — для полных URL.

Что такое encodeURI()?

encodeURI() — это встроенная функция JavaScript, предназначенная для кодирования полного идентификатора ресурса (URI). Она преобразует символы, недопустимые в URI, в их процентно-кодированные эквиваленты, но при этом намеренно сохраняет символы, имеющие структурное значение внутри URI.

В частности, encodeURI() не кодирует следующие символы: A-Z a-z 0-9 ; , / ? : @ & = + $ - _ . ! ~ * ' ( ) #. Это означает, что общая структура URL после кодирования остаётся неизменной.

// encodeURI() сохраняет структуру URL
const url = 'https://example.com/my page?name=John Doe&city=New York';
console.log(encodeURI(url));
// "https://example.com/my%20page?name=John%20Doe&city=New%20York"
// Обратите внимание: :, /, ?, & и = НЕ кодируются

Такое поведение делает encodeURI() идеальным выбором, когда у вас есть полный URL, который может содержать пробелы или не-ASCII символы, но чьи структурные символы (разделитель протокола, разделители пути, маркеры строки запроса) должны остаться как есть.

Что такое encodeURIComponent()?

encodeURIComponent() предназначена для кодирования отдельного компонента URI, например значения параметра запроса или сегмента пути. В отличие от encodeURI(), она кодирует почти каждый специальный символ, включая те, что имеют структурное значение в URL.

Единственные символы, которые encodeURIComponent() не кодирует, — это: A-Z a-z 0-9 - _ . ! ~ * ' ( ). Всё остальное, включая /, ?, &, =, # и :, подвергается процентному кодированию.

// encodeURIComponent() кодирует всё, кроме незарезервированных символов
const value = 'Tom & Jerry / Friends?';
console.log(encodeURIComponent(value));
// "Tom%20%26%20Jerry%20%2F%20Friends%3F"
// Обратите внимание: &, / и ? КОДИРУЮТСЯ

// Формирование URL с параметром запроса
const url = 'https://example.com/search?q=' + encodeURIComponent(value);
// "https://example.com/search?q=Tom%20%26%20Jerry%20%2F%20Friends%3F"

Поскольку функция кодирует структурные символы, её никогда не следует применять encodeURIComponent() к полному URL. Это привело бы к кодированию ://, всех разделителей пути / и разделителя запроса ?, сделав URL непригодным для использования.

Ключевые различия с первого взгляда

Характеристика encodeURI() encodeURIComponent()
Назначение Кодирование полного URI Кодирование компонента URI
Кодирует / Нет Да (%2F)
Кодирует ? Нет Да (%3F)
Кодирует & Нет Да (%26)
Кодирует = Нет Да (%3D)
Кодирует # Нет Да (%23)
Кодирует : Нет Да (%3A)
Кодирует пробелы Да (%20) Да (%20)
Кодирует Unicode Да Да

Когда использовать каждую функцию

Правило простое: используйте encodeURI(), когда нужно закодировать полный URL, сохранив его структуру корректной. Используйте encodeURIComponent(), когда нужно закодировать отдельное значение, которое будет вставлено в URL.

// Сценарий 1: Кодирование полного URL с пробелами
const fullUrl = 'https://example.com/my documents/file name.pdf';
const encoded = encodeURI(fullUrl);
// "https://example.com/my%20documents/file%20name.pdf"

// Сценарий 2: Сборка URL из частей
const baseUrl = 'https://api.example.com/search';
const query = 'price >= 100 & category = books';
const finalUrl = baseUrl + '?q=' + encodeURIComponent(query);
// "https://api.example.com/search?q=price%20%3E%3D%20100%20%26%20category%20%3D%20books"

// Сценарий 3: Кодирование URL перенаправления как параметра
const redirectUrl = 'https://example.com/callback?token=abc';
const loginUrl = 'https://auth.example.com/login?redirect=' +
  encodeURIComponent(redirectUrl);
// Весь URL перенаправления кодируется как единое значение параметра

Типичные ошибки и как их избежать

Ошибка 1: Использование encodeURI() для значений параметров запроса. Поскольку encodeURI() не кодирует & или =, применение её к значению параметра, содержащему эти символы, нарушит структуру строки запроса.

// НЕПРАВИЛЬНО
const bad = 'https://example.com/search?q=' + encodeURI('salt & pepper');
// "https://example.com/search?q=salt%20&%20pepper"
// Сервер видит q="salt " и дополнительный параметр " pepper"

// ПРАВИЛЬНО
const good = 'https://example.com/search?q=' + encodeURIComponent('salt & pepper');
// "https://example.com/search?q=salt%20%26%20pepper"

Ошибка 2: Применение encodeURIComponent() к полному URL. Это разрушает структуру URL, кодируя все слэши, двоеточия и знаки вопроса.

// НЕПРАВИЛЬНО
console.log(encodeURIComponent('https://example.com/path?key=value'));
// "https%3A%2F%2Fexample.com%2Fpath%3Fkey%3Dvalue"
// Это больше не корректный URL!

// ПРАВИЛЬНО
console.log(encodeURI('https://example.com/path?key=value'));
// "https://example.com/path?key=value" (уже корректен, кодировать нечего)

Ошибка 3: Двойное кодирование. Если строка уже процентно-закодирована, повторное кодирование закодирует знаки %, превратив %20 в %2520. Всегда проверяйте, не было ли значение уже закодировано, прежде чем применять функции кодирования.

Более безопасная современная альтернатива — API URL и URLSearchParams, которые выполняют кодирование автоматически и помогают полностью избежать этих подводных камней.

Похожие статьи

Попробуйте наши бесплатные инструменты