const bcrypt = require("bcryptjs");
const User = require("../models/User");

const saveSession = (req, res, message, user) => {
  req.session.user = {
    id: user._id,
    username: user.username
  };

  req.session.save((error) => {
    if (error) {
      return res.status(500).json({ message: "Session could not be saved" });
    }

    res.json({ message, user: req.session.user });
  });
};

const register = async (req, res) => {
  try {
    const { username, password } = req.body;

    if (!username || !password) {
      return res.status(400).json({ message: "Username and password are required" });
    }

    const existingUser = await User.findOne({ username: username.trim() });
    if (existingUser) {
      return res.status(400).json({ message: "Username already exists" });
    }

    const hashedPassword = await bcrypt.hash(password, 10);
    const user = await User.create({
      username: username.trim(),
      password: hashedPassword
    });

    saveSession(req, res, "Account created successfully", user);
  } catch (error) {
    res.status(500).json({ message: "Registration failed", error: error.message });
  }
};

const login = async (req, res) => {
  try {
    const { username, password } = req.body;

    if (!username || !password) {
      return res.status(400).json({ message: "Username and password are required" });
    }

    const user = await User.findOne({ username: username.trim() });
    if (!user) {
      return res.status(400).json({ message: "Invalid username or password" });
    }

    const isPasswordCorrect = await bcrypt.compare(password, user.password);
    if (!isPasswordCorrect) {
      return res.status(400).json({ message: "Invalid username or password" });
    }

    saveSession(req, res, "Login successful", user);
  } catch (error) {
    res.status(500).json({ message: "Login failed", error: error.message });
  }
};

const logout = (req, res) => {
  req.session.destroy((error) => {
    if (error) {
      return res.status(500).json({ message: "Logout failed" });
    }

    res.clearCookie("connect.sid");
    res.json({ message: "Logout successful" });
  });
};

const getSession = (req, res) => {
  if (!req.session || !req.session.user) {
    return res.status(401).json({ message: "No active session" });
  }

  res.json({ user: req.session.user });
};

const recoverPassword = async (req, res) => {
  try {
    const { username, newPassword } = req.body;

    if (!username || !newPassword) {
      return res.status(400).json({ message: "Username and new password are required" });
    }

    const user = await User.findOne({ username: username.trim() });
    if (!user) {
      return res.status(404).json({ message: "User account was not found" });
    }

    user.password = await bcrypt.hash(newPassword, 10);
    await user.save();

    res.json({ message: "Password changed successfully" });
  } catch (error) {
    res.status(500).json({ message: "Password recovery failed", error: error.message });
  }
};

module.exports = {
  register,
  login,
  logout,
  getSession,
  recoverPassword
};
