Assembly level exceptoin handler?

A

Andy

Hi all,

I was wondering if it was possible to catch any unhandled exception at
the assembly level. What i'd like to do is catch the exception, wrap
it, log it, and then rethrow it.

It doesn't seem like the GUI should be receiving an ArgumentException
that is thrown from my datalayer, and while I do have try blocks where
i think errors are likely to occur, i'd like to handle the rare
exception in other areas.

It seems like i could use the AppDomain to do this, but then each
layers handler would be triggered when an exception occured in any one.

Thanks
Andy
 
G

Guest

Yes. You can capture it for the purposes of logging it, but can not recover
from it
as well you shouldn't want to because if it was unhandled then you probably
are
not in a stable position to continue. The following code will catch the
unhandled
error and log it to a file, then continue to abort the application.


public class BaseException : Exception, ISerializable
{
public BaseException ()
: base ()
{
}
public BaseException ( string message )
: base ( message )
{

}
public BaseException ( string message, Exception innerException )
: base ( message, innerException )
{
}
protected BaseException ( SerializationInfo info, StreamingContext context )
: base ( info, context )
{
}

}

public sealed class UnhandledExceptionHandler : BaseException
{

public UnhandledExceptionHandler ()
: base ()
{
}

/// <summary>
/// Catches and logs any unhandled exceptions throw in the application.
/// Does NOT handle the error and proceed. The application will still
terminate, but
/// the reasons for the termination will be logged for further review.
/// </summary>
/// <param name="sender"></param>
/// <param name="t"></param>
/// <example>
/// Before Application.Run add the following lines
/// <code>
/// UnhandledExceptionHandler eh = new UnhandledExceptionHandler();
/// AppDomain.CurrentDomain.UnhandledException += new
UnhandledExceptionEventHandler ( eh.OnThreadException );
/// </code>
/// </example>
public void OnThreadException ( object sender, UnhandledExceptionEventArgs
t )
{
//Write the information to a log file.
// OpenOrCreateFile is a company method, it just opens a stream after
ensuring it doesn't exist etc.
using ( System.IO.StreamWriter sw = OpenOrCreateFile (
@"C:\UnhandledButCaughtErrors.txt", false ) )
{
Exception ex = null;
sw.Write (
"\r\n====================================================\r\n" );
sw.Write ( sender.ToString () + "\r\n" );
sw.Write ( "Caught Error on " + DateTime.Now + "\r\n" );
try
{
ex = (Exception)t.ExceptionObject;
}
catch
{
sw.Write ( "UNABLE TO EXTRACT EXCEPTION FROM '" + t.ToString () +
"'\r\n" );
sw.Write ( "====================================================\r\n" );
return;
}
sw.Write ( "Source: " + ex.Source + "\r\n" );
sw.Write ( "Message: " + ex.Message + "\r\n" );
sw.Write ( "TargetSite: " + ex.TargetSite + "\r\n" );
sw.Write ( "Stacktrace: " + ex.StackTrace + "\r\n" );
sw.Write ( "====================================================\r\n" );
}
}
}


You would then execute this code before the Application.Run call:

UnhandledExceptionHandler eh = new UnhandledExceptionHandler ();
AppDomain.CurrentDomain.UnhandledException += new
UnhandledExceptionEventHandler ( eh.OnThreadException );
 
A

Andy

Thanks gmccallum, thats almost what I'm looking for.

I was looking for something similar that would work in my library
assembly, which doesn't have an entry point or any calls to
Application.Run, so I was hoping there was an assembly attribute or
OnLoad event or something similar to do this with.

Thanks
Andy
 
B

Bruce Wood

Generally speaking, you set up global exception handlers in
applications, not in libraries. It's up to each application to decide
what to do with unhandled exceptions.

That said, if you're writing in-house software, and you just want to
make it easy for other developers (set and forget), then you could do
something like create a static class in your library and set up the
global exception handler in that class's static constructor. Then
create static constructors for the other classes in your library and
have them reference the class that sets up the exception handler.

Since static constructors have to run before any method or property in
the class can run, you're guaranteed that the first reference to any
class in your library will set up the global exception handler.

However, as I said, this would be reasonable only for in-house
software. If your library is to be used in various different contexts,
as the developer of an application using your library I would be pissed
off if I set up my own global exception handler for my specific
application, only to have my global exception handler be replaced by
yours when I make the first call into your library.
 
A

Andy

Bruce,

Thanks for the feedback. I think I'll abadon this idea, since it seems
more trouble than its worth.

Just for my own information, when you have a statement obj.Event += new
Handler(), I thought that would add another listener to the event, not
replace existing handlers tied to Event. Is that not the case?

Thanks
Andy
 
B

Bruce Wood

Yes, silly me. I wasn't thinking.

Of course your library would just add another listener, not replace the
event handler for the application. My mistake.,
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Top