Compare commits

...

6 Commits

Author SHA1 Message Date
khwezi e97fd6cd3f Merge pull request 'Added debug logging' (#24) from emailjobs into master
Reviewed-on: #24
2026-05-15 23:09:21 +02:00
Khwezi Mngoma 7f4246ac63 Added debug logging
continuous-integration/drone/pr Build is passing
2026-05-15 23:08:15 +02:00
khwezi 184c7c252a Merge pull request 'Set misfireThreshold to 2min and eased Cluster node checkin limit' (#23) from emailjobs into master
Reviewed-on: #23
2026-05-15 22:29:08 +02:00
Khwezi Mngoma dfc62c8fe1 Set misfireThreshold to 2min and eased Cluster node checkin limit
continuous-integration/drone/pr Build is passing
2026-05-15 22:28:18 +02:00
khwezi bfe8c458d6 Merge pull request 'Optimised quartz' (#22) from emailjobs into master
Reviewed-on: #22
2026-05-15 09:52:06 +02:00
Khwezi Mngoma 0f91f102e5 Optimised quartz
continuous-integration/drone/pr Build is passing
2026-05-15 09:51:26 +02:00
3 changed files with 15 additions and 5 deletions
+7 -3
View File
@@ -34,7 +34,7 @@ public static class Quartz
storage.UseClustering(cluster => storage.UseClustering(cluster =>
{ {
cluster.CheckinInterval = TimeSpan.FromSeconds(30); cluster.CheckinInterval = TimeSpan.FromSeconds(30);
cluster.CheckinMisfireThreshold = TimeSpan.FromSeconds(2); cluster.CheckinMisfireThreshold = TimeSpan.FromSeconds(90);
}); });
}); });
}); });
@@ -48,6 +48,8 @@ public static class Quartz
services.ConfigureCommon(); services.ConfigureCommon();
services.AddQuartzHostedService(options => options.WaitForJobsToComplete = true);
services.AddQuartz(config => services.AddQuartz(config =>
{ {
config.SchedulerName = schedulerName; config.SchedulerName = schedulerName;
@@ -60,6 +62,8 @@ public static class Quartz
config.UseDefaultThreadPool(options => options.MaxConcurrency = 1); config.UseDefaultThreadPool(options => options.MaxConcurrency = 1);
config.UseTimeZoneConverter(); config.UseTimeZoneConverter();
config.SetProperty("quartz.jobStore.misfireThreshold", TimeSpan.FromMinutes(2).TotalMilliseconds.ToString());
config.UsePersistentStore(storage => config.UsePersistentStore(storage =>
{ {
storage.PerformSchemaValidation = false; storage.PerformSchemaValidation = false;
@@ -72,7 +76,7 @@ public static class Quartz
storage.UseClustering(cluster => storage.UseClustering(cluster =>
{ {
cluster.CheckinInterval = TimeSpan.FromSeconds(30); cluster.CheckinInterval = TimeSpan.FromSeconds(30);
cluster.CheckinMisfireThreshold = TimeSpan.FromSeconds(2); cluster.CheckinMisfireThreshold = TimeSpan.FromSeconds(90);
}); });
}); });
}); });
@@ -86,13 +90,13 @@ public static class Quartz
{ {
options.Scheduling.IgnoreDuplicates = true; options.Scheduling.IgnoreDuplicates = true;
options.Scheduling.OverWriteExistingData = true; options.Scheduling.OverWriteExistingData = true;
options["quartz.plugin.jobHistory.type"] = "Quartz.Plugin.History.LoggingJobHistoryPlugin, Quartz.Plugins"; options["quartz.plugin.jobHistory.type"] = "Quartz.Plugin.History.LoggingJobHistoryPlugin, Quartz.Plugins";
options["quartz.plugin.triggerHistory.type"] = "Quartz.Plugin.History.LoggingTriggerHistoryPlugin, Quartz.Plugins"; options["quartz.plugin.triggerHistory.type"] = "Quartz.Plugin.History.LoggingTriggerHistoryPlugin, Quartz.Plugins";
}); });
services.AddTransient<RetryJobListener>(); services.AddTransient<RetryJobListener>();
services.AddTransient<IJobOrchestrator, JobOrchestrator>(); services.AddTransient<IJobOrchestrator, JobOrchestrator>();
services.AddQuartzHostedService(options => options.WaitForJobsToComplete = true);
return services; return services;
} }
@@ -52,7 +52,7 @@ public class JobOrchestrator(ISchedulerFactory schedulerFactory) : IJobOrchestra
.WithIdentity(triggerKey) .WithIdentity(triggerKey)
.WithDescription($"Scheduled via Main Job at {now:g} UTC") .WithDescription($"Scheduled via Main Job at {now:g} UTC")
.WithCronSchedule(cronExpression, cron => cron .WithCronSchedule(cronExpression, cron => cron
.WithMisfireHandlingInstructionFireAndProceed()) .WithMisfireHandlingInstructionIgnoreMisfires())
.StartAt(now) .StartAt(now)
.Build(); .Build();
@@ -13,6 +13,8 @@ public class ProcessEmailNotificationsEventHandler(IDbContextFactory<ShopDbConte
{ {
try try
{ {
logger.LogInformation("Started");
using var context = await contextFactory.CreateDbContextAsync(cancellationToken); using var context = await contextFactory.CreateDbContextAsync(cancellationToken);
var notifications = await context.Notifications var notifications = await context.Notifications
@@ -52,6 +54,10 @@ public class ProcessEmailNotificationsEventHandler(IDbContextFactory<ShopDbConte
{ {
logger.LogError(ex, ex.Message); logger.LogError(ex, ex.Message);
} }
finally
{
logger.LogInformation("Finished");
}
} }
private async Task<Result> SendEmailAsync(Notification notification, EmailService service, CancellationToken cancellationToken = default) private async Task<Result> SendEmailAsync(Notification notification, EmailService service, CancellationToken cancellationToken = default)