refactor(sidebar): split nav views and add router decorator
Signed-off-by: Noa Virellia <noa@requiem.garden>
This commit is contained in:
@@ -1,20 +0,0 @@
|
||||
import type { ReactNode } from 'react';
|
||||
import React, { Suspense } from 'react';
|
||||
|
||||
export function withFallback<P extends object>(
|
||||
Component: React.ComponentType<P>,
|
||||
fallback: ReactNode,
|
||||
) {
|
||||
const Wrapped: React.FC<P> = (props) => {
|
||||
return (
|
||||
<Suspense fallback={fallback}>
|
||||
<Component {...props} />
|
||||
</Suspense>
|
||||
);
|
||||
};
|
||||
|
||||
Wrapped.displayName = `withFallback(${Component.displayName! || Component.name || 'Component'
|
||||
})`;
|
||||
|
||||
return Wrapped;
|
||||
}
|
||||
@@ -1,8 +1,8 @@
|
||||
import type { NavData } from '@/lib/navData';
|
||||
import * as React from 'react';
|
||||
import NixOSLogo from '@/assets/nixos.svg?react';
|
||||
import { NavMain } from '@/components/sidebar/nav-main';
|
||||
import { NavSecondary } from '@/components/sidebar/nav-secondary';
|
||||
import { NavMain } from '@/components/sidebar/nav-main.view';
|
||||
import { NavSecondary } from '@/components/sidebar/nav-secondary.view';
|
||||
import {
|
||||
Sidebar,
|
||||
SidebarContent,
|
||||
@@ -12,9 +12,8 @@ import {
|
||||
SidebarMenuButton,
|
||||
SidebarMenuItem,
|
||||
} from '@/components/ui/sidebar';
|
||||
import { NavUser } from './nav-user';
|
||||
|
||||
export function AppSidebar({ navData, ...props }: React.ComponentProps<typeof Sidebar> & { navData: NavData }) {
|
||||
export function AppSidebar({ navData, footerWidget, ...props }: React.ComponentProps<typeof Sidebar> & { navData: NavData; footerWidget: React.ReactNode }) {
|
||||
return (
|
||||
<Sidebar collapsible="offcanvas" {...props}>
|
||||
<SidebarHeader>
|
||||
@@ -37,7 +36,7 @@ export function AppSidebar({ navData, ...props }: React.ComponentProps<typeof Si
|
||||
<NavSecondary items={navData.navSecondary} className="mt-auto" />
|
||||
</SidebarContent>
|
||||
<SidebarFooter>
|
||||
<NavUser />
|
||||
{footerWidget}
|
||||
</SidebarFooter>
|
||||
</Sidebar>
|
||||
);
|
||||
11
client/cms/src/components/sidebar/nav-user.container.tsx
Normal file
11
client/cms/src/components/sidebar/nav-user.container.tsx
Normal file
@@ -0,0 +1,11 @@
|
||||
import { useUserInfo } from '@/hooks/data/useUserInfo';
|
||||
import { NavUserView } from './nav-user.view';
|
||||
|
||||
export function NavUserContainer() {
|
||||
const { data } = useUserInfo();
|
||||
return (
|
||||
<NavUserView
|
||||
user={data.data!}
|
||||
/>
|
||||
);
|
||||
}
|
||||
18
client/cms/src/components/sidebar/nav-user.skeletion.tsx
Normal file
18
client/cms/src/components/sidebar/nav-user.skeletion.tsx
Normal file
@@ -0,0 +1,18 @@
|
||||
import { IconDotsVertical } from '@tabler/icons-react';
|
||||
import { SidebarMenuButton } from '../ui/sidebar';
|
||||
import { Skeleton } from '../ui/skeleton';
|
||||
|
||||
export function NavUserSkeleton() {
|
||||
return (
|
||||
<SidebarMenuButton
|
||||
size="lg"
|
||||
>
|
||||
<Skeleton className="h-8 w-8 rounded-lg" />
|
||||
<div className="flex flex-col flex-1 gap-1">
|
||||
<Skeleton className="h-3 w-16" />
|
||||
<Skeleton className="h-3 w-24" />
|
||||
</div>
|
||||
<IconDotsVertical className="ml-auto size-4" />
|
||||
</SidebarMenuButton>
|
||||
);
|
||||
}
|
||||
@@ -1,5 +1,6 @@
|
||||
import { identicon } from '@dicebear/collection';
|
||||
import type { ServiceUserUserInfoData } from '@/client';
|
||||
|
||||
import { identicon } from '@dicebear/collection';
|
||||
import { createAvatar } from '@dicebear/core';
|
||||
import {
|
||||
IconDotsVertical,
|
||||
@@ -25,15 +26,10 @@ import {
|
||||
SidebarMenuItem,
|
||||
useSidebar,
|
||||
} from '@/components/ui/sidebar';
|
||||
import { useUserInfo } from '@/hooks/data/useUserInfo';
|
||||
import { logout } from '@/lib/token';
|
||||
import { withFallback } from '../hoc/with-fallback';
|
||||
import { Skeleton } from '../ui/skeleton';
|
||||
|
||||
export function NavUser_() {
|
||||
export function NavUserView({ user }: { user: ServiceUserUserInfoData }) {
|
||||
const { isMobile } = useSidebar();
|
||||
const { data } = useUserInfo();
|
||||
const user = data.data!;
|
||||
|
||||
const IdentIcon = useMemo(() => {
|
||||
const avatar = createAvatar(identicon, {
|
||||
@@ -94,20 +90,3 @@ export function NavUser_() {
|
||||
</SidebarMenu>
|
||||
);
|
||||
}
|
||||
|
||||
function NavUserSkeleton() {
|
||||
return (
|
||||
<SidebarMenuButton
|
||||
size="lg"
|
||||
>
|
||||
<Skeleton className="h-8 w-8 rounded-lg" />
|
||||
<div className="flex flex-col flex-1 gap-1">
|
||||
<Skeleton className="h-3 w-16" />
|
||||
<Skeleton className="h-3 w-24" />
|
||||
</div>
|
||||
<IconDotsVertical className="ml-auto size-4" />
|
||||
</SidebarMenuButton>
|
||||
);
|
||||
}
|
||||
|
||||
export const NavUser = withFallback(NavUser_, <NavUserSkeleton />);
|
||||
Reference in New Issue
Block a user