简体   繁体   中英

WCF Performance Question

I'm pretty much new at WCF and have a performance question. I have the following code that is executing at the client:

    try
    {
      for (int i = 0; i < 20; i++)
      {
         stopwatch.Reset();
         stopwatch.Start();

         var psn = client.GetPsnByPsnId(21);
         var psnList = client.GetPsnBySmartBizClientId(2);
         var container = client.GetContainerByContainerId(3);
         var containerList = client.GetContainerBySmartBizClientId(2);

         stopwatch.Stop();
         Console.WriteLine(string.Format("Pass # {0} completed in {1} milliseconds", i + 1,stopwatch.ElapsedMilliseconds));
     }
   }
   catch (FaultException exception)
   {
      MessageBox.Show(string.Format("Error occurred. The error message is {0}", exception.Message));
   }
   finally
   {
      client.Close();
      client = null;
   }

This code hits a WCF service that is hosted as a Windows service using HTTP binding under .NET 4.0. The problem I have is this. The very first time through the loop, on the very first WCF call (client.GetPsnByPsnID()), there is a very significant delay, 10+ seconds in fact. But, after this first call, each subsequent call, each time through the loop, takes < 1 second, as I would expect. I'm sure this is a WCF issue because if I call the first method outside of WCF, I get < 1 second performance.

Anyone have any idea what might be causing the initial delay?

EDIT: Here is the OnStart code for the Windows Service:

protected override void OnStart(string[] args)
{
   serviceHost = new ServiceHost(typeof(ServiceMethods),new Uri("http://111.111.111.111:1111/Psn"));

   // Add an endpoint and the methods the endpoint will support.
   serviceHost.AddServiceEndpoint(typeof(IServiceMethods), WcfConfiguration.GenerateBinding(Enumerations.WcfBindingType.HTTP), "");

   WcfConfiguration.CreateMexData(serviceHost);
   serviceHost.Open();
}

And here is the GenerateBinding method:

public static System.ServiceModel.Channels.Binding GenerateBinding(Enumerations.WcfBindingType bindingType)
{
   System.ServiceModel.Channels.Binding binding = null;

   BasicHttpBinding httpBinding = new BasicHttpBinding();
   httpBinding.Security.Mode = ((bindingType == Enumerations.WcfBindingType.HTTP) ? BasicHttpSecurityMode.None : BasicHttpSecurityMode.Transport);
   httpBinding.OpenTimeout = new TimeSpan(0, 0, 30);
   httpBinding.SendTimeout = new TimeSpan(0, 0, 30);
   httpBinding.ReceiveTimeout = new TimeSpan(0, 0, 30);
   httpBinding.Security.Transport.ClientCredentialType = HttpClientCredentialType.None;
   httpBinding.ReaderQuotas.MaxStringContentLength = httpBinding.ReaderQuotas.MaxStringContentLength;
   httpBinding.MaxReceivedMessageSize = httpBinding.MaxReceivedMessageSize;
   httpBinding.ReaderQuotas.MaxArrayLength = 1048576;
   httpBinding.MaxBufferSize = httpBinding.MaxBufferSize;

   binding = httpBinding;
   break;
   }
   return binding;
}

public static void CreateMexData(ServiceHost host)
{
  ServiceMetadataBehavior behavior = new ServiceMetadataBehavior();

  behavior.HttpGetEnabled = true;
  host.Description.Behaviors.Add(behavior);
  host.AddServiceEndpoint(typeof(IMetadataExchange), MetadataExchangeBindings.CreateMexHttpBinding(), "mex");
}

If the service is not getting any hits in between your test runs, it may actually be shutting down the WCF service application, and when a new request comes in it totally restarts the app, also taking more time. This can be changed in IIS settings (assuming you're hosting in IIS) so that Worker processes either take longer to shutdown, or don't shutdown at all.

Also, WCF is making the TCP/Http Connection on your first call, subsequent calls are likely using pooled connections. Not having to reestablish the TCP/Http connection saves you a bunch of time.

Finally, With your current implementation, best case scenario you're still doing 4 server round-trips per iteration. You would probably be better served by batching your wcf calls together to reduce round-trips.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM