没有ASP.NET Core的.NET Core中的DI

gza*_*zak 5 daemon dependency-injection .net-core asp.net-core

我正在寻找使用.NET Core编写一个守护进程,它基本上就像一个chron作业,只是在某个时间间隔内编排API/DB调用.因此,它不需要公开任何Web路由,因此不需要ASP.NET Core.

但是,afaik ASP.NET Core是您可以获得Startup所有可能需要的所有DI管道和基于环境的配置的好类.

我看到它的方式,我有两个选择:

  1. 放弃ASP.NET Core并自己连接DI框架.如果我走那条路,我该怎么做?
  2. 包含仅用于DI部分的ASP.NET Core,但是如何在任何请求上下文之外生成"永远运行"的后台任务?我的理解是,DI框架非常假设有一些进入的请求来协调所有注入.

Joe*_*kes 12

您似乎提出了多个问题,让我尝试一一回答。

无需启动类的依赖注入。

这绝对是可能的。由于该类Startup是 WebHostBuilder 包(其中包含 Kestrel/webserver)的一部分。依赖注入是nuget包,只是对该包的依赖,因此可以通过以下方式单独使用:

var services = new ServiceCollection();
services.AddTransient<IMyInterface, MyClass>();
var serviceProvider = services.BuildServiceProvider(); //ioc container
serviceProvider.GetService<IMyInterface>();
Run Code Online (Sandbox Code Playgroud)

因此,在您的程序主程序(启动函数)中,您可以添加此代码,甚至可以使 ServiceProvider Staticaly 可用。

请注意,IHostingEnvironment 也是 kestrel 包的一部分,您无法使用,但有一些简单的解决方法。

登记

我不确定生成后台任务/永远运行到底是什么意思。但在 dotnet 中,您可以生成任务来TaskCreationOptions.LongRunning告诉调度程序您的任务将运行很长时间,并且 dotnet 我们会为此优化线程。您也可以在这些任务中使用serviceProvider

DI 的唯一缺点是您需要在应用程序启动时对其进行设置,并且无法在运行应用程序时添加新服务(实际上您可以添加服务然后重建 serviceProvider,但使用另一个外部 IOC 容器更容易)。如果您考虑运行某种会自动注册依赖项的插件系统,那么您最好创建自己的工厂方法。

另请注意,使用插件时,当它们作为 dll 加载时,无法卸载,因此如果理论上您有无限数量的插件,则每次添加新插件时,您的内存都会慢慢积累。

  • “DI 的唯一缺点是您需要在应用程序启动时对其进行设置,并且无法在运行应用程序时添加新服务”。我想说这根本不是一个缺点,因为 [Register-Resolve-Register 是一种反模式](/sf/answers/2979371671/)。 (3认同)

Dal*_*oft 7

从 .NET Core 2.1 开始,这可以/应该使用通用主机来完成。来自 .NET Core 文档:

“通用主机的目标是将 HTTP 管道与 Web 主机 API 解耦,以支持更广泛的主机场景......”

https://learn.microsoft.com/en-us/aspnet/core/fundamentals/host/generic-host?view=aspnetcore-2.1

public static async Task Main(string[] args)
{
  var builder = new HostBuilder()
    .ConfigureAppConfiguration((hostingContext, config) =>

    .ConfigureServices((hostContext, services) =>
    {
       // ...
    });

  await builder.RunConsoleAsync();
}
Run Code Online (Sandbox Code Playgroud)