Подтвердить что ты не робот

Преобразовать заголовок в пунктирную строку, удобную для URL

Я хотел бы написать метод С#, который преобразует любой заголовок в строку, удобную для URL, аналогично тому, что делает переполнение стека:

  • заменить пробелы тире
  • убрать скобки
  • и т.п.

Я думаю об удалении зарезервированных символов в соответствии со стандартом RFC 3986 (из Википедии), но я не знаю, будет ли этого достаточно? Это сделало бы ссылки работоспособными, но кто-нибудь знает, какие другие символы заменяются здесь в stackoverflow? Я не хочу заканчивать с% -s в моих URL...

Текущая реализация

string result = Regex.Replace(value.Trim(), @"[!*'""'();:@&+=$,/\\?%#\[\]<>«»{}_]");
return Regex.Replace(result.Trim(), @"[\s*[\-–—\s]\s*]", "-");

Мои вопросы

  1. Какие символы я должен удалить?
  2. Должен ли я ограничить максимальную длину результирующей строки?
  3. Кто-нибудь знает, какие правила применяются к заголовкам здесь, на SO?
4b9b3361

Ответ 1

Вместо того, чтобы искать заменяемые вещи, список unreserved chars настолько короток, что это сделает приятное ясное регулярное выражение.

return Regex.Replace(value, @"[^A-Za-z0-9_\.~]+", "-");

(Обратите внимание, что я не включил тире в список разрешенных символов, поэтому он сжимается оператором "1 или больше" [+], так что несколько тире (в исходном или сгенерированном или комбинация) свертываются, как полагает Доминик Роджер.)

Вы также можете удалить общие слова ( "the", "an", "a" и т.д.), хотя это может слегка изменить смысл предложения. Вероятно, вы хотите удалить любые трейлинг-тире и периоды.

Также настоятельно рекомендуем делать то, что делают SO и другие, и включать уникальный идентификатор, отличный от заголовка, а затем использовать только этот уникальный идентификатор при обработке URL-адреса. Итак http://example.com/articles/1234567/is-the-pop-catholic (обратите внимание на отсутствие "e" ) и http://example.com/articles/1234567/is-the-pope-catholic на тот же ресурс.

Ответ 2

Я бы делал:

string url = title;
url = Regex.Replace(url, @"^\W+|\W+$", "");
url = Regex.Replace(url, @"'\"", "");
url = Regex.Replace(url, @"_", "-");
url = Regex.Replace(url, @"\W+", "-");

В основном, что это делает:

  • разделяет символы без слова с начала и конца заголовка;
  • удаляет одинарные и двойные кавычки (в основном, чтобы избавиться от апострофов в середине слов);
  • заменяет символы подчеркивания дефисом (символы подчеркивания являются технически символом слова вместе с цифрами и буквами); и
  • заменяет все группы символов, отличных от слова, на один дефис.

Ответ 3

Большинство "sluggifiers" (методы преобразования имен типа дружественного URL) имеют тенденцию делать следующее:

  • Разделите все, кроме пробелов, тире, подчеркивания и буквенно-цифровых символов.
  • (Необязательно) Удалите "общие слова" (a, a, an и т.д.).
  • Заменить пробелы и символы подчеркивания тире.
  • (Необязательно) Преобразование в нижний регистр.

Насколько я знаю, StackOverflow sluggifier делает # 1, # 3 и # 4, но не # 2.

Ответ 4

Как насчет этого:

string FriendlyURLTitle(string pTitle)
{
    pTitle = pTitle.Replace(" ", "-");
    pTitle = HttpUtility.UrlEncode(pTitle);
    return Regex.Replace(pTitle, "\%[0-9A-Fa-f]{2}", "");
}

Ответ 5

вот как я в настоящее время путаю слова.

        public static string Slug(this string value)
    {
        if (value.HasValue())
        {
            var builder = new StringBuilder();
            var slug = value.Trim().ToLowerInvariant();

            foreach (var c in slug)
            {
                switch (c)
                {
                    case ' ':
                        builder.Append("-");
                        break;
                    case '&':
                        builder.Append("and");
                        break;
                    default:

                        if ((c >= '0' && c <= '9') || (c >= 'a' && c <= 'z') && c != '-')
                        {
                            builder.Append(c);
                        }

                        break;
                }
            }

            return builder.ToString();
        }

        return string.Empty;
    }

Ответ 6

Я использую этот...

    public static string ToUrlFriendlyString(this string value)
    {
        value = (value ?? "").Trim().ToLower();

        var url = new StringBuilder();

        foreach (char ch in value)
        {
            switch (ch)
            {
                case ' ':
                    url.Append('-');
                    break;
                default:
                    url.Append(Regex.Replace(ch.ToString(), @"[^A-Za-z0-9'()\*\\+_~\:\/\?\-\.,;=#\[\]@!$&]", ""));
                    break;
            }
        }

        return url.ToString();
    }

Ответ 7

Это работает для меня

string output = Uri.UnescapeDataString(input);