import * as React from "react";
import {
  Box,
  Container,
  Paper,
  Typography,
  Button,
  IconButton,
  CircularProgress,
  Alert,
  Snackbar,
  Dialog,
  DialogTitle,
  DialogContent,
  DialogContentText,
  DialogActions,
  Chip,
} from "@mui/material";
import DeleteIcon from "@mui/icons-material/Delete";
import AddCircleIcon from "@mui/icons-material/AddCircle";
import RefreshIcon from "@mui/icons-material/Refresh";
import ContentCopyIcon from "@mui/icons-material/ContentCopy";
import { useResourceByName, useConfig, defaultFieldComponents } from "../react-openapi";
import type { ResourceField } from "../react-openapi";

interface ReportSnapshotQuery {
  accounts?: string[];
  ignore_self?: boolean;
  start_date?: string;
  end_date?: string;
}

interface ReportSnapshot {
  id: string;
  snapshot_id: string;
  created_at: string;
  query?: ReportSnapshotQuery;
}

function formatDate(iso: string) {
  const d = new Date(iso);
  return d.toLocaleString();
}

export default function ReportSnapshots() {
  const [ignoreSelf, setIgnoreSelf] = React.useState(true);
  const [startDate, setStartDate] = React.useState("");
  const [endDate, setEndDate] = React.useState("");
  const [minAmount, setMinAmount] = React.useState("");
  const [maxAmount, setMaxAmount] = React.useState("");
  const [snackbar, setSnackbar] = React.useState<{ message: string; severity: "success" | "error" } | null>(null);
  const [deleteTarget, setDeleteTarget] = React.useState<ReportSnapshot | null>(null);
  const [createdSnapshotId, setCreatedSnapshotId] = React.useState<string | null>(null);

  const { useList, useCreate, useDelete, components } = useResourceByName("reports", { fieldComponents: defaultFieldComponents });

  const { data: listData, isLoading, isFetching, refetch } = useList();
  const createMutation = useCreate();
  const deleteMutation = useDelete();

  const config = useConfig();
  const reportsRes = config?.resources.find((r: any) => r.name === "reports");
  const ignoreSelfField: ResourceField | undefined = reportsRes?.fields?.ignore_self;
  const startDateField: ResourceField | undefined = reportsRes?.fields?.start_date;
  const endDateField: ResourceField | undefined = reportsRes?.fields?.end_date;
  const minAmountField: ResourceField | undefined = reportsRes?.fields?.min_amount;
  const maxAmountField: ResourceField | undefined = reportsRes?.fields?.max_amount;

  const snapshots: ReportSnapshot[] = listData?.data ?? [];

  const handleCreate = async () => {
    try {
      const payload: Record<string, any> = {};
      if (ignoreSelf) payload.ignore_self = true;
      if (startDate) payload.start_date = new Date(startDate).toISOString();
      if (endDate) payload.end_date = new Date(endDate).toISOString();
      if (minAmount) payload.min_amount = parseFloat(minAmount);
      if (maxAmount) payload.max_amount = parseFloat(maxAmount);

      const result = await createMutation.mutateAsync(payload);
      const snapshotId = (result as any)?.snapshot_id;
      if (snapshotId) {
        setCreatedSnapshotId(snapshotId);
        setSnackbar({ message: `Snapshot created: ${snapshotId}`, severity: "success" });
      } else {
        setSnackbar({ message: "Snapshot created", severity: "success" });
      }
      resetForm();
    } catch (err: any) {
      setSnackbar({ message: err?.response?.data?.detail || "Failed to create snapshot", severity: "error" });
    }
  };

  const resetForm = () => {
    setIgnoreSelf(true);
    setStartDate("");
    setEndDate("");
    setMinAmount("");
    setMaxAmount("");
  };

  const handleDelete = async () => {
    if (!deleteTarget) return;
    try {
      await deleteMutation.mutateAsync(deleteTarget.snapshot_id);
      setSnackbar({ message: "Snapshot deleted", severity: "success" });
    } catch {
      setSnackbar({ message: "Failed to delete snapshot", severity: "error" });
    }
    setDeleteTarget(null);
  };

  return (
    <Container sx={{ mt: 4, mb: 4 }}>
      <Typography variant="h5" fontWeight="bold" gutterBottom>
        Report Snapshots
      </Typography>

      <Paper sx={{ p: 3, mb: 4, borderRadius: 4 }} variant="outlined">
        <Typography variant="subtitle1" fontWeight={600} gutterBottom>
          Generate New Snapshot
        </Typography>

        <Box sx={{ display: "flex", flexDirection: "column", gap: 2 }}>
          {ignoreSelfField && components?.FormField && (
            <components.FormField
              name="ignore_self"
              field={ignoreSelfField}
              value={ignoreSelf}
              onChange={(val: boolean) => setIgnoreSelf(val)}
            />
          )}

          <Box sx={{ display: "flex", gap: 2 }}>
            {startDateField && components?.date && (
              <Box sx={{ flex: 1 }}>
                <components.date
                  name="start_date"
                  field={startDateField}
                  value={startDate}
                  onChange={(val: string) => setStartDate(val)}
                />
              </Box>
            )}
            {endDateField && components?.date && (
              <Box sx={{ flex: 1 }}>
                <components.date
                  name="end_date"
                  field={endDateField}
                  value={endDate}
                  onChange={(val: string) => setEndDate(val)}
                />
              </Box>
            )}
          </Box>

          <Box sx={{ display: "flex", gap: 2 }}>
            {minAmountField && components?.FormField && (
              <Box sx={{ flex: 1 }}>
                <components.FormField
                  name="min_amount"
                  field={minAmountField}
                  value={minAmount}
                  onChange={(val: string) => setMinAmount(val)}
                />
              </Box>
            )}
            {maxAmountField && components?.FormField && (
              <Box sx={{ flex: 1 }}>
                <components.FormField
                  name="max_amount"
                  field={maxAmountField}
                  value={maxAmount}
                  onChange={(val: string) => setMaxAmount(val)}
                />
              </Box>
            )}
          </Box>

          <Button
            variant="contained"
            startIcon={<AddCircleIcon />}
            onClick={handleCreate}
            disabled={createMutation.isPending}
          >
            {createMutation.isPending ? "Generating..." : "Generate Snapshot"}
          </Button>

          {createdSnapshotId && (
            <Alert severity="success" onClose={() => setCreatedSnapshotId(null)}>
              Snapshot created: <strong>{createdSnapshotId}</strong>. Use it in the Dashboard snapshot selector.
            </Alert>
          )}
        </Box>
      </Paper>

      <Paper sx={{ borderRadius: 4 }} variant="outlined">
        <Box sx={{ display: "flex", alignItems: "center", justifyContent: "space-between", p: 2, pb: 0 }}>
          <Typography variant="subtitle1" fontWeight={600}>
            Existing Snapshots
          </Typography>
          <IconButton onClick={() => refetch()} disabled={isFetching}>
            <RefreshIcon />
          </IconButton>
        </Box>

        {isLoading ? (
          <Box sx={{ display: "flex", justifyContent: "center", p: 4 }}>
            <CircularProgress />
          </Box>
        ) : snapshots.length === 0 ? (
          <Box sx={{ p: 4, textAlign: "center", color: "text.secondary" }}>
            No snapshots yet
          </Box>
        ) : (
          <Box sx={{ overflowX: "auto" }}>
            <Box component="table" sx={{ width: "100%", borderCollapse: "collapse" }}>
              <Box component="thead">
                <Box component="tr" sx={{ borderBottom: 1, borderColor: "divider" }}>
                  {["Snapshot ID", "Created", "Query", "Actions"].map((h) => (
                    <Box
                      key={h}
                      component="th"
                      sx={{ px: 2, py: 1.5, textAlign: h === "Actions" ? "right" : "left", fontWeight: 600, fontSize: "0.8rem", color: "text.secondary", whiteSpace: "nowrap" }}
                    >
                      {h}
                    </Box>
                  ))}
                </Box>
              </Box>
              <Box component="tbody">
                {snapshots.map((snap: ReportSnapshot) => (
                  <Box
                    key={snap.id}
                    component="tr"
                    sx={{ borderBottom: 1, borderColor: "divider", "&:last-child": { borderBottom: 0 }, "&:hover": { bgcolor: "action.hover" } }}
                  >
                    <Box component="td" sx={{ px: 2, py: 1.5, fontFamily: "monospace", fontSize: "0.8rem" }}>
                      <Box sx={{ display: "flex", alignItems: "center", gap: 0.5 }}>
                        {snap.snapshot_id}
                        <IconButton
                          size="small"
                          onClick={() => {
                            navigator.clipboard.writeText(snap.snapshot_id);
                            setSnackbar({ message: "Copied!", severity: "success" });
                          }}
                          sx={{ opacity: 0.5, '&:hover': { opacity: 1 } }}
                        >
                          <ContentCopyIcon sx={{ fontSize: 14 }} />
                        </IconButton>
                      </Box>
                    </Box>
                    <Box component="td" sx={{ px: 2, py: 1.5, fontSize: "0.875rem" }}>
                      {formatDate(snap.created_at)}
                    </Box>
                    <Box component="td" sx={{ px: 2, py: 1.5 }}>
                      {snap.query ? (
                        <Box sx={{ display: "flex", gap: 0.5, flexWrap: "wrap" }}>
                          {snap.query.accounts && <Chip label={`${snap.query.accounts.length} account(s)`} size="small" variant="outlined" />}
                          {snap.query.ignore_self && <Chip label="ignore_self" size="small" variant="outlined" />}
                          {snap.query.start_date && <Chip label="start" size="small" variant="outlined" />}
                          {snap.query.end_date && <Chip label="end" size="small" variant="outlined" />}
                        </Box>
                      ) : (
                        <Typography variant="body2" color="text.secondary">\u2014</Typography>
                      )}
                    </Box>
                    <Box component="td" sx={{ px: 2, py: 1.5 }}>
                      <Box sx={{ display: "flex", gap: 0.5, justifyContent: "flex-end" }}>
                        <IconButton size="small" onClick={() => setDeleteTarget(snap)}>
                          <DeleteIcon fontSize="small" />
                        </IconButton>
                      </Box>
                    </Box>
                  </Box>
                ))}
              </Box>
            </Box>
          </Box>
        )}
      </Paper>

      <Snackbar
        open={!!snackbar}
        autoHideDuration={4000}
        onClose={() => setSnackbar(null)}
        anchorOrigin={{ vertical: "bottom", horizontal: "center" }}
      >
        {snackbar ? <Alert severity={snackbar.severity} onClose={() => setSnackbar(null)}>{snackbar.message}</Alert> : undefined}
      </Snackbar>

      <Dialog open={!!deleteTarget} onClose={() => setDeleteTarget(null)}>
        <DialogTitle>Delete Snapshot?</DialogTitle>
        <DialogContent>
          <DialogContentText>
            This will permanently delete the report snapshot.
          </DialogContentText>
        </DialogContent>
        <DialogActions>
          <Button onClick={() => setDeleteTarget(null)}>Cancel</Button>
          <Button onClick={handleDelete} color="error" disabled={deleteMutation.isPending}>
            {deleteMutation.isPending ? "Deleting..." : "Delete"}
          </Button>
        </DialogActions>
      </Dialog>
    </Container>
  );
}
