Merge branch 'pass-lifetime-fixes' into 'main'
[ProtonMail-WebClient.git] / packages / components / containers / contacts / modals / ContactDeleteModal.tsx
blob132bb98c21f4db303d3e5e6e999106b93ba8f45a
1 import { c, msgid } from 'ttag';
3 import { Button } from '@proton/atoms';
4 import Alert from '@proton/components/components/alert/Alert';
5 import ErrorButton from '@proton/components/components/button/ErrorButton';
6 import type { ModalProps } from '@proton/components/components/modalTwo/Modal';
7 import Prompt from '@proton/components/components/prompt/Prompt';
8 import useApi from '@proton/components/hooks/useApi';
9 import useEventManager from '@proton/components/hooks/useEventManager';
10 import useNotifications from '@proton/components/hooks/useNotifications';
11 import { useLoading } from '@proton/hooks';
12 import { useContacts } from '@proton/mail/contacts/hooks';
13 import { clearContacts, deleteContacts } from '@proton/shared/lib/api/contacts';
14 import { allSucceded } from '@proton/shared/lib/api/helpers/response';
15 import { wait } from '@proton/shared/lib/helpers/promise';
16 import type { Contact } from '@proton/shared/lib/interfaces/contacts';
18 import { getDeleteText } from '../../general/helper';
20 export interface ContactDeleteProps {
21     contactIDs: string[];
22     deleteAll?: boolean;
23     onDelete?: () => void;
26 type Props = ContactDeleteProps & ModalProps;
28 const ContactDeleteModal = ({ contactIDs = [], deleteAll, onDelete, ...rest }: Props) => {
29     const api = useApi();
30     const { createNotification } = useNotifications();
31     const { call } = useEventManager();
32     const [loadingDelete, withLoadingDelete] = useLoading();
33     const [contacts = []] = useContacts();
35     const handleDelete = async () => {
36         // Call the callback and close the modal and wait a bit to trigger the event manager
37         // In order eventual contact view can be closed and will not try to request the contact
38         const delayedClosing = async () => {
39             onDelete?.();
40             rest.onClose?.();
41             await wait(1000);
42             await call();
43         };
45         if (deleteAll) {
46             await api(clearContacts());
47             void delayedClosing();
48             return createNotification({ text: c('Success').t`Contacts deleted` });
49         }
50         const apiSuccess = allSucceded(await api(deleteContacts(contactIDs)));
51         void delayedClosing();
52         if (!apiSuccess) {
53             return createNotification({ text: c('Error').t`Some contacts could not be deleted`, type: 'warning' });
54         }
55         createNotification({
56             text: c('Success').ngettext(msgid`Contact deleted`, `Contacts deleted`, contactIDs.length),
57         });
58     };
60     const count = contactIDs.length;
61     const contact = contacts.find((contact: Contact) => contact.ID === contactIDs[0]);
62     const Name = contact?.Name || contact?.ContactEmails?.[0]?.Email || '';
63     const title =
64         count === 1
65             ? getDeleteText(Name)
66             : c('Title').ngettext(msgid`Delete ${count} contact`, `Delete ${count} contacts`, count);
68     const text =
69         count === 1
70             ? c('Warning').t`Are you sure you want to permanently delete this contact?`
71             : c('Warning').ngettext(
72                   msgid`Are you sure you want to permanently delete ${count} contact?`,
73                   `Are you sure you want to permanently delete ${count} contacts?`,
74                   count
75               );
77     return (
78         <Prompt
79             title={
80                 <div className="text-ellipsis" title={title}>
81                     {title}
82                 </div>
83             }
84             buttons={[
85                 <ErrorButton
86                     data-testid="delete-button"
87                     onClick={() => withLoadingDelete(handleDelete())}
88                     loading={loadingDelete}
89                 >{c('Action').t`Delete`}</ErrorButton>,
90                 <Button onClick={rest.onClose} autoFocus>{c('Action').t`Cancel`}</Button>,
91             ]}
92             {...rest}
93         >
94             <Alert className="mb-4" type="error">
95                 {text}
96             </Alert>
97         </Prompt>
98     );
101 export default ContactDeleteModal;