TelegramBot/webui/components/app-sidebar.tsx

232 lines
6.3 KiB
TypeScript
Executable file

"use client";
import * as React from "react"
import {
Home,
MessageSquare,
Users,
Sparkles,
User,
Trash2,
LogOut
} from "lucide-react"
import Link from "next/link"
import Image from "next/image"
import {
Sidebar,
SidebarContent,
SidebarFooter,
SidebarGroup,
SidebarGroupContent,
SidebarGroupLabel,
SidebarHeader,
SidebarMenu,
SidebarMenuButton,
SidebarMenuItem,
useSidebar,
} from "@/components/ui/sidebar"
import { ThemeToggle } from "@/components/theme-toggle"
import { SiYoutube } from "react-icons/si"
import { RiTelegram2Line } from "react-icons/ri"
import { useAuth } from "@/contexts/auth-context"
import { Badge } from "@/components/ui/badge"
interface AccountItem {
title: string;
url: string;
icon: React.ComponentType<React.SVGProps<SVGSVGElement>>;
danger?: boolean;
}
const navigation = [
{
title: "Home",
url: "/",
icon: Home,
},
{
title: "About",
url: "/about",
icon: MessageSquare,
},
]
const features = [
{
title: "AI Commands",
url: "/#ai-features",
icon: Sparkles,
},
{
title: "Video Download",
url: "/#youtube-features",
icon: SiYoutube,
},
{
title: "User Accounts & UI",
url: "/#user-features",
icon: Users,
},
]
export function AppSidebar() {
const { isAuthenticated, loading, logout } = useAuth();
const { setOpenMobile, isMobile } = useSidebar();
const handleMenuItemClick = () => {
if (isMobile) {
setOpenMobile(false);
}
};
const accountItems: AccountItem[] = React.useMemo(() => {
if (loading) {
return [];
}
if (isAuthenticated) {
return [
{
title: "My Account",
url: "/account",
icon: User,
},
{
title: "Logout",
url: "#",
icon: LogOut,
danger: true,
},
{
title: "Delete Account",
url: "/account/delete",
icon: Trash2,
danger: true,
},
];
} else {
return [
{
title: "Sign in with Telegram",
url: "/login",
icon: RiTelegram2Line,
},
];
}
}, [isAuthenticated, loading]);
return (
<Sidebar variant="inset">
<SidebarHeader>
<SidebarMenu>
<SidebarMenuItem>
<SidebarMenuButton size="lg" asChild>
<div className="flex flex-row justify-between gap-3">
<Link href="/" className="flex flex-row gap-2" onClick={handleMenuItemClick}>
<div className="flex aspect-square size-8 items-center justify-center rounded-lg bg-primary/10 p-1">
<Image
src="/kowalski.svg"
alt="Kowalski Logo"
width={20}
height={20}
className="dark:invert -mt-1"
/>
</div>
<div className="grid flex-1 text-left text-sm leading-tight">
<span className="truncate font-semibold text-lg">Kowalski</span>
</div>
</Link>
<Badge className="text-xs">Beta</Badge>
</div>
</SidebarMenuButton>
</SidebarMenuItem>
</SidebarMenu>
</SidebarHeader>
<SidebarContent>
<SidebarGroup>
<SidebarGroupLabel>Navigation</SidebarGroupLabel>
<SidebarGroupContent>
<SidebarMenu>
{navigation.map((item) => (
<SidebarMenuItem key={item.title}>
<SidebarMenuButton asChild>
<Link href={item.url} onClick={handleMenuItemClick}>
<item.icon />
<span>{item.title}</span>
</Link>
</SidebarMenuButton>
</SidebarMenuItem>
))}
</SidebarMenu>
</SidebarGroupContent>
</SidebarGroup>
{!loading && (
<SidebarGroup>
<SidebarGroupLabel>Account</SidebarGroupLabel>
<SidebarGroupContent>
<SidebarMenu>
{accountItems.map((item) => (
<SidebarMenuItem key={item.title}>
{item.title === "Logout" ? (
<SidebarMenuButton
onClick={() => {
logout();
handleMenuItemClick();
}}
className={item.danger ? "text-red-600 hover:text-red-700 dark:text-red-400 dark:hover:text-red-300" : ""}
>
<item.icon />
<span>{item.title}</span>
</SidebarMenuButton>
) : (
<SidebarMenuButton asChild>
<Link
href={item.url}
onClick={handleMenuItemClick}
className={item.danger ? "text-red-600 hover:text-red-700 dark:text-red-400 dark:hover:text-red-300" : ""}
>
<item.icon />
<span>{item.title}</span>
</Link>
</SidebarMenuButton>
)}
</SidebarMenuItem>
))}
</SidebarMenu>
</SidebarGroupContent>
</SidebarGroup>
)}
<SidebarGroup>
<SidebarGroupLabel>Features</SidebarGroupLabel>
<SidebarGroupContent>
<SidebarMenu>
{features.map((item) => (
<SidebarMenuItem key={item.title}>
<SidebarMenuButton asChild>
<Link href={item.url} onClick={handleMenuItemClick}>
<item.icon />
<span>{item.title}</span>
</Link>
</SidebarMenuButton>
</SidebarMenuItem>
))}
</SidebarMenu>
</SidebarGroupContent>
</SidebarGroup>
</SidebarContent>
<SidebarFooter>
<SidebarMenu>
<SidebarMenuItem>
<div className="flex items-center justify-end">
<ThemeToggle />
</div>
</SidebarMenuItem>
</SidebarMenu>
</SidebarFooter>
</Sidebar>
)
}