Reputation: 1808
I'm having difficulties getting uncaught exceptions logged when deploying my ASP.NET MVC 5 application to an Azure App Service slot. When an uncaught exception occurs, the app rightly returns a 500 and the standard "Error. An error occurred while processing your request" Error.cshtml page, but never records any mention of the exception in any of my logs.
Current Setup:
<customErrors />
in my Web.configs, but they are showing as off locally and on remotely, as expected and desiredApplication_Error
override to Global.asax
(see below)ExceptionLoggingFilter
(see below) and registered it in my FilterConfig.cs
pipepline as the first itemApplication_Error override in Global.asax:
protected void Application_Error(Object sender, EventArgs e)
{
Trace.TraceError("Uncaught exception bubbled up. Details: {0}", e);
Logger log = LogManager.GetCurrentClassLogger();
Exception ex = Server.GetLastError();
log.Fatal(ex, "Uncaught exception bubbled up to MVC root.");
}
Customer ExceptionLoggingFilter registered in GlobalFilters:
private static readonly Logger Logger = LogManager.GetCurrentClassLogger();
public void OnException(ExceptionContext filterContext)
{
var ex = filterContext.Exception;
var request = filterContext.HttpContext.Request;
Logger.Fatal(ex, "Uncaught exception bubbled up to MVC root.");
}
FilterConfig.cs:
public static void RegisterGlobalFilters(GlobalFilterCollection filters)
{
filters.Add(new ExceptionLoggerFilter());
filters.Add(new HandleErrorAttribute());
}
NLog.config:
...
<targets async="true">
<target xsi:type="File" name="f" fileName="${basedir}/logs/${shortdate}.log" layout="${longdate} ${uppercase:${level}} ${message} ${exception:format=tostring}" />
<target xsi:type="Trace" name="trace" layout="${logger} ${message} ${exception:format=tostring}" />
<!-- another target for sending data to Slack here... -->
</targets>
...
<rules>
<logger name="*" minlevel="Debug" writeTo="f" />
<logger name="*" minlevel="Trace" writeTo="trace" />
</rules>
...
What I've tried:
I created an action that purposely triggers an uncaught exception (var neverResult = Convert.ToInt32("a");
) and when I navigate to that page I get the custom error page. Implementing <customErrors mode="Off" />
in production on Azure does what I'd expect: I know see the full error message and stack trace when navigating to that example action BUT I do not get any logging going on, not from NLog, traces, watching the streaming logs, nada.
I've tried adding the additional handlers and filters for logging errors as explained above, and still nothing, though I know by remote debugging that the code is all being run in those additional handlers. Locally everything gets logged just fine.
Help!
I'm at a bit of a loss here even where to look next. Not sure if I need to look at Azure setting, how ASP.NET is handling things, or if NLog is off (even though it logs everything else fine). Any direction is greatly appreciated.
Update: Added actual filters config and NLog config.
Upvotes: 1
Views: 870
Reputation: 58733
I actually tried this with your configuration and found the problem.
If you use Logger.Fatal, the Trace message gets written in Verbose level for some reason. Change your logging filter to use the Error function:
Logger.Error(ex, "Uncaught exception bubbled up to MVC root.");
And also, exception filters run last-to-first, so in your case HandleErrorAttribute runs first. It however doesn't mean your filter won't run (ASP.NET Core is a bit different in this regard).
The Fatal function of NLog calls the Fail function of the Trace class, which is supposed to be used to show a message box to the user in Windows environments. For some reason that is on Verbose level on IIS.
TL;DR Don't use Fatal()
, use Error()
.
Upvotes: 2