【问题标题】:MVC redirect to default routeMVC 重定向到默认路由
【发布时间】:2012-07-17 08:42:58
【问题描述】:

这是我的默认路线:

routes.MapRouteLowercase(
                "Default",
                "{country}/{controller}/{action}/{id}",
                new {
                    country = "uk",
                    controller = "Home",
                    action = "Index",
                    id = UrlParameter.Optional
                },
                new[] { "Presentation.Controllers" }
                );

我们知道,当有人访问 www.domain.com/ 时,MVC 的路由会根据上述路由确定默认的控制器和要执行的操作,但 URL 将保持不变。对于使用默认值的每个路由,是否有内置或优雅的方式来执行从 www.domain.com/ 到 www.domain.com/uk/{controller}/{action}/ 的 301 重定向?

【问题讨论】:

  • 您可以从默认控制器进行重定向,例如索引操作

标签: c# asp.net-mvc-3 asp.net-mvc-routing


【解决方案1】:

我创建了一个在路由级别执行重定向的自定义路由处理程序。感谢Phil Haack

这是完整的作品。

重定向路由处理程序

public class RedirectRouteHandler : IRouteHandler
{
    private string _redirectUrl;

    public RedirectRouteHandler(string redirectUrl)
    {
        _redirectUrl = redirectUrl;
    }

    public IHttpHandler GetHttpHandler(RequestContext requestContext)
    {
        if (_redirectUrl.StartsWith("~/"))
        {
            string virtualPath = _redirectUrl.Substring(2);
            Route route = new Route(virtualPath, null);
            var vpd = route.GetVirtualPath(requestContext,
                requestContext.RouteData.Values);
            if (vpd != null)
            {
                _redirectUrl = "~/" + vpd.VirtualPath;
            }
        }

        return new RedirectHandler(_redirectUrl, false);
    } 
}

重定向 http 处理程序

public class RedirectHandler : IHttpHandler
{
    private readonly string _redirectUrl;

    public RedirectHandler(string redirectUrl, bool isReusable)
    {
        _redirectUrl = redirectUrl;
        IsReusable = isReusable;
    }

    public bool IsReusable { get; private set; }

    public void ProcessRequest(HttpContext context)
    {
        context.Response.Status = "301 Moved Permanently";
        context.Response.StatusCode = 301;
        context.Response.AddHeader("Location", _redirectUrl);
    }
}

路线扩展

public static class RouteExtensions
{
    public static void Redirect(this RouteCollection routes, string url, string redirectUrl)
    {
        routes.Add(new Route(url, new RedirectRouteHandler(redirectUrl)));
    }
}

有了所有这些,我可以在 Global.asax.cs 中映射路线时做这样的事情。

routes.Redirect("", "/uk/Home/Index");

routes.Redirect("uk", "/uk/Home/Index");

routes.Redirect("uk/Home", "/uk/Home/Index");

.. other routes

【讨论】:

  • routes.Redirect 是否应该先于所有其他路线(例如 MapRoute)?这适用于旧的 .aspx 页面路由吗? foo.aspx -> /foo
【解决方案2】:

在我的项目中,我通常将“IndexRedirect”作为路由中的默认操作(其 URL 将永远不可见),它只会重定向到“真实”索引页面(其 URL 将始终可见)。

您可以在所有控制器类的基类中创建此操作。

【讨论】:

  • 这是最好的解决方案!
  • 一个新奇的想法,真希望我自己也想过!
猜你喜欢
  • 1970-01-01
  • 2015-09-30
  • 1970-01-01
  • 2018-02-14
  • 1970-01-01
  • 1970-01-01
  • 2012-04-12
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多