Configure ASP.NET Health Monitoring to ignore specific errors? - asp.net

My ASP.NET app has a web.config healthMonitoring section set up to email me when errors occur. Periodically I get errors that I would like to ignore, such as Invalid Viewstate or ScriptResource.axd errors. Is there any way to configure web.config to NOT email me when the exception message matches a certain search string or regex?
I believe this is similar to Ignore HealthMonitoring event by EventDetailCode.

You can create a custom event provider by inheriting from the System.Web.Management.WebEventProvider base provider class. This way you could handle the errors you want to by emailing them and ignoring any others. Checkout "How to Write a Custom Web Event Provider for ASP.NET 2.0" and "Creating Custom Event Providers" for more info.

are you raising the events yourself, or are they raised in the background. I would look at the EventCode for the event and see if you can use that to distinguish between this event type and another? If you are raising the event yourself, like in a catch statement, you can easily separate it out. But if you are using the global blanket for catching all errors, there is no way. The only way is to use the event code in eventMapping and then add rules to catch that event and send it to a provider.

Related

Should I catch all my exceptions in the global.asax?

If I am just logging exception details in my web app, do I really need to put in exception handling logic for each tier? Why not just let them all bubble up the stack trace to the global.asax and log them there?
I would suggest against using any exception handling logic in any layer of your application unless:
The exception is not a fatal one, meaning that there is some action you can take to recover, or
The application should continue functioning and the exception should be "ignored." An example: when checking out at an online retailer you are sent a receipt via email. If that fails - but the other order processing stuff succeeds - the user should not be shown an error page. Here, we want the workflow to continue even though there is an exception. Most exceptions do not fall into this category.
Of course, exceptions - whether they are fatal or not or should be "ignored" or not - need to be logged and developers notified. This is best handled through an event handler for the Application.Error event. Yes, this can be done in Global.asax, but I think it's cleaner to use an HTTP Module-based approach, either Health Monitoring or ELMAH.
I've written an article on this topic that I'd like to recommend to you - Exception Handling Advice for ASP.NET Web Applications. Here is the article in summary:
My advice for handling exceptions in an ASP.NET application can be boiled down to the following guidelines:
(a) Create and use a meaningful custom error page.
(b) In general, do not catch exceptions. Let them bubble up to the ASP.NET runtime. Some cases where catching an exception makes sense include:
When there is a plausible way to recover from the exception by performing some alternative logic,
When a peripheral part of the application's workflow throws and exception and that exception should not derail the entire application, and
When you need to include additional information with the exception by throwing a new exception that has the original exception as its inner exception.
(c) Log all exceptions to some persistent store and use email (or some other medium) to notify developers when an exception occurs in production. Consider using ELMAH or ASP.NET's built-in Health Monitoring system to facilitate this process.
Exceptions should bubble up to whatever layer can handle them in a meaningful way, being aware of the Single Responsibility principle. For instance, your data layer should not be invested in logging.
The Application.Error event is a good place for catch-all error handling: that is, unexpected and/or fatal errors that require no special treatment beyond logging/alerting and redirecting to an error page.
If your web app makes use of the Microsoft AJAX extensions and partial postbacks, you'll need to handle exceptions in at least two places:
Global.asax
Your ScriptManager's OnAsyncPostBackError handler
For further information on OnAsyncPostBackError, check out:
http://msforge.net/blogs/janko/archive/2008/02/13/handling-exceptions-in-asp-net-ajax.aspx
http://msdn.microsoft.com/en-us/library/system.web.ui.scriptmanager.onasyncpostbackerror.aspx
I say that on global try to catch the error that you miss on the logic steps of your program and redirect them on an "error page", or a "not found page".
All other errors not necessary show the error on the user, and not need to send it to an error page.
For example, in page with 2 or more, different modules, if the one throw an error, just hide it, and show the rest. Similar try to catch errors when they happens and handle them the best non visual way to the user if this is possible, log them and correct them later.
Now this error that happens only on one module, you can see it on your log and correct it, but until you do that, user see something on your page and not a full error page.
Usually what I do is do a try...catch in the code, but instead of logging on the catch what I do is pass it on with a message stating where the error came from, etc. Then I use Elmah to catch all of the errors and log them.
That way you only have to deal with the logging in one area and satisfy the Single Responsiblity Principle, but you have more information available for debugging purposes. It can also be helpful when you get that data error that only seems to occur with 1 out of 500 users.

ASP.NET logging Events in DB

Can ASP.NET's System.web.Management be used for logging events like user logins, password changes and access to certain resources? Should system.Web.Management be used for logging of errors and health monitoring instead?
I want to log events without re-inventing the whole thing. I know ELMAH is used for errors; can it be used for logging events too?
From the article ELMAH - Error Logging Modules And Handlers on the now defunct DoNetSlackers:
Error signaling is exposed via the ErrorSignal class, which provides a single overloaded method called Raise. Simply put, exceptions raised via the ErrorSignal class are not thrown, therefore they don't bubble up, but instead are only sent out to ELMAH, as well as to whomever subscribes to the Raise event of the ErrorSignal class.
The code snippet below shows how to obtain an instance of the ErrorSignal class, which is unique per application and can be retrieved simply with the static FromCurrentContext method, and then use it to signal an exception.
ErrorSignal.FromCurrentContext().Raise(new NotSupportedException());
The difference between signaling and throwing an exception is that in the first case no one will ever know about the error except ELMAH.
Further Reading:
How to get ELMAH to work with ASP.NET MVC [HandleError] attribute?

How to implement automatic bug/crash report for ASP.NET web application?

Everyone probably notices that most modern applications nowadays has a way for user to send crash/bug report either automatically or with user permission. Some examples are Mozilla Crash Reporter or most Microsoft applications.
I really like this feature since it allows me to collect the bugs report quickly with helpful information than just let my user reports the bug/issue traditionally such as submit a help ticket.
I wonder if there is an easy or systematic way to implement that capability in ASP.NET web application.
Have you guys had any experience or knowledge to share for both WebForms and MVC applications? Or if this could be implemented in Client-side like JavaScript/JQuery, that'd be good.
Thanks!
ASP.NET 2.0 introducted Health monitoring, which allows you to do this by just adding some stuff to the web.config. See: http://msdn.microsoft.com/en-us/library/ms998306.aspx
It can log to mail, sql, eventlog, etc. and allows you to set buffers. So it for example won't kill your mailserver if the sql database goes down or if some user discovers a bug and tries to call it too often a second :-)
You can also log failed authentication and app pool restarts with it, it's pretty usefull if you just need it working quick. It's still questionnable if it is the best solution to manage all the errors. Because it might not got all the information you need, for example browser version or smt like that.
ELMAH is a library that plugs in and detects exceptions. You can also log an event yourself. The events and a great deal of data like url parameters and browser information can be emailed to administrators and optionally stored in a database for display. (Rather like an event log for the web site.) It doesn't have a built-in user form that I've seen, but can probably be extended to include such an option.
I've been using/customizing it for about two years now and it is really exceptional.
Another option might be to use Kampyle which includes a feedback box on the bottom right of your web site. You could use Javascript to trigger the box to appear if an issue is detected on the web site.
For an ASP.NET applicatino--or any Web application for that matter--isn't this just a two-step process of:
Logging the error (obviously); and
Put a form on the error document to allow the user to enter feedback.
Or is there more to this?
Your errors will pass through the Application_Error method of the Global.asax.cs file (which you may have to create). I use this fact to capture the error and log it to a database:
void Application_Error(object sender, EventArgs e)
{
try
{
SqlConnection errConnection = new SqlConnection("Your connection string");
// After setting up a command object, I call a stored procedure to save information about
// the crash. I pass two primary arguments. The first is the URL:
errCommand.Parameters.Add("#URL", SqlDbType.VarChar).Value = Request.Url.ToString();
// The second is the error information.
errCommand.Parameters.Add("#EI", SqlDbType.Text).Value = Server.GetLastError().ToString();
// I pass some other information from my session as well...
// After setting up an output parameter called ErrorID, I call the command...
errCommand.ExecuteNonQuery();
// Now Error ID is stored in the session.
Session["ErrorID"] = (int)ErrorID.Value;
}
catch { } // I do NOT want the error handling call to throw an error.
}
Now, you should have set up your Web.Config file so that a specific page gains control when an error occurs. In this page, you'll check the session for the error ID and show it to the user. In the output, I ask the user to write down the error if they would like to call us for more information. If we do receive a request, I can go into the database and get a complete trace of the error.
You can checkout my tutorial on how to implement exception logging in asp.net - http://jesal.us/blog/index.php/2008/04/08/exception-logging-using-the-database/

Extend the exception thrown from ASP.NET when calling a Webservice from JQuery

I'm using JQuery to load controls dynamically in an ASP.NET development environment using JSON and WebServices. Within this solution I have a business logic layer which has a built in validation mechanism (i.e. validating properties and business rules similar to that of CSLA)
When requesting a new control to be loaded dynamically using JQuery and an ASP.NET WebService, I would like to validate the input from the current control against the business logic validation mechanism (i.e. server side validation) and notify the user if there was any problems.
I managed to achieve this, however, when validation fails in the web service I would like to throw a customer exception containing the validation field id's and associated error messages.
In JQuery, I test for this specific ExceptionType and would like to apply the error messages dynamically to the controls listed in the exception type properties. This is where my problem comes in. Even though I created a custom exception with custom properties the exception that is passed to JQuery in JSON format from the WebService is still a standard exception with none of the additional properties listed. I could simply create a JSON formatted string of values in the exception's message property but would ultimately prefer something a little more elegant. Does anyone know how you can override the serialized exception created by ASP.NET for situations such as this...
Thank you in advance...
G
I ran into something very similar a couple days ago - basically there's no way to make ASP.NET generate custom exceptions. This is by design, since returning a specific type of exceptions would
[...] expose implementation
details/bugs to the clients. We could
do something with special exception
type that we let pass through, but its
too late for this release [...]
You could always return different HTTP status codes, and have the browser handle them as custom exceptions - for example, a 500 error would mean one thing, a 401 something else, etc. I think the best solution is to make your method return a string with the exception stack - not elegant, but at least this way the client has all the exception details.
Dave Ward also has info on ASP.NET AJAX service errors.

How do you log errors (Exceptions) in your ASP.NET apps?

I'm looking for the best way to log errors in an ASP.NET application.
I want to be able to receive emails when errors occurs in my application, with detailed information about the Exception and the current Request.
In my company we used to have our own ErrorMailer, catching everything in the Global.asax Application_Error. It was "Ok" but not very flexible nor configurable.
We switched recently to NLog. It's much more configurable, we can define different targets for the errors, filter them, buffer them (not tried yet). It's a very good improvement.
But I discovered lately that there's a whole Namespace in the .Net framework for this purpose : System.Web.Management and it can be configured in the healthMonitoring section of web.config.
Have you ever worked with .Net health monitoring? What is your solution for error logging?
I use elmah. It has some really nice features and here is a CodeProject article on it. I think the StackOverflow team uses elmah also!
I've been using Log4net, configured to email details of fatal errors. It's also set up to log everything to a log file, which is invaluable when trying to debug problems. The other benefit is that if that standard functionality doesn't do what you want it to, it's fairly easy to write a custom appender which can process the logging information as required.
Having said that, I'm using this in tandem with a custom error handler which sends out a html email with a bit more information than is included in the standard log4net emails - page, session variables, cookies, http server variables, etc.
These are both wired up in the Application_OnError event, where the exception is logged as a fatal exception in log4net (which then causes it to be emailed to a specified email address), and also handled using the custom error handler.
First heard about Elmah from the Coding Horror blog entry, Crash Responsibly, and although it looks promising I'm yet to implement it any projects.
I've been using the Enterprise Library's Logging objects. It allows you to have different types of logging (flat file, e-mail, and/or database). It's pretty customizable and has a pretty good interface for updating your web.config for the configuration of the logging. Usually I call my logging from the On Error in the Global.asax.
Here's a link to the MSDN
I use log4net and where ever I expect an exception I log it to the appropriate level. I tend not to re-throw the exception because it doesn't really allow for as-nice user experience, there is less info you can provide at the current state.
I'll have Application_Error also configured to catch any exception which was not expected and the error is logged as a Fatal priority through log4net (well, 404's are detected and logged as Info as they aren't that high severity).
My team uses log4net from Apache. It's pretty lightweight and easy to setup. Best of all, it's completely configurable from the web.config file, so once you've got the hooks in your code setup, you can completely change the way logging is done just by changing the web.config file.
log4net supports logging to a wide variety of locations - database, email, text file, Windows event log, etc. My team has it configured to send detailed error information to a database, and also send an email to the entire team with enough information for us to determine in which part of the code the error originated. Then we know who is responsible for that piece of code, and they can go to the database to get more detailed information.
I recently built an asp.net webservice with NLog, which I use for all my desktop apps. The logging works fine when I'm debugging in Visual Studio, but as soon as I switch to IIS the log file isn't created; I've not yet determined why, but it the fact that I need to look for a solution makes me want to try something else for my asp.net needs!
We use EnterpriseLibrary.ExceptionHandling.Logging. I like it a bit better than log4net because not only do we control the logging completely, but we can control the Throw/NoThrow decision within config as well.
We use a custom homegrown logging util we wrote. It requires you to implement logging on your own everywhere you need it. But, it also allows you to capture a lot more than just the exception.
For example our code would look like this:
Try
Dim p as New Person()
p.Name = "Joe"
p.Age = 30
Catch ex as Exception
Log.LogException(ex,"Err creating person and assigning name/age")
Throw ex
End Try
This way our logger will write all the info we need to a SQL database. We have email alerts set up at the DB level to look for certain errors or frequently occurring errors. It helps us identify exactly where the errors are coming from.
This might not be exactly what you're looking for. Another approach similar to using Global.asax is to us a code injection technique like AOP with PostSharp. This allows you to inject custom code at the beginning and end of every method or on every exception. It's an interesting approach but I believe it may have a heavy performance overhead.

Resources