Blog – Scheduling using Quartz Actor.

Posted on Jun 18, 2021.

If you’re using Akka.NET and ever need to deal with scheduling at a set time, then you’d probably need to use the Quartz Actor that already provides the ability to schedule cron jobs as opposed to using the Context.System.Scheduler which sends the message repeatedly after every set interval with/without a given delay.

At the time of writing, there aren’t many examples of how to use the cron scheduling actor in my use case which involved the ability of cancelling the scheduler in the correct manner so I had to delve into the source code and come up with an implementation that isn’t too difficult to grasp.

So, in order to create the scheduler job, firstly you have to initialise the Quartz actor;

var quartzActor = Context.ActorOf(Props.Create(() => new QuartzActor()));

Then you’d have to build the trigger with the cron schedule, you can find the correct cron format from the official quartz scheduler.

var cronSchedule =  "0 0 14 * * ?"; // every day at 14:00
var quartzTrigger = TriggerBuilder.Create().WithCronSchedule(cronSchedule).Build();

Now instantiate the CreateJob passing down the receiver, message and quartzTrigger. Then send the message to the quartzActor we initialised earlier.

var createJobCommand = new CreateJob(this.Self, new ProcessCronScheduleMessage(), quartzTrigger);

Once the quartz actor receives the CreateJob message, it will send back JobCreated message with JobKey and TriggerKey properties, these are necessary for cancelling the correct job. If there is any issues with the trigger builder, cron schedule format or the receiver being null, then it will send back CreateJobFail message. At last, ProcessCronScheduleMessage will be sent to the current actor every day at 14:00 until the job is cancelled.

To be able to cancel the current job later, you have to handle JobCreated message and store the properties in the actor state so we can use them to cancel the current job when required.

Once you store the JobCreated message we can use the JobKey and TriggerKey properties and instantiate RemoveJob, and forward to the quartz actor;

var removeJob = new RemoveJob(currentJob.JobKey, currentJob.TriggerKey);

Consequently Quartz Actor will send back either JobRemoved for successful removal or RemoveJobFail for not being able to find the correct running scheduler job by the given JobKey and TriggerKey.