我有一个针对 .Net 4.8 的旧版 ASP.Net Web Forms 应用程序,我想在其中使用依赖注入。我们选择的引擎是 LightInject。
借助此答案和 Microsoft.AspNet.WebFormsDependencyInjection.Unity 项目中ContainerServiceProvider.Cs的源代码,我能够为 LightInject 创建自己的IServiceProvider容器并将其分配给HttpRuntime.WebObjectActivator:
void Application_Start(object sender, EventArgs e)
{
...
// Register the service provider
ContainerServiceProvider containerServiceProvider = new ContainerServiceProvider(HttpRuntime.WebObjectActivator);
HttpRuntime.WebObjectActivator = containerServiceProvider;
// Register services used with dependency injection
var container = containerServiceProvider.Container;
container.Register<IDummyService, DummyService>();
}
我可以注册我的服务,并通过HttpRuntime.WebObjectActivator.GetService()
.
但是,我还没有看到构造函数(或属性)注入在起作用......当我使用以下构造函数声明一个 ASPX 页面(比如 About.aspx)时,当我访问该页面时出现错误:“'About' 确实不包含带 0 个参数的构造函数”
public About(IDummyService dummy)
{
...
}
编辑:这是因为该网站在其配置文件中针对的是旧版本的 .Net。重定向4.8 修复了第一个问题。
现在问题不同了:如果我调试ContainerServiceProvider
我实现的,我可以看到.Net 尝试获取ASP.about_aspx
在临时程序集中定义的服务(例如C:/Windows/Microsoft.NET/Framework64/v4.0.30319/Temporary ASP.NET Files/root/e15e9fc8/41270200/App_Web_cdps00j5.DLL
:),我的 LightInject 容器不知道。
所以我不确定我还需要做什么才能让构造函数注入在我的页面中工作。我假设我必须以某种方式告诉 LightInject 我的页面是依赖注入的候选者,但我不知道如何做到这一点(文档非常稀缺)。另外,我想知道 Unity 是如何工作的,因为除了我重用的实现之外,我在Microsoft.AspNet.WebFormsDependencyInjection.Unity的源代码中看不到任何魔力。ContainerServiceProvider.cs
更新:我尝试手动注册所有实现页面的类型,但它不起作用:
foreach (var assembly in BuildManager.GetReferencedAssemblies().Cast<Assembly>())
{
try
{
container.RegisterAssembly(
assembly,
() => new LightInject.PerScopeLifetime(),
(serviceType, implementingType) => serviceType.IsSubclassOf(typeof(System.Web.UI.Page)));
}
catch
{
}
}