Best Practice for Closing WCF

I read that the best practice for using a WCF proxy would be the following:

YourClientProxy clientProxy = new YourClientProxy();

try
{
   .. use your service
   clientProxy.Close();
}
catch(FaultException)
{
   clientProxy.Abort();
}
catch(CommunicationException)
{
   clientProxy.Abort();
}
catch (TimeoutException)
{ 
   clientProxy.Abort();
}

      

My problem is that after I allocated my proxy, I assigned event handlers to it and also initialized another method with the proxy:

public void InitProxy()
{
    sdksvc = new SdkServiceClient();
    sdksvc.InitClusteringObjectCompleted += new EventHandler<InitClusteringObjectCompletedEventArgs>(sdksvc_InitClusteringObjectCompleted);
    sdksvc.InitClusteringObjectAsync(Utils.DSN, Utils.USER,Utils.PASSWORD);
    sdksvc.DoClusteringCompleted += new EventHandler<DoClusteringCompletedEventArgs>(sdksvc_DoClusteringCompleted);
    sdksvc.CreateTablesCompleted += new EventHandler<CreateTablesCompletedEventArgs>(sdksvc_CreateTablesCompleted);
}

      

Now I need to call the InitProxy () method every time I use the proxy if I want to use it, as best practice shows.

Any ideas on how to avoid this?

0


source to share


2 answers


There are several options. One option is to write a helper class like this:

public class SvcClient : IDisposable {
   public SvcClient(ICommunicationObject service) {
      if( service == null ) {
         throw ArgumentNullException("service");
      }
      _service = service;
      // Add your event handlers here, e.g. using your example:
      sdksvc = new SdkServiceClient();
      sdksvc.InitClusteringObjectCompleted += new EventHandler<InitClusteringObjectCompletedEventArgs>(sdksvc_InitClusteringObjectCompleted);
      sdksvc.InitClusteringObjectAsync(Utils.DSN, Utils.USER,Utils.PASSWORD);
      sdksvc.DoClusteringCompleted += new EventHandler<DoClusteringCompletedEventArgs>(sdksvc_DoClusteringCompleted);
      sdksvc.CreateTablesCompleted += new EventHandler<CreateTablesCompletedEventArgs>(sdksvc_CreateTablesCompleted);
   }
   public void Dispose() {
      try {
         if( _service.State == CommunicationState.Faulted ) {
            _service.Abort();
         }
      }
      finally {
         _service.Close();
      }
   }
   private readonly ICommunicationObject _service;
}

      

To use this class, write the following:



var clientProxy = new YourClientProxy();
using(new SvcClient(clientProxy)) {
   // use clientProxy as usual. No need to call Abort() and/or Close() here.
}

      

When the constructor for SvcClient

is called, it then sets an instance SdkServiceClient

as desired. In addition, the class SvcClient

cleans up the service client proxy and also interrupts and / or closes the connection as needed, regardless of how the control flow exits the using

-block.

0


source


I don't see how ClientProxy and InitProxy () are related, but if they are strong related, I would move the ClientProxy initialization to InitProxy (or create a method that initializes both) so you can control both of their lives from there.



0


source







All Articles