A partire dalla versione 3.1 di .NET Core è possibile definire all’interno di un applicazione Web ASP.NET Core servizi eseguiti in background. Una volta creato un servizio è necessario registrarlo all’interno di IServiceCollection dell’istanza per poterlo mandare in esecuzione.
La creazione di un servizio è piuttosto semplice: è necessrio creare una classe che eredita da IHostedService ed implementare i due metodi dell’interfaccia, StartAsync e StopAsync.
using Microsoft.Extensions.Hosting;
namespace SimpleServiceExample
{
public class MyService : IHostedService
{
public Task StartAsync(CancellationToken cancellationToken)
{
return Task.CompletedTask;
}
public Task StopAsync(CancellationToken cancellationToken)
{
return Task.CompletedTask;
}
}
}Una volta eseguita l’applicazione viene mandato in esecuzione il codice contenuto all’interno di StartAsync, ma è da tenere in considerazione che l’applicazione web verrà avviata soltanto al termine dell’esecuzione blocco StartAsync. Nel caso in cui all’interno di StartAsync sia contenuto del codice che dovrà essere eseguito all’infinito, l’applicazione Web non verrebbe mai eseguita.
Per ovviare a questo problema è necessario, all’interno di StartAsync, eseguire codice in un thread separato con una sintassi del tipo Task.Run(async () => … ). In questo modo l’applicazione web potrà essere eseguita correttamente.
using Microsoft.Extensions.Hosting;
namespace SimpleServiceExample
{
public class MyService: IHostedService
{
public Task StartAsync(CancellationToken cancellationToken)
{
Task.Run(async () =>
{
while (!cancellationToken.IsCancellationRequested)
{
await Task.Delay(new TimeSpan(0, 0, 20)); // 20 second delay
}
});
return Task.CompletedTask;
}
public Task StopAsync(CancellationToken cancellationToken)
{
return Task.CompletedTask;
}
}
}Per la registrazione del servizio in un applicazione all’interno di Startup.cs nel metodo ConfigureServices aggiungere alla service collections il servizio che dovrà essere eseguito:
public void ConfigureServices(IServiceCollection services)
{
// Add dependency injection.
services.AddHostedService<MyService>();
...
}Nel caso in cui l’applicazione sia sviluppata in .NET Core 6 è possibile registrare il tutto all’interno della Program.cs:
builder.Services.AddHostedService<MyService>();