Originally posted on https://samueleresca.net
Sometimes it is necessary to schedule and create long-running methods for our .NET Core applications. Manage scheduled and long-running methods is complicated. For example, unhandled exception in a thread not associated with a request, will take down the process. Secondly, if you run your site on multiple instances can cause to run the same task at the same time. Finally, application domain can go down and take down your background task with it. In order to improve safety and stability of our services, it is better to avoid to manage them within the application, because they can cause your services to be un-responsible. To remove waits you should place your long-running method invocation into background task. However, there are different ways to scheduling background tasks in the cloud world:
- Azure WebJobs: They have built-in triggers for a number of different events inside of Azure, for example: storage queues, blobs, service bus queues, topics and schedule triggers. This means that it is possible, to set up a WebJob that monitors a blob storage account for new items;
- Azure Functions: they take a bunch f concepts from WebJobs and improve them in some interesting ways. First, Functions enable a whole raft of new trigger types. HTTP triggers also unlock the ability to build very small webhooks that can be deployed at a very low cost;
What about on-premise solutions?
Let's talk about Hangfire. An easy way to perform background processing in .NET and .NET Core applications. You can safely restart your application and use Hangfire with ASP.NET without worrying about application pool recycles.
Background tasks using Hangfire
The following example uses Hangfire to trigger and manage background tasks on ASP.NET Core application. In order to use Hangfire, you should install the related package using following command: PM> Install-Package Hangfire
How it works?
Hangfire takes the responsibility to process your background tasks. In order to manage our tasks, it uses a persistent storage: SQL Server, Redis, PostgreSQL, MongoDB. Here is an overview of hangfire workflow: [caption id="attachment_3179" align="aligncenter" width="542"] http://docs.hangfire.io/en/latest/
This distributed way of handle tasks, give us the ability to throw unhandled exceptions or terminate your application, background jobs will be re-tried automatically.
Configure hangfire
Let's see how to configure hangfire. ASP.NET Core uses the Startup.cs
file to initialize services and external dependencies. The Startup.cs
file contains following methods:
-
ConfigureServices
is where dependencies are registered with a container; -
Configure
is where the middleware pipeline is defined. It controls how your application responds to requests;
In order to configure hangfire we should add the following code:
The line 20
registers the dependencies of hangfire by using SQL server. Line 31
initialises the dashboard middleware, and Line 32
initializes the hangfire server.
Adding new tasks
Finally, we can proceed by adding a new task to our application. There are different ways to schedule our tasks:
Fire-and-forget jobs: are executed only once and almost immediately after creation.
Delayed jobs: are executed only once too, but not immediately, after a certain time interval.
Recurring jobs: fire many times on the specified CRON schedule.
Continuations: are executed when its parent job has been finished.
Monitoring tasks
Hangfire provides an easy way to check and monitor our tasks. You can call the following route:
https://app_hostname/hangfire
In order to access to the hangfire dashboard.
Final thought
In conclusion, if you think you can write a background tasks in ASP.NET Core yourself, you are probably wrong. There are a lot of conditions and unexpected behavior you should consider. Tools like hangfire can help us to delegate our tasks to a 3rd party system. Here are some useful references about hangfire:
How to run Background Tasks in ASP.NET - Scott Hanselman
Cheers :)
Cover photo: Chihuly Garden and Glass @ Seattle Center
Top comments (5)
Hi Samuele. First of all nice article. I've some questions about Hangfire too. Let's start with an introduction.
For instance we're hosting our application in Azure cloud as App Service. We've set up sutoscalling for our application, so our application will be running on 1-3 instances depending of incomming traffic. And now time for questions :)
I'll be grateful for your response.
Cheers.
Hi Rafal,
thank you for the feedback and for your time:)
Hangfire can manage autoscaling and different instances. At the same time, it is possible run multiple instances inside a process, machine, or several machines.
In detail, Hangfire uses a distributed locks to perform the coordination logic. It also uses a separate data source, to store Tasks informations.
The availability settings of the data source are delegate to the data source, for example, you may use a replica set of mongodb to improve datasource availability.
Let me know,
Sem
Thank you for your answer. They're very useful. I think I'll try to use Hangfire in the nearest future.
Is this something similar to Quartz?
Hi Pawel,
I dont know very well Quartz. I think that the difference is that Quartz does not use a data source, and also does not provide a out-of-box dashboard for monitoring tasks
Best,
Samuele