'use client';

import { useState, useRef, useEffect, useMemo } from 'react';
import { Bell, ChevronDown, Wifi, Menu, Building2, Check, Settings, KeyRound, LogOut } from 'lucide-react';
import Link from 'next/link';
import { usePathname } from 'next/navigation';
import { useAuth } from '@client/contexts/AuthContext';
import { listBranches, switchBranch, type Branch } from '@client/api/branches';
import { listNotifications, markAllNotificationsRead, type Notification } from '@client/api/notifications';
import { toast } from 'sonner';
import { useLanguage } from '@client/contexts/LanguageContext';

interface TopbarProps {
  onMobileMenuToggle?: () => void;
  pageTitle?: string;
  pageSubtitle?: string;
  isAdminMode?: boolean;
}

function formatTimeAgo(dateStr: string, t: (k: string, f: string, v?: Record<string, string | number>) => string): string {
  if (!dateStr) return '';
  const diff = Date.now() - new Date(dateStr).getTime();
  const mins = Math.floor(diff / 60000);
  if (mins < 1) return t('common.justNow', 'just now');
  if (mins < 60) return t('common.minAgo', '{{count}} min ago', { count: mins });
  const hrs = Math.floor(mins / 60);
  if (hrs < 24) return t('common.hrAgo', '{{count}} hr ago', { count: hrs });
  return t('common.daysAgo', '{{count}}d ago', { count: Math.floor(hrs / 24) });
}

export default function Topbar({ onMobileMenuToggle, pageTitle, pageSubtitle, isAdminMode = false }: TopbarProps) {
  const { t } = useLanguage();
  const tRef = useRef(t);
  useEffect(() => { tRef.current = t; }, [t]);
  const [showNotifications, setShowNotifications] = useState(false);
  const [showBranchSwitcher, setShowBranchSwitcher] = useState(false);
  const [showProfileMenu, setShowProfileMenu] = useState(false);
  const [activeBranches, setActiveBranches] = useState<Branch[]>([]);
  const [activeBranch, setActiveBranch] = useState<Branch | null>(null);
  const [switching, setSwitching] = useState(false);
  const [notifications, setNotifications] = useState<Notification[]>([]);
  const [unreadCount, setUnreadCount] = useState(0);
  const profileMenuRef = useRef<HTMLDivElement>(null);
  const branchMenuRef = useRef<HTMLDivElement>(null);
  const notifMenuRef = useRef<HTMLDivElement>(null);
  const shownEscalationKeys = useRef<Set<string>>(new Set());
  const sseConnectedRef = useRef(false);
  // Tracks the restaurant name across renders to detect a post-save change
  // (undefined = not yet seen, distinguishes "first render" from "name is null").
  const prevRestaurantNameRef = useRef<string | null | undefined>(undefined);
  const pathname = usePathname();
  const { userRecord, branchId: authBranchId, sessionBranchId, loading: authLoading, signOut } = useAuth();
  const userRecordRef = useRef(userRecord);
  userRecordRef.current = userRecord;

  const userName = userRecord?.name || t('common.user', 'User');
  const userEmail = userRecord?.email || '';
  const userInitials = userName.split(' ').map((n: string) => n[0]).join('').toUpperCase().slice(0, 2) || 'U';
  // Owner is the only role allowed to use the "All branches" (restaurant-wide)
  // view. Staff and managers are pinned to a single branch and the server
  // 403s any null-branch switch from them — gating the UI here too keeps the
  // dropdown from showing an option they can't use.
  const isOwner = userRecord?.role === 'owner';
  // The session is in "All branches" mode when the JWT carries branchId=null.
  // We must check the *literal* session branch (`sessionBranchId`), NOT the
  // coalesced `authBranchId` — `/api/auth/me` falls back the coalesced field
  // to the user's pinned default for legacy per-branch UIs, which would mask
  // the all-branches state. For owners, null is a deliberate choice; for
  // non-owners it can't happen (the server pin guard prevents it), but we
  // still require isOwner as defense-in-depth.
  const isAllBranchesView = isOwner && sessionBranchId === null;

  const allBranchesLabel = useMemo(
    () =>
      userRecord?.restaurants?.name
        ? `${userRecord.restaurants.name} — ${t('topbar.allBranches', 'All Branches')}`
        : t('topbar.allBranches', 'All Branches'),
    [userRecord?.restaurants?.name, t]
  );

  const refreshBranches = (jwtBranchId?: string | null, autoSwitch = false) => {
    listBranches()
      .then(async res => {
        const all = res.branches ?? [];
        const active = all.filter(b => b.isActive);
        setActiveBranches(active);

        if (jwtBranchId) {
          const match = active.find(b => b.id === jwtBranchId);
          if (match) {
            setActiveBranch(match);
          } else if (autoSwitch && active.length > 0) {
            setActiveBranch(active[0]);
            try {
              await switchBranch(active[0].id);
              window.location.reload();
            } catch {}
          } else {
            setActiveBranch(active[0] ?? null);
          }
        } else if (isOwner) {
          // Owner with null JWT branch = "All branches" view. Don't pick a
          // default — keep activeBranch null so the button shows the
          // all-branches label and we don't silently re-pin the session.
          setActiveBranch(null);
        } else {
          setActiveBranch(prev => {
            const existing = prev ? active.find(b => b.id === prev.id) : null;
            return existing ?? active[0] ?? null;
          });
        }
      })
      .catch(() => {});
  };

  useEffect(() => {
    if (authLoading) return;
    // Pass the literal session branch (`sessionBranchId`) — using the
    // coalesced `authBranchId` here would cause owners in All branches mode
    // to silently re-pin to their DB default branch on every reload.
    refreshBranches(sessionBranchId, true);
    // isOwner is derived from userRecord which is in the same auth payload,
    // so it changes in lockstep with sessionBranchId/authLoading and doesn't
    // need its own dep.
    // eslint-disable-next-line react-hooks/exhaustive-deps
  }, [sessionBranchId, authLoading]);

  // Re-sync the branch-switcher display state whenever the restaurant name
  // changes after mount (e.g. a profile save that calls refreshUserRecord()).
  // The sessionBranchId/authLoading effect handles the initial load; this
  // effect handles the name-change case where neither of those deps change.
  useEffect(() => {
    if (authLoading) return;
    const name = userRecord?.restaurants?.name ?? null;
    const prev = prevRestaurantNameRef.current;
    prevRestaurantNameRef.current = name;
    // undefined → first render, handled by the sessionBranchId effect above.
    // Same name → no profile rename occurred, nothing to do.
    if (prev === undefined || prev === name) return;
    refreshBranches(sessionBranchId, false);
    // refreshBranches closes over sessionBranchId; it is intentionally omitted
    // from deps so the effect only fires on actual name changes, not on every
    // session-branch switch (which the other effect already handles).
    // eslint-disable-next-line react-hooks/exhaustive-deps
  }, [userRecord?.restaurants?.name, authLoading]);

  useEffect(() => {
    const load = () => {
      listNotifications({ limit: '10' })
        .then(res => {
          const incoming = res.notifications ?? [];
          setNotifications(prev => {
            const prevIds = new Set(prev.map(n => n.id));
            const brandNew = incoming.filter(n => !n.isRead && !prevIds.has(n.id));
            brandNew.forEach(n => {
              if (n.type === 'escalation') {
                const dedupeKey = `notif-${n.id}`;
                if (!shownEscalationKeys.current.has(dedupeKey)) {
                  shownEscalationKeys.current.add(dedupeKey);
                  if (!sseConnectedRef.current) {
                    toast.warning(n.title, { description: n.message || undefined, duration: 8000 });
                  }
                }
              } else {
                toast(n.title, { description: n.message || undefined, duration: 5000 });
              }
            });
            return incoming;
          });
          setUnreadCount(res.unread ?? 0);
        })
        .catch(() => {});
    };
    load();
    const id = setInterval(load, 5_000);
    return () => clearInterval(id);
  }, []);

  useEffect(() => {
    let es: EventSource | null = null;
    let retryTimer: ReturnType<typeof setTimeout> | null = null;

    function connect() {
      es = new EventSource('/api/alerts/escalations');
      es.onopen = () => {
        sseConnectedRef.current = true;
      };
      es.onmessage = (ev) => {
        try {
          const data = JSON.parse(ev.data) as { conversationId?: string; reason?: string };
          if (!data.conversationId) return;
          const dedupeKey = `sse-${data.conversationId}`;
          if (shownEscalationKeys.current.has(dedupeKey)) return;
          shownEscalationKeys.current.add(dedupeKey);
          toast.warning(tRef.current('topbar.humanAgentRequest', 'Customer requesting human agent'), {
            description: data.reason || tRef.current('topbar.humanAgentDesc', 'A customer needs an agent'),
            duration: 10000,
          });
        } catch { /* ignore parse errors */ }
      };
      es.onerror = () => {
        sseConnectedRef.current = false;
        es?.close();
        if (!userRecordRef.current?.restaurant_id) return;
        retryTimer = setTimeout(connect, 10_000);
      };
    }

    connect();
    return () => {
      sseConnectedRef.current = false;
      es?.close();
      if (retryTimer) clearTimeout(retryTimer);
    };
  }, []);

  const handleMarkAllRead = async () => {
    try {
      await markAllNotificationsRead();
      setNotifications(prev => prev.map(n => ({ ...n, isRead: true })));
      setUnreadCount(0);
    } catch {}
  };

  const handleSwitchBranch = async (branch: Branch) => {
    if (branch.id === activeBranch?.id) { setShowBranchSwitcher(false); return; }
    setSwitching(true);
    setShowBranchSwitcher(false);
    try {
      await switchBranch(branch.id);
      window.location.reload();
    } catch {
      setSwitching(false);
    }
  };

  // Owner-only path that clears the session's active branch and reloads
  // into the restaurant-wide view. No-op when already in that view.
  const handleSwitchToAllBranches = async () => {
    if (isAllBranchesView) { setShowBranchSwitcher(false); return; }
    setSwitching(true);
    setShowBranchSwitcher(false);
    try {
      await switchBranch(null);
      window.location.reload();
    } catch {
      setSwitching(false);
    }
  };

  const closeAllMenus = () => {
    setShowNotifications(false);
    setShowBranchSwitcher(false);
    setShowProfileMenu(false);
  };

  useEffect(() => {
    const handleClickOutside = (e: MouseEvent) => {
      const target = e.target as Node;
      if (showProfileMenu && profileMenuRef.current && !profileMenuRef.current.contains(target)) {
        setShowProfileMenu(false);
      }
      if (showBranchSwitcher && branchMenuRef.current && !branchMenuRef.current.contains(target)) {
        setShowBranchSwitcher(false);
      }
      if (showNotifications && notifMenuRef.current && !notifMenuRef.current.contains(target)) {
        setShowNotifications(false);
      }
    };
    if (showProfileMenu || showBranchSwitcher || showNotifications) {
      document.addEventListener('mousedown', handleClickOutside);
    }
    return () => document.removeEventListener('mousedown', handleClickOutside);
  }, [showProfileMenu, showBranchSwitcher, showNotifications]);

  useEffect(() => {
    closeAllMenus();
  }, [pathname]);

  const getNotifIcon = (type: string) => {
    switch (type) {
      case 'order': return <span className="w-2 h-2 rounded-full" style={{ backgroundColor: 'hsl(var(--danger))' }} />;
      case 'ai': return <span className="w-2 h-2 rounded-full" style={{ backgroundColor: 'hsl(var(--warning))' }} />;
      case 'billing': return <span className="w-2 h-2 rounded-full" style={{ backgroundColor: 'hsl(var(--success))' }} />;
      default: return <span className="w-2 h-2 rounded-full" style={{ backgroundColor: 'hsl(var(--info))' }} />;
    }
  };

  return (
    <header
      className="h-16 flex items-center justify-between px-4 lg:px-6 shrink-0"
      style={{
        backgroundColor: isAdminMode ? 'hsl(231, 40%, 12%)' : 'hsl(var(--surface))',
        borderBottom: `1px solid ${isAdminMode ? 'rgba(255,255,255,0.1)' : 'hsl(var(--border))'}`,
      }}
    >
      <div className="flex items-center gap-3">
        <button className="lg:hidden btn-ghost p-2" onClick={onMobileMenuToggle} aria-label={t('topbar.toggleMenu', 'Toggle menu')} style={{ color: isAdminMode ? 'rgba(255,255,255,0.7)' : undefined }}>
          <Menu size={20} />
        </button>
        {pageTitle && (
          <div>
            <h1 className="text-base font-semibold" style={{ color: isAdminMode ? 'white' : 'hsl(var(--foreground))' }}>{pageTitle}</h1>
            {pageSubtitle && <p className="text-xs" style={{ color: isAdminMode ? 'rgba(255,255,255,0.5)' : 'hsl(var(--muted-foreground))' }}>{pageSubtitle}</p>}
          </div>
        )}
      </div>

      <div className="flex items-center gap-2">
        {!isAdminMode && activeBranches.length > 0 && (
          <div className="relative" ref={branchMenuRef}>
            <button
              className="hidden sm:flex items-center gap-2 px-3 py-1.5 rounded-lg text-sm font-medium transition-colors"
              style={{ backgroundColor: 'hsl(var(--muted))', border: '1px solid hsl(var(--border))', color: 'hsl(var(--foreground))' }}
              onClick={() => {
                if (!showBranchSwitcher) refreshBranches(sessionBranchId, false);
                setShowBranchSwitcher(!showBranchSwitcher);
                setShowNotifications(false);
                setShowProfileMenu(false);
              }}
              disabled={switching}
            >
              {switching ? (
                <span className="w-3.5 h-3.5 border-2 border-current/30 border-t-current rounded-full animate-spin" />
              ) : (
                <Building2 size={14} style={{ color: 'hsl(var(--primary))' }} />
              )}
              <span>
                {isAllBranchesView
                  ? allBranchesLabel
                  : (activeBranch?.name ?? t('topbar.selectBranch', 'Select Branch'))}
              </span>
              <ChevronDown size={13} style={{ color: 'hsl(var(--muted-foreground))' }} />
            </button>

            {showBranchSwitcher && (
              <div className="absolute right-0 top-full mt-2 w-64 rounded-xl shadow-xl z-50 fade-in" style={{ backgroundColor: 'hsl(var(--surface))', border: '1px solid hsl(var(--border))', boxShadow: 'var(--shadow-xl)' }}>
                <div className="px-4 py-3" style={{ borderBottom: '1px solid hsl(var(--border))' }}>
                  <p className="text-xs font-semibold uppercase tracking-wider" style={{ color: 'hsl(var(--muted-foreground))' }}>{t('topbar.switchBranch', 'Switch Branch')}</p>
                </div>
                <div className="py-1">
                  {isOwner && (
                    <>
                      <button
                        className="w-full flex items-center justify-between px-4 py-2.5 transition-colors hover:bg-muted/50 text-left"
                        onClick={handleSwitchToAllBranches}
                      >
                        <div className="flex items-center gap-3">
                          <div className="w-7 h-7 rounded-lg flex items-center justify-center" style={{ backgroundColor: 'hsl(var(--primary-light))' }}>
                            <Building2 size={13} style={{ color: 'hsl(var(--primary))' }} />
                          </div>
                          <div>
                            <p className="text-sm font-medium" style={{ color: 'hsl(var(--foreground))' }}>
                              {t('topbar.allBranches', 'All Branches')}
                            </p>
                            <p className="text-xs" style={{ color: 'hsl(var(--muted-foreground))' }}>
                              {t('topbar.allBranchesDesc', 'Restaurant-wide view')}
                            </p>
                          </div>
                        </div>
                        {isAllBranchesView && (
                          <Check size={14} style={{ color: 'hsl(var(--primary))' }} />
                        )}
                      </button>
                      <div className="my-1" style={{ borderTop: '1px solid hsl(var(--border))' }} />
                    </>
                  )}
                  {activeBranches.map(branch => (
                    <button
                      key={branch.id}
                      className="w-full flex items-center justify-between px-4 py-2.5 transition-colors hover:bg-muted/50 text-left"
                      onClick={() => handleSwitchBranch(branch)}
                    >
                      <div className="flex items-center gap-3">
                        <div className="w-7 h-7 rounded-lg flex items-center justify-center" style={{ backgroundColor: 'hsl(var(--primary-light))' }}>
                          <Building2 size={13} style={{ color: 'hsl(var(--primary))' }} />
                        </div>
                        <div>
                          <p className="text-sm font-medium" style={{ color: 'hsl(var(--foreground))' }}>{branch.name}</p>
                          {branch.address && <p className="text-xs" style={{ color: 'hsl(var(--muted-foreground))' }}>{branch.address}</p>}
                        </div>
                      </div>
                      {activeBranch?.id === branch.id && (
                        <Check size={14} style={{ color: 'hsl(var(--primary))' }} />
                      )}
                    </button>
                  ))}
                </div>
                <div className="px-4 py-2.5" style={{ borderTop: '1px solid hsl(var(--border))' }}>
                  <Link href="/branch-management" className="text-xs font-semibold w-full text-center block" style={{ color: 'hsl(var(--primary))' }}>
                    {t('topbar.manageBranches', 'Manage Branches →')}
                  </Link>
                </div>
              </div>
            )}
          </div>
        )}

        {isAdminMode && (
          <div
            className="hidden sm:flex items-center px-2.5 py-1 rounded-full text-xs font-semibold"
            style={{ backgroundColor: 'rgba(255,255,255,0.08)', border: '1px solid rgba(255,255,255,0.12)', color: 'rgba(255,255,255,0.55)' }}
          >
            v{process.env.NEXT_PUBLIC_APP_VERSION ?? ''}
          </div>
        )}

        <div
          className="hidden sm:flex items-center gap-2 px-3 py-1.5 rounded-full text-xs font-semibold"
          style={isAdminMode
            ? { backgroundColor: 'rgba(255,255,255,0.1)', border: '1px solid rgba(255,255,255,0.15)', color: 'rgba(255,255,255,0.8)' }
            : { backgroundColor: 'hsl(var(--success-bg))', border: '1px solid hsl(var(--success-border))', color: 'hsl(var(--success))' }
          }
        >
          <span className="w-1.5 h-1.5 rounded-full bg-current animate-pulse" />
          <Wifi size={12} />
          <span>{isAdminMode ? t('topbar.platformOnline', 'Platform Online') : t('topbar.agentOnline', 'Agent Online')}</span>
        </div>

        <div className="relative" ref={notifMenuRef}>
          <button
            className="btn-ghost p-2 relative"
            onClick={() => { setShowNotifications(!showNotifications); setShowBranchSwitcher(false); setShowProfileMenu(false); }}
            aria-label={t('topbar.notifications', 'Notifications')}
            style={{ color: isAdminMode ? 'rgba(255,255,255,0.7)' : undefined }}
          >
            <Bell size={18} />
            {unreadCount > 0 && (
              <span className="absolute top-1 right-1 w-4 h-4 flex items-center justify-center rounded-full text-white font-bold" style={{ fontSize: '9px', backgroundColor: 'hsl(var(--danger))' }}>
                {unreadCount > 9 ? '9+' : unreadCount}
              </span>
            )}
          </button>

          {showNotifications && (
            <div className="absolute right-0 top-full mt-2 w-80 rounded-xl shadow-xl z-50 fade-in" style={{ backgroundColor: 'hsl(var(--surface))', border: '1px solid hsl(var(--border))', boxShadow: 'var(--shadow-xl)' }}>
              <div className="flex items-center justify-between px-4 py-3" style={{ borderBottom: '1px solid hsl(var(--border))' }}>
                <span className="font-semibold text-sm">{t('topbar.notifications', 'Notifications')}</span>
                <div className="flex items-center gap-2">
                  {unreadCount > 0 && (
                    <>
                      <span className="badge badge-danger text-xs">{unreadCount} {t('topbar.new', 'new')}</span>
                      <button onClick={handleMarkAllRead} className="text-xs font-semibold" style={{ color: 'hsl(var(--primary))' }}>{t('topbar.markAllRead', 'Mark all read')}</button>
                    </>
                  )}
                </div>
              </div>
              <div className="divide-y max-h-72 overflow-y-auto">
                {notifications.length === 0 ? (
                  <div className="px-4 py-6 text-center">
                    <p className="text-xs" style={{ color: 'hsl(var(--muted-foreground))' }}>{t('topbar.noNotifications', 'No notifications yet')}</p>
                  </div>
                ) : (
                  notifications.map(n => (
                    <div
                      key={n.id}
                      className={`flex gap-3 px-4 py-3 cursor-pointer transition-colors hover:bg-muted/50 ${n.isRead ? 'opacity-60' : ''}`}
                      style={!n.isRead ? { backgroundColor: 'hsl(var(--primary-light))' } : {}}
                    >
                      <div className="mt-1.5 shrink-0">{getNotifIcon(n.type)}</div>
                      <div className="flex-1 min-w-0">
                        <p className="text-xs leading-relaxed" style={{ color: 'hsl(var(--foreground))' }}>{n.message}</p>
                        <p className="text-xs mt-0.5" style={{ color: 'hsl(var(--muted-foreground))' }}>{formatTimeAgo(n.createdAt, t)}</p>
                      </div>
                    </div>
                  ))
                )}
              </div>
              <div className="px-4 py-2.5" style={{ borderTop: '1px solid hsl(var(--border))' }}>
                <Link href={isAdminMode ? '/admin/notifications' : '/notifications'} className="text-xs font-semibold w-full text-center block" style={{ color: 'hsl(var(--primary))' }}>
                  {t('topbar.viewAllNotifications', 'View all notifications')}
                </Link>
              </div>
            </div>
          )}
        </div>

        <div className="relative" ref={profileMenuRef}>
          <button
            onClick={() => { setShowProfileMenu(!showProfileMenu); setShowNotifications(false); setShowBranchSwitcher(false); }}
            className="w-8 h-8 rounded-full flex items-center justify-center text-xs font-bold cursor-pointer transition-shadow hover:ring-2 hover:ring-primary/30"
            style={{ backgroundColor: 'hsl(var(--primary-light))', color: 'hsl(var(--primary))' }}
          >
            {userInitials}
          </button>

          {showProfileMenu && (
            <div
              className="absolute right-0 top-full mt-2 w-56 rounded-xl shadow-xl z-50 fade-in"
              style={{ backgroundColor: 'hsl(var(--surface))', border: '1px solid hsl(var(--border))', boxShadow: 'var(--shadow-xl)' }}
            >
              <div className="px-4 py-3" style={{ borderBottom: '1px solid hsl(var(--border))' }}>
                <p className="text-sm font-semibold truncate" style={{ color: 'hsl(var(--foreground))' }}>{userName}</p>
                {userEmail && <p className="text-xs mt-0.5 truncate" style={{ color: 'hsl(var(--muted-foreground))' }}>{userEmail}</p>}
              </div>

              <div className="py-1">
                <Link
                  href={isAdminMode ? '/admin/branding' : '/restaurant-settings'}
                  className="w-full flex items-center gap-3 px-4 py-2.5 text-left transition-colors hover:bg-black/5 text-sm"
                  style={{ color: 'hsl(var(--foreground))' }}
                  onClick={() => setShowProfileMenu(false)}
                >
                  <Settings size={15} style={{ color: 'hsl(var(--muted-foreground))' }} />
                  {t('topbar.settings', 'Settings')}
                </Link>
                <Link
                  href={isAdminMode ? '/admin/change-password' : '/change-password'}
                  className="w-full flex items-center gap-3 px-4 py-2.5 text-left transition-colors hover:bg-black/5 text-sm"
                  style={{ color: 'hsl(var(--foreground))' }}
                  onClick={() => setShowProfileMenu(false)}
                >
                  <KeyRound size={15} style={{ color: 'hsl(var(--muted-foreground))' }} />
                  {t('topbar.changePassword', 'Change Password')}
                </Link>
              </div>

              <div className="py-1" style={{ borderTop: '1px solid hsl(var(--border))' }}>
                <button
                  onClick={() => { setShowProfileMenu(false); signOut(); }}
                  className="w-full flex items-center gap-3 px-4 py-2.5 text-left transition-colors hover:bg-black/5 text-sm"
                  style={{ color: 'hsl(var(--danger))' }}
                >
                  <LogOut size={15} />
                  {t('topbar.logOut', 'Log Out')}
                </button>
              </div>
            </div>
          )}
        </div>
      </div>
    </header>
  );
}
