Bugfix: Fix crash if the next reminder is deleted before it can be sent.

Also enable some debug logging, just in case it acts up again.
This commit is contained in:
Starbeamrainbowlabs 2019-02-08 11:30:16 +00:00
parent b5deb649dc
commit a4d996fb3d
Signed by: sbrl
GPG key ID: 1BE5172E637709C2
2 changed files with 18 additions and 18 deletions

View file

@ -313,8 +313,9 @@ namespace RhinoReminds
private void interruptReminderWatcher() private void interruptReminderWatcher()
{ {
reminderWatcherReset?.Cancel(); CancellationTokenSource oldToken = reminderWatcherReset;
reminderWatcherReset = new CancellationTokenSource(); reminderWatcherReset = new CancellationTokenSource();
oldToken?.Cancel();
} }
private async Task watchForReminders() private async Task watchForReminders()
@ -324,12 +325,12 @@ namespace RhinoReminds
// ----- Events ----- // ----- Events -----
// This will run on the firing thread, not on this thread // This will run on the firing thread, not on this thread
reminderList.OnReminderListUpdate += (object sender, Reminder newReminder) => { reminderList.OnReminderListUpdate += (object sender, ReminderListUpdateEventArgs eventArgs) => {
Reminder newNextReminder = reminderList.GetNextReminder(); Reminder newNextReminder = reminderList.GetNextReminder();
//Console.WriteLine("[Rhino/Reminderd/Canceller] Reminder added - comparing."); Console.WriteLine("[Rhino/Reminderd/Canceller] Reminder added - comparing.");
//Console.WriteLine($"[Rhino/Reminderd/Canceller] {nextReminder} / {newNextReminder}"); Console.WriteLine($"[Rhino/Reminderd/Canceller] {nextReminder} / {newNextReminder}");
if (nextReminder != newNextReminder) { if (nextReminder != newNextReminder) {
//Console.WriteLine($"[Rhino/Reminderd/Canceller] Cancelling"); Console.WriteLine($"[Rhino/Reminderd/Canceller] Cancelling");
nextReminder = newNextReminder; nextReminder = newNextReminder;
interruptReminderWatcher(); interruptReminderWatcher();
} }
@ -345,35 +346,34 @@ namespace RhinoReminds
nextWaitingTime = nextReminder.Time - DateTime.Now; nextWaitingTime = nextReminder.Time - DateTime.Now;
if (DateTime.Now < nextReminder.Time) if (DateTime.Now < nextReminder.Time)
{ {
//Console.WriteLine($"[Rhino/Reminderd] Sleeping for {nextWaitingTime}"); Console.WriteLine($"[Rhino/Reminderd] Sleeping for {nextWaitingTime}");
await Task.Delay(nextWaitingTime, reminderWatcherResetToken); await Task.Delay(nextWaitingTime, reminderWatcherResetToken);
} }
} }
else { else {
//Console.WriteLine("[Rhino/Reminderd] Sleeping until interrupted"); Console.WriteLine("[Rhino/Reminderd] Sleeping until interrupted");
await Task.Delay(Timeout.Infinite, reminderWatcherResetToken); await Task.Delay(Timeout.Infinite, reminderWatcherResetToken);
} }
} }
catch (TaskCanceledException) catch (TaskCanceledException)
{ {
//Console.WriteLine("[Rhino/Reminderd] Sleep interrupted, recalculating"); Console.WriteLine("[Rhino/Reminderd] Sleep interrupted, recalculating");
interruptReminderWatcher();
continue; continue;
} }
if (reminderWatcherResetToken.IsCancellationRequested) if (reminderWatcherResetToken.IsCancellationRequested)
{ {
Console.WriteLine("[Rhino/Reminderd] Sleep interrupted, recalculating (but no exception thrown)"); Console.WriteLine("[Rhino/Reminderd] Sleep interrupted, recalculating (but no exception thrown)");
interruptReminderWatcher();
continue; continue;
} }
Console.WriteLine($"[Rhino/Reminderd] Sending notification {nextReminder}"); Console.WriteLine($"[Rhino/Reminderd] Sending notification {nextReminder}");
Jid targetJid = nextReminder.Jid; // Apparently nextReminder is null after the sendAndDeleteReminder() call - very odd!
sendAndDeleteReminder(nextReminder); sendAndDeleteReminder(nextReminder);
if (nextWaitingTime.TotalMilliseconds < 0) { if (nextWaitingTime.TotalMilliseconds < 0) {
client.SendChatMessage( client.SendChatMessage(
nextReminder.Jid, targetJid,
"(Sorry I'm late reminding you! I might not have been running at the time, " + "(Sorry I'm late reminding you! I might not have been running at the time, " +
"or you might have scheduled a reminder for the past)" "or you might have scheduled a reminder for the past)"
); );
@ -383,15 +383,12 @@ namespace RhinoReminds
private void sendAndDeleteReminder(Reminder nextReminder) private void sendAndDeleteReminder(Reminder nextReminder)
{ {
try try {
{
client.SendChatMessage( client.SendChatMessage(
nextReminder.Jid, nextReminder.Jid,
$"Hello! You asked me to remind you {nextReminder.Message} at {nextReminder.Time}.".Trim().Replace(@"\s+", " ") $"Hello! You asked me to remind you {nextReminder.Message} at {nextReminder.Time}.".Trim().Replace(@"\s+", " ")
); );
} } catch (Exception error) {
catch (Exception error)
{
Console.Error.WriteLine($"[Rhino/Reminderd] Caught error sending message to client: {error}"); Console.Error.WriteLine($"[Rhino/Reminderd] Caught error sending message to client: {error}");
Console.Error.WriteLine($"[Rhink/Reminderd] Offending reminder: {nextReminder}"); Console.Error.WriteLine($"[Rhink/Reminderd] Offending reminder: {nextReminder}");
client.SendChatMessage(nextReminder.Jid, "Oops! I encountered an error sending you a reminder. Please contact my operator!"); client.SendChatMessage(nextReminder.Jid, "Oops! I encountered an error sending you a reminder. Please contact my operator!");

View file

@ -6,7 +6,8 @@ using S22.Xmpp;
namespace RhinoReminds namespace RhinoReminds
{ {
public delegate void OnReminderListUpdateHandler(object sender, Reminder newReminder); public class ReminderListUpdateEventArgs : EventArgs { }
public delegate void OnReminderListUpdateHandler(object sender, ReminderListUpdateEventArgs newReminder);
public class ReminderList public class ReminderList
{ {
@ -32,7 +33,7 @@ namespace RhinoReminds
result.TweakTime(); result.TweakTime();
Reminders.Add(result); Reminders.Add(result);
OnReminderListUpdate(this, result); OnReminderListUpdate(this, new ReminderListUpdateEventArgs());
return result; return result;
} }
@ -50,6 +51,8 @@ namespace RhinoReminds
public void DeleteReminder(Reminder nextReminder) { public void DeleteReminder(Reminder nextReminder) {
if (!Reminders.Remove(nextReminder)) if (!Reminders.Remove(nextReminder))
throw new ApplicationException($"Error: Failed to remove the reminder {nextReminder} from the list!"); throw new ApplicationException($"Error: Failed to remove the reminder {nextReminder} from the list!");
OnReminderListUpdate(this, new ReminderListUpdateEventArgs());
} }