Cleanup - unused files / unused exports / duplicate exports
[ProtonMail-WebClient.git] / packages / components / containers / organization / useOrganizationUnprivatizationModals.tsx
blob90f1fb284081cedab4a94d918a2fc175791a1d5e
1 import { c, msgid } from 'ttag';
3 import { deleteMembers } from '@proton/account/members/actions';
4 import { selectDisabledMembers } from '@proton/account/members/selectors';
5 import {
6     selectJoinedUnprivatizationState,
7     unprivatizeApprovalMembers,
8     unprivatizeMembersBackground,
9 } from '@proton/account/members/unprivatizeMembers';
10 import { useOrganizationKey } from '@proton/account/organizationKey/hooks';
11 import { Button } from '@proton/atoms';
12 import useModalState from '@proton/components/components/modalTwo/useModalState';
13 import Prompt, { type PromptProps } from '@proton/components/components/prompt/Prompt';
14 import useVerifyOutboundPublicKeys from '@proton/components/containers/keyTransparency/useVerifyOutboundPublicKeys';
15 import useNotifications from '@proton/components/hooks/useNotifications';
16 import useLoading from '@proton/hooks/useLoading';
17 import { useDispatch, useSelector } from '@proton/redux-shared-store';
18 import type { Member } from '@proton/shared/lib/interfaces';
20 import { MemberListBanner, MembersList } from './MemberListBanner';
22 interface Props extends Omit<PromptProps, 'children' | 'buttons'> {
23     members: Member[];
24     onConfirm: () => void;
27 const ConfirmDeleteMembers = ({ members, onConfirm, ...rest }: Props) => {
28     const n = members.length;
29     return (
30         <Prompt
31             title={c('sso').ngettext(msgid`Delete ${n} inactive user?`, `Delete ${n} inactive users?`, n)}
32             buttons={[
33                 <Button
34                     color="danger"
35                     onClick={() => {
36                         onConfirm();
37                         rest.onClose?.();
38                     }}
39                 >{c('Action').t`Delete`}</Button>,
40                 <Button onClick={rest.onClose}>{c('Action').t`Cancel`}</Button>,
41             ]}
42             {...rest}
43         >
44             {n === 1
45                 ? c('Info').t`This will permanently delete the data and all email addresses associated with this user.`
46                 : c('Info')
47                       .t`This will permanently delete the data and all email addresses associated with these users.`}
48         </Prompt>
49     );
52 const useOrganizationUnprivatizationModals = () => {
53     const [organizationKey] = useOrganizationKey();
55     const joinedUnprivatizationState = useSelector(selectJoinedUnprivatizationState);
56     const disabledMembers = useSelector(selectDisabledMembers);
57     const dispatch = useDispatch();
58     const verifyOutboundPublicKeys = useVerifyOutboundPublicKeys();
59     const [loadingDelete, withLoadingDelete] = useLoading();
60     const { createNotification } = useNotifications();
62     const unprivatizationApprovalInfo = (() => {
63         const membersToUnprivatize = joinedUnprivatizationState.approval.map(({ member }) => member);
64         if (!organizationKey?.privateKey || !membersToUnprivatize.length) {
65             return null;
66         }
67         const n = membersToUnprivatize.length;
68         return (
69             <MemberListBanner
70                 icon="info-circle"
71                 members={
72                     <>
73                         {c('sso').ngettext(
74                             msgid`${n} user has joined your organization through your Identity Provider. Review the account now:`,
75                             `${n} users have joined your organization through your Identity Provider. Review their accounts now:`,
76                             n
77                         )}
78                         <MembersList members={membersToUnprivatize} />
79                     </>
80                 }
81                 action={
82                     <Button
83                         size="small"
84                         loading={joinedUnprivatizationState.loading.approval}
85                         onClick={() => {
86                             dispatch(unprivatizeApprovalMembers({ membersToUnprivatize }));
87                         }}
88                     >
89                         {c('unprivatization').t`Approve all`}
90                     </Button>
91                 }
92             />
93         );
94     })();
96     const unprivatizationFailureInfo = (() => {
97         const membersToUnprivatize = joinedUnprivatizationState.failures.map(({ member }) => member);
98         if (!organizationKey?.privateKey || !membersToUnprivatize.length) {
99             return null;
100         }
101         const n = membersToUnprivatize.length;
102         return (
103             <MemberListBanner
104                 icon="exclamation-triangle-filled"
105                 members={
106                     <>
107                         {c('unprivatization').ngettext(
108                             msgid`Could not automatically enable administrator access for ${n} user, because their encryption keys have been updated in the meanwhile:`,
109                             `Could not automatically enable administrator access for ${n} users, because their encryption keys have been updated in the meanwhile:`,
110                             n
111                         )}
112                         <MembersList members={membersToUnprivatize} />
113                     </>
114                 }
115                 action={
116                     <Button
117                         size="small"
118                         loading={joinedUnprivatizationState.loading.automatic}
119                         onClick={() => {
120                             dispatch(
121                                 unprivatizeMembersBackground({
122                                     verifyOutboundPublicKeys,
123                                     target: {
124                                         type: 'action',
125                                         members: membersToUnprivatize,
126                                     },
127                                     options: {
128                                         ignoreRevisionCheck: true,
129                                     },
130                                 })
131                             );
132                         }}
133                     >
134                         {c('unprivatization').t`Enable manually`}
135                     </Button>
136                 }
137             />
138         );
139     })();
141     const [confirmDeleteProps, setConfirmDelete, renderConfirmDelete] = useModalState();
143     const disabledInfo = (() => {
144         if (!disabledMembers.length) {
145             return null;
146         }
147         const n = disabledMembers.length;
148         return (
149             <MemberListBanner
150                 icon="info-circle"
151                 members={
152                     <>
153                         {c('sso').ngettext(
154                             msgid`${n} user is inactive. You can safely remove this user from your organization.`,
155                             `${n} users are inactive. You can safely remove them from your organization.`,
156                             n
157                         )}
158                         <MembersList members={disabledMembers} />
159                     </>
160                 }
161                 action={
162                     <Button
163                         size="small"
164                         loading={loadingDelete}
165                         onClick={() => {
166                             setConfirmDelete(true);
167                         }}
168                     >
169                         {c('sso').ngettext(msgid`Delete ${n} user`, `Delete ${n} users`, n)}
170                     </Button>
171                 }
172             />
173         );
174     })();
176     const memberInfo = (
177         <>
178             {unprivatizationApprovalInfo}
179             {unprivatizationFailureInfo}
180             {disabledInfo}
182             {renderConfirmDelete && (
183                 <ConfirmDeleteMembers
184                     members={disabledMembers}
185                     onConfirm={() => {
186                         withLoadingDelete(
187                             dispatch(deleteMembers({ members: disabledMembers })).then((result) => {
188                                 if (result.success.length && !result.failure.length) {
189                                     confirmDeleteProps.onClose();
190                                     createNotification({
191                                         text: c('Info').t`All inactive members deleted`,
192                                     });
193                                 }
194                             })
195                         );
196                     }}
197                     {...confirmDeleteProps}
198                 />
199             )}
200         </>
201     );
203     return {
204         memberInfo,
205     };
208 export default useOrganizationUnprivatizationModals;