在HTTPContext范围中注册的对象仍由Model.InstancesOf方法报告

时间:2012-07-31 19:34:30

标签: structuremap

初始化我的aspx页面时,我在StructureMap容器​​中声明它(在OnInit内部)以将其注入适当的演示者:

container.Configure(x => x.For<IMyInterface>().HttpContextScoped().Use(this));

HttpContextScope应强制在当前请求结束时从容器中删除“this”(即页面对象)。为了证明这一点,我在上面的行之后添加了以下代码:

IEnumerable<InstanceRef> refs = container.Model.InstancesOf<IMyInterface>();
foreach (InstanceRef r in refs)
{
  Type t = r.ConcreteType;
}

问题是:

为什么refs收集在每次回发中增加1?

它不仅会增加,而且r.ConcreteType不会引发任何异常 - 这意味着底层对象确实存在。页面被注入到演示者中,演示者本身在HttpContext范围内声明。

HttpContext范围似乎工作不正确,我做错了什么?

提前致谢


我已经考虑过了,结果如下。如果我将容器配置为创建我的类的新实例(它(配置)将只在Application_Start期间完成一次),容器将创建一个实例然后 - 在最后真正删除它的Http请求。但我只注册此类的现有实例。容器不是实例的所有者,因此它可能不会删除它 - 但配置会保留对它的引用(因此根本不能删除它)。另一方面,任何人都不会随时删除配置项(但在每个Http请求中都会添加)。

所以这一切都有效。当然,这是我对“HttpContextScoped”(以及其他一些东西:-()的误解。

所以,我正处于起点:有没有办法从配置中删除这样的注册?

将帖子 好像我无法删除这样的注册。解决方案是:使用手动属性注入替换自动构造函数注入。即:创建演示者(没有其视图)然后 - 手动设置视图:thePresenter.View = this; 上述注册没有添加,问题就不会出现了。

1 个答案:

答案 0 :(得分:1)

这一行:

container.Configure(x => x.For<IMyInterface>().HttpContextScoped().Use(this));

具有误导性。它会让您认为您将其注册为HttpContextScoped,但实际上它已注册为单身人士。

您可以使用lambda“创建”对象:

container.Configure(x => x.For<IMyInterface>().HttpContextScoped().Use(c => this));

lambda方法用于创建对象,但仍应适用正常的范围规则。事实上,如果你使用工厂,你甚至可能根本不需要范围规则(因为lambda被懒惰地评估)。