Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit bc28599

Browse files
committed
feat: add warning dialog when removing member from organization
1 parent c330af0 commit bc28599

File tree

3 files changed

+88
-52
lines changed

3 files changed

+88
-52
lines changed

site/src/pages/ManagementSettingsPage/CustomRolesPage/CustomRolesPage.tsx

+3-1
Original file line numberDiff line numberDiff line change
@@ -90,7 +90,9 @@ export const CustomRolesPage: FC = () => {
9090
onCancel={() => setRoleToDelete(undefined)}
9191
onConfirm={async () => {
9292
try {
93-
await deleteRoleMutation.mutateAsync(roleToDelete!.name);
93+
if (roleToDelete) {
94+
await deleteRoleMutation.mutateAsync(roleToDelete.name);
95+
}
9496
setRoleToDelete(undefined);
9597
await organizationRolesQuery.refetch();
9698
displaySuccess("Custom role deleted successfully!");

site/src/pages/ManagementSettingsPage/OrganizationMembersPage.tsx

+83-37
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,5 @@
1-
import {
2-
groupsByUserId,
3-
groupsByUserIdInOrganization,
4-
} from "api/queries/groups";
1+
import { getErrorMessage } from "api/errors";
2+
import { groupsByUserIdInOrganization } from "api/queries/groups";
53
import {
64
addOrganizationMember,
75
organizationMembers,
@@ -11,9 +9,12 @@ import {
119
} from "api/queries/organizations";
1210
import { organizationRoles } from "api/queries/roles";
1311
import type { OrganizationMemberWithUserData, User } from "api/typesGenerated";
12+
import { ConfirmDialog } from "components/Dialogs/ConfirmDialog/ConfirmDialog";
13+
import { displayError, displaySuccess } from "components/GlobalSnackbar/utils";
1414
import { Loader } from "components/Loader/Loader";
15+
import { Stack } from "components/Stack/Stack";
1516
import { useAuthenticated } from "contexts/auth/RequireAuth";
16-
import type { FC } from "react";
17+
import { type FC, useState } from "react";
1718
import { useMutation, useQuery, useQueryClient } from "react-query";
1819
import { useParams } from "react-router-dom";
1920
import { useOrganizationSettings } from "./ManagementSettingsLayout";
@@ -52,44 +53,89 @@ const OrganizationMembersPage: FC = () => {
5253
const organization = organizations?.find((o) => o.name === organizationName);
5354
const permissionsQuery = useQuery(organizationPermissions(organization?.id));
5455

56+
const [memberToDelete, setMemberToDelete] =
57+
useState<OrganizationMemberWithUserData>();
58+
5559
const permissions = permissionsQuery.data;
5660
if (!permissions) {
5761
return <Loader />;
5862
}
5963

6064
return (
61-
<OrganizationMembersPageView
62-
allAvailableRoles={organizationRolesQuery.data}
63-
canEditMembers={permissions.editMembers}
64-
error={
65-
membersQuery.error ??
66-
addMemberMutation.error ??
67-
removeMemberMutation.error ??
68-
updateMemberRolesMutation.error
69-
}
70-
isAddingMember={addMemberMutation.isLoading}
71-
isUpdatingMemberRoles={updateMemberRolesMutation.isLoading}
72-
me={me}
73-
members={members}
74-
groupsByUserId={groupsByUserIdQuery.data}
75-
addMember={async (user: User) => {
76-
await addMemberMutation.mutateAsync(user.id);
77-
void membersQuery.refetch();
78-
}}
79-
removeMember={async (member: OrganizationMemberWithUserData) => {
80-
await removeMemberMutation.mutateAsync(member.user_id);
81-
void membersQuery.refetch();
82-
}}
83-
updateMemberRoles={async (
84-
member: OrganizationMemberWithUserData,
85-
newRoles: string[],
86-
) => {
87-
await updateMemberRolesMutation.mutateAsync({
88-
userId: member.user_id,
89-
roles: newRoles,
90-
});
91-
}}
92-
/>
65+
<>
66+
<OrganizationMembersPageView
67+
allAvailableRoles={organizationRolesQuery.data}
68+
canEditMembers={permissions.editMembers}
69+
error={
70+
membersQuery.error ??
71+
addMemberMutation.error ??
72+
removeMemberMutation.error ??
73+
updateMemberRolesMutation.error
74+
}
75+
isAddingMember={addMemberMutation.isLoading}
76+
isUpdatingMemberRoles={updateMemberRolesMutation.isLoading}
77+
me={me}
78+
members={members}
79+
groupsByUserId={groupsByUserIdQuery.data}
80+
addMember={async (user: User) => {
81+
await addMemberMutation.mutateAsync(user.id);
82+
void membersQuery.refetch();
83+
}}
84+
removeMember={setMemberToDelete}
85+
updateMemberRoles={async (
86+
member: OrganizationMemberWithUserData,
87+
newRoles: string[],
88+
) => {
89+
await updateMemberRolesMutation.mutateAsync({
90+
userId: member.user_id,
91+
roles: newRoles,
92+
});
93+
}}
94+
/>
95+
96+
<ConfirmDialog
97+
type="delete"
98+
open={memberToDelete !== undefined}
99+
onClose={() => setMemberToDelete(undefined)}
100+
title="Remove member"
101+
confirmText="Remove"
102+
onConfirm={async () => {
103+
try {
104+
if (memberToDelete) {
105+
await removeMemberMutation.mutateAsync(memberToDelete?.user_id);
106+
}
107+
setMemberToDelete(undefined);
108+
await membersQuery.refetch();
109+
displaySuccess("User removed from organization successfully!");
110+
} catch (error) {
111+
setMemberToDelete(undefined);
112+
displayError(
113+
getErrorMessage(error, "Failed to remove user from organization"),
114+
);
115+
}
116+
}}
117+
description={
118+
<Stack>
119+
<p>
120+
Removing this member will also:
121+
<ul>
122+
<li>Remove them from all groups in this organization</li>
123+
<li>Remove all user role assignments</li>
124+
<li>
125+
Irreversibly orphan all their workspaces associated with this
126+
organization
127+
</li>
128+
</ul>
129+
</p>
130+
131+
<p>
132+
Are you sure you want to remove{" "}
133+
<strong>{memberToDelete?.username}</strong>?
134+
</p>
135+
</Stack>
136+
}
137+
/>
138+
</>
93139
);
94140
};
95141

site/src/pages/ManagementSettingsPage/OrganizationMembersPageView.tsx

+2-14
Original file line numberDiff line numberDiff line change
@@ -44,7 +44,7 @@ interface OrganizationMembersPageViewProps {
4444
members: Array<OrganizationMemberTableEntry> | undefined;
4545
groupsByUserId: GroupsByUserId | undefined;
4646
addMember: (user: User) => Promise<void>;
47-
removeMember: (member: OrganizationMemberWithUserData) => Promise<void>;
47+
removeMember: (member: OrganizationMemberWithUserData) => void;
4848
updateMemberRoles: (
4949
member: OrganizationMemberWithUserData,
5050
newRoles: string[],
@@ -135,19 +135,7 @@ export const OrganizationMembersPageView: FC<
135135
<MoreMenuContent>
136136
<MoreMenuItem
137137
danger
138-
onClick={async () => {
139-
try {
140-
await props.removeMember(member);
141-
displaySuccess("Member removed successfully.");
142-
} catch (error) {
143-
displayError(
144-
getErrorMessage(
145-
error,
146-
"Failed to remove member.",
147-
),
148-
);
149-
}
150-
}}
138+
onClick={() => props.removeMember(member)}
151139
>
152140
Remove
153141
</MoreMenuItem>

0 commit comments

Comments
 (0)