Autofac和MVC整合:每个注册API控制器类型 [英] Autofac and MVC integration: Register Type per API Controller
问题描述
我与.NET 4.5,ASP.NET MVC 5,包的NuGet工作:
Autofac 3.5.2
Autofac ASP.NET网页API 5个积分3.0.0-RC1
我有一个接口,2个不同的实现方式:
公共类MemoryStreamService:IStreamService {...}
公共类HttpStreamService:IStreamService {...}
此外,通过构造函数注入使用接口的另一具体类:
公共类MainService:IMainService
{
公共MainService(IStreamService streamService){...}
}
和我有利用构造函数注入主要服务过2的ASP.NET Web API控制器:
公共类MemoryStreamController:ApiController
{
公共MemoryStreamController(IMainService mainService){...}
}公共类HttpStreamController:ApiController
{
公共HttpStreamController(IMainService mainService){...}
}
我要的是使用MemoryStreamService实现时需要先MemoryStreamController呼叫的情况下被实例化IStreamService的一个实例,当我们在为HttpStreamController呼叫的背景下HttpStreamService实施。
我想实现这一目标通过以下方式在注册范围内的Global.asax.cs的Application_Start()在Autofac建设者的控制器和服务类:
builder.RegisterType< MainService>()为<&IMainService GT;();builder.RegisterType< MemoryStreamService>()
。至于< IStreamService>()
.InstancePerApiControllerType(typeof运算(MemoryStreamController));builder.RegisterType< HttpStreamService>()
。至于< IStreamService>()
.InstancePerApiControllerType(typeof运算(HttpStreamController));builder.RegisterApiControllers(Assembly.GetExecutingAssembly());
不过貌似InstancePerApiControllerType()为不工作:我越来越总是IStreamService的第一个实施注册类型为两个控制器(本例中,MemoryStreamController中)
我如何需要配置Autofac在由MemoryStreamController处理请求的情况下获得MemoryStreamService的一个实例,并通过HttpStreamController?
hadled HttpStreamService的呼叫实例修改:如果我没有使用依赖注入的控制器,这是我会做什么:
公共类MemoryStreamController:ApiController
{
公共MemoryStreamController()
{
this.mainService =新MainService(新MemoryStreamService());
}
}公共类HttpStreamController:ApiController
{
公共HttpStreamController()
{
this.mainService =新MainService(新HttpStreamService());
}
}
所以我的问题可以理解为:我如何可以通过使用Autofac登记我的两个控制器和我的所有服务达到同样
我已经按照@TravisIllig建议(感谢!)和:结果
1)用于两个流服务命名注册,结果
2)使用2 MainService命名注册,他们在流服务的类型不同,因为它们可以采取如参数搜索
3)通过指定每个命名MainService适当注册的控制器。
builder.RegisterType< HttpStreamService>()命名为<&IStreamService GT(HttpService的);建设者
.RegisterType< MainService>()
。至于< IMainService>()
.WithParameter(ResolvedParameter.ForNamed&所述; IStreamService&GT(memoryService))
.Named&所述; IMainService&GT(mainServiceForMemoryStreams);建设者
.RegisterType< MainService>()
。至于< IMainService>()
.WithParameter(ResolvedParameter.ForNamed< IStreamService>(HttpService的))
.Named&所述; IMainService&GT(mainServiceForHttpStreams);//这是我注册的API其它控制器
builder.RegisterApiControllers(Assembly.GetExecutingAssembly());//手动注册需要IStreamService的一个特定实例的控制器。
需要被放置在后//这些注册RegisterApiControllers(),以便调用Autofac执行所需注射。
builder.RegisterType< MemoryStreamController>()
.WithParameter(ResolvedParameter.ForNamed&所述; IMainService&GT(mainServiceForMemoryStreams));
builder.RegisterType< HttpStreamController>()
.WithParameter(ResolvedParameter.ForNamed&所述; IMainService&GT(mainServiceForHttpStreams));
I'm working with .Net 4.5, ASP.NET MVC 5, and the NuGet packages: Autofac 3.5.2 Autofac ASP.NET Web Api 5 Integration 3.0.0-rc1
I have 2 different implementations of an interface:
public class MemoryStreamService : IStreamService { ... }
public class HttpStreamService : IStreamService { ... }
Also another concrete class that uses the interface by constructor injection:
public class MainService : IMainService
{
public MainService(IStreamService streamService) { ... }
}
And I have 2 ASP.NET Web API Controllers using the main service by constructor injection too:
public class MemoryStreamController : ApiController
{
public MemoryStreamController(IMainService mainService) { ... }
}
public class HttpStreamController : ApiController
{
public HttpStreamController(IMainService mainService) { ... }
}
What I want is to use the MemoryStreamService implementation when an instance of IStreamService need to be instantiated in the context of a call to MemoryStreamController, and the HttpStreamService implementation when we are in the context of a call to the HttpStreamController.
I'm trying to accomplish that by registering the controllers and service classes in Autofac builder at Application_Start() within Global.asax.cs in the following way:
builder.RegisterType<MainService>().As<IMainService>();
builder.RegisterType<MemoryStreamService>()
.As<IStreamService>()
.InstancePerApiControllerType(typeof(MemoryStreamController));
builder.RegisterType<HttpStreamService>()
.As<IStreamService>()
.InstancePerApiControllerType(typeof(HttpStreamController));
builder.RegisterApiControllers(Assembly.GetExecutingAssembly());
But looks like the InstancePerApiControllerType() does not work for that: I'm getting always the first registered implementation Type of the IStreamService (in this sample, MemoryStreamController) for both Controllers.
How do I need to configure Autofac for getting an instance of MemoryStreamService in the context of a request handled by MemoryStreamController, and an instance of HttpStreamService for calls hadled by HttpStreamController?
EDIT: If I weren't using dependency injection for the controllers, this is what I would do:
public class MemoryStreamController : ApiController
{
public MemoryStreamController()
{
this.mainService = new MainService(new MemoryStreamService());
}
}
public class HttpStreamController : ApiController
{
public HttpStreamController()
{
this.mainService = new MainService(new HttpStreamService());
}
}
So my question can be read as: How can I achieve the same by using Autofac for registering both my controllers and all my services?
I've followed @TravisIllig advice (thanks!) and:
1) used named registrations for both "stream services",
2) used 2 named registrations for MainService, they differ in the type of stream service they can take as parameter
3) registered the controllers by specifying each named MainService as appropriate.
builder.RegisterType<MemoryStreamService>().Named<IStreamService>("memoryService");
builder.RegisterType<HttpStreamService>().Named<IStreamService>("httpService");
builder
.RegisterType<MainService>()
.As<IMainService>()
.WithParameter(ResolvedParameter.ForNamed<IStreamService>("memoryService"))
.Named<IMainService>("mainServiceForMemoryStreams");
builder
.RegisterType<MainService>()
.As<IMainService>()
.WithParameter(ResolvedParameter.ForNamed<IStreamService>("httpService"))
.Named<IMainService>("mainServiceForHttpStreams");
// This is for registering the other controllers of my API
builder.RegisterApiControllers(Assembly.GetExecutingAssembly());
// Manually registers controllers that need an specific instance of IStreamService.
// These registrations needs to be placed after the "RegisterApiControllers()" call in order to Autofac to perform the desired injections.
builder.RegisterType<MemoryStreamController>()
.WithParameter(ResolvedParameter.ForNamed<IMainService>("mainServiceForMemoryStreams"));
builder.RegisterType<HttpStreamController>()
.WithParameter(ResolvedParameter.ForNamed<IMainService>("mainServiceForHttpStreams"));
这篇关于Autofac和MVC整合:每个注册API控制器类型的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!