import response from "../../response.js";
import models from "../../models/index.js";

export const getStdExercises = async (req, res) => {
  try {
    const stdExercise = await models.StdExercise.findAll();
    response(200, stdExercise, "Success", res);
  } catch (error) {
    console.log(error);
    response(500, null, "Error retrieving student exercise data!", res);
  }
};

export const getStdExerciseById = async (req, res) => {
  try {
    const { id } = req.params;
    const stdExercise = await models.StdExercise.findByPk(id);

    if (!stdExercise) {
      return response(404, null, "Student exercise data not found", res);
    }

    response(200, stdExercise, "Success", res);
  } catch (error) {
    console.log(error);
    res.status(500).json({ message: "Internal Server Error" });
  }
};

export const stdAnswerExercise = async (req, res, next) => {
  try {
    const { answers } = req.body;

    if (!Array.isArray(answers) || answers.length === 0) {
      return response(400, null, "Answers array is required", res);
    }

    for (const answer of answers) {
      const { ID_STUDENT_LEARNING, ID_ADMIN_EXERCISE, ANSWER_STUDENT } = answer;

      if (!ID_STUDENT_LEARNING) {
        return response(400, null, "Id student learning is required", res);
      }

      const existingStdLearning = await models.StdLearning.findByPk(
        ID_STUDENT_LEARNING
      );
      if (!existingStdLearning) {
        return response(404, null, "Id student learning not found", res);
      }

      if (!ID_ADMIN_EXERCISE) {
        return response(400, null, "Id exercise is required", res);
      }

      const exercise = await models.Exercise.findOne({
        where: {
          ID_ADMIN_EXERCISE: ID_ADMIN_EXERCISE,
          ID_LEVEL: existingStdLearning.ID_LEVEL,
        },
      });
      if (!exercise) {
        return response(404, null, "Exercise not found in this level", res);
      }

      if (!ANSWER_STUDENT) {
        return response(400, null, "Answer is required", res);
      }

      const existingStdExercise = await models.StdExercise.findOne({
        where: {
          ID_STUDENT_LEARNING: ID_STUDENT_LEARNING,
          ID_ADMIN_EXERCISE: ID_ADMIN_EXERCISE,
        },
      });

      if (existingStdExercise) {
        existingStdExercise.ANSWER_STUDENT = ANSWER_STUDENT;
        await existingStdExercise.save();
      } else {
        await models.StdExercise.create({
          ID_STUDENT_LEARNING,
          ID_ADMIN_EXERCISE,
          ANSWER_STUDENT,
        });
      }
    }

    req.params.id = answers[0].ID_STUDENT_LEARNING;
    next();
  } catch (error) {
    console.log(error);
    return response(
      500,
      null,
      "Error creating or updating student exercise data!",
      res
    );
  }
};

export const getStudentAnswersByStdLearningId = async (req, res) => {
  try {
    const { id } = req.params;

    const stdLearning = await models.StdLearning.findByPk(id, {
      include: [
        {
          model: models.StdExercise,
          as: "stdExercises",
          include: [
            {
              model: models.Exercise,
              as: "stdExerciseExercises",
              attributes: ["ID_ADMIN_EXERCISE", "TITLE", "QUESTION", "QUESTION_TYPE"],
            },
          ],
          attributes: [
            "ID_STUDENT_EXERCISE",
            "ANSWER_STUDENT",
            "IS_CORRECT",
            "RESULT_SCORE_STUDENT",
            "TIME_STUDENT_EXC",
          ],
        },
      ],
      attributes: ["ID_STUDENT_LEARNING", "ID_LEVEL", "SCORE", "IS_PASS"],
    });

    if (!stdLearning) {
      return res.status(404).json({
        message: "Student learning data not found",
      });
    }

    const sortedExercises = stdLearning.stdExercises.sort((a, b) => {
      const titleA = a.stdExerciseExercises.TITLE.toUpperCase();
      const titleB = b.stdExerciseExercises.TITLE.toUpperCase();

      if (titleA < titleB) return -1;
      if (titleA > titleB) return 1;
      return 0;
    });

    const mappedExercises = sortedExercises.map((exercise) => ({
      ...exercise.toJSON(),
      exerciseDetails: exercise.stdExerciseExercises,
      stdExerciseExercises: undefined,
    }));

    return res.status(200).json({
      message: "Student learning exercises retrieved successfully",
      data: {
        ...stdLearning.toJSON(),
        stdExercises: mappedExercises,
      },
    });
  } catch (error) {
    console.error(error);
    return res.status(500).json({
      message: "Error retrieving student learning exercises",
    });
  }
};
