Castle Windsor,根据一些上下文参数选择服务实现

时间:2013-07-05 10:33:55

标签: castle-windsor windsor-facilities

使用Castle Windsor 3.2 我需要根据上下文参数动态解决服务实现。 以下是我想要做的基本示例:

我有服务IFoo

public interface IFoo
{
   object GetSomething();
}

由2个不同的类Foo1和Foo2

实现
public class FooBase
{
   public int Number {get; private set;}

   public FooBase(int number)
   {
      Number = number;
   }
}

public class Foo1 : IFoo
{
   public Foo1(int number):base(number)
   public object GetSomething()
   {
      return "Foo1";
   }
}

public class Foo2 : IFoo
{
   public Foo2(int number):base(number)
   public object GetSomething()
   {
      return "Foo2";
   }
}

我想用数字作为参数调用城堡windsor resolve方法,并根据我想拥有Foo1或Foo2对象的数字:

var foo1 = container.Resolve<IFoo>(new {number= 1});
// foo1 is Foo1
var foo2 = container.Resolve<IFoo>(new {number= 2});
// foo2 is Foo2

我尝试了几种可能的解决方案,但由于缺少Castle Windsor文档和示例,我真的很困惑,并补充说大多数示例都不是最新的并且使用的是过时的API。

所以我看到了一些使用以下概念的例子,但它们似乎都不是我的要求:

  1. HandlerSelector
  2. 类型工厂设施
  3. UsingFactoryMethod

2 个答案:

答案 0 :(得分:1)

使用以下注册码:

container = new WindsorContainer();
        container.AddFacility<TypedFactoryFacility>();
        container.Register(
            Component.For<FooSelector>,
            Component.For<Foo1>(),
            Component.For<Foo2>(),
            Component.For<IFooFactory>().AsFactory(c => c.SelectedWith<FooSelector>())
        );

创建一个Foo工厂:

public interface IFooFactory
{
    IFoo CreateFoo(int number);
}

和选择器:

public class FooSelector : DefaultTypedFactoryComponentSelector
{
    protected override Type GetComponentType(System.Reflection.MethodInfo method, object[] arguments)
    {
        var argument = (int) arguments[0];
        if (argument == 1) return typeof (Foo1);
        if (argument == 2) return typeof(Foo2);
        throw new ApplicationException();
    }
}

现在解析IFooFactory并使用您想要的值调用create method。

亲切的问候, Marwijn。

答案 1 :(得分:0)

以下代码对我有用:

container = new WindsorContainer();
        container.AddFacility<TypedFactoryFacility>();
        container.Register(
            Component.For<IFoo>().ImplementedBy<Foo1>().Named("Foo1"),
            Component.For<IFoo>().ImplementedBy<Foo2>().Named("Foo2"),
            Component.For<IFooFactory>().AsFactory(c => c.SelectedWith<FooSelector>())
        );

创建一个Foo工厂:

public interface IFooFactory
{
    IFoo CreateFoo(int number);
}

和选择器:

public class FooSelector : DefaultTypedFactoryComponentSelector
{
    protected override string GetComponentName(System.Reflection.MethodInfo method, object[] arguments)
    {
        var argument = (int) arguments[0];
        return string.Format("Foo{0}", argument);
    }
}