const { Permission, Role, Menu, RolePermission, MenuPermission } = require('../models');
const responseFormat = require('../utils/response');
const { Op } = require('sequelize');

/**
 * 构建权限树形结构
 */
function buildPermissionTree(permissions, parentId = null) {
  const tree = [];
  
  for (const permission of permissions) {
    if (permission.parent_id === parentId) {
      const children = buildPermissionTree(permissions, permission.id);
      const node = {
        ...permission.toJSON(),
        children: children.length > 0 ? children : undefined
      };
      tree.push(node);
    }
  }
  
  return tree;
}

/**
 * 权限管理控制器
 */
class PermissionController {
  /**
   * 获取权限列表
   */
  async getPermissions(req, res) {
    try {
      const { 
        page = 1, 
        limit = 10, 
        module, 
        type, 
        status = 'active',
        keyword 
      } = req.query;

      const offset = (page - 1) * limit;
      const where = { status };

      // 模块筛选
      if (module) {
        where.module = module;
      }

      // 类型筛选
      if (type) {
        where.type = type;
      }

      // 关键词搜索
      if (keyword) {
        where[Op.or] = [
          { name: { [Op.like]: `%${keyword}%` } },
          { code: { [Op.like]: `%${keyword}%` } },
          { description: { [Op.like]: `%${keyword}%` } }
        ];
      }

      const { count, rows } = await Permission.findAndCountAll({
        where,
        include: [
          {
            model: Permission,
            as: 'parent',
            attributes: ['id', 'name', 'code']
          },
          {
            model: Permission,
            as: 'children',
            attributes: ['id', 'name', 'code', 'type']
          }
        ],
        order: [['sort_order', 'ASC'], ['id', 'ASC']],
        limit: parseInt(limit),
        offset: parseInt(offset)
      });

      res.json(responseFormat.success({
        permissions: rows,
        pagination: {
          total: count,
          page: parseInt(page),
          limit: parseInt(limit),
          pages: Math.ceil(count / limit)
        }
      }, '获取权限列表成功'));
    } catch (error) {
      console.error('获取权限列表失败:', error);
      res.status(500).json(responseFormat.error('获取权限列表失败'));
    }
  }

  /**
   * 获取权限树形结构
   */
  async getPermissionTree(req, res) {
    try {
      const { module, type } = req.query;
      const where = { status: 'active' };

      if (module) {
        where.module = module;
      }

      if (type) {
        where.type = type;
      }

      const permissions = await Permission.findAll({
        where,
        order: [['sort_order', 'ASC'], ['id', 'ASC']]
      });

      // 构建树形结构
      const tree = buildPermissionTree(permissions);

      res.json(responseFormat.success(tree, '获取权限树成功'));
    } catch (error) {
      console.error('获取权限树失败:', error);
      res.status(500).json(responseFormat.error('获取权限树失败'));
    }
  }

  /**
   * 获取单个权限详情
   */
  async getPermissionById(req, res) {
    try {
      const { id } = req.params;

      const permission = await Permission.findByPk(id, {
        include: [
          {
            model: Permission,
            as: 'parent',
            attributes: ['id', 'name', 'code']
          },
          {
            model: Permission,
            as: 'children',
            attributes: ['id', 'name', 'code', 'type']
          }
        ]
      });

      if (!permission) {
        return res.status(404).json(responseFormat.error('权限不存在'));
      }

      res.json(responseFormat.success(permission, '获取权限详情成功'));
    } catch (error) {
      console.error('获取权限详情失败:', error);
      res.status(500).json(responseFormat.error('获取权限详情失败'));
    }
  }

  /**
   * 创建权限
   */
  async createPermission(req, res) {
    try {
      const {
        name,
        code,
        description,
        module,
        type = 'operation',
        parent_id,
        sort_order = 0
      } = req.body;

      // 验证必填字段
      if (!name || !code || !module) {
        return res.status(400).json(responseFormat.error('权限名称、权限代码和所属模块为必填项'));
      }

      // 检查权限代码是否已存在
      const existingPermission = await Permission.findOne({ where: { code } });
      if (existingPermission) {
        return res.status(400).json(responseFormat.error('权限代码已存在'));
      }

      // 如果有父权限，验证父权限是否存在
      if (parent_id) {
        const parentPermission = await Permission.findByPk(parent_id);
        if (!parentPermission) {
          return res.status(400).json(responseFormat.error('父权限不存在'));
        }
      }

      const permission = await Permission.create({
        name,
        code,
        description,
        module,
        type,
        parent_id,
        sort_order,
        status: 'active'
      });

      res.status(201).json(responseFormat.created(permission, '创建权限成功'));
    } catch (error) {
      console.error('创建权限失败:', error);
      res.status(500).json(responseFormat.error('创建权限失败'));
    }
  }

  /**
   * 更新权限
   */
  async updatePermission(req, res) {
    try {
      const { id } = req.params;
      const {
        name,
        code,
        description,
        module,
        type,
        parent_id,
        sort_order,
        status
      } = req.body;

      const permission = await Permission.findByPk(id);
      if (!permission) {
        return res.status(404).json(responseFormat.error('权限不存在'));
      }

      // 如果修改了权限代码，检查是否与其他权限冲突
      if (code && code !== permission.code) {
        const existingPermission = await Permission.findOne({ 
          where: { 
            code,
            id: { [Op.ne]: id }
          } 
        });
        if (existingPermission) {
          return res.status(400).json(responseFormat.error('权限代码已存在'));
        }
      }

      // 如果有父权限，验证父权限是否存在且不是自己
      if (parent_id) {
        if (parent_id == id) {
          return res.status(400).json(responseFormat.error('不能将自己设为父权限'));
        }
        const parentPermission = await Permission.findByPk(parent_id);
        if (!parentPermission) {
          return res.status(400).json(responseFormat.error('父权限不存在'));
        }
      }

      await permission.update({
        name: name || permission.name,
        code: code || permission.code,
        description: description !== undefined ? description : permission.description,
        module: module || permission.module,
        type: type || permission.type,
        parent_id: parent_id !== undefined ? parent_id : permission.parent_id,
        sort_order: sort_order !== undefined ? sort_order : permission.sort_order,
        status: status || permission.status
      });

      res.json(responseFormat.success(permission, '更新权限成功'));
    } catch (error) {
      console.error('更新权限失败:', error);
      res.status(500).json(responseFormat.error('更新权限失败'));
    }
  }

  /**
   * 删除权限
   */
  async deletePermission(req, res) {
    try {
      const { id } = req.params;

      const permission = await Permission.findByPk(id);
      if (!permission) {
        return res.status(404).json(responseFormat.error('权限不存在'));
      }

      // 检查是否有子权限
      const childrenCount = await Permission.count({ where: { parent_id: id } });
      if (childrenCount > 0) {
        return res.status(400).json(responseFormat.error('该权限下还有子权限，无法删除'));
      }

      // 检查是否有角色在使用该权限
      const rolePermissionCount = await RolePermission.count({ where: { permission_id: id } });
      if (rolePermissionCount > 0) {
        return res.status(400).json(responseFormat.error('该权限正在被角色使用，无法删除'));
      }

      // 检查是否有菜单在使用该权限
      const menuPermissionCount = await MenuPermission.count({ where: { permission_id: id } });
      if (menuPermissionCount > 0) {
        return res.status(400).json(responseFormat.error('该权限正在被菜单使用，无法删除'));
      }

      await permission.destroy();

      res.json(responseFormat.success(null, '删除权限成功'));
    } catch (error) {
      console.error('删除权限失败:', error);
      res.status(500).json(responseFormat.error('删除权限失败'));
    }
  }

  /**
   * 获取角色权限
   */
  async getRolePermissions(req, res) {
    try {
      const { roleId } = req.params;

      const role = await Role.findByPk(roleId, {
        include: [
          {
            model: Permission,
            as: 'rolePermissions',
            through: {
              attributes: ['granted']
            }
          }
        ]
      });

      if (!role) {
        return res.status(404).json(responseFormat.error('角色不存在'));
      }

      res.json(responseFormat.success({
        role: {
          id: role.id,
          name: role.name,
          description: role.description
        },
        permissions: role.rolePermissions
      }, '获取角色权限成功'));
    } catch (error) {
      console.error('获取角色权限失败:', error);
      res.status(500).json(responseFormat.error('获取角色权限失败'));
    }
  }

  /**
   * 分配角色权限
   */
  async assignRolePermissions(req, res) {
    try {
      const { roleId } = req.params;
      const { permissionIds } = req.body;

      if (!Array.isArray(permissionIds)) {
        return res.status(400).json(responseFormat.error('权限ID列表格式错误'));
      }

      const role = await Role.findByPk(roleId);
      if (!role) {
        return res.status(404).json(responseFormat.error('角色不存在'));
      }

      // 删除现有的角色权限关联
      await RolePermission.destroy({ where: { role_id: roleId } });

      // 创建新的角色权限关联
      if (permissionIds.length > 0) {
        const rolePermissions = permissionIds.map(permissionId => ({
          role_id: roleId,
          permission_id: permissionId,
          granted: true
        }));

        await RolePermission.bulkCreate(rolePermissions);
      }

      res.json(responseFormat.success(null, '分配角色权限成功'));
    } catch (error) {
      console.error('分配角色权限失败:', error);
      res.status(500).json(responseFormat.error('分配角色权限失败'));
    }
  }

  /**
   * 获取模块列表
   */
  async getModules(req, res) {
    try {
      const modules = await Permission.findAll({
        attributes: ['module'],
        group: ['module'],
        order: [['module', 'ASC']]
      });

      const moduleList = modules.map(item => item.module);

      res.json(responseFormat.success(moduleList, '获取模块列表成功'));
    } catch (error) {
      console.error('获取模块列表失败:', error);
      res.status(500).json(responseFormat.error('获取模块列表失败'));
    }
  }

}

module.exports = new PermissionController();