import { useState } from "react";
import { useBackLayer } from "../../app/useBackLayer.js";
import { readSavedServerOrigin, writeSavedServerOrigin } from "../../api-base.js";
import { platformRuntime } from "../../platform/runtime.js";
import { useI18n } from "../../shared/I18nProvider.jsx";
import { BackIcon } from "../../shared/ActionIcons.jsx";
import { pairDeviceAtOrigin } from "../auth/auth-api.js";
import { verifyServerConnection } from "./connection.js";
import { clearPcConnectionChangeRequest, isPcConnectionChangeRequested } from "./connection-mode.js";
import { scanConnectionSetupQr } from "./qr-scanner.js";
import { useReviewDemo } from "../review-demo/ReviewDemo.jsx";

export function NativeConnectionGate({ children }) {
  const { language, setLanguage, t } = useI18n();
  const { startReviewDemo } = useReviewDemo();
  const savedOrigin = platformRuntime.isNative ? readSavedServerOrigin() : "";
  const changeRequested = Boolean(savedOrigin) && isPcConnectionChangeRequested();
  const [address, setAddress] = useState("");
  const [pending, setPending] = useState(false);
  const [scanning, setScanning] = useState(false);
  const [error, setError] = useState("");

  function cancelChangePc() {
    clearPcConnectionChangeRequest();
    globalThis.location.reload();
  }
  useBackLayer(changeRequested, cancelChangePc, "connection-change");
  useBackLayer(scanning, () => setScanning(false), "qr-scanner");

  if (!platformRuntime.isNative || (savedOrigin && !changeRequested)) return children;

  async function saveConnection(candidate, pairing = null) {
    const origin = await verifyServerConnection(candidate);
    if (pairing) {
      if (pairing.origin !== origin) throw new Error("invalid_pairing_payload");
      await pairDeviceAtOrigin(pairing);
    }
    writeSavedServerOrigin(undefined, origin);
    clearPcConnectionChangeRequest();
    globalThis.location.reload();
  }

  async function connect(event) {
    event.preventDefault();
    setPending(true);
    setError("");
    try {
      await saveConnection(address);
    } catch (connectionError) {
      setError(connectionError.message === "secure_server_required" ? t("connection.httpsRequired") : t("connection.unreachable"));
      setPending(false);
    }
  }

  async function scanQr() {
    setPending(true);
    setScanning(true);
    setError("");
    try {
      const scanned = await scanConnectionSetupQr(undefined, { instructions: t("connection.scanInstructions"), cancel: t("settings.back") });
      await saveConnection(scanned.origin, scanned.pairing);
    } catch (scanError) {
      if (["secure_server_required", "invalid_server_address", "invalid_qr_code", "invalid_pairing_payload", "pairing_unavailable", "pairing_rate_limited"].includes(scanError.message)) setError(t("connection.invalidQr"));
      else if (scanError.message === "pc_unreachable") setError(t("connection.unreachable"));
      else setError(t("connection.scanFailed"));
      setScanning(false);
      setPending(false);
    }
  }

  return <main className="connection-page">
    {changeRequested && <button type="button" className="screen-back conversation-back connection-back" aria-label={t("settings.back")} onClick={cancelChangePc}><BackIcon /></button>}
    <div className="connection-language" aria-label={t("settings.language")}>
      <button type="button" className={language === "ko" ? "active" : ""} aria-pressed={language === "ko"} onClick={() => setLanguage("ko")}>한국어</button>
      <button type="button" className={language === "en" ? "active" : ""} aria-pressed={language === "en"} onClick={() => setLanguage("en")}>English</button>
    </div>
    <form className="connection-card" onSubmit={connect}>
      <p className="connection-kicker">Code Remote Manager</p>
      <h1>{t("connection.title")}</h1>
      <p>{t("connection.description")}</p>
      <button className="connection-scan" type="button" disabled={pending} onClick={scanQr}>{pending ? t("connection.connecting") : t("connection.scanQr")}</button>
      <p className="connection-divider"><span>{t("connection.orEnterAddress")}</span></p>
      <label htmlFor="pc-address">{t("connection.address")}</label>
      <input id="pc-address" type="url" inputMode="url" autoCapitalize="none" autoCorrect="off" spellCheck="false" placeholder="https://your-pc.tailnet.ts.net" value={address} onChange={(event) => setAddress(event.target.value)} disabled={pending} />
      {error && <p className="connection-error" role="alert">{error}</p>}
      <button type="submit" disabled={pending || !address.trim()}>{pending ? t("connection.connecting") : t("connection.connect")}</button>
      <p className="connection-note">{t("connection.note")}</p>
      <button className="connection-review-demo" type="button" disabled={pending} onClick={startReviewDemo}>{t("reviewDemo.start")}</button>
    </form>
  </main>;
}
