import { useCallback, useEffect, useRef, useState } from "react";
import { Button, Field, Input, MessageBar, MessageBarBody, Select, Spinner, Text } from "@fluentui/react-components";
import { PlayRegular } from "@fluentui/react-icons";
import { useCommonSectionStyles } from "../../components/commonStyles";
import { useSchedule } from "../../hooks/useBlocklist";
import { useBlocklistStyles } from "./blocklistStyles";
import type { ScheduleConfig, ScheduleFrequency } from "../../types/blocklist";

const FREQUENCY_LABELS: Record<ScheduleFrequency, string> = {
  hourly: "Every N hours",
  daily: "Daily",
  weekly: "Weekly",
};

const DAYS = ["Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday", "Sunday"];

interface ScheduleSectionProps {
  onRunImport: () => void;
  runImportRunning: boolean;
}

export function BlocklistScheduleSection({ onRunImport, runImportRunning }: ScheduleSectionProps): React.JSX.Element {
  const styles = useBlocklistStyles();
  const sectionStyles = useCommonSectionStyles();
  const { info, loading, error, saveSchedule } = useSchedule();
  const [saving, setSaving] = useState(false);
  const [saveMsg, setSaveMsg] = useState<string | null>(null);
  const saveTimeoutRef = useRef<ReturnType<typeof setTimeout> | null>(null);

  const config = info?.config ?? {
    frequency: "daily" as ScheduleFrequency,
    interval_hours: 24,
    hour: 3,
    minute: 0,
    day_of_week: 0,
  };

  const [draft, setDraft] = useState<ScheduleConfig>(config);

  const handleSave = useCallback((): void => {
    if (saveTimeoutRef.current) {
      clearTimeout(saveTimeoutRef.current);
      saveTimeoutRef.current = null;
    }

    setSaving(true);
    saveSchedule(draft)
      .then(() => {
        setSaveMsg("Schedule saved.");
        setSaving(false);
        saveTimeoutRef.current = setTimeout(() => {
          setSaveMsg(null);
          saveTimeoutRef.current = null;
        }, 3000);
      })
      .catch((err: unknown) => {
        setSaveMsg(err instanceof Error ? err.message : "Failed to save schedule");
        setSaving(false);
      });
  }, [draft, saveSchedule]);

  useEffect(() => {
    return (): void => {
      if (saveTimeoutRef.current) {
        clearTimeout(saveTimeoutRef.current);
      }
    };
  }, []);

  return (
    <div className={sectionStyles.section}>
      <div className={sectionStyles.sectionHeader}>
        <Text size={500} weight="semibold">
          Import Schedule
        </Text>
        <Button icon={<PlayRegular />} appearance="secondary" onClick={onRunImport} disabled={runImportRunning}>
          {runImportRunning ? <Spinner size="tiny" /> : "Run Now"}
        </Button>
      </div>

      {error && (
        <MessageBar intent="error">
          <MessageBarBody>{error}</MessageBarBody>
        </MessageBar>
      )}
      {saveMsg && (
        <MessageBar intent={saveMsg === "Schedule saved." ? "success" : "error"}>
          <MessageBarBody>{saveMsg}</MessageBarBody>
        </MessageBar>
      )}

      {loading ? (
        <div className={styles.centred}>
          <Spinner label="Loading schedule…" />
        </div>
      ) : (
        <>
          <div className={styles.scheduleForm}>
            <Field label="Frequency" className={styles.scheduleField}>
              <Select
                value={draft.frequency}
                onChange={(_ev, d) => { setDraft((p) => ({ ...p, frequency: d.value as ScheduleFrequency })); }}
              >
                {(["hourly", "daily", "weekly"] as ScheduleFrequency[]).map((f) => (
                  <option key={f} value={f}>
                    {FREQUENCY_LABELS[f]}
                  </option>
                ))}
              </Select>
            </Field>

            {draft.frequency === "hourly" && (
              <Field label="Every (hours)" className={styles.scheduleField}>
                <Input
                  type="number"
                  value={String(draft.interval_hours)}
                  onChange={(_ev, d) => { setDraft((p) => ({ ...p, interval_hours: Math.max(1, parseInt(d.value, 10) || 1) })); }}
                  min={1}
                  max={168}
                />
              </Field>
            )}

            {draft.frequency !== "hourly" && (
              <>
                {draft.frequency === "weekly" && (
                  <Field label="Day of week" className={styles.scheduleField}>
                    <Select
                      value={String(draft.day_of_week)}
                      onChange={(_ev, d) => { setDraft((p) => ({ ...p, day_of_week: parseInt(d.value, 10) })); }}
                    >
                      {DAYS.map((day, i) => (
                        <option key={day} value={i}>
                          {day}
                        </option>
                      ))}
                    </Select>
                  </Field>
                )}

                <Field label="Hour (UTC)" className={styles.scheduleField}>
                  <Select
                    value={String(draft.hour)}
                    onChange={(_ev, d) => { setDraft((p) => ({ ...p, hour: parseInt(d.value, 10) })); }}
                  >
                    {Array.from({ length: 24 }, (_, i) => (
                      <option key={i} value={i}>
                        {String(i).padStart(2, "0")}:00
                      </option>
                    ))}
                  </Select>
                </Field>

                <Field label="Minute" className={styles.scheduleField}>
                  <Select
                    value={String(draft.minute)}
                    onChange={(_ev, d) => { setDraft((p) => ({ ...p, minute: parseInt(d.value, 10) })); }}
                  >
                    {[0, 15, 30, 45].map((m) => (
                      <option key={m} value={m}>
                        {String(m).padStart(2, "0")}
                      </option>
                    ))}
                  </Select>
                </Field>
              </>
            )}

            <Button appearance="primary" className={styles.saveButton} onClick={handleSave} disabled={saving}>
              {saving ? <Spinner size="tiny" /> : "Save Schedule"}
            </Button>
          </div>

          <div className={styles.metaRow}>
            <div className={styles.metaItem}>
              <Text size={200} weight="semibold">
                Last run
              </Text>
              <Text size={200}>{info?.last_run_at ?? "Never"}</Text>
            </div>
            <div className={styles.metaItem}>
              <Text size={200} weight="semibold">
                Next run
              </Text>
              <Text size={200}>{info?.next_run_at ?? "Not scheduled"}</Text>
            </div>
          </div>
        </>
      )}
    </div>
  );
}
