Сервер.Функция urlencode и методу HttpUtility.Функция urlencode
есть ли разница между сервером.UrlEncode и HttpUtility.Функция urlencode?
6 ответов
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
имейте в виду, что вы, вероятно, не должны использовать ни один из этих методов. Microsoft Библиотека Сценариев Anti-Cross Site включает в себя замену HttpUtility.UrlEncode
и HttpUtility.HtmlEncode
более соответствует стандартам, и более безопасной. В качестве бонуса вы получаете JavaScriptEncode
способ также.
перемотка вперед почти 9 лет с тех пор, как это было впервые задано, и в мире .NET Core и .NET Standard, кажется, наиболее распространенные варианты у нас есть для URL-кодирования WebUtility.Функция urlencode (при System.Net
) и Uri.EscapeDataString. Судя по самому популярному ответу здесь и в других местах, Uri.EscapeDataString кажется предпочтительнее. Но так ли это? Я сделал некоторый анализ, чтобы понять разницу и вот что я придумал с:
-
WebUtility.UrlEncode
кодирует пространство как+
;Uri.EscapeDataString
кодирует его как%20
. -
Uri.EscapeDataString
процентов-кодирует!
,(
,)
и*
;WebUtility.UrlEncode
нет. -
WebUtility.UrlEncode
процентов-кодирует~
;Uri.EscapeDataString
нет. -
Uri.EscapeDataString
бросает!--16--> на строках длиной более 65 520 символов;WebUtility.UrlEncode
нет. (более распространенная проблема, чем вы могли бы подумать, особенно при работе с URL-кодированной формой данные.) -
Uri.EscapeDataString
бросает!--16--> на высокая суррогатные символы;WebUtility.UrlEncode
нет. (Это вещь UTF-16, вероятно, намного менее распространенная.)
для целей кодирования URL-адресов символы вписываются в одну из 3 категорий: unreserved (legal в URL-адресе); reserved (legal in, но имеет особое значение, поэтому вы может хотите закодировать его); и все остальное (всегда должно быть закодировано).
по в RFC, зарезервированных символов: :/?#[]@!$&'()*+,;=
и неограниченные символы буквенно-цифровые и -._~
Приговор
Uri.EscapeDataString четко определяет свою миссию: % - кодирует все зарезервированные и нелегальные символы. WebUtility.Функция urlencode более неоднозначно как в определении, так и в реализации. Как ни странно, он кодирует некоторые зарезервированные символы, но не другие (почему скобки, а не скобки??), и еще более странно, что он кодирует то, что невинно незаслуженно ~
символ.
поэтому я согласен с популярным советом-используйте Uri.EscapeDataString когда это возможно, и понять, что зарезервированные символы, такие как /
и ?
будет закодирован. Если вам нужно иметь дело с потенциально большими строками, особенно с содержимым формы в URL-кодировке, вам нужно либо вернуться к WebUtility.Функция urlencode и принять его причуды, или иначе работать вокруг проблемы.
EDIT: я попытка чтобы исправить все причуды, упомянутые выше в Flurl через 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}");
сервер.UrlEncode () обеспечивает обратную совместимость с классическим ASP,
Server.UrlEncode(str);
эквивалентно:
HttpUtility.UrlEncode(str, Response.ContentEncoding);