@rapidmx/web-client 0.30.0 → 0.31.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/apps/admin/audit-log/index.tsx +3 -3
- package/apps/admin/branding/index.tsx +3 -3
- package/apps/admin/data-requests/index.tsx +18 -7
- package/apps/admin/distribution-lists/[uid].tsx +3 -3
- package/apps/admin/distribution-lists/index.tsx +3 -3
- package/apps/admin/distribution-lists/new/index.tsx +3 -3
- package/apps/admin/domains/[uid].tsx +6 -5
- package/apps/admin/domains/index.tsx +3 -3
- package/apps/admin/domains/new/index.tsx +3 -3
- package/apps/admin/escrow-scopes/[uid].tsx +11 -5
- package/apps/admin/escrow-scopes/index.tsx +3 -3
- package/apps/admin/escrow-scopes/new/index.tsx +9 -3
- package/apps/admin/index.tsx +4 -4
- package/apps/admin/ingest-queue/index.tsx +3 -3
- package/apps/admin/mailboxes/[uid].tsx +15 -7
- package/apps/admin/quarantine/index.tsx +4 -4
- package/apps/admin/retention-policy/index.tsx +3 -3
- package/apps/admin/signing-certificates/index.tsx +3 -3
- package/apps/admin/transport-rules/[uid].tsx +4 -4
- package/apps/admin/transport-rules/index.tsx +3 -3
- package/apps/admin/transport-rules/new/index.tsx +3 -3
- package/apps/escrow/matters/[uid].tsx +26 -2
- package/apps/escrow/matters/new/index.tsx +4 -0
- package/apps/shared/calendar/calendarLiveUpdates.ts +11 -10
- package/apps/shared/calendar/useCalendarReminders.ts +2 -0
- package/apps/shared/components/admin/ActionAlert.tsx +32 -0
- package/apps/shared/components/admin/diagnostics/InformationPanel.tsx +1 -1
- package/apps/shared/components/admin/diagnostics/InstalledPlugins.tsx +1 -1
- package/apps/shared/components/admin/diagnostics/LogsPanel.tsx +1 -1
- package/apps/shared/components/admin/diagnostics/RuntimePanel.tsx +1 -1
- package/apps/shared/components/admin/diagnostics/SystemPanel.tsx +1 -1
- package/apps/shared/components/admin/distributionLists/MemberListCard.tsx +4 -4
- package/apps/shared/components/admin/elevation.ts +19 -0
- package/apps/shared/components/admin/escrowScopes/EscrowScopeKeyAndHoldersFields.tsx +58 -3
- package/apps/shared/components/admin/layout/AdminShell.tsx +6 -1
- package/apps/shared/components/admin/mailboxes/EraseLeftoverDataDialog.tsx +3 -3
- package/apps/shared/components/admin/mailboxes/EscrowScopeCard.tsx +4 -4
- package/apps/shared/components/admin/mailboxes/LeftoverMailboxesSection.tsx +4 -4
- package/apps/shared/components/admin/mailboxes/ResourceSettingsCard.tsx +3 -3
- package/apps/shared/components/admin/mailboxes/ShareAccessCard.tsx +6 -6
- package/apps/shared/components/admin/settings/BrandingForm.tsx +22 -9
- package/apps/shared/components/admin/settings/DomainDnsSetup.tsx +4 -4
- package/apps/shared/components/admin/settings/EncryptionPolicyForm.tsx +33 -4
- package/apps/shared/components/admin/settings/LoadedSettingsForm.tsx +3 -3
- package/apps/shared/components/admin/settings/MailboxCreateForm.tsx +8 -3
- package/apps/shared/components/admin/settings/MailboxPolicyForm.tsx +3 -3
- package/apps/shared/components/admin/settings/PluginsManager.tsx +39 -17
- package/apps/shared/components/admin/settings/RetentionPolicyForm.tsx +25 -12
- package/apps/shared/components/admin/setup/EscrowSetupStep.tsx +40 -7
- package/apps/shared/components/admin/setup/SetupWizard.tsx +8 -6
- package/apps/shared/components/admin/signOut.ts +3 -0
- package/apps/shared/components/admin/usePagedList.tsx +2 -2
- package/apps/shared/components/calendar/DescriptionEditor.tsx +2 -1
- package/apps/shared/components/calendar/EventDetails.tsx +34 -8
- package/apps/shared/components/calendar/EventEditor.tsx +90 -40
- package/apps/shared/components/calendar/EventFormParts.tsx +5 -2
- package/apps/shared/components/calendar/EventMatchNav.tsx +14 -2
- package/apps/shared/components/calendar/EventModal.tsx +25 -1
- package/apps/shared/components/calendar/FindATime.tsx +10 -2
- package/apps/shared/components/calendar/ListView.tsx +99 -25
- package/apps/shared/components/calendar/RecurrenceEditor.tsx +19 -8
- package/apps/shared/components/calendar/SplitDayView.tsx +14 -18
- package/apps/shared/components/calendar/TaskQuickForm.tsx +3 -2
- package/apps/shared/components/calendar/TimeGridView.tsx +35 -19
- package/apps/shared/components/calendar/gridLayout.ts +94 -0
- package/apps/shared/components/calendar/layout/CalendarShell.tsx +1 -1
- package/apps/shared/components/calendar/timePicker.ts +5 -2
- package/apps/shared/components/contacts/ContactCard.tsx +15 -4
- package/apps/shared/components/contacts/ContactDetailPane.tsx +54 -15
- package/apps/shared/components/contacts/ContactForm.tsx +61 -17
- package/apps/shared/components/contacts/ContactPhotoEditor.tsx +88 -0
- package/apps/shared/components/contacts/ContactPhotoField.tsx +36 -39
- package/apps/shared/components/contacts/layout/ContactsShell.tsx +1 -1
- package/apps/shared/components/contacts/participantDetails.ts +18 -1
- package/apps/shared/components/layout/AppShell.tsx +9 -0
- package/apps/shared/components/layout/KeyEnrollmentGate.tsx +9 -4
- package/apps/shared/components/layout/MailboxProvisioning.tsx +31 -3
- package/apps/shared/components/layout/RecoveryCodeUnlock.tsx +4 -2
- package/apps/shared/components/mail/ConversationList.tsx +49 -6
- package/apps/shared/components/mail/ConversationThreadPane.tsx +1 -1
- package/apps/shared/components/mail/MenuButton.tsx +3 -400
- package/apps/shared/components/mail/MessageDetailPane.tsx +16 -13
- package/apps/shared/components/mail/compose/ComposeToolbar.tsx +11 -1
- package/apps/shared/components/mail/compose/ComposeWindow.tsx +57 -11
- package/apps/shared/components/mail/compose/GifPicker.tsx +10 -4
- package/apps/shared/components/mail/compose/RecipientInput.tsx +9 -7
- package/apps/shared/components/mail/compose/composeFlushRegistry.ts +14 -1
- package/apps/shared/components/mail/compose/encryptionRequirement.ts +5 -0
- package/apps/shared/components/mail/compose/quotedBody.ts +31 -6
- package/apps/shared/components/mail/layout/MailShell.tsx +1 -1
- package/apps/shared/components/mail/reading/MessageBody.tsx +13 -7
- package/apps/shared/components/mail/reading/bodyContent.ts +2 -0
- package/apps/shared/components/mail/reading/bodyHtml.ts +25 -2
- package/apps/shared/components/mail/writableMailboxes.ts +2 -0
- package/apps/shared/components/rules/RuleBuilder.tsx +11 -2
- package/apps/shared/components/settings/GravatarSetting.tsx +27 -0
- package/apps/shared/components/settings/layout/SettingsShell.tsx +1 -1
- package/apps/shared/components/tasks/dueDate.ts +29 -0
- package/apps/shared/components/tasks/layout/TasksShell.tsx +1 -1
- package/apps/shared/mail/decryptedMessages.ts +51 -2
- package/apps/shared/mail/listSnapshots.ts +2 -0
- package/apps/shared/mail/outbox/sendDecision.ts +14 -3
- package/apps/shared/mail/outbox/sendJob.ts +5 -0
- package/apps/shared/mail/useMailLiveUpdates.ts +7 -1
- package/apps/shared/mail/usePermanentDelete.tsx +3 -1
- package/apps/shared/notifications/apiErrors.ts +2 -0
- package/apps/shared/notifications/preferences.ts +1 -1
- package/apps/shared/notifications/store.ts +3 -1
- package/apps/shared/plugins/pluginNav.ts +4 -2
- package/apps/www/calendar/index.tsx +24 -12
- package/apps/www/contacts/[uid].tsx +6 -1
- package/apps/www/contacts/index.tsx +66 -12
- package/apps/www/index.tsx +91 -28
- package/apps/www/messages/[uid].tsx +8 -3
- package/apps/www/settings/auto-reply/index.tsx +13 -0
- package/apps/www/settings/blocked-senders/index.tsx +4 -0
- package/apps/www/settings/encryption/index.tsx +66 -4
- package/apps/www/settings/privacy/index.tsx +4 -1
- package/apps/www/settings/profile/index.tsx +12 -1
- package/apps/www/settings/sharing/index.tsx +11 -1
- package/apps/www/settings/signatures/[uid].tsx +6 -4
- package/apps/www/tasks/index.tsx +97 -29
- package/dist/apps/admin/audit-log/index.js +3 -3
- package/dist/apps/admin/branding/index.js +3 -3
- package/dist/apps/admin/data-requests/index.js +17 -7
- package/dist/apps/admin/distribution-lists/[uid].js +3 -3
- package/dist/apps/admin/distribution-lists/index.js +3 -3
- package/dist/apps/admin/distribution-lists/new/index.js +3 -3
- package/dist/apps/admin/domains/[uid].js +6 -5
- package/dist/apps/admin/domains/index.js +3 -3
- package/dist/apps/admin/domains/new/index.js +3 -3
- package/dist/apps/admin/escrow-scopes/[uid].js +11 -6
- package/dist/apps/admin/escrow-scopes/index.js +3 -3
- package/dist/apps/admin/escrow-scopes/new/index.js +9 -4
- package/dist/apps/admin/index.js +4 -4
- package/dist/apps/admin/ingest-queue/index.js +3 -3
- package/dist/apps/admin/mailboxes/[uid].js +15 -7
- package/dist/apps/admin/quarantine/index.js +4 -4
- package/dist/apps/admin/retention-policy/index.js +3 -3
- package/dist/apps/admin/signing-certificates/index.js +3 -3
- package/dist/apps/admin/transport-rules/[uid].js +4 -4
- package/dist/apps/admin/transport-rules/index.js +3 -3
- package/dist/apps/admin/transport-rules/new/index.js +3 -3
- package/dist/apps/escrow/matters/[uid].js +8 -3
- package/dist/apps/escrow/matters/new/index.js +4 -0
- package/dist/apps/shared/calendar/calendarLiveUpdates.d.ts +11 -7
- package/dist/apps/shared/calendar/calendarLiveUpdates.js +10 -9
- package/dist/apps/shared/calendar/useCalendarReminders.js +2 -0
- package/dist/apps/shared/components/admin/ActionAlert.d.ts +13 -0
- package/dist/apps/shared/components/admin/ActionAlert.js +24 -0
- package/dist/apps/shared/components/admin/diagnostics/InformationPanel.js +1 -1
- package/dist/apps/shared/components/admin/diagnostics/InstalledPlugins.js +1 -1
- package/dist/apps/shared/components/admin/diagnostics/LogsPanel.js +1 -1
- package/dist/apps/shared/components/admin/diagnostics/RuntimePanel.js +1 -1
- package/dist/apps/shared/components/admin/diagnostics/SystemPanel.js +1 -1
- package/dist/apps/shared/components/admin/distributionLists/MemberListCard.js +4 -4
- package/dist/apps/shared/components/admin/elevation.d.ts +9 -0
- package/dist/apps/shared/components/admin/elevation.js +16 -0
- package/dist/apps/shared/components/admin/escrowScopes/EscrowScopeKeyAndHoldersFields.d.ts +2 -0
- package/dist/apps/shared/components/admin/escrowScopes/EscrowScopeKeyAndHoldersFields.js +41 -1
- package/dist/apps/shared/components/admin/layout/AdminShell.js +2 -1
- package/dist/apps/shared/components/admin/mailboxes/EraseLeftoverDataDialog.js +3 -3
- package/dist/apps/shared/components/admin/mailboxes/EscrowScopeCard.js +4 -4
- package/dist/apps/shared/components/admin/mailboxes/LeftoverMailboxesSection.js +4 -4
- package/dist/apps/shared/components/admin/mailboxes/ResourceSettingsCard.js +3 -3
- package/dist/apps/shared/components/admin/mailboxes/ShareAccessCard.js +6 -6
- package/dist/apps/shared/components/admin/settings/BrandingForm.js +17 -7
- package/dist/apps/shared/components/admin/settings/DomainDnsSetup.js +4 -4
- package/dist/apps/shared/components/admin/settings/EncryptionPolicyForm.js +17 -5
- package/dist/apps/shared/components/admin/settings/LoadedSettingsForm.js +3 -3
- package/dist/apps/shared/components/admin/settings/MailboxCreateForm.js +8 -3
- package/dist/apps/shared/components/admin/settings/MailboxPolicyForm.js +3 -3
- package/dist/apps/shared/components/admin/settings/PluginsManager.js +26 -12
- package/dist/apps/shared/components/admin/settings/RetentionPolicyForm.js +17 -10
- package/dist/apps/shared/components/admin/setup/EscrowSetupStep.js +18 -8
- package/dist/apps/shared/components/admin/setup/SetupWizard.js +8 -6
- package/dist/apps/shared/components/admin/signOut.js +3 -0
- package/dist/apps/shared/components/admin/usePagedList.js +2 -2
- package/dist/apps/shared/components/calendar/DescriptionEditor.js +2 -1
- package/dist/apps/shared/components/calendar/EventDetails.d.ts +3 -1
- package/dist/apps/shared/components/calendar/EventDetails.js +7 -4
- package/dist/apps/shared/components/calendar/EventEditor.js +81 -33
- package/dist/apps/shared/components/calendar/EventFormParts.d.ts +3 -1
- package/dist/apps/shared/components/calendar/EventFormParts.js +3 -3
- package/dist/apps/shared/components/calendar/EventMatchNav.d.ts +1 -1
- package/dist/apps/shared/components/calendar/EventMatchNav.js +12 -2
- package/dist/apps/shared/components/calendar/EventModal.js +10 -2
- package/dist/apps/shared/components/calendar/FindATime.js +4 -3
- package/dist/apps/shared/components/calendar/ListView.d.ts +10 -4
- package/dist/apps/shared/components/calendar/ListView.js +92 -27
- package/dist/apps/shared/components/calendar/RecurrenceEditor.d.ts +4 -1
- package/dist/apps/shared/components/calendar/RecurrenceEditor.js +15 -10
- package/dist/apps/shared/components/calendar/SplitDayView.js +11 -17
- package/dist/apps/shared/components/calendar/TaskQuickForm.js +3 -2
- package/dist/apps/shared/components/calendar/TimeGridView.js +23 -21
- package/dist/apps/shared/components/calendar/gridLayout.d.ts +41 -0
- package/dist/apps/shared/components/calendar/gridLayout.js +83 -0
- package/dist/apps/shared/components/calendar/layout/CalendarShell.js +1 -1
- package/dist/apps/shared/components/calendar/timePicker.js +5 -2
- package/dist/apps/shared/components/contacts/ContactCard.js +9 -3
- package/dist/apps/shared/components/contacts/ContactDetailPane.d.ts +5 -3
- package/dist/apps/shared/components/contacts/ContactDetailPane.js +11 -5
- package/dist/apps/shared/components/contacts/ContactForm.js +54 -16
- package/dist/apps/shared/components/contacts/ContactPhotoEditor.d.ts +21 -0
- package/dist/apps/shared/components/contacts/ContactPhotoEditor.js +56 -0
- package/dist/apps/shared/components/contacts/ContactPhotoField.d.ts +7 -4
- package/dist/apps/shared/components/contacts/ContactPhotoField.js +19 -21
- package/dist/apps/shared/components/contacts/layout/ContactsShell.js +1 -1
- package/dist/apps/shared/components/contacts/participantDetails.d.ts +4 -1
- package/dist/apps/shared/components/contacts/participantDetails.js +17 -1
- package/dist/apps/shared/components/layout/AppShell.js +9 -0
- package/dist/apps/shared/components/layout/KeyEnrollmentGate.js +2 -3
- package/dist/apps/shared/components/layout/MailboxProvisioning.d.ts +4 -1
- package/dist/apps/shared/components/layout/MailboxProvisioning.js +24 -2
- package/dist/apps/shared/components/layout/RecoveryCodeUnlock.d.ts +4 -2
- package/dist/apps/shared/components/layout/RecoveryCodeUnlock.js +4 -2
- package/dist/apps/shared/components/mail/ConversationList.js +49 -6
- package/dist/apps/shared/components/mail/ConversationThreadPane.js +1 -1
- package/dist/apps/shared/components/mail/MenuButton.d.ts +2 -78
- package/dist/apps/shared/components/mail/MenuButton.js +2 -211
- package/dist/apps/shared/components/mail/MessageDetailPane.js +10 -6
- package/dist/apps/shared/components/mail/compose/ComposeToolbar.d.ts +3 -0
- package/dist/apps/shared/components/mail/compose/ComposeToolbar.js +10 -1
- package/dist/apps/shared/components/mail/compose/ComposeWindow.js +55 -10
- package/dist/apps/shared/components/mail/compose/GifPicker.js +10 -4
- package/dist/apps/shared/components/mail/compose/RecipientInput.js +9 -7
- package/dist/apps/shared/components/mail/compose/composeFlushRegistry.d.ts +7 -1
- package/dist/apps/shared/components/mail/compose/composeFlushRegistry.js +13 -1
- package/dist/apps/shared/components/mail/compose/encryptionRequirement.d.ts +5 -0
- package/dist/apps/shared/components/mail/compose/quotedBody.js +28 -5
- package/dist/apps/shared/components/mail/layout/MailShell.js +1 -1
- package/dist/apps/shared/components/mail/reading/MessageBody.js +11 -6
- package/dist/apps/shared/components/mail/reading/bodyContent.js +2 -0
- package/dist/apps/shared/components/mail/reading/bodyHtml.d.ts +5 -1
- package/dist/apps/shared/components/mail/reading/bodyHtml.js +23 -2
- package/dist/apps/shared/components/mail/writableMailboxes.js +2 -0
- package/dist/apps/shared/components/rules/RuleBuilder.js +9 -1
- package/dist/apps/shared/components/settings/GravatarSetting.d.ts +6 -0
- package/dist/apps/shared/components/settings/GravatarSetting.js +15 -0
- package/dist/apps/shared/components/settings/layout/SettingsShell.js +1 -1
- package/dist/apps/shared/components/tasks/dueDate.d.ts +12 -0
- package/dist/apps/shared/components/tasks/dueDate.js +26 -0
- package/dist/apps/shared/components/tasks/layout/TasksShell.js +1 -1
- package/dist/apps/shared/mail/decryptedMessages.d.ts +8 -0
- package/dist/apps/shared/mail/decryptedMessages.js +46 -2
- package/dist/apps/shared/mail/listSnapshots.js +2 -0
- package/dist/apps/shared/mail/outbox/sendDecision.d.ts +6 -3
- package/dist/apps/shared/mail/outbox/sendDecision.js +13 -3
- package/dist/apps/shared/mail/outbox/sendJob.d.ts +1 -0
- package/dist/apps/shared/mail/outbox/sendJob.js +5 -1
- package/dist/apps/shared/mail/useMailLiveUpdates.d.ts +3 -0
- package/dist/apps/shared/mail/useMailLiveUpdates.js +6 -1
- package/dist/apps/shared/mail/usePermanentDelete.d.ts +2 -0
- package/dist/apps/shared/mail/usePermanentDelete.js +1 -1
- package/dist/apps/shared/notifications/apiErrors.js +2 -0
- package/dist/apps/shared/notifications/preferences.d.ts +1 -1
- package/dist/apps/shared/notifications/preferences.js +1 -1
- package/dist/apps/shared/notifications/store.js +3 -1
- package/dist/apps/shared/plugins/pluginNav.d.ts +2 -1
- package/dist/apps/shared/plugins/pluginNav.js +4 -2
- package/dist/apps/www/calendar/index.js +24 -12
- package/dist/apps/www/contacts/[uid].js +6 -2
- package/dist/apps/www/contacts/index.js +62 -11
- package/dist/apps/www/index.js +85 -30
- package/dist/apps/www/messages/[uid].js +8 -3
- package/dist/apps/www/settings/auto-reply/index.js +13 -1
- package/dist/apps/www/settings/blocked-senders/index.js +4 -0
- package/dist/apps/www/settings/encryption/index.js +29 -5
- package/dist/apps/www/settings/privacy/index.js +3 -2
- package/dist/apps/www/settings/profile/index.js +4 -1
- package/dist/apps/www/settings/sharing/index.js +10 -1
- package/dist/apps/www/settings/signatures/[uid].js +6 -4
- package/dist/apps/www/tasks/index.js +94 -32
- package/dist/lib/admin/auditLogApi.js +2 -2
- package/dist/lib/admin/distributionListsApi.js +2 -2
- package/dist/lib/admin/domainsApi.js +2 -2
- package/dist/lib/admin/escrowAuditLogApi.js +2 -2
- package/dist/lib/admin/escrowScopesApi.js +2 -2
- package/dist/lib/admin/pluginsApi.d.ts +13 -2
- package/dist/lib/admin/pluginsApi.js +8 -0
- package/dist/lib/admin/retentionPolicyApi.d.ts +3 -0
- package/dist/lib/admin/retentionPolicyApi.js +3 -0
- package/dist/lib/admin/transportRulesApi.js +2 -2
- package/dist/lib/appearance/preferencesApi.d.ts +1 -1
- package/dist/lib/appearance/preferencesApi.js +3 -14
- package/dist/lib/auth/session.d.ts +51 -12
- package/dist/lib/auth/session.js +214 -38
- package/dist/lib/branding/brandingApi.d.ts +3 -3
- package/dist/lib/branding/brandingApi.js +9 -21
- package/dist/lib/calendar/calendarApi.js +3 -1
- package/dist/lib/calendar/eventSearch.js +43 -6
- package/dist/lib/calendar/freeBusyApi.d.ts +2 -1
- package/dist/lib/calendar/freeBusyApi.js +13 -5
- package/dist/lib/calendar/recurrence.js +51 -3
- package/dist/lib/calendar/useDayKey.d.ts +7 -0
- package/dist/lib/calendar/useDayKey.js +43 -0
- package/dist/lib/components/avatar/ContactAvatar.d.ts +6 -2
- package/dist/lib/components/avatar/ContactAvatar.js +37 -8
- package/dist/lib/components/avatar/ContactPhotoAvatar.d.ts +11 -0
- package/dist/lib/components/avatar/ContactPhotoAvatar.js +18 -0
- package/dist/lib/components/forms/CameraCaptureModal.d.ts +17 -0
- package/dist/lib/components/forms/CameraCaptureModal.js +88 -0
- package/dist/lib/components/forms/ImageEditBadge.d.ts +28 -0
- package/dist/lib/components/forms/ImageEditBadge.js +62 -0
- package/dist/lib/components/menus/MenuButton.d.ts +78 -0
- package/dist/lib/components/menus/MenuButton.js +219 -0
- package/dist/lib/components/navigation/BottomTabBar.d.ts +3 -1
- package/dist/lib/components/navigation/BottomTabBar.js +22 -3
- package/dist/lib/components/overlays/PopoverPortal.d.ts +2 -1
- package/dist/lib/components/overlays/PopoverPortal.js +3 -2
- package/dist/lib/components/pickers/TimeZonePicker.js +13 -1
- package/dist/lib/contacts/contactsApi.d.ts +5 -2
- package/dist/lib/contacts/contactsApi.js +16 -19
- package/dist/lib/contacts/gravatar.d.ts +14 -3
- package/dist/lib/contacts/gravatar.js +42 -5
- package/dist/lib/contacts/preparePhoto.d.ts +24 -0
- package/dist/lib/contacts/preparePhoto.js +250 -0
- package/dist/lib/contacts/useContactPhotoSrc.d.ts +19 -0
- package/dist/lib/contacts/useContactPhotoSrc.js +153 -0
- package/dist/lib/contacts/vcard.d.ts +3 -0
- package/dist/lib/contacts/vcard.js +59 -7
- package/dist/lib/crypto/escrowKeys.d.ts +8 -0
- package/dist/lib/crypto/escrowKeys.js +20 -1
- package/dist/lib/crypto/messageSecurity.d.ts +7 -4
- package/dist/lib/crypto/messageSecurity.js +23 -5
- package/dist/lib/crypto/passwordUnlock.d.ts +6 -1
- package/dist/lib/crypto/passwordUnlock.js +13 -2
- package/dist/lib/crypto/smime.js +12 -2
- package/dist/lib/mail/compose/composeQuoting.js +3 -2
- package/dist/lib/mail/compose/quotedImages.d.ts +6 -3
- package/dist/lib/mail/compose/quotedImages.js +35 -9
- package/dist/lib/mail/labelsApi.js +2 -2
- package/dist/lib/mail/mailApi.d.ts +8 -5
- package/dist/lib/mail/mailApi.js +73 -39
- package/dist/lib/mail/mailDetailHooks.js +11 -3
- package/dist/lib/mail/mailFilterRulesApi.js +2 -2
- package/dist/lib/mail/mailSignaturesApi.js +2 -2
- package/dist/lib/mail/mailboxImportApi.d.ts +1 -1
- package/dist/lib/mail/mailboxImportApi.js +3 -15
- package/dist/lib/mail/messageBodySanitizer.d.ts +6 -0
- package/dist/lib/mail/messageBodySanitizer.js +44 -1
- package/dist/lib/search/queryGrammar.js +12 -4
- package/dist/lib/search/searchTier3.d.ts +6 -1
- package/dist/lib/search/searchTier3.js +54 -25
- package/dist/lib/tasks/tasksApi.js +3 -3
- package/dist/lib/util/api.d.ts +26 -4
- package/dist/lib/util/api.js +73 -16
- package/dist/lib/util/apiQuery.d.ts +11 -0
- package/dist/lib/util/apiQuery.js +11 -0
- package/dist/lib/util/settleWithLimit.d.ts +5 -0
- package/dist/lib/util/settleWithLimit.js +25 -0
- package/lib/admin/auditLogApi.ts +2 -2
- package/lib/admin/distributionListsApi.ts +2 -2
- package/lib/admin/domainsApi.ts +2 -2
- package/lib/admin/escrowAuditLogApi.ts +2 -2
- package/lib/admin/escrowScopesApi.ts +2 -2
- package/lib/admin/pluginsApi.ts +21 -2
- package/lib/admin/retentionPolicyApi.ts +4 -0
- package/lib/admin/transportRulesApi.ts +2 -2
- package/lib/appearance/preferencesApi.ts +3 -14
- package/lib/auth/session.ts +239 -39
- package/lib/branding/brandingApi.ts +9 -21
- package/lib/calendar/calendarApi.ts +3 -1
- package/lib/calendar/eventSearch.ts +46 -6
- package/lib/calendar/freeBusyApi.ts +14 -6
- package/lib/calendar/recurrence.ts +59 -8
- package/lib/calendar/useDayKey.ts +45 -0
- package/lib/components/avatar/ContactAvatar.tsx +46 -8
- package/lib/components/avatar/ContactPhotoAvatar.tsx +26 -0
- package/lib/components/forms/CameraCaptureModal.tsx +133 -0
- package/lib/components/forms/ImageEditBadge.tsx +121 -0
- package/lib/components/menus/MenuButton.tsx +408 -0
- package/lib/components/navigation/BottomTabBar.tsx +30 -8
- package/lib/components/overlays/PopoverPortal.tsx +3 -2
- package/lib/components/pickers/TimeZonePicker.tsx +17 -1
- package/lib/contacts/contactsApi.ts +18 -19
- package/lib/contacts/gravatar.ts +47 -5
- package/lib/contacts/preparePhoto.ts +273 -0
- package/lib/contacts/useContactPhotoSrc.ts +177 -0
- package/lib/contacts/vcard.ts +60 -7
- package/lib/crypto/escrowKeys.ts +21 -1
- package/lib/crypto/messageSecurity.ts +33 -9
- package/lib/crypto/passwordUnlock.ts +14 -2
- package/lib/crypto/smime.ts +13 -2
- package/lib/mail/compose/composeQuoting.ts +3 -2
- package/lib/mail/compose/quotedImages.ts +39 -9
- package/lib/mail/labelsApi.ts +2 -2
- package/lib/mail/mailApi.ts +96 -39
- package/lib/mail/mailDetailHooks.ts +11 -3
- package/lib/mail/mailFilterRulesApi.ts +2 -2
- package/lib/mail/mailSignaturesApi.ts +2 -2
- package/lib/mail/mailboxImportApi.ts +9 -15
- package/lib/mail/messageBodySanitizer.ts +47 -1
- package/lib/search/queryGrammar.ts +13 -4
- package/lib/search/searchTier3.ts +65 -32
- package/lib/tasks/tasksApi.ts +3 -3
- package/lib/util/api.ts +99 -16
- package/lib/util/apiQuery.ts +13 -0
- package/lib/util/settleWithLimit.ts +25 -0
- package/package.json +1 -1
|
@@ -3,11 +3,11 @@
|
|
|
3
3
|
// SPDX-License-Identifier: MPL-2.0
|
|
4
4
|
///////////////////////////////////////////////////////////////////////////////
|
|
5
5
|
import React, { useEffect, useRef, useState } from "react";
|
|
6
|
-
import { ApiRequestError } from "../../../lib/util/api.js";
|
|
7
6
|
import { AuditLogEntry, AuditLogFilters, listAuditLog } from "../../../lib/admin/auditLogApi.js";
|
|
8
7
|
import AdminShell, { AdminShellProps } from "../../shared/components/admin/layout/AdminShell.js";
|
|
9
|
-
import Alert from "
|
|
8
|
+
import Alert from "../../shared/components/admin/ActionAlert.js";
|
|
10
9
|
import Button from "../../../lib/components/buttons/Button.js";
|
|
10
|
+
import { actionErrorMessage } from "../../shared/components/admin/elevation.js";
|
|
11
11
|
|
|
12
12
|
const PAGE_SIZE = 25;
|
|
13
13
|
/** How long typing in a filter box has to pause before the log is re-fetched. */
|
|
@@ -71,7 +71,7 @@ function AuditLogContent() {
|
|
|
71
71
|
if (!cancelled) setEntries(data);
|
|
72
72
|
})
|
|
73
73
|
.catch((err) => {
|
|
74
|
-
if (!cancelled) setError(err
|
|
74
|
+
if (!cancelled) setError(actionErrorMessage(err, "Could not load the audit log."));
|
|
75
75
|
})
|
|
76
76
|
.finally(() => {
|
|
77
77
|
if (!cancelled) setLoading(false);
|
|
@@ -3,11 +3,11 @@
|
|
|
3
3
|
// SPDX-License-Identifier: MPL-2.0
|
|
4
4
|
///////////////////////////////////////////////////////////////////////////////
|
|
5
5
|
import React, { useEffect, useState } from "react";
|
|
6
|
-
import { ApiRequestError } from "../../../lib/util/api.js";
|
|
7
6
|
import { Branding, getBranding } from "../../../lib/branding/brandingApi.js";
|
|
8
7
|
import AdminShell, { AdminShellProps } from "../../shared/components/admin/layout/AdminShell.js";
|
|
9
8
|
import BrandingForm from "../../shared/components/admin/settings/BrandingForm.js";
|
|
10
|
-
import Alert from "
|
|
9
|
+
import Alert from "../../shared/components/admin/ActionAlert.js";
|
|
10
|
+
import { actionErrorMessage } from "../../shared/components/admin/elevation.js";
|
|
11
11
|
|
|
12
12
|
export default function BrandingPage(props: Omit<AdminShellProps, "active">) {
|
|
13
13
|
return (
|
|
@@ -25,7 +25,7 @@ function BrandingContent() {
|
|
|
25
25
|
useEffect(() => {
|
|
26
26
|
getBranding()
|
|
27
27
|
.then(setBranding)
|
|
28
|
-
.catch((err) => setLoadError(err
|
|
28
|
+
.catch((err) => setLoadError(actionErrorMessage(err, "Could not load branding.")))
|
|
29
29
|
.finally(() => setLoading(false));
|
|
30
30
|
}, []);
|
|
31
31
|
|
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
// SPDX-License-Identifier: MPL-2.0
|
|
4
4
|
///////////////////////////////////////////////////////////////////////////////
|
|
5
5
|
import React, { ChangeEvent, FormEvent, useEffect, useRef, useState } from "react";
|
|
6
|
-
import {
|
|
6
|
+
import { actionErrorMessage } from "../../shared/components/admin/elevation.js";
|
|
7
7
|
import {
|
|
8
8
|
DataExportFormat,
|
|
9
9
|
createExportRequest,
|
|
@@ -24,7 +24,7 @@ import {
|
|
|
24
24
|
import { Folder, listFolders } from "../../../lib/mail/mailApi.js";
|
|
25
25
|
import AdminShell, { AdminShellProps } from "../../shared/components/admin/layout/AdminShell.js";
|
|
26
26
|
import { LoadMoreButton, usePagedList } from "../../shared/components/admin/usePagedList.js";
|
|
27
|
-
import Alert from "
|
|
27
|
+
import Alert from "../../shared/components/admin/ActionAlert.js";
|
|
28
28
|
import Button from "../../../lib/components/buttons/Button.js";
|
|
29
29
|
import Modal from "../../../lib/components/overlays/Modal.js";
|
|
30
30
|
|
|
@@ -90,7 +90,7 @@ function ExportRequestsSection() {
|
|
|
90
90
|
setMailboxUid("");
|
|
91
91
|
await list.reload();
|
|
92
92
|
} catch (err) {
|
|
93
|
-
setCreateError(err
|
|
93
|
+
setCreateError(actionErrorMessage(err, "Could not start this export."));
|
|
94
94
|
} finally {
|
|
95
95
|
setCreating(false);
|
|
96
96
|
}
|
|
@@ -185,7 +185,11 @@ function ImportRequestsSection() {
|
|
|
185
185
|
void list.reload();
|
|
186
186
|
}, []);
|
|
187
187
|
|
|
188
|
+
// Only the latest lookup's answer is applied: a slower answer for a mailbox typed earlier would otherwise list its folders beside the mailbox now named.
|
|
189
|
+
const folderLookup = useRef(0);
|
|
190
|
+
|
|
188
191
|
function handleLoadFolders() {
|
|
192
|
+
const lookup = ++folderLookup.current;
|
|
189
193
|
const uid = mailboxUid.trim();
|
|
190
194
|
setTargetFolderUid("");
|
|
191
195
|
setFolders([]);
|
|
@@ -195,11 +199,18 @@ function ImportRequestsSection() {
|
|
|
195
199
|
}
|
|
196
200
|
listFolders(uid)
|
|
197
201
|
.then((all) => {
|
|
202
|
+
if (lookup !== folderLookup.current) {
|
|
203
|
+
return;
|
|
204
|
+
}
|
|
198
205
|
const mailFolders = all.filter((f) => !NON_MAIL_FOLDER_TYPES.has(f.type));
|
|
199
206
|
setFolders(mailFolders);
|
|
200
207
|
setTargetFolderUid(mailFolders[0]?.uid ?? "");
|
|
201
208
|
})
|
|
202
|
-
.catch((err) =>
|
|
209
|
+
.catch((err) => {
|
|
210
|
+
if (lookup === folderLookup.current) {
|
|
211
|
+
setFolderError(actionErrorMessage(err, "Could not load this mailbox's folders."));
|
|
212
|
+
}
|
|
213
|
+
});
|
|
203
214
|
}
|
|
204
215
|
|
|
205
216
|
function handleFileChange(e: ChangeEvent<HTMLInputElement>) {
|
|
@@ -212,7 +223,7 @@ function ImportRequestsSection() {
|
|
|
212
223
|
setUploading(true);
|
|
213
224
|
uploadMailboxImport(file, { format: importFormatFromFilename(file.name), targetFolderUid, mailboxUid: mailboxUid.trim() })
|
|
214
225
|
.then(() => list.reload())
|
|
215
|
-
.catch((err) => setUploadError(err
|
|
226
|
+
.catch((err) => setUploadError(actionErrorMessage(err, "Could not upload this file.")))
|
|
216
227
|
.finally(() => setUploading(false));
|
|
217
228
|
}
|
|
218
229
|
|
|
@@ -345,7 +356,7 @@ function ErasureRequestsSection() {
|
|
|
345
356
|
closeApproveModal();
|
|
346
357
|
await list.reload();
|
|
347
358
|
} catch (err) {
|
|
348
|
-
setApproveError(err
|
|
359
|
+
setApproveError(actionErrorMessage(err, "Could not approve this request."));
|
|
349
360
|
} finally {
|
|
350
361
|
setApproving(false);
|
|
351
362
|
}
|
|
@@ -370,7 +381,7 @@ function ErasureRequestsSection() {
|
|
|
370
381
|
closeDenyModal();
|
|
371
382
|
await list.reload();
|
|
372
383
|
} catch (err) {
|
|
373
|
-
setDenyError(err
|
|
384
|
+
setDenyError(actionErrorMessage(err, "Could not deny this request."));
|
|
374
385
|
} finally {
|
|
375
386
|
setDenying(false);
|
|
376
387
|
}
|
|
@@ -3,11 +3,11 @@
|
|
|
3
3
|
// SPDX-License-Identifier: MPL-2.0
|
|
4
4
|
///////////////////////////////////////////////////////////////////////////////
|
|
5
5
|
import React, { useEffect, useState } from "react";
|
|
6
|
-
import { ApiRequestError } from "../../../lib/util/api.js";
|
|
7
6
|
import { DistributionList, getDistributionList } from "../../../lib/admin/distributionListsApi.js";
|
|
8
7
|
import AdminShell, { AdminShellProps } from "../../shared/components/admin/layout/AdminShell.js";
|
|
9
8
|
import MemberListCard from "../../shared/components/admin/distributionLists/MemberListCard.js";
|
|
10
|
-
import Alert from "
|
|
9
|
+
import Alert from "../../shared/components/admin/ActionAlert.js";
|
|
10
|
+
import { actionErrorMessage } from "../../shared/components/admin/elevation.js";
|
|
11
11
|
|
|
12
12
|
export default function DistributionListDetailPage(props: Omit<AdminShellProps, "active"> & { params: { uid: string } }) {
|
|
13
13
|
return (
|
|
@@ -27,7 +27,7 @@ function DistributionListDetailContent({ uid }: { uid: string }) {
|
|
|
27
27
|
setError(null);
|
|
28
28
|
getDistributionList(uid)
|
|
29
29
|
.then(setList)
|
|
30
|
-
.catch((err) => setError(err
|
|
30
|
+
.catch((err) => setError(actionErrorMessage(err, "Could not load this distribution list.")))
|
|
31
31
|
.finally(() => setLoading(false));
|
|
32
32
|
}, [uid]);
|
|
33
33
|
|
|
@@ -3,11 +3,11 @@
|
|
|
3
3
|
// SPDX-License-Identifier: MPL-2.0
|
|
4
4
|
///////////////////////////////////////////////////////////////////////////////
|
|
5
5
|
import React, { useEffect, useState } from "react";
|
|
6
|
-
import { ApiRequestError } from "../../../lib/util/api.js";
|
|
7
6
|
import { DistributionList, listDistributionLists } from "../../../lib/admin/distributionListsApi.js";
|
|
8
7
|
import AdminShell, { AdminShellProps } from "../../shared/components/admin/layout/AdminShell.js";
|
|
9
|
-
import Alert from "
|
|
8
|
+
import Alert from "../../shared/components/admin/ActionAlert.js";
|
|
10
9
|
import Button from "../../../lib/components/buttons/Button.js";
|
|
10
|
+
import { actionErrorMessage } from "../../shared/components/admin/elevation.js";
|
|
11
11
|
|
|
12
12
|
const PAGE_SIZE = 25;
|
|
13
13
|
|
|
@@ -30,7 +30,7 @@ function DistributionListsContent() {
|
|
|
30
30
|
setError(null);
|
|
31
31
|
listDistributionLists({ page, limit: PAGE_SIZE })
|
|
32
32
|
.then(setLists)
|
|
33
|
-
.catch((err) => setError(err
|
|
33
|
+
.catch((err) => setError(actionErrorMessage(err, "Could not load distribution lists.")))
|
|
34
34
|
.finally(() => setLoading(false));
|
|
35
35
|
}, [page]);
|
|
36
36
|
|
|
@@ -4,12 +4,12 @@
|
|
|
4
4
|
///////////////////////////////////////////////////////////////////////////////
|
|
5
5
|
import React, { FormEvent, useState } from "react";
|
|
6
6
|
import { useRouter } from "@rapidrest/react/client";
|
|
7
|
-
import { ApiRequestError } from "../../../../lib/util/api.js";
|
|
8
7
|
import { createDistributionList } from "../../../../lib/admin/distributionListsApi.js";
|
|
9
8
|
import AdminShell, { AdminShellProps } from "../../../shared/components/admin/layout/AdminShell.js";
|
|
10
|
-
import Alert from "
|
|
9
|
+
import Alert from "../../../shared/components/admin/ActionAlert.js";
|
|
11
10
|
import Button from "../../../../lib/components/buttons/Button.js";
|
|
12
11
|
import FormField from "../../../../lib/components/forms/FormField.js";
|
|
12
|
+
import { actionErrorMessage } from "../../../shared/components/admin/elevation.js";
|
|
13
13
|
|
|
14
14
|
const INPUT_CLASS =
|
|
15
15
|
"w-full text-sm py-2.5 px-3 border border-border rounded-sm bg-surface text-text focus:outline-none focus:border-primary";
|
|
@@ -52,7 +52,7 @@ function NewDistributionListForm() {
|
|
|
52
52
|
});
|
|
53
53
|
void navigate(`/admin/distribution-lists/${encodeURIComponent(list.uid)}`);
|
|
54
54
|
} catch (err) {
|
|
55
|
-
setError(err
|
|
55
|
+
setError(actionErrorMessage(err, "Could not create the distribution list."));
|
|
56
56
|
} finally {
|
|
57
57
|
setSaving(false);
|
|
58
58
|
}
|
|
@@ -4,14 +4,14 @@
|
|
|
4
4
|
///////////////////////////////////////////////////////////////////////////////
|
|
5
5
|
import React, { useState } from "react";
|
|
6
6
|
import { useRouter } from "@rapidrest/react/client";
|
|
7
|
-
import { ApiRequestError } from "../../../lib/util/api.js";
|
|
8
7
|
import { deleteDomain, Domain, updateDomain } from "../../../lib/admin/domainsApi.js";
|
|
9
8
|
import AdminShell, { AdminShellProps } from "../../shared/components/admin/layout/AdminShell.js";
|
|
10
9
|
import DomainDnsSetup from "../../shared/components/admin/settings/DomainDnsSetup.js";
|
|
11
|
-
import Alert from "
|
|
10
|
+
import Alert from "../../shared/components/admin/ActionAlert.js";
|
|
12
11
|
import Button from "../../../lib/components/buttons/Button.js";
|
|
13
12
|
import FormField from "../../../lib/components/forms/FormField.js";
|
|
14
13
|
import Modal from "../../../lib/components/overlays/Modal.js";
|
|
14
|
+
import { actionErrorMessage } from "../../shared/components/admin/elevation.js";
|
|
15
15
|
|
|
16
16
|
const INPUT_CLASS =
|
|
17
17
|
"w-full text-sm py-2.5 px-3 border border-border rounded-sm bg-surface text-text focus:outline-none focus:border-primary";
|
|
@@ -52,7 +52,7 @@ function DomainDetailContent({ uid }: { uid: string }) {
|
|
|
52
52
|
await deleteDomain(domain!.uid, domain!.version);
|
|
53
53
|
void navigate("/admin/domains");
|
|
54
54
|
} catch (err) {
|
|
55
|
-
setDeleteError(err
|
|
55
|
+
setDeleteError(actionErrorMessage(err, "Could not delete this domain."));
|
|
56
56
|
setDeleting(false);
|
|
57
57
|
}
|
|
58
58
|
}
|
|
@@ -62,18 +62,19 @@ function DomainDetailContent({ uid }: { uid: string }) {
|
|
|
62
62
|
setAliasInput((current) => (current === null ? d?.aliasOf ?? "" : current));
|
|
63
63
|
}
|
|
64
64
|
|
|
65
|
+
// A blank input is sent as "" (the server's way to clear an alias): an absent key (what `undefined` becomes in JSON) leaves the stored alias alone.
|
|
65
66
|
async function handleSaveAlias() {
|
|
66
67
|
setSavingAlias(true);
|
|
67
68
|
setAliasError(null);
|
|
68
69
|
setAliasSaved(false);
|
|
69
70
|
try {
|
|
70
|
-
const updated = await updateDomain({ uid: domain!.uid, version: domain!.version, aliasOf: aliasInput!.trim()
|
|
71
|
+
const updated = await updateDomain({ uid: domain!.uid, version: domain!.version, aliasOf: aliasInput!.trim() });
|
|
71
72
|
setDomain(updated);
|
|
72
73
|
setAliasInput(updated.aliasOf ?? "");
|
|
73
74
|
setAliasSaved(true);
|
|
74
75
|
setRefreshCount((c) => c + 1);
|
|
75
76
|
} catch (err) {
|
|
76
|
-
setAliasError(err
|
|
77
|
+
setAliasError(actionErrorMessage(err, "Could not update this domain."));
|
|
77
78
|
} finally {
|
|
78
79
|
setSavingAlias(false);
|
|
79
80
|
}
|
|
@@ -3,11 +3,11 @@
|
|
|
3
3
|
// SPDX-License-Identifier: MPL-2.0
|
|
4
4
|
///////////////////////////////////////////////////////////////////////////////
|
|
5
5
|
import React, { useEffect, useState } from "react";
|
|
6
|
-
import { ApiRequestError } from "../../../lib/util/api.js";
|
|
7
6
|
import { Domain, listDomains } from "../../../lib/admin/domainsApi.js";
|
|
8
7
|
import AdminShell, { AdminShellProps } from "../../shared/components/admin/layout/AdminShell.js";
|
|
9
|
-
import Alert from "
|
|
8
|
+
import Alert from "../../shared/components/admin/ActionAlert.js";
|
|
10
9
|
import Button from "../../../lib/components/buttons/Button.js";
|
|
10
|
+
import { actionErrorMessage } from "../../shared/components/admin/elevation.js";
|
|
11
11
|
|
|
12
12
|
const PAGE_SIZE = 25;
|
|
13
13
|
|
|
@@ -30,7 +30,7 @@ function DomainsListContent() {
|
|
|
30
30
|
setError(null);
|
|
31
31
|
listDomains({ page, limit: PAGE_SIZE })
|
|
32
32
|
.then(setDomains)
|
|
33
|
-
.catch((err) => setError(err
|
|
33
|
+
.catch((err) => setError(actionErrorMessage(err, "Could not load domains.")))
|
|
34
34
|
.finally(() => setLoading(false));
|
|
35
35
|
}, [page]);
|
|
36
36
|
|
|
@@ -4,12 +4,12 @@
|
|
|
4
4
|
///////////////////////////////////////////////////////////////////////////////
|
|
5
5
|
import React, { FormEvent, useEffect, useState } from "react";
|
|
6
6
|
import { useRouter } from "@rapidrest/react/client";
|
|
7
|
-
import { ApiRequestError } from "../../../../lib/util/api.js";
|
|
8
7
|
import { createDomain, Domain, listDomains } from "../../../../lib/admin/domainsApi.js";
|
|
9
8
|
import AdminShell, { AdminShellProps } from "../../../shared/components/admin/layout/AdminShell.js";
|
|
10
|
-
import Alert from "
|
|
9
|
+
import Alert from "../../../shared/components/admin/ActionAlert.js";
|
|
11
10
|
import Button from "../../../../lib/components/buttons/Button.js";
|
|
12
11
|
import FormField from "../../../../lib/components/forms/FormField.js";
|
|
12
|
+
import { actionErrorMessage } from "../../../shared/components/admin/elevation.js";
|
|
13
13
|
|
|
14
14
|
const INPUT_CLASS =
|
|
15
15
|
"w-full text-sm py-2.5 px-3 border border-border rounded-sm bg-surface text-text focus:outline-none focus:border-primary";
|
|
@@ -52,7 +52,7 @@ function NewDomainForm() {
|
|
|
52
52
|
const domain = await createDomain({ name: name.trim(), aliasOf: aliasOf || undefined });
|
|
53
53
|
void navigate(`/admin/domains/${encodeURIComponent(domain.uid)}`);
|
|
54
54
|
} catch (err) {
|
|
55
|
-
setError(err
|
|
55
|
+
setError(actionErrorMessage(err, "Could not create the domain."));
|
|
56
56
|
} finally {
|
|
57
57
|
setSaving(false);
|
|
58
58
|
}
|
|
@@ -4,7 +4,6 @@
|
|
|
4
4
|
///////////////////////////////////////////////////////////////////////////////
|
|
5
5
|
import React, { FormEvent, useEffect, useState } from "react";
|
|
6
6
|
import { useRouter } from "@rapidrest/react/client";
|
|
7
|
-
import { ApiRequestError } from "../../../lib/util/api.js";
|
|
8
7
|
import { toDatetimeLocal } from "../../../lib/util/dateInput.js";
|
|
9
8
|
import {
|
|
10
9
|
deleteEscrowScope,
|
|
@@ -16,12 +15,14 @@ import {
|
|
|
16
15
|
import AdminShell, { AdminShellProps } from "../../shared/components/admin/layout/AdminShell.js";
|
|
17
16
|
import EscrowScopeKeyAndHoldersFields, {
|
|
18
17
|
EscrowScopeKeyAndHoldersValue,
|
|
18
|
+
keyValidityError,
|
|
19
19
|
selfAsHolderError,
|
|
20
20
|
} from "../../shared/components/admin/escrowScopes/EscrowScopeKeyAndHoldersFields.js";
|
|
21
|
-
import Alert from "
|
|
21
|
+
import Alert from "../../shared/components/admin/ActionAlert.js";
|
|
22
22
|
import Button from "../../../lib/components/buttons/Button.js";
|
|
23
23
|
import FormField from "../../../lib/components/forms/FormField.js";
|
|
24
24
|
import Modal from "../../../lib/components/overlays/Modal.js";
|
|
25
|
+
import { actionErrorMessage } from "../../shared/components/admin/elevation.js";
|
|
25
26
|
|
|
26
27
|
const INPUT_CLASS =
|
|
27
28
|
"w-full text-sm py-2.5 px-3 border border-border rounded-sm bg-surface text-text focus:outline-none focus:border-primary";
|
|
@@ -145,7 +146,7 @@ function EscrowScopeDetailContent({ uid, adminUid }: { uid: string; adminUid?: s
|
|
|
145
146
|
setFields(toFieldsValue(loaded));
|
|
146
147
|
}
|
|
147
148
|
})
|
|
148
|
-
.catch((err) => setError(err
|
|
149
|
+
.catch((err) => setError(actionErrorMessage(err, "Could not load this escrow scope.")))
|
|
149
150
|
.finally(() => setLoading(false));
|
|
150
151
|
}, [uid]);
|
|
151
152
|
|
|
@@ -165,6 +166,11 @@ function EscrowScopeDetailContent({ uid, adminUid }: { uid: string; adminUid?: s
|
|
|
165
166
|
setError("The public key, its type, and its fingerprint are all required.");
|
|
166
167
|
return;
|
|
167
168
|
}
|
|
169
|
+
const validityError = keyValidityError(fields!);
|
|
170
|
+
if (validityError) {
|
|
171
|
+
setError(validityError);
|
|
172
|
+
return;
|
|
173
|
+
}
|
|
168
174
|
if (fields!.holderUserUids.length === 0) {
|
|
169
175
|
setError("At least one holder is required.");
|
|
170
176
|
return;
|
|
@@ -208,7 +214,7 @@ function EscrowScopeDetailContent({ uid, adminUid }: { uid: string; adminUid?: s
|
|
|
208
214
|
setFields(toFieldsValue(updated));
|
|
209
215
|
setSaved(true);
|
|
210
216
|
} catch (err) {
|
|
211
|
-
setError(err
|
|
217
|
+
setError(actionErrorMessage(err, "Could not save this escrow scope."));
|
|
212
218
|
} finally {
|
|
213
219
|
setSaving(false);
|
|
214
220
|
}
|
|
@@ -231,7 +237,7 @@ function EscrowScopeDetailContent({ uid, adminUid }: { uid: string; adminUid?: s
|
|
|
231
237
|
} catch (err) {
|
|
232
238
|
// Most commonly a 409 ("referenced by an existing Matter") — see `deleteEscrowScope()`'s own
|
|
233
239
|
// doc comment - surfaced as-is rather than special-cased.
|
|
234
|
-
setDeleteError(err
|
|
240
|
+
setDeleteError(actionErrorMessage(err, "Could not delete this escrow scope."));
|
|
235
241
|
setDeleting(false);
|
|
236
242
|
}
|
|
237
243
|
}
|
|
@@ -3,11 +3,11 @@
|
|
|
3
3
|
// SPDX-License-Identifier: MPL-2.0
|
|
4
4
|
///////////////////////////////////////////////////////////////////////////////
|
|
5
5
|
import React, { useEffect, useState } from "react";
|
|
6
|
-
import { ApiRequestError } from "../../../lib/util/api.js";
|
|
7
6
|
import { EscrowScope, listEscrowScopes } from "../../../lib/admin/escrowScopesApi.js";
|
|
8
7
|
import AdminShell, { AdminShellProps } from "../../shared/components/admin/layout/AdminShell.js";
|
|
9
|
-
import Alert from "
|
|
8
|
+
import Alert from "../../shared/components/admin/ActionAlert.js";
|
|
10
9
|
import Button from "../../../lib/components/buttons/Button.js";
|
|
10
|
+
import { actionErrorMessage } from "../../shared/components/admin/elevation.js";
|
|
11
11
|
|
|
12
12
|
const PAGE_SIZE = 25;
|
|
13
13
|
|
|
@@ -30,7 +30,7 @@ function EscrowScopesContent() {
|
|
|
30
30
|
setError(null);
|
|
31
31
|
listEscrowScopes({ page, limit: PAGE_SIZE })
|
|
32
32
|
.then(setScopes)
|
|
33
|
-
.catch((err) => setError(err
|
|
33
|
+
.catch((err) => setError(actionErrorMessage(err, "Could not load escrow scopes.")))
|
|
34
34
|
.finally(() => setLoading(false));
|
|
35
35
|
}, [page]);
|
|
36
36
|
|
|
@@ -4,16 +4,17 @@
|
|
|
4
4
|
///////////////////////////////////////////////////////////////////////////////
|
|
5
5
|
import React, { FormEvent, useState } from "react";
|
|
6
6
|
import { useRouter } from "@rapidrest/react/client";
|
|
7
|
-
import { ApiRequestError } from "../../../../lib/util/api.js";
|
|
8
7
|
import { createEscrowScope } from "../../../../lib/admin/escrowScopesApi.js";
|
|
9
8
|
import AdminShell, { AdminShellProps } from "../../../shared/components/admin/layout/AdminShell.js";
|
|
10
9
|
import EscrowScopeKeyAndHoldersFields, {
|
|
11
10
|
emptyEscrowScopeKeyAndHoldersValue,
|
|
11
|
+
keyValidityError,
|
|
12
12
|
selfAsHolderError,
|
|
13
13
|
} from "../../../shared/components/admin/escrowScopes/EscrowScopeKeyAndHoldersFields.js";
|
|
14
|
-
import Alert from "
|
|
14
|
+
import Alert from "../../../shared/components/admin/ActionAlert.js";
|
|
15
15
|
import Button from "../../../../lib/components/buttons/Button.js";
|
|
16
16
|
import FormField from "../../../../lib/components/forms/FormField.js";
|
|
17
|
+
import { actionErrorMessage } from "../../../shared/components/admin/elevation.js";
|
|
17
18
|
|
|
18
19
|
const INPUT_CLASS =
|
|
19
20
|
"w-full text-sm py-2.5 px-3 border border-border rounded-sm bg-surface text-text focus:outline-none focus:border-primary";
|
|
@@ -46,6 +47,11 @@ function NewEscrowScopeForm({ adminUid }: { adminUid?: string }) {
|
|
|
46
47
|
setError("The public key, its type, and its fingerprint are all required.");
|
|
47
48
|
return;
|
|
48
49
|
}
|
|
50
|
+
const validityError = keyValidityError(keyAndHolders);
|
|
51
|
+
if (validityError) {
|
|
52
|
+
setError(validityError);
|
|
53
|
+
return;
|
|
54
|
+
}
|
|
49
55
|
if (keyAndHolders.holderUserUids.length === 0) {
|
|
50
56
|
setError("At least one holder is required.");
|
|
51
57
|
return;
|
|
@@ -78,7 +84,7 @@ function NewEscrowScopeForm({ adminUid }: { adminUid?: string }) {
|
|
|
78
84
|
});
|
|
79
85
|
void navigate(`/admin/escrow-scopes/${encodeURIComponent(created.uid)}`);
|
|
80
86
|
} catch (err) {
|
|
81
|
-
setError(err
|
|
87
|
+
setError(actionErrorMessage(err, "Could not create the escrow scope."));
|
|
82
88
|
} finally {
|
|
83
89
|
setSaving(false);
|
|
84
90
|
}
|
package/apps/admin/index.tsx
CHANGED
|
@@ -4,15 +4,15 @@
|
|
|
4
4
|
///////////////////////////////////////////////////////////////////////////////
|
|
5
5
|
import React, { useEffect, useState } from "react";
|
|
6
6
|
import { useRouter } from "@rapidrest/react/client";
|
|
7
|
-
import { ApiRequestError } from "../../lib/util/api.js";
|
|
8
7
|
import { listMailboxes, Mailbox } from "../../lib/mail/mailApi.js";
|
|
9
8
|
import { reopenSetup } from "../../lib/admin/setupApi.js";
|
|
10
9
|
import AdminShell, { AdminShellProps } from "../shared/components/admin/layout/AdminShell.js";
|
|
11
10
|
import LeftoverMailboxesSection from "../shared/components/admin/mailboxes/LeftoverMailboxesSection.js";
|
|
12
11
|
import MailboxTable from "../shared/components/admin/mailboxes/MailboxTable.js";
|
|
13
|
-
import Alert from "
|
|
12
|
+
import Alert from "../shared/components/admin/ActionAlert.js";
|
|
14
13
|
import Button from "../../lib/components/buttons/Button.js";
|
|
15
14
|
import Modal from "../../lib/components/overlays/Modal.js";
|
|
15
|
+
import { actionErrorMessage } from "../shared/components/admin/elevation.js";
|
|
16
16
|
|
|
17
17
|
const PAGE_SIZE = 25;
|
|
18
18
|
|
|
@@ -37,7 +37,7 @@ function MailboxesListContent() {
|
|
|
37
37
|
// The administration scope: every mailbox as administrative metadata - the console never shows anybody's mail.
|
|
38
38
|
listMailboxes({ page, limit: PAGE_SIZE, scope: "admin" })
|
|
39
39
|
.then(setMailboxes)
|
|
40
|
-
.catch((err) => setError(err
|
|
40
|
+
.catch((err) => setError(actionErrorMessage(err, "Could not load mailboxes.")))
|
|
41
41
|
.finally(() => setLoading(false));
|
|
42
42
|
}, [page]);
|
|
43
43
|
|
|
@@ -51,7 +51,7 @@ function MailboxesListContent() {
|
|
|
51
51
|
await reopenSetup();
|
|
52
52
|
void navigate("/admin/setup");
|
|
53
53
|
} catch (err) {
|
|
54
|
-
setError(err
|
|
54
|
+
setError(actionErrorMessage(err, "Could not reopen setup."));
|
|
55
55
|
setReopening(false);
|
|
56
56
|
setConfirmingSetup(false);
|
|
57
57
|
}
|
|
@@ -3,11 +3,11 @@
|
|
|
3
3
|
// SPDX-License-Identifier: MPL-2.0
|
|
4
4
|
///////////////////////////////////////////////////////////////////////////////
|
|
5
5
|
import React, { useEffect, useState } from "react";
|
|
6
|
-
import { ApiRequestError } from "../../../lib/util/api.js";
|
|
7
6
|
import { IngestQueueEntry, listIngestQueue } from "../../../lib/mail/mailApi.js";
|
|
8
7
|
import AdminShell, { AdminShellProps } from "../../shared/components/admin/layout/AdminShell.js";
|
|
9
|
-
import Alert from "
|
|
8
|
+
import Alert from "../../shared/components/admin/ActionAlert.js";
|
|
10
9
|
import Button from "../../../lib/components/buttons/Button.js";
|
|
10
|
+
import { actionErrorMessage } from "../../shared/components/admin/elevation.js";
|
|
11
11
|
|
|
12
12
|
const PAGE_SIZE = 25;
|
|
13
13
|
|
|
@@ -56,7 +56,7 @@ function IngestQueueContent() {
|
|
|
56
56
|
if (!cancelled) setEntries(data);
|
|
57
57
|
})
|
|
58
58
|
.catch((err) => {
|
|
59
|
-
if (!cancelled) setError(err
|
|
59
|
+
if (!cancelled) setError(actionErrorMessage(err, "Could not load the ingest queue."));
|
|
60
60
|
})
|
|
61
61
|
.finally(() => {
|
|
62
62
|
if (!cancelled) setLoading(false);
|
|
@@ -4,13 +4,14 @@
|
|
|
4
4
|
///////////////////////////////////////////////////////////////////////////////
|
|
5
5
|
import React, { useEffect, useState } from "react";
|
|
6
6
|
import { useRouter } from "@rapidrest/react/client";
|
|
7
|
-
import { ApiRequestError } from "../../../lib/util/api.js";
|
|
8
7
|
import { deleteMailbox, getMailbox, impersonateUser, Mailbox } from "../../../lib/mail/mailApi.js";
|
|
9
8
|
import AdminShell, { AdminShellProps } from "../../shared/components/admin/layout/AdminShell.js";
|
|
9
|
+
import { actionErrorMessage } from "../../shared/components/admin/elevation.js";
|
|
10
|
+
import { resetNotifications } from "../../shared/notifications/store.js";
|
|
10
11
|
import ShareAccessCard from "../../shared/components/admin/mailboxes/ShareAccessCard.js";
|
|
11
12
|
import ResourceSettingsCard from "../../shared/components/admin/mailboxes/ResourceSettingsCard.js";
|
|
12
13
|
import EscrowScopeCard from "../../shared/components/admin/mailboxes/EscrowScopeCard.js";
|
|
13
|
-
import Alert from "
|
|
14
|
+
import Alert from "../../shared/components/admin/ActionAlert.js";
|
|
14
15
|
import Button from "../../../lib/components/buttons/Button.js";
|
|
15
16
|
import { describeTimeZone } from "../../../lib/util/timeZone.js";
|
|
16
17
|
import Modal from "../../../lib/components/overlays/Modal.js";
|
|
@@ -64,9 +65,11 @@ function MailboxDetailContent({
|
|
|
64
65
|
setAccessError(null);
|
|
65
66
|
try {
|
|
66
67
|
await impersonateUser(impersonationBaseUrl ?? "", mailbox!.ownerUserUid!);
|
|
68
|
+
// The administrator's own notification history is not the impersonated user's to read.
|
|
69
|
+
resetNotifications();
|
|
67
70
|
window.location.href = "/";
|
|
68
71
|
} catch (err) {
|
|
69
|
-
setAccessError(err
|
|
72
|
+
setAccessError(actionErrorMessage(err, "Could not impersonate this user."));
|
|
70
73
|
setImpersonating(false);
|
|
71
74
|
}
|
|
72
75
|
}
|
|
@@ -92,19 +95,24 @@ function MailboxDetailContent({
|
|
|
92
95
|
// Most commonly a 409 if this mailbox is a custodian on an open legal hold (restapi's own
|
|
93
96
|
// `assertNotOnLegalHold()`, naming the blocking Matter uid(s)) - surfaced as-is, same as
|
|
94
97
|
// every other destructive-action error in this codebase, rather than special-cased here.
|
|
95
|
-
setDeleteError(err
|
|
98
|
+
setDeleteError(actionErrorMessage(err, "Could not delete this mailbox."));
|
|
96
99
|
setDeleting(false);
|
|
97
100
|
}
|
|
98
101
|
}
|
|
99
102
|
|
|
100
103
|
useEffect(() => {
|
|
104
|
+
// An answer for a mailbox since replaced (another uid) must not be shown as the current one: the delete and impersonate actions act on what is shown.
|
|
105
|
+
let cancelled = false;
|
|
101
106
|
setLoading(true);
|
|
102
107
|
setError(null);
|
|
103
108
|
// The administration scope: administrative metadata only - the console never shows a mailbox's mail or settings.
|
|
104
109
|
getMailbox(uid, { scope: "admin" })
|
|
105
|
-
.then(setMailbox)
|
|
106
|
-
.catch((err) => setError(err
|
|
107
|
-
.finally(() => setLoading(false));
|
|
110
|
+
.then((loaded) => !cancelled && setMailbox(loaded))
|
|
111
|
+
.catch((err) => !cancelled && setError(actionErrorMessage(err, "Could not load this mailbox.")))
|
|
112
|
+
.finally(() => !cancelled && setLoading(false));
|
|
113
|
+
return () => {
|
|
114
|
+
cancelled = true;
|
|
115
|
+
};
|
|
108
116
|
}, [uid]);
|
|
109
117
|
|
|
110
118
|
if (loading) {
|
|
@@ -3,12 +3,12 @@
|
|
|
3
3
|
// SPDX-License-Identifier: MPL-2.0
|
|
4
4
|
///////////////////////////////////////////////////////////////////////////////
|
|
5
5
|
import React, { useEffect, useState } from "react";
|
|
6
|
-
import { ApiRequestError } from "../../../lib/util/api.js";
|
|
7
6
|
import { listQuarantine, QuarantineEntry, releaseQuarantineEntry } from "../../../lib/mail/mailApi.js";
|
|
8
7
|
import AdminShell, { AdminShellProps } from "../../shared/components/admin/layout/AdminShell.js";
|
|
9
|
-
import Alert from "
|
|
8
|
+
import Alert from "../../shared/components/admin/ActionAlert.js";
|
|
10
9
|
import Button from "../../../lib/components/buttons/Button.js";
|
|
11
10
|
import Modal from "../../../lib/components/overlays/Modal.js";
|
|
11
|
+
import { actionErrorMessage } from "../../shared/components/admin/elevation.js";
|
|
12
12
|
|
|
13
13
|
const PAGE_SIZE = 25;
|
|
14
14
|
|
|
@@ -45,7 +45,7 @@ function QuarantineContent({ userUid }: { userUid?: string }) {
|
|
|
45
45
|
// The administration scope: any mailbox's held mail, recorded in the audit log.
|
|
46
46
|
listQuarantine(uid, { page, limit: PAGE_SIZE, scope: "admin" })
|
|
47
47
|
.then(setEntries)
|
|
48
|
-
.catch((err) => setError(err
|
|
48
|
+
.catch((err) => setError(actionErrorMessage(err, "Could not load quarantine.")))
|
|
49
49
|
.finally(() => setLoading(false));
|
|
50
50
|
}
|
|
51
51
|
|
|
@@ -74,7 +74,7 @@ function QuarantineContent({ userUid }: { userUid?: string }) {
|
|
|
74
74
|
closeReleaseModal();
|
|
75
75
|
reload(mailboxUid!);
|
|
76
76
|
} catch (err) {
|
|
77
|
-
setReleaseError(err
|
|
77
|
+
setReleaseError(actionErrorMessage(err, "Could not mark this message released."));
|
|
78
78
|
} finally {
|
|
79
79
|
setReleasing(false);
|
|
80
80
|
}
|
|
@@ -3,11 +3,11 @@
|
|
|
3
3
|
// SPDX-License-Identifier: MPL-2.0
|
|
4
4
|
///////////////////////////////////////////////////////////////////////////////
|
|
5
5
|
import React, { useEffect, useState } from "react";
|
|
6
|
-
import { ApiRequestError } from "../../../lib/util/api.js";
|
|
7
6
|
import { RetentionPolicy, getRetentionPolicy } from "../../../lib/admin/retentionPolicyApi.js";
|
|
8
7
|
import AdminShell, { AdminShellProps } from "../../shared/components/admin/layout/AdminShell.js";
|
|
9
8
|
import RetentionPolicyForm from "../../shared/components/admin/settings/RetentionPolicyForm.js";
|
|
10
|
-
import Alert from "
|
|
9
|
+
import Alert from "../../shared/components/admin/ActionAlert.js";
|
|
10
|
+
import { actionErrorMessage } from "../../shared/components/admin/elevation.js";
|
|
11
11
|
|
|
12
12
|
export default function RetentionPolicyPage(props: Omit<AdminShellProps, "active">) {
|
|
13
13
|
return (
|
|
@@ -25,7 +25,7 @@ function RetentionPolicyContent() {
|
|
|
25
25
|
useEffect(() => {
|
|
26
26
|
getRetentionPolicy()
|
|
27
27
|
.then(setPolicy)
|
|
28
|
-
.catch((err) => setLoadError(err
|
|
28
|
+
.catch((err) => setLoadError(actionErrorMessage(err, "Could not load the retention policy.")))
|
|
29
29
|
.finally(() => setLoading(false));
|
|
30
30
|
}, []);
|
|
31
31
|
|