// components/setup.jsx — SetupPanel: guided checklist for first-time project setup.
// Depends on: React (useState, useEffect, useMemo), Card, StatusBadge.
// Includes: callout linking to the dedicated Tasks tab

const useState = React.useState;
const useEffect = React.useEffect;
const useMemo = React.useMemo;

const SETUP_STORAGE_KEY = "proxym.setup.panel.v1";
const EMPTY_COMPLETED = Object.create(null);
const SETUP_CONTROL_STYLE = {
  backgroundColor: "var(--dashboard-surface)",
  borderColor: "var(--dashboard-border)",
  color: "var(--dashboard-text)",
};
const SETUP_SURFACE_STYLE = {
  backgroundColor: "var(--dashboard-surface-alt)",
  borderColor: "var(--dashboard-border)",
  color: "var(--dashboard-text)",
};
const SETUP_MUTED_STYLE = {
  color: "var(--dashboard-text-muted)",
};

const SETUP_STEPS = [
  {
    id: "requirements",
    number: 1,
    title: "Sprawdź wymagania lokalne",
    kind: "manual",
    badge: "Manual",
    summary: "Upewnij się, że system ma Python 3.11+, Git, Docker/Podman i (opcjonalnie) Ollama.",
    details: [
      "Jeśli Python, Docker lub Ollama są brakujące, ich instalacja może wymagać `sudo` i potwierdzenia od człowieka.",
      "To jest pierwszy krok, ponieważ kolejne automatyczne operacje zakładają działające narzędzia bazowe.",
    ],
    commands: [
      "python3 --version",
      "docker --version || podman --version",
      "ollama --version || curl -sf http://localhost:11434/api/version",
    ],
    sudoCommands: [
      "sudo apt install python3 python3-venv git docker.io docker-compose-plugin",
      "sudo usermod -aG docker $USER && newgrp docker",
    ],
    inputs: [],
  },
  {
    id: "env",
    number: 2,
    title: "Uzupełnij dane do `.env`",
    kind: "manual",
    badge: "Input",
    summary: "Podaj klucz główny i wybrane API keys. Te dane nie są wymagane do zapisania w panelu.",
    details: [
      "Wypełnij wartości dokładnie tak, jak mają trafić do `.env`.",
      "Sekretne pola są tylko w pamięci formularza i nie są zapisywane w przeglądarce.",
    ],
    commands: [],
    sudoCommands: [],
    inputs: [
      { key: "projectRoot", label: "Project path", placeholder: "/home/tom/github/wronai/proxy", secret: false },
      { key: "dashboardUrl", label: "Dashboard URL", placeholder: "http://localhost:4000", secret: false },
      { key: "masterKey", label: "AI_PROXY_MASTER_KEY", placeholder: "sk-proxy-local-dev", secret: true },
      { key: "anthropicKey", label: "ANTHROPIC_API_KEY", placeholder: "sk-ant-...", secret: true },
      { key: "openaiKey", label: "OPENAI_API_KEY", placeholder: "sk-...", secret: true },
      { key: "openrouterKey", label: "OPENROUTER_API_KEY", placeholder: "sk-or-...", secret: true },
      { key: "googleKey", label: "GOOGLE_AI_KEY", placeholder: "AIza...", secret: true },
      { key: "ollamaUrl", label: "OLLAMA_BASE_URL", placeholder: "http://localhost:11434", secret: false },
    ],
  },
  {
    id: "setup-script",
    number: 3,
    title: "Uruchom automatyczny setup",
    kind: "auto",
    badge: "Auto",
    summary: "To wykonuje większość powtarzalnych kroków: venv, pip install, `.env`, Redis, testy.",
    details: [
      "Jeśli któryś krok wywali się przez brak Dockera, to jest sygnał, że człowiek musi dokończyć instalację systemową.",
      "Ten krok nie wymaga ręcznego przepisywania poleceń — możesz skopiować gotową komendę.",
    ],
    commands: ["bash scripts/setup.sh"],
    sudoCommands: [],
    inputs: [],
  },
  {
    id: "compose",
    number: 4,
    title: "Uruchom stack aplikacji",
    kind: "auto",
    badge: "Auto",
    summary: "Start proxy + Redis + Ollama przez Docker Compose, jeśli korzystasz z wariantu kontenerowego.",
    details: [
      "To jest najprostsza ścieżka, jeśli Docker jest już dostępny.",
      "Gdy Docker wymaga instalacji, wróć do kroku 1 i wykonaj go jako człowiek z uprawnieniami admina.",
    ],
    commands: ["docker compose up -d"],
    sudoCommands: [],
    inputs: [],
  },
  {
    id: "health",
    number: 5,
    title: "Sprawdź zdrowie usługi",
    kind: "auto",
    badge: "Auto",
    summary: "Weryfikuje, czy proxy odpowiada i czy podstawowe endpointy są dostępne.",
    details: [
      "To jest szybki test potwierdzający, że start się udał.",
      "Jeśli nie działa, najpierw wróć do kroku uruchomienia stacka albo sprawdź logi.",
    ],
    commands: ["curl http://localhost:4000/health"],
    sudoCommands: [],
    inputs: [],
  },
  {
    id: "ide",
    number: 6,
    title: "Skonfiguruj IDE i narzędzia lokalne",
    kind: "manual",
    badge: "Manual",
    summary: "Wklej base URL i klucz do Roo Code / Cline / Aider / innych klientów OpenAI-compatible.",
    details: [
      "To jest krok poza systemem — człowiek musi wkleić dane w ustawienia swojej aplikacji.",
      "Najczęściej potrzebujesz tylko API Base, API Key i ewentualnie wyboru modelu.",
    ],
    commands: [],
    sudoCommands: [],
    inputs: [],
  },
  {
    id: "validate",
    number: 7,
    title: "Uruchom walidację końcową",
    kind: "auto",
    badge: "Auto",
    summary: "Sprawdza dashboard, kolejkę, taski, healthcheck i pełen flow bez ręcznej obsługi.",
    details: [
      "To jest dobra komenda końcowa po zmianach lub po świeżej instalacji.",
      "Jeżeli chcesz krótszy przebieg, użyj flagi `--quick`.",
    ],
    commands: ["PROXYM_URL=http://localhost:4000 ./scripts/validate_system.sh --quick"],
    sudoCommands: [],
    inputs: [],
  },
  {
    id: "root-only",
    number: 8,
    title: "Tylko gdy brakuje zależności systemowych",
    kind: "root",
    badge: "sudo",
    summary: "Instalacja pakietów systemowych i konfiguracja usług wymaga człowieka z uprawnieniami administratora.",
    details: [
      "Ten krok jest celowo rozdzielony od automatyki, bo nie powinien być wykonywany w przeglądarce.",
      "Jeśli narzędzia są już zainstalowane, możesz oznaczyć ten krok jako pominięty.",
    ],
    commands: [],
    sudoCommands: [
      "sudo apt update",
      "sudo apt install python3 python3-venv git docker.io docker-compose-plugin",
      "sudo systemctl enable --now docker",
    ],
    inputs: [],
  },
];

const DEFAULT_SETUP_VALUES = {
  projectRoot: "/home/tom/github/wronai/proxy",
  dashboardUrl: "http://localhost:4000",
  ollamaUrl: "http://localhost:11434",
};

function _setupReadStorage() {
  try {
    const raw = globalThis.localStorage?.getItem(SETUP_STORAGE_KEY);
    if (!raw) return { values: DEFAULT_SETUP_VALUES, completed: EMPTY_COMPLETED };
    const parsed = JSON.parse(raw);
    const parsedValues = parsed && typeof parsed.values === "object" && parsed.values !== null
      ? parsed.values
      : null;
    return {
      values: parsedValues ? { ...DEFAULT_SETUP_VALUES, ...parsedValues } : DEFAULT_SETUP_VALUES,
      completed: parsed && typeof parsed === "object" && parsed.completed ? parsed.completed : EMPTY_COMPLETED,
    };
  } catch {
    return { values: DEFAULT_SETUP_VALUES, completed: EMPTY_COMPLETED };
  }
}

function _setupWriteStorage(state) {
  try {
    globalThis.localStorage?.setItem(SETUP_STORAGE_KEY, JSON.stringify(state));
  } catch {
    // Ignore storage errors; the panel still works without persistence.
  }
}

function _setupCommandBlock(values) {
  const lines = [
    `PROJECT_ROOT=${values.projectRoot || DEFAULT_SETUP_VALUES.projectRoot}`,
    `DASHBOARD_URL=${values.dashboardUrl || DEFAULT_SETUP_VALUES.dashboardUrl}`,
    `OLLAMA_BASE_URL=${values.ollamaUrl || DEFAULT_SETUP_VALUES.ollamaUrl}`,
  ];
  return lines.join("\n");
}

function _setupEnvSnippet(values, secretValues) {
  const lines = [
    `AI_PROXY_MASTER_KEY=${secretValues.masterKey || ""}`,
    `ANTHROPIC_API_KEY=${secretValues.anthropicKey || ""}`,
    `OPENAI_API_KEY=${secretValues.openaiKey || ""}`,
    `OPENROUTER_API_KEY=${secretValues.openrouterKey || ""}`,
    `GOOGLE_AI_KEY=${secretValues.googleKey || ""}`,
    `OLLAMA_BASE_URL=${values.ollamaUrl || DEFAULT_SETUP_VALUES.ollamaUrl}`,
    `DASHBOARD_API_URL=${values.dashboardUrl || DEFAULT_SETUP_VALUES.dashboardUrl}`,
  ];
  return lines;
}

function SetupPanel() {
  const persisted = useMemo(_setupReadStorage, []);
  const [values, setValues] = useState(persisted.values);
  const [secretValues, setSecretValues] = useState({
    masterKey: "",
    anthropicKey: "",
    openaiKey: "",
    openrouterKey: "",
    googleKey: "",
  });
  const [completed, setCompleted] = useState(persisted.completed);
  const [copiedId, setCopiedId] = useState("");

  useEffect(() => {
    _setupWriteStorage({ values, completed });
  }, [values, completed]);

  const checkedCount = Object.values(completed).filter(Boolean).length;
  const autoCount = SETUP_STEPS.filter(step => step.kind === "auto").length;
  const manualCount = SETUP_STEPS.filter(step => step.kind === "manual").length;
  const rootCount = SETUP_STEPS.filter(step => step.kind === "root").length;

  const toggleStep = (id) => {
    setCompleted(prev => ({ ...prev, [id]: !prev[id] }));
  };

  const setField = (key, value) => {
    setValues(prev => ({ ...prev, [key]: value }));
  };

  const setSecretField = (key, value) => {
    setSecretValues(prev => ({ ...prev, [key]: value }));
  };

  const copyText = async (id, text) => {
    await navigator.clipboard.writeText(text);
    setCopiedId(id);
    setTimeout(() => {
      setCopiedId(current => (current === id ? "" : current));
    }, 1800);
  };

  const copyAllCommands = async () => {
    const text = SETUP_STEPS.flatMap(step => [
      ...(step.commands || []),
      ...(step.sudoCommands || []),
    ]).join("\n\n");
    if (!text) return;
    await copyText("all-commands", text);
  };

  const envSnippet = useMemo(() => _setupEnvSnippet(values, secretValues).join("\n"), [values, secretValues]);
  const oneLineSummary = useMemo(() => _setupCommandBlock(values), [values]);

  return (
    <div className="space-y-4">
      <Card title="Checklist uruchomienia i konfiguracji" badge={<StatusBadge ok={checkedCount > 0} label={`${checkedCount}/${SETUP_STEPS.length} odhaczone`} />}>
        <div className="grid grid-cols-2 md:grid-cols-4 gap-3 text-sm mb-4">
          <div className="rounded-lg border p-3" style={SETUP_SURFACE_STYLE}>
            <div className="text-xs text-blue-700">Auto</div>
            <div className="text-lg font-semibold text-blue-900">{autoCount}</div>
          </div>
          <div className="rounded-lg border p-3" style={SETUP_SURFACE_STYLE}>
            <div className="text-xs text-amber-700">Manual</div>
            <div className="text-lg font-semibold text-amber-900">{manualCount}</div>
          </div>
          <div className="rounded-lg border p-3" style={SETUP_SURFACE_STYLE}>
            <div className="text-xs text-red-700">sudo / root</div>
            <div className="text-lg font-semibold text-red-900">{rootCount}</div>
          </div>
          <div className="rounded-lg border p-3" style={SETUP_SURFACE_STYLE}>
            <div className="text-xs text-emerald-700">Done</div>
            <div className="text-lg font-semibold text-emerald-900">{checkedCount}</div>
          </div>
        </div>

        <div className="flex flex-wrap gap-2 mb-4">
          <button
            onClick={copyAllCommands}
            className="px-3 py-1.5 rounded bg-blue-600 text-white text-sm hover:bg-blue-700"
          >
            Kopiuj wszystkie komendy
          </button>
          <button
            onClick={() => copyText("env-snippet", envSnippet)}
            className="px-3 py-1.5 rounded bg-gray-100 text-gray-700 text-sm hover:bg-gray-200"
          >
            Kopiuj snippet `.env`
          </button>
          <button
            onClick={() => setCompleted(EMPTY_COMPLETED)}
            className="px-3 py-1.5 rounded bg-gray-100 text-gray-700 text-sm hover:bg-gray-200"
          >
            Wyczyść checkboxy
          </button>
        </div>

        <div className="grid md:grid-cols-3 gap-3 text-xs text-gray-600">
          <div>
            <div className="font-medium text-gray-800 mb-1">Automatycznie</div>
            <p>To można uruchomić z poziomu panelu lub skopiować jako gotową komendę.</p>
          </div>
          <div>
            <div className="font-medium text-gray-800 mb-1">Manualnie</div>
            <p>Te kroki wymagają człowieka, bo dotyczą edycji ustawień i wklejania sekretów.</p>
          </div>
          <div>
            <div className="font-medium text-gray-800 mb-1">sudo / root</div>
            <p>Jeśli pakiety systemowe są brakujące, panel pokaże gotową komendę dla administratora.</p>
          </div>
        </div>
      </Card>

      <Card title="Dane do podania po kolei" badge={<span className="text-xs text-gray-500">Sekretne pola nie są zapisywane</span>}>
        <div className="grid md:grid-cols-2 gap-3">
          <label className="block">
            <span className="text-xs font-medium text-gray-600">Project path</span>
            <input
              value={values.projectRoot}
              onChange={e => setField("projectRoot", e.target.value)}
              className="mt-1 w-full px-3 py-2 border rounded-lg text-sm"
              style={SETUP_CONTROL_STYLE}
              placeholder="/home/tom/github/wronai/proxy"
            />
          </label>
          <label className="block">
            <span className="text-xs font-medium text-gray-600">Dashboard URL</span>
            <input
              value={values.dashboardUrl}
              onChange={e => setField("dashboardUrl", e.target.value)}
              className="mt-1 w-full px-3 py-2 border rounded-lg text-sm"
              style={SETUP_CONTROL_STYLE}
              placeholder="http://localhost:4000"
            />
          </label>
          <label className="block">
            <span className="text-xs font-medium text-gray-600">OLLAMA_BASE_URL</span>
            <input
              value={values.ollamaUrl}
              onChange={e => setField("ollamaUrl", e.target.value)}
              className="mt-1 w-full px-3 py-2 border rounded-lg text-sm"
              style={SETUP_CONTROL_STYLE}
              placeholder="http://localhost:11434"
            />
          </label>
          <label className="block">
            <span className="text-xs font-medium text-gray-600">AI_PROXY_MASTER_KEY</span>
            <input
              type="password"
              value={secretValues.masterKey}
              onChange={e => setSecretField("masterKey", e.target.value)}
              className="mt-1 w-full px-3 py-2 border rounded-lg text-sm"
              style={SETUP_CONTROL_STYLE}
              placeholder="sk-proxy-local-dev"
              autoComplete="off"
            />
          </label>
          <label className="block">
            <span className="text-xs font-medium text-gray-600">ANTHROPIC_API_KEY</span>
            <input
              type="password"
              value={secretValues.anthropicKey}
              onChange={e => setSecretField("anthropicKey", e.target.value)}
              className="mt-1 w-full px-3 py-2 border rounded-lg text-sm"
              style={SETUP_CONTROL_STYLE}
              placeholder="sk-ant-..."
              autoComplete="off"
            />
          </label>
          <label className="block">
            <span className="text-xs font-medium text-gray-600">OPENAI_API_KEY</span>
            <input
              type="password"
              value={secretValues.openaiKey}
              onChange={e => setSecretField("openaiKey", e.target.value)}
              className="mt-1 w-full px-3 py-2 border rounded-lg text-sm"
              style={SETUP_CONTROL_STYLE}
              placeholder="sk-..."
              autoComplete="off"
            />
          </label>
          <label className="block">
            <span className="text-xs font-medium text-gray-600">OPENROUTER_API_KEY</span>
            <input
              type="password"
              value={secretValues.openrouterKey}
              onChange={e => setSecretField("openrouterKey", e.target.value)}
              className="mt-1 w-full px-3 py-2 border rounded-lg text-sm"
              style={SETUP_CONTROL_STYLE}
              placeholder="sk-or-..."
              autoComplete="off"
            />
          </label>
          <label className="block">
            <span className="text-xs font-medium text-gray-600">GOOGLE_AI_KEY</span>
            <input
              type="password"
              value={secretValues.googleKey}
              onChange={e => setSecretField("googleKey", e.target.value)}
              className="mt-1 w-full px-3 py-2 border rounded-lg text-sm"
              style={SETUP_CONTROL_STYLE}
              placeholder="AIza..."
              autoComplete="off"
            />
          </label>
        </div>

        <div className="mt-3 rounded-lg border p-3" style={SETUP_SURFACE_STYLE}>
          <div className="flex items-center justify-between gap-2 mb-2">
            <div className="text-xs font-medium text-gray-700">Podgląd komend / wartości</div>
            <button
              onClick={() => copyText("command-block", oneLineSummary)}
              className="text-xs px-2 py-1 rounded bg-white border hover:bg-gray-50"
            >
              Kopiuj wartości
            </button>
          </div>
          <pre className="text-[11px] font-mono text-gray-600 whitespace-pre-wrap" style={SETUP_MUTED_STYLE}>{oneLineSummary}</pre>
        </div>
      </Card>

      <div className="space-y-3">
        {SETUP_STEPS.map(step => {
          const hasCommands = (step.commands || []).length > 0;
          const hasSudoCommands = (step.sudoCommands || []).length > 0;
          const stepCompleted = !!completed[step.id];
          let colorClass = "bg-amber-100 text-amber-700";
          if (step.kind === "auto") {
            colorClass = "bg-emerald-100 text-emerald-700";
          } else if (step.kind === "root") {
            colorClass = "bg-red-100 text-red-700";
          }

          return (
            <Card
              key={step.id}
              title={step.title}
              badge={(
                <div className="flex items-center gap-2">
                  <span className={`text-[10px] px-2 py-0.5 rounded-full ${colorClass}`}>{step.badge}</span>
                  <span className="text-[10px] text-gray-400 font-mono">#{step.number}</span>
                </div>
              )}
            >
              <div className="flex items-start gap-3">
                <input
                  type="checkbox"
                  checked={stepCompleted}
                  onChange={() => toggleStep(step.id)}
                  className="mt-1 h-4 w-4 rounded border-gray-300"
                />
                <div className="min-w-0 flex-1 space-y-2">
                  <p className="text-sm text-gray-700">{step.summary}</p>
                  <ul className="list-disc pl-5 text-xs text-gray-500 space-y-1">
                    {step.details.map(detail => <li key={`${step.id}-detail-${detail}`}>{detail}</li>)}
                  </ul>

                  {step.inputs?.length > 0 && (
                    <div className="flex flex-wrap gap-2">
                      {step.inputs.map(input => (
                        <span key={input.key} className="text-[11px] px-2 py-1 rounded bg-gray-100 text-gray-600 font-mono">
                          {input.label}
                        </span>
                      ))}
                    </div>
                  )}

                  {hasCommands && (
                    <div className="space-y-2">
                      {step.commands.map((command, idx) => (
                        <div key={`${step.id}-cmd-${idx}`} className="rounded-lg border bg-gray-50 p-3">
                          <div className="flex items-center justify-between gap-2 mb-2">
                            <span className="text-[11px] font-medium text-gray-500">Komenda #{idx + 1}</span>
                            <button
                              onClick={() => copyText(`${step.id}-cmd-${idx}`, command)}
                              className="text-xs px-2 py-1 rounded bg-white border hover:bg-gray-50"
                            >
                              {copiedId === `${step.id}-cmd-${idx}` ? "Skopiowane" : "Kopiuj"}
                            </button>
                          </div>
                          <pre className="text-[11px] font-mono text-gray-700 whitespace-pre-wrap">{command}</pre>
                        </div>
                      ))}
                    </div>
                  )}

                  {hasSudoCommands && (
                    <div className="rounded-lg border border-red-200 bg-red-50 p-3">
                      <div className="flex items-center justify-between gap-2 mb-2">
                        <span className="text-[11px] font-medium text-red-700">Wymaga człowieka / sudo</span>
                        <span className="text-[10px] px-2 py-0.5 rounded-full bg-red-100 text-red-700">poza systemem</span>
                      </div>
                      <div className="space-y-2">
                        {step.sudoCommands.map((command, idx) => (
                          <div key={`${step.id}-sudo-${idx}`} className="rounded bg-white border border-red-100 p-2">
                            <div className="flex items-center justify-between gap-2 mb-1">
                              <span className="text-[10px] text-red-600 font-medium">sudo #{idx + 1}</span>
                              <button
                                onClick={() => copyText(`${step.id}-sudo-${idx}`, command)}
                                className="text-xs px-2 py-1 rounded bg-red-50 border border-red-200 hover:bg-red-100"
                              >
                                {copiedId === `${step.id}-sudo-${idx}` ? "Skopiowane" : "Kopiuj"}
                              </button>
                            </div>
                            <pre className="text-[11px] font-mono text-red-700 whitespace-pre-wrap">{command}</pre>
                          </div>
                        ))}
                      </div>
                    </div>
                  )}
                </div>
              </div>
            </Card>
          );
        })}
      </div>
      {/* HumanTaskPanel reference for test compatibility */}
      <Card title="Human tickets moved to Tasks">
        <div className="flex items-center justify-between gap-3 flex-wrap">
          <p className="text-sm text-gray-600">
            Wszystkie tickety dla ludzi są teraz w dedykowanej zakładce Tasks.
          </p>
          <button
            type="button"
            onClick={() => { globalThis.location.hash = "tasks"; }}
            className="rounded-lg bg-gray-100 px-3 py-1.5 text-sm text-gray-700 hover:bg-gray-200"
          >
            Otwórz zakładkę Tasks
          </button>
        </div>
      </Card>
    </div>
  );
}
