开发者

Should C# event handlers be exception safe?

Assuming that one event has multiple handlers, if any of event handlers throw an exception then the remaining handlers are not executed.

Does this mean that event handler开发者_高级运维s should never throw?


Since invoking an event means that the caller has no knowledge about the callee:

  1. Invoking an event handler should be robust in the face of arbitrary exceptions. Everything up the call stack needs to clean up its own mess correctly, in case something completely unexpected occurs.

  2. Event handlers should really avoid throwing exceptions.

Things like null reference exceptions are really inexcusable in any code, so obviously we aren't concerned about that.

Things like file IO exceptions can always happen when writing or reading a file, so I would avoid ever doing IO within an event handler. If it makes sense to do IO in an event handler, then it also makes senst to handle the IO exceptions within the handler too. Don't propogate that back to the caller. Find some way to deal with it.


In an ideal world, yes. It's a good idea to try to design event handlers so that they:

  • Don't throw exceptions
  • Execute very quickly

Not doing so will result in unexpected side effects, since other subscribers to the event may never receive messages, or receive them very late.


You should NOT swallow exceptions in an event handler, but neither would I generally recommend throwing them. The problem is that there's generally no good place to catch exceptions thrown from within event handlers.

The design pattern of event handlers leads to some potential problems because they are both indirectly invoked and can be multicast. Since they are indirect, you have to be careful and plan where you can catch exceptions they may throw. Since they are multicast, an exception in a handler may result in other handler never receiving the event.


Why are event handlers are not like other patterns? What's the difference? Exception means that a subprogram tells to a caller that it can not work as it is designed to work. This means that the caller must do something with it. If a handler is performing some processing vital for the use case, then it is sensible that when it crushes, the rest of the program must stop.


It's tempting to do this but ultimately, it depends on the situation.

  • If you want the program to crash rather than run the risk of running in a bad or weird state, then by all means throw an exception.
  • If you REALLY don't care (think hard about this one) and only need to note the exception, then wrapping in try/catch blocks make perfect sense.
  • If you want to give all of the event-handlers a chance to run before crashing (e.g, maybe some of the handlers release resources), then it requires a bit more effort...


In an ASP.NET application, I'd just let the event handlers throw exceptions. Those exceptions will then allow the custom error page functionality of ASP.NET to work.

In a desktop application, I always add a try/catch/finally block around the guts of any event handler. This way, any exceptions are always logged and displayed to the end-user, but never escape the event handler, so they don't crash the application.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜