fix: close a message in the reader once its scheduled send is cancelled instead of still showing it as scheduled

This commit is contained in:
Linus Rath
2026-10-28 10:28:11 +01:00
parent 039ed0598b
commit 780b64461e
3 changed files with 22 additions and 4 deletions
+3
View File
@@ -2474,8 +2474,11 @@ export function MailApp({ linkSegments: routeSegments }: MailAppProps = {}) {
// and compose again".
const handleCancelScheduledSend = async (email: Email) => {
if (email.isSmimeScheduled || email.scheduledUndoStatus !== 'pending') return;
const wasOpen = useEmailStore.getState().selectedEmail?.id === email.id;
const restored = await cancelScheduledForEdit(email);
if (restored === undefined) return;
// The store closed it in the reader; on a phone or tablet the list comes back.
if (wasOpen && (isMobile || isTablet)) handleMobileBack();
toast.success(
tViewer('send_cancelled'),
t('notifications.moved_to_mailbox', { mailbox: t('sidebar.mailboxes.drafts') }),
@@ -110,6 +110,19 @@ describe('cancelling a send and restoring the draft', () => {
await expect(useEmailStore.getState().cancelScheduledEmailForEdit(client, scheduled)).resolves.toEqual({ id: 'sent-1' });
});
// The reader kept showing the Scheduled banner and its buttons for a
// message that was back in Drafts.
it('closes the cancelled message in the reader, and leaves another open message alone', async () => {
useEmailStore.setState({ selectedEmail: { ...scheduled, isScheduled: true } as Email });
await useEmailStore.getState().cancelScheduledEmailForEdit(client, scheduled);
expect(useEmailStore.getState().selectedEmail).toBeNull();
const other = { id: 'other-1' } as Email;
useEmailStore.setState({ selectedEmail: other });
await useEmailStore.getState().cancelScheduledEmailForEdit(client, scheduled);
expect(useEmailStore.getState().selectedEmail).toBe(other);
});
it('restores mail sent from the own identity in the own Drafts, as before', async () => {
const restored = await useEmailStore.getState().cancelUndoSend(client, { ...pending, submissionAccountId: 'account-1' });
+6 -4
View File
@@ -7966,13 +7966,15 @@ export const useEmailStore = create<EmailStore>((set, get) => ({
try {
if (email.isSmimeScheduled) {
await client.deleteEmail(email.id, accountId);
set(state => ({
selectedEmail: state.selectedEmail?.id === email.id ? null : state.selectedEmail,
selectedEmailKeys: dropFromSelection(state, e => e.id === email.id),
}));
} else {
await restoreSentToDraft(client, get().mailboxes, email.id, accountId);
}
// Gone from Scheduled either way: the reader must not keep showing it
// with the Scheduled banner and its buttons.
set(state => ({
selectedEmail: state.selectedEmail?.id === email.id ? null : state.selectedEmail,
selectedEmailKeys: dropFromSelection(state, e => e.id === email.id),
}));
} catch (error) {
void get().fetchScheduledEmails(client);
throw new SendCancelledCleanupError(email.isSmimeScheduled ? 'remove' : 'restore', error);