import { useCallback, useEffect, useMemo, useState } from "react";
import { useQuery } from "@apollo/client/react";
import { connect } from "react-redux";
import { createStructuredSelector } from "reselect";
import { selectBodyshop, selectCurrentUser } from "../../redux/user/user.selectors";
import { selectDarkMode } from "../../redux/application/application.selectors.js";
import { INITIAL_TASKS, TASKS_CENTER_POLL_INTERVAL, useSocket } from "../../contexts/SocketIO/useSocket";
import { useIsEmployee } from "../../utils/useIsEmployee";
import TaskCenterComponent from "./task-center.component";
import { setModalContext } from "../../redux/modals/modals.actions";
import { QUERY_TASKS_NO_DUE_DATE_PAGINATED, QUERY_TASKS_WITH_DUE_DATES } from "../../graphql/tasks.queries";

const mapStateToProps = createStructuredSelector({
  bodyshop: selectBodyshop,
  currentUser: selectCurrentUser,
  isDarkMode: selectDarkMode
});

const mapDispatchToProps = (dispatch) => ({
  setTaskUpsertContext: (context) => dispatch(setModalContext({ context, modal: "taskUpsert" }))
});

const TaskCenterContainer = ({
  visible,
  onClose,
  bodyshop,
  currentUser,
  setTaskUpsertContext,
  incompleteTaskCount,
  isDarkMode
}) => {
  const [tasks, setTasks] = useState([]);
  const { isConnected } = useSocket();
  const isEmployee = useIsEmployee(bodyshop, currentUser);

  const assignedToId = useMemo(() => {
    const employee = bodyshop?.employees?.find((e) => e.user_email === currentUser?.email);
    return employee?.id || null;
  }, [bodyshop, currentUser]);

  // Query 1: Tasks with due dates
  const {
    data: dueDateData,
    loading: dueLoading,
    error: dueError
  } = useQuery(QUERY_TASKS_WITH_DUE_DATES, {
    variables: {
      bodyshop: bodyshop?.id,
      assigned_to: assignedToId,
      order: [{ due_date: "asc" }, { created_at: "desc" }]
    },
    skip: !bodyshop?.id || !assignedToId || !isEmployee || !currentUser?.email,
    fetchPolicy: "cache-and-network",
    pollInterval: isConnected ? 0 : TASKS_CENTER_POLL_INTERVAL
  });

  // Query 2: Tasks with no due date (paginated)
  const {
    data: noDueDateData,
    loading: noDueLoading,
    error: noDueError,
    fetchMore
  } = useQuery(QUERY_TASKS_NO_DUE_DATE_PAGINATED, {
    variables: {
      bodyshop: bodyshop?.id,
      assigned_to: assignedToId,
      order: [{ priority: "asc" }, { created_at: "desc" }],
      limit: INITIAL_TASKS, // Adjust this constant as needed
      offset: 0
    },
    skip: !bodyshop?.id || !assignedToId || !isEmployee || !currentUser?.email,
    fetchPolicy: "cache-and-network",
    pollInterval: isConnected ? 0 : TASKS_CENTER_POLL_INTERVAL
  });

  // Combine tasks from both queries
  useEffect(() => {
    const dueDateTasks = dueDateData?.tasks || [];
    const noDueDateTasks = noDueDateData?.tasks || [];
    setTasks([...dueDateTasks, ...noDueDateTasks]);
  }, [dueDateData, noDueDateData]);

  const noDueDateLength = noDueDateData?.tasks?.length || 0;
  const totalNoDueDate = noDueDateData?.tasks_aggregate?.aggregate?.count || 0;
  const hasMore = noDueDateLength < totalNoDueDate;

  // Handle pagination for no-due-date tasks
  const handleLoadMore = () => {
    fetchMore({
      variables: {
        offset: noDueDateData?.tasks?.length || 0
      },
      updateQuery: (prev, { fetchMoreResult }) => {
        if (!fetchMoreResult) return prev;
        return {
          ...prev,
          tasks: [...prev.tasks, ...fetchMoreResult.tasks],
          tasks_aggregate: fetchMoreResult.tasks_aggregate
        };
      }
    });
  };

  const handleTaskClick = useCallback(
    (id) => {
      const task = tasks.find((t) => t.id === id);
      if (task) {
        setTaskUpsertContext({
          context: {
            existingTask: task
          }
        });
      }
    },
    [tasks, setTaskUpsertContext]
  );

  const createNewTask = () => {
    setTaskUpsertContext({ actions: {}, context: {} });
  };

  return (
    <TaskCenterComponent
      visible={visible}
      onClose={onClose}
      tasks={tasks}
      loading={dueLoading || noDueLoading}
      error={dueError || noDueError}
      onTaskClick={handleTaskClick}
      onLoadMore={handleLoadMore}
      hasMore={hasMore}
      createNewTask={createNewTask}
      incompleteTaskCount={incompleteTaskCount}
      isDarkMode={isDarkMode}
    />
  );
};

export default connect(mapStateToProps, mapDispatchToProps)(TaskCenterContainer);
