OperationContext属性在编写自定义ServiceHostFactory之后抛出ObjectDisposedException

时间:2015-05-08 16:57:15

标签: c# wcf wcf-security

更新:在进一步调查过程中,我意识到错误不是我原先想到的自定义ServiceHostFactory,而是我在内部包装OperationContext的方式。我今天晚些时候要更新这个问题。

我最近在我的IIS托管的WCF Web服务中添加了一个自定义ServiceHostFactory,试图将Ninject的依赖注入用于我的服务构造函数。出于某种原因,每当我尝试访问属于OperationContext.Current的属性时,都会抛出以下异常跟踪:

2015-05-08 10:30:39.5718 MyErrorHandler System.ObjectDisposedException: Message is closed.
   at System.ServiceModel.Channels.BufferedMessage.get_Headers()
   at System.ServiceModel.Channels.DelegatingMessage.get_Headers()
   at System.ServiceModel.OperationContext.get_IncomingMessageHeaders()
... (my code here)
   at SyncInvokeFindCurves(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.ProcessMessage41(MessageRpc& rpc)
   at System.ServiceModel.Dispatcher.ImmutableDispatchRuntime.ProcessMessage4(MessageRpc& rpc)
   at System.ServiceModel.Dispatcher.ImmutableDispatchRuntime.ProcessMessage31(MessageRpc& rpc)
   at System.ServiceModel.Dispatcher.ImmutableDispatchRuntime.ProcessMessage3(MessageRpc& rpc)
   at System.ServiceModel.Dispatcher.ImmutableDispatchRuntime.ProcessMessage2(MessageRpc& rpc)
   at System.ServiceModel.Dispatcher.ImmutableDispatchRuntime.ProcessMessage11(MessageRpc& rpc)
   at System.ServiceModel.Dispatcher.ImmutableDispatchRuntime.ProcessMessage1(MessageRpc& rpc)
   at System.ServiceModel.Dispatcher.MessageRpc.Process(Boolean isOperationContextSet) 
2015-05-08 10:31:51.2459 MyErrorHandler System.TimeoutException: The service's security session did not receive a 'close' message from the client within the configured timeout (00:00:10).
   at System.ServiceModel.Security.SecuritySessionServerSettings.ServerSecuritySimplexSessionChannel.OnClose(TimeSpan timeout)
   at System.ServiceModel.Channels.CommunicationObject.Close(TimeSpan timeout)
   at System.ServiceModel.Channels.ServiceChannel.OnClose(TimeSpan timeout)
   at System.ServiceModel.Channels.CommunicationObject.Close(TimeSpan timeout)
   at System.ServiceModel.Dispatcher.MessageRpc.CloseChannel() 

在调试器中,我注意到ObjectDisposedException不仅针对OperationContext.IncomingMessageHeaders抛出,也针对OperationContext.ServiceSecurityContext和其他许多抛出。

我尝试了几种不同的服务主机工厂实现,包括:

  • 自定义服务主机工厂,其扩展ServiceHostFactory并返回带有自定义ServiceHost的{​​{1}}
  • 扩展IInstanceProvider
  • 的自定义服务主机工厂

但无济于事,因为所有人都有同样的问题。我也试过插入NinjectServiceHostFactory,但它仍然没有解决这个问题的根本原因。我也试过谷歌搜索这个错误信息以及可能失败的组件,但我还没有找到类似于我的情况。

以下是我可以用来说明问题的最简单的代码:

IErrorHandler

我的配置包括:

public class WorkingServiceHostFactoryWithNinject : NinjectServiceHostFactory
{
    // ReSharper disable once PrivateFieldCanBeConvertedToLocalVariable
    // ReSharper disable once FieldCanBeMadeReadOnly.Local
    private IKernel _kernel;

    /// <summary>
    /// Initializes the factory.
    /// </summary>
    public WorkingServiceHostFactoryWithNinject()
    {
        _kernel = new StandardKernel();
        _kernel.Bind<IDummyDependency>().To<DummyDependency>();
        ...
        SetKernel(_kernel);
    }
}

<wsHttpBinding>
  <binding name="ServiceBinding" 
            maxBufferPoolSize="4000000000" 
            maxReceivedMessageSize="2000000000" 
            allowCookies="true">
    <readerQuotas maxDepth="32" 
                  maxBytesPerRead="2000000000"
                  maxStringContentLength="2000000000" 
                  maxArrayLength="2000000000" />
    <security mode="TransportWithMessageCredential">
      <transport clientCredentialType="Basic" proxyCredentialType="None" realm="" />
      <message clientCredentialType="UserName" />
    </security>
  </binding>
</wsHttpBinding>

我确切知道的是<serviceBehaviors> <behavior name="ServiceBehavior"> <serviceCredentials> <serviceCertificate findValue="**redacted**" storeLocation="LocalMachine" storeName="My" x509FindType="FindBySubjectName" /> <userNameAuthentication userNamePasswordValidationMode="Custom" customUserNamePasswordValidatorType="CustomUserNamePasswordValidator, MyAssembly" /> </serviceCredentials> <serviceDebug includeExceptionDetailInFaults="true" /> <serviceMetadata httpGetEnabled="true" httpsGetEnabled="true" /> <serviceSecurityAudit auditLogLocation="Application" serviceAuthorizationAuditLevel="Failure" messageAuthenticationAuditLevel="Failure" suppressAuditFailure="true"/> </behavior> </serviceBehaviors> 在我编写自己的ServiceHostFactory之前没有这样做。看起来好像垃圾收集器太早处理了这个消息......

0 个答案:

没有答案