Search code examples
asp.netwcffaultexception

Fault Exceptions never being catched at client


I am trying to implement a FaultException in a WCF service. I referred various articles. However it seems that FaultExceptions are never being catched at client. I have written code like this,

Service Contract -

 [ServiceContract]
    public interface IService2
    {
        [OperationContract]
        [FaultContract(typeof(MyException))]
        [DebuggerStepThrough]
        MyException GetData(int value);
    }

    [DataContract]
    public class MyException 
    {
        [DataMember]
        public bool Result { get; set; }

        [DataMember]
        public string ErrorMessage { get; set; }

        [DataMember]
        public Exception MyInnerException { get; set; }

        [DataMember]
        public string ClientMessage { get; set; }
    }

Service Implementation -

public class Service1 : IService2
    {

        public MyException GetData(int value)
        {
            MyException mx = new MyException();
            try
            {
                double a = 44;
                if (value == 0)
                {
                    throw new DivideByZeroException();
                }
                double res = a / value;
                mx.ClientMessage = "Everything is well";
                mx.Result = true;
                return mx;
            }
            catch (DivideByZeroException dvex)
            {
                mx.Result = true;
                mx.ClientMessage = "Divide by zero";
                mx.MyInnerException = dvex;
                mx.ErrorMessage = dvex.StackTrace;
                throw new FaultException<MyException>(mx, dvex.ToString());
            }                      

        }
    }

Client (aspx.cs page) -

try
            {
                FaultContractsDemo.ServiceReference1.Service2Client o = new ServiceReference1.Service2Client();
                MyException data = o.GetData(0);
                if (data.Result)
                    lblMessage.Text = "All is well";
            }
            catch (FaultException<MyException> ex)
            {
                lblMessage.Text = ex.Detail.ClientMessage;
            }

The service layer throws an exception, but client never recieves any. I am getting unhandled exception like,

The underlying connection was closed: The connection was closed unexpectedly.


Solution

  • I could reproduce this issue (in a different, but very similar situation). The problem is caused by this combination:

    // Fault class:
    [DataMember]
    public Exception MyInnerException { get; set; }
    
    // Just before throwing the FaultException
    mx.MyInnerException = dvex; // <-- DivideByZeroException
    

    WCF does not like serializing the DivideByZeroException, which is necessary to get it across the wire. Comment out that line and things will probably start to work.

    To add to this, normally you wouldn't want to pass the inner exception (at least: not like this), because that would be considered a security risk. There's one exception though: this is when you're debugging. In that case, refer to the article on IncludeExceptionDetailInFaults: this allows you to see exception details on the client side.