views:

495

answers:

3

Our WCF services occaisionally spawn a worker thread to handle something that the client doesn't care about. The worker threads do not report any status back to the client. In fact, the service has probably already returned results to the client by the time the thread finishes.

One of these background threads recently caused an exception. The exception went unhandled, so IIS crashed.

I can fix this particular exception, but in the future, someone may add some code that causes another unexpected exception. I want to prevent this from crashing IIS in the future.

I know System.Windows.Forms apps can handle thread exceptions by implementing Application.ThreadException. Is there something similar I can do from a WCF service? Or if Application.ThreadException is the way to go, how would I hook it up from a WCF service?

The MSDN documentation for AppDomain.UnhandledException says it does not prevent crashing. Docs for ServiceModel.AsynchronousThreadExceptionHandler suggest it is only for WCF threads.

At a minimum, I'd like to grab a stack trace from the exception before crashing, but avoid future crashes completely would be ideal.

Again, let me stress this is not an exception I want to return as a WCF fault to a client.

+2  A: 

Since you don't know what caused the exception, the only sensible thing to do is crash. You have no idea what state the service is in, and you could make things worse by continuing.

Remember that IIS will restart the service for you, clean, and presumably working.

John Saunders
Please say the reason for the downvote. Answers are unlikely to improve without knowing what's wrong with them.
John Saunders
I agree with this... if you have an expected exception you should handle it close to its origin. If it's unexpected it should allow the app to crash.
Anderson Imes
Our code in the worker threads will not be doing anything crazy that would have left stuff in an unknown state. Unless IIS itself might be whacked, I'd rather not crash. I'd rather log the issue and keep it chugging along. (Note that I did not down-vote anything.)
Paul Williams
You may not be doing anything crazy today, but you, or .NET, or something you call, may do so tomorrow. All those threads are in the same AppDomain, in the same process; whatever caused the one thread to die might very well cause the other to fail, due to shared memory or other shared resources.
John Saunders
That's true. So would you recommend using AppDomain.UnhandledException to log the original exception before the process dies?
Paul Williams
I would use that as a last resort. To be honest, I'm always sensitive to the need for try/catch around thread and event handlers. I almost never make that mistake anymore. As a result, I've never really depended on UnhandledException. I've implemented it, but I don't think I've ever seen it fire, except in tests.
John Saunders
That's what I personally do.... Handle AppDomain.UnhandledException before the process dies. It's probably overkill, though... if you are using the Tracing API built into .NET it'll likely do this for you automatically using whatever trace listener you have setup for your app right before it bombs."How I learned to stop worrying and love the bomb" :)
Anderson Imes
+1  A: 

If you're spawning threads, you should always make sure they have exception guards. The AppDomain handling for unhandled exceptions only provides a way to log and trace the error, but it won't stop the host from crashing.

tomasr
Yeah, I'm hoping everyone will wrap thread methods with a high-level try/catch. How would one hookup the AppDomain.UnhandledException handler in a WCF service?
Paul Williams
You'd need to do it during startup of the domain. That could be either something in your startup code if you have a custom host, or in your Global.asax if you're hosting in IIS, like in a regular asp.net app.
tomasr
A: 

You could take a look at implementing IErrorHandler with a Dispatch Behavior:

http://msdn.microsoft.com/en-us/library/system.servicemodel.dispatcher.ierrorhandler.aspx

MattK