我正在显示在MVC中进行301重定向的 正确
方法,因为并非所有浏览器都能正确响应301重定向请求,并且您需要为用户提供一个继续选项,而不是由ASP生成的默认“对象已移动”页面。净。
RedirectAspxPermanentRoute
我们构建了一个自定义
Routebase子类,该子类可检测URL何时以结尾,
.aspx并路由至我们
SystemController以设置301重定向。它要求您传入URL映射(要匹配的URL)以路由值(用于生成MVC
URL)。
public class RedirectAspxPermanentRoute : Routebase{ private readonly IDictionary<string, object> urlMap; public RedirectAspxPermanentRoute(IDictionary<string, object> urlMap) { if (urlMap == null) throw new ArgumentNullException("urlMap"); this.urlMap = urlMap; } public override RouteData GetRouteData(HttpContextbase httpContext) { var path = httpContext.Request.Path; if (path.EndsWith(".aspx")) { if (!urlMap.ContainsKey(path)) return null; var routevalues = urlMap[path]; var routeData = new RouteData(this, new MvcRouteHandler()); routeData.Values["controller"] = "System"; routeData.Values["action"] = "Status301"; routeData.DataTokens["routevalues"] = routevalues; return routeData; } return null; } public override VirtualPathData GetVirtualPath(RequestContext requestContext, RoutevalueDictionary values) { return null; }}请注意,第一个检查是针对
.aspx扩展名的,因此如果扩展名不匹配,则其余逻辑将被完全跳过。这将为您的方案提供最佳性能。
系统控制器
我们将设置
SystemController为像往常一样返回视图。如果浏览器由于301而无法重定向,则用户将看到该视图。
using System; using System.Net;using System.Web;using System.Web.Mvc;public class SystemController : Controller{ // // GET: /System/Status301/ public ActionResult Status301() { var routevalues = this.Request.RequestContext.RouteData.DataTokens["routevalues"]; var url = this.GetAbsoluteUrl(routevalues); Response.CacheControl = "no-cache"; Response.StatusCode = (int)HttpStatusCode.MovedPermanently; Response.RedirectLocation = url; ViewBag.DestinationUrl = url; return View(); } private string GetAbsoluteUrl(object routevalues) { var urlBuilder = new UriBuilder(Request.Url.AbsoluteUri) { Path = Url.RouteUrl(routevalues) }; var enpredAbsoluteUrl = urlBuilder.Uri.ToString(); return HttpUtility.UrlDepre(enpredAbsoluteUrl); }}Status301.cshtml
请遵循MVC的约定,并确保将其放置在
/Views/System/文件夹中。
因为它是301响应的视图,所以可以使其与网站其余部分的主题匹配。因此,如果用户最终来到这里,那仍然不是一个糟糕的体验。
该视图将尝试通过Javascript 和 meta-Refresh
自动重定向用户。这两个功能都可以在浏览器中关闭,但是用户很可能会将其放置在应有的位置。如果没有,您应该告诉用户:
- 该页面具有新位置。
- 如果没有自动重定向,他们需要单击链接。
- 他们应该更新自己的书签。
@{ ViewBag.Title = "Page Moved";}@section metaRefresh { <meta http-equiv="refresh" content="5;@ViewBag.DestinationUrl" />}<h2 >Page Moved</h2><p> The page has moved. Click on the following URL if you are not redirected automatically in 5 seconds. Be sure to update your bookmarks.</p><a href="@ViewBag.DestinationUrl">@ViewBag.DestinationUrl</a>.<script> //<!-- setTimeout(function () { window.location = "@ViewBag.DestinationUrl"; }, 5000); //--></script>用法
首先,您需要在页面中添加一个部分,
_Layout.cshtml以便可以将元刷新添加到页面的头部。
<!DOCTYPE html><html lang="en"> <head> <meta charset="utf-8" /> <title>@ViewBag.Title - My ASP.NET MVC Application</title> <link href="~/favicon.ico" rel="shortcut icon" type="image/x-icon" /> <!-- Add this so the view can update this section --> @RenderSection("metaRefresh", required: false) <meta name="viewport" content="width=device-width" /> @Styles.Render("~/Content/css") @scripts.Render("~/bundles/modernizr") </head> <!-- layout pre omitted --></html>然后将添加
RedirectAspxRoute到您的路由配置。
public class RouteConfig{ public static void RegisterRoutes(RouteCollection routes) { routes.IgnoreRoute("{resource}.axd/{*pathInfo}"); routes.Add(new RedirectAspxPermanentRoute( new Dictionary<string, object>() { // Old URL on the left, new route values on the right. { @"/about-us.aspx", new { controller = "Home", action = "about" } }, { @"/contact-us.aspx", new { controller = "Home", action = "Contact" } } }) ); routes.MapRoute( name: "Default", url: "{controller}/{action}/{id}", defaults: new { controller = "Home", action = "Index", id = UrlParameter.Optional } ); }}


