Coder Perfect

How to manually log failures with ELMAH

Problem

Is it possible to use ELMAH to perform the following?

logger.Log(" something");

I’m going to do something similar to this:

try 
{
    // Code that might throw an exception 
}
catch(Exception ex)
{
    // I need to log error here...
}

Because this exception was handled, ELMAH will not automatically log it.

Asked by Omu

Solution #1

Since ELMAH 1.0, there has been a direct log writing method:

try 
{
    some code 
}
catch(Exception ex)
{
    Elmah.ErrorLog.GetDefault(HttpContext.Current).Log(new Elmah.Error(ex));
}

ELMAH 1.2 adds a more adaptable API:

try 
{
    some code 
}
catch(Exception ex)
{
    Elmah.ErrorSignal.FromCurrentContext().Raise(ex);
}

There is a distinction between the two approaches:

Answered by Andrey Kamaev

Solution #2

I’d suggest wrapping the call to Elmah in your own simple wrapper class.

using Elmah;

public static class ErrorLog
{
    /// <summary>
    /// Log error to Elmah
    /// </summary>
    public static void LogError(Exception ex, string contextualMessage=null)
    {
        try
        {
            // log error to Elmah
            if (contextualMessage != null) 
            {
                // log exception with contextual information that's visible when 
                // clicking on the error in the Elmah log
                var annotatedException = new Exception(contextualMessage, ex); 
                ErrorSignal.FromCurrentContext().Raise(annotatedException, HttpContext.Current);
            }
            else 
            {
                ErrorSignal.FromCurrentContext().Raise(ex, HttpContext.Current);
            }

            // send errors to ErrorWS (my own legacy service)
            // using (ErrorWSSoapClient client = new ErrorWSSoapClient())
            // {
            //    client.LogErrors(...);
            // }
        }
        catch (Exception)
        {
            // uh oh! just keep going
        }
    }
}

Then, if you need to log an error, simply call it.

try {
   ...
} 
catch (Exception ex) 
{
    // log this and continue
    ErrorLog.LogError(ex, "Error sending email for order " + orderID);
}

The following are some of the advantages:

Note: For contextual information, I’ve added a ‘contextualMessage’ attribute. You can leave it out if you want, but I find it really helpful. Elmah unwraps exceptions automatically, so the underlying exception is still reported in the log, but the contextualMessage is accessible when you click on it.

Answered by Simon_Weaver

Solution #3

To log a problem without throwing an exception, use the Elmah.ErrorSignal() method.

try
{
    // Some code
}
catch(Exception ex)
{
    // Log error
    Elmah.ErrorSignal.FromCurrentContext().Raise(ex);

    // Continue
}

Answered by bigtv

Solution #4

catch(Exception ex)
{
    Elmah.ErrorSignal.FromCurrentContext().Raise(ex);
}

Answered by Darin Dimitrov

Solution #5

Yes, it’s conceivable. ELMAH was created with the intention of catching unhandled exceptions. The ErrorSignal class, on the other hand, can be used to indicate an exception to ELMAH. Those exceptions aren’t thrown (they don’t pop up), but they are transmitted to ELMAH (and to subscribers of the Raise event of the ErrorSignal class).

A small example:

protected void ThrowExceptionAndSignalElmah()
{
    ErrorSignal.FromCurrentContext().Raise(new NotSupportedException());
}

Answered by Christophe Geers

Post is based on https://stackoverflow.com/questions/7441062/how-to-use-elmah-to-manually-log-errors