如何指示 Ninject 对给定类型的任何请求子类型使用工厂方法?

How to instruct Ninject to use a factory method for any requested subtype of a given type?

我有一个基本 Dto 类型,其中有几个通用逻辑和代码(更改通知、验证等)。由于技术原因,每当我必须创建具体 DTO 类型的实例时,如 PersonDTO 我必须使用工厂方法。

var personDto = Dto.Create<PersonDTO>();
// or a non-generic variant like
var personDto = Dto.Create(typeof(PersonDTO));

现在我怎么能要求 Ninject 在我需要注入任何 Dto 后代时使用这个工厂方法呢?我的意思是

Bind<Dto>().ToMethod(ctx => Dto.Create(ctx.Request.Service));

但它不仅可以应用于基础 Dto 请求,还可以应用于任何 Dto 后代类型的每个请求。

我知道我可能会使用约定 Ninject 扩展的 "for all ..." 类功能,但如果可能的话,我宁愿使用没有另一个库的方法。

对于每个需要可解析的类型 (IResolutionRoot.Get<SomeType>()),都需要有一个绑定,例如:

Bind<Dto>().To..
Bind<DtoBla>().To..

除非您要对多种类型进行绑定,例如:

Bind<Dto,DtoBla>().To...

当您想要将多个类型绑定到同一个 实例 时,此重载特别有用,例如,如果您想要一个单例 FooBar : IFoo, IBar 解析为 IFooIBar.

现在,如果您必须做很多非常相似的绑定,Ninject.Extensions.Conventions 只是一个库,可以让您更轻松地完成任务。你不需要使用它,你也可以自己编程类型检测(使用反射)和绑定创建。

反射部分已经在Whosebug上翻了很多遍了,例子见:

  • Generating a list of child classes with reflection in .NET 3.5
  • Register all declared child classes of a class in C#
  • Get all derived types of a type
  • Search an assembly for all child types?

当然,如果你不想用Ninject.Extensions.Reflection,你也可以直接去看看它的源码,看看它是怎么做到的,把相关部分copy过来! ;-)