mirror of
https://github.com/bulwarkmail/webmail.git
synced 2026-11-04 16:14:07 +00:00
feat: ask between a new message and Files for a file opened with the desktop app
This commit is contained in:
@@ -114,6 +114,23 @@ describe('launches', () => {
|
||||
expect(draft?.files.map((file) => file.name)).toEqual(['report.pdf']);
|
||||
});
|
||||
|
||||
it('several files sent to the app go on one draft, without a question', async () => {
|
||||
const { takeHandoff } = await import('@/lib/launch-handoff');
|
||||
await run({ type: 'files', reason: 'attach', failed: [], files: [{ name: 'a.pdf', data: text('a') }, { name: 'b.png', data: text('b') }] });
|
||||
expect(takeHandoff('compose')?.files.map((file) => file.name)).toEqual(['a.pdf', 'b.png']);
|
||||
});
|
||||
|
||||
it('a file opened with the app asks: new message or Files, a new message first', async () => {
|
||||
const { takeHandoff } = await import('@/lib/launch-handoff');
|
||||
const { listenForFileChoices } = await import('@/lib/file-drop/choice');
|
||||
const asked = vi.fn();
|
||||
const stop = listenForFileChoices(asked);
|
||||
await run({ type: 'files', reason: 'attach', ask: true, failed: [], files: [{ name: 'report.pdf', data: text('pdf') }] });
|
||||
expect(asked).toHaveBeenCalledWith({ files: [expect.objectContaining({ name: 'report.pdf' })], preferred: 'new-message' });
|
||||
expect(takeHandoff('compose')).toBeNull();
|
||||
stop();
|
||||
});
|
||||
|
||||
it('says so when a file could not be read', async () => {
|
||||
await run({ type: 'files', reason: 'open', failed: ['gone.eml'], files: [] });
|
||||
expect(notifyFailed).toHaveBeenCalledWith(['gone.eml']);
|
||||
|
||||
@@ -9,6 +9,7 @@ import { isAppLocked } from '@/lib/desktop/app-lock-state';
|
||||
import { getDesktopBridge } from '@/lib/desktop/bridge';
|
||||
import type { DesktopOsCommand } from '@/lib/desktop/types';
|
||||
import { openMailLink } from '@/lib/desktop/mail-links';
|
||||
import { requestFileChoice } from '@/lib/file-drop/choice';
|
||||
import { handleReminderCommand } from '@/lib/desktop/reminder-notifications';
|
||||
import type { MailNotificationContext } from '@/lib/desktop/mail-notifications';
|
||||
import { handOffDraft, handOffFiles, handOffNewMessage, kindForFile } from '@/lib/launch-handoff';
|
||||
@@ -131,7 +132,10 @@ async function handleNotification(action: string, rawContext: string, reply: str
|
||||
function handleFiles(command: Extract<DesktopOsCommand, { type: 'files' }>, env: OsCommandEnv): void {
|
||||
const made = command.files.map(({ name, data }) => new File([new Uint8Array(data)], name));
|
||||
const failed = [...command.failed];
|
||||
if (command.reason === 'attach') {
|
||||
if (command.reason === 'attach' && command.ask) {
|
||||
// Opened with the app ("Open with"): the same choice as dropping it on the window.
|
||||
requestFileChoice({ files: made, preferred: 'new-message' });
|
||||
} else if (command.reason === 'attach') {
|
||||
if (made.length > 0) handOffDraft({ files: made });
|
||||
} else {
|
||||
for (const file of made) {
|
||||
|
||||
@@ -550,7 +550,8 @@ export type DesktopOsCommand =
|
||||
| { type: 'open-mailbox'; mailboxId: string }
|
||||
| { type: 'mailto'; url: string }
|
||||
| { type: 'webcal'; url: string }
|
||||
| { type: 'files'; reason: 'open' | 'attach'; files: DesktopOsFile[]; failed: string[] }
|
||||
/** `ask`: opened with the app, so the user picks between a new message and Files. Without it, attach. */
|
||||
| { type: 'files'; reason: 'open' | 'attach'; files: DesktopOsFile[]; failed: string[]; ask?: boolean }
|
||||
| { type: 'notification'; action: string; context: string; reply?: string };
|
||||
|
||||
export interface DesktopOsNotification {
|
||||
|
||||
Reference in New Issue
Block a user