I need to add multiple instances of the same class to DI like this
program.cs
using PruebaWorkerService1;
var builder = Host.CreateApplicationBuilder(args);
builder.Services.AddHostedService<Worker>( x => new Worker("worker1"));
builder.Services.AddHostedService<Worker>(x => new Worker("worker2"));
builder.Services.AddHostedService<Worker>(x => new Worker("worker3"));
var host = builder.Build();
host.Run();
Worker.cs
namespace PruebaWorkerService1;
public class Worker : BackgroundService{
private readonly string _msg;
public Worker(string msg){
this._msg = msg;
}
protected override async Task ExecuteAsync(CancellationToken stoppingToken){
while (!stoppingToken. IsCancellationRequested){
Console.WriteLine(("Worker running at: {time} {msg}", DateTimeOffset.Now, _msg));
await Task.Delay(1000, stoppingToken);
}
}
Result:
Result Only Worker1 was instanceated. I thought with diferent arguments (msg) it would create different instances. What do I need to do to create more than one instance of a service?
AddHostedService
will add only the first service for type, the subsequent registrations will be ignored (internally it uses TryAddEnumerable
). You have following options:
Add a descendant type per the setting and register it, not Worker
Use a hacky approach with manual registration via descriptor:
builder.Services.Add(ServiceDescriptor.Singleton<IHostedService>(_ => new Worker("worker1")));
builder.Services.Add(ServiceDescriptor.Singleton<IHostedService>(_ => new Worker("worker2")));
builder.Services.Add(ServiceDescriptor.Singleton<IHostedService>(_ => new Worker("worker3")));
Handle the settings in the worker, for example create a thread/task per the setting and run them in ExecuteAsync
(for example check out this answer)