我想用ASP.NET WebAPI设置Castle Windsor。ASP Web Api - IoC - 解决HttpRequestMessage
我也使用Hyprlinkr软件包(https://github.com/ploeh/Hyprlinkr),因此需要将HttpRequestMessage实例注入到我的控制器的某个依赖项中。
我正在关注Mark Seemann的这篇文章 - http://blog.ploeh.dk/2012/04/19/WiringHttpControllerContextWithCastleWindsor.aspx,但我发现虽然API运行,但是当我打电话给它时,请求只是挂起。没有错误信息。就好像它处于无限循环中一样。它挂在我的自定义ControllerActivator中解决的呼叫
我想我的一些城堡注册是错误的。如果我删除上面的文章中提到的那些,那么我可以成功地调用API(尽管没有我需要解决的问题)
任何想法?
代码如下
//Global.asax
public class WebApiApplication : HttpApplication
{
private readonly IWindsorContainer container;
public WebApiApplication()
{
container =
new WindsorContainer(
new DefaultKernel(
new InlineDependenciesPropagatingDependencyResolver(),
new DefaultProxyFactory()),
new DefaultComponentInstaller());
container.Install(new DependencyInstaller());
}
protected void Application_Start()
{
GlobalConfiguration.Configuration.Services.Replace(typeof(IHttpControllerActivator), new WindsorCompositionRoot(this.container));
}
// installer
public class DependencyInstaller : IWindsorInstaller
{
public void Install(IWindsorContainer container, IConfigurationStore store)
{
container.AddFacility<TypedFactoryFacility>();
container.Register(
Component.For<ValuesController>()
.Named("ValuesController")
.LifeStyle.PerWebRequest,
Component.For<IResourceLinker>()
.ImplementedBy<RouteLinker>()
.LifeStyle.PerWebRequest,
Component.For<IResourceModelBuilder>()
.ImplementedBy<ResourceModelBuilder>()
.LifeStyle.PerWebRequest,
Component.For<HttpRequestMessage>()
.Named("HttpRequestMessage")
.LifeStyle.PerWebRequest
);
}
}
//Activator
public class WindsorCompositionRoot : IHttpControllerActivator
{
private readonly IWindsorContainer container;
public WindsorCompositionRoot(IWindsorContainer container)
{
this.container = container;
}
public IHttpController Create(
HttpRequestMessage request,
HttpControllerDescriptor controllerDescriptor,
Type controllerType)
{
var controller = (IHttpController)this.container.Resolve(controllerType, new { request = request });
request.RegisterForDispose(
new Release(
() => this.container.Release(controller)));
return controller;
}
// DependencyResolver
public class InlineDependenciesPropagatingDependencyResolver : DefaultDependencyResolver
{
protected override CreationContext RebuildContextForParameter(CreationContext current, Type parameterType)
{
if (parameterType.ContainsGenericParameters)
{
return current;
}
return new CreationContext(parameterType, current, true);
}
}
编辑*********** 附加信息****************
所以我成立了一个场景,其中控制器只需要一个HttpRequestMessage作为一个构造函数参数,结果发现:
这工作:
//controller
public class ValuesController : ApiController
{
private readonly HttpRequestMessage _httpReq;
public ValuesController(HttpRequestMessage httpReq)
{
_httpReq = httpReq;
}
//IHttpControllerActivator
public IHttpController Create(
HttpRequestMessage httpRequest,
HttpControllerDescriptor controllerDescriptor,
Type controllerType)
{
var controller = (IHttpController)this.container.Resolve(
controllerType, new { httpReq = httpRequest });
return controller;
但是,这不。
//controller
public class ValuesController : ApiController
{
private readonly HttpRequestMessage _httpReq;
public ValuesController(HttpRequestMessage request)
{
_httpReq = request;
}
//IHttpControllerActivator
public IHttpController Create(
HttpRequestMessage request,
HttpControllerDescriptor controllerDescriptor,
Type controllerType)
{
var controller = (IHttpController)this.container.Resolve(
controllerType, new { request = request });
return controller;
即当不久对象有一个名为“请求”属性和构造函数控制器ARG被称为“请求”。它以某种方式使控制器认为它的请求属性为空。这是什么导致我看到的错误:
无法重用'ApiController'实例。 'ApiController'必须是每个传入消息构造的 。检查您的自定义 'IHttpControllerActivator'并确保它不会制造 相同的实例。
在System.Web.Http.ApiController.ExecuteAsync( controllerContext,的CancellationToken的CancellationToken HttpControllerContext)在 System.Web.Http.Dispatcher.HttpControllerDispatcher.SendAsyncInternal(HttpRequestMessage 请求,的CancellationToken的CancellationToken)在 System.Web.Http .Dispatcher.HttpControllerDispatcher.SendAsync(HttpRequestMessage 请求,的CancellationToken的CancellationToken)
具有此 How can I enrich object composition in StructureMap without invoking setter injection?
读它解释了一个类似的情况。
当然,hyprlinkr对于HttpRequestMessage被称为“request”,因此我确实需要指定具有该属性名称的anon对象。
任何想法?
连接到上面的帖子介绍如何使用温莎城堡与Web API的预览。由于预览和RTM版本之间发生了重大变化,因此这里描述的方法不再有效。请参考http://blog.ploeh.dk/2012/10/03/DependencyInjectionInASPNETWebAPIWithCastleWindsor.aspx对于如何使DI工作与温莎城堡中的Web API RTM的说明。 –
谢谢 - 是的 - 我跟着那个。我只是不知道如何为hyprlinkr需要的HttpRequestMessage进行注册。你能为我指出正确的方向吗? – ChrisCa
像这样:http://stackoverflow.com/q/10854701/126014 –