Since it is not possible to catch regular exception from a WCF service in a silverlight application, there is another way to do it by using BehaviorExtensionElement.
1. On Server-side First create a behavior like this:
public class MyFaultBehavior : BehaviorExtensionElement, IEndpointBehavior { public void ApplyDispatchBehavior(ServiceEndpoint endpoint, EndpointDispatcher endpointDispatcher) { SilverlightFaultMessageInspector inspector = new SilverlightFaultMessageInspector(); endpointDispatcher.DispatchRuntime.MessageInspectors.Add(inspector); } public class SilverlightFaultMessageInspector : IDispatchMessageInspector { public void BeforeSendReply(ref Message reply, object correlationState) { if (reply.IsFault) { HttpResponseMessageProperty property = new HttpResponseMessageProperty(); // Here the response code is changed to 200. property.StatusCode = System.Net.HttpStatusCode.OK; reply.Properties[HttpResponseMessageProperty.Name] = property; } } public object AfterReceiveRequest(ref Message request, IClientChannel channel, InstanceContext instanceContext) { // Do nothing to the incoming message. return null; } } // The following methods are stubs and not relevant. public void AddBindingParameters(ServiceEndpoint endpoint, BindingParameterCollection bindingParameters) { } public void ApplyClientBehavior(ServiceEndpoint endpoint, ClientRuntime clientRuntime) { } public void Validate(ServiceEndpoint endpoint) { } public override System.Type BehaviorType { get { return typeof(MyFaultBehavior); } } protected override object CreateBehavior() { return new MyFaultBehavior(); } }
2. On Server-side Modify you web.config:
<system.serviceModel> <!--Add a behavior extension within the service model--> <extensions> <behaviorExtensions> <add name="myFault" type="SilverlightWCF.Web.MyFaultBehavior, SilverlightWCF.Web, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null"/> </behaviorExtensions> </extensions> <behaviors> <!--Add a endpointBehavior below the behaviors--> <endpointBehaviors> <behavior name="myFaultBehavior"> <myFault/> </behavior> </endpointBehaviors> <serviceBehaviors> <behavior name="SilverlightWCF.Web.MyCoolServiceBehavior"> <serviceMetadata httpGetEnabled="true"/> <!--For debugging, it might be cool to have some more error information. to get this, set includeExceptionDetailInFaults to true--> <serviceDebug includeExceptionDetailInFaults="true"/> </behavior> </serviceBehaviors> </behaviors> ... <serviceHostingEnvironment aspNetCompatibilityEnabled="true"/> <services> <service behaviorConfiguration="SilverlightWCF.Web.MyCoolServiceBehavior" name="SilverlightWCF.Web.MyCoolService"> <!--Set the behaviorConfiguration of the endpoint--> <endpoint address="" binding="customBinding" bindingConfiguration="customBinding0" contract="SilverlightWCF.Web.MyCoolService" behaviorConfiguration="myFaultBehavior"/> <endpoint address="mex" binding="mexHttpBinding" contract="IMetadataExchange"/> </service> </services> </system.serviceModel>
3. On Server-side Throw you FaultException
[OperationContract] public void Foo() { throw new FaultException("this is my Exception"); }
4. On Client-side Catch the Exception like this:
void serviceClient_FooCompleted(object sender, System.ComponentModel.AsyncCompletedEventArgs e) { if (e.Error == null) { // In case of success } else if (e.Error is FaultException) { FaultException fault = e.Error as FaultException; string text = e.Error.Message; } }
via http://www.codeproject.com/KB/silverlight/SilverlightWCFService.aspx
Pingback: Handling and Troubleshooting WCF Faults in Silverlight « Vincent Leung .NET Tech Clips