diff options
| author | MohamedBassem <me@mbassem.com> | 2024-03-13 21:43:44 +0000 |
|---|---|---|
| committer | Mohamed Bassem <me@mbassem.com> | 2024-03-14 16:40:45 +0000 |
| commit | 04572a8e5081b1e4871e273cde9dbaaa44c52fe0 (patch) | |
| tree | 8e993acb732a50d1306d4d6953df96c165c57f57 /apps/web/components/dashboard/lists | |
| parent | 2df08ed08c065e8b91bc8df0266bd4bcbb062be4 (diff) | |
| download | karakeep-04572a8e5081b1e4871e273cde9dbaaa44c52fe0.tar.zst | |
structure: Create apps dir and copy tooling dir from t3-turbo repo
Diffstat (limited to 'apps/web/components/dashboard/lists')
| -rw-r--r-- | apps/web/components/dashboard/lists/AllListsView.tsx | 66 | ||||
| -rw-r--r-- | apps/web/components/dashboard/lists/DeleteListButton.tsx | 77 | ||||
| -rw-r--r-- | apps/web/components/dashboard/lists/ListView.tsx | 25 |
3 files changed, 168 insertions, 0 deletions
diff --git a/apps/web/components/dashboard/lists/AllListsView.tsx b/apps/web/components/dashboard/lists/AllListsView.tsx new file mode 100644 index 00000000..81f31cde --- /dev/null +++ b/apps/web/components/dashboard/lists/AllListsView.tsx @@ -0,0 +1,66 @@ +"use client"; + +import { Button } from "@/components/ui/button"; +import { api } from "@/lib/trpc"; +import { ZBookmarkList } from "@hoarder/trpc/types/lists"; +import { keepPreviousData } from "@tanstack/react-query"; +import { Plus } from "lucide-react"; +import Link from "next/link"; +import { useNewListModal } from "@/components/dashboard/sidebar/NewListModal"; + +function ListItem({ + name, + icon, + path, +}: { + name: string; + icon: string; + path: string; +}) { + return ( + <Link href={path}> + <div className="bg-background rounded-md border border-gray-200 px-4 py-2 text-lg"> + <p className="text-nowrap"> + {icon} {name} + </p> + </div> + </Link> + ); +} + +export default function AllListsView({ + initialData, +}: { + initialData: ZBookmarkList[]; +}) { + const { setOpen: setIsNewListModalOpen } = useNewListModal(); + let { data: lists } = api.lists.list.useQuery(undefined, { + initialData: { lists: initialData }, + placeholderData: keepPreviousData, + }); + + // TODO: This seems to be a bug in react query + lists ||= { lists: initialData }; + + return ( + <div className="flex flex-col flex-wrap gap-2 md:flex-row"> + <Button + className="my-auto flex h-full" + onClick={() => setIsNewListModalOpen(true)} + > + <Plus /> + <span className="my-auto">New List</span> + </Button> + <ListItem name="Favourites" icon="⭐️" path={`/dashboard/favourites`} /> + <ListItem name="Archive" icon="🗄️" path={`/dashboard/archive`} /> + {lists.lists.map((l) => ( + <ListItem + key={l.id} + name={l.name} + icon={l.icon} + path={`/dashboard/lists/${l.id}`} + /> + ))} + </div> + ); +} diff --git a/apps/web/components/dashboard/lists/DeleteListButton.tsx b/apps/web/components/dashboard/lists/DeleteListButton.tsx new file mode 100644 index 00000000..5303b217 --- /dev/null +++ b/apps/web/components/dashboard/lists/DeleteListButton.tsx @@ -0,0 +1,77 @@ +"use client"; + +import { Button } from "@/components/ui/button"; +import { + Dialog, + DialogClose, + DialogContent, + DialogFooter, + DialogHeader, + DialogTitle, + DialogTrigger, +} from "@/components/ui/dialog"; +import { Trash } from "lucide-react"; +import { useRouter } from "next/navigation"; +import { toast } from "@/components/ui/use-toast"; +import { api } from "@/lib/trpc"; +import { ActionButton } from "@/components/ui/action-button"; +import { useState } from "react"; +import { ZBookmarkList } from "@hoarder/trpc/types/lists"; + +export default function DeleteListButton({ list }: { list: ZBookmarkList }) { + const [isDialogOpen, setDialogOpen] = useState(false); + + const router = useRouter(); + + const listsInvalidationFunction = api.useUtils().lists.list.invalidate; + const { mutate: deleteList, isPending } = api.lists.delete.useMutation({ + onSuccess: () => { + listsInvalidationFunction(); + toast({ + description: `List "${list.icon} ${list.name}" is deleted!`, + }); + router.push("/"); + }, + onError: () => { + toast({ + variant: "destructive", + description: `Something went wrong`, + }); + }, + }); + return ( + <Dialog open={isDialogOpen} onOpenChange={setDialogOpen}> + <DialogTrigger asChild> + <Button className="mt-auto flex gap-2" variant="destructive"> + <Trash className="size-5" /> + <span className="hidden md:block">Delete List</span> + </Button> + </DialogTrigger> + <DialogContent> + <DialogHeader> + <DialogTitle> + Delete {list.icon} {list.name}? + </DialogTitle> + </DialogHeader> + <span> + Are you sure you want to delete {list.icon} {list.name}? + </span> + <DialogFooter className="sm:justify-end"> + <DialogClose asChild> + <Button type="button" variant="secondary"> + Close + </Button> + </DialogClose> + <ActionButton + type="button" + variant="destructive" + loading={isPending} + onClick={() => deleteList({ listId: list.id })} + > + Delete + </ActionButton> + </DialogFooter> + </DialogContent> + </Dialog> + ); +} diff --git a/apps/web/components/dashboard/lists/ListView.tsx b/apps/web/components/dashboard/lists/ListView.tsx new file mode 100644 index 00000000..2d48d9e3 --- /dev/null +++ b/apps/web/components/dashboard/lists/ListView.tsx @@ -0,0 +1,25 @@ +"use client"; + +import BookmarksGrid from "@/components/dashboard/bookmarks/BookmarksGrid"; +import { ZBookmark } from "@hoarder/trpc/types/bookmarks"; +import { ZBookmarkListWithBookmarks } from "@hoarder/trpc/types/lists"; +import { api } from "@/lib/trpc"; + +export default function ListView({ + bookmarks, + list: initialData, +}: { + list: ZBookmarkListWithBookmarks; + bookmarks: ZBookmark[]; +}) { + const { data } = api.lists.get.useQuery( + { listId: initialData.id }, + { + initialData, + }, + ); + + return ( + <BookmarksGrid query={{ ids: data.bookmarks }} bookmarks={bookmarks} /> + ); +} |
