交换机的业务合同执行在运行时WCF交换机、合同、业务、WCF

2023-09-05 01:01:28 作者:断了线的风筝

我将如何切换的服务合同的履行在运行时?

How would I switch the implementation of the service contract at runtime?

说我有:

[ServiceContract]
public interface IService {
    [OperationContract]
    DoWork();
}

public class ServiceA : IService {
    public string DoWork() {
        // ....
    }
}

public class ServiceB : IService {
    public string DoWork() {
        // ....
    }
}

我希望能够切换正在使用从说一个配置文件或在这两者之间的数据库中的值执行。它也有可能做到这一点,而WCF服务是热的?

I'd like to be able to switch the implementation that is being used from say a config file or a value in a database between the two. Would it also be possible to do this while the WCF service is hot?

推荐答案

您需要通过实施IServiceBehavior接口写servicebehavior,并用实例提供初始化服务实例。下面初始化一个新的服务实例,您可以实现不同的逻辑:

You need to write a servicebehavior by implementing IServiceBehavior, and initialize the service instance using an instance provider. The following initializes a new service instance, you may implement a different logic:

public class XInstanceProviderServiceBehavior : Attribute, IServiceBehavior
{        

    public void ApplyDispatchBehavior(ServiceDescription serviceDescription, ServiceHostBase serviceHostBase)
    {
        foreach (var item in serviceHostBase.ChannelDispatchers)
        {
            var dispatcher = item as ChannelDispatcher;
            if (dispatcher != null) 
            {
                dispatcher.Endpoints.ToList().ForEach(endpoint =>
                {
                    endpoint.DispatchRuntime.InstanceProvider = new XInstanceProvider(serviceDescription.ServiceType);
                });
            }
        }
    }

    public void Validate(ServiceDescription serviceDescription, ServiceHostBase serviceHostBase)
    {
    }

    public void AddBindingParameters(ServiceDescription serviceDescription, ServiceHostBase serviceHostBase, Collection<ServiceEndpoint> endpoints, BindingParameterCollection bindingParameters)
    {
    }
}

和有您的实例提供类实现IInstanceProvider和getInstance方法返回相关的实例。

And have your instance provider class implement IInstanceProvider and return related instance in GetInstance method.

public XInstanceProvider :IInstanceProvider
{
    ...

    public object GetInstance(InstanceContext instanceContext, System.ServiceModel.Channels.Message message)
    {
        return new ServiceX();
    }
}

然后,所有你需要的是增加servicebehaviour服务;像

Then all you need is to add servicebehaviour to service; something like

[XInstanceProviderServiceBehavior()]    
    public class MyService : IMyService