import { LoadingButton } from "@mui/lab";
import { Box, Button, Chip, Grid, MenuItem, Select, Switch, TextField } from "@mui/material";
import { useFormik } from "formik";
import React, { useMemo, useRef, useState } from "react";
import { useSelector } from "react-redux";
import * as Yup from "yup";
import EditIcon from '@mui/icons-material/Edit';

/* ----------------- Custom Imports ----------------- */
import PageHeader from "../../components/PageHeader";
import Table from "../../components/Table";
import ConfirmationModal from "../Modal/ConfirmationModal";
import CustomModal from "../Modal/Modal";
import { useStyles } from "./userStyles";

/* ----------------- Assets ----------------- */
import AddIcon from "@mui/icons-material/Add";
import {
  getUsers,
  deleteUserById,
  getRoles,
  getUserById,
  resendPasswordMailer,
  revokeAdminTransferAccess,
  transferMasterAdminAccess,
} from "../../services/users.service";

/* ----------------- Utils ----------------- */
import { format } from "date-fns";
import MultiSelect from "../../components/MultiSelect";
import { NOTIFICATION, NOT_AVAILABLE_TEXT } from "../../constants";
import { pushNotification } from "../../utils/notification";

/* ----------------- Validation Schema ----------------- */
const validationSchema = Yup.object().shape({
  userName: Yup.string().required("User Name is required"),
  email: Yup.string()
    .email("Invalid Email Address")
    .required("Email is required"),
  mobile: Yup.string()
    .matches(/^\d{10}$/, "Mobile Number must be exactly 10 digits")
    .required("Mobile Number is required"),
});

function Users() {
  const ref = useRef(null);
  const defaultFormData = useRef({
    userName: "",
    email: "q@gmail.com",
    mobile: "1234567890",
    isEditUser: false,
    lastName: "",
    userType: "",
    appointmentType: [],
    appointmentTypeObject: "",
  });

  const fieldRefs = {
    userName: useRef(null),
    email: useRef(null),
    mobile: useRef(null),
    lastName: useRef(null),
    userType: useRef(null),
    appointmentType: useRef(null),
  };

  const classes = useStyles();

  /* ----------------- State Variables ----------------- */
  const [showModal, setShowModal] = useState(false);
  const [showUserAccessModal, setShowUserAccessModal] = useState(false);
  const [isEditUser, setIsEditUser] = useState(false);
  const [deleteModal, setDeleteModal] = useState(false);
  const [masterAdminModal, setMasterAdminModal] = useState(false);
  const [buttonLoading, setButtonLoading] = useState(false);
  const [userId, setUserId] = useState();
  const [userTotalCount, setUserTotalCount] = useState(0);
  const [selectedCheckboxes, setSelectedCheckboxes] = useState({});
  const [checkboxError, setCheckboxError] = useState(false);
  const [roles, setRoles] = useState();
  const [isAdmin, setIsAdmin] = useState();

  const isBsAdmin = useSelector((state) => state?.login?.user?.isBsAdmin);

  /* ----------------- Get Users ----------------- */
  const getData = async (filters) => {
    const resp = await getUsers(filters);
    console.log(resp);
    console.log(resp?.data?.totalCount);
    setUserTotalCount(resp?.data?.totalCount);

    const role = await getRoles({ page: 0 });
    setRoles(role?.data);

    return { data: resp?.data?.records, rowCount: resp?.data?.totalCount };
  };

  const editUser = async (row) => {
    try {
      const userData = await getUserById(row?.original?.id);
      const formData = {
        userName: userData?.name,
        email: userData?.email,
        mobile: userData?.mobile,
        isEditUser: true,
      };
      // const updatedCheckboxes = roles.reduce(
      //   (acc, role) => ({
      //     ...acc,
      //     [role?.id]: userData?.roles.some(
      //       (roleData) => roleData?.id === role?.id
      //     ),
      //   }),
      //   {}
      // );

      // setSelectedCheckboxes(updatedCheckboxes);
      // formik.setValues(formData);
      // toggle();
      // setIsEditUser(true);
      // setUserId(row?.original?.id);
    } catch ({ resp }) {
      // eslint-disable-next-line no-console
      console.error(resp?.data?.message);
    }
  };

  const handleToggleButton = async (row) => {
    try {
      // Replace this with your actual API call to update user status
      // Example: await updateUserStatus(row.id, !row.isActive);
      
      // For now, just show a notification
      pushNotification(
        `${row.name}'s status has been ${row.isActive ? 'deactivated' : 'activated'}`, 
        NOTIFICATION.SUCCESS
      );
      
      // Refresh the table data
      ref.current.reFetchData();
    } catch (error) {
      console.error(error);
      pushNotification('Failed to update status', NOTIFICATION.ERROR);
    }
  };

  /* ----------------- Handle Submit ----------------- */
  const handleSubmit = async (values, formik) => {
    try {
      // if (!showUserAccessModal) {
      //   setShowUserAccessModal(true);
      //   return;
      // }

      // const hasSelectedCheckbox =
      //   Object.values(selectedCheckboxes).some(Boolean);
      // if (!hasSelectedCheckbox) {
      //   setCheckboxError(true);
      //   return;
      // }
      // setCheckboxError(false);

      // const combinedValues = {
      //   ...values,
      //   name: values.userName,
      //   roles: Object.entries(selectedCheckboxes)
      //     .filter(
      //       ([id, isChecked]) =>
      //         isChecked && id !== 'transferMasterAdminAccess' && id !== null
      //     )
      //     .map(([id]) => parseInt(id)),
      //   transferMasterAdminAccess:
      //     selectedCheckboxes.transferMasterAdminAccess || false,
      // };
      // delete combinedValues.userName;
      // delete combinedValues.confirmPassword;

      // let response = isEditUser
      //   ? await updateUserById(userId, combinedValues)
      //   : await addUser(combinedValues);

      // if (response.status === 200) {
      // pushNotification(response?.data?.message, NOTIFICATION.SUCCESS);
      pushNotification("Doctor added successfully", NOTIFICATION.SUCCESS);
      // ref.current.reFetchData();
      toggle();
      formik.resetForm();
      setSelectedCheckboxes({});
      // }
    } catch (error) {
      // eslint-disable-next-line no-console
      console.log(error);
    }
  };

  /* ----------------- Toggle Modal ----------------- */
  const toggle = () => {
    setIsEditUser(false);
    setShowUserAccessModal(false);
    setShowModal(!showModal);
  };

  /* ----------------- Handle Checkbox Change ----------------- */
  const handleCheckboxChange = (id, isChecked) => {
    setSelectedCheckboxes({ ...selectedCheckboxes, [id]: isChecked });
  };

  /* ----------------- Table Columns ----------------- */
  const columns = useMemo(
    () => [
      {
        size: 30,
        header: "S.no.",
        Cell: (props) => {
          const tableState = props?.table?.getState();
          const serialNumber = (
            props?.row?.index +
            1 +
            tableState?.pagination?.pageIndex * tableState?.pagination?.pageSize
          )
            ?.toString()
            ?.padStart(1, "0");
          return <span>{serialNumber}.</span>;
        },
        enableSorting: false,
      },
      {
        accessorFn: ({ name }) => name || NOT_AVAILABLE_TEXT,
        accessorKey: "name",
        header: "Doctor/Nurse Name",
        isBold: true,
      },
      {
        accessorFn: ({ userType }) => userType || NOT_AVAILABLE_TEXT,
        accessorKey: "userType",
        header: "User Type",
      },
      {
        accessorKey: "appointmentTypes",
        header: "Appointment Types",
        Cell: ({ row }) => {
          const appointmentTypes = row?.original?.appointmentTypes;
          
          // Convert to array if it's a string (comma-separated values)
          const typesArray = Array.isArray(appointmentTypes) && appointmentTypes.length > 0
            ? appointmentTypes 
            : typeof appointmentTypes === 'string' && appointmentTypes.trim() !== ''
              ? appointmentTypes.split(',').map(type => type.trim())
              : [];
          
          return (
            <Box sx={{ display: 'flex', flexWrap: 'wrap', gap: 0.5 }}>
              {typesArray.length > 0 ? (
                typesArray.map((type, index) => {
                  const label = typeof type === 'string' 
                    ? type 
                    : type?.name || type?.type || String(type);
                    
                  return (
                    <Chip
                      key={index}
                      label={label}
                      size="small"
                      variant="outlined"
                      sx={{ 
                        margin: '2px', 
                        borderRadius: '16px',
                        backgroundColor: '#f5f5f5',
                        '& .MuiChip-label': { fontSize: '0.75rem' }
                      }}
                    />
                  );
                })
              ) : (
                <Chip
                  label={NOT_AVAILABLE_TEXT}
                  size="small"
                  variant="outlined"
                  sx={{ 
                    margin: '2px', 
                    borderRadius: '16px',
                    backgroundColor: '#f0f0f0',
                    color: '#757575',
                    '& .MuiChip-label': { fontSize: '0.75rem' }
                  }}
                />
              )}
            </Box>
          );
        },
      },
      {
        accessorKey: "createdAt",
        Cell: ({ row }) => (
          <div className={classes.dateStyle}>
            {format(new Date(row?.original?.createdAt), "dd MMM, yyyy")}
          </div>
        ),
        header: "Added On",
      },
      {
        accessorFn: ({ email }) => email || NOT_AVAILABLE_TEXT,
        accessorKey: "status",
        header: "Status",
      },
      {
        size: 30,
        accessorKey: "actions",
        header: "Actions",
        enableSorting: false,
        Cell: ({ row }) => (
          <div>
            <Switch
              checked={row?.original?.isActive}
              onChange={() => handleToggleButton(row?.original)}
              inputProps={{ "aria-label": "Status toggle" }}
              color="primary"
            />
          </div>
        ),
      }
    ],
    []
  );

  const formik = useFormik({
    initialValues: defaultFormData.current,
    validationSchema,
    onSubmit: (values) => handleSubmit(values, formik),
  });

  /* ----------------- Handle Cancel ----------------- */
  const handleCancel = () => {
    toggle();
    formik.resetForm();
  };

  const deleteUserToggle = (row) => {
    setDeleteModal(!deleteModal);
    setSelectedUserData(row?.original);
  };

  const makeMasterAdminToggle = (row) => {
    setMasterAdminModal((prev) => !prev);
    setSelectedUserData(row?.original);
  };

  /* ----------------- Transfer Master Admin Access to User ----------------- */
  const handleTransferMasterAdminAccess = async () => {
    setButtonLoading(true);
    try {
      const response = await transferMasterAdminAccess(seletedUserData?.id);
      if (response.status === 200) {
        pushNotification(response?.data?.message, NOTIFICATION.SUCCESS);
        ref.current.resetPage(true);
        makeMasterAdminToggle();
      }
    } catch (error) {
      // eslint-disable-next-line no-console
      console.error(error?.response?.data?.message);
    } finally {
      ref.current.reFetchData();
      setButtonLoading(false);
    }
  };

  /* ----------------- Delete User ----------------- */
  const deleteUser = async () => {
    setButtonLoading(true);
    try {
      const response = await deleteUserById(seletedUserData?.id);
      if (response.status === 200) {
        pushNotification(response?.data?.message, NOTIFICATION.SUCCESS);
        ref.current.resetPage(true);
        deleteUserToggle();
      }
    } catch (error) {
      // eslint-disable-next-line no-console
      console.error(error?.response?.data?.message);
    } finally {
      ref.current.reFetchData();
      setButtonLoading(false);
    }
  };

  const handleuserAccessCancel = () => {
    setCheckboxError(false);
    setShowUserAccessModal(false);
  };

  const getRowStyle = (row) =>
    row?.original?.isAdmin ? { backgroundColor: "#E7F4EE !important" } : {};

  const handleSubmitClick = async () => {
    const formikErrors = await formik.validateForm();
    const errors = Object.keys(formikErrors);

    if (errors.length) {
      // Find the first invalid field and focus it
      const firstErrorField = errors[0];
      const firstErrorRef = fieldRefs[firstErrorField]?.current;

      if (firstErrorRef) {
        // Scroll to the first invalid field smoothly
        if (typeof firstErrorRef?.scrollIntoView === "function") {
          firstErrorRef?.scrollIntoView({
            behavior: "smooth",
            block: "center",
          });
        }

        // Focus the field after a slight delay (to ensure scrolling completes first)
        setTimeout(() => firstErrorRef.focus(), 300);
      }

      // Show error notification
      if (formik?.touched[firstErrorField])
        pushNotification(formikErrors[firstErrorField], NOTIFICATION.ERROR);
    }

    formik.handleSubmit();
  };

  return (
    <Box>
      <PageHeader
        pageTitle="Doctors/Nurses List"
        addButtonTitle="Add Doctor/Nurse"
        onAddButtonClick={toggle}
        addButtonIcon={<AddIcon />}
        addButtonDisabled={userTotalCount === 10}
        // permissionName={'CREATE_USERS'}
        infiniteDropdown
      />

      <Box className={classes.tableMainDiv}>
        <Table
          columns={columns}
          getData={getData}
          options={{ enableRowSelection: false }}
          showAction={true}
          hideShowPerPage={true}
          showSearchBox={true}
          ref={ref}
          searchText={"user"}
          getRowStyle={getRowStyle}
          actions={[
            {
              onClick: editUser,
              text: 'Edit',
              icon: (
                <EditIcon
                  // className={classes.tableActionIcons}
                  alt="Edit"
                />
              ),
              // permissionName: "CREATE_USERS",
            },
          ]}
        />
      </Box>

      {/* --------------- ADD User Modal --------------- */}
      {showModal && !showUserAccessModal && (
        <CustomModal
          isScrolling={true}
          noPadding
          showFooter
          footerLeftButtonTitle="Cancel"
          footerRightButtonTitle="Submit"
          onFooterLeftButtonClick={() => handleCancel()}
          onFooterRightButtonClick={() => handleSubmit()}
          title={isEditUser ? "Edit Doctor/Nurse" : "Add New Doctor/Nurse"}
          isTitleLeft={true}
          onClose={() => {
            formik.resetForm();
            setShowModal(false);
            setSelectedCheckboxes([]);
            setIsAdmin(false);
          }}
          modalBodyFunction={() => (
            <Box
              sx={{
                "& .MuiDialogContent-root": {
                  padding: "0px",
                },
              }}
            >
              <form className={classes.form}>
                <TextField
                  className={classes.userName}
                  color="secondary"
                  placeholder="First Name"
                  variant="outlined"
                  margin="normal"
                  fullWidth
                  inputProps={{
                    form: {
                      autocomplete: "off",
                    },
                  }}
                  name="userName"
                  value={formik.values.userName}
                  onChange={formik.handleChange}
                  onBlur={(e) => {
                    formik.setFieldValue("userName", e.target.value.trim());
                    formik.handleBlur(e);
                  }}
                  inputRef={fieldRefs.userName}
                  error={Boolean(
                    formik.errors.userName && formik.touched.userName
                  )}
                  helperText={
                    formik.errors.userName && formik.touched.userName ? (
                      <span className={classes.errorMessage}>
                        <i>{formik.errors.userName}</i>
                      </span>
                    ) : (
                      ""
                    )
                  }
                />
                <TextField
                  className={classes.lastName}
                  color="secondary"
                  placeholder="Last Name"
                  variant="outlined"
                  margin="normal"
                  fullWidth
                  inputProps={{
                    form: {
                      autocomplete: "off",
                    },
                  }}
                  name="lastName"
                  value={formik.values.lastName}
                  onChange={formik.handleChange}
                  onBlur={(e) => {
                    formik.setFieldValue("lastName", e.target.value.trim());
                    formik.handleBlur(e);
                  }}
                  inputRef={fieldRefs.lastName}
                  error={Boolean(
                    formik.errors.lastName && formik.touched.lastName
                  )}
                  helperText={
                    formik.errors.lastName && formik.touched.lastName ? (
                      <span className={classes.errorMessage}>
                        <i>{formik.errors.lastName}</i>
                      </span>
                    ) : (
                      ""
                    )
                  }
                />
                <Select
                  select
                  className={classes.perPageDropdown}
                  fullWidth
                  style={{ marginTop: "15px" }}
                  defaultValue={true}
                >
                  <MenuItem value={true}>Doctor</MenuItem>
                  <MenuItem value={false}>Nurse</MenuItem>
                </Select>

                <MultiSelect
                  apiCall={getRoles}
                  searchParams={{ additionalParam: "value" }}
                  formik={formik}
                  fieldValue="appointmentType"
                  fieldObjectValue="appointmentTypeObject"
                  getOptionLabel={(option) => option.name}
                  searchDebounceTime={500}
                  fieldName="appointmentType"
                  placeholderText="Select Appointment Types"
                  styleForSelectorParent={classes.multiSelectParent}
                  styleForSelector={classes.multiSelectChild}
                  inputRef={fieldRefs.appointmentType}
                />
                {/* <TextField
                  className={classes.emailField}
                  color="secondary"
                  placeholder="Enter Email ID"
                  variant="outlined"
                  margin="normal"
                  fullWidth
                  inputProps={{
                    form: {
                      autocomplete: 'off',
                    },
                  }}
                  name="email"
                  disabled={isEditUser}
                  value={formik.values.email}
                  onChange={formik.handleChange}
                  onBlur={formik.handleBlur}
                  inputRef={fieldRefs.email}
                  error={Boolean(formik.errors.email && formik.touched.email)}
                  helperText={
                    formik.errors.email && formik.touched.email ? (
                      <span className={classes.errorMessage}>
                        <i>{formik.errors.email}</i>
                      </span>
                    ) : (
                      ''
                    )
                  }
                />
                <TextField
                  className={classes.phoneNumberField}
                  color="secondary"
                  placeholder="Enter 10-Digits mobile number"
                  variant="outlined"
                  margin="normal"
                  fullWidth
                  name="mobile"
                  value={formik.values.mobile}
                  onChange={(e) => {
                    if (e.target.value.length <= 10) {
                      formik.handleChange(e);
                    }
                  }}
                  onBlur={formik.handleBlur}
                  inputRef={fieldRefs.mobile}
                  error={Boolean(formik.errors.mobile && formik.touched.mobile)}
                  helperText={
                    formik.errors.mobile && formik.touched.mobile ? (
                      <span className={classes.errorMessage}>
                        <i>{formik.errors.mobile}</i>
                      </span>
                    ) : (
                      ''
                    )
                  }
                  inputProps={{
                    type: 'string',
                    pattern: '[0-9]*',
                    autocomplete: 'password',
                    form: {
                      autocomplete: 'off',
                    },
                  }}
                /> */}
              </form>
            </Box>
          )}
        />
      )}

      {/* ----------- Choose User Access Modal----------- */}
      {showModal && showUserAccessModal && formik.isValid && (
        <CustomModal
          showBack={true}
          title="Choose User Access"
          isTitleLeftWithBackAndCloseButton={true}
          noPadding
          onFooterLeftButtonClick={() => handleuserAccessCancel()}
          onFooterRightButtonClick={() => formik.handleSubmit()}
          footerLeftButtonTitle="Cancel"
          footerRightButtonTitle="Add"
          showFooter
          onClose={() => {
            formik.resetForm();
            setSelectedCheckboxes([]);
            setShowModal(false);
            setIsAdmin(false);
          }}
          backFunctionCall={() => {
            setShowUserAccessModal(false);
          }}
          modalBodyFunction={() => <></>}
          footerContent={
            <Box>
              <Grid container>
                <Grid item lg={3}>
                  <LoadingButton
                    size="small"
                    variant="contained"
                    color="secondary"
                    onClick={() => setCheckboxError(false)} // Clear error on cancel
                  >
                    Cancel
                  </LoadingButton>
                </Grid>
                <Grid item lg={3}>
                  <LoadingButton
                    size="small"
                    variant="contained"
                    onClick={handleSubmit}
                  >
                    Add
                  </LoadingButton>
                </Grid>
              </Grid>
            </Box>
          }
        />
      )}

      {/* ----------- Delete User Modal ----------- */}
      {deleteModal && (
        <ConfirmationModal
          heading="Delete User"
          bodyContent="Deleting this user will delete all the data added to this user and it will not be recoverable once deleted."
          confirmationLine="Are you sure you want to permanently delete?"
          leftButtonText="Cancel"
          rightButtonText="Delete Anyway"
          onCancel={deleteUserToggle}
          onConfirm={deleteUser}
          buttonLoading={buttonLoading}
        />
      )}

      {/* ----------- Make User Master Admin Modal ----------- */}
      {masterAdminModal && (
        <ConfirmationModal
          heading="Make User Master Admin"
          bodyContent="The request for access privileges to Master Admin will be given to this user."
          confirmationLine="Are you sure you want to make this user Master Admin?"
          leftButtonText="Cancel"
          rightButtonText="Save"
          onCancel={makeMasterAdminToggle}
          onConfirm={handleTransferMasterAdminAccess}
          buttonLoading={buttonLoading}
        />
      )}

    </Box>
  );
}

export default Users;
