diff --git a/client/src/features/email/components/SendBookDialog.vue b/client/src/features/email/components/SendBookDialog.vue index 7cc6bff89..cb128dd58 100644 --- a/client/src/features/email/components/SendBookDialog.vue +++ b/client/src/features/email/components/SendBookDialog.vue @@ -106,8 +106,7 @@ watch( loaded.value = false await Promise.all([fetchRecipients(), fetchGroups(), fetchProviders(), fetchTemplates(), fetchPreferences()].map((p) => p.catch(() => undefined))) loaded.value = true - const defaultRecipient = preferences.value?.defaultRecipientId - selectedIds.value = defaultRecipient && recipients.value.some((r) => r.id === defaultRecipient) ? [defaultRecipient] : [] + selectedIds.value = initialRecipientIds() providerId.value = preferences.value?.defaultProviderId ?? providers.value[0]?.id ?? null }, { immediate: true }, @@ -115,6 +114,14 @@ watch( onBeforeUnmount(stopPolling) +/** The starred recipient, or the only one when nobody starred it: creating a recipient never makes it the default. */ +function initialRecipientIds(): number[] { + const defaultId = preferences.value?.defaultRecipientId + if (defaultId && recipients.value.some((r) => r.id === defaultId)) return [defaultId] + const [only, ...rest] = recipients.value + return only && rest.length === 0 ? [only.id] : [] +} + /** What each picked recipient gets, and the line a row shows when that differs from the rest. */ function exceptionFor(recipient: EmailRecipient): { text: string; warn: boolean } | null { if (singleBookId.value === null || files.value.length === 0) return null diff --git a/client/src/features/email/components/__tests__/SendBookDialog.spec.ts b/client/src/features/email/components/__tests__/SendBookDialog.spec.ts index 68290d929..d64a8d0cb 100644 --- a/client/src/features/email/components/__tests__/SendBookDialog.spec.ts +++ b/client/src/features/email/components/__tests__/SendBookDialog.spec.ts @@ -120,6 +120,31 @@ describe('SendBookDialog', () => { expect(mockState.sendBook).toHaveBeenCalledWith({ bookIds: [12], recipientIds: [10], providerId: 3, templateId: undefined, fileId: undefined }) }) + it('picks the only recipient when nobody starred one', async () => { + recipients.value = recipients.value.slice(0, 1) + groups.value = [] + preferences.value = null + mountSheet() + await flushPromises() + + expect(recipientRow('Kindle Paperwhite').getAttribute('aria-checked')).toBe('true') + + buttonByText('Send').click() + await flushPromises() + + expect(mockState.sendBook).toHaveBeenCalledWith(expect.objectContaining({ recipientIds: [10], providerId: 3 })) + }) + + it('leaves the choice open when several recipients exist and none is starred', async () => { + preferences.value = null + mountSheet() + await flushPromises() + + expect(recipientRow('Kindle Paperwhite').getAttribute('aria-checked')).toBe('false') + expect(recipientRow('Ana Beck').getAttribute('aria-checked')).toBe('false') + expect(buttonByText('Send').disabled).toBe(true) + }) + it('says what a recipient gets only when it differs from the rest', async () => { mountSheet() await flushPromises()