/* hub.jsx — Project Hub (thiết kế BIM-UP): Shell + RightRail + assembly.
   Dùng window.HubIcon (không đụng Icon workspace); wiring dữ liệu thật. */
(function () {
  const { useState } = React;
  const Icon = window.HubIcon;
  const firstName = (s) => { const p = (s || "").trim().split(/\s+/); return p[p.length - 1] || s || "bạn"; };

  /* ---------- Sidebar ---------- */
  function Sidebar({ section, setSection, projects, onOpen, auth, onGoSettings }) {
    const name = (auth && auth.profile && auth.profile.full_name) || (auth && auth.user && auth.user.email) || "Khách";
    const role = (auth && auth.profile && auth.profile.role) || "—";
    const taskN = String((window.__hubTasks || 0));
    const NAV = [
      { id: "home", label: "Trang chủ", icon: "home3" },
      { id: "projects", label: "Dự án", icon: "layers", count: String(projects.length) },
      { id: "tasks", label: "Nhiệm vụ", icon: "checkCircle", count: taskN },
      { id: "members", label: "Thành viên", icon: "users" },
      { id: "settings", label: "Cài đặt", icon: "gear" },
    ];
    return (
      <aside className="side">
        <div className="side-brand">
          <div className="logo-mark">
            <img src="/cde/bimup-mark.png" alt="BIM-UP" style={{ width: "100%", height: "100%", objectFit: "contain", display: "block" }} />
          </div>
          <div><div className="logo-word">BIM<b>·UP</b></div><div className="logo-sub">Common Data Environment</div></div>
        </div>
        <div className="side-scroll">
          <div className="nav-label">Điều hướng</div>
          {NAV.map(n => {
            const Ico = Icon[n.icon];
            return (
              <div key={n.id} className={"nav-item " + (section === n.id ? "active" : "")} onClick={() => setSection(n.id)}>
                <Ico size={18} /><span className="lbl">{n.label}</span>
                {n.count && <span className="nav-count">{n.count}</span>}
              </div>
            );
          })}
          <div className="nav-label">Dự án của tôi</div>
          {projects.map(p => (
            <div key={p.code} className="proj-item" onClick={() => onOpen(p)} title={p.name}>
              <span className="proj-dot" style={{ background: p.accent || "var(--bimup-2)" }} />
              <span className="proj-name"><span className="t">{p.name}</span><span className="s">{p.role} · {p.docs || 0} hồ sơ</span></span>
              <span className="proj-code">{p.code}</span>
            </div>
          ))}
        </div>
        <div className="side-foot">
          <div className="mini-prof" onClick={onGoSettings}>
            <Avatar name={name} size={36} url={auth && auth.profile && auth.profile.avatar_url} />
            <div style={{ flex: 1, minWidth: 0 }}>
              <div style={{ fontSize: 13.5, fontWeight: 800, lineHeight: 1.2, whiteSpace: "nowrap", overflow: "hidden", textOverflow: "ellipsis" }}>{name}</div>
              <div style={{ fontSize: 11.5, color: "var(--ink-3)", fontWeight: 600 }}>{role}</div>
            </div>
            <Icon.chevUD size={15} color="var(--ink-4)" />
          </div>
        </div>
      </aside>
    );
  }

  /* ---------- TopBar (+ notif popover + avatar menu) ---------- */
  function TopBar({ theme, setTheme, auth, notifs, setNotifs, onLogout, onGoSettings, onCreate }) {
    const [notifOpen, setNotifOpen] = useState(false);
    const [menuOpen, setMenuOpen] = useState(false);
    const name = (auth && auth.profile && auth.profile.full_name) || (auth && auth.user && auth.user.email) || "Khách";
    const role = (auth && auth.profile && auth.profile.role) || "—";
    const unread = notifs.filter(n => !n.read).length;
    const close = () => { setNotifOpen(false); setMenuOpen(false); };
    const markAll = () => setNotifs(notifs.map(n => ({ ...n, read: true })));
    const markOne = (id) => setNotifs(notifs.map(n => n.id === id ? { ...n, read: true } : n));

    return (
      <header className="topbar">
        <div className="search"><Icon.search size={17} /><span style={{ flex: 1 }}>Tìm dự án, hồ sơ, người dùng…</span><span className="kbd">⌘K</span></div>
        <div style={{ marginLeft: "auto", display: "flex", alignItems: "center", gap: 10 }}>
          {onCreate && <button className="btn brand" onClick={onCreate}><Icon.plus size={16} /> Tạo</button>}

          <div className="hub-top-bell">
            <button className="icon-btn" onClick={() => { setNotifOpen(v => !v); setMenuOpen(false); }} title="Thông báo">
              <Icon.bell size={18} />{unread > 0 && <span className="badge-dot">{unread}</span>}
            </button>
            {notifOpen && (
              <div className="hub-pop">
                <div className="hub-pop-head"><span>Thông báo</span><button className="hub-pop-mark" onClick={markAll}>Đã đọc hết</button></div>
                {notifs.map(n => (
                  <div key={n.id} className={"hub-pop-item " + (n.read ? "" : "unread")} onClick={() => markOne(n.id)}>
                    <span className="x" dangerouslySetInnerHTML={{ __html: n.text }} /><span className="t">{n.time}</span>
                  </div>
                ))}
                {!notifs.length && <div className="hub-pop-empty">Không có thông báo</div>}
              </div>
            )}
          </div>

          <button className="icon-btn" onClick={() => setTheme(theme === "dark" ? "light" : "dark")} title="Sáng / Tối">
            {theme === "dark" ? <Icon.sun size={18} /> : <Icon.moon size={18} />}
          </button>

          <div className="hub-top-user">
            <button className="hub-avatar-btn" onClick={() => { setMenuOpen(v => !v); setNotifOpen(false); }}>
              <Avatar name={name} size={38} url={auth && auth.profile && auth.profile.avatar_url} />
            </button>
            {menuOpen && (
              <div className="hub-menu">
                <div className="hub-menu-id"><div className="n">{name}</div><div className="r">{role}</div></div>
                <div className="hub-menu-item" onClick={() => { onGoSettings(); close(); }}><Icon.users size={15} /> Hồ sơ của tôi</div>
                <div className="hub-menu-item" onClick={() => { onGoSettings(); close(); }}><Icon.gear size={15} /> Cài đặt</div>
                <div className="hub-menu-item" onClick={() => { setTheme(theme === "dark" ? "light" : "dark"); close(); }}>
                  {theme === "dark" ? <Icon.sun size={15} /> : <Icon.moon size={15} />} Đổi giao diện</div>
                <div className="hub-menu-sep" />
                <div className="hub-menu-item danger" onClick={onLogout}><Icon.ban size={15} /> Đăng xuất</div>
              </div>
            )}
          </div>
        </div>
        {(notifOpen || menuOpen) && <div className="hub-overlay" onClick={close} />}
      </header>
    );
  }

  /* ---------- HomeHero ---------- */
  function HomeHero({ auth, projects, tasksN, unread }) {
    const h = new Date().getHours();
    const greet = h < 11 ? "Chào buổi sáng" : h < 14 ? "Chào buổi trưa" : h < 18 ? "Chào buổi chiều" : "Chào buổi tối";
    const name = (auth && auth.profile && auth.profile.full_name) || (auth && auth.user && auth.user.email) || "bạn";
    const stats = [
      { ic: "layers", v: String(projects.length), l: "Dự án của bạn" },
      { ic: "checkCircle", v: String(tasksN), l: "Nhiệm vụ liên quan" },
      { ic: "bell", v: String(unread), l: "Thông báo chưa đọc" },
    ];
    return (
      <div className="hero fu">
        <div className="hero-grid" />
        <div className="hero-sub">{greet} 👋</div>
        <div className="hero-title">Chào mừng trở lại, <b>{firstName(name)}</b></div>
        <div className="hero-stats">
          {stats.map((s, i) => { const Ico = Icon[s.ic]; return (
            <div className="hstat" key={i}>
              <div className="hstat-ico"><Ico size={19} /></div>
              <div><div className="v tnum">{s.v}</div><div className="l">{s.l}</div></div>
            </div>); })}
        </div>
      </div>
    );
  }

  /* ---------- Right rail ---------- */
  function Notifications({ notifs, setNotifs }) {
    const unread = notifs.filter(n => !n.read).length;
    const markAll = () => setNotifs(notifs.map(n => ({ ...n, read: true })));
    return (
      <div className="rcard fu">
        <div className="rcard-head">
          <div style={{ display: "flex", alignItems: "center", gap: 8, minWidth: 0 }}>
            <span className="rcard-title">Thông báo</span>
            {unread > 0 && <span style={{ fontSize: 11, fontWeight: 800, color: "#fff", background: "var(--bimup-2)", borderRadius: 99, padding: "1px 8px", whiteSpace: "nowrap", flex: "none" }}>{unread} mới</span>}
          </div>
          <span className="rcard-link" onClick={markAll}>Đã đọc hết</span>
        </div>
        <div>
          {notifs.map(n => {
            const t = TYPE[n.type] || TYPE.other; const Ico = Icon[t.ic] || Icon.dots;
            return (
              <div key={n.id} className={"noti " + (n.read ? "" : "unread")}>
                <div className="noti-ico" style={{ background: tint(t.c), color: t.c }}><Ico size={16} /></div>
                <div style={{ flex: 1, minWidth: 0 }}>
                  <div className="noti-txt" dangerouslySetInnerHTML={{ __html: n.text }} />
                  <div className="noti-time">{n.time}</div>
                </div>
                {!n.read && <span className="noti-unreaddot" />}
              </div>
            );
          })}
        </div>
      </div>
    );
  }

  function OnlineMembers({ members }) {
    const onlineIds = (typeof window.useOnlineIds === "function") ? window.useOnlineIds() : new Set();
    const withOn = members.map(m => ({ ...m, online: onlineIds.has(m.id) }));
    const online = withOn.filter(m => m.online);
    const offline = withOn.filter(m => !m.online);
    const Row = ({ m }) => (
      <div className="online-row">
        <Avatar name={m.name} size={36} ring={m.online} url={m.avatar_url} />
        <div style={{ flex: 1, minWidth: 0 }}><div className="online-name">{m.name}</div><div className="online-role">{m.role || "—"}</div></div>
      </div>
    );
    return (
      <div className="rcard fu">
        <div className="rcard-head">
          <div style={{ display: "flex", alignItems: "center", gap: 8 }}>
            <span className="rcard-title">Thành viên</span>
            <span style={{ display: "inline-flex", alignItems: "center", gap: 6, fontSize: 12, fontWeight: 700, color: "var(--ink-3)" }}>
              <span style={{ width: 7, height: 7, borderRadius: 99, background: "var(--ok)" }} /> {online.length} online
            </span>
          </div>
          <span className="rcard-link">Mời</span>
        </div>
        <div style={{ paddingBottom: 8 }}>
          {online.map(m => <Row key={m.id} m={m} />)}
          {offline.length > 0 && <div style={{ fontSize: 10.5, fontWeight: 700, letterSpacing: ".1em", color: "var(--ink-4)", padding: "12px 18px 6px" }}>NGOẠI TUYẾN</div>}
          {offline.map(m => <div key={m.id} style={{ opacity: .6 }}><Row m={m} /></div>)}
        </div>
      </div>
    );
  }

  /* ---------- Create project modal (admin) ---------- */
  const PROJ_ACCENTS = ["#2563eb", "#0d9488", "#7c3aed", "#e2683c"];
  const PHASE_HINTS = ["Chuẩn bị đầu tư", "Thiết kế cơ sở", "Thiết kế kỹ thuật",
    "Thiết kế bản vẽ thi công", "Thi công", "Bàn giao", "Vận hành"];

  function CreateProjectModal({ onClose, onCreated }) {
    const [f, setF] = useState({ code: "", name: "", client: "", phase: "", accent: PROJ_ACCENTS[0] });
    const [busy, setBusy] = useState(false);
    const [err, setErr] = useState("");
    const set = (k, v) => setF(s => ({ ...s, [k]: v }));
    const submit = async () => {
      if (!f.code.trim()) { setErr("Nhập mã dự án"); return; }
      if (!f.name.trim()) { setErr("Nhập tên dự án"); return; }
      setBusy(true); setErr("");
      try {
        const proj = await cdeData.createProject(f);
        if (onCreated) await onCreated(proj);   // cha đóng modal + reload danh sách
      } catch (e) { setErr(e.message || "Tạo dự án thất bại"); setBusy(false); }
    };
    const inp = { width: "100%", height: 40, padding: "0 12px", borderRadius: 10, border: "1px solid var(--line)", background: "var(--surface)", color: "var(--ink)", font: "inherit", fontSize: 13.5, fontWeight: 600, outline: "none", marginTop: 6 };
    const lb = { display: "block", fontSize: 11.5, fontWeight: 700, color: "var(--ink-3)", marginTop: 14 };
    return (
      <div onClick={onClose} style={{ position: "fixed", inset: 0, zIndex: 60, background: "rgba(8,19,23,.5)", backdropFilter: "blur(3px)", display: "grid", placeItems: "center" }}>
        <div onClick={(e) => e.stopPropagation()} className="card" style={{ width: 480, padding: 24, boxShadow: "var(--shadow-lg)", maxHeight: "92vh", overflowY: "auto" }}>
          <div style={{ fontWeight: 800, fontSize: 16 }}>Tạo dự án mới</div>
          <div style={{ fontSize: 12.5, color: "var(--ink-3)", fontWeight: 500, marginTop: 2 }}>Khởi tạo không gian CDE</div>

          <div style={{ display: "flex", gap: 12 }}>
            <div style={{ width: 158 }}><label style={lb}>Mã dự án *</label>
              <input autoFocus style={{ ...inp, textTransform: "uppercase" }} value={f.code}
                onChange={(e) => set("code", e.target.value)} placeholder="VD: HCMC-T1" /></div>
            <div style={{ flex: 1 }}><label style={lb}>Tên dự án *</label>
              <input style={inp} value={f.name} onChange={(e) => set("name", e.target.value)} placeholder="VD: Chung cư HCMC Tower 1" /></div>
          </div>

          <label style={lb}>Chủ đầu tư</label>
          <input style={inp} value={f.client} onChange={(e) => set("client", e.target.value)} placeholder="VD: Công ty CP Đầu tư Xây dựng…" />

          <label style={lb}>Giai đoạn</label>
          <input style={inp} list="cp-phase-hints" value={f.phase} onChange={(e) => set("phase", e.target.value)} placeholder="VD: Thiết kế kỹ thuật" />
          <datalist id="cp-phase-hints">{PHASE_HINTS.map(p => <option key={p} value={p} />)}</datalist>

          <label style={lb}>Màu nhấn</label>
          <div style={{ display: "flex", gap: 10, marginTop: 8 }}>
            {PROJ_ACCENTS.map(c => (
              <button key={c} type="button" onClick={() => set("accent", c)} title={c}
                style={{ width: 34, height: 34, borderRadius: 10, background: c, cursor: "pointer",
                  border: f.accent === c ? "3px solid var(--ink)" : "3px solid transparent",
                  boxShadow: f.accent === c ? "0 0 0 1px var(--line)" : "none" }} />
            ))}
          </div>

          {err && <div style={{ marginTop: 14, fontSize: 12.5, color: "var(--danger)", fontWeight: 600 }}>{err}</div>}
          <div style={{ display: "flex", gap: 10, justifyContent: "flex-end", marginTop: 20 }}>
            <button className="btn" onClick={onClose} disabled={busy}>Huỷ</button>
            <button className="btn brand" disabled={busy} onClick={submit} style={{ opacity: busy ? .6 : 1 }}>
              <Icon.plus size={14} /> {busy ? "Đang tạo…" : "Tạo dự án"}
            </button>
          </div>
        </div>
      </div>
    );
  }

  /* ---------- Delete project modal (admin, type-to-confirm) ---------- */
  function DeleteProjectModal({ project, onClose, onDeleted }) {
    const [val, setVal] = useState("");
    const [busy, setBusy] = useState(false);
    const [err, setErr] = useState("");
    const ok = val.trim().toUpperCase() === String(project.code || "").toUpperCase();
    const submit = async () => {
      if (!ok) return;
      setBusy(true); setErr("");
      try { await cdeData.deleteProject(project.code); if (onDeleted) await onDeleted(); }
      catch (e) { setErr(e.message || "Xóa dự án thất bại"); setBusy(false); }
    };
    const inp = { width: "100%", height: 40, padding: "0 12px", borderRadius: 10, border: "1px solid var(--line)", background: "var(--surface)", color: "var(--ink)", font: "inherit", fontSize: 13.5, fontWeight: 700, outline: "none", marginTop: 8 };
    return (
      <div onClick={onClose} style={{ position: "fixed", inset: 0, zIndex: 60, background: "rgba(8,19,23,.5)", backdropFilter: "blur(3px)", display: "grid", placeItems: "center" }}>
        <div onClick={(e) => e.stopPropagation()} className="card" style={{ width: 460, padding: 24, boxShadow: "var(--shadow-lg)" }}>
          <div style={{ fontWeight: 800, fontSize: 16, color: "var(--danger)" }}>Xóa vĩnh viễn dự án</div>
          <div style={{ fontSize: 13, color: "var(--ink-2)", fontWeight: 700, marginTop: 8 }}>{project.name} <span style={{ color: "var(--ink-4)", fontWeight: 600 }}>({project.code})</span></div>
          <div style={{ fontSize: 12.5, color: "var(--ink-3)", fontWeight: 500, marginTop: 10, lineHeight: 1.55 }}>
            Toàn bộ tài liệu, hồ sơ, RFI, phê duyệt, cấu hình… của dự án sẽ bị <b>xóa sạch và KHÔNG thể hồi phục</b>. Nếu chỉ muốn ẩn, hãy dùng <b>Lưu trữ</b>.
          </div>
          <label style={{ display: "block", fontSize: 11.5, fontWeight: 700, color: "var(--ink-3)", marginTop: 16 }}>Gõ mã <b style={{ color: "var(--ink)" }}>{project.code}</b> để xác nhận</label>
          <input autoFocus value={val} onChange={(e) => setVal(e.target.value)} placeholder={project.code} style={inp}
            onKeyDown={(e) => { if (e.key === "Enter" && ok) submit(); }} />
          {err && <div style={{ marginTop: 12, fontSize: 12.5, color: "var(--danger)", fontWeight: 600 }}>{err}</div>}
          <div style={{ display: "flex", gap: 10, justifyContent: "flex-end", marginTop: 18 }}>
            <button className="btn" onClick={onClose} disabled={busy}>Huỷ</button>
            <button className="btn" disabled={!ok || busy} onClick={submit}
              style={{ background: "var(--danger)", color: "#fff", borderColor: "var(--danger)", opacity: (!ok || busy) ? .5 : 1 }}>
              {busy ? "Đang xóa…" : "Xóa vĩnh viễn"}
            </button>
          </div>
        </div>
      </div>
    );
  }

  /* ---------- Assembly ---------- */
  function ProjectHub({ auth, projects, members, activities, notifications, reload, onOpen, onLogout, theme, setTheme, accent, setAccent }) {
    const [section, setSection] = useState("home");
    const [mounted, setMounted] = useState(false);
    const [creating, setCreating] = useState(false);
    const [delTarget, setDelTarget] = useState(null);
    const isAdmin = !!(auth && auth.profile && auth.profile.role === "admin");
    const archiveProj = async (p) => {
      try { await cdeData.archiveProject(p.code, p.status !== "archived"); if (reload) await reload(); }
      catch (e) { alert(e.message || "Cập nhật dự án thất bại"); }
    };
    const [notifs, setNotifs] = useState(() => (notifications || []).map(n => ({ ...n })));
    React.useEffect(() => { const t = setTimeout(() => setMounted(true), 30); return () => clearTimeout(t); }, []);

    const name = (auth && auth.profile && auth.profile.full_name) || (auth && auth.user && auth.user.email) || "bạn";
    const tasks = (activities || []).filter(a => a.type === "task");
    window.__hubUser = name;
    window.__hubAvatars = (() => {
      const map = {};
      (members || []).forEach(m => { if (m.name && m.avatar_url) map[m.name] = m.avatar_url; });
      if (auth && auth.profile && auth.profile.avatar_url) map[name] = auth.profile.avatar_url;
      return map;
    })();
    // map id → hồ sơ sống (tên + ảnh hiện tại) để bảng tin tra theo actor_id, đồng bộ khi đổi tên/ảnh
    window.__hubMembersById = (() => {
      const map = {};
      (members || []).forEach(m => { if (m.id) map[m.id] = { name: m.name, avatar_url: m.avatar_url || null }; });
      if (auth && auth.profile && auth.profile.id) map[auth.profile.id] = { name, avatar_url: auth.profile.avatar_url || null };
      return map;
    })();
    window.__hubTasks = tasks.length;
    const unread = notifs.filter(n => !n.read).length;
    const goSettings = () => setSection("settings");

    const content = () => {
      if (section === "projects")
        return <div className="hub-wide"><h1 className="hub-h1">Dự án</h1><div className="ph-grid">
          {projects.map(p => <ProjectCard key={p.code} project={p} onOpen={onOpen}
            onArchive={isAdmin ? archiveProj : undefined} onDelete={isAdmin ? setDelTarget : undefined} />)}
          {isAdmin && (
            <div className="proj-card create" onClick={() => setCreating(true)}>
              <span className="create-ic"><Icon.plus size={22} /></span>
              <div className="create-t">Tạo dự án mới</div>
              <div className="create-s">Khởi tạo không gian CDE</div>
            </div>
          )}
        </div></div>;
      if (section === "members")
        return <div className="hub-wide"><MemberDirectory members={members} /></div>;
      if (section === "settings")
        return <div className="hub-wide"><h1 className="hub-h1">Cài đặt</h1><SettingsPage auth={auth} theme={theme} setTheme={setTheme} accent={accent} setAccent={setAccent} onLogout={onLogout} /></div>;
      if (section === "tasks")
        return <div className="feed-wrap"><h1 className="hub-h1">Nhiệm vụ</h1><ActivityFeed items={tasks} me={name} /></div>;
      return <div className="feed-wrap"><HomeHero auth={auth} projects={projects} tasksN={tasks.length} unread={unread} /><ActivityFeed items={activities} me={name} /></div>;
    };

    return (
      <div className={"hub " + (mounted ? "mounted" : "")}>
        <Sidebar section={section} setSection={setSection} projects={projects} onOpen={onOpen} auth={auth} onGoSettings={goSettings} />
        <div className="main">
          <TopBar theme={theme} setTheme={setTheme} auth={auth} notifs={notifs} setNotifs={setNotifs}
            onLogout={onLogout} onGoSettings={goSettings} onCreate={isAdmin ? () => setCreating(true) : null} />
          <div className="content">{content()}</div>
        </div>
        <aside className="rail">
          <Notifications notifs={notifs} setNotifs={setNotifs} />
          <OnlineMembers members={members} />
        </aside>
        {creating && <CreateProjectModal onClose={() => setCreating(false)}
          onCreated={async () => { setCreating(false); if (reload) await reload(); }} />}
        {delTarget && <DeleteProjectModal project={delTarget} onClose={() => setDelTarget(null)}
          onDeleted={async () => { setDelTarget(null); if (reload) await reload(); }} />}
      </div>
    );
  }

  window.ProjectHub = ProjectHub;
})();
