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

URL-адреса с косой чертой в параметре?

Вопрос:

Я создаю wiki-программное обеспечение, в основном клон wikipedia/mediawiki, но в ASP.NET MVC (это MVC, поэтому не рекомендуем мне ScrewTurn).

Теперь у меня есть вопрос:

Я использую это сопоставление маршрутов, чтобы направить URL-адрес, например:
http://en.wikipedia.org/wiki/ASP.NET

        routes.MapRoute(
            "Wiki", // Routenname
            //"{controller}/{action}/{id}", // URL mit Parametern
            "wiki/{id}", // URL mit Parametern
            new { controller = "Wiki", action = "dbLookup", id = UrlParameter.Optional } // Parameterstandardwerte
        );

Теперь мне просто показалось, что могут быть такие названия, как "AS/400":
http://en.wikipedia.org/wiki/AS/400

Кстати, есть и этот (название "Slash" ):
http://en.wikipedia.org/wiki//

И этот:
http://en.wikipedia.org/wiki//dev/null

В целом, в Википедии есть список интересных названий: http://en.wikipedia.org/wiki/Wikipedia:Articles_with_slashes_in_title

Как правильно сделать маршруты, подобные этому маршруту?

Изменить:
Что-то вроде:
Если URL-адрес начинается с /Wiki/, и если он не начинается с /wiki/Edit/ (но не /Wiki/Edit ) затем передайте весь остальной URL-адрес в качестве идентификатора.

Изменить:
Хм, еще одна проблема: Как я могу маршрутизировать этот:
http://en.wikipedia.org/wiki/C&A

Википедия может...

Изменить:
Согласно википедии, из-за столкновений с синтаксисом wikitext, только следующие символы никогда не могут использоваться в названиях страниц (и они не поддерживаются DISPLAYTITLE):

# < > [ ] | { }

http://en.wikipedia.org/wiki/Wikipedia:Naming_conventions_(technical_restrictions)#Forbidden_characters

Изменить:
Чтобы разрешить * и &, поместить

<httpRuntime requestPathInvalidCharacters="" />

в раздел < system.web > в файле web.config

(Найдено здесь: http://www.christophercrooker.com/use-any-characters-you-want-in-your-urls-with-aspnet-4-and-iis)

4b9b3361

Ответ 1

Вы можете использовать общий путь для захвата всего, что следует за частью wiki URL-адреса в токен id:

routes.MapRoute(
    "Wiki",
    "wiki/{*id}",
     new { controller = "Wiki", action = "DbLookup", id = UrlParameter.Optional }
);

Теперь, если у вас есть следующий запрос: /wiki/AS/400 он отобразит следующее действие в контроллере wiki:

public ActionResult DbLookup(string id)
{
    // id will equal AS/400 here
    ...
}

Что касается /wiki//, я верю, что вы получите ошибку 400 Bad Request с веб-сервера до того, как этот запрос когда-либо достигнет конвейера ASP.NET. Вы можете проверить следующее сообщение в блоге.

Ответ 2

@Darin: Ну, это очевидно, вопрос в следующем: почему? контроллер + action + id даны, он как будто передает все это для маршрутизации снова... - Quandary Jun 13 '11 at 17:38

Quandry - возможно, вы уже поняли это, так как ваш вопрос старше года, но когда вы вызываете RedirectToAction, вы фактически отправляете ответ HTTP 302 на браузер, что вызывает браузер чтобы сделать запрос GET указанному действию. Следовательно, бесконечный цикл, который вы видите.

Смотрите: Controller.RedirectToAction Method

Ответ 3

в Attribute Routing в mvc я была та же проблема, имеющая / в строке abc/cde в HttpGet

        [Route("verifytoken/{*token}")]
        [AllowAnonymous]
        [HttpGet]
        public ActionResult VerifyToken(string token)
        {
          //logic here
        }

поэтому вам нужно поместить *, потому что после этого он будет считаться параметром

Ответ 4

По-прежнему в качестве опции пишите в файл Global.asax:

 var uri = Context.Request.Url.ToString();
        if (UriHasRedundantSlashes(uri))
        {
            var correctUri = RemoveRedundantSlashes(uri);
            Response.RedirectPermanent(correctUri);
        }
    }

    private string RemoveRedundantSlashes(string uri)
    {
        const string http = "http://";
        const string https = "https://";
        string prefix = string.Empty;

        if (uri.Contains(http))
        {
            uri = uri.Replace(http, string.Empty);
            prefix = http;
        }
        else if (uri.Contains(https))
        {
            uri = uri.Replace(https, string.Empty);
            prefix = https;
        }

        while (uri.Contains("//"))
        {
            uri = uri.Replace("//", "/");
        }

        if (!string.IsNullOrEmpty(prefix))
        {
            return prefix + uri;
        }
        return uri;
    }

    private bool UriHasRedundantSlashes(string uri)
    {
        const string http = "http://";
        const string https = "https://";

        if (uri.Contains(http))
        {
            uri = uri.Replace(http, string.Empty);
        }
        else if (uri.Contains(https))
        {
            uri = uri.Replace(https, string.Empty);
        }
        return uri.Contains("//");
    }

Смотрите: https://pro-papers.com/