import React from "react";
import { useForm } from "react-hook-form";
import { useNavigate } from "react-router-dom";
import { yupResolver } from "@hookform/resolvers/yup";
import * as yup from "yup";
import { AuthContext, tokenExpireError } from "Src/authContext";
import { GlobalContext } from "Context/Global";
import { getNonNullValue } from "Utils/utils";
import MkdSDK from "Utils/MkdSDK";
import { ModalSidebar } from "Components/ModalSidebar";
import { BiFilterAlt, BiSearch } from "react-icons/bi";
import { AiOutlineClose, AiOutlinePlus } from "react-icons/ai";
import { RiDeleteBin5Line } from "react-icons/ri";
import EditAdminCmsPage from "../Edit/EditAdminCmsPage";
import AddAdminCmsPage from "../Add/AddAdminCmsPage";
import AddButton from "Components/AddButton";
import SkeletonLoader from "Components/Skeleton/Skeleton";
import PaginationBar from "Components/PaginationBar";

let sdk = new MkdSDK();

const columns = [
  {
    header: "Page",
    accessor: "page",
    isSorted: false,
    isSortedDesc: false,
    mappingExist: false,
    mappings: {},
  },
  {
    header: "Identifier",
    accessor: "content_key",
    isSorted: false,
    isSortedDesc: false,
    mappingExist: false,
    mappings: {},
  },
  {
    header: "Content Type",
    accessor: "content_type",
    isSorted: false,
    isSortedDesc: false,
    mappingExist: false,
    mappings: {},
  },
  {
    header: "Action",
    accessor: "",
  },
];

const AdminCmsListPage = () => {
  const { dispatch } = React.useContext(AuthContext);
  const { dispatch: globalDispatch } = React.useContext(GlobalContext);
  const [query, setQuery] = React.useState("");
  const [data, setCurrentTableData] = React.useState([]);
  const [pageSize, setPageSize] = React.useState(10);
  const [pageCount, setPageCount] = React.useState(0);
  const [dataTotal, setDataTotal] = React.useState(0);
  const [currentPage, setPage] = React.useState(0);
  const [canPreviousPage, setCanPreviousPage] = React.useState(false);
  const [canNextPage, setCanNextPage] = React.useState(false);
  const [showAddSidebar, setShowAddSidebar] = React.useState(false);
  const [showEditSidebar, setShowEditSidebar] = React.useState(false);
  const [isLoading, setIsLoading] = React.useState(false);
  const [openFilter, setOpenFilter] = React.useState(false);
  const [showFilterOptions, setShowFilterOptions] = React.useState(false);
  const [selectedOptions, setSelectedOptions] = React.useState([]);
  const [filterConditions, setFilterConditions] = React.useState([]);
  const [searchValue, setSearchValue] = React.useState("");
  const [optionValue, setOptionValue] = React.useState("eq");
  const [activeEditId, setActiveEditId] = React.useState();
  const navigate = useNavigate();

  const schema = yup.object({
    page: yup.string(),
    key: yup.string(),
    type: yup.string(),
  });

  const selectType = [
    { key: "", value: "All" },
    { key: "text", value: "Text" },
    { key: "image", value: "Image" },
    { key: "number", value: "Number" },
  ];

  const {
    register,
    handleSubmit,
    setError,
    formState: { errors },
  } = useForm({
    resolver: yupResolver(schema),
  });

  function onSort(columnIndex) {
    console.log(columns[columnIndex]);
    if (columns[columnIndex].isSorted) {
      columns[columnIndex].isSortedDesc = !columns[columnIndex].isSortedDesc;
    } else {
      columns.map((i) => (i.isSorted = false));
      columns.map((i) => (i.isSortedDesc = false));
      columns[columnIndex].isSorted = true;
    }

    (async function () {
      await getData(0, pageSize);
    })();
  }

  function updatePageSize(limit) {
    (async function () {
      setPageSize(limit);
      await getData(0, limit);
    })();
  }

  function previousPage() {
    (async function () {
      await getData(currentPage - 1 > 0 ? currentPage - 1 : 0, pageSize);
    })();
  }

  function nextPage() {
    (async function () {
      await getData(
        currentPage + 1 <= pageCount ? currentPage + 1 : 0,
        pageSize
      );
    })();
  }

  const addFilterCondition = (option, selectedValue, inputValue) => {
    const input =
      selectedValue === "eq" && isNaN(inputValue)
        ? `"${inputValue}"`
        : inputValue;
    const condition = `${option},${selectedValue},${input}`;
    setFilterConditions((prevConditions) => {
      const newConditions = prevConditions.filter(
        (condition) => !condition.includes(option)
      );
      return [...newConditions, condition];
    });
    setSearchValue(inputValue);
  };

  async function getData(pageNum, limitNum, data) {
    // setIsLoading(true);
    try {
      sdk.setTable("cms");
      const result = await sdk.callRestAPI(
        {
          payload: { ...data },
          page: pageNum,
          limit: limitNum,
          // sortId: sortField.length ? sortField[0].accessor : "",
          // direction: sortField.length
          //   ? sortField[0].isSortedDesc
          //     ? "DESC"
          //     : "ASC"
          //   : "",
        },
        "PAGINATE"
      );

      const { list, total, limit, num_pages, page } = result;

      setCurrentTableData(list);
      setPageSize(limit);
      setPageCount(num_pages);
      setPage(page);
      setDataTotal(total);
      setCanPreviousPage(page > 1);
      setCanNextPage(page + 1 <= num_pages);
    } catch (error) {
      console.log("ERROR", error);
      tokenExpireError(dispatch, error.message);
    }
    // setIsLoading(false);
  }

  const onSubmit = (data) => {
    let page = getNonNullValue(data.page);
    let key = getNonNullValue(data.key);
    let type = getNonNullValue(data.type);
    let filter = { page, content_key: key, content_type: type };
    getData(0, 10, filter);
  };

  React.useEffect(() => {
    globalDispatch({
      type: "SETPATH",
      payload: {
        path: "cms",
      },
    });

    (async function () {
      await getData(1, pageSize);
    })();
  }, []);

  React.useEffect(() => {
    if (!showAddSidebar) {
      getData(1, pageSize, filterConditions);
    }
  }, [showAddSidebar]);

  return (
    <div className="px-8">
      <div className="flex items-center justify-between py-3">
        <form
          className="bg-brown-main-bg relative rounded"
          onSubmit={handleSubmit(onSubmit)}
        >
          <div className="flex items-center gap-4 text-gray-700">
            <div
              className="flex cursor-pointer items-center justify-between gap-3 rounded-md border border-[#0003] px-3 py-1"
              onClick={() => setOpenFilter(!openFilter)}
            >
              <BiFilterAlt />
              <span>Filters</span>
              {selectedOptions.length > 0 && (
                <span className="flex h-6 w-6 items-center justify-center rounded-full bg-gray-800 text-start  text-white">
                  {selectedOptions.length > 0 ? selectedOptions.length : null}
                </span>
              )}
            </div>
            <div className=" flex cursor-pointer items-center justify-between gap-3 rounded-md border border-[#0003] px-2 py-1 focus-within:border-gray-400">
              <BiSearch className="text-xl text-gray-200" />
              <input
                type="text"
                placeholder="search"
                className="border-none p-0 placeholder:text-left  focus:outline-none"
                style={{ boxShadow: "0 0 transparent" }}
                onInput={(e) =>
                  addFilterCondition("name", "cs", e.target?.value)
                }
              />
              <AiOutlineClose className="text-lg text-gray-200" />
            </div>
          </div>
          {openFilter && (
            <div className="top-fill filter-form-holder bg-brown-main-bg absolute  left-0 z-20 mt-4 min-w-[70%] rounded-md border border-[#0003] p-5 shadow-xl">
              {selectedOptions?.map((option, index) => (
                <div
                  key={index}
                  className="mb-2 flex w-full items-center justify-between gap-3 text-gray-600"
                >
                  <div className=" mb-3  w-1/3 rounded-md border border-black/60 px-3 py-2 leading-tight text-gray-700 outline-none">
                    {option}
                  </div>
                  <select
                    className="w-[30%] appearance-none border-none outline-0"
                    onChange={(e) => {
                      setOptionValue(e.target.value);
                    }}
                  >
                    <option value="eq" selected>
                      equals
                    </option>
                    <option value="cs">contains</option>
                    <option value="sw">start with</option>
                    <option value="ew">ends with</option>
                    <option value="lt">lower than</option>
                    <option value="le">lower or equal</option>
                    <option value="ge">greater or equal</option>
                    <option value="gt">greater than</option>
                    <option value="bt">between</option>
                    <option value="in">in</option>
                    <option value="is">is null</option>
                  </select>

                  <input
                    type="text"
                    placeholder="Enter value"
                    className=" mb-3 w-1/3 rounded-md border px-3 py-2 leading-tight text-gray-700 outline-none"
                    onChange={(e) =>
                      addFilterCondition(option, optionValue, e.target.value)
                    }
                  />

                  <RiDeleteBin5Line
                    className=" cursor-pointer text-xl"
                    onClick={() => {
                      setSelectedOptions((prevOptions) =>
                        prevOptions.filter((op) => op !== option)
                      );
                      setFilterConditions((prevConditions) => {
                        return prevConditions.filter(
                          (condition) => !condition.includes(option)
                        );
                      });
                    }}
                  />
                </div>
              ))}

              <div className="search-buttons relative flex items-center justify-between font-semibold">
                <div
                  // type="submit"
                  className="bg-brown-main-bg mr-2 flex w-auto cursor-pointer items-center gap-2 rounded px-4 py-2.5 font-medium leading-tight text-gray-600 transition duration-150 ease-in-out "
                  onClick={() => {
                    setShowFilterOptions(!showFilterOptions);
                  }}
                >
                  <AiOutlinePlus />
                  Add filter
                </div>

                {showFilterOptions && (
                  <div className="bg-brown-main-bg absolute top-11 z-10 px-5 py-3 text-gray-600 shadow-md">
                    <ul className="flex flex-col gap-2 text-gray-500">
                      {columns.slice(0, -1).map((column) => (
                        <li
                          key={column.header}
                          className={`${
                            selectedOptions.includes(column.header)
                              ? "cursor-not-allowed text-gray-400"
                              : "cursor-pointer"
                          }`}
                          onClick={() => {
                            if (!selectedOptions.includes(column.header)) {
                              setSelectedOptions((prev) => [
                                ...prev,
                                column.header,
                              ]);
                            }
                            setShowFilterOptions(false);
                          }}
                        >
                          {column.header}
                        </li>
                      ))}
                    </ul>
                  </div>
                )}
                {selectedOptions.length > 0 && (
                  <div
                    // type="reset"
                    onClick={() => {
                      setSelectedOptions([]);
                      setFilterConditions([]);
                    }}
                    className="inline-block cursor-pointer  rounded px-6  py-2.5 font-medium leading-tight text-gray-600  transition duration-150 ease-in-out"
                  >
                    Clear all filter
                  </div>
                )}
              </div>
            </div>
          )}
        </form>
        {/* <form className="p-5 bg-brown-main-bg shadow rounded mb-10" onSubmit={handleSubmit(onSubmit)}>
          <h4 className="md:text-xl font-medium text-[16px]">CMS Search</h4>
          <div className="filter-form-holder mt-10 flex flex-wrap">
            <div className="mb-4 w-full md:w-1/2 pr-2 pl-2">
              <label className="capitalize capitalize block text-gray-700 text-sm font-bold mb-2">Page</label>
              <input
                type="text"
                placeholder="Page"
                {...register("page")}
                className="shadow appearance-none border  rounded w-full py-2 px-3 text-gray-700 mb-3 leading-tight focus:outline-none focus:shadow-outline"
              />
              <p className="text-red-500 text-xs italic">{errors.page?.message}</p>
            </div>
            <div className="mb-4 w-full md:w-1/2 pr-2 pl-2">
              <label className="capitalize capitalize block text-gray-700 text-sm font-bold mb-2">Identifier</label>
              <input
                type="text"
                placeholder="Identifier"
                {...register("key")}
                className="shadow appearance-none border  rounded w-full py-2 px-3 text-gray-700 mb-3 leading-tight focus:outline-none focus:shadow-outline"
              />
              <p className="text-red-500 text-xs italic">{errors.key?.message}</p>
            </div>

            <div className="mb-4 w-full md:w-1/2 pr-2 pl-2">
              <label className="capitalize capitalize block text-gray-700 text-sm font-bold mb-2">Content Type</label>
              <select className="shadow border  rounded w-full py-2 px-3 text-gray-700 mb-3 leading-tight focus:outline-none focus:shadow-outline" {...register("type")}>
                {selectType.map((option) => (
                  <option name="type" value={option.key} key={option.key} defaultValue="">
                    {option.value}
                  </option>
                ))}
              </select>
              <p className="text-red-500 text-xs italic"></p>
            </div>
          </div>

          <button type="submit" className=" block ml-2 bg-blue-500 hover:bg-blue-700 text-white font-bold py-2 px-4 rounded focus:outline-none focus:shadow-outline">
            Search
          </button>
        </form> */}
        <AddButton onClick={() => setShowAddSidebar(true)} />
      </div>

      {isLoading ? (
        <SkeletonLoader />
      ) : (
        <div>
          <div className="overflow-x-auto  shadow ">
            <table className="min-w-full divide-y divide-[#1f1d1a]/10">
              <thead>
                <tr>
                  {columns.map((column, i) => (
                    <th
                      key={i}
                      scope="col"
                      className="px-6 py-3 text-left text-xs font-medium uppercase tracking-wider text-gray-500"
                      onClick={() => onSort(i)}
                    >
                      {column.header}
                      <span>
                        {column.isSorted
                          ? column.isSortedDesc
                            ? " ▼"
                            : " ▲"
                          : ""}
                      </span>
                    </th>
                  ))}
                </tr>
              </thead>
              <tbody className="font-iowan-regular divide-y divide-[#1f1d1a]/10">
                {data?.length === 0 && (
                  <div className="w-full py-3 text-center">No data</div>
                )}
                {data.map((row, i) => {
                  return (
                    <tr className="  md:h-[60px]" key={i}>
                      {columns.map((cell, index) => {
                        if (cell.accessor == "") {
                          return (
                            <td
                              key={index}
                              className="whitespace-nowrap px-6 py-4"
                            >
                              <button
                                className="cursor-pointer text-xs text-[#4F46E5]"
                                onClick={() => {
                                  setActiveEditId(row?.id);
                                  setShowEditSidebar(true);
                                  // navigate("/admin/edit-cms/" + row.id, {
                                  //   state: row,
                                  // });
                                }}
                              >
                                {" "}
                                Edit
                              </button>
                            </td>
                          );
                        }
                        if (cell.mapping) {
                          return (
                            <td
                              key={index}
                              className="whitespace-nowrap px-6 py-4"
                            >
                              {cell.mapping[row[cell.accessor]]}
                            </td>
                          );
                        }
                        return (
                          <td
                            key={index}
                            className="whitespace-nowrap px-6 py-4"
                          >
                            {row[cell.accessor]}
                          </td>
                        );
                      })}
                    </tr>
                  );
                })}
              </tbody>
            </table>
          </div>
        </div>
      )}
      <PaginationBar
        currentPage={currentPage}
        pageCount={pageCount}
        pageSize={pageSize}
        canPreviousPage={canPreviousPage}
        canNextPage={canNextPage}
        updatePageSize={updatePageSize}
        previousPage={previousPage}
        nextPage={nextPage}
      />
      <ModalSidebar
        isModalActive={showAddSidebar}
        closeModalFn={() => setShowAddSidebar(false)}
      >
        <AddAdminCmsPage setSidebar={setShowAddSidebar} />
      </ModalSidebar>
      <ModalSidebar
        isModalActive={showEditSidebar}
        closeModalFn={() => setShowEditSidebar(false)}
      >
        <EditAdminCmsPage
          activeId={activeEditId}
          setSidebar={setShowEditSidebar}
        />
      </ModalSidebar>
    </div>
  );
};

export default AdminCmsListPage;
