import React, { useState, useCallback, forwardRef } from 'react';
import { clsx } from 'clsx';
import { useLocation, useNavigate } from 'react-router-dom';
import { useAuthUser, useIsAuthenticated } from '../../../stores';
import { getNavigationRoutes, canAccessRoute, ROUTES } from '../../../router/routes.config';
import { Button } from '../../ui';
import { Badge } from '../../ui';
import { Tooltip } from '../../ui';
import {
  LayoutDashboard,
  Package,
  Factory,
  BarChart3,
  Brain,
  ShoppingCart,
  Truck,
  Zap,
  Database,
  GraduationCap,
  Bell,
  Settings,
  ChevronLeft,
  ChevronRight,
  ChevronDown,
  Dot,
  Menu
} from 'lucide-react';

export interface SidebarProps {
  className?: string;
  /**
   * Whether the sidebar is open (mobile drawer state)
   */
  isOpen?: boolean;
  /**
   * Whether the sidebar is collapsed (desktop state)
   */
  isCollapsed?: boolean;
  /**
   * Callback when sidebar is closed (mobile)
   */
  onClose?: () => void;
  /**
   * Callback when sidebar collapse state is toggled (desktop)
   */
  onToggleCollapse?: () => void;
  /**
   * Custom navigation items
   */
  customItems?: NavigationItem[];
  /**
   * Show/hide collapse button
   */
  showCollapseButton?: boolean;
  /**
   * Show/hide footer
   */
  showFooter?: boolean;
}

export interface NavigationItem {
  id: string;
  label: string;
  path: string;
  icon?: React.ComponentType<{ className?: string }>;
  badge?: {
    text: string;
    variant?: 'default' | 'primary' | 'success' | 'warning' | 'error';
  };
  children?: NavigationItem[];
  requiredPermissions?: string[];
  requiredRoles?: string[];
  disabled?: boolean;
  external?: boolean;
}

export interface SidebarRef {
  scrollToItem: (path: string) => void;
  expandItem: (path: string) => void;
  collapseItem: (path: string) => void;
}

const iconMap: Record<string, React.ComponentType<{ className?: string }>> = {
  dashboard: LayoutDashboard,
  inventory: Package,
  production: Factory,
  sales: BarChart3,
  forecasting: Brain,
  orders: ShoppingCart,
  procurement: Truck,
  pos: Zap,
  data: Database,
  training: GraduationCap,
  notifications: Bell,
  settings: Settings,
};

/**
 * Sidebar - Navigation sidebar with collapsible menu items and role-based access
 * 
 * Features:
 * - Hierarchical navigation menu with icons
 * - Icons for menu items with fallback support
 * - Collapsible sections with smooth animations
 * - Active state highlighting with proper contrast
 * - Role-based menu filtering and permissions
 * - Responsive design with mobile drawer mode
 * - Keyboard navigation support
 * - Smooth scrolling to items
 * - Badge support for notifications/counts
 */
export const Sidebar = forwardRef<SidebarRef, SidebarProps>(({
  className,
  isOpen = false,
  isCollapsed = false,
  onClose,
  onToggleCollapse,
  customItems,
  showCollapseButton = true,
  showFooter = true,
}, ref) => {
  const location = useLocation();
  const navigate = useNavigate();
  const user = useAuthUser();
  const isAuthenticated = useIsAuthenticated();
  
  const [expandedItems, setExpandedItems] = useState<Set<string>>(new Set());
  const sidebarRef = React.useRef<HTMLDivElement>(null);

  // Get navigation routes from config
  const navigationRoutes = getNavigationRoutes();
  
  // Convert route config to navigation items
  const convertRoutesToItems = (routes: typeof navigationRoutes): NavigationItem[] => {
    return routes.map(route => ({
      id: route.path,
      label: route.title,
      path: route.path,
      icon: route.icon ? iconMap[route.icon] : undefined,
      requiredPermissions: route.requiredPermissions,
      requiredRoles: route.requiredRoles,
      children: route.children ? convertRoutesToItems(route.children) : undefined,
    }));
  };

  const navigationItems = customItems || convertRoutesToItems(navigationRoutes);

  // Filter items based on user permissions
  const filterItemsByPermissions = (items: NavigationItem[]): NavigationItem[] => {
    if (!isAuthenticated || !user) return [];

    return items.filter(item => {
      const userRoles = user.role ? [user.role] : [];
      const userPermissions: string[] = user?.permissions || [];

      const hasAccess = !item.requiredPermissions && !item.requiredRoles || 
        canAccessRoute(
          { 
            path: item.path, 
            requiredRoles: item.requiredRoles, 
            requiredPermissions: item.requiredPermissions 
          } as any,
          isAuthenticated,
          userRoles,
          userPermissions
        );

      if (hasAccess && item.children) {
        item.children = filterItemsByPermissions(item.children);
      }

      return hasAccess;
    });
  };

  const visibleItems = filterItemsByPermissions(navigationItems);

  // Handle item click
  const handleItemClick = useCallback((item: NavigationItem) => {
    if (item.disabled) return;

    if (item.children && item.children.length > 0) {
      // Toggle expansion for parent items
      setExpandedItems(prev => {
        const newSet = new Set(prev);
        if (newSet.has(item.id)) {
          newSet.delete(item.id);
        } else {
          newSet.add(item.id);
        }
        return newSet;
      });
    } else {
      // Navigate to item
      if (item.external) {
        window.open(item.path, '_blank');
      } else {
        navigate(item.path);
        if (onClose) onClose(); // Close mobile drawer
      }
    }
  }, [navigate, onClose]);

  // Scroll to item
  const scrollToItem = useCallback((path: string) => {
    const element = sidebarRef.current?.querySelector(`[data-path="${path}"]`);
    if (element) {
      element.scrollIntoView({ behavior: 'smooth', block: 'center' });
    }
  }, []);

  // Expand item
  const expandItem = useCallback((path: string) => {
    setExpandedItems(prev => new Set(prev).add(path));
  }, []);

  // Collapse item
  const collapseItem = useCallback((path: string) => {
    setExpandedItems(prev => {
      const newSet = new Set(prev);
      newSet.delete(path);
      return newSet;
    });
  }, []);

  // Auto-expand parent items for active path
  React.useEffect(() => {
    const findParentPaths = (items: NavigationItem[], targetPath: string, parents: string[] = []): string[] => {
      for (const item of items) {
        const currentPath = [...parents, item.id];
        
        if (item.path === targetPath) {
          return parents;
        }
        
        if (item.children) {
          const found = findParentPaths(item.children, targetPath, currentPath);
          if (found.length > 0) {
            return found;
          }
        }
      }
      return [];
    };

    const parentPaths = findParentPaths(visibleItems, location.pathname);
    if (parentPaths.length > 0) {
      setExpandedItems(prev => new Set([...prev, ...parentPaths]));
    }
  }, [location.pathname, visibleItems]);

  // Expose ref methods
  React.useImperativeHandle(ref, () => ({
    scrollToItem,
    expandItem,
    collapseItem,
  }), [scrollToItem, expandItem, collapseItem]);

  // Handle keyboard navigation
  React.useEffect(() => {
    const handleKeyDown = (e: KeyboardEvent) => {
      if (e.key === 'Escape' && isOpen && onClose) {
        onClose();
      }
    };

    document.addEventListener('keydown', handleKeyDown);
    return () => document.removeEventListener('keydown', handleKeyDown);
  }, [isOpen, onClose]);

  // Render navigation item
  const renderItem = (item: NavigationItem, level = 0) => {
    const isActive = location.pathname === item.path || location.pathname.startsWith(item.path + '/');
    const isExpanded = expandedItems.has(item.id);
    const hasChildren = item.children && item.children.length > 0;
    const ItemIcon = item.icon;

    const itemContent = (
      <div
        className={clsx(
          'flex items-center w-full text-left transition-colors duration-200',
          'group relative',
          level > 0 && 'pl-6',
        )}
      >
        {ItemIcon && (
          <ItemIcon 
            className={clsx(
              'flex-shrink-0 transition-colors duration-200',
              isCollapsed ? 'w-5 h-5' : 'w-4 h-4 mr-3',
              isActive 
                ? 'text-[var(--color-primary)]' 
                : 'text-[var(--text-tertiary)] group-hover:text-[var(--text-primary)]'
            )} 
          />
        )}
        
        {!ItemIcon && level > 0 && (
          <Dot className={clsx(
            'flex-shrink-0 w-4 h-4 mr-3 transition-colors duration-200',
            isActive 
              ? 'text-[var(--color-primary)]' 
              : 'text-[var(--text-tertiary)]'
          )} />
        )}

        {(!isCollapsed || level > 0) && (
          <>
            <span className={clsx(
              'flex-1 truncate transition-colors duration-200 text-sm font-medium',
              isActive 
                ? 'text-[var(--color-primary)]' 
                : 'text-[var(--text-primary)] group-hover:text-[var(--text-primary)]'
            )}>
              {item.label}
            </span>

            {item.badge && (
              <Badge
                variant={item.badge.variant || 'default'}
                size="sm"
                className="ml-2 text-xs"
              >
                {item.badge.text}
              </Badge>
            )}

            {hasChildren && (
              <ChevronDown className={clsx(
                'flex-shrink-0 w-4 h-4 ml-2 transition-transform duration-200',
                isExpanded && 'transform rotate-180',
                isActive 
                  ? 'text-[var(--color-primary)]' 
                  : 'text-[var(--text-tertiary)] group-hover:text-[var(--text-primary)]'
              )} />
            )}
          </>
        )}
      </div>
    );

    const button = (
      <button
        onClick={() => handleItemClick(item)}
        disabled={item.disabled}
        data-path={item.path}
        className={clsx(
          'w-full rounded-lg transition-all duration-200',
          'focus:outline-none focus:ring-2 focus:ring-[var(--color-primary)]/20',
          isActive && 'bg-[var(--color-primary)]/10 border-l-2 border-[var(--color-primary)]',
          !isActive && 'hover:bg-[var(--bg-secondary)]',
          item.disabled && 'opacity-50 cursor-not-allowed',
          isCollapsed && !hasChildren ? 'flex justify-center items-center p-2 mx-1' : 'p-3'
        )}
        aria-expanded={hasChildren ? isExpanded : undefined}
        aria-current={isActive ? 'page' : undefined}
        title={isCollapsed ? item.label : undefined}
      >
        {itemContent}
      </button>
    );

    return (
      <li key={item.id} className="relative">
        {isCollapsed && !hasChildren && ItemIcon ? (
          <Tooltip content={item.label} side="right">
            {button}
          </Tooltip>
        ) : (
          button
        )}

        {hasChildren && isExpanded && (!isCollapsed || level > 0) && (
          <ul className="mt-1 space-y-1 pl-4">
            {item.children?.map(child => renderItem(child, level + 1))}
          </ul>
        )}
      </li>
    );
  };

  if (!isAuthenticated) {
    return null;
  }

  return (
    <>
      {/* Desktop Sidebar */}
      <aside
        ref={sidebarRef}
        className={clsx(
          'fixed left-0 top-[var(--header-height)] bottom-0',
          'bg-[var(--bg-primary)] border-r border-[var(--border-primary)]',
          'transition-all duration-300 ease-in-out z-[var(--z-fixed)]',
          'hidden lg:flex lg:flex-col',
          isCollapsed ? 'w-[var(--sidebar-collapsed-width)]' : 'w-[var(--sidebar-width)]',
          className
        )}
        aria-label="Navegación principal"
      >
        {/* Navigation */}
        <nav className={clsx('flex-1 overflow-y-auto', isCollapsed ? 'px-1 py-4' : 'p-4')}>
          <ul className={clsx(isCollapsed ? 'space-y-1' : 'space-y-2')}>
            {visibleItems.map(item => renderItem(item))}
          </ul>
        </nav>

        {/* Collapse button */}
        {showCollapseButton && (
          <div className={clsx('border-t border-[var(--border-primary)]', isCollapsed ? 'p-2' : 'p-4')}>
            <Button
              variant="ghost"
              size="sm"
              onClick={onToggleCollapse}
              className={clsx(
                'w-full flex items-center justify-center',
                isCollapsed ? 'p-2' : 'px-4 py-2'
              )}
              aria-label={isCollapsed ? 'Expandir sidebar' : 'Contraer sidebar'}
            >
              {isCollapsed ? (
                <ChevronRight className="w-4 h-4" />
              ) : (
                <>
                  <ChevronLeft className="w-4 h-4 mr-2" />
                  <span className="text-sm">Contraer</span>
                </>
              )}
            </Button>
          </div>
        )}

        {/* Footer */}
        {showFooter && !isCollapsed && (
          <div className="p-4 border-t border-[var(--border-primary)]">
            <div className="text-xs text-[var(--text-tertiary)] text-center">
              Panadería IA v2.0.0
            </div>
          </div>
        )}
      </aside>

      {/* Mobile Drawer */}
      <aside
        className={clsx(
          'fixed left-0 top-[var(--header-height)] bottom-0 w-[var(--sidebar-width)]',
          'bg-[var(--bg-primary)] border-r border-[var(--border-primary)]',
          'transition-transform duration-300 ease-in-out z-[var(--z-fixed)]',
          'lg:hidden flex flex-col',
          isOpen ? 'translate-x-0' : '-translate-x-full'
        )}
        aria-label="Navegación principal"
        role="dialog"
        aria-modal="true"
      >
        {/* Mobile header */}
        <div className="flex items-center justify-between p-4 border-b border-[var(--border-primary)]">
          <h2 className="text-lg font-semibold text-[var(--text-primary)]">
            Navegación
          </h2>
          <Button
            variant="ghost"
            size="sm"
            onClick={onClose}
            className="p-2"
            aria-label="Cerrar navegación"
          >
            <Menu className="w-4 h-4" />
          </Button>
        </div>

        {/* Navigation */}
        <nav className="flex-1 p-4 overflow-y-auto">
          <ul className="space-y-2">
            {visibleItems.map(item => renderItem(item))}
          </ul>
        </nav>

        {/* Footer */}
        {showFooter && (
          <div className="p-4 border-t border-[var(--border-primary)]">
            <div className="text-xs text-[var(--text-tertiary)] text-center">
              Panadería IA v2.0.0
            </div>
          </div>
        )}
      </aside>
    </>
  );
});

Sidebar.displayName = 'Sidebar';