WCF调用导致内存泄漏

时间:2011-07-05 14:26:45

标签: wcf memory-leaks

我们遇到了泄漏内存的WCF服务调用问题。在我们的研究中,我们认为我们正确地调用服务并正确处理从它返回的错误。我们甚至用MSDN文章和从MS网站获得的样本WCF代码证实了这一点。

以下是导致泄漏的代码示例。在SaveAssociation调用上,另一端的代码抛出异常。这会导致通道进入故障状态。第一个catch语句捕获异常(SystemException)并在客户端上调用Abort(),它应该立即中止会话并关闭客户端连接。但是,观看此过程会在循环中反复运行此代码,我们只会看到进程爬升和爬升所使用的内存。

var client = new FrameworkServiceReference.MAServiceClient();

// Get User domain name
client.ClientCredentials.UserName.UserName = "username";
client.ClientCredentials.UserName.Password = "password";

OperationContextScope a1 = new OperationContextScope(client.InnerChannel);
MessageHeader<string> customHeaderAppID = new MessageHeader<string>("Account Management");
System.ServiceModel.Channels.MessageHeader a2 = customHeaderAppID.GetUntypedHeader("application", "http://www.ma.com");
OperationContext.Current.OutgoingMessageHeaders.Add(a2);

try
{
            client.SaveAssociation(association);
            client.Close();
}
catch (SystemException se)
{
            client.Abort();
}
catch (Exception ex)
{
            client.Abort();
}

以下是我们收到的错误......

System.ServiceModel.FaultException`1[System.ServiceModel.ExceptionDetail]: Object reference not set to an instance of an object. (Fault Detail is equal to An ExceptionDetail, likely created by IncludeExceptionDetailInFaults=true, whose value is:
System.NullReferenceException: Object reference not set to an instance of an object.
   at Multiview.Business.Core.CoreObject.ValidateItem(String Item, String Value)
   at Multiview.Business.Core.User.UpdateUser()
   at Multiview.Business.Core.User.Save()
   at Multiview.Core.ServiceLibrary.MultiviewService.SaveCRMUser(User user, Guid CRMGuid)
   at SyncInvokeSaveCRMUser(Object , Object[] , Object[] )
   at System.ServiceModel.Dispatcher.SyncMethodInvoker.Invoke(Object instance, Object[] inputs, Object[]& outputs)
   at System.ServiceModel.Dispatcher.DispatchOperationRuntime.InvokeBegin(MessageRpc& rpc)
   at System.ServiceModel.Dispatcher.ImmutableDispatchRuntime.ProcessMessage5(MessageRpc& rpc)
   at System.ServiceModel.Dispatcher.ImmutableDispatchRuntime.ProcessMessage4(MessageRpc& rpc)
   at System.ServiceModel.Dispatcher.ImmutableDispatchRuntime.ProcessMessage3(MessageRpc& rpc)
   at System.ServiceMode...).

可以做些什么来阻止这种泄漏?

2 个答案:

答案 0 :(得分:2)

如果服务器上的内存增加,请检查服务器日志。您返回的对象可能具有循环引用。这意味着当它返回时,服务器将在序列化对象时抛出堆栈溢出。

尝试使用以下命令配置您的服务:

IncludeExceptionDetailInFaults=true

创建一些日志(服务器端和客户端端):

<system.diagnostics>
<sources>
  <source name="System.ServiceModel" switchValue="Error, ActivityTracing" propagateActivity="true">
    <listeners>
      <add name="xml" />
    </listeners>
  </source>
  <source name="CardSpace">
    <listeners>
      <add name="xml" />
    </listeners>
  </source>
  <source name="System.IO.Log">
    <listeners>
      <add name="xml" />
    </listeners>
  </source>
  <source name="System.Runtime.Serialization">
    <listeners>
      <add name="xml" />
    </listeners>
  </source>
  <source name="System.IdentityModel">
    <listeners>
      <add name="xml" />
    </listeners>
  </source>
</sources>
<sharedListeners>
  <add name="xml" type="System.Diagnostics.XmlWriterTraceListener" initializeData="C:\t\mylog.svclog" />
</sharedListeners>
</system.diagnostics>

答案 1 :(得分:1)

如果你有内存泄漏问题,你应该从一些内存分析器开始,找出你的内存中有哪些对象。这将导致您泄漏的来源。

您可以从OperationContextScope是一次性的事实开始。