Ich verwende derzeit log4net in meiner ASP.NET MVC-Anwendung, um Ausnahmen zu protokollieren. Ich mache das so, indem ich alle meine Controller von einer BaseController-Klasse erben lasse. Im OnActionExecuting-Ereignis des BaseControllers protokolliere ich alle Ausnahmen, die möglicherweise aufgetreten sind:
protected override void OnActionExecuted(ActionExecutedContext filterContext)
{
// Log any exceptions
ILog log = LogManager.GetLogger(filterContext.Controller.GetType());
if (filterContext.Exception != null)
{
log.Error("Unhandled exception: " + filterContext.Exception.Message +
". Stack trace: " + filterContext.Exception.StackTrace,
filterContext.Exception);
}
}
Dies funktioniert hervorragend, wenn während einer Controller-Aktion eine nicht behandelte Ausnahme aufgetreten ist.
Für 404-Fehler habe ich einen benutzerdefinierten Fehler in meiner web.config wie folgt eingerichtet:
<customErrors mode="On">
<error statusCode="404" redirect="~/page-not-found"/>
</customErrors>
Und in der Controller-Aktion, die die URL "Seite nicht gefunden" verarbeitet, protokolliere ich die angeforderte Original-URL:
[AcceptVerbs(HttpVerbs.Get)]
public ActionResult PageNotFound()
{
log.Warn("404 page not found - " + Utils.SafeString(Request.QueryString["aspxerrorpath"]));
return View();
}
Und das funktioniert auch.
Das Problem, das ich habe, ist, wie Fehler protokolliert werden, die sich auf den ASPX-Seiten selbst befinden. Angenommen, ich habe einen Kompilierungsfehler auf einer der Seiten oder einen Inline-Code, der eine Ausnahme auslöst:
<% ThisIsNotAValidFunction(); %>
<% throw new Exception("help!"); %>
Es scheint, dass das HandleError-Attribut dies korrekt auf meine Error.aspx-Seite im freigegebenen Ordner umleitet, aber es wird definitiv nicht von der OnActionExecuted-Methode meines BaseControllers abgefangen. Ich dachte, ich könnte den Protokollierungscode vielleicht auf der Error.aspx-Seite selbst platzieren, bin mir aber nicht sicher, wie ich die Fehlerinformationen auf dieser Ebene abrufen soll.