Skip to content

Commit

Permalink
bulk delete users
Browse files Browse the repository at this point in the history
  • Loading branch information
Felix-Asante committed Dec 29, 2023
1 parent d71d419 commit 9e9e3e4
Show file tree
Hide file tree
Showing 2 changed files with 71 additions and 4 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,7 @@ export default function CreateNewUserContent() {

const getRandomPassword = () => {
const password = generateRandomPassword(8);
setValue("password", password);
setValue("password", password, { shouldTouch: true, shouldDirty: true });
setIsPassword(false);
};

Expand Down
73 changes: 70 additions & 3 deletions src/app/(dashboard)/users/_sections/UsersTable.tsx
Original file line number Diff line number Diff line change
@@ -1,10 +1,15 @@
import { deleteUser } from "@/actions/users";
import EmptyContent from "@/components/shared/EmptyContent";
import TextField from "@/components/shared/input/TextField";
import HStack from "@/components/shared/layout/HStack";
import Modal from "@/components/shared/modal";
import { UserRoles } from "@/config/constants";
import { ERRORS } from "@/config/constants/errors";
import useDebounce from "@/hooks/useDebounce";
import useQueryParams from "@/hooks/useQueryParam";
import { useServerAction } from "@/hooks/useServerAction";
import { User } from "@/types/auth";
import { getErrorMessage } from "@/utils/helpers";
import {
Button,
Chip,
Expand All @@ -18,6 +23,7 @@ import {
import { Trash2Icon } from "lucide-react";
import { useEffect, useState } from "react";
import { useForm } from "react-hook-form";
import { toast } from "sonner";

const columns = [
{ label: "Joined at", key: "JoinedAt" },
Expand All @@ -37,15 +43,48 @@ export default function UsersTable({ users }: UsersTableProps) {
"toggle" | "replace" | undefined
>("toggle");
const [selectedUsers, setSelectedUsers] = useState<Set<string>>(new Set([]));
const [selectedUser, setSelectedUser] = useState<string | null>(null);
const { add, query } = useQueryParams();
const search = useDebounce(watch("search"), 2000);

const [runDeleteUser, { loading }] = useServerAction<any, typeof deleteUser>(
deleteUser,
);

useEffect(() => {
add("search", search);
}, [search]);

const adminRoleSelected = query?.role === UserRoles.PLACE_ADMIN;

const removeUser = async (id: string) => {
try {
if (!id || adminRoleSelected) {
toast.error("Operation not allowed");
return;
}
await runDeleteUser(id);
toast.success("User successfully deleted");
setSelectedUser(null);
} catch (error) {
toast.error(getErrorMessage(error));
}
};

const bulkDelete = async () => {
try {
let userIds: string[] = [];
if (typeof selectedUsers === "string") {
userIds = users?.map((user) => user?.id);
} else {
userIds = [...selectedUsers];
}
await Promise.all(userIds?.map((user) => removeUser(user)));
} catch (error) {
toast.error(getErrorMessage(error));
}
};

return (
<div className='border rounded-md p-3'>
<HStack className='items-center justify-between'>
Expand All @@ -65,8 +104,8 @@ export default function UsersTable({ users }: UsersTableProps) {
color='danger'
disableRipple
className='font-semibold'
// onClick={onOpen}
isDisabled={selectedUsers?.size === 0 || adminRoleSelected}
onClick={bulkDelete}
isDisabled={selectedUsers?.size === 0 || adminRoleSelected || loading}
>
Delete users
</Button>
Expand Down Expand Up @@ -112,7 +151,7 @@ export default function UsersTable({ users }: UsersTableProps) {
size='sm'
disableRipple
color='danger'
// onClick={() => setSelectedCategory(category)}
onClick={() => setSelectedUser(user?.id)}
isIconOnly
isDisabled={adminRoleSelected}
>
Expand All @@ -124,6 +163,34 @@ export default function UsersTable({ users }: UsersTableProps) {
))}
</TableBody>
</Table>
<Modal
isOpen={selectedUser !== null}
onClose={() => setSelectedUser(null)}
title='Delete user'
description={ERRORS.MESSAGE.DELETE_PROMPT}
content={
<HStack className='justify-end'>
<Button
variant='bordered'
radius='sm'
size='sm'
onClick={() => setSelectedUser(null)}
isDisabled={loading}
>
Cancel
</Button>
<Button
color='primary'
radius='sm'
size='sm'
onClick={() => removeUser(selectedUser!)}
isLoading={loading}
>
Continue
</Button>
</HStack>
}
/>
</div>
);
}

0 comments on commit 9e9e3e4

Please sign in to comment.