当前位置: 首页 > 知识库问答 >
问题:

如何使用新的 DI 通过 IWebJobsStartup 将 ILogger 注入 Azure 函数?

乐正远
2023-03-14

我正在使用< code>Azure Function v2。下面是我使用构造函数注入的函数:

public sealed class FindAccountFunction
{
    private readonly IAccountWorkflow m_accountWorkflow;

    private readonly IMapper m_mapper;

    private readonly ILogger m_logger;

    public FindAccountFunction(ILogger logger, IMapper mapper, IAccountWorkflow accountWorkflow)
    {
        m_logger = logger;
        m_mapper = mapper;
        m_accountWorkflow = accountWorkflow;
    }

    [FunctionName("FindAccount")]
    public async Task<IActionResult> Run(
            [HttpTrigger(AuthorizationLevel.Function, Verbs.Get, Route = "v1/accounts/")] HttpRequest httpRequest, ILogger logger)
    {
        // Do stuff.
    }
}

我在从IWebJobsStartup派生的Startup类中声明了我要注入Azure函数的所有依赖项:

    public sealed class Startup : IWebJobsStartup
    {
        public void Configure(IWebJobsBuilder webJobsBuilder)
        {
            //  Registers the application settings' class.
            webJobsBuilder.Services.AddSingleton<IApplicationSettings, ApplicationSettings>();

            //  ** Registers the ILogger instance **
            //  ** ?? **

            //  Registers the IMapper instance for the contracts.
            var mapperConfiguration = new MapperConfiguration(cfg => cfg.AddProfile(new MyProfile()));

     webJobsBuilder.Services.AddSingleton(mapperConfiguration.CreateMapper());

            // Registers custom services.
            webJobsBuilder.Services.AddTransient<IStorageService, StorageService>();

            webJobsBuilder.Services.AddTransient<IAccountWorkflow, AccountWorkflow>();
        }
   }

Azure函数调用其他依赖于ILogger的注入服务,例如< code > iaccountworf :

public sealed class AccountWorkflow : IAccountWorkflow
{  
    public AccountWorkflow(ILogger logger, IStorageService storageService)
    {
        if(logger is null)
            throw new ArgumentNullException();
    }
}

问题在于DI找不到任何<code>ILogger

问题

如何在< code>IWebJobsStartup中设置< code>ILogger的注入?

共有3个答案

穆博简
2023-03-14

您应该从启动类中删除AddLogging方法的调用。默认记录器已经由azure函数主机设置。

[assembly: WebJobsStartup(typeof(StartUp))]
public class StartUp : IWebJobsStartup
{
    public void Configure(IWebJobsBuilder builder)
    {
        builder.Services.AddSingleton<AppSettings>();

        builder.Services.AddTransient<IMyService, MyService>();
    }
}

public MyFunction(IMyService service, ILogger<IMyService> logger)
{
    this.service = service;
    this.logger = logger;
}

自azure函数运行时2.0.12265以来,azure函数现在支持实例方法

经福
2023-03-14

我设法解决了这个问题:

注入我的类如下:MyClass.cs:

public class MyClass
{
    private readonly ILogger<MyClass> _logger;

    public MyClass(ILogger<MyClass> logger)
    {
        _logger = logger;
    }
}

Startup.cs:

[assembly: FunctionsStartup(typeof(Namespace.Startup))]   

namespace Namespace {    
public class Startup : FunctionsStartup 
{
    public override void Configure(IFunctionsHostBuilder builder) 
    {
        builder.Services.AddLogging(); 
    }
  }
}
刁英朗
2023-03-14

引用使用依赖注入。NET Azure函数

要注册服务,您可以创建一个configure方法,并将组件添加到IFunctionsHostBuilder实例中。Azure函数主机创建一个IFunctionsHostBuilder,并将其直接传递到您配置的方法中。

若要注册configure方法,必须添加一个assembly属性,该属性使用< code>FunctionsStartup属性指定configure方法的类型。

所以在这种情况下

[assembly: FunctionsStartup(typeof(MyNamespace.Startup))]    
namespace MyNamespace {
    public class Startup : FunctionsStartup {
        public override void Configure(IFunctionsHostBuilder builder) {
            //  ** Registers the ILogger instance **
            builder.Services.AddLogging();

            //  Registers the application settings' class.
            //...

            //...omitted for brevity    
        }
    }
}

我相信,既然您有权访问服务集合,那么您应该能够向其添加日志记录

public void Configure(IWebJobsBuilder webJobsBuilder) {       

    //  ** Registers the ILogger instance **
    webJobsBuilder.Services.AddLogging();

    //OR
    //webJobsBuilder.Services.AddLogging(builder => {
    //    //...
    //});

    //  Registers the application settings' class.
    //...

    //...removed for brevity
}

并且在函数的构造函数中有一个< code>ILoggerFactory。

//...

//Ctor
public FindAccountFunction(ILoggerFactory loggerFactory, IMapper mapper, IAccountWorkflow accountWorkflow) {
    m_logger = loggerFactory.CreateLogger<FindAccountFunction>();
    m_mapper = mapper;
    m_accountWorkflow = accountWorkflow;
}

//...
 类似资料:
  • 我有一个关于 azure 函数 v1 中的依赖注入的新问题。 实际情况: 我有一个azure函数V1,我想在其中引用我的业务服务,而无需重新发明轮子即可使用我的服务。我在Internet上搜索并找到了这篇来自Microsoft的有趣文章。 但是,它似乎只适用于azure函数v2(. net core),因为每当我尝试安装时,我总是收到以下错误: 检测到Microsoft.Azure.WebJobs

  • 我正在从升级我们的一个Azure功能应用程序。NET Core 3.1 to。NET 6。因此,我需要实现依赖注入。 我们的项目还利用了第三方API,我们有自己的项目来与该API进行通信。该项目有一个类对象,我们使用设置填充该对象,然后将其传递到我们的API注册调用中,以促进与此第三方API的通信。大致如下: 在我们的主web项目中,我们以前利用Autofac进行依赖注入,我们的注册看起来像这样:

  • 希望一些比我更了解Azure功能的人能提供帮助。 开箱即用,您可以使用应用程序设置中的APPINSIGHTS_INSTRUMENTATIONKEY设置登录到应用程序Insights...这将在基本级别记录函数请求,然后允许您执行等操作。 这只是被跟踪器或ilogger所掩盖。

  • 我喜欢在构造函数中传递运行时依赖项的主要原因是: 它使依赖关系成为必需的 它提供了设置实例变量的中心位置 将依赖项设置为实例变量,可以避免在类中从一个方法传递到另一个方法,或者将它分两次或多次传递给两个或更多个公共方法 这导致我在使用Guice时使用了很多辅助注射。与不使用DI相比,这会产生额外的代码,因此阅读以下内容:辅助注入到底有多有用? 似乎大多数人不会使用辅助注入在构造函数中传递运行时(派

  • 似乎Microsoft.NET.Sdk.Functions版本3.0.4与EntityFrameworkCore一起打破了DI。 在3.0.3中,我可以在DI中添加一个InMemoryDatabase,并在我的函数中使用它,但是升级到3.0.4中断声明: Microsoft.Extensions.DependencyInjection.Abstractions:尝试激活AzureFunction.