以编程方式设置InstanceContextMode

时间:2012-01-17 21:49:16

标签: wcf-web-api

有办法做到这一点......

[ServiceBehavior(InstanceContextMode = InstanceContextMode.Single)]

...编程?

原因是我想在集成测试我的服务时直接将我的服务实例传入我的自托管助手类。

我正在使用Castle Windsor来创建我的所有对象,这在使用测试网站时可以正常工作。但是当我尝试使用我的HttpWebService帮助程序类时,我收到以下错误...

System.InvalidOperationException was unhandled by user code
  Message=In order to use one of the ServiceHost constructors that takes a service instance, the InstanceContextMode of the service must be set to InstanceContextMode.Single.  This can be configured via the ServiceBehaviorAttribute.  Otherwise, please consider using the ServiceHost constructors that take a Type argument.
  Source=System.ServiceModel

这是我的助手类的构造函数......

public HttpWebService(string baseUri, string acceptType, TApi serviceInstance = null)
{
    _baseUri = baseUri;
    _acceptType = acceptType.ToLower();

    _host = serviceInstance == null
                ? new HttpServiceHost(typeof (TApi), baseUri)
                : new HttpServiceHost(serviceInstance, baseUri);
    _host.Open();
    _client = new HttpClient();
    _client.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue(_acceptType));
}

所以,我需要在“集成测试模式”下以编程方式设置InstanceContextMode,即 - 在我的帮助类中。

我想我需要做这样的事情......

if (serviceInstance != null)
{
    _host = new HttpServiceHost(serviceInstance, baseUri);
    var whatDoIDoNow = null;
    _host.Description.Behaviors.Add(whatDoIDoNow);
}

任何帮助/指导都会很棒,因为我真的坚持这个。

3 个答案:

答案 0 :(得分:54)

我正在回答我自己的问题,因为我在stackoverflow上找到了另一个answer的解决方案,我认为stackoverflow是一个很好的搜索地点,甚至不需要提问,所以希望我会添加通过回答我自己的问题并找到另一个答案的链接,而不仅仅是关闭我自己的问题来实现这种丰富性。

我的代码现在看起来像这样......

public HttpWebService(string baseUri, string acceptType, TApi serviceInstance = null)
{
    _baseUri = baseUri;
    _acceptType = acceptType.ToLower();

    if (serviceInstance != null)
    {
        _host = new HttpServiceHost(serviceInstance, baseUri);
        var behaviour = _host.Description.Behaviors.Find<ServiceBehaviorAttribute>();
        behaviour.InstanceContextMode = InstanceContextMode.Single;
    }
    _host = _host ?? new HttpServiceHost(typeof (TApi), baseUri);

    _host.Open();
    _client = new HttpClient();
    _client.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue(_acceptType));
}

我改变了这个......

_host = serviceInstance == null
            ? new HttpServiceHost(typeof (TApi), baseUri)
            : new HttpServiceHost(serviceInstance, baseUri);

......对此...

if (serviceInstance != null)
{
    _host = new HttpServiceHost(serviceInstance, baseUri);
    var behaviour = _host.Description.Behaviors.Find<ServiceBehaviorAttribute>();
    behaviour.InstanceContextMode = InstanceContextMode.Single;
}
_host = _host ?? new HttpServiceHost(typeof (TApi), baseUri);

答案 1 :(得分:1)

即使原始答案包含解决方案,它也只是问题的直接答案

ServiceHost host = new ServiceHost(typeof(YourService)); //Or get the Servicehost
((ServiceBehaviorAttribute)host.Description.
Behaviors[typeof(ServiceBehaviorAttribute)]).InstanceContextMode 
= InstanceContextMode.Single;

答案 2 :(得分:0)

我们还可以在Service类上使用ServiceBehaviourAttribute来设置InstanceContextMode,如下所示:

[ServiceBehavior(InstanceContextMode = InstanceContextMode.Single,
ConcurrencyMode = ConcurrencyMode.Multiple)]
public class MyService : IMyService
{
//service code
}