Castle-Windsor是否支持通过XML配置的ForwardedTypes?

9

我有一个实现多个接口的类。 我想通过XML注册这些接口。 我找到的所有文档都是针对新的Fluent接口的。 这个选项是否支持通过XML实现? 如果要添加此功能,需要哪些步骤?


只是让你知道,现在它已经内置在框架中了。 - Krzysztof Kozmic
@Krzysztof:我需要这个功能,但不想重新发明轮子。不幸的是,我找不到任何关于通过Xml配置进行内置类型转发的文档或链接。 - johnny g
Johny G - 这在文档中有详细说明:http://www.castleproject.org/container/documentation/v21/manual/windsorconfigref.html - Krzysztof Kozmic
1个回答

10

[更新] 在Windsor 2.1或更高版本中,现在可以实现此功能。请参阅此处的语法文档。


截至目前,XML解释器尚未实现此功能。不过,通过一个工具即可轻松添加支持(显然,当希望添加其他缺失配置解析器功能时,该技术也很有用)。

首先,我们添加一个工具,它将检测是否为某个类型创建了处理程序,同时将注册任何转发服务,以便它们指向现有的处理程序:

public class HandlerForwardingFacility : AbstractFacility
{
  IConversionManager conversionManager;

  protected override void Init()
  {
    conversionManager = (IConversionManager)Kernel.GetSubSystem(SubSystemConstants.ConversionManagerKey);
    Kernel.HandlerRegistered += new HandlerDelegate(Kernel_HandlerRegistered);      
  }

  void Kernel_HandlerRegistered(IHandler handler, ref bool stateChanged)
  {
    if (handler is ForwardingHandler) return;

    var model = handler.ComponentModel;

    if (model.Configuration == null) return;

    var forward = model.Configuration.Children["forward"];
    if (forward == null) return;

    foreach (var service in forward.Children)
    {
      Type forwardedType = (Type)conversionManager.PerformConversion(service, typeof (Type));
      Kernel.RegisterHandlerForwarding(forwardedType, model.Name);
    }
  }
}

当然,我们需要在代码中使用它。对于这个例子,我将创建一个支持两个独立服务(IDuck和IDog)的突变鸭/狗组件:

public interface IDog
{
  void Bark();
}

public interface IDuck
{
  void Quack();
}

public class Mutant : IDog, IDuck
{
  public void Bark()
  {
    Console.WriteLine("Bark");
  }

  public void Quack()
  {
    Console.WriteLine("Quack");
  }
}

现在开始配置容器:

 <castle>
  <facilities>
    <facility id="facility.handlerForwarding" type="Example.Facilities.HandlerForwardingFacility, Example" />
  </facilities>
  <components>
    <component id="mutant" service="Example.IDog, Example" type="Example.Mutant, Example">
      <forward>
        <service>Example.IDuck, Example</service>
      </forward>
    </component>
  </components>
</castle>

现在我们可以愉快地执行这样一个测试:

  WindsorContainer container = new WindsorContainer(new XmlInterpreter());

  var dog = container.Resolve<IDog>();
  var duck = container.Resolve<IDuck>();

  Assert.AreSame(dog, duck);
希望这能有所帮助。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接