import { useEffect, useState } from 'react';
import { Upload, FolderOpen, Loader2 } from 'lucide-react';
import {
  GetWebPublishConfig, SaveWebPublishConfig, WebPublishColumns,
  TestWebPublishFTP, PublishLogNow, GetWebPublishStatus, PickBackupFolder,
} from '../../wailsjs/go/main/App';
import { Button } from '@/components/ui/button';
import { Input } from '@/components/ui/input';
import { Label } from '@/components/ui/label';
import { Checkbox } from '@/components/ui/checkbox';
import { Select, SelectTrigger, SelectValue, SelectContent, SelectItem } from '@/components/ui/select';
import { useI18n } from '@/lib/i18n';
import { cn } from '@/lib/utils';

type Cfg = {
  enabled: boolean; format: string; folder: string; file_name: string; title: string;
  count: number; interval_min: number; columns: string[];
  ftp_enabled: boolean; ftp_host: string; ftp_port: number; ftp_user: string;
  ftp_password: string; ftp_tls: boolean; ftp_folder: string; ftp_file_name: string;
};
type Col = { key: string; header: string };

export function WebPublishPanel() {
  const { t } = useI18n();
  const [cfg, setCfg] = useState<Cfg | null>(null);
  const [cols, setCols] = useState<Col[]>([]);
  const [busy, setBusy] = useState<'' | 'test' | 'publish'>('');
  const [msg, setMsg] = useState('');
  const [err, setErr] = useState('');
  // Raw text for the two numeric boxes: bound straight to the number they could
  // not be cleared, the same trap as the Recent-QSOs Max field.
  const [countText, setCountText] = useState('');
  const [everyText, setEveryText] = useState('');

  useEffect(() => {
    (async () => {
      try {
        const [c, k, st] = await Promise.all([GetWebPublishConfig(), WebPublishColumns(), GetWebPublishStatus()]);
        setCfg(c as any);
        setCols((k ?? []) as Col[]);
        setCountText(String((c as any).count ?? 100));
        setEveryText(String((c as any).interval_min ?? 0));
        const s: any = st;
        if (s?.last_err) setErr(s.last_err);
        else if (s?.last_run) setMsg(t('wpub.lastRun') + ' ' + s.last_run);
      } catch (e: any) { setErr(String(e?.message ?? e)); }
    })();
    // eslint-disable-next-line react-hooks/exhaustive-deps
  }, []);

  if (!cfg) return <p className="text-xs text-muted-foreground">…</p>;
  const set = (p: Partial<Cfg>) => setCfg((c) => (c ? { ...c, ...p } : c));

  // Every control saves immediately: this panel has no Save button of its own,
  // matching the other "saved instantly" panels.
  const save = async (next: Cfg) => {
    setCfg(next);
    try { await SaveWebPublishConfig(next as any); setErr(''); }
    catch (e: any) { setErr(String(e?.message ?? e)); }
  };
  const patch = (p: Partial<Cfg>) => save({ ...cfg, ...p });

  const toggleCol = (key: string) => {
    const has = cfg.columns?.includes(key);
    patch({ columns: has ? cfg.columns.filter((c) => c !== key) : [...(cfg.columns ?? []), key] });
  };

  const run = async (what: 'test' | 'publish') => {
    setBusy(what); setMsg(''); setErr('');
    try {
      const r = what === 'test' ? await TestWebPublishFTP(cfg as any) : await PublishLogNow();
      setMsg(String(r));
    } catch (e: any) { setErr(String(e?.message ?? e)); }
    finally { setBusy(''); }
  };

  return (
    <div className="space-y-4 max-w-3xl">
      <p className="text-xs text-muted-foreground leading-relaxed">{t('wpub.hint')}</p>

      <label className="flex items-center gap-2 text-sm cursor-pointer">
        <Checkbox checked={cfg.enabled} onCheckedChange={(c) => patch({ enabled: !!c })} />
        {t('wpub.enable')}
      </label>

      {cfg.enabled && (<>
        {/* ── The file ── */}
        <div className="space-y-2 border-t border-border/60 pt-3">
          <Label className="text-xs font-semibold">{t('wpub.fileSection')}</Label>
          <div className="grid grid-cols-[130px_1fr] gap-2 items-center">
            <Label className="text-sm">{t('wpub.format')}</Label>
            <Select value={cfg.format} onValueChange={(v) => patch({ format: v })}>
              <SelectTrigger className="h-8 w-56"><SelectValue /></SelectTrigger>
              <SelectContent>
                <SelectItem value="html">{t('wpub.formatHtml')}</SelectItem>
                <SelectItem value="csv">{t('wpub.formatCsv')}</SelectItem>
              </SelectContent>
            </Select>

            <Label className="text-sm">{t('wpub.folder')}</Label>
            <div className="flex gap-2">
              <Input className="h-8 font-mono text-xs flex-1" value={cfg.folder}
                onChange={(e) => set({ folder: e.target.value })} onBlur={() => patch({ folder: cfg.folder })} />
              <Button variant="outline" size="sm" className="h-8" onClick={async () => {
                try { const p = await PickBackupFolder(); if (p) patch({ folder: p }); } catch { /* cancelled */ }
              }}><FolderOpen className="size-3.5" /> {t('wpub.browse')}</Button>
            </div>

            <Label className="text-sm">{t('wpub.fileName')}</Label>
            <Input className="h-8 w-56 font-mono text-xs" value={cfg.file_name}
              onChange={(e) => set({ file_name: e.target.value })} onBlur={() => patch({ file_name: cfg.file_name })} />

            <Label className="text-sm">{t('wpub.title')}</Label>
            <Input className="h-8" placeholder={t('wpub.titlePh')} value={cfg.title}
              onChange={(e) => set({ title: e.target.value })} onBlur={() => patch({ title: cfg.title })} />

            <Label className="text-sm">{t('wpub.count')}</Label>
            <Input type="number" min={1} max={100000} className="h-8 w-28 font-mono text-xs" value={countText}
              onChange={(e) => setCountText(e.target.value)}
              onBlur={() => {
                const n = Math.floor(Number(countText));
                if (Number.isFinite(n) && n > 0) patch({ count: n }); else setCountText(String(cfg.count));
              }} />

            <Label className="text-sm">{t('wpub.every')}</Label>
            <div className="flex items-center gap-2">
              <Input type="number" min={0} max={1440} className="h-8 w-28 font-mono text-xs" value={everyText}
                onChange={(e) => setEveryText(e.target.value)}
                onBlur={() => {
                  const n = Math.floor(Number(everyText));
                  if (Number.isFinite(n) && n >= 0) patch({ interval_min: n }); else setEveryText(String(cfg.interval_min));
                }} />
              <span className="text-xs text-muted-foreground">{t('wpub.everyHint')}</span>
            </div>
          </div>
        </div>

        {/* ── Columns ── */}
        <div className="space-y-2 border-t border-border/60 pt-3">
          <Label className="text-xs font-semibold">{t('wpub.columns')}</Label>
          <div className="flex flex-wrap gap-1.5">
            {cols.map((c) => {
              const on = cfg.columns?.includes(c.key);
              return (
                <button key={c.key} type="button" onClick={() => toggleCol(c.key)}
                  className={cn('px-2 py-0.5 rounded-full border text-[11px] font-medium transition-colors',
                    on ? 'border-primary bg-primary text-primary-foreground' : 'border-border text-muted-foreground hover:bg-muted')}>
                  {c.header}
                </button>
              );
            })}
          </div>
          <p className="text-[11px] text-muted-foreground">{t('wpub.columnsHint')}</p>
        </div>

        {/* ── Upload ── */}
        <div className="space-y-2 border-t border-border/60 pt-3">
          <label className="flex items-center gap-2 text-sm cursor-pointer">
            <Checkbox checked={cfg.ftp_enabled} onCheckedChange={(c) => patch({ ftp_enabled: !!c })} />
            {t('wpub.ftpEnable')}
          </label>
          {cfg.ftp_enabled && (
            <div className="grid grid-cols-[130px_1fr] gap-2 items-center">
              <Label className="text-sm">{t('wpub.ftpHost')}</Label>
              <div className="flex gap-2">
                <Input className="h-8 flex-1" placeholder="ftp.example.com" value={cfg.ftp_host}
                  onChange={(e) => set({ ftp_host: e.target.value })} onBlur={() => patch({ ftp_host: cfg.ftp_host })} />
                <Input type="number" className="h-8 w-24 font-mono text-xs" value={cfg.ftp_port}
                  onChange={(e) => set({ ftp_port: Number(e.target.value) || 21 })}
                  onBlur={() => patch({ ftp_port: cfg.ftp_port })} />
              </div>
              <Label className="text-sm">{t('wpub.ftpUser')}</Label>
              <Input className="h-8" value={cfg.ftp_user}
                onChange={(e) => set({ ftp_user: e.target.value })} onBlur={() => patch({ ftp_user: cfg.ftp_user })} />
              <Label className="text-sm">{t('wpub.ftpPassword')}</Label>
              <Input type="password" className="h-8" value={cfg.ftp_password}
                onChange={(e) => set({ ftp_password: e.target.value })} onBlur={() => patch({ ftp_password: cfg.ftp_password })} />
              <Label className="text-sm">{t('wpub.ftpFolder')}</Label>
              <Input className="h-8 font-mono text-xs" placeholder="/www/log" value={cfg.ftp_folder}
                onChange={(e) => set({ ftp_folder: e.target.value })} onBlur={() => patch({ ftp_folder: cfg.ftp_folder })} />
              <Label className="text-sm">{t('wpub.ftpFileName')}</Label>
              <Input className="h-8 w-56 font-mono text-xs" value={cfg.ftp_file_name}
                onChange={(e) => set({ ftp_file_name: e.target.value })} onBlur={() => patch({ ftp_file_name: cfg.ftp_file_name })} />
              <span />
              <label className="flex items-center gap-2 text-sm cursor-pointer">
                <Checkbox checked={cfg.ftp_tls} onCheckedChange={(c) => patch({ ftp_tls: !!c })} />
                {t('wpub.ftpTls')}
              </label>
            </div>
          )}
        </div>

        <div className="flex items-center gap-3 border-t border-border/60 pt-3 flex-wrap">
          <Button size="sm" onClick={() => run('publish')} disabled={busy !== ''}>
            {busy === 'publish' ? <Loader2 className="size-3.5 animate-spin" /> : <Upload className="size-3.5" />}
            {t('wpub.publishNow')}
          </Button>
          {cfg.ftp_enabled && (
            <Button variant="outline" size="sm" onClick={() => run('test')} disabled={busy !== ''}>
              {busy === 'test' ? <Loader2 className="size-3.5 animate-spin" /> : null}
              {t('wpub.testFtp')}
            </Button>
          )}
        </div>
      </>)}

      {msg && <p className="text-xs text-success break-all">{msg}</p>}
      {err && <p className="text-xs text-danger break-all">{err}</p>}
    </div>
  );
}
