我认为您有几个选择,通常情况下,Autofac 需要在容器中包含类型才能解析它。
最简单直接的解决方案就是注册类型。如果您在构建容器时引用了 Type,则可以使用它来注册它使用 Autofac 并解决它。
Type customType = GetTheRuntimeType();
var builder = new ContainerBuilder();
builder.RegisterType(customType);
如果需要,您可以添加更多内容(InstancePerLifetimeScope() 或 As<IInterface>() 或其他任何内容),但也可以。
如果您在构建容器时没有类型,那么您可以选择事后手动注入属性。有点像服务位置,但这意味着您可以将类型创建分开。
Type customType = GetTheRuntimeType();
var builder = new ContainerBuilder();
// register everything else, then
var container = builder.Build();
using(var scope = container.BeginLifetimeScope())
{
var instance = Activator.CreateInstance(customType);
scope.InjectUnsetProperties(instance);
}
这不是构造函数注入,而是属性。但这很容易。
第三个选项是最集成的,但可能是最难的。你可以implement a registration source 告诉 Autofac 你的类型。我不打算把代码放在这里,因为它有很多内容而且我不是在编译器,而是read the docs and check it out。文档中有示例。这就是 Autofac 在您从未明确注册时动态处理 IEnumerable<T> 之类的方式。您可以想出任何一组您想要的运行时类型,并且所有这些都可以使用注册源动态插入到容器中。
如果您有能力执行第一个选项并仅注册类型,我建议您这样做。这是进行良好集成的最简单方法。
属性注入的东西有效,但它有点像黑客。取决于您的解决方案需要多长时间,或者您是否只需要让它真正快速运行。
注册源解决方案绝对是最健壮的。如果您在创建容器之前没有运行时类型,那么这是最佳选择。从一开始就很难开始工作,但它会更具可扩展性,因为您可以从中捎带任何额外的运行时类型需求。
无论你做什么,不要在你的容器构建后使用Update()添加注册。它已经被标记为过时一年左右,并且即将推出。它不会为您提供长期解决方案。