import { Leave } from "./LeaveModel.js";

// Mark leave
export const markLeave = async (req, res) => {
  try {
    const { date, time, location, reason, leaveType } = req.body;
    const userId = req.user._id;
    const userType = req.userType;

    // Parse the input date
    const [year, month, day] = date.split("/");
    const parsedDate = new Date(Date.UTC(year, month - 1, day));
    const today = new Date();
    today.setUTCHours(0, 0, 0, 0);

    // Check if the date in req.body is not today's date
    if (parsedDate.getTime() !== today.getTime()) {
      return res.status(400).json({
        success: false,
        message: `Leave can only be marked for today's date: ${
          today.toISOString().split("T")[0]
        }`,
      });
    }

    // Get the start and end of the day to check if the leave is already marked
    const startOfDay = new Date(parsedDate);
    const endOfDay = new Date(parsedDate);
    endOfDay.setUTCHours(23, 59, 59, 999);

    // Check if the leave record exists for today
    const existingLeave = await Leave.findOne({
      userId,
      userType,
      records: {
        $elemMatch: {
          date: { $gte: startOfDay, $lte: endOfDay },
        },
      },
    });

    if (existingLeave) {
      return res.status(400).json({
        success: false,
        message: "Leave for today is already marked.",
      });
    }

    // Check if leave record exists for the user
    let leave = await Leave.findOne({ userId, userType });

    if (!leave) {
      // Create a new leave record if it doesn't exist
      leave = new Leave({
        userId,
        userType,
        records: [],
      });
    }

    // Add the new leave record to the array
    leave.records.push({ date: startOfDay, time, location, reason, leaveType });
    await leave.save();

    res.status(201).json({
      success: true,
      message: "Leave marked successfully",
      record: { date: startOfDay, time, location, reason, leaveType },
    });
  } catch (error) {
    res.status(500).json({
      success: false,
      message: error.message || "Something went wrong",
    });
  }
};

// Helper function to check if two dates are on the same day
function isSameDay(date1, date2) {
  return (
    date1.getFullYear() === date2.getFullYear() &&
    date1.getMonth() === date2.getMonth() &&
    date1.getDate() === date2.getDate()
  );
}

// Get leave by user ID
export const getLeaveByUser = async (req, res) => {
  try {
    const userId = req.user._id;

    const leave = await Leave.findOne({
      userId,
    }).populate("userId", "name email");

    if (!leave) {
      return res.status(404).json({
        success: false,
        message: "No leave records found for this user.",
      });
    }

    res.status(200).json({
      success: true,
      leave,
    });
  } catch (error) {
    res.status(500).json({
      success: false,
      message: error.message || "Something went wrong",
    });
  }
};

// Admin route to get leave by user ID
export const AdmingetLeaveByUser = async (req, res) => {
  try {
    const { id } = req.params;
    const { page = 1, show = 10 } = req.query;
    const limit = parseInt(show);
    const skip = (page - 1) * limit;

    // Find leave records for the given user
    const leaveDoc = await Leave.findOne({
      userId: id,
    }).populate("userId", "name email");

    if (!leaveDoc) {
      return res.status(404).json({
        success: false,
        message: "No leave records found for this user.",
      });
    }

    // Pagination and slicing records
    const totalData = leaveDoc.records.length;
    const paginatedRecords = leaveDoc.records.slice(skip, skip + limit);

    res.status(200).json({
      success: true,
      user: leaveDoc.userId,
      leave: paginatedRecords,
      userType: leaveDoc.userType,
      total_data: totalData,
    });
  } catch (error) {
    res.status500().json({
      success: false,
      message: error.message || "Something went wrong",
    });
  }
};

export const getTodayLeave = async (req, res) => {
  try {
    // Step 1: Get today's date in UTC and set the time to 00:00:00.000
    const today = new Date();
    const todayStartUTC = new Date(Date.UTC(today.getUTCFullYear(), today.getUTCMonth(), today.getUTCDate(), 0, 0, 0));
    const tomorrowStartUTC = new Date(todayStartUTC);
    tomorrowStartUTC.setUTCDate(todayStartUTC.getUTCDate() + 1); // Start of the next day

    // Step 2: Parse query parameters
    const { page = 1, show = 10 } = req.query;
    const limit = parseInt(show, 10);
    const skip = (page - 1) * limit;

    // Step 3: Aggregate query to get today's leave records
    const leavesWithUserLookup = await Leave.aggregate([
      { $unwind: '$records' },
      {
        $match: {
          'records.date': {
            $gte: todayStartUTC,
            $lt: tomorrowStartUTC
          }
        }
      },
      {
        $lookup: {
          from: 'salescoordinators',
          localField: 'userId',
          foreignField: '_id',
          as: 'salesCoOrdinatorUser'
        }
      },
      {
        $lookup: {
          from: 'territorymanagers',
          localField: 'userId',
          foreignField: '_id',
          as: 'territoryManagerUser'
        }
      },
      {
        $addFields: {
          user: {
            $cond: {
              if: { $eq: ["$userType", "SalesCoOrdinator"] },
              then: { $arrayElemAt: ["$salesCoOrdinatorUser", 0] },
              else: { $arrayElemAt: ["$territoryManagerUser", 0] }
            }
          }
        }
      },
      {
        $project: {
          salesCoOrdinatorUser: 0,
          territoryManagerUser: 0
        }
      }
    ]);

    // Step 4: Calculate total data
    const totalData = leavesWithUserLookup.length;

    // Step 5: Implement pagination
    const paginatedLeaves = leavesWithUserLookup.slice(skip, skip + limit);

    // Step 6: Format the response
    const formattedLeaves = paginatedLeaves.map(record => ({
      user: record.user ? {
        id: record.user._id,
        name: record.user.name,
        email: record.user.email,
        mobileNumber: record.user.mobileNumber,
        userType: record.userType,
        uniqueId: record.user.uniqueId,
      } : null,
      date: record.records.date,
      time: record.records.time,
      location: record.records.location,
      reason: record.records.reason,
      leaveType: record.records.leaveType,
    }));

    // Send response
    res.status(200).json({
      success: true,
      total_data: totalData,
      leave: formattedLeaves,
      page: parseInt(page, 10),
      limit: limit,
    });
  } catch (error) {
    console.error("Error fetching today’s leave:", error);
    res.status(500).json({
      success: false,
      message: error.message || "Something went wrong",
    });
  }
};
