Server.UrlEncode против HttpUtility.UrlEncode

Есть ли разница между Server.UrlEncode и HttpUtility.UrlEncode?

Ответ 1

HttpServerUtility.UrlEncode будет использовать HttpUtility.UrlEncode внутренне. Особой разницы нет. Причиной существования Server.UrlEncode является совместимость с классическим ASP.

Ответ 2

У меня были значительные головные боли с этими методами раньше, Я рекомендую вам избегать любого варианта 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 - эта вещь действительно непонятна. Он кодирует:

  • "== > " %20"
  • "100% true" == > "100 % %20true" (нормально, ваш URL-адрес сейчас сломан)
  • "test A.aspx # anchor B" == > "test %20A.aspx # anchor %20B"
  • "test A.aspx? hmm # anchor B" == > "test %20A.aspx? hmm #anchor B" (обратите внимание на разницу с предыдущей escape-последовательностью!)

Он также имеет красивую специфическую документацию MSDN "Кодирует часть пути строки URL для надежной передачи HTTP с веб-сервера клиенту". - фактически не объясняя, что он делает. Вы менее склонны стрелять в ногу с помощью Узи...

Короче говоря, придерживайтесь Uri.EscapeDataString.

Ответ 3

Имейте в виду, что вы, вероятно, не должны использовать ни один из этих методов. Microsoft Библиотека скриптов для Anti-Cross Site содержит замены для HttpUtility.UrlEncode и HttpUtility.HtmlEncode, которые являются более стандартизованными и более безопасными. В качестве бонуса вы также получаете метод JavaScriptEncode.

Ответ 4

Server.UrlEncode() предназначен для обеспечения обратной совместимости с классическим ASP,

Server.UrlEncode(str);

Является эквивалентным:

HttpUtility.UrlEncode(str, Response.ContentEncoding);

Ответ 5

То же самое, Server.UrlEncode() вызывает HttpUtility.UrlEncode()

Ответ 6

Ускоренная перемотка почти через 9 лет с тех пор, как это было впервые задано, и в мире .NET Core и .NET Standard кажется, что наиболее распространенными параметрами для URL-кодирования являются WebUtility.UrlEncode (под System.Net) и Uri.EscapeDataString. Судя по самому популярному ответу здесь и в других местах, предпочтительнее Uri.EscapeDataString. Но так ли? Я сделал некоторый анализ, чтобы понять различия, и вот что я придумал:

В целях кодирования URL символы вписываются в одну из трех категорий: безоговорочно (легально по URL-адресу); зарезервировано (легально, но имеет особое значение, поэтому вы можете его закодировать); и все остальное (всегда должно быть закодировано).

В соответствии с RFC зарезервированные символы: :/?#[]@!$&'()*+,;=

И незарезервированные символы являются буквенно-цифровыми и -._~

Вердикт

Uri.EscapeDataString четко определяет свою миссию:% -encode все зарезервированные и незаконные символы. WebUtility.UrlEncode более двусмысленна как в определении, так и в реализации. Как ни странно, он кодирует некоторые зарезервированные символы, но не другие (почему круглые скобки, а не скобки?), А незнакомец все еще кодирует тот невинно безоговорочный символ ~.

Поэтому я согласен с популярным советом - используйте Uri.EscapeDataString, когда это возможно, и поймите, что зарезервированные символы, такие как / и ?, будут закодированы. Если вам нужно иметь дело с потенциально большими строками, особенно с содержимым формы с кодировкой URL-адреса, вам нужно либо вернуться на WebUtility.UrlEncode, либо принять его причуды, либо иначе обойти проблему.

Здесь код, который я использовал, чтобы определить, какие символы кодируются по-разному:

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}");