2009-11-07 27 views
5

我从一个静态的网站设计一个新的动态网站。我有路线全部排序,但我有我的行动方法的问题。正确的控制器代码重定向

下面是代码,但是当测试并查看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 }); 
} 
+0

正如评论我的答复中提到,你是在这里的影响做了两个ActionResults。 301重定向本身就是一个ActionResult,然后你用另一个** AFTER **跟踪它的响应已发送。 – 2009-11-09 14:30:09

回答

14

我赞同列维的意见。这不是控制器的工作。我已经倾向于使用this自定义的ActionResult为301的。以下是带有更多选项的修改版本。

对于ASP.NET MVC V2 +,使用RedirectResult。在动作

//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"); 
+0

感谢但Levi说调用Response.End抛出异常,是否有效? – Jon 2009-11-09 09:27:13

+0

如果不执行你的代码,我猜这个错误类似于'HTTP头被发送后无法重定向'。这是因为您发送了回复,并在发送回复后重定向了用户。 'Response.End();'应该是你做的最后一件事。 – 2009-11-09 14:25:51

+0

这是因为在我给出的代码示例中,PermanentRedirectResult ** IS ** ActionResult。实际上,在你的代码中,你有两个ActionResults。 – 2009-11-09 14:27:46

1

控制器不应该负责设置301和重定向位置。这个逻辑应该被封装在一个ActionResult中,并且控制器应该返回该ActionResult的一个实例。请记住,到Response.End方法()不返回(它抛出一个异常);遵循它的行将不会执行。

0

从MVC 2.0

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(); 
    } 
} 

用法有一个在这个 “RedirectResult” 内置动作结果类。请参阅这篇文章的详细信息 - MVC RedirectResult