gpt4 book ai didi

asp.net - 如何在 ASP.NET Web 窗体中使用依赖注入(inject)

转载 作者:行者123 更新时间:2023-12-02 08:31:52 24 4
gpt4 key购买 nike

我正在尝试找出一种将依赖项注入(inject)与 ASP.NET Web 窗体控件结合使用的方法。

我有很多控件可以直接创建存储库,并使用它们来访问和绑定(bind)数据等。

我正在寻找一种模式,可以将存储库从外部传递给控件(IoC),因此我的控件仍然不知道存储库的构造方式以及它们来自何处等。

我不想让我的控件依赖于 IoC 容器,因此我只想能够使用构造函数或属性注入(inject)来构造控件。

(让事情变得复杂的是,这些控件是由 CMS 在运行时构建并放置在页面上的!)

有什么想法吗?

最佳答案

2019 年更新:随着 Web Forms 4.7.2 的引入,现在对 DI 有了更好的支持。这使得下面的内容无效。请参阅:Wiring up Simple Injector in WebForms in .NET 4.7.2

您可以通过将默认的 PageHandlerFactory 替换为自定义的来使用自动构造函数注入(inject)。这样您就可以使用重载的构造函数来加载依赖项。您的页面可能如下所示:

public partial class HomePage : System.Web.UI.Page
{
private readonly IDependency dependency;

public HomePage(IDependency dependency)
{
this.dependency = dependency;
}

// Do note this protected ctor. You need it for this to work.
protected HomePage () { }
}

可以在 web.config 中配置自定义 PageHandlerFactory,如下所示:

<?xml version="1.0"?>
<configuration>
<system.web>
<httpHandlers>
<add verb="*" path="*.aspx"
type="YourApp.CustomPageHandlerFactory, YourApp"/>
</httpHandlers>
</system.web>
</configuration>

您的CustomPageHandlerFactory可能如下所示:

public class CustomPageHandlerFactory : PageHandlerFactory
{
private static object GetInstance(Type type)
{
// TODO: Get instance using your favorite DI library.
// for instance using the Common Service Locator:
return Microsoft.Practices.ServiceLocation
.ServiceLocator.Current.GetInstance(type);
}

public override IHttpHandler GetHandler(HttpContext cxt,
string type, string vPath, string path)
{
var page = base.GetHandler(cxt, type, vPath, path);

if (page != null)
{
// Magic happens here ;-)
InjectDependencies(page);
}

return page;
}

private static void InjectDependencies(object page)
{
Type pageType = page.GetType().BaseType;

var ctor = GetInjectableCtor(pageType);

if (ctor != null)
{
object[] arguments = (
from parameter in ctor.GetParameters()
select GetInstance(parameter.ParameterType)
.ToArray();

ctor.Invoke(page, arguments);
}
}

private static ConstructorInfo GetInjectableCtor(
Type type)
{
var overloadedPublicConstructors = (
from constructor in type.GetConstructors()
where constructor.GetParameters().Length > 0
select constructor).ToArray();

if (overloadedPublicConstructors.Length == 0)
{
return null;
}

if (overloadedPublicConstructors.Length == 1)
{
return overloadedPublicConstructors[0];
}

throw new Exception(string.Format(
"The type {0} has multiple public " +
"ctors and can't be initialized.", type));
}
}

缺点是,这仅在完全信任模式下运行时才有效。您可以阅读有关它的更多信息 here 。但请注意,在部分信任中开发 ASP.NET 应用程序 seems a lost cause .

关于asp.net - 如何在 ASP.NET Web 窗体中使用依赖注入(inject),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/589374/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com