|
|
@@ -2,52 +2,257 @@
|
|
|
|
|
|
import Link from "next/link";
|
|
|
import Image from "next/image";
|
|
|
-import { LoginLink, LogoutLink } from "@kinde-oss/kinde-auth-nextjs/server";
|
|
|
+import { LoginLink, LogoutLink, RegisterLink } from "@kinde-oss/kinde-auth-nextjs/server";
|
|
|
import { useKindeBrowserClient } from "@kinde-oss/kinde-auth-nextjs";
|
|
|
+import {
|
|
|
+ NavigationMenu,
|
|
|
+ NavigationMenuContent,
|
|
|
+ NavigationMenuItem,
|
|
|
+ NavigationMenuLink,
|
|
|
+ NavigationMenuList,
|
|
|
+ NavigationMenuTrigger,
|
|
|
+} from "@/components/ui/navigation-menu";
|
|
|
+import { Button } from "@/components/ui/button";
|
|
|
+import { Sheet, SheetContent, SheetTrigger } from "@/components/ui/sheet";
|
|
|
+import { Menu, FileText, Upload, Home, Folder, Settings, User, LogOut, LogIn } from "lucide-react";
|
|
|
+import { cn } from "@/lib/utils";
|
|
|
+import React from "react";
|
|
|
+
|
|
|
+const navigationItems = [
|
|
|
+ {
|
|
|
+ title: "Files",
|
|
|
+ href: "/files",
|
|
|
+ description: "Browse and manage your files",
|
|
|
+ icon: Folder,
|
|
|
+ },
|
|
|
+ {
|
|
|
+ title: "Upload",
|
|
|
+ href: "/upload",
|
|
|
+ description: "Upload new files to the platform",
|
|
|
+ icon: Upload,
|
|
|
+ },
|
|
|
+ {
|
|
|
+ title: "API Docs",
|
|
|
+ href: "/api-docs",
|
|
|
+ description: "View API documentation",
|
|
|
+ icon: FileText,
|
|
|
+ },
|
|
|
+];
|
|
|
+
|
|
|
+const userMenuItems = [
|
|
|
+ {
|
|
|
+ title: "Profile",
|
|
|
+ href: "/profile",
|
|
|
+ description: "Manage your profile settings",
|
|
|
+ icon: User,
|
|
|
+ },
|
|
|
+ {
|
|
|
+ title: "Settings",
|
|
|
+ href: "/settings",
|
|
|
+ description: "Configure your preferences",
|
|
|
+ icon: Settings,
|
|
|
+ },
|
|
|
+];
|
|
|
|
|
|
export default function Header() {
|
|
|
const { isAuthenticated, getUser } = useKindeBrowserClient();
|
|
|
const user = getUser();
|
|
|
|
|
|
return (
|
|
|
- <header className="border-b border-gray-200 bg-white">
|
|
|
- <div className="mx-auto max-w-7xl px-4 sm:px-6 lg:px-8">
|
|
|
- <div className="flex justify-between items-center py-4">
|
|
|
- <div className="flex items-center">
|
|
|
- <Link href="/" className="flex items-center">
|
|
|
- <img
|
|
|
- src="/vtorio.svg"
|
|
|
- alt="vtor.io"
|
|
|
- className="h-8 w-auto"
|
|
|
- />
|
|
|
- </Link>
|
|
|
- </div>
|
|
|
- <div className="flex items-center space-x-4">
|
|
|
- {!isAuthenticated &&
|
|
|
- <LoginLink
|
|
|
- className="rounded-full border border-solid border-transparent transition-colors flex items-center justify-center bg-foreground text-background gap-2 hover:bg-[#383838] dark:hover:bg-[#ccc] text-sm sm:text-base h-10 sm:h-12 px-4 sm:px-5">
|
|
|
- Login
|
|
|
+ <header className="sticky top-0 z-50 w-full border-b bg-background/95 backdrop-blur supports-[backdrop-filter]:bg-background/60">
|
|
|
+ <div className="container flex h-16 items-center justify-between">
|
|
|
+ <div className="flex items-center gap-6">
|
|
|
+ <Link href="/" className="flex items-center space-x-2">
|
|
|
+ <Image
|
|
|
+ src="/vtorio.svg"
|
|
|
+ alt="vtor.io"
|
|
|
+ width={32}
|
|
|
+ height={32}
|
|
|
+ className="h-8 w-auto"
|
|
|
+ />
|
|
|
+ <span className="font-bold text-xl hidden sm:inline">vtor.io</span>
|
|
|
+ </Link>
|
|
|
+
|
|
|
+ <NavigationMenu className="hidden md:flex">
|
|
|
+ <NavigationMenuList>
|
|
|
+ <NavigationMenuItem>
|
|
|
+ <Link href="/" legacyBehavior passHref>
|
|
|
+ <NavigationMenuLink className={cn(
|
|
|
+ "group inline-flex h-9 w-max items-center justify-center rounded-md bg-background px-4 py-2 text-sm font-medium transition-colors hover:bg-accent hover:text-accent-foreground focus:bg-accent focus:text-accent-foreground focus:outline-none disabled:pointer-events-none disabled:opacity-50"
|
|
|
+ )}>
|
|
|
+ <Home className="mr-2 h-4 w-4" />
|
|
|
+ Home
|
|
|
+ </NavigationMenuLink>
|
|
|
+ </Link>
|
|
|
+ </NavigationMenuItem>
|
|
|
+
|
|
|
+ {navigationItems.map((item) => (
|
|
|
+ <NavigationMenuItem key={item.title}>
|
|
|
+ <Link href={item.href} legacyBehavior passHref>
|
|
|
+ <NavigationMenuLink className={cn(
|
|
|
+ "group inline-flex h-9 w-max items-center justify-center rounded-md bg-background px-4 py-2 text-sm font-medium transition-colors hover:bg-accent hover:text-accent-foreground focus:bg-accent focus:text-accent-foreground focus:outline-none disabled:pointer-events-none disabled:opacity-50"
|
|
|
+ )}>
|
|
|
+ <item.icon className="mr-2 h-4 w-4" />
|
|
|
+ {item.title}
|
|
|
+ </NavigationMenuLink>
|
|
|
+ </Link>
|
|
|
+ </NavigationMenuItem>
|
|
|
+ ))}
|
|
|
+ </NavigationMenuList>
|
|
|
+ </NavigationMenu>
|
|
|
+ </div>
|
|
|
+
|
|
|
+ <div className="flex items-center gap-4">
|
|
|
+ {isAuthenticated ? (
|
|
|
+ <>
|
|
|
+ <NavigationMenu className="hidden md:flex">
|
|
|
+ <NavigationMenuList>
|
|
|
+ <NavigationMenuItem>
|
|
|
+ <NavigationMenuTrigger className="h-9">
|
|
|
+ <div className="flex items-center gap-2">
|
|
|
+ <Image
|
|
|
+ className="rounded-full"
|
|
|
+ src={user?.picture || "/default-avatar.png"}
|
|
|
+ alt="User Avatar"
|
|
|
+ width={24}
|
|
|
+ height={24}
|
|
|
+ />
|
|
|
+ <span className="text-sm font-medium">{user?.given_name || user?.email}</span>
|
|
|
+ </div>
|
|
|
+ </NavigationMenuTrigger>
|
|
|
+ <NavigationMenuContent>
|
|
|
+ <ul className="grid gap-3 p-6 w-[300px]">
|
|
|
+ {userMenuItems.map((item) => (
|
|
|
+ <li key={item.title}>
|
|
|
+ <NavigationMenuLink asChild>
|
|
|
+ <Link
|
|
|
+ href={item.href}
|
|
|
+ className="block select-none space-y-1 rounded-md p-3 leading-none no-underline outline-none transition-colors hover:bg-accent hover:text-accent-foreground"
|
|
|
+ >
|
|
|
+ <div className="flex items-center gap-2">
|
|
|
+ <item.icon className="h-4 w-4" />
|
|
|
+ <div className="text-sm font-medium leading-none">{item.title}</div>
|
|
|
+ </div>
|
|
|
+ <p className="line-clamp-2 text-sm leading-snug text-muted-foreground">
|
|
|
+ {item.description}
|
|
|
+ </p>
|
|
|
+ </Link>
|
|
|
+ </NavigationMenuLink>
|
|
|
+ </li>
|
|
|
+ ))}
|
|
|
+ <li>
|
|
|
+ <LogoutLink className="block select-none space-y-1 rounded-md p-3 leading-none no-underline outline-none transition-colors hover:bg-accent hover:text-accent-foreground">
|
|
|
+ <div className="flex items-center gap-2">
|
|
|
+ <LogOut className="h-4 w-4" />
|
|
|
+ <div className="text-sm font-medium leading-none">Logout</div>
|
|
|
+ </div>
|
|
|
+ <p className="line-clamp-2 text-sm leading-snug text-muted-foreground">
|
|
|
+ Sign out of your account
|
|
|
+ </p>
|
|
|
+ </LogoutLink>
|
|
|
+ </li>
|
|
|
+ </ul>
|
|
|
+ </NavigationMenuContent>
|
|
|
+ </NavigationMenuItem>
|
|
|
+ </NavigationMenuList>
|
|
|
+ </NavigationMenu>
|
|
|
+
|
|
|
+ <div className="hidden md:flex items-center gap-2">
|
|
|
+ <LogoutLink>
|
|
|
+ <Button variant="ghost" size="sm">
|
|
|
+ <LogOut className="h-4 w-4 mr-2" />
|
|
|
+ Logout
|
|
|
+ </Button>
|
|
|
+ </LogoutLink>
|
|
|
+ </div>
|
|
|
+ </>
|
|
|
+ ) : (
|
|
|
+ <div className="hidden md:flex items-center gap-2">
|
|
|
+ <LoginLink>
|
|
|
+ <Button variant="ghost" size="sm">
|
|
|
+ <LogIn className="h-4 w-4 mr-2" />
|
|
|
+ Login
|
|
|
+ </Button>
|
|
|
</LoginLink>
|
|
|
- }
|
|
|
- { user &&
|
|
|
- <>
|
|
|
- <Image
|
|
|
- className="rounded-full ml-auto"
|
|
|
- src={user.picture!}
|
|
|
- alt="User Avatar"
|
|
|
- width={35}
|
|
|
- height={35}
|
|
|
- />
|
|
|
- {user.email}
|
|
|
- </>
|
|
|
- }
|
|
|
- { isAuthenticated &&
|
|
|
- <LogoutLink
|
|
|
- className="rounded-full border border-solid border-black/[.08] dark:border-white/[.145] transition-colors flex items-center justify-center hover:bg-[#f2f2f2] dark:hover:bg-[#1a1a1a] hover:border-transparent text-sm sm:text-base h-10 sm:h-12 px-4 sm:px-5">
|
|
|
- Logout
|
|
|
- </LogoutLink>
|
|
|
- }
|
|
|
- </div>
|
|
|
+ <RegisterLink>
|
|
|
+ <Button size="sm">Sign Up</Button>
|
|
|
+ </RegisterLink>
|
|
|
+ </div>
|
|
|
+ )}
|
|
|
+
|
|
|
+ {/* Mobile Menu */}
|
|
|
+ <Sheet>
|
|
|
+ <SheetTrigger asChild className="md:hidden">
|
|
|
+ <Button variant="ghost" size="icon">
|
|
|
+ <Menu className="h-5 w-5" />
|
|
|
+ <span className="sr-only">Toggle menu</span>
|
|
|
+ </Button>
|
|
|
+ </SheetTrigger>
|
|
|
+ <SheetContent side="right" className="w-[300px]">
|
|
|
+ <div className="flex flex-col space-y-4 mt-8">
|
|
|
+ <Link href="/" className="flex items-center space-x-2">
|
|
|
+ <Home className="h-4 w-4" />
|
|
|
+ <span>Home</span>
|
|
|
+ </Link>
|
|
|
+
|
|
|
+ {navigationItems.map((item) => (
|
|
|
+ <Link
|
|
|
+ key={item.title}
|
|
|
+ href={item.href}
|
|
|
+ className="flex items-center space-x-2"
|
|
|
+ >
|
|
|
+ <item.icon className="h-4 w-4" />
|
|
|
+ <span>{item.title}</span>
|
|
|
+ </Link>
|
|
|
+ ))}
|
|
|
+
|
|
|
+ {isAuthenticated ? (
|
|
|
+ <>
|
|
|
+ <div className="border-t pt-4">
|
|
|
+ <div className="flex items-center space-x-2 mb-4">
|
|
|
+ <Image
|
|
|
+ className="rounded-full"
|
|
|
+ src={user?.picture || "/default-avatar.png"}
|
|
|
+ alt="User Avatar"
|
|
|
+ width={32}
|
|
|
+ height={32}
|
|
|
+ />
|
|
|
+ <span className="font-medium">{user?.given_name || user?.email}</span>
|
|
|
+ </div>
|
|
|
+
|
|
|
+ {userMenuItems.map((item) => (
|
|
|
+ <Link
|
|
|
+ key={item.title}
|
|
|
+ href={item.href}
|
|
|
+ className="flex items-center space-x-2 py-2"
|
|
|
+ >
|
|
|
+ <item.icon className="h-4 w-4" />
|
|
|
+ <span>{item.title}</span>
|
|
|
+ </Link>
|
|
|
+ ))}
|
|
|
+
|
|
|
+ <LogoutLink className="flex items-center space-x-2 py-2 text-red-600">
|
|
|
+ <LogOut className="h-4 w-4" />
|
|
|
+ <span>Logout</span>
|
|
|
+ </LogoutLink>
|
|
|
+ </div>
|
|
|
+ </>
|
|
|
+ ) : (
|
|
|
+ <div className="border-t pt-4 space-y-2">
|
|
|
+ <LoginLink>
|
|
|
+ <Button variant="ghost" className="w-full justify-start">
|
|
|
+ <LogIn className="h-4 w-4 mr-2" />
|
|
|
+ Login
|
|
|
+ </Button>
|
|
|
+ </LoginLink>
|
|
|
+ <RegisterLink>
|
|
|
+ <Button className="w-full">Sign Up</Button>
|
|
|
+ </RegisterLink>
|
|
|
+ </div>
|
|
|
+ )}
|
|
|
+ </div>
|
|
|
+ </SheetContent>
|
|
|
+ </Sheet>
|
|
|
</div>
|
|
|
</div>
|
|
|
</header>
|