.NET Core依赖注入是否与.NET Framework向后兼容?

16

我想将一个.NET Framework库重建为.NET Core,并在.NET Framework应用程序中使用该库。

这个库需要一个数据库连接字符串,在.NET Core中,我会使用依赖注入将带有连接字符串配置的内容传递给库类。

public MyRepository(IConfiguration config)
{
    _connectionString = config.GetConnectionString("MyDb");
}

我该如何在不引入复杂的 DI 框架的情况下,从 .NET Framework 4.6 库中使用这个类呢?

2个回答

27

我已经在.NET Framework 4.7.1中使用了新的Microsoft.Extensions库,主要包括DependencyInjectionConfiguration库。

2.x版本的库与.NET Standard 2.0兼容,这意味着它们可以添加到任何与.NET Standard 2.0兼容的运行时应用程序中,例如.NET Framework 4.7.1及以上版本或.NET Core 2.0及以上版本。

在旧版运行时(4.6.1及更高版本),NuGet可能需要添加一些具有较新版本的某些系统程序集的额外软件包,例如System.Runtime。

你无法将2.0扩展包添加到4.6中。你可以添加旧版的1.x版本,这些版本用于.NET Core 1.x。

在.NET Core和完整框架中,配置扩展的方法是相同的:

  1. 你创建一个ConfigurationBuilder,添加配置提供程序,并在最后调用Build()以获取IConfigurationRoot对象:

IConfigurationRoot configRoot = new ConfigurationBuilder()
    .AddUserSecrets<Program>()
    .AddJsonFile($"appsettings.json")
    .Build();
  • 创建一个ServiceCollection,注册服务并调用BuildServiceProvider()来获取ServiceProvider。您将使用该 ServiceProvider 创建需要注入的类的实例。

  • ASP.NET Core,也适用于完整的框架,提供额外的辅助库来隐藏样板代码。

    IServiceCollection services = new ServiceCollection();
    ServiceProvider provider= services.AddSingleton<MyService>()
                                      .AddTransient<AnotherService>()
                                      .AddTransient<ServiceThatNeedsTheOthers>()
                                      .BuildServiceProvider();
    

    假设第三个服务是:

    public class ServiceThatNeedsTheOthers
    {
        public ServiceThatNeedsTheOthers(MyService s1,AnotherService s2){..}
    }
    

    您可以使用以下方式创建:

    var service3=provider.GetRequiredService<ServiceThatNeedsTheOthers>();
    

    所有这些内容都在Mark Michaelis的Essential .NET专栏中进行了描述,例如Dependency Injection with .NET CoreConfiguration in .NET Core。这些文章展示了如何在需要编写所有样板代码的控制台应用程序中设置和使用扩展。

    PS ASP.NET Core 2.0也可以瞄准完整框架。对于新的Web应用程序,创建一个针对4.7.1的ASP.NET Core 2.0项目可能是有意义的。


    已删除4.6版本的.NET Framework,因为我对如何在与dotnet标准兼容的.NET Framework中执行此操作感兴趣。 - fantastischIdee
    然后使用4.7.1版本。它是标准2.0兼容的,因此不需要任何额外的库。 - Panagiotis Kanavos
    @fantastischIdee PS ASP.NET Core 2.0也可以针对完整框架进行目标设置,而不仅仅是Core。如果您想创建Web应用程序,您应该创建一个ASP.NET Core 2.0项目。 - Panagiotis Kanavos
    @PanagiotisKanavos,我该如何在标准的 .NET Framework 中使用 log4net 添加 ILogger 的 DI? - fededim
    1
    轻而易举。您只需添加相同的Net Core包Microsoft.Extensions.Logging.Log4Net.AspNetCore,并使用services.AddLogging(opt => opt.AddLog4Net("log4net.config")),非常感谢您的回答。 - fededim
    显示剩余5条评论

    1
    您描述的情况是 .NET Standard 旨在实现的。只有类库项目可以针对 .netstandard,任何此类库都与最新的 .NET Framework 应用程序以及 .NET Core 应用程序兼容。
    Microsoft.Extensions.DependencyInjection 和 Microsoft.Extensions.Configuration 中的 .NET Core 组件也与 .netstandard 兼容,这意味着您可以在库和应用程序中使用它们。
    因此,是的,您可以在 .NET Framework 中使用 .NET Core DI,在库场景中,只需坚持使用 .NET Standard API,它也将与所有 .NET 实现一起工作。我有一些非常大、非常复杂的 .netstandard20 库,我将其与针对两个框架的应用程序一起使用,我很少需要问自己一个给定的 API 是否兼容,因为现在覆盖范围非常好,但您可以在 此处 找到完整列表。

    是的,我理解 .NET Standard 的目标。但我对如何设置我的 .NET Framework 应用程序以使 IConfiguration 在 MyRepository 中可用并感兴趣。在 .NET Core 中,这是通过 WebHost.CreateDefaultBuilder 为我完成的... - fantastischIdee
    你是否熟悉组合根的DI概念?基本上,应用程序负责注册DI服务,然后在你的库中构造函数DI将自动工作。(如果你的库也需要注册DI服务,请向库添加服务注册扩展,并在应用程序启动期间从应用程序调用它。)如果你不熟悉,我可以打开另一个答案来演示。 - McGuireV10
    1
    @fantastischIdee 4.6不行。4.6.1可能,只需添加软件包。但是为控制台/非核心应用程序配置软件包则另当别论。 - Panagiotis Kanavos
    @McGuireV10 你不能随意添加任何DI库而不进行配置。ASP.NET Core提供了帮助程序来完成这项工作,这在.NET Core控制台应用程序中甚至都不可用。这不是关于DI的一般性问题。 - Panagiotis Kanavos
    1
    @PanagiotisKanavos 我有六个.NET Core实用控制台程序,每5分钟24/7启动一个非常复杂的DI依赖库,同样的库也适用于.NET Framework Azure网站。不太确定你想说什么,但是.NET Core DI很容易使用,无需ASP.NET Core。 - McGuireV10
    已删除4.6版本的.NET Framework,因为我对如何在与dotnet标准兼容的.NET Framework中执行此操作感兴趣。 - fantastischIdee

    网页内容由stack overflow 提供, 点击上面的
    可以查看英文原文,
    原文链接