/* demoapp.jsx — per-brand chrome shells wrapping the shared Chatbot +
   AIRS Inspector. Each business renders a distinct, believable product.
   A slim dark "presenter toolbar" (Last Rose) sits above every app and
   holds Back-to-hub + the Security toggle. */

let _mid = 0;
const nextId = () => "m" + (++_mid) + "-" + Math.random().toString(36).slice(2, 6);

function NavItem({ label, active, theme, onDark }) {
  const c = onDark ? "#fff" : theme.ink;
  return (
    <span
      className="cursor-default rounded-lg px-3 py-1.5 text-[13.5px] font-medium transition-colors"
      style={{
        color: active ? theme.primary : (onDark ? "rgba(255,255,255,0.8)" : theme.sub),
        background: active ? theme.tintBubble : "transparent",
        fontWeight: active ? 700 : 500,
      }}
    >
      {label}
    </span>
  );
}

const CHROME = () => ({ evercare: window.EvercareChrome, nro: window.NroChrome, bloom: window.BloomChrome });

function DemoApp({ business, onBack, mode = "dark", route }) {
  const t = business.theme;
  const sh = window.SHELL_THEMES[mode] || window.SHELL_THEMES.dark;
  const [messages, setMessages] = React.useState([]);
  const [events, setEvents] = React.useState([]);
  const [busy, setBusy] = React.useState(false);
  const [inspectorOpen, setInspectorOpen] = React.useState(false);
  const [seenCount, setSeenCount] = React.useState(0);
  // stable per-session id passed to the chat seam (mock ignores it; a real
  // backend uses it to thread conversation state).
  const sessionId = React.useRef("sess-" + Math.random().toString(36).slice(2, 10)).current;

  async function handleSend(text) {
    if (busy) return;
    setMessages((m) => [...m, { id: nextId(), role: "user", text, time: new Date() }]);
    setBusy(true);
    // TODO: backend — sendMessage is the single integration seam (data.jsx)
    const { reply, airs } = await window.sendMessage(business.id, text, sessionId);
    const blocked = airs.verdict === "block";
    const flagged = airs.verdict === "flag";
    setMessages((m) => [...m, { id: nextId(), role: "bot", text: reply, time: new Date(), blocked, flagged }]);
    setEvents((ev) => [...ev, { id: nextId(), time: new Date(), userText: text, reply, airs, blocked }]);
    setBusy(false);
  }

  // Built-in "Malicious Prompt" presets — sent through the SAME real path as a
  // typed message (real AIRS verdict + backend logs; mock classifier fallback
  // when no backend is wired). NOT the canned simulateAttack metadata.
  async function handleSimulate(attack) {
    if (busy) return;
    setInspectorOpen(true);
    setMessages((m) => [...m, { id: nextId(), role: "user", text: attack.text, time: new Date() }]);
    setBusy(true);
    const { reply, airs } = await window.sendMessage(business.id, attack.text, sessionId);
    const blocked = airs.verdict === "block";
    const flagged = airs.verdict === "flag";
    setMessages((m) => [...m, { id: nextId(), role: "bot", text: reply, time: new Date(), blocked, flagged }]);
    setEvents((ev) => [...ev, { id: nextId(), time: new Date(), userText: attack.text, reply, airs, blocked }]);
    setBusy(false);
  }

  // count of alerts the presenter hasn't opened the panel to see
  const alerts = events.filter((e) => e.airs.verdict !== "allow").length;
  const unseen = inspectorOpen ? 0 : Math.max(0, alerts - seenCount);
  React.useEffect(() => { if (inspectorOpen) setSeenCount(alerts); }, [inspectorOpen, alerts]);

  const Chrome = CHROME()[business.id] || window.EvercareChrome;

  return (
    <div className="relative h-full w-full overflow-hidden a-fade" style={{ background: sh.page }}>
      {/* presenter toolbar */}
      <div className="flex h-12 items-center justify-between px-4" style={{ background: sh.header, backdropFilter: "blur(14px)", borderBottom: `1px solid ${sh.headerBorder}`, fontFamily: "'Manrope', sans-serif" }}>
        <button onClick={onBack} className="inline-flex items-center gap-1.5 rounded-lg px-2.5 py-1.5 text-[13px] font-medium transition-colors" style={{ color: sh.ink }}>
          <Icon name="ArrowLeft" size={16} /> Back to hub
        </button>
        <div className="flex items-center gap-2">
          <RoseMark size={18} color={sh.accent} petals={6} />
          <span className="hidden text-[12px] sm:inline" style={{ color: sh.faint }}>Last Rose · <span style={{ color: sh.sub }}>{business.name}</span></span>
          {route && <OpenInNewTab href={route} size={13} className="h-7 w-7" title={"Open " + business.name + " in new tab"} style={{ color: sh.sub, background: sh.chip, border: `1px solid ${sh.headerBorder}` }} />}
        </div>
        <button
          onClick={() => setInspectorOpen((v) => !v)}
          className="relative inline-flex items-center gap-2 rounded-lg px-3 py-1.5 text-[13px] font-semibold transition-all active:scale-95"
          style={{
            background: inspectorOpen ? sh.accent : sh.accentSoft,
            color: inspectorOpen ? "#fff" : sh.accentText,
            border: `1px solid ${sh.accent}55`,
          }}
        >
          <Icon name="ShieldHalf" size={15} /> Security
          {unseen > 0 && (
            <span className="absolute -right-1.5 -top-1.5 flex h-4 min-w-4 items-center justify-center rounded-full px-1 text-[10px] font-bold text-white" style={{ background: "#ff4d4d", animation: "lr-pulse-ring 1.8s infinite" }}>{unseen}</span>
          )}
        </button>
      </div>

      {/* branded app region (scrolls) + inspector overlay */}
      <div className="relative" style={{ height: "calc(100% - 48px)" }}>
        <div className="lr-scroll h-full overflow-y-auto">
          <Chrome business={business}>
            <Chatbot business={business} messages={messages} busy={busy} onSend={handleSend} />
          </Chrome>
        </div>

        <Inspector
          open={inspectorOpen}
          business={business}
          events={events}
          busy={busy}
          mode={mode}
          onClose={() => setInspectorOpen(false)}
          onSimulate={handleSimulate}
        />
      </div>
    </div>
  );
}

window.NavItem = NavItem;
window.DemoApp = DemoApp;
