public async Task <IActionResult> EditRecurringReminder(ulong guildId, EditRecurringReminderMessageViewModel vm) { if (!ModelState.IsValid) { return(View(vm)); } if (vm.Id == default(long)) { var newReminder = new RecurringReminderMessage { ChannelId = vm.ChannelId, Enabled = vm.Enabled, Message = vm.Message, CronExpression = vm.CronExpression, GuildId = guildId }; await _reminderService.Create(newReminder); return(RedirectToAction("RemembotSettings", "Settings")); } var reminder = await _reminderService.Find(vm.Id); reminder.ChannelId = vm.ChannelId; reminder.Enabled = vm.Enabled; reminder.Message = vm.Message; reminder.CronExpression = vm.CronExpression; await _reminderService.Update(reminder); return(RedirectToAction("RemembotSettings", "Settings")); }
public async Task Caching_Entity_Service_Expression() { using (var context = GetInMemoryContext()) { var cache = new FluentDictionaryCache(); var entityService = new CachedEntityService <RecurringReminderMessage>(context, new EntityChangedDispatcher <RecurringReminderMessage>(), cache); var reminder = new RecurringReminderMessage { Message = "Test Message", Id = 1, Fault = RecurringReminderMessage.FaultType.None, Enabled = true, GuildId = 100, ChannelId = 1, CronExpression = "* * * * *" }; await entityService.Create(reminder); Expression <Func <RecurringReminderMessage, bool> > predicate = r => r.Id == reminder.Id; var pkReminder = (await entityService .Get(predicate)) .FirstOrDefault(); var key = entityService.GetCacheKey(predicate, null); var cacheEntry = cache.WithKey(key) .Get <List <RecurringReminderMessage> >(); Assert.True(cacheEntry.Value != null); Assert.True(cacheEntry.Value[0].Id == pkReminder.Id); Assert.True(cacheEntry.Value[0].Message == "Test Message"); pkReminder.Message = "Test Message 2"; await entityService.Update(pkReminder); cacheEntry = cache.WithKey(key) .Get <List <RecurringReminderMessage> >(); Assert.True(cacheEntry.Value == null); var lastCheck = (await entityService .Get(predicate)) .FirstOrDefault(); Assert.True(lastCheck?.Message == "Test Message 2"); } }
/// <summary> /// Gets a long status message based on the <see cref="RecurringReminderMessage.FaultType"/> of the <see cref="RecurringReminderMessage"/>. /// </summary> /// <param name="reminderMessage"></param> /// <returns></returns> public static string GetFaultLongMessage(this RecurringReminderMessage reminderMessage) { switch (reminderMessage.Fault) { case RecurringReminderMessage.FaultType.InvalidChannel: return("The channel for this reminder no longer exists. Please update to an existing channel."); case RecurringReminderMessage.FaultType.InvalidCron: return("The Cron expression that specifies the recurrence for this reminder is not valid."); default: return(null); } }
/// <summary> /// Gets a short status message based on the <see cref="RecurringReminderMessage.FaultType"/> of the <see cref="RecurringReminderMessage"/>. /// </summary> /// <param name="reminderMessage"></param> /// <returns></returns> public static string GetFaultShortMessage(this RecurringReminderMessage reminderMessage) { switch (reminderMessage.Fault) { case RecurringReminderMessage.FaultType.InvalidChannel: return("Invalid Channel"); case RecurringReminderMessage.FaultType.InvalidCron: return("Invalid Cron Expression"); default: return(null); } }
static (bool HasFault, string Status) GetEnabledStatus(RecurringReminderMessage reminderMessage) { if (reminderMessage.Fault == RecurringReminderMessage.FaultType.None) { if (reminderMessage.Enabled) { return(false, "Enabled"); } return(false, "Disabled"); } else { return(true, reminderMessage.GetFaultShortMessage()); } }
public async Task Caching_Entity_Service_PK() { using (var context = GetInMemoryContext()) { var cache = new FluentDictionaryCache(); var entityService = new CachedEntityService <RecurringReminderMessage>(context, new EntityChangedDispatcher <RecurringReminderMessage>(), cache); var reminder = new RecurringReminderMessage { Message = "Test Message", Id = 1, Fault = RecurringReminderMessage.FaultType.None, Enabled = true, GuildId = 100, ChannelId = 1, CronExpression = "* * * * *" }; await entityService.Create(reminder); var pkReminder = await entityService.Find(reminder.Id); var key = CachedEntityService <RecurringReminderMessage> .GetCacheKey(new object[] { reminder.Id }); var cacheEntry = cache.WithKey(key).Get <RecurringReminderMessage>(); Assert.True(cacheEntry.Value != null); Assert.True(cacheEntry.Value.Id == pkReminder.Id); Assert.True(cacheEntry.Value.Message == "Test Message"); pkReminder.Message = "Test Message 2"; await entityService.Update(pkReminder); cacheEntry = cache.WithKey(key).Get <RecurringReminderMessage>(); Assert.True(cacheEntry.Value == null); var lastCheck = await entityService.Find(reminder.Id); Assert.True(lastCheck.Message == "Test Message 2"); } }
/// <summary> /// Helper method to start or update the recurring job. /// </summary> /// <param name="reminder"></param> private void StartOrUpdateJob(RecurringReminderMessage reminder) { using (var scope = _scopeFactory.CreateScope()) { var reminderJob = scope.ServiceProvider.GetRequiredService <RecurringReminderMessageJob>(); try { _jobService.ScheduleRecurringJob(() => reminderJob.Run(reminder), reminder.CronExpression, reminder.GetJobId()); } catch (ArgumentException) { var reminderService = scope.ServiceProvider.GetRequiredService <IEntityService <RecurringReminderMessage> >(); reminder.Fault = RecurringReminderMessage.FaultType.InvalidCron; reminderService.Update(reminder); } } }
/// <summary> /// Background job execution for reminder messages for the Remembot module. /// ** NOTE - DO NOT make changes to this signature. If changes are needed, make a new method to use. /// Changing this file's signature will cause errors with the existing job queues. /// </summary> /// <param name="reminder"></param> /// <returns></returns> public async Task Run(RecurringReminderMessage reminder) { using (var scope = _scopeFactory.CreateScope()) { var channel = _bot.Client.GetChannel(reminder.ChannelId); if (channel is null) { _logger.LogWarning("Attempt was made to send reminder to channel {ChannelId} that doesn't exist. Removing reminder and stopping job for guild {GuildId}.", reminder.ChannelId, reminder.GuildId); await DisableJob(); return; } if (channel is SocketTextChannel stc) { await stc.SendMessageAsync(reminder.Message); } else { _logger.LogInformation("Attempt was made to send reminder to a non-text channel {ChannelId}. Disabling reminder for guild {GuildId}.", reminder.ChannelId, reminder.GuildId); await DisableJob(); } async Task DisableJob() { var entityService = scope.ServiceProvider.GetRequiredService <IEntityService <RecurringReminderMessage> >(); var trackedEntity = await entityService.Find(reminder.Id); trackedEntity.Enabled = false; trackedEntity.Fault = RecurringReminderMessage.FaultType.InvalidChannel; await entityService.Update(trackedEntity); _jobService.CancelRecurringJob(reminder.GetJobId()); } } }
/// <summary> /// Helper method to stop the recurring job if it exists. /// </summary> /// <param name="reminder"></param> private void StopJobIfExists(RecurringReminderMessage reminder) { _jobService.CancelRecurringJob(reminder.GetJobId()); }