Сервер.UrlEncode противHttpUtility.UrlEncode
Вопрос
Есть ли разница между Server.UrlEncode и HttpUtility.UrlEncode?
Решение
HttpServerUtility.UrlEncode
будет использовать HttpUtility.UrlEncode
внутренне.Здесь нет никакой конкретной разницы.Причина существования Server.UrlEncode
есть совместимость с классическим ASP.
Другие советы
Раньше у меня были сильные головные боли при использовании этих методов, Я рекомендую вам избегать любой вариант UrlEncode
, и вместо этого использовать Uri.EscapeDataString
- по крайней мере, у этого человека понятное поведение.
Давайте посмотрим...
HttpUtility.UrlEncode(" ") == "+" //breaks ASP.NET when used in paths, non-
//standard, undocumented.
Uri.EscapeUriString("a?b=e") == "a?b=e" // makes sense, but rarely what you
// want, since you still need to
// escape special characters yourself
Но моим личным фаворитом должно быть HttpUtility.UrlPathEncode UrlPathEncode - эта штука действительно непостижима.Он кодирует:
- " " ==> "%20"
- "100% true" ==> "100%%20true" (ок, теперь ваш URL не работает)
- "тест A.aspx#привязка B" ==> "тест%20A.aspx#якорь%20B"
- "тест A.aspx?хм#привязка B" ==> "тест%20A.aspx?хм#якорь B" (обратите внимание на разницу с предыдущей escape-последовательностью!)
В нем также есть специальная документация MSDN для lovelily "Кодирует часть пути строки URL для надежной передачи HTTP с веб-сервера клиенту ". - без фактического объяснения того, что это делает.У вас меньше шансов выстрелить себе в ногу из "УЗИ"...
Короче говоря, придерживайтесь Uri.EscapeDataString (Экранированный запрос).
Перенесемся почти на 9 лет вперед с тех пор, как этот вопрос был задан впервые, и в мире .NET Core и .NET Standard, похоже, наиболее распространенными вариантами, которые у нас есть для кодирования URL, являются Веб-использование.UrlEncode (под System.Net
) и Uri.EscapeDataString (Экранированный запрос).Судя по самому популярному ответу здесь и в других местах, Uri.EscapeDataString (Экранированный запрос) представляется предпочтительным.Но так ли это?Я провел некоторый анализ, чтобы понять различия, и вот что я получил:
WebUtility.UrlEncode
кодирует пространство как+
;Uri.EscapeDataString
кодирует его как%20
.Uri.EscapeDataString
процент-кодирует!
,(
,)
, и*
;WebUtility.UrlEncode
не делает этого.WebUtility.UrlEncode
процент-кодирует~
;Uri.EscapeDataString
не делает этого.Uri.EscapeDataString
бросаетUriFormatException
для строк длиной более 65 520 символов;WebUtility.UrlEncode
не делает этого.(Более распространенная проблема, чем вы могли бы подумать, особенно при работе с данными формы в кодировке URL.)Uri.EscapeDataString
бросаетUriFormatException
на высокие суррогатные символы;WebUtility.UrlEncode
не делает этого.(Это формат UTF-16, вероятно, гораздо менее распространенный.)
Для целей кодирования URL-адресов символы подпадают под одну из 3 категорий:неограниченный (законный в URL-адресе);зарезервировано (законно, но имеет особое значение, поэтому вы мог бы хотите его закодировать);и все остальное (всегда должно быть закодировано).
В соответствии с RFC, зарезервированными символами являются: :/?#[]@!$&'()*+,;=
А незарегистрированные символы являются буквенно-цифровыми и -._~
Вердикт суда
Uri.EscapeDataString (Экранированный запрос) четко определяет свою миссию:% -кодирует все зарезервированные и недопустимые символы. Веб-использование.UrlEncode является более двусмысленным как в определении, так и в реализации.Как ни странно, он кодирует некоторые зарезервированные символы, но не другие (почему круглые скобки, а не скобки??), и еще более странно, что он кодирует невинно незаслуженные ~
характер.
Поэтому я согласен с популярным советом - используйте Uri.EscapeDataString (Экранированный запрос) когда это возможно, и понимать, что зарезервированные символы, такие как /
и ?
будет закодирован.Если вам нужно иметь дело с потенциально большими строками, особенно с содержимым формы в кодировке URL, вам нужно либо вернуться к Веб-использование.UrlEncode и примите его причуды или иным образом решите проблему.
Редактировать: Я уже попытка чтобы исправить ВСЕ причуды, упомянутые выше в Флурл через Url.Encode
, Url.EncodeIllegalCharacters
, и Url.Decode
статические методы.Они находятся в основной пакет (который является крошечным и не включает в себя весь HTTP-материал), или не стесняйтесь копировать их из исходного кода.Я приветствую любые ваши комментарии / отзывы по этому поводу.
Вот код, который я использовал, чтобы выяснить, какие символы кодируются по-разному:
var diffs =
from i in Enumerable.Range(0, char.MaxValue + 1)
let c = (char)i
where !char.IsHighSurrogate(c)
let diff = new {
Original = c,
UrlEncode = WebUtility.UrlEncode(c.ToString()),
EscapeDataString = Uri.EscapeDataString(c.ToString()),
}
where diff.UrlEncode != diff.EscapeDataString
select diff;
foreach (var diff in diffs)
Console.WriteLine($"{diff.Original}\t{diff.UrlEncode}\t{diff.EscapeDataString}");
Имейте в виду, что вам, вероятно, не следует использовать ни один из этих методов.Корпорация Майкрософт Библиотека межсайтовых скриптов включает в себя замены для HttpUtility.UrlEncode
и HttpUtility.HtmlEncode
это и более соответствует стандартам, и более безопасно.В качестве бонуса вы получаете JavaScriptEncode
также и метод.
Сервер.UrlEncode() существует для обеспечения обратной совместимости с классическим ASP,
Server.UrlEncode(str);
Эквивалентно:
HttpUtility.UrlEncode(str, Response.ContentEncoding);
Тот же самый, Server.UrlEncode()
звонки HttpUtility.UrlEncode()