/**
 * Trouve-KA — contrôles du robot (pause, seeds, recrawl, blocage)
 * Author: Simon-Pierre Boucher
 * Contact: contact@spboucher.ai
 */

"use client";

import { useState, type FormEvent } from "react";
import { Button } from "@/components/ui/button";
import { Card, CardContent, CardHeader, CardTitle } from "@/components/ui/card";
import { Input } from "@/components/ui/input";
import { adminFetch, UnauthorizedError } from "@/lib/admin";

type Feedback = { kind: "ok" | "err"; text: string } | null;

interface ControlsProps {
  token: string;
  paused: boolean;
  onUnauthorized: () => void;
  /** Rafraîchit la vue d'ensemble après une action réussie. */
  onRefresh: () => void;
}

export function Controls({
  token,
  paused,
  onUnauthorized,
  onRefresh,
}: ControlsProps) {
  const [busy, setBusy] = useState<string | null>(null);
  const [feedback, setFeedback] = useState<Feedback>(null);
  const [seeds, setSeeds] = useState("");
  const [recrawlTarget, setRecrawlTarget] = useState("");
  const [blockDomain, setBlockDomain] = useState("");

  async function run(
    name: string,
    action: () => Promise<unknown>,
    okMessage: string,
  ): Promise<boolean> {
    setBusy(name);
    setFeedback(null);
    try {
      await action();
      setFeedback({ kind: "ok", text: okMessage });
      onRefresh();
      return true;
    } catch (err) {
      if (err instanceof UnauthorizedError) {
        onUnauthorized();
        return false;
      }
      setFeedback({ kind: "err", text: "L'opération a échoué. Réessayez." });
      return false;
    } finally {
      setBusy(null);
    }
  }

  function togglePause() {
    const path = paused ? "/api/admin/resume" : "/api/admin/pause";
    run(
      "pause",
      () => adminFetch(path, token, { method: "POST" }),
      paused ? "Robot relancé." : "Robot mis en pause.",
    );
  }

  function submitSeeds(event: FormEvent) {
    event.preventDefault();
    const urls = seeds
      .split("\n")
      .map((line) => line.trim())
      .filter((line) => /^https?:\/\//.test(line));
    if (urls.length === 0) {
      setFeedback({
        kind: "err",
        text: "Entrez au moins une URL valide (une par ligne, http:// ou https://).",
      });
      return;
    }
    run(
      "seeds",
      () =>
        adminFetch("/api/admin/seeds", token, {
          method: "POST",
          body: JSON.stringify({ urls }),
        }),
      `${urls.length} seed(s) ajouté(s) au frontier.`,
    ).then((ok) => {
      if (ok) setSeeds("");
    });
  }

  function submitRecrawl(event: FormEvent) {
    event.preventDefault();
    const target = recrawlTarget.trim();
    if (!target) return;
    const body = /^https?:\/\//.test(target)
      ? { url: target }
      : { domain: target };
    run(
      "recrawl",
      () =>
        adminFetch("/api/admin/recrawl", token, {
          method: "POST",
          body: JSON.stringify(body),
        }),
      "Recrawl demandé.",
    ).then((ok) => {
      if (ok) setRecrawlTarget("");
    });
  }

  function submitBlock(event: FormEvent) {
    event.preventDefault();
    const domain = blockDomain.trim();
    if (!domain) return;
    run(
      "block",
      () =>
        adminFetch("/api/admin/domains/block", token, {
          method: "POST",
          body: JSON.stringify({ domain }),
        }),
      `Domaine « ${domain} » bloqué.`,
    ).then((ok) => {
      if (ok) setBlockDomain("");
    });
  }

  return (
    <Card>
      <CardHeader className="flex items-center justify-between gap-3">
        <CardTitle>Contrôles du robot</CardTitle>
        <Button
          variant={paused ? "default" : "outline"}
          size="sm"
          onClick={togglePause}
          disabled={busy !== null}
        >
          {paused ? "Reprendre le crawl" : "Mettre en pause"}
        </Button>
      </CardHeader>
      <CardContent className="space-y-6">
        <form onSubmit={submitSeeds}>
          <label htmlFor="seeds-admin" className="klabel block">
            Ajouter des seeds (une URL par ligne)
          </label>
          <textarea
            id="seeds-admin"
            rows={3}
            value={seeds}
            onChange={(event) => setSeeds(event.target.value)}
            placeholder={"https://www.quebec.ca\nhttps://www.mamunicipalite.qc.ca"}
            className="field mt-2 text-sm"
          />
          <Button
            type="submit"
            size="sm"
            className="mt-2"
            disabled={busy !== null}
          >
            {busy === "seeds" ? "Ajout…" : "Ajouter au frontier"}
          </Button>
        </form>

        <form onSubmit={submitRecrawl}>
          <label htmlFor="recrawl-admin" className="klabel block">
            Recrawler une URL ou un domaine
          </label>
          <div className="mt-2 flex flex-col gap-2 sm:flex-row">
            <Input
              id="recrawl-admin"
              value={recrawlTarget}
              onChange={(event) => setRecrawlTarget(event.target.value)}
              placeholder="https://exemple.quebec/page ou exemple.quebec"
              className="flex-1"
            />
            <Button type="submit" size="sm" disabled={busy !== null}>
              {busy === "recrawl" ? "Envoi…" : "Recrawler"}
            </Button>
          </div>
        </form>

        <form onSubmit={submitBlock}>
          <label htmlFor="block-admin" className="klabel block">
            Bloquer un domaine
          </label>
          <div className="mt-2 flex flex-col gap-2 sm:flex-row">
            <Input
              id="block-admin"
              value={blockDomain}
              onChange={(event) => setBlockDomain(event.target.value)}
              placeholder="spam-exemple.com"
              className="flex-1"
            />
            <Button
              type="submit"
              variant="danger"
              size="sm"
              disabled={busy !== null}
            >
              {busy === "block" ? "Blocage…" : "Bloquer"}
            </Button>
          </div>
        </form>

        <p aria-live="polite" className="min-h-5 text-sm">
          {feedback ? (
            <span
              className={
                feedback.kind === "ok"
                  ? "font-medium text-green"
                  : "font-medium text-danger"
              }
            >
              {feedback.text}
            </span>
          ) : null}
        </p>
      </CardContent>
    </Card>
  );
}
