具有多种依赖实现的 WCF 服务

发布于 2024-09-30 06:19:02 字数 357 浏览 1 评论 0原文

我有一个 WCF 服务,将从不同的客户端调用。

WCF 服务在内部使用 ISomething。该接口有多种实现,我需要一些客户端使用一种实现,而其他客户端使用不同的实现。

此外,我正在使用 Unity 和 IoC 容器。我通常会设置一个自定义工厂来允许 wcf 服务本身及其依赖关系图一起解析,但是如果我有依赖关系的多个实现,我认为我不能采用这种方法,而必须求助于解析服务中的 ISomething(有效地使用 Unity 作为服务定位器)并不理想。

所以我需要解决

(1)如何指定客户端需要哪个 ISomething 实现(例如,使用标头、在每个方法中传递实现字符串、托管多个端点等)

(2)Unity 如何适应?

I have a WCF service that will be called from a various clients.

Internally the WCF service uses an ISomething. There are multiple implementations of this interface and I need some clients to use one implementation and other clients to use a different implementation.

In addition, I am using Unity and an IoC container. I would typically set up a custom factory to allow the wcf service itself to be resolved along with its dependency graph, but if I have multiple implementations of a dependency, I do not think I can go with this approach and would have to resort to resolving the ISomething within the service (effectively using Unity as a service locator) which is not ideal.

So I need to work out

(1) how to specify which implementation of ISomething a client needs (eg. use a header, pass implementation string in each method, host multiple endpoints etc.)

(2) how Unity fits in?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

弃爱 2024-10-07 06:19:02

一种选择是编写一个为您执行选择的装饰器:

public class RoutingSomething : ISomething
{
    private readonly ISomeContext ctx;
    private readonly ISomething s1;
    private readonly ISomething s2;
    private readonly ISomething s3;

    public RoutingSomething(ISomeContext ctx)
    {
        this.ctx = ctx;

        // An even better design would be to inject these too
        this.s1 = new BarSomething();
        this.s2 = new BazSomething();
        this.s3 = new QuxSomething();
    }

    // Assuming ISomething has a Foo method:
    public void Foo()
    {
        if(this.ctx.Bar())
        {
            this.s1.Foo();
            return;
        }
        if(this.ctx.Baz())
        {
            this.s2.Foo();
            return;
        }
        if(this.ctx.Qux())
        {
            this.s3.Foo();
            return;
        }
    }
}

您可以对此进行概括,以便 ISomeContext 只是 ISomething 的抽象工厂。然后开始变成 基于运行时上下文改变依赖关系的通用解决方案

除了其他组件之外,您现在还可以在 Unity 中注册 RoutingSomething。当容器解析服务时,它会将 RoutingSomething 的实例注入其中。

One option is to write a Decorator that performs the selection for you:

public class RoutingSomething : ISomething
{
    private readonly ISomeContext ctx;
    private readonly ISomething s1;
    private readonly ISomething s2;
    private readonly ISomething s3;

    public RoutingSomething(ISomeContext ctx)
    {
        this.ctx = ctx;

        // An even better design would be to inject these too
        this.s1 = new BarSomething();
        this.s2 = new BazSomething();
        this.s3 = new QuxSomething();
    }

    // Assuming ISomething has a Foo method:
    public void Foo()
    {
        if(this.ctx.Bar())
        {
            this.s1.Foo();
            return;
        }
        if(this.ctx.Baz())
        {
            this.s2.Foo();
            return;
        }
        if(this.ctx.Qux())
        {
            this.s3.Foo();
            return;
        }
    }
}

You could generalize this so that ISomeContext is simply an Abstract Factory of ISomething. This then begins to turn into the general solution to varying dependencies based on run-time context.

You can now register RoutingSomething in Unity in addition to your other components. When the container resolves the service, it'll inject an instance of RoutingSomething into it.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文