다음을 통해 공유


Consuming Faults, Part 2

Picking up from last time, we were going to look at consuming exceptions to possibly produce a fault message. The same machinery is used here as for the reverse conversion process. Exceptions go through an instance of FaultConverter, you can create your own FaultConverter in a custom channel to control the behavior, and we have a default FaultConverter for a variety of common exception types.

Here's the entire interface for FaultConverter, including the two methods that we used last time for consuming fault messages.

 public abstract class FaultConverter
{
   protected FaultConverter();

   public static FaultConverter GetDefaultFaultConverter(MessageVersion version);
   protected abstract bool OnTryCreateException(Message message, MessageFault fault, out Exception exception);
   protected abstract bool OnTryCreateFaultMessage(Exception exception, out Message message);
   public bool TryCreateException(Message message, MessageFault fault, out Exception exception);
   public bool TryCreateFaultMessage(Exception exception, out Message message);
}

The two methods of interest for today are TryCreateFaultMessage and OnTryCreateFaultMessage. TryCreateFaultMessage takes in an exception and potentially produces a fault message. Override OnTryCreateFaultMessage to handle exceptions and return whether you were successful. Unlike TryCreateException, TryCreateFaultMessage does not reject a null exception argument. This means that you need to do the check yourself if needed. However, the output of TryCreateFaultMessage has the same level of screening as TryCreateException. If you claim that your FaultConverter handled the exception but don't provide a fault message, then we'll throw an InvalidOperationException. If your FaultConverter claims it didn't handle the exception but provides a fault message anyway, we'll again throw an InvalidOperationException.

There are four exception types that the default fault converter will handle to produce specific fault messages.

1.
The private exception type for MustUnderstand (this will look like a CommunicationException to you) becomes a MustUnderstand fault
2.
ActionNotSupportedException becomes an ActionNotSupported fault
3.
The private exception type for ActionMismatch (this will look like a ProtocolException to you) becomes an ActionMismatch fault
4.
MessageHeaderException becomes an InvalidAddressingHeader fault if generated by a duplicate header and a MessageAddressingHeaderRequired fault otherwise

ActionMismatch and MessageHeaderException require WS-Addressing 1.0 for support. ActionNotSupportedException requires either of the versions of WS-Addressing. MustUnderstand works even if you're not using WS-Addressing.

Next time: 2006 Year in Review

Comments

  • Anonymous
    December 29, 2006
    PingBack from http://blogs.msdn.com/drnick/archive/2006/12/28/consuming-faults-part-1.aspx

  • Anonymous
    January 08, 2007
    The last piece of this eleven part series on fault messages covers advice for channel authors that need

  • Anonymous
    January 11, 2007
    What's the best way to expose arbitrary Exceptions wrapped as Faults to clients?  In other words, I want to make the service layer as transparent as possible for developers.  So if they know a service method may throw an exception that derives from Exception or ApplicationException, they only need be concerned with catching that type instead of a FaultException type.  Possible?

  • Anonymous
    January 11, 2007
    The comment has been removed

  • Anonymous
    January 25, 2007
    Let's pick up where we left off last time with the question… How do I modify the HTTP status code that

  • Anonymous
    February 19, 2007
    I haven't forgotten about the goal to put together a table of contents for all of these articles. The

  • Anonymous
    April 11, 2008
    One of the annoyances in service design is that you have to dedicate lots of thinking to your error propagation