【问题标题】:catch exceptions from all Pages从所有页面捕获异常
【发布时间】:2016-01-20 16:06:48
【问题描述】:

我正在尝试从我正在维护的站点中记录所有“一般错误”,以调试代码隐藏,而不必向用户显示详细的错误页面。 web.config 说:

<customErrors mode="RemoteOnly" defaultRedirect="~/GeneralError.html"/>

它适用于除以零、空引用异常、缺少 dll 等问题。经过大量阅读后,我发现这些是“未处理的异常”,但未到达 @987654324 中的处理程序 Application_Error() @。在每页的基础上,什么是有效的:

protected override void OnError(EventArgs e)
{
    Exception TheException = Server.GetLastError();
    // todo: log the exception to the database
    base.OnError(e); //pass the exception to the regular handler
    return;
}

但这是否可以更改为使用单一方法记录所有页面的未处理异常?如何覆盖或修改基类Page

我也想过把日志放在GeneralError.aspx的代码隐藏中,但是这样就没有堆栈跟踪或异常消息,而且任何用户都可以直接调用这个页面来烦我们。

我使用一些帖子中提到的IErrorHandler 接口进行了调查,但这应该与 WinForm 应用程序有关,而不是与 asp.net 网络应用程序有关。

【问题讨论】:

    标签: c# asp.net exception


    【解决方案1】:

    在 Global.asax 文件中使用 Application_Error 方法。

    在您的 Application_Error 方法实现调用 Server.GetLastError() 中,记录 Server.GetLastError() 返回的异常的详细信息。

    Exception LastError;
    String ErrMessage;
    
    LastError = Server.GetLastError();
    
    if (LastError != null)
       ErrMessage = LastError.Message;
    else
       ErrMessage = "No Errors";
    
    Response.Write("Last Error = " + ErrMessage);
    

    请参阅此处MSDN,或者如果您想要完整的 Microsoft 示例,请访问 Complete Example for Error Handlers

    【讨论】:

    • 我对此进行了调查,但如果页面上出现简单的未处理异常,则不会调用 Application_Error 处理程序。另见:stackoverflow.com/a/16348903/1845672
    • 哪一个?在普通的 ASP.Net 应用程序中,Global.asax 类中的 Application_Error 应该捕获错误。
    • 不,它应该捕获所有未处理的异常。我所追求的“未处理”异常将在某个地方处理,这就是 GeneralError 页面的显示方式。真正未处理的异常将关闭 IIS 服务器,并且在 Global.asax 处理程序中只能看到此类异常。我测试了页面上的 OnError 可以看到我不起眼的页面异常,但 Global.asax 中没有。
    【解决方案2】:

    创建一个新类:

    public class MyPage : System.Web.UI.Page
    {
         protected override void OnError(EventArgs e)
         {
             Exception TheException = Server.GetLastError();
             // todo: log the exception to the database
             base.OnError(e); //pass the exception to the regular handler
             return;
         }
    }
    

    而不是从 System.Web.UI.Page 继承,而是从您的各个页面上的 MyPage 继承。

    【讨论】:

    • 这意味着更改我们网站所有 100 多个页面中的基类名称,并且在创建新页面时要小心。我希望有一些像Page.OnError += mynewhandler 这样的单一声明。
    【解决方案3】:

    我目前正在研究https://msdn.microsoft.com/en-us/library/aa479332.aspx,通过https://stackoverflow.com/a/138088/1845672 找到它用完全相同的方法讨论了我的问题:提供一种解决方案,以可维护的方式记录所有页面上的错误,而无需修改所有页面。

    微软网站上的下载链接已过时。根据:https://code.google.com/p/elmah/issues/detail?id=64,源代码已从微软网站移至:elmah.googlecode.com/files/GDN-ELMAH-1.0.5527-setup.zip。

    看起来这是一个完整的解决方案。 . .

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2018-11-01
      • 2011-11-09
      • 1970-01-01
      • 1970-01-01
      • 2022-11-23
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多