const ONBOARDING_STORAGE_KEY = "wxbot_portal_onboarding_v1";
const ONBOARDING_STEPS = ["扫码", "目录", "授权", "模式", "保存", "确认"];

function readOnboardingStatus() {
  try {
    const value = localStorage.getItem(ONBOARDING_STORAGE_KEY);
    return ["completed", "skipped"].includes(value) ? value : "";
  } catch (_error) {
    return "";
  }
}

const storedOnboardingStatus = readOnboardingStatus();

const state = {
  config: null,
  accounts: [],
  vncPassword: "",
  desktopUrl: "",
  sdkOnline: false,
  sdkPhase: "checking",
  sdkRuntime: {},
  formDirty: false,
  groupRequireAtMeApplied: false,
  groupModeSaving: false,
  controlMode: localStorage.getItem("wxbot_control_mode") || "observe",
  onboardingOpen: !storedOnboardingStatus,
  onboardingStep: 0,
  onboardingStatus: storedOnboardingStatus,
};

const $ = (id) => document.getElementById(id);

function toast(message) {
  const el = $("toast");
  el.textContent = message;
  el.hidden = false;
  window.clearTimeout(toast._timer);
  toast._timer = window.setTimeout(() => {
    el.hidden = true;
  }, 2600);
}

function setBadge(el, text, kind) {
  el.textContent = text;
  el.className = `badge ${kind || "neutral"}`;
}

function maskSecret(value) {
  const text = String(value || "").trim();
  if (!text) return "";
  if (text.length <= 8) return `${text.slice(0, 2)}***${text.slice(-2)}`;
  return `${text.slice(0, 8)}...${text.slice(-4)}`;
}

function storeOnboardingStatus(status) {
  state.onboardingStatus = status;
  try {
    localStorage.setItem(ONBOARDING_STORAGE_KEY, status);
  } catch (_error) {
    // The guide remains usable when storage is disabled; it may appear again next visit.
  }
}

function selectedAccountPath() {
  return String(
    $("accountSelect")?.value ||
      state.config?.wechat_data_dir_linux ||
      state.sdkRuntime.account?.data_dir ||
      "",
  ).trim();
}

function currentActivationCode() {
  return String($("activationCode")?.value || state.config?.activation_code || "").trim();
}

function inferOnboardingStep() {
  const runtime = state.sdkRuntime || {};
  const phase = runtime.phase || "checking";
  const accountConfigured = Boolean(selectedAccountPath() || runtime.account?.configured);
  const activationConfigured = Boolean(currentActivationCode() || runtime.activation?.configured);

  if (phase === "active" && runtime.auth_active === true) return 5;
  if (
    runtime.config_ready === true ||
    (accountConfigured &&
      activationConfigured &&
      ["starting", "offline", "authorization_error", "error"].includes(phase))
  ) {
    return 5;
  }
  if (accountConfigured && activationConfigured) return 3;
  if (accountConfigured) return 2;
  if (state.accounts.length || runtime.account?.configured) return 1;
  return 0;
}

function onboardingContent(step) {
  const runtime = state.sdkRuntime || {};
  const phase = runtime.phase || "checking";
  const accountCount = state.accounts.length;
  const accountPath = selectedAccountPath();
  const activationCode = currentActivationCode();
  const receiveLabel = $("receiveEnabled")?.checked === false ? "消息采集关" : "消息采集开";
  const sendLabel = $("sendEnabled")?.checked === false ? "不发送" : "可发送";
  const groupLabel = $("groupMentionOnly")?.checked ? "群消息仅 @我" : "全部群消息入队";

  if (step === 0) {
    return {
      kicker: "微信登录",
      title: "在右侧扫码登录微信",
      detail: "开启操作模式后，在 Linux 微信桌面完成扫码；引导位于配置侧栏，不会盖住桌面。",
      status: accountCount ? `已发现 ${accountCount} 个微信账号` : "等待微信登录",
      kind: accountCount ? "ok" : "waiting",
      primary: "允许操作并扫码",
    };
  }
  if (step === 1) {
    return {
      kicker: "账号发现",
      title: accountCount ? "微信目录已检测到" : "等待微信数据目录出现",
      detail: accountCount
        ? accountCount === 1
          ? "已找到一个账号目录，可以直接使用。"
          : "检测到多个账号，请在下方选择本次要接入的账号。"
        : "登录成功后系统会自动检测目录；页面每 6 秒检查一次，也可以立即重试。",
      status: accountCount ? `检测到 ${accountCount} 个账号目录` : "正在自动检测…",
      kind: accountCount ? "ok" : "waiting",
      primary: accountCount === 1 ? "使用检测到的账号" : accountCount ? "选择账号目录" : "立即检测",
    };
  }
  if (step === 2) {
    return {
      kicker: "授权信息",
      title: "填写 SDK 授权码",
      detail: "确认授权服务地址，然后填写 Activation Code。授权码仅保存到本机配置。",
      status: activationCode ? `已填写 ${maskSecret(activationCode)}` : "等待填写授权码",
      kind: activationCode ? "ok" : "waiting",
      primary: activationCode ? "继续选择模式" : "前往填写",
    };
  }
  if (step === 3) {
    return {
      kicker: "消息策略",
      title: "选择采集、发送与群消息范围",
      detail: "消息采集总开关同时控制私聊和群聊；群消息可进一步选择全部入队或仅 @我的消息入队。",
      status: `${receiveLabel} · ${sendLabel} · ${groupLabel}`,
      kind: "ok",
      primary: "确认模式",
    };
  }
  if (step === 4) {
    const ready = Boolean(accountPath && activationCode);
    return {
      kicker: "保存配置",
      title: "保存并启动 SDK",
      detail: ready
        ? "保存会写入当前账号与消息模式，并触发 SDK 启动或重启。"
        : "保存前需要先选择微信账号目录并填写授权码。",
      status: ready ? "配置已就绪" : "配置尚未完整",
      kind: ready ? "ok" : "danger",
      primary: "保存并启动 SDK",
      disabled: !ready,
    };
  }

  const active = phase === "active" && runtime.auth_active === true;
  const starting = phase === "starting" || phase === "checking";
  return {
    kicker: "激活确认",
    title: active ? "SDK 已激活，接入完成" : starting ? "正在确认 SDK 激活" : "SDK 尚未激活",
    detail: runtime.detail || (starting ? "配置已保存，正在等待 SDK 完成授权与初始化。" : "请查看下方 SDK 状态后重试。"),
    status: active
      ? "SDK API 在线 · 授权有效"
      : starting
        ? "自动检查中…"
        : runtime.label || "等待 SDK 状态",
    kind: active ? "ok" : starting ? "waiting" : "danger",
    primary: active ? "完成并收起" : "立即刷新状态",
    active,
  };
}

function renderOnboarding() {
  const panel = $("onboardingPanel");
  panel.hidden = !state.onboardingOpen;
  $("onboardingBtn").setAttribute("aria-expanded", String(state.onboardingOpen));
  $("onboardingBtn").classList.toggle("active", state.onboardingOpen);
  if (!state.onboardingOpen) return;

  const step = Math.max(0, Math.min(ONBOARDING_STEPS.length - 1, state.onboardingStep));
  const content = onboardingContent(step);
  $("onboardingProgressText").textContent = `${step + 1} / ${ONBOARDING_STEPS.length}`;
  $("onboardingStepNumber").textContent = String(step + 1).padStart(2, "0");
  $("onboardingStepKicker").textContent = content.kicker;
  $("onboardingStepTitle").textContent = content.title;
  $("onboardingStepDetail").textContent = content.detail;
  $("onboardingStatus").textContent = content.status;
  $("onboardingStatus").className = `onboarding-status ${content.kind || "waiting"}`;
  $("skipOnboardingBtn").textContent = state.onboardingStatus ? "收起" : "跳过引导";

  const backButton = $("onboardingBackBtn");
  backButton.hidden = step === 0 || content.active === true;
  backButton.textContent = step === 5 ? "检查配置" : "上一步";
  const primaryButton = $("onboardingPrimaryBtn");
  primaryButton.textContent = content.primary;
  primaryButton.disabled = content.disabled === true;

  for (const item of document.querySelectorAll("[data-onboarding-step]")) {
    const itemStep = Number(item.dataset.onboardingStep);
    item.classList.toggle("current", itemStep === step);
    item.classList.toggle("complete", itemStep < step);
    if (itemStep === step) item.setAttribute("aria-current", "step");
    else item.removeAttribute("aria-current");
  }
}

function syncOnboardingFromState() {
  const inferredStep = inferOnboardingStep();
  if (inferredStep > state.onboardingStep) state.onboardingStep = inferredStep;
  if (state.sdkPhase === "active" && state.sdkRuntime.auth_active === true) {
    if (state.onboardingStatus !== "completed") storeOnboardingStatus("completed");
  }
  renderOnboarding();
}

function openOnboarding() {
  state.onboardingOpen = true;
  state.onboardingStep = inferOnboardingStep();
  renderOnboarding();
  window.requestAnimationFrame(() => {
    $("onboardingPanel").scrollIntoView({ behavior: "smooth", block: "start" });
  });
}

function dismissOnboarding() {
  if (!state.onboardingStatus) storeOnboardingStatus("skipped");
  state.onboardingOpen = false;
  renderOnboarding();
}

function finishOnboarding() {
  storeOnboardingStatus("completed");
  state.onboardingOpen = false;
  renderOnboarding();
  toast("新手引导已完成，之后可随时重新打开");
}

function revealControl(elementId) {
  const element = $(elementId);
  if (!element) return;
  element.scrollIntoView({ behavior: "smooth", block: "center" });
  window.setTimeout(() => element.focus(), 180);
}

async function handleOnboardingPrimary() {
  const step = state.onboardingStep;
  if (step === 0) {
    state.controlMode = "control";
    localStorage.setItem("wxbot_control_mode", state.controlMode);
    renderDesktopMode();
    state.onboardingStep = 1;
    renderOnboarding();
    if (window.matchMedia("(max-width: 900px)").matches) {
      document.querySelector(".desktop-shell").scrollIntoView({ behavior: "smooth", block: "start" });
    }
    return;
  }
  if (step === 1) {
    if (state.accounts.length === 1) {
      const account = state.accounts[0];
      $("accountSelect").value = account.path;
      if (!$("selfWxid").value.trim()) $("selfWxid").value = account.self_wxid || "";
      $("dataDir").textContent = account.path;
      markFormDirty();
      state.onboardingStep = 2;
      renderOnboarding();
      revealControl("activationCode");
      return;
    }
    if (state.accounts.length > 1) {
      revealControl("accountSelect");
      return;
    }
    await refreshConfig();
    syncOnboardingFromState();
    return;
  }
  if (step === 2) {
    if (!currentActivationCode()) {
      revealControl("activationCode");
      return;
    }
    state.onboardingStep = 3;
    renderOnboarding();
    revealControl("receiveEnabled");
    return;
  }
  if (step === 3) {
    state.onboardingStep = 4;
    renderOnboarding();
    return;
  }
  if (step === 4) {
    $("configForm").requestSubmit();
    return;
  }
  if (state.sdkPhase === "active" && state.sdkRuntime.auth_active === true) {
    finishOnboarding();
    return;
  }
  await refreshAll();
  void monitorSdkStartup();
}

function handleOnboardingBack() {
  state.onboardingStep = Math.max(0, state.onboardingStep - 1);
  renderOnboarding();
  if (state.onboardingStep === 4) revealControl("saveConfigBtn");
}

function readFormDraft() {
  return {
    auth_base_url: $("authBaseUrl").value,
    activation_code: $("activationCode").value,
    wechat_data_dir_linux: $("accountSelect").value,
    self_wxid_linux: $("selfWxid").value,
    receive_enabled: $("receiveEnabled").checked,
    send_enabled: $("sendEnabled").checked,
    group_require_at_me: $("groupMentionOnly").checked,
  };
}

function setGroupMode(requireAtMe) {
  $("groupMentionOnly").checked = requireAtMe;
  $("groupAllMessages").checked = !requireAtMe;
}

function setGroupModeSaving(saving) {
  state.groupModeSaving = saving;
  $("groupMentionOnly").disabled = saving;
  $("groupAllMessages").disabled = saving;
  document.querySelector(".segmented-control").setAttribute("aria-busy", String(saving));
}

async function saveGroupMode() {
  if (state.groupModeSaving) return;
  const requireAtMe = $("groupMentionOnly").checked;
  const previous = state.groupRequireAtMeApplied;
  if (requireAtMe === previous) return;

  setGroupModeSaving(true);
  try {
    const res = await fetch("/portal-api/message-settings", {
      method: "POST",
      headers: { "Content-Type": "application/json" },
      body: JSON.stringify({ group_require_at_me: requireAtMe }),
    });
    const payload = await res.json();
    if (!res.ok || !payload.ok) throw new Error(payload.error || "群消息范围更新失败");

    state.groupRequireAtMeApplied = requireAtMe;
    if (state.config) state.config.group_require_at_me = requireAtMe;
    state.sdkRuntime.group_require_at_me = requireAtMe;
    state.sdkRuntime.group_capture_mode = requireAtMe ? "mention_only" : "all_group_messages";
    if (state.sdkRuntime.config_ready === true) {
      $("sdkGroupState").textContent = requireAtMe ? "仅 @我" : "全部入队";
    }
    const appliedLive = payload.applied_live === true || payload.sdk_action === "hot_reload";
    toast(
      appliedLive
        ? "群消息范围已热更新，无需重启 SDK"
        : "群消息范围已保存，将在 SDK 启动后生效",
    );
  } catch (error) {
    setGroupMode(previous);
    toast(`${error.message || "群消息范围更新失败"}；已恢复原值`);
  } finally {
    setGroupModeSaving(false);
    syncOnboardingFromState();
  }
}

function renderDesktopMode() {
  const observe = state.controlMode !== "control";
  $("observeBtn").classList.toggle("selected", observe);
  $("controlBtn").classList.toggle("selected", !observe);
  $("desktopOverlay").classList.toggle("hidden", !observe);
  if (state.config !== null) applyDesktopUrl(true);
}

function buildDesktopUrl() {
  const params = new URLSearchParams({
    autoconnect: "1",
    path: "vnc/websockify",
    resize: "remote",
    reconnect: "true",
    reconnect_delay: "2000",
    view_only: state.controlMode === "control" ? "false" : "true",
  });
  const secret = state.vncPassword ? `#password=${encodeURIComponent(state.vncPassword)}` : "";
  return `/vnc/vnc.html?${params.toString()}${secret}`;
}

function applyDesktopUrl(force = false) {
  const frame = $("desktopFrame");
  const next = buildDesktopUrl();
  if (!force && state.desktopUrl === next && frame.src !== "about:blank") return;
  state.desktopUrl = next;
  frame.src = next;
}

function phaseBadgeKind(phase) {
  if (phase === "active") return "ok";
  if (["authorization_error", "error", "offline"].includes(phase)) return "danger";
  return "warn";
}

function renderDeviceIdentity(identity = {}) {
  const fields = [
    ["deviceId", identity.device_id],
    ["devicePublicKeySha256", identity.device_public_key_sha256],
  ];
  for (const [elementId, rawValue] of fields) {
    const value = String(rawValue || "").trim();
    const element = $(elementId);
    element.textContent = value || "等待 SDK 初始化身份";
    element.dataset.copyValue = value;
    const button = document.querySelector(`[data-copy-target="${elementId}"]`);
    if (button) button.disabled = !value;
  }
}

function sdkVersion(runtime = {}) {
  const value =
    runtime.sdk_version ||
    runtime.version ||
    runtime.client_version ||
    runtime.build?.version ||
    "";
  return String(value).trim() || "未上报";
}

function renderSdkRuntime(runtime = {}) {
  const phase = runtime.phase || "checking";
  const label = runtime.label || "正在检查";
  const online = runtime.sdk_online === true;
  const activation = runtime.activation || {};
  const account = runtime.account || {};
  const apiPort = runtime.api_port || 5080;

  state.sdkRuntime = runtime;
  state.sdkOnline = online;
  state.sdkPhase = phase;
  renderDeviceIdentity(runtime.device_identity || {});

  const panel = $("sdkStatusPanel");
  panel.dataset.phase = phase;
  $("sdkStateTitle").textContent = label;
  $("sdkDetail").textContent = runtime.detail || "正在读取 SDK 配置与运行状态";
  $("sdkConnection").textContent = online ? "API 在线" : phase === "starting" ? "启动中" : "API 离线";
  $("sdkVersion").textContent = sdkVersion(runtime);
  $("sdkActivation").textContent = activation.configured
    ? activation.masked || maskSecret(state.config?.activation_code)
    : "未填写";
  $("sdkApiState").textContent = online ? `在线 · :${apiPort}` : `离线 · :${apiPort}`;

  const runtimeReady = runtime.config_ready === true;
  $("sdkReceiveState").textContent = !runtimeReady
    ? "待配置"
    : runtime.receive_enabled
      ? online ? "运行中" : "已启用"
      : "已暂停";
  $("sdkSendState").textContent = !runtimeReady
    ? "待配置"
    : runtime.send_enabled
      ? online ? "运行中" : "已启用"
      : "已关闭";
  $("sdkGroupState").textContent = !runtimeReady
    ? "待配置"
    : runtime.group_require_at_me
      ? "仅 @我"
      : "全部入队";

  const error = $("sdkError");
  const errorText = runtime.last_error || "";
  error.hidden = !errorText;
  error.textContent = errorText;

  setBadge($("sdkBadge"), `SDK ${label}`, phaseBadgeKind(phase));
  if (account.configured) {
    setBadge($("wechatBadge"), "微信账号已选择", "ok");
  } else if (state.accounts.length) {
    setBadge($("wechatBadge"), "检测到微信账号", "warn");
  } else {
    setBadge($("wechatBadge"), "等待微信扫码", "warn");
  }
  syncOnboardingFromState();
}

function renderConfig(payload) {
  const firstLoad = state.config === null;
  const draft = state.formDirty ? readFormDraft() : null;
  state.config = payload.config || {};
  state.accounts = payload.accounts || [];
  state.vncPassword = payload.desktop?.vnc_password || "";
  applyDesktopUrl(firstLoad);
  $("configPath").textContent = payload.config_path || "-";

  const values = draft || state.config;
  $("authBaseUrl").value = values.auth_base_url || "";
  $("activationCode").value = values.activation_code || "";
  $("selfWxid").value = values.self_wxid_linux || "";
  $("receiveEnabled").checked = values.receive_enabled !== false;
  $("sendEnabled").checked = values.send_enabled !== false;
  state.groupRequireAtMeApplied = state.config.group_require_at_me === true;
  setGroupMode(values.group_require_at_me === true);

  const select = $("accountSelect");
  select.innerHTML = "";
  const empty = document.createElement("option");
  empty.value = "";
  empty.textContent = state.accounts.length ? "请选择微信账号目录" : "未检测到账号目录，请先扫码登录";
  select.appendChild(empty);

  for (const account of state.accounts) {
    const option = document.createElement("option");
    option.value = account.path;
    option.textContent = `${account.name} (${account.self_wxid || "unknown"})`;
    option.dataset.selfWxid = account.self_wxid || "";
    select.appendChild(option);
  }

  const selectedDir = values.wechat_data_dir_linux || "";
  if (selectedDir) {
    const exists = Array.from(select.options).some((item) => item.value === selectedDir);
    if (!exists) {
      const option = document.createElement("option");
      option.value = selectedDir;
      option.textContent = selectedDir;
      select.appendChild(option);
    }
    select.value = selectedDir;
  }
  $("dataDir").textContent = select.value || "-";

  if (payload.sdk_runtime) renderSdkRuntime(payload.sdk_runtime);
  else syncOnboardingFromState();
}

async function refreshConfig({ discardDraft = false } = {}) {
  if (discardDraft) state.formDirty = false;
  const res = await fetch("/portal-api/config", { cache: "no-store" });
  const payload = await res.json();
  if (!payload.ok) throw new Error(payload.error || "读取配置失败");
  renderConfig(payload);
}

async function refreshSdkStatus() {
  try {
    const res = await fetch("/portal-api/status", { cache: "no-store" });
    const payload = await res.json();
    if (!payload.ok) throw new Error(payload.error || `状态接口 ${res.status}`);
    renderSdkRuntime(payload.sdk_runtime || {});
  } catch (error) {
    renderSdkRuntime({
      phase: "offline",
      label: "状态服务不可用",
      detail: "暂时无法读取 SDK 状态，请稍后刷新",
      sdk_online: false,
      config_ready: Boolean(state.config?.activation_code && state.config?.wechat_data_dir_linux),
      activation: {
        configured: Boolean(state.config?.activation_code),
        masked: maskSecret(state.config?.activation_code),
      },
      account: { configured: Boolean(state.config?.wechat_data_dir_linux) },
      receive_enabled: state.config?.receive_enabled !== false,
      send_enabled: state.config?.send_enabled === true,
      group_require_at_me: state.config?.group_require_at_me === true,
      api_port: 5080,
      last_error: "",
      device_identity: state.sdkRuntime.device_identity || {},
    });
  }
}

async function refreshAll(options = {}) {
  try {
    await refreshConfig(options);
  } catch (error) {
    toast(error.message || "读取配置失败");
  }
  await refreshSdkStatus();
}

async function saveConfig(event) {
  event.preventDefault();
  const saveButton = $("saveConfigBtn");
  saveButton.disabled = true;
  saveButton.textContent = "正在保存...";
  const body = {
    auth_base_url: $("authBaseUrl").value.trim(),
    activation_code: $("activationCode").value.trim(),
    wechat_data_dir_linux: $("accountSelect").value,
    self_wxid_linux: $("selfWxid").value.trim(),
    sender_backend: "auto",
    receive_enabled: $("receiveEnabled").checked,
    send_enabled: $("sendEnabled").checked,
    group_require_at_me: $("groupMentionOnly").checked,
  };
  try {
    const res = await fetch("/portal-api/config", {
      method: "POST",
      headers: { "Content-Type": "application/json" },
      body: JSON.stringify(body),
    });
    const payload = await res.json();
    if (!payload.ok) throw new Error(payload.error || "保存失败");
    state.formDirty = false;
    renderSdkRuntime({
      phase: "starting",
      label: "正在启动",
      detail: "配置已保存，SDK 正在授权或初始化数据库",
      sdk_online: false,
      config_ready: true,
      activation: { configured: true, masked: maskSecret(body.activation_code) },
      account: { configured: true, data_dir: body.wechat_data_dir_linux },
      receive_enabled: body.receive_enabled,
      send_enabled: body.send_enabled,
      group_require_at_me: body.group_require_at_me,
      api_port: 5080,
      device_identity: state.sdkRuntime.device_identity || {},
    });
    toast(`配置已保存：${maskSecret(body.activation_code)}`);
    await refreshAll({ discardDraft: true });
    void monitorSdkStartup();
  } finally {
    saveButton.disabled = false;
    saveButton.textContent = "保存并启动 SDK";
  }
}

async function monitorSdkStartup() {
  for (let attempt = 0; attempt < 60; attempt += 1) {
    if (["active", "authorization_error", "error"].includes(state.sdkPhase)) return;
    await new Promise((resolve) => window.setTimeout(resolve, 2000));
    await refreshSdkStatus();
  }
}

function reloadDesktop() {
  const frame = $("desktopFrame");
  const current = buildDesktopUrl();
  frame.src = "about:blank";
  window.setTimeout(() => {
    frame.src = current;
    state.desktopUrl = current;
  }, 120);
}

async function logout() {
  try {
    await fetch("/portal-auth/logout", { method: "POST", credentials: "same-origin" });
  } finally {
    window.location.replace("/login.html");
  }
}

async function copyIdentity(targetId) {
  const element = $(targetId);
  const value = String(element?.dataset.copyValue || "").trim();
  if (!value) return;
  if (navigator.clipboard?.writeText) {
    await navigator.clipboard.writeText(value);
  } else {
    const textarea = document.createElement("textarea");
    textarea.value = value;
    textarea.setAttribute("readonly", "");
    textarea.style.position = "fixed";
    textarea.style.opacity = "0";
    document.body.appendChild(textarea);
    textarea.select();
    const copied = document.execCommand("copy");
    textarea.remove();
    if (!copied) throw new Error("浏览器未允许复制");
  }
  toast("已复制完整设备身份");
}

function markFormDirty() {
  state.formDirty = true;
}

function bindEvents() {
  $("onboardingBtn").addEventListener("click", () => {
    if (state.onboardingOpen) dismissOnboarding();
    else openOnboarding();
  });
  $("skipOnboardingBtn").addEventListener("click", dismissOnboarding);
  $("onboardingBackBtn").addEventListener("click", handleOnboardingBack);
  $("onboardingPrimaryBtn").addEventListener("click", () => {
    handleOnboardingPrimary().catch((error) => toast(error.message || "引导操作失败"));
  });
  $("refreshBtn").addEventListener("click", () => refreshAll());
  $("reloadConfigBtn").addEventListener("click", () => refreshAll({ discardDraft: true }));
  $("reloadDesktopBtn").addEventListener("click", reloadDesktop);
  $("logoutBtn").addEventListener("click", logout);
  for (const button of document.querySelectorAll("[data-copy-target]")) {
    button.addEventListener("click", () => {
      copyIdentity(button.dataset.copyTarget).catch((error) => toast(error.message || "复制失败"));
    });
  }
  $("configForm").addEventListener("submit", (event) => {
    saveConfig(event).catch((error) => toast(error.message || "保存失败"));
  });

  for (const element of $("configForm").querySelectorAll('input:not([name="group_capture_mode"]), select')) {
    element.addEventListener("input", () => {
      markFormDirty();
      syncOnboardingFromState();
    });
    element.addEventListener("change", () => {
      markFormDirty();
      syncOnboardingFromState();
    });
  }

  for (const radio of document.querySelectorAll('input[name="group_capture_mode"]')) {
    radio.addEventListener("change", () => {
      syncOnboardingFromState();
      saveGroupMode().catch((error) => toast(error.message || "群消息范围更新失败"));
    });
  }

  $("accountSelect").addEventListener("change", () => {
    const selected = $("accountSelect").selectedOptions[0];
    const wxid = selected?.dataset?.selfWxid || "";
    if (wxid && !$("selfWxid").value.trim()) $("selfWxid").value = wxid;
    $("dataDir").textContent = $("accountSelect").value || "-";
    syncOnboardingFromState();
  });

  $("observeBtn").addEventListener("click", () => {
    state.controlMode = "observe";
    localStorage.setItem("wxbot_control_mode", state.controlMode);
    renderDesktopMode();
  });

  $("controlBtn").addEventListener("click", () => {
    state.controlMode = "control";
    localStorage.setItem("wxbot_control_mode", state.controlMode);
    renderDesktopMode();
  });
}

bindEvents();
renderDesktopMode();
renderOnboarding();
refreshAll();
window.setInterval(() => {
  if (document.hidden) return;
  void refreshSdkStatus();
  if (!state.accounts.length) void refreshConfig();
}, 6000);
