更正301重定向的控制器代码

时间:2009-11-07 16:20:34

标签: asp.net asp.net-mvc asp.net-mvc-routing

我正在从静态网站设计一个新的动态网站。我的路线全部排序但我对我的行动方法有疑问。

下面是代码,但在测试和查看Firebug报告的标头时,如果我取出Response.End它是302重定向,我假设因为我设置301但是然后调用另一个动作使其成为302,但如果我放入Response.End我得到301。

我猜测添加Response.RedirectLocation实际上正在执行301重定向,因此我将返回值更改为EmptyResult或null,即使该行代码永远不会被执行,只是应用程序编译?

public ActionResult MoveOld(string id)
{
    string pagename = String.Empty;

    if(id == "2")
    {
      pagename = WebPage.SingleOrDefault(x => x.ID == 5).URL;
    }

    Response.StatusCode = 301;
    Response.StatusDescription = "301 Moved Permanently";
    Response.RedirectLocation = pagename;
    Response.End();

    return RedirectToAction("Details", new { pageName = pagename });
}

4 个答案:

答案 0 :(得分:14)

我回应列维的评论。这不是控制器的工作。我倾向于使用this自定义ActionResult for 301's。以下是具有更多选项的修改版本。

对于ASP.NET MVC v2 +,请使用RedirectResult

public class PermanentRedirectResult : ActionResult
{
  public string Url { get; set; }

  public PermanentRedirectResult(string url)
  {
    Url = url;
  }

  public PermanentRedirectResult(RequestContext context, string actionName, string controllerName)
  {
    UrlHelper urlHelper = new UrlHelper(context);
    string url = urlHelper.Action(actionName, controllerName);

    Url = url;
  }

  public PermanentRedirectResult(RequestContext context, string actionName, string controllerName, object values)
  {
    UrlHelper urlHelper = new UrlHelper(context);
    string url = urlHelper.Action(actionName, controllerName, values);

    Url = url;
  }

  public PermanentRedirectResult(RequestContext context, string actionName, string controllerName, RouteValueDictionary values)
  {
    UrlHelper urlHelper = new UrlHelper(context);
    string url = urlHelper.Action(actionName, controllerName, values);

    Url = url;
  }

  public override void ExecuteResult(ControllerContext context)
  {
    if (context == null)
    {
      throw new ArgumentNullException("context");
    }
    context.HttpContext.Response.StatusCode = 301;
    context.HttpContext.Response.RedirectLocation = Url;
    context.HttpContext.Response.End();
  }
}

行动中的用法

//Just passing a url that is already known
return new PermanentRedirectResult(url);

//*or*

//Redirect to a different controller/action
return new PermanentRedirectResult(ControllerContext.RequestContext, "ActionName", "ControllerName");

答案 1 :(得分:1)

控制器不应负责设置301和重定向位置。此逻辑应封装在ActionResult中,控制器应返回该ActionResult的实例。请记住,Response.End()方法不会返回(它会引发异常);跟随它的行将不会执行。

答案 2 :(得分:0)

答案 3 :(得分:0)

从MVC 2.0开始,这个“RedirectResult”有一个内置的动作结果类。有关详细信息,请参阅此帖子 - MVC RedirectResult