Skip to content

Commit

Permalink
[Admin ] - Gab/feature tag (#157)
Browse files Browse the repository at this point in the history
* add api

* test integration
  • Loading branch information
gidoo5331 authored Jan 2, 2025
1 parent cb1f97e commit 0271cfa
Show file tree
Hide file tree
Showing 4 changed files with 131 additions and 8 deletions.
29 changes: 29 additions & 0 deletions apps/admin/api/tag/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -46,3 +46,32 @@ export const useGetTags = (
queryKey: [QUERY_KEYS.TAGS,JSON.stringify(query)],
queryFn: () => getTags(query),
})


/**
* Feature tag
*
* @throws {Error} - Throws an error if there's a problem with the API response.
*
* @returns {Promise<object>} - The tag data.
*/

const featureTag = async (id: string) => {
try {
await fetchClient<Tag>(`/v1/tags/${id}/feature`, {
method: 'PATCH',
})
} catch (error) {
if (error instanceof Error) {
throw error
}

// Error from server.
if (error instanceof Response) {
const response = await error.json()
throw new Error(response.message)
}
}
}

export const useFeatureTag = () => useMutation({mutationFn: featureTag})
85 changes: 85 additions & 0 deletions apps/admin/modules/tag/feature/index.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,85 @@
import { Button } from "@/components/ui/button";
import { Dispatch, SetStateAction } from "react";
import {
Dialog,
DialogContent,
DialogDescription,
DialogHeader,
DialogTitle,
DialogFooter,
DialogOverlay,
} from "@/components/ui/dialog";
import { useToast } from "@/hooks/use-toast";
import { useFeatureTag } from "@/api";
import { Loader2Icon } from "lucide-react";

interface FeatureTagModalProps {
data?: Tag;
refetch: VoidFunction;
opened: boolean;
setOpened: Dispatch<SetStateAction<boolean>>;
}

export const FeatureTagModal = ({
data,
refetch,
opened,
setOpened,
}: FeatureTagModalProps) => {
const { toast } = useToast();
const { mutate, isPending: isLoading } = useFeatureTag();

const handleSubmit = () => {
if (!data) {
toast({
title: "Tag data not found",
variant: "destructive",
})
return;
}

mutate(
data.id,
{
onError: () => {
toast({
title: "We couldn't process your request",
variant: "destructive",
})

}, onSuccess: () => {
refetch()
toast({
title: "Tag marked as featured",
variant: "success",
});
setOpened(false);
}
}
)
};

const name = <span className="capitalize">{data?.name}'s </span>

return (
<Dialog open={opened} onOpenChange={() => setOpened(false)}>
<DialogOverlay className="bg-black/10" />
<DialogContent className="sm:max-w-[425px] bg-white dark:bg-black top-32">
<DialogHeader>
<DialogTitle className="leading-normal">
Feature {data?.name ? name : "this"} tag
</DialogTitle>
<DialogDescription className="text-gray-600 dark:text-gray-400">
Are you sure you want to mark{" "}
{data?.name ? name : "this"} tag as featured?
</DialogDescription>
</DialogHeader>
<DialogFooter>
<Button className="bg-emerald-600 hover:bg-emerald-400" disabled={isLoading} type="button" onClick={() => handleSubmit()}>
{ isLoading ? <Loader2Icon className="animate-spin" /> : null} Yes, mark as featured
</Button>
</DialogFooter>
</DialogContent>
</Dialog>
);
};
24 changes: 16 additions & 8 deletions apps/admin/modules/tag/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ import { useSearchParams } from "next/navigation";
import { localizedDayjs } from "@/lib/date";
import { DataTableColumnHeader } from "@/components/table/components";
import { createDataTableError } from "@/lib/utils";
import { FeatureTagModal } from "./feature";

const TAGS_PER_PAGE = 50;

Expand Down Expand Up @@ -74,7 +75,7 @@ export const ListTags = () => {
accessorKey: "name",
header: ({ column }) => <DataTableColumnHeader column={column} title={"Name"} />,
cell: ({ row }) => (<div className="capitalize flex flex-row justify-start align-middle">
<StarIcon className="mr-2 h-4 w-4" color="gold"/> {row.original.name}
{row.original.isFeatured ? <StarIcon className="mr-2 h-4 w-4" color="gold"/> : <span className="mr-2 h-4 w-4"/> } {row.original.name}
</div>),
},
{
Expand Down Expand Up @@ -115,24 +116,25 @@ export const ListTags = () => {
</DropdownMenuTrigger>
<DropdownMenuContent align="end">
<DropdownMenuLabel>Options</DropdownMenuLabel>
{row.original.isFeatured ?
(
<DropdownMenuItem
onClick={() => {
setSelectedTag(row.original);
setOpenFeaturedModal(true)
}}
>
<StarIcon className="mr-2 h-4 w-4" />
Feature
</DropdownMenuItem>
<DropdownMenuItem
<StarOffIcon className="mr-2 h-4 w-4" />
UnFeature
</DropdownMenuItem>):(<DropdownMenuItem
onClick={() => {
setSelectedTag(row.original);
setOpenFeaturedModal(true)
}}
>
<StarOffIcon className="mr-2 h-4 w-4" />
UnFeature
</DropdownMenuItem>
<StarIcon className="mr-2 h-4 w-4" />
Feature
</DropdownMenuItem>)}
</DropdownMenuContent>
</DropdownMenu>
);
Expand Down Expand Up @@ -170,6 +172,12 @@ export const ListTags = () => {
</DataTable>
</div>

<FeatureTagModal
opened={openFeaturedModal}
setOpened={setOpenFeaturedModal}
data={selectedTag}
refetch={refetch}
/>
</>
);
};
1 change: 1 addition & 0 deletions apps/admin/types/tag/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ interface Tag {
slug: string
name: string
description: NullableString
isFeatured: boolean
createdByAdmin: Admin
createdByUser: User
createdAt: Date
Expand Down

0 comments on commit 0271cfa

Please sign in to comment.