import React, { useState, useEffect } from "react";
import { useNavigate } from "react-router-dom";
import { toast } from "react-toastify";
import "react-toastify/dist/ReactToastify.css";
import {
  Box,
  Button,
  Card,
  CardContent,
  CardHeader,
  Checkbox,
  Chip,
  Dialog,
  DialogActions,
  DialogContent,
  DialogTitle,
  Divider,
  FormControlLabel,
  Grid,
  IconButton,
  Menu,
  MenuItem,
  Pagination,
  Paper,
  Select,
  Stack,
  Table,
  TableBody,
  TableCell,
  TableContainer,
  TableHead,
  TableRow,
  TextField,
  Typography,
} from "@mui/material";
import {
  Add,
  ArrowBack,
  CheckCircle,
  Close,
  Delete,
  Edit,
  MoreVert,
  PlayArrow,
  Search,
  Settings,
  ViewList,
} from "@mui/icons-material";
import ReportSqlBuilderApi from "./../../../ApiServices/ReportSQLBuilderAPI";
import { addSQLReport } from "./../../../ApiServices/AddReportSQLBuilderAPI";
import { UpdateReportSQLBuilder } from "./../../../ApiServices/UpdateReportSQLBuilderAPI";
import { deleteReportSQL } from "./../../../ApiServices/DeleteReportSQLAPI";
import ReportBuilderService from "../../../ApiServices/ReportBuilderService";

const ReportBuilderSQL = () => {
  const [userDetails, setUserDetails] = useState([]);
  const [searchQuery, setSearchQuery] = useState("");
  const [loading, setLoading] = useState(true);
  const [rowsPerPage, setRowsPerPage] = useState(10);
  const [currentPage, setCurrentPage] = useState(1);
  const navigate = useNavigate();
  const [visibleColumns, setVisibleColumns] = useState({
    reportName: true,
    description: true,
    action: true,
    status: true,
  });
  const [editDialogOpen, setEditDialogOpen] = useState(false);
  const [addDialogOpen, setAddDialogOpen] = useState(false);
  const [selectedReport, setSelectedReport] = useState(null);
  const [editData, setEditData] = useState({
    reportName: "",
    description: "",
    active: false,
  });
  const [newData, setNewData] = useState({
    reportName: "",
    description: "",
    active: false,
    isSql: true,
    Rpt_builder2_lines: [{ model: "" }],
  });
  const [deleteConfirmOpen, setDeleteConfirmOpen] = useState(false);
  const [itemToDelete, setItemToDelete] = useState({ id: null, name: "" });
  const [reportConfigOpen, setReportConfigOpen] = useState(false);
  const [reportConfigData, setReportConfigData] = useState({
    conn_name: "",
    date_param_req: "",
    std_param_html: "",
    adhoc_param_html: "",
    column_str: "",
    sql_str: "",
    id: null,
  });
  const [databaseConnections, setDatabaseConnections] = useState([]);
  const [columnsMenuAnchor, setColumnsMenuAnchor] = useState(null);
  const [rowsMenuAnchor, setRowsMenuAnchor] = useState(null);

  const fetchUserDetails = async () => {
    try {
      setLoading(true);
      const data = await ReportSqlBuilderApi.fetchUserDetails();
      setUserDetails(data);
      toast.success("Data fetched successfully!");
    } catch (error) {
      console.error("Error fetching user details:", error);
      toast.error("Failed to fetch user details.");
    } finally {
      setLoading(false);
    }
  };

  useEffect(() => {
    fetchUserDetails();
  }, []);

  const handleSearch = (e) => {
    setSearchQuery(e.target.value);
    setCurrentPage(1);
  };

  const filteredData = userDetails.filter((item) =>
    item.reportName?.toLowerCase().includes(searchQuery.toLowerCase())
  );

  const totalPages = Math.ceil(filteredData.length / rowsPerPage);
  const paginatedData = filteredData.slice(
    (currentPage - 1) * rowsPerPage,
    currentPage * rowsPerPage
  );

  const handleEdit = (report) => {
    setEditData(report);
    setEditDialogOpen(true);
  };

  const handleEditSubmit = async () => {
    try {
      const updatedReport = await UpdateReportSQLBuilder(editData.id, editData);
      setUserDetails(
        userDetails.map((detail) =>
          detail.id === editData.id ? { ...detail, ...editData } : detail
        )
      );
      setEditDialogOpen(false);
      toast.success("Report updated successfully");
    } catch (error) {
      console.error("Error updating report:", error);
      toast.error("Failed to update report");
    }
  };

  const handleAddSubmit = async () => {
    try {
      const addedReport = await addSQLReport(newData);
      setUserDetails([...userDetails, addedReport]);
      setAddDialogOpen(false);
      setNewData({
        reportName: "",
        description: "",
        active: false,
        isSql: true,
        Rpt_builder2_lines: [{ model: "" }],
      });
      toast.success("Report added successfully");
    } catch (error) {
      console.error("Error adding report:", error);
      toast.error("Failed to add report");
    }
  };

  const handleDelete = async () => {
    try {
      await deleteReportSQL(itemToDelete.id);
      setUserDetails(userDetails.filter((item) => item.id !== itemToDelete.id));
      setDeleteConfirmOpen(false);
      toast.success("Report deleted successfully");
    } catch (error) {
      console.error("Error deleting report:", error);
      toast.error("Failed to delete report");
    }
  };

  const fetchDatabaseConnections = async () => {
    try {
      const response = await ReportBuilderService.getDatabase();
      setDatabaseConnections(response?.data || []);
    } catch (error) {
      console.error("Error fetching database connections:", error);
      toast.error("Failed to load database connections");
    }
  };

  const handleRowClick = async (report) => {
    try {
      setLoading(true);
      await fetchDatabaseConnections();
      
      const response = await ReportBuilderService.getrbLineDetailsById(
        report.rpt_builder2_lines[0].id
      );
      
      let configData = {};
      if (report.Rpt_builder2_lines?.length > 0) {
        try {
          const modelData = JSON.parse(report.Rpt_builder2_lines[0].model);
          configData = {
            conn_name: modelData.conn_name || "",
            date_param_req: modelData.date_param_req || "",
            std_param_html: modelData.std_param_html || "",
            adhoc_param_html: modelData.adhoc_param_html || "",
            column_str: modelData.column_str || "",
            sql_str: modelData.sql_str || "",
            id: report.rpt_builder2_lines[0].id,
          };
        } catch (error) {
          console.error("Error parsing report config:", error);
          configData = {
            conn_name: "",
            date_param_req: "",
            std_param_html: "",
            adhoc_param_html: "",
            column_str: "",
            sql_str: "",
            id: report.rpt_builder2_lines[0].id,
          };
        }
      }
      
      setReportConfigData(configData);
      setReportConfigOpen(true);
    } catch (error) {
      console.error("Error fetching report config:", error);
      toast.error("Failed to load report configuration");
    } finally {
      setLoading(false);
    }
  };

  const handleReportConfigUpdate = async () => {
    try {
      setLoading(true);
      const reportData = {
        conn_name: reportConfigData.conn_name,
        sql_str: reportConfigData.sql_str,
        date_param_req: reportConfigData.date_param_req,
        column_str: reportConfigData.column_str,
        adhoc_param_html: reportConfigData.adhoc_param_html,
        std_param_html: reportConfigData.std_param_html,
      };

      const saveReportData = {
        header_id: reportConfigData.id,
        model: JSON.stringify(reportData),
      };

      await ReportBuilderService.updaterbLineData(
        saveReportData,
        reportConfigData.id
      );
      setReportConfigOpen(false);
      toast.success("Report configuration updated");
      fetchUserDetails();
    } catch (error) {
      console.error("Error updating report config:", error);
      toast.error("Failed to update report configuration");
    } finally {
      setLoading(false);
    }
  };

  const goToRunner = (report) => {
    if (!report || typeof report.isSql === "undefined") return;
    navigate(
      report.isSql
        ? `/admin/report-runner/${report.id}`
        : `/admin/report-runner2/${report.id}`
    );
  };

  const toggleColumn = (column) => {
    setVisibleColumns((prev) => ({
      ...prev,
      [column]: !prev[column],
    }));
  };

  return (
    <Box sx={{ p: 3 }}>
      <Card sx={{ mb: 3 }}>
        <CardContent>
          <Grid container spacing={2} alignItems="center">
            <Grid item xs={12} md={6}>
              <Typography variant="h5" component="h1">
                Report Builder (SQL)
              </Typography>
            </Grid>
            <Grid item xs={12} md={6}>
              <Stack direction="row" spacing={2} justifyContent="flex-end">
                <Button
                  variant="contained"
                  startIcon={<PlayArrow />}
                  onClick={() => navigate("/dashboard/reports")}
                >
                  Report Runner
                </Button>
                <Button
                  variant="contained"
                  startIcon={<Add />}
                  onClick={() => setAddDialogOpen(true)}
                >
                  Add Report
                </Button>
              </Stack>
            </Grid>
          </Grid>
        </CardContent>
      </Card>

      <Card>
        <CardContent>
          <Grid container spacing={2} alignItems="center" sx={{ mb: 2 }}>
            <Grid item xs={12} md={6}>
              <TextField
                fullWidth
                variant="outlined"
                placeholder="Search"
                value={searchQuery}
                onChange={handleSearch}
                InputProps={{
                  startAdornment: (
                    <Search sx={{ color: "action.active", mr: 1 }} />
                  ),
                }}
              />
            </Grid>
            <Grid item xs={12} md={6}>
              <Stack direction="row" spacing={2} justifyContent="flex-end">
                <Button
                  variant="outlined"
                  onClick={(e) => setColumnsMenuAnchor(e.currentTarget)}
                  startIcon={<ViewList />}
                >
                  Manage Columns
                </Button>
                <Menu
                  anchorEl={columnsMenuAnchor}
                  open={Boolean(columnsMenuAnchor)}
                  onClose={() => setColumnsMenuAnchor(null)}
                >
                  {Object.keys(visibleColumns).map((column) => (
                    <MenuItem key={column} onClick={() => toggleColumn(column)}>
                      <FormControlLabel
                        control={
                          <Checkbox checked={visibleColumns[column]} readOnly />
                        }
                        label={column.charAt(0).toUpperCase() + column.slice(1)}
                      />
                    </MenuItem>
                  ))}
                </Menu>

                <Button
                  variant="outlined"
                  onClick={(e) => setRowsMenuAnchor(e.currentTarget)}
                  endIcon={<MoreVert />}
                >
                  {rowsPerPage} rows
                </Button>
                <Menu
                  anchorEl={rowsMenuAnchor}
                  open={Boolean(rowsMenuAnchor)}
                  onClose={() => setRowsMenuAnchor(null)}
                >
                  {[5, 10, 20, 50].map((num) => (
                    <MenuItem
                      key={num}
                      onClick={() => {
                        setRowsPerPage(num);
                        setRowsMenuAnchor(null);
                      }}
                    >
                      {num}
                      {rowsPerPage === num && (
                        <CheckCircle sx={{ ml: 1, color: "primary.main" }} />
                      )}
                    </MenuItem>
                  ))}
                </Menu>
              </Stack>
            </Grid>
          </Grid>

          <TableContainer component={Paper}>
            <Table>
              <TableHead>
                <TableRow>
                  <TableCell>Go To</TableCell>
                  {visibleColumns.reportName && <TableCell>Report Name</TableCell>}
                  {visibleColumns.description && <TableCell>Description</TableCell>}
                  {visibleColumns.status && <TableCell>Status</TableCell>}
                  {visibleColumns.action && <TableCell>Actions</TableCell>}
                </TableRow>
              </TableHead>
              <TableBody>
                {paginatedData.length === 0 ? (
                  <TableRow>
                    <TableCell colSpan={5} align="center">
                      No records found
                    </TableCell>
                  </TableRow>
                ) : (
                  paginatedData
                    .filter((detail) => detail.isSql)
                    .map((detail) => (
                      <TableRow
                        key={detail.id}
                        hover
                        onClick={() => handleRowClick(detail)}
                        sx={{ cursor: "pointer" }}
                      >
                        <TableCell>
                          <IconButton
                            onClick={(e) => {
                              e.stopPropagation();
                              handleRowClick(detail);
                            }}
                          >
                            <Settings color="primary" />
                          </IconButton>
                        </TableCell>
                        {visibleColumns.reportName && (
                          <TableCell>{detail.reportName}</TableCell>
                        )}
                        {visibleColumns.description && (
                          <TableCell>
                            {detail.description || "No description available"}
                          </TableCell>
                        )}
                        {visibleColumns.status && (
                          <TableCell>
                            <Chip
                              label={detail.active ? "Active" : "Inactive"}
                              color={detail.active ? "success" : "error"}
                              size="small"
                            />
                          </TableCell>
                        )}
                        {visibleColumns.action && (
                          <TableCell>
                            <IconButton
                              onClick={(e) => {
                                e.stopPropagation();
                                handleEdit(detail);
                              }}
                            >
                              <Edit color="primary" />
                            </IconButton>
                            <IconButton
                              onClick={(e) => {
                                e.stopPropagation();
                                setItemToDelete({
                                  id: detail.id,
                                  name: detail.reportName,
                                });
                                setDeleteConfirmOpen(true);
                              }}
                            >
                              <Delete color="error" />
                            </IconButton>
                          </TableCell>
                        )}
                      </TableRow>
                    ))
                )}
              </TableBody>
            </Table>
          </TableContainer>

          <Stack
            direction="row"
            justifyContent="space-between"
            alignItems="center"
            sx={{ mt: 2 }}
          >
            <Typography variant="body2">
              Showing {(currentPage - 1) * rowsPerPage + 1} to{" "}
              {Math.min(currentPage * rowsPerPage, filteredData.length)} of{" "}
              {filteredData.length} entries
            </Typography>
            <Pagination
              count={totalPages}
              page={currentPage}
              onChange={(e, page) => setCurrentPage(page)}
              color="primary"
            />
          </Stack>
        </CardContent>
      </Card>

      {/* Edit Dialog */}
      <Dialog open={editDialogOpen} onClose={() => setEditDialogOpen(false)}>
        <DialogTitle>
          Edit Report
          <IconButton
            sx={{ position: "absolute", right: 8, top: 8 }}
            onClick={() => setEditDialogOpen(false)}
          >
            <Close />
          </IconButton>
        </DialogTitle>
        <DialogContent>
          <Box sx={{ mt: 2 }}>
            <TextField
              fullWidth
              label="Report Name"
              value={editData.reportName || ""}
              onChange={(e) =>
                setEditData({ ...editData, reportName: e.target.value })
              }
              sx={{ mb: 2 }}
            />
            <TextField
              fullWidth
              label="Description"
              value={editData.description || ""}
              onChange={(e) =>
                setEditData({ ...editData, description: e.target.value })
              }
              sx={{ mb: 2 }}
            />
            <FormControlLabel
              control={
                <Checkbox
                  checked={editData.active || false}
                  onChange={(e) =>
                    setEditData({ ...editData, active: e.target.checked })
                  }
                />
              }
              label="Active"
            />
          </Box>
        </DialogContent>
        <DialogActions>
          <Button onClick={() => setEditDialogOpen(false)}>Cancel</Button>
          <Button variant="contained" onClick={handleEditSubmit}>
            Save Changes
          </Button>
        </DialogActions>
      </Dialog>

      {/* Add Dialog */}
      <Dialog open={addDialogOpen} onClose={() => setAddDialogOpen(false)}>
        <DialogTitle>
          Add New Report
          <IconButton
            sx={{ position: "absolute", right: 8, top: 8 }}
            onClick={() => setAddDialogOpen(false)}
          >
            <Close />
          </IconButton>
        </DialogTitle>
        <DialogContent>
          <Box sx={{ mt: 2 }}>
            <TextField
              fullWidth
              label="Report Name"
              value={newData.reportName}
              onChange={(e) =>
                setNewData({ ...newData, reportName: e.target.value })
              }
              sx={{ mb: 2 }}
            />
            <TextField
              fullWidth
              label="Description"
              value={newData.description}
              onChange={(e) =>
                setNewData({ ...newData, description: e.target.value })
              }
              sx={{ mb: 2 }}
            />
            <FormControlLabel
              control={
                <Checkbox
                  checked={newData.active}
                  onChange={(e) =>
                    setNewData({ ...newData, active: e.target.checked })
                  }
                />
              }
              label="Active"
            />
          </Box>
        </DialogContent>
        <DialogActions>
          <Button onClick={() => setAddDialogOpen(false)}>Cancel</Button>
          <Button variant="contained" onClick={handleAddSubmit}>
            Add Report
          </Button>
        </DialogActions>
      </Dialog>

      {/* Delete Confirmation Dialog */}
      <Dialog
        open={deleteConfirmOpen}
        onClose={() => setDeleteConfirmOpen(false)}
      >
        <DialogTitle>Confirm Deletion</DialogTitle>
        <DialogContent>
          <Typography>
            Are you sure you want to delete "{itemToDelete.name}"? This action
            cannot be undone.
          </Typography>
        </DialogContent>
        <DialogActions>
          <Button onClick={() => setDeleteConfirmOpen(false)}>Cancel</Button>
          <Button variant="contained" color="error" onClick={handleDelete}>
            Delete
          </Button>
        </DialogActions>
      </Dialog>

      {/* Report Configuration Dialog */}
      <Dialog
        open={reportConfigOpen}
        onClose={() => setReportConfigOpen(false)}
        maxWidth="md"
        fullWidth
      >
        <DialogTitle>
          Report Configuration
          <IconButton
            sx={{ position: "absolute", right: 8, top: 8 }}
            onClick={() => setReportConfigOpen(false)}
          >
            <Close />
          </IconButton>
        </DialogTitle>
        <DialogContent>
          <Box sx={{ mt: 2 }}>
            <Grid container spacing={2}>
              <Grid item xs={12} md={6}>
                <TextField
                  select
                  fullWidth
                  label="Connection Name"
                  name="conn_name"
                  value={reportConfigData.conn_name}
                  onChange={(e) =>
                    setReportConfigData({
                      ...reportConfigData,
                      conn_name: e.target.value,
                    })
                  }
                  sx={{ mb: 2 }}
                >
                  <MenuItem value="">Select Database Connection</MenuItem>
                  {databaseConnections.map((db) => (
                    <MenuItem key={db.name} value={db.name}>
                      {db.name}
                    </MenuItem>
                  ))}
                </TextField>
              </Grid>
              <Grid item xs={12} md={6}>
                <TextField
                  select
                  fullWidth
                  label="Date Parameter Required"
                  name="date_param_req"
                  value={reportConfigData.date_param_req}
                  onChange={(e) =>
                    setReportConfigData({
                      ...reportConfigData,
                      date_param_req: e.target.value,
                    })
                  }
                  sx={{ mb: 2 }}
                >
                  <MenuItem value="">Select Option</MenuItem>
                  <MenuItem value="Yes">Yes</MenuItem>
                  <MenuItem value="No">No</MenuItem>
                </TextField>
              </Grid>
            </Grid>

            <TextField
              fullWidth
              multiline
              rows={5}
              label="SQL String"
              name="sql_str"
              value={reportConfigData.sql_str}
              onChange={(e) =>
                setReportConfigData({
                  ...reportConfigData,
                  sql_str: e.target.value,
                })
              }
              sx={{ mb: 2 }}
              InputProps={{
                style: { fontFamily: "monospace" },
              }}
            />

            <TextField
              fullWidth
              multiline
              rows={3}
              label="Column String (html)"
              name="column_str"
              value={reportConfigData.column_str}
              onChange={(e) =>
                setReportConfigData({
                  ...reportConfigData,
                  column_str: e.target.value,
                })
              }
              sx={{ mb: 2 }}
            />

            <Grid container spacing={2}>
              <Grid item xs={12} md={6}>
                <TextField
                  fullWidth
                  multiline
                  rows={3}
                  label="Standard Parameter String (html)"
                  name="std_param_html"
                  value={reportConfigData.std_param_html}
                  onChange={(e) =>
                    setReportConfigData({
                      ...reportConfigData,
                      std_param_html: e.target.value,
                    })
                  }
                  sx={{ mb: 2 }}
                />
              </Grid>
              <Grid item xs={12} md={6}>
                <TextField
                  fullWidth
                  multiline
                  rows={3}
                  label="Adhoc Parameter String (html)"
                  name="adhoc_param_html"
                  value={reportConfigData.adhoc_param_html}
                  onChange={(e) =>
                    setReportConfigData({
                      ...reportConfigData,
                      adhoc_param_html: e.target.value,
                    })
                  }
                  sx={{ mb: 2 }}
                />
              </Grid>
            </Grid>
          </Box>
        </DialogContent>
        <DialogActions>
          <Button onClick={() => setReportConfigOpen(false)}>Cancel</Button>
          <Button variant="contained" onClick={handleReportConfigUpdate}>
            Update Configuration
          </Button>
        </DialogActions>
      </Dialog>
    </Box>
  );
};

export default ReportBuilderSQL;