Skip to content

Commit 87d50f1

Browse files
chore(site): refactor groups to use react-query (coder#9701)
1 parent 161a3cf commit 87d50f1

File tree

10 files changed

+331
-668
lines changed

10 files changed

+331
-668
lines changed

site/src/api/api.ts

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -969,6 +969,24 @@ export const patchGroup = async (
969969
return response.data;
970970
};
971971

972+
export const addMember = async (groupId: string, userId: string) => {
973+
return patchGroup(groupId, {
974+
name: "",
975+
display_name: "",
976+
add_users: [userId],
977+
remove_users: [],
978+
});
979+
};
980+
981+
export const removeMember = async (groupId: string, userId: string) => {
982+
return patchGroup(groupId, {
983+
name: "",
984+
display_name: "",
985+
add_users: [],
986+
remove_users: [userId],
987+
});
988+
};
989+
972990
export const deleteGroup = async (groupId: string): Promise<void> => {
973991
await axios.delete(`/api/v2/groups/${groupId}`);
974992
};

site/src/api/queries/groups.ts

Lines changed: 101 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,101 @@
1+
import { QueryClient } from "@tanstack/react-query";
2+
import * as API from "api/api";
3+
import { checkAuthorization } from "api/api";
4+
import {
5+
CreateGroupRequest,
6+
Group,
7+
PatchGroupRequest,
8+
} from "api/typesGenerated";
9+
10+
const GROUPS_QUERY_KEY = ["groups"];
11+
12+
const getGroupQueryKey = (groupId: string) => ["group", groupId];
13+
14+
export const groups = (organizationId: string) => {
15+
return {
16+
queryKey: GROUPS_QUERY_KEY,
17+
queryFn: () => API.getGroups(organizationId),
18+
};
19+
};
20+
21+
export const group = (groupId: string) => {
22+
return {
23+
queryKey: getGroupQueryKey(groupId),
24+
queryFn: () => API.getGroup(groupId),
25+
};
26+
};
27+
28+
export const groupPermissions = (groupId: string) => {
29+
return {
30+
queryKey: [...getGroupQueryKey(groupId), "permissions"],
31+
queryFn: () =>
32+
checkAuthorization({
33+
checks: {
34+
canUpdateGroup: {
35+
object: {
36+
resource_type: "group",
37+
resource_id: groupId,
38+
},
39+
action: "update",
40+
},
41+
},
42+
}),
43+
};
44+
};
45+
46+
export const createGroup = (queryClient: QueryClient) => {
47+
return {
48+
mutationFn: ({
49+
organizationId,
50+
...request
51+
}: CreateGroupRequest & { organizationId: string }) =>
52+
API.createGroup(organizationId, request),
53+
onSuccess: async () => {
54+
await queryClient.invalidateQueries(GROUPS_QUERY_KEY);
55+
},
56+
};
57+
};
58+
59+
export const patchGroup = (queryClient: QueryClient) => {
60+
return {
61+
mutationFn: ({
62+
groupId,
63+
...request
64+
}: PatchGroupRequest & { groupId: string }) =>
65+
API.patchGroup(groupId, request),
66+
onSuccess: async (updatedGroup: Group) =>
67+
invalidateGroup(queryClient, updatedGroup.id),
68+
};
69+
};
70+
71+
export const deleteGroup = (queryClient: QueryClient) => {
72+
return {
73+
mutationFn: API.deleteGroup,
74+
onSuccess: async (_: void, groupId: string) =>
75+
invalidateGroup(queryClient, groupId),
76+
};
77+
};
78+
79+
export const addMember = (queryClient: QueryClient) => {
80+
return {
81+
mutationFn: ({ groupId, userId }: { groupId: string; userId: string }) =>
82+
API.addMember(groupId, userId),
83+
onSuccess: async (updatedGroup: Group) =>
84+
invalidateGroup(queryClient, updatedGroup.id),
85+
};
86+
};
87+
88+
export const removeMember = (queryClient: QueryClient) => {
89+
return {
90+
mutationFn: ({ groupId, userId }: { groupId: string; userId: string }) =>
91+
API.removeMember(groupId, userId),
92+
onSuccess: async (updatedGroup: Group) =>
93+
invalidateGroup(queryClient, updatedGroup.id),
94+
};
95+
};
96+
97+
export const invalidateGroup = (queryClient: QueryClient, groupId: string) =>
98+
Promise.all([
99+
queryClient.invalidateQueries(GROUPS_QUERY_KEY),
100+
queryClient.invalidateQueries(getGroupQueryKey(groupId)),
101+
]);

site/src/pages/GroupsPage/CreateGroupPage.tsx

Lines changed: 11 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -1,41 +1,33 @@
1-
import { useMachine } from "@xstate/react";
21
import { useOrganizationId } from "hooks/useOrganizationId";
32
import { FC } from "react";
43
import { Helmet } from "react-helmet-async";
54
import { useNavigate } from "react-router-dom";
65
import { pageTitle } from "utils/page";
7-
import { createGroupMachine } from "xServices/groups/createGroupXService";
86
import CreateGroupPageView from "./CreateGroupPageView";
7+
import { useMutation, useQueryClient } from "@tanstack/react-query";
8+
import { createGroup } from "api/queries/groups";
99

1010
export const CreateGroupPage: FC = () => {
11+
const queryClient = useQueryClient();
1112
const navigate = useNavigate();
1213
const organizationId = useOrganizationId();
13-
const [createState, sendCreateEvent] = useMachine(createGroupMachine, {
14-
context: {
15-
organizationId,
16-
},
17-
actions: {
18-
onCreate: (_, { data }) => {
19-
navigate(`/groups/${data.id}`);
20-
},
21-
},
22-
});
23-
const { error } = createState.context;
14+
const createGroupMutation = useMutation(createGroup(queryClient));
2415

2516
return (
2617
<>
2718
<Helmet>
2819
<title>{pageTitle("Create Group")}</title>
2920
</Helmet>
3021
<CreateGroupPageView
31-
onSubmit={(data) => {
32-
sendCreateEvent({
33-
type: "CREATE",
34-
data,
22+
onSubmit={async (data) => {
23+
const newGroup = await createGroupMutation.mutateAsync({
24+
organizationId,
25+
...data,
3526
});
27+
navigate(`/groups/${newGroup.id}`);
3628
}}
37-
formErrors={error}
38-
isLoading={createState.matches("creatingGroup")}
29+
formErrors={createGroupMutation.error}
30+
isLoading={createGroupMutation.isLoading}
3931
/>
4032
</>
4133
);

0 commit comments

Comments
 (0)
pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy