简体   繁体   中英

ASP.Net core Azure Webjob (SDK 3.0.10) DI not resolving

I'm creating a .net core Azure webjob triggered by a Q-message on Azure Q-storage.

When the webjob is triggered I get the following error.

System.InvalidOperationException: 'Unable to resolve service for type 'xxx.SERVICE.Cloud.ICloudStorageService' while attempting to activate 'xxx.Functions'.'

Any suggestions ?

In program.cs / main I wired up DI :

IServiceCollection services = new ServiceCollection();
//...
services.AddTransient<ICloudStorageService, AzureBlobStorageService>();

And the 'hart' of the webjob

public class Functions
{
    private readonly ICloudStorageService _storageService;

    public Functions(ICloudStorageService cloudStorageService)
    {
        _storageService = cloudStorageService;
    }

    public async Task ProcessQueueMessage(
        [QueueTrigger(AzureQueues.NoShowUploads)] BatchJob job
        , ILogger logger
        )
    {
        //...
    }
}

The AzureBlobStorageService class implements the ICloudStorageService interface

public class AzureBlobStorageService : ICloudStorageService
{
    //...
}

UPDATE:

class Program
    {
        static void Main(string[] args)
        {
            var environment = Environment.GetEnvironmentVariable("ASPNETCORE_ENVIRONMENT");

            var configuration = new ConfigurationBuilder()
                .SetBasePath(Directory.GetCurrentDirectory())
                .AddJsonFile("appsettings.json", optional: false, reloadOnChange: true)
                .AddJsonFile($"appsettings.{environment}.json", optional: true, reloadOnChange: true)
                .AddEnvironmentVariables()
                .Build();

            IServiceCollection services = new ServiceCollection();

            services.Configure<SendGridClientOptions>(options =>
            {
                                services.Configure<AzureQueueOptions>(options =>
            {
                configuration.GetSection("AzureQueueOptions").Bind(options);
                options.StorageConnectionString = configuration.GetConnectionString("Storage");
            });
            services.Configure<AzureBlobStorageOptions>(options =>
            {
                configuration.GetSection("AzureBlobStorageOptions").Bind(options);
                options.StorageConnectionString = configuration.GetConnectionString("Storage");
            });

            services.AddTransient<Functions, Functions>();
            services.AddTransient<ICloudStorageService, AzureBlobStorageService>();
            services.AddTransient<WebJobEntryPoint>();

            services.BuildServiceProvider().GetService<WebJobEntryPoint>().Run();

        }
    }

The webentrypoint class

  public class WebJobEntryPoint
    {
        private readonly MailOptions _mailOptions;
        private readonly SendGridClientOptions _sendGridClientOptions;
        private readonly AzureBlobStorageOptions _azureBlobStorageOptions;
        private readonly AzureQueueOptions _azureQueueOptions;

        public WebJobEntryPoint(
            IOptionsMonitor<SendGridClientOptions> sendGridClientOptionsMonitor,
            IOptionsMonitor<MailOptions> mailOptionsMonitor,
            IOptionsMonitor<AzureBlobStorageOptions> azureBlobStorageOptionsMonitor,
            IOptionsMonitor<AzureQueueOptions> azureQueueOptionsMonitor)
        {
            _sendGridClientOptions = sendGridClientOptionsMonitor.CurrentValue;
            _mailOptions = mailOptionsMonitor.CurrentValue;
            _azureBlobStorageOptions = azureBlobStorageOptionsMonitor.CurrentValue;
            _azureQueueOptions = azureQueueOptionsMonitor.CurrentValue;
        }

        public void Run()
        {
            var builder = new HostBuilder()
                .ConfigureWebJobs(webJobConfiguration =>
                {
                    webJobConfiguration.AddAzureStorageCoreServices();
                    webJobConfiguration.AddAzureStorage(c => c.BatchSize = _azureQueueOptions.BatchSize);
                })
                .ConfigureLogging((context, b) =>
                {
                    b.AddConsole();
                });

            var host = builder.Build();
            using (host)
            {
                host.Run();
            }
        }
    }

With your current design the host is unaware of the service registrations that were done in main.

Here is a simplification of the current setup based on what was provided in the original example:

class Program {
    static void Main(string[] args) {
        var environment = Environment.GetEnvironmentVariable("ASPNETCORE_ENVIRONMENT");

        var configuration = new ConfigurationBuilder()
            .SetBasePath(Directory.GetCurrentDirectory())
            .AddJsonFile("appsettings.json", optional: false, reloadOnChange: true)
            .AddJsonFile($"appsettings.{environment}.json", optional: true, reloadOnChange: true)
            .AddEnvironmentVariables()
            .Build();

        var azureQueueOptions = configuration.GetSection("AzureQueueOptions").Get<AzureQueueOptions>();
        azureQueueOptions.StorageConnectionString = configuration.GetConnectionString("Storage");

        var builder = new HostBuilder()
            .ConfigureWebJobs(webJobConfiguration => {
                webJobConfiguration.AddAzureStorageCoreServices();
                webJobConfiguration.AddAzureStorage(c => c.BatchSize = azureQueueOptions.BatchSize);
            })
            .ConfigureServices(services => {
                services.AddTransient<Functions>();
                services.AddTransient<ICloudStorageService, AzureBlobStorageService>();
            })
            .ConfigureLogging((context, config) => {
                config.AddConsole();
            });

        var host = builder.Build();

        host.Run();
    }
}

That or create an actual Startup and have the builder use it:

var builder = new HostBuilder()
    .UseStartup<Startup>()
    //...omitted for brevity

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM