This is my Quartz configuration:
<quartz>
<add key="quartz.scheduler.instanceName" value="EmailScheduler" />
<!-- Configure Thread Pool -->
<add key="quartz.threadPool.type" value="Quartz.Simpl.SimpleThreadPool, Quartz" />
<add key="quartz.threadPool.threadCount" value="10" />
<add key="quartz.threadPool.threadPriority" value="Normal" />
<!-- Configure Job Store -->
<add key="quartz.jobStore.misfireThreshold" value="60000" />
<add key="quartz.jobStore.type" value="Quartz.Impl.AdoJobStore.JobStoreTX, Quartz" />
<add key="quartz.jobStore.driverDelegateType" value="Quartz.Impl.AdoJobStore.StdAdoDelegate, Quartz" />
<add key="quartz.jobStore.dataSource" value="default" />
<add key="quartz.jobStore.lockHandler.type" value="Quartz.Impl.AdoJobStore.UpdateLockRowSemaphore, Quartz" />
<add key="quartz.dataSource.default.provider" value="SqlServer-20" />
<add key="quartz.dataSource.default.connectionString" value="data source= ......" />
<add key="quartz.jobStore.tablePrefix" value="QRTZ_" />
</quartz>
here is my IInterruptableJob
:
public class JobC : Quartz.IInterruptableJob
{
public void Interrupt()
{
Console.WriteLine("Job Interrupt() called at " + DateTime.Now);
}
public void Execute(IJobExecutionContext context)
{
// what code I should write here to detect misfires???
Console.WriteLine("FireTime at " + context.FireTimeUtc.Value + " PreviousFireTime at:" + (context.PreviousFireTimeUtc.HasValue ? context.PreviousFireTimeUtc.Value.ToString() : "NULL"));
}
}
Here is my job and trigger:
var job = JobBuilder.Create<JobC>().WithIdentity(new JobKey("JobC")).RequestRecovery(true).Build();
var trigger = TriggerBuilder.Create()
.WithSimpleSchedule(x => x
.RepeatForever()
.WithIntervalInSeconds(2)
// I'm ignoring misfires here, but seems it doesn't work!
.WithMisfireHandlingInstructionIgnoreMisfires())
.StartNow()
.Build();
var scheduler = new Quartz.Impl.StdSchedulerFactory().GetScheduler();
scheduler.Start();
scheduler.ScheduleJob(job, trigger);
After I call scheduler.PauseAll()
all jobs pause and after calling scheduler.ResumeAll()
all missed fires, get fired! but I want to ignore them and just continue from now on.
Thanks in advance.
Are you sure your triggers meet the defined misfire threshold? If you have threshold of 60 seconds as you configuration states, every trigger that is not considered misfired but have met their scheduled fire time will be fired as soon as possible after resume.
So you should see the ignore behavior if your pause lasts as least threshold value, which is 60 seconds in this case.
It may seems stupid, but I made following extension method to detect misfires inside Execute
method:
public static bool IsMissedFire(this IJobExecutionContext context, int offsetMilliseconds)
{
if (!context.ScheduledFireTimeUtc.HasValue)
return false;
if (!context.FireTimeUtc.HasValue)
return false;
var scheduledFireTimeUtc = context.ScheduledFireTimeUtc.Value;
var fireTimeUtc = context.FireTimeUtc.Value;
return fireTimeUtc.Subtract(scheduledFireTimeUtc).TotalMilliseconds > offsetMilliseconds;
}
Usage is simple:
public void Execute(IJobExecutionContext context)
{
if (context.IsMissedFire(1000))
Console.WriteLine("Missfire");
else
Console.WriteLine("Fire");
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With