【问题标题】:Resolving a Generic with a Generic parameter in Castle Windsor在 Castle Windsor 中使用 Generic 参数解析 Generic
【发布时间】:2009-11-04 21:47:09
【问题描述】:

我正在尝试注册 IRequestHandler1[GenericTestRequest1[T]] 之类的类型,该类型将由 GenericTestRequestHandler`1[T] 实现,但我目前从 Windsor 收到错误“Castle.MicroKernel.ComponentNotFoundException : No component for支持服务“是否支持这种类型的操作?或者它是否远离支持的寄存器( Component.For(typeof( IList).ImplementedBy( typeof( List ) ) )

以下是破坏测试的示例。 ///////////////////////////////////////// ////

public interface IRequestHandler{}

public interface IRequestHandler<TRequest> : IRequestHandler where TRequest : Request{} 

public class  GenericTestRequest<T> : Request{} 

public class GenericTestRequestHandler<T> : RequestHandler<GenericTestRequest<T>>{}

[TestFixture]
public class ComponentRegistrationTests{
   [Test]
   public void DoNotAutoRegisterGenericRequestHandler(){

var IOC = new Castle.Windsor.WindsorContainer();
var type = typeof( IRequestHandler<> ).MakeGenericType( typeof( GenericTestRequest<> ) );
IOC.Register( Component.For( type ).ImplementedBy( typeof( GenericTestRequestHandler<> ) ) );

var requestHandler = IoC.Container.Resolve( typeof(IRequestHandler<GenericTestRequest<String>>));

Assert.IsInstanceOf <IRequestHandler<GenericTestRequest<String>>>( requestHandler );
Assert.IsNotNull( requestHandler );
}
}

【问题讨论】:

    标签: .net inversion-of-control castle-windsor ioc-container


    【解决方案1】:

    我认为这里的问题是服务类型不是泛型类型定义,而实现类型。以下测试全部通过,证明了这一点:

    [Test]
    public void ServiceIsNotGenericTypeDefinition() {
        var service = typeof(IRequestHandler<>).MakeGenericType(typeof(GenericTestRequest<>));
        Assert.IsFalse(service.IsGenericTypeDefinition);
    }
    
    [Test]
    public void ImplementationIsGenericTypeDefinition() {
        var implementation = typeof (GenericTestRequestHandler<>);
        Assert.IsTrue(implementation.IsGenericTypeDefinition);
    }
    
    [Test]
    [ExpectedException(typeof(InvalidOperationException))]
    public void FillOpenGenericType() {
        var service = typeof(IRequestHandler<>).MakeGenericType(typeof(GenericTestRequest<>));
        service.MakeGenericType(typeof (string));
    }
    

    这是因为接口上实际打开的参数类型是“内部”类型,而不是“结果”类型。

    所以这就像用接口ICollection(不是通用的ICollection!)和实现类型List&lt;&gt;注册一个组件。当您向 Windsor 询问 ICollection 时,它不知道将什么类型参数应用于实现类型。

    在您的情况下,情况更糟,因为您要求IRequestHandler&lt;GenericTestRequest&lt;String&gt;&gt; 并没有真正注册。 (IRequestHandler&lt;GenericTestRequest&lt;&gt;&gt;)

    希望这很清楚......

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2012-06-06
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-11-30
      • 2014-08-18
      • 2016-02-26
      • 1970-01-01
      相关资源
      最近更新 更多