抽象类中的依赖注入,ASP.NET Core
Posted
技术标签:
【中文标题】抽象类中的依赖注入,ASP.NET Core【英文标题】:Dependency Injection in abstract class, ASP.NET Core 【发布时间】:2018-09-13 03:10:27 【问题描述】:在我的 ASP.NET Core 2 项目中,我创建了继承 RazorPage 类的新类,以在视图中添加一些额外的属性。
public abstract class WebViewPage<TModel> : Microsoft.AspNetCore.Mvc.Razor.RazorPage<TModel>
public string Version
get
return "1.00.100";
public User CurrentUser
get
//challenge is here:
//return _services.GetRequiredService<IUserService>().GetCurrentUser();
public abstract class WebViewPage : WebViewPage<dynamic>
和_ViewImport.cshtml
文件更改为:
@inherits MyProject.WebViewPage<TModel>
@addTagHelper *, Microsoft.AspNetCore.Mvc.TagHelpers
在挑战代码被标记为评论之前,该项目运行良好。但是,如何将依赖项注入抽象类?或者如何解析抽象类中的服务?
这是我的StartUp.cs
文件:
public void ConfigureServices(IServiceCollection services)
services.AddMemoryCache();
services.AddMvc();
services.AddTransient<IUserService, UserService>();
//services.AddScoped<IRazorPage<?>, WebViewPage<?>(); // ?: challenge!
【问题讨论】:
我想你可以创建一个构造函数来请求依赖项,就像你可以对任何类做的那样?你试过吗? 你不能实例化抽象类,因此你不能用它来注册。你总是必须使用 concrete 类 @Tseng 您对 DI 不适用于抽象类的评论有参考吗? @JayJayJay:C#(或一般的 OOP)基础知识。 abstract class。你想如何实例化抽象类?它只提供了一个基本的实现。要实例化它,您需要一个从基类继承的 concrete 类型/实现。因此,您需要一个一个地注册派生类。 .NET Core 的 DI (Microsoft.Extensions.DependencyInjection
) 不像其他 IoC 容器那样支持程序集或类型扫描,因此您不能在一次调用中注册“所有从 Y 派生的类型”。您必须使用反射、一些 LINQ(或 for/foreach 循环)来过滤它,然后在循环中注册派生类型。内置 IoC 旨在简单且开箱即用,您可以插入具有扩展功能的 3rd 方容器(例如从 Y 派生的扫描或自动注册类型)
【参考方案1】:
如果您需要访问剃须刀页面内的服务提供商,您可以通过Context
property 访问HttpContext
,例如:
var userService = Context.RequestServices.GetRequiredService<IUserService>();
一个可能更好的选择是有一个将IUserService
作为依赖的构造函数。因此,您的类型的实现必须传递该依赖项,本质上要求它们自己具有构造函数依赖项(这是一个很好的显式设计)。
至于依赖注册部分,注意你一般不能注册抽象类,因为它们不能被实例化。
但一般来说,为了注册泛型类型,您必须使用更详细的 AddScoped
重载,它采用实际的 Type
参数:
services.AddScoped(typeof(IRazorPage<>), typeof(WebViewPage<>));
进行泛型方法调用需要一个真实类型作为泛型类型参数,因此您必须在IRazorPage<T>
和WebViewPage<T>
中为类型参数T
指定具体类型。由于您明确不想在此处使用具体类型,而是希望告诉依赖注入容器支持 any 类型,因此您不能在此处使用此语法。
由于typeof
运算符可以确定实际的通用 类型,您可以使用它而无需使用将注册限制为单一类型的特定类型参数。
【讨论】:
如何回答如何将服务注入WebViewPage
?其实我觉得不需要在容器中加入WebViewPage
@CamiloTerevinto 我理解 OP,因为他们不知道如何注册 WebViewPage
作为他们的实现,因为他们显示的 Startup
中的注释行。
我明白真正的问题在于“//挑战在这里://return _services.GetRequiredService以上是关于抽象类中的依赖注入,ASP.NET Core的主要内容,如果未能解决你的问题,请参考以下文章
ASP.NET Core Web 应用程序系列- 使用ASP.NET Core内置的IoC容器DI进行批量依赖注入
ASP.NET Core Web 应用程序系列- 使用ASP.NET Core内置的IoC容器DI进行批量依赖注入(MVC当中应用)