Learn how to use the new template available in ASP.NET Core 3.0 to build a worker service. Credit: Thinkstock ASP.NET Core 3.0 Preview 3 adds support for creating worker services, which are background services like Windows services and Linux daemons. There is a new template for creating a worker service in Visual Studio as well. To work with worker services in Visual Studio, you should have the beta versions (Preview Version 3 or later) of ASP.NET Core 3.0 and .NET Core 3.0 runtimes installed on your system. Create a new worker service application First, let’s create an ASP.NET Core project in Visual Studio 2019. Follow these steps o create a new ASP.NET Core project in Visual Studio: Launch the Visual Studio IDE. Click Create New Project. In the Create New Project window, select ASP.NET Core Web Application from the list of templates. Click Next. In the Configure Your New Project window that appears, specify the name and location for the new project. Click Create. The window Create New ASP.NET Core Web Application appears. Select .NET Core as the runtime and ASP.NET Core 3.0 (or later) from the dropdown menu at the top. Select Worker Service as the project template to create a new worker service application Ensure that the check box Enable Docker Support is unchecked, because you won’t be using this feature here. Ensure that Authentication is set as No Authentication, because you won’t be using authentication either. Click Create. This creates a new worker service application in Visual Studio. IDG A new worker service in ASP.NET Core. The Program class The default implementation of the worker service contains two classes: the Program and Worker classes. The Program class is like the one you have in web applications, with the difference that instead of a Startup class, you have a Worker class. Here’s what the Program class looks like. Note how the AddHostedService method is used. public class Program { public static void Main(string[] args) { CreateHostBuilder(args).Build().Run(); } public static IHostBuilder CreateHostBuilder(string[] args) => Host.CreateDefaultBuilder(args) .ConfigureServices((hostContext, services) => { services.AddHostedService<Worker>(); }); } The Worker class The Worker class provides support for dependency injection. The Worker service class extends the BackgroundService class in the Microsost.Extensions.Hosting.Abstractions package. The BackroundService abstract class extends the IHostedService interface and contains the declarations of the StartAsync, StopAsync, and ExecuteAsync methods. public abstract class BackgroundService : IHostedService, IDisposable { public virtual void Dispose(); public virtual Task StartAsync(CancellationToken cancellationToken); public virtual Task StopAsync(CancellationToken cancellationToken); protected abstract Task ExecuteAsync(CancellationToken stoppingToken); } The constructor of the Worker class accepts an instance of type ILogger as an argument. The following code snippet shows the default implementation of the Worker class: public class Worker : BackgroundService { private readonly ILogger<Worker> _logger; public Worker(ILogger<Worker> logger) { _logger = logger; } protected override async Task ExecuteAsync (CancellationToken stoppingToken) { while (!stoppingToken.IsCancellationRequested) { _logger.LogInformation ("Worker running at: {time}", DateTimeOffset.Now); await Task.Delay(1000, stoppingToken); } } } IDG You can run the worker service as an .exe file from Visual Studio or even as a Windows service. To run worker service as a Windows service, you should add the Microsoft.Extensions.Hosting.WindowsServices NuGet package to your project. You can run the worker service much the same way you run applications in Visual Studio: by pressing F5 or Ctrl+F5. When you run the minimalistic worker service, the figure shows what the output looks like. Extend the default worker service You can override the methods of the BackgroundService abstract class to add more functionality to the worker service. You can override the ExecuteAsync method to write the code for performing any long running tasks. The following code shows the enhanced version of the Worker class; the StartAsync, ExecuteAsync, and StopAsync methods have been implemented. public class Worker : BackgroundService { private readonly ILogger<Worker> _logger; public Worker(ILogger<Worker> logger) { _logger = logger; } public override Task StartAsync(CancellationToken cancellationToken) { _logger.LogInformation ("Worker service has been started at: {0}", DateTime.Now); return base.StartAsync(cancellationToken); } protected override Task ExecuteAsync(CancellationToken stoppingToken) { _logger.LogInformation ("Worker service running at: {0}", DateTime.Now); return Task.CompletedTask; } public override Task StopAsync(CancellationToken cancellationToken) { _logger.LogInformation ("Worker service has been stopped at: {0}", DateTime.Now); return base.StopAsync(cancellationToken); } public override void Dispose() { _logger.LogInformation ("Worker service has been disposed at: {0}", DateTime.Now); base.Dispose(); } } Log data in the worker service To use logging in your worker service, you should add a reference to the Microsoft.Extensions.Logging assembly. The default logger in a worker service is ConsoleLogger. You can also use EventLog as the log target in your worker service. To use EventLog as the log target, add the Microsoft.Extensions.Logging.EventLog NuGet package to your project. The following code snippet illustrates how you can configure the logging output to event log in the CreateHostBuilder method of the Program class: public static IHostBuilder CreateHostBuilder(string[] args) => Host.CreateDefaultBuilder(args) .ConfigureLogging(logFactory => logFactory.AddEventLog()) .ConfigureServices(services => { services.AddHostedService<Worker>(); }); Related content feature 14 great preprocessors for developers who love to code Sometimes it seems like the rules of programming are designed to make coding a chore. Here are 14 ways preprocessors can help make software development fun again. By Peter Wayner Nov 18, 2024 10 mins Development Tools Software Development feature Designing the APIs that accidentally power businesses Well-designed APIs, even those often-neglected internal APIs, make developers more productive and businesses more agile. By Jean Yang Nov 18, 2024 6 mins APIs Software Development news Spin 3.0 supports polyglot development using Wasm components Fermyon’s open source framework for building server-side WebAssembly apps allows developers to compose apps from components created with different languages. By Paul Krill Nov 18, 2024 2 mins Microservices Serverless Computing Development Libraries and Frameworks news Go language evolving for future hardware, AI workloads The Go team is working to adapt Go to large multicore systems, the latest hardware instructions, and the needs of developers of large-scale AI systems. By Paul Krill Nov 15, 2024 3 mins Google Go Generative AI Programming Languages Resources Videos