属性似乎完全没有起作用

11

我在控制器操作中使用[HandleError]属性时遇到了问题 - 它似乎根本不起作用(即使过滤器存在或不存在,我都得到相同的结果...)。当抛出异常时,我得到标准的红色服务器错误在'/'应用程序错误页面而不是我的自定义视图。

我在SO上找到了几个关于此主题的其他线程,在大多数情况下,将web.config中的customErrors选项设置为On可以解决该问题。但这对我没有用,因此我需要找到另一种解决方案。

我的控制器操作:

[HandleError]
public ActionResult Index()
{
    throw new Exception("oops...");
    return View();
}

在我的web.config文件中

<customErrors mode="On"></customErrors>

我已确保Error.aspx文件也在Shared目录中。我错过了什么吗?

我正在运行ASP.NET MVC RC Refresh。

6个回答

14

有两件有用的事情需要知道:

默认情况下,当在开发服务器下运行时,HandleError 不会执行任何操作。这样做是为了向开发人员展示更有用的信息:

public virtual void OnException(ExceptionContext filterContext) {
    if (filterContext == null) {
        throw new ArgumentNullException("filterContext");
    }

    // If custom errors are disabled, we need to let the normal ASP.NET
    // exception handler execute so that the user can see useful
    // debugging information.
    if (filterContext.ExceptionHandled
        || ! filterContext.HttpContext.IsCustomErrorEnabled) {
        return;
    }

请注意,这种情况正是customError所要控制的。如果设置customError="On"没有改变这种行为:

  1. 检查您的语法。
  2. 确保您正在编辑项目根目录中的Web.config,而不是在Views文件夹中的那个。
  3. 确保没有代码设置了HttpContext.IsCustomErrorEnabled
  4. 如果所有方法都无效,请尝试在Web.config中关闭调试。

其次,有某些类型的错误HandleError永远不会处理,特别是ASP.NET编译错误。您没有说遇到了哪种错误。


谢谢您的回复!您的第一条评论确实解释了为什么我看不到效果...在上传到服务器之前,我有没有办法在本地测试错误处理?如何操作?我的项目已经编译完成,但我故意抛出运行时异常来测试错误处理。 - Tomas Aschan
你好。我已经尝试过customErrors =“On”,带有和不带有默认重定向,customErrors =“Off”,完全删除节点以及将debug =“false”设置,唯一的区别是在红色错误页面上显示的信息...它是调试还是使用Cassini导致了问题? - Tomas Aschan
当你说Cassini时,你是指ASP.NET开发服务器吗?它们不是同一个东西,我不知道Cassini是做什么的。 - Craig Stuntz
是的,那就是我的意思。当我在VS中点击“播放”时,默认运行的东西 =) 我了解到它们实际上是相同的(如果我没记错的话,在WROX的《ASP.NET 2.0入门》中...)。在IIS中进行调试能解决这个问题吗? - Tomas Aschan
我现在已经配置了网站在IIS上运行,而不是在ASP.NET开发服务器上运行,但没有成功。这方面有什么想法吗? - Tomas Aschan
显示剩余2条评论

4

您还需要指定要重定向的页面。

<customErrors mode="On" defaultRedirect="Error.aspx" />

抱歉,/Shared/部分不应该出现在这里,但您需要告诉MVC将用户发送到哪个页面以使用Error.aspx。然后默认路由程序会在共享文件夹中查找名为Error.aspx的内容。很晚了! :) 我想这就是为什么有人给我答案打负号的原因! :) 至少在这里它有效!

此外,根据这篇文章http://weblogs.asp.net/scottgu/archive/2008/07/14/asp-net-mvc-preview-4-release-part-1.aspx(这是我能找到的最新版本,尽管它只是PV4...),这并不是必需的。 - Tomas Aschan
我读了那篇文章,但对我来说,除非我指定重定向到哪里,否则错误是无法处理的。 - mhenrixon
在我的 web.config 文件中我写了 <customErrors mode="On" defaultRedirect="Error.aspx"></customErrors>,当一个异常被抛出时,我会在这个网址上得到一个 404 错误:http://localhost:52812/Error.aspx?aspxerrorpath=/Program/Edit。 - Tomas Aschan

3

我遇到了同样的问题,花了整整两天才最终找到解决方法。原来是Site.Master页面出现了错误,而Error.aspx使用了与其他页面相同的主页面。显然,Error.aspx无法处理这种情况。

我的解决方案是创建一个特定的Error.master页面,它是轻量级的,不包含任何模型数据。此外,我创建了一个静态的Error.htm文件,以防从Error.aspx发生错误。Web.config设置如下:

<customErrors mode="On">
    <error statusCode="500" redirect="Error.htm" />
</customErrors>

希望这能有所帮助。

我的Error.aspx页面也抛出了它自己的异常。这真是调试的一个痛点! - Zack Peterson
Error.htm 似乎返回了 HTTP 响应状态码 200,而不是应该的 500! - Zack Peterson

0
我尝试了上面的建议,但都没有对我起作用。最终解决问题的方法是从我的错误控制器中删除这行代码。
Response.StatusCode = (int)HttpStatusCode.NotFound;

由于IIS错误消息一直干扰我的错误处理,我感到非常苦恼。虽然这并不理想,因为我想在响应中提供该状态码,但我发现删除它可以防止IIS 7+干扰我的错误处理。

DaTribe


如果你想使用它,并且你可以,你需要首先设置 Response.TrySkipIisCustomErrors = true - ehdv

0

为了解决404问题,当应该显示Error.aspx页面时,我不得不从httpHandler部分中排除Error.aspx,这会阻止直接访问任何视图(大约在MVC2框架周围)。我通过将Error.aspx放入“错误”子文件夹中,并在此子文件夹中放置一个web.config,在httpHandlers部分中加入了<remove path="*" verb="*" />来实现这一点。我的这个问题(以及解决方案)可能特定于MVC 2。

注意:移动Error.aspx后记得更新defaultRedirect引用 :)


0

这个问题的另一个原因可能是,

在由VS2008 / VS2008 Express生成的模板MVC应用程序中,Error.aspx(由VS生成)使用Master Page。

如果Master Page访问任何ViewData,它将抛出空引用异常,然后error.aspx将不会显示。

请使用此简单代码作为您的Error.aspx,它将解决该问题(以及CustomErrors = On)

<%@ Page Language="C#"  Inherits="System.Web.Mvc.ViewPage<System.Web.Mvc.HandleErrorInfo>" %>
<%= Model.Exception.Message %>

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接