import React, { useCallback, useEffect, useMemo, useState } from 'react';
import { Link, Outlet, useLocation, useNavigate } from 'react-router-dom';
import { useTranslation } from 'react-i18next';
import {
    LayoutDashboard,
    Inbox,
    Users,
    Calendar,
    CalendarDays,
    AlertTriangle,
    Star,
    Ban,
    Ticket,
    CreditCard,
    Shield,
    FileSearch,
    Activity,
    ChevronLeft,
    ChevronRight,
    LogOut,
    User,
    Search,
    Rows3,
    Check,
    Languages,
} from 'lucide-react';
import { useAuthStore } from '@/store/authStore';
import { useAdminWebSocket } from '@/hooks/useAdminWebSocket';
import { useUpdateProfile } from '@/hooks/useProfile';
import {
    filterNavGroupsByRole,
    getMenuSelectedKey,
    canReceiveWsNotification,
    NAV_GROUPS,
    type NavItem,
} from '@/config/adminAccess';
import { notify } from '@/lib/notify';
import { cn } from '@/lib/utils';
import { getTableDensity, toggleTableDensity, type TableDensity } from '@/lib/density';
import { Button } from '@/components/ui/button';
import { ScrollArea } from '@/components/ui/scroll-area';
import { Avatar, AvatarFallback, AvatarImage } from '@/components/ui/avatar';
import {
    DropdownMenu,
    DropdownMenuContent,
    DropdownMenuItem,
    DropdownMenuLabel,
    DropdownMenuSeparator,
    DropdownMenuTrigger,
} from '@/components/ui/dropdown-menu';
import { ErrorBoundary } from '@/components/ErrorBoundary';
import { CommandPalette } from '@/components/CommandPalette';
import { useCommandPaletteHotkey } from '@/hooks/useCommandPaletteHotkey';
import { HeaderNodeMetrics } from '@/components/HeaderNodeMetrics';
import { healthApi } from '@/api/healthApi';

function formatBuildLabel(version: string, sha: string): string {
    const shortSha = sha && sha !== 'unknown' && sha !== 'dev' ? sha.slice(0, 12) : sha;
    return `${version} (${shortSha})`;
}

const navIconByKey: Record<string, React.ComponentType<{ className?: string }>> = {
    '/dashboard': LayoutDashboard,
    '/inbox/reports': Inbox,
    '/inbox/tickets': Ticket,
    '/users': Users,
    '/calendars': Calendar,
    '/events': CalendarDays,
    '/reports': AlertTriangle,
    '/reviews': Star,
    '/banned-words': Ban,
    '/tickets': Ticket,
    '/subscriptions': CreditCard,
    '/admins': Shield,
    '/audit': FileSearch,
    '/monitoring': Activity,
};

function NavLinkItem({ item, active, collapsed }: { item: NavItem; active: boolean; collapsed: boolean }) {
    const { t } = useTranslation();
    const Icon = navIconByKey[item.key] ?? LayoutDashboard;
    const label = t(item.label);
    return (
        <Link
            to={item.key}
            title={collapsed ? label : undefined}
            className={cn(
                'flex items-center gap-2 rounded-md px-3 py-2 text-sm transition-colors',
                collapsed && 'justify-center px-2',
                active
                    ? 'bg-sidebar-accent text-white font-medium'
                    : 'text-sidebar-foreground/80 hover:bg-sidebar-accent/60 hover:text-white'
            )}
        >
            <Icon className="h-4 w-4 shrink-0" />
            {!collapsed && <span className="truncate">{label}</span>}
        </Link>
    );
}

const ControlCenterLayout: React.FC = () => {
    useAdminWebSocket();
    const { t } = useTranslation();
    const navigate = useNavigate();
    const location = useLocation();
    const { user, logout } = useAuthStore();
    const updateProfile = useUpdateProfile();
    const [collapsed, setCollapsed] = useState(false);
    const [paletteOpen, setPaletteOpen] = useState(false);
    const [density, setDensity] = useState<TableDensity>(() => getTableDensity());
    const [apiVersionLabel, setApiVersionLabel] = useState<string | null>(null);

    const openPalette = useCallback(() => setPaletteOpen(true), []);
    useCommandPaletteHotkey(openPalette);

    const adminVersionLabel = formatBuildLabel(
        import.meta.env.VITE_APP_VERSION || '0.0',
        import.meta.env.VITE_GIT_SHA || 'dev'
    );

    useEffect(() => {
        let cancelled = false;
        healthApi
            .getAdminHealth()
            .then((info) => {
                if (cancelled) return;
                setApiVersionLabel(
                    formatBuildLabel(info.version || '0.0', info.git_sha || 'unknown')
                );
            })
            .catch(() => {
                if (!cancelled) setApiVersionLabel(null);
            });
        return () => {
            cancelled = true;
        };
    }, []);

    const selectedKey = getMenuSelectedKey(location.pathname);
    const groups = useMemo(() => filterNavGroupsByRole(NAV_GROUPS, user?.role), [user?.role]);

    useEffect(() => {
        const handler = (event: CustomEvent) => {
            const msg = event.detail;
            if (msg.type === 'report_created') {
                if (!canReceiveWsNotification('report_created', user?.role)) return;
                const { report_id, target_type, reason } = msg.data || {};
                const inboxPath = report_id
                    ? `/inbox/reports?selected=${report_id}`
                    : '/inbox/reports';
                notify.info(
                    [
                        report_id ? t('ws.reportId', { id: report_id }) : t('ws.newReport'),
                        target_type ? t('ws.onTarget', { type: target_type }) : '',
                        reason ? `(${reason})` : '',
                    ]
                        .filter(Boolean)
                        .join(' '),
                    {
                        action: {
                            label: t('ws.open'),
                            onClick: () => navigate(inboxPath),
                        },
                    }
                );
            } else if (msg.type === 'ticket_created') {
                if (!canReceiveWsNotification('ticket_created', user?.role)) return;
                const { ticket_id } = msg.data || {};
                const inboxPath = ticket_id
                    ? `/inbox/tickets?selected=${ticket_id}`
                    : '/inbox/tickets';
                notify.info(
                    ticket_id ? t('ws.ticketCreated', { id: ticket_id }) : t('ws.newTicket'),
                    {
                        action: {
                            label: t('ws.open'),
                            onClick: () => navigate(inboxPath),
                        },
                    }
                );
            }
        };
        window.addEventListener('admin-ws-message', handler as EventListener);
        return () => window.removeEventListener('admin-ws-message', handler as EventListener);
    }, [navigate, user?.role, t]);

    const handleLogout = async () => {
        await logout();
        navigate('/login');
    };

    const handleDensityToggle = () => {
        const next = toggleTableDensity();
        setDensity(next);
        notify.info(next === 'compact' ? t('layout.densityCompact') : t('layout.densityNormal'));
    };

    const displayName = (() => {
        const nick = user?.nickname;
        const email = user?.email;
        if (nick && nick !== '-' && nick !== 'undefined') return nick;
        if (email && email !== '-' && email !== 'undefined') return email;
        return user?.id ?? t('common.emDash');
    })();

    const initials = displayName.slice(0, 2).toUpperCase();

    return (
        <div className="flex min-h-screen bg-background">
            <aside
                className={cn(
                    'flex flex-col border-r bg-[hsl(var(--sidebar))] text-[hsl(var(--sidebar-foreground))] transition-[width]',
                    collapsed ? 'w-16' : 'w-60'
                )}
            >
                <div className="flex h-14 items-center justify-between px-3 border-b border-white/10">
                    {!collapsed && (
                        <span className="font-semibold text-sm truncate">
                            {import.meta.env.VITE_APP_TITLE || t('common.appTitle')}
                        </span>
                    )}
                    <Button
                        variant="ghost"
                        size="icon"
                        className="text-sidebar-foreground hover:bg-sidebar-accent shrink-0"
                        onClick={() => setCollapsed((v) => !v)}
                    >
                        {collapsed ? <ChevronRight className="h-4 w-4" /> : <ChevronLeft className="h-4 w-4" />}
                    </Button>
                </div>

                <ScrollArea className="flex-1 px-2 py-3">
                    <nav className="space-y-4">
                        {groups.map((group) => (
                            <div key={group.id}>
                                {!collapsed && (
                                    <p className="mb-1 px-3 text-[11px] font-semibold uppercase tracking-wider text-sidebar-foreground/50">
                                        {t(group.label)}
                                    </p>
                                )}
                                <div className="space-y-0.5">
                                    {group.items.map((item) => (
                                        <NavLinkItem
                                            key={item.key}
                                            item={item}
                                            collapsed={collapsed}
                                            active={selectedKey === item.key}
                                        />
                                    ))}
                                </div>
                            </div>
                        ))}
                    </nav>
                </ScrollArea>
            </aside>

            <div className="flex min-w-0 flex-1 flex-col">
                <header className="flex h-14 items-center gap-3 border-b bg-card px-4">
                    <HeaderNodeMetrics className="min-w-0 flex-1" />
                    <div className="ml-auto flex shrink-0 items-center gap-1 sm:gap-2">
                        <Button
                            variant="outline"
                            size="sm"
                            className="hidden sm:inline-flex gap-2 text-muted-foreground"
                            onClick={openPalette}
                        >
                            <Search className="h-3.5 w-3.5" />
                            {t('layout.search')}
                            <kbd className="pointer-events-none rounded border bg-muted px-1.5 py-0.5 font-mono text-[10px]">
                                ⌘K
                            </kbd>
                        </Button>
                        <Button
                            variant="ghost"
                            size="icon"
                            className="sm:hidden"
                            title={t('layout.searchHotkey')}
                            onClick={openPalette}
                        >
                            <Search className="h-4 w-4" />
                        </Button>
                        <Button
                            variant="ghost"
                            size="icon"
                            title={density === 'compact' ? t('layout.densityToNormal') : t('layout.densityToCompact')}
                            onClick={handleDensityToggle}
                        >
                            <Rows3 className="h-4 w-4" />
                        </Button>
                        <DropdownMenu>
                            <DropdownMenuTrigger asChild>
                                <Button variant="ghost" className="gap-2 px-2">
                                    <Avatar className="h-8 w-8">
                                        <AvatarImage src={user?.avatar_url ?? undefined} alt={displayName} />
                                        <AvatarFallback>{initials}</AvatarFallback>
                                    </Avatar>
                                    <span className="hidden sm:inline max-w-[120px] truncate text-sm font-medium">
                                        {displayName}
                                    </span>
                                </Button>
                            </DropdownMenuTrigger>
                            <DropdownMenuContent align="end" className="w-56">
                                <DropdownMenuLabel>
                                    <div className="flex flex-col">
                                        <span>{displayName}</span>
                                        <span className="text-xs font-normal text-muted-foreground">{user?.role}</span>
                                    </div>
                                </DropdownMenuLabel>
                                <DropdownMenuSeparator />
                                <DropdownMenuItem onClick={() => navigate('/profile')}>
                                    <User className="mr-2 h-4 w-4" />
                                    {t('layout.myProfile')}
                                </DropdownMenuItem>
                                <DropdownMenuSeparator />
                                <DropdownMenuLabel className="flex items-center gap-2 text-xs font-normal text-muted-foreground">
                                    <Languages className="h-3.5 w-3.5" />
                                    {t('layout.uiLanguage')}
                                </DropdownMenuLabel>
                                <DropdownMenuItem
                                    disabled={updateProfile.isPending}
                                    onClick={() => {
                                        if ((user?.language || 'ru') === 'ru') return;
                                        updateProfile.mutate({ language: 'ru' });
                                    }}
                                >
                                    <Check
                                        className={cn(
                                            'mr-2 h-4 w-4',
                                            (user?.language || 'ru') === 'ru' ? 'opacity-100' : 'opacity-0'
                                        )}
                                    />
                                    {t('common.langRu')}
                                </DropdownMenuItem>
                                <DropdownMenuItem
                                    disabled={updateProfile.isPending}
                                    onClick={() => {
                                        if (user?.language === 'en') return;
                                        updateProfile.mutate({ language: 'en' });
                                    }}
                                >
                                    <Check
                                        className={cn(
                                            'mr-2 h-4 w-4',
                                            user?.language === 'en' ? 'opacity-100' : 'opacity-0'
                                        )}
                                    />
                                    {t('common.langEn')}
                                </DropdownMenuItem>
                                <DropdownMenuSeparator />
                                <DropdownMenuLabel className="space-y-0.5 text-xs font-normal text-muted-foreground">
                                    <div>{t('layout.adminVersion', { version: adminVersionLabel })}</div>
                                    <div>
                                        {apiVersionLabel
                                            ? t('layout.apiVersion', { version: apiVersionLabel })
                                            : t('layout.apiVersionUnavailable')}
                                    </div>
                                </DropdownMenuLabel>
                                <DropdownMenuSeparator />
                                <DropdownMenuItem onClick={handleLogout} className="text-destructive focus:text-destructive">
                                    <LogOut className="mr-2 h-4 w-4" />
                                    {t('layout.logout')}
                                </DropdownMenuItem>
                            </DropdownMenuContent>
                        </DropdownMenu>
                    </div>
                </header>

                <main className="cc-main-surface flex-1 overflow-auto p-4 md:p-6">
                    <ErrorBoundary>
                        <Outlet />
                    </ErrorBoundary>
                </main>
            </div>

            <CommandPalette open={paletteOpen} onOpenChange={setPaletteOpen} />
        </div>
    );
};

export default ControlCenterLayout;
