none
Using IErrorHandler to return data rather than a fault RRS feed

  • Question

  • It is my understanding that IErrorHandler:

    > can be used to change what kind of fault/exception is returned
    > but cannot be used to stop faults from being returned but instead providing a message response that is constructed in the IErrorHandler.


    If it IS possible to use IErrorHandler to intercept exceptions and return a message response instead of an exception or fault, could someone explain how that would be done?

    Thanks.

    Monday, October 13, 2008 5:50 PM

Answers

  • You can definitely use IErrorHandler to return a custom message, not a fault. The example below does that.

     

        public class Post961f822b_046b_4119_927c_7b8ed00b6844  
        {  
            [ServiceContract]  
            public interface ITest  
            {  
                [OperationContract]  
                string EchoString(string text);  
            }  
            public class Service : ITest  
            {  
                public string EchoString(string text)  
                {  
                    if (text == "world"throw new Exception("Error here!");  
                    return text;  
                }  
            }  
            public class MyErrorHandler : IErrorHandler  
            {  
                public bool HandleError(Exception error)  
                {  
                    return true;  
                }  
     
                public void ProvideFault(Exception error, MessageVersion version, ref Message fault)  
                {  
                    fault = Message.CreateMessage(version, "The reply action""A custom message");  
                }  
            }  
            public class MyServiceBehavior : IServiceBehavior  
            {  
                public void AddBindingParameters(ServiceDescription serviceDescription, ServiceHostBase serviceHostBase, System.Collections.ObjectModel.Collection<ServiceEndpoint> endpoints, BindingParameterCollection bindingParameters)  
                {  
                }  
                public void ApplyDispatchBehavior(ServiceDescription serviceDescription, ServiceHostBase serviceHostBase)  
                {  
                    foreach (ChannelDispatcher channelDispatcher in serviceHostBase.ChannelDispatchers)  
                    {  
                        channelDispatcher.ErrorHandlers.Add(new MyErrorHandler());  
                    }  
                }  
                public void Validate(ServiceDescription serviceDescription, ServiceHostBase serviceHostBase)  
                {  
                }  
            }  
            static Binding GetBinding()  
            {  
                BasicHttpBinding result = new BasicHttpBinding();  
                return result;  
            }  
     
            static void CallEchoString(string address, string param)  
            {  
                HttpWebRequest req = (HttpWebRequest)HttpWebRequest.Create(address);  
                req.Method = "POST";  
                req.ContentType = "text/xml; charset=utf-8";  
                req.Headers.Add("SOAPAction""http://tempuri.org/ITest/EchoString");  
                Stream reqStream = req.GetRequestStream();  
                string reqBody = @"<s:Envelope xmlns:s=""http://schemas.xmlsoap.org/soap/envelope/"">  
      <s:Body>  
        <EchoString xmlns=""http://tempuri.org/"">  
          <text>" + param + @"</text>
        </EchoString>
      </s:Body>
    </s:Envelope>";  
                byte[] reqBodyBytes = Encoding.UTF8.GetBytes(reqBody);  
                reqStream.Write(reqBodyBytes, 0, reqBodyBytes.Length);  
                reqStream.Close();  
                HttpWebResponse resp;  
                try 
                {  
                    resp = (HttpWebResponse)req.GetResponse();  
                }  
                catch (WebException e)  
                {  
                    resp = (HttpWebResponse)e.Response;  
                }  
                Console.WriteLine("HTTP/{0} {1} {2}", resp.ProtocolVersion, (int)resp.StatusCode, resp.StatusDescription);  
                Console.WriteLine(new StreamReader(resp.GetResponseStream()).ReadToEnd());  
                Console.WriteLine();  
            }  
     
            public static void Test()  
            {  
                string baseAddress = "http://localhost:8000/Service";  
                ServiceHost host = new ServiceHost(typeof(Service), new Uri(baseAddress));  
                host.AddServiceEndpoint(typeof(ITest), GetBinding(), "");  
                host.Description.Behaviors.Add(new MyServiceBehavior());  
                host.Open();  
                Console.WriteLine("Host opened");  
     
                CallEchoString(baseAddress, "Hello");  
                CallEchoString(baseAddress, "world");  
     
                //ChannelFactory<ITest> factory = new ChannelFactory<ITest>(GetBinding(), new EndpointAddress(baseAddress));  
                //ITest proxy = factory.CreateChannel();  
     
                //Console.WriteLine(proxy.EchoString("Hello"));  
     
                //((IClientChannel)proxy).Close();  
                //factory.Close();  
     
                Console.Write("Press ENTER to close the host");  
                Console.ReadLine();  
                host.Close();  
            }  
        }  
     

     

    Monday, October 13, 2008 10:15 PM