// 시스템 관리 컨트롤러
const { getDb } = require('../dbPool');
const bcrypt = require('bcryptjs');
const { ApiError, asyncHandler, handleDatabaseError } = require('../utils/errorHandler');
const { validateSchema, schemas } = require('../utils/validator');

/**
 * 시스템 상태 확인
 */
exports.getSystemStatus = asyncHandler(async (req, res) => {
  try {
    const db = await getDb();
    
    // 데이터베이스 연결 상태 확인
    const [dbStatus] = await db.query('SELECT 1 as status');
    
    // 시스템 상태 정보
    const systemStatus = {
      server: 'online',
      database: dbStatus.length > 0 ? 'online' : 'offline'
    };
    
    res.health('healthy', systemStatus);
    
  } catch (error) {
    handleDatabaseError(error, '시스템 상태 확인');
  }
});

/**
 * 데이터베이스 상태 확인
 */
exports.getDatabaseStatus = asyncHandler(async (req, res) => {
  try {
    const db = await getDb();
    
    // 데이터베이스 연결 수 확인
    const [connections] = await db.query('SHOW STATUS LIKE "Threads_connected"');
    const [maxConnections] = await db.query('SHOW VARIABLES LIKE "max_connections"');
    
    // 데이터베이스 크기 확인
    const [dbSize] = await db.query(`
      SELECT 
        ROUND(SUM(data_length + index_length) / 1024 / 1024, 2) AS size_mb
      FROM information_schema.tables 
      WHERE table_schema = DATABASE()
    `);
    
    const dbStatus = {
      status: 'online',
      connections: parseInt(connections[0]?.Value || 0),
      max_connections: parseInt(maxConnections[0]?.Value || 0),
      size_mb: dbSize[0]?.size_mb || 0
    };
    
    res.success(dbStatus, '데이터베이스 상태 조회 성공');
    
  } catch (error) {
    handleDatabaseError(error, '데이터베이스 상태 확인');
  }
});

/**
 * 시스템 알림 조회
 */
exports.getSystemAlerts = async (req, res) => {
  try {
    const db = await getDb();
    
    // 최근 실패한 로그인 시도
    const [failedLogins] = await db.query(`
      SELECT COUNT(*) as count 
      FROM login_logs 
      WHERE login_status = 'failed' 
      AND login_time > DATE_SUB(NOW(), INTERVAL 1 HOUR)
    `);
    
    // 비활성 사용자 수
    const [inactiveusers] = await db.query(`
      SELECT COUNT(*) as count 
      FROM users 
      WHERE is_active = 0
    `);
    
    const alerts = [];
    
    if (failedLogins[0]?.count > 5) {
      alerts.push({
        type: 'security',
        level: 'warning',
        message: `최근 1시간 동안 ${failedLogins[0].count}회의 로그인 실패가 발생했습니다.`,
        timestamp: new Date().toISOString()
      });
    }
    
    if (inactiveusers[0]?.count > 0) {
      alerts.push({
        type: 'user',
        level: 'info',
        message: `${inactiveusers[0].count}명의 비활성 사용자가 있습니다.`,
        timestamp: new Date().toISOString()
      });
    }
    
    res.json({
      success: true,
      alerts: alerts
    });
    
  } catch (error) {
    console.error('시스템 알림 조회 오류:', error);
    res.status(500).json({
      success: false,
      error: '시스템 알림을 조회할 수 없습니다.'
    });
  }
};

/**
 * 최근 시스템 활동 조회
 */
exports.getRecentActivities = async (req, res) => {
  try {
    const db = await getDb();
    
    // 최근 로그인 활동
    const [loginActivities] = await db.query(`
      SELECT 
        ll.login_time as created_at,
        u.name as user_name,
        ll.login_status,
        ll.ip_address,
        'login' as activity_type
      FROM login_logs ll
      LEFT JOIN users u ON ll.user_id = u.user_id
      ORDER BY ll.login_time DESC
      LIMIT 10
    `);
    
    // 비밀번호 변경 활동
    const [passwordActivities] = await db.query(`
      SELECT 
        pcl.changed_at as created_at,
        u.name as user_name,
        pcl.change_type,
        'password_change' as activity_type
      FROM password_change_logs pcl
      LEFT JOIN users u ON pcl.user_id = u.user_id
      ORDER BY pcl.changed_at DESC
      LIMIT 5
    `);
    
    // 활동 통합 및 정렬
    const activities = [
      ...loginActivities.map(activity => ({
        type: activity.login_status === 'success' ? 'login' : 'login_failed',
        title: activity.login_status === 'success' 
          ? `${activity.user_name || '알 수 없는 사용자'} 로그인` 
          : `로그인 실패 (${activity.ip_address})`,
        description: activity.login_status === 'success' 
          ? `IP: ${activity.ip_address}` 
          : `사용자: ${activity.user_name || '알 수 없음'}`,
        created_at: activity.created_at
      })),
      ...passwordActivities.map(activity => ({
        type: 'password_change',
        title: `${activity.user_name || '알 수 없는 사용자'} 비밀번호 변경`,
        description: `변경 유형: ${activity.change_type}`,
        created_at: activity.created_at
      }))
    ];
    
    // 시간순 정렬
    activities.sort((a, b) => new Date(b.created_at) - new Date(a.created_at));
    
    res.json({
      success: true,
      data: activities.slice(0, 15)
    });
    
  } catch (error) {
    console.error('최근 활동 조회 오류:', error);
    res.status(500).json({
      success: false,
      error: '최근 활동을 조회할 수 없습니다.'
    });
  }
};

/**
 * 사용자 통계 조회
 */
exports.getUserStats = async (req, res) => {
  try {
    const db = await getDb();
    
    // 전체 사용자 수
    const [totalusers] = await db.query('SELECT COUNT(*) as count FROM users');
    
    // 활성 사용자 수
    const [activeusers] = await db.query('SELECT COUNT(*) as count FROM users WHERE is_active = 1');
    
    // 최근 24시간 로그인 사용자 수
    const [recentLogins] = await db.query(`
      SELECT COUNT(DISTINCT user_id) as count 
      FROM login_logs 
      WHERE login_status = 'success' 
      AND login_time > DATE_SUB(NOW(), INTERVAL 24 HOUR)
    `);
    
    // 권한별 사용자 수
    const [roleStats] = await db.query(`
      SELECT role, COUNT(*) as count 
      FROM users 
      WHERE is_active = 1
      GROUP BY role
    `);
    
    res.json({
      success: true,
      data: {
        total: totalusers[0]?.count || 0,
        active: activeusers[0]?.count || 0,
        recent_logins: recentLogins[0]?.count || 0,
        by_role: roleStats
      }
    });
    
  } catch (error) {
    console.error('사용자 통계 조회 오류:', error);
    res.status(500).json({
      success: false,
      error: '사용자 통계를 조회할 수 없습니다.'
    });
  }
};

/**
 * 모든 사용자 목록 조회 (시스템 관리자용)
 */
exports.getAllUsers = asyncHandler(async (req, res) => {
  try {
    const db = await getDb();
    
    const [users] = await db.query(`
      SELECT
        user_id,
        username,
        name,
        email,
        role,
        access_level,
        is_active,
        last_login_at,
        failed_login_attempts,
        locked_until,
        created_at,
        updated_at
      FROM users
      ORDER BY created_at DESC
    `);
    
    res.list(users, '사용자 목록 조회 성공');
    
  } catch (error) {
    handleDatabaseError(error, '사용자 목록 조회');
  }
});

/**
 * 사용자 생성
 */
exports.createUser = asyncHandler(async (req, res) => {
  const { username, password, name, email, role, access_level } = req.body;

  // 스키마 기반 유효성 검사
  validateSchema(req.body, schemas.createUser);

  try {
    const db = await getDb();

    // 사용자명 중복 확인
    const [existing] = await db.query('SELECT user_id FROM users WHERE username = ?', [username]);
    if (existing.length > 0) {
      throw new ApiError('이미 존재하는 사용자명입니다.', 409);
    }

    // 이메일 중복 확인 (이메일이 제공된 경우)
    if (email) {
      const [existingEmail] = await db.query('SELECT user_id FROM users WHERE email = ?', [email]);
      if (existingEmail.length > 0) {
        throw new ApiError('이미 사용 중인 이메일입니다.', 409);
      }
    }

    // 비밀번호 해시화
    const hashedPassword = await bcrypt.hash(password, 10);

    // 사용자 생성
    const [result] = await db.query(`
      INSERT INTO users (username, password, name, email, role, access_level, is_active, created_at, password_changed_at)
      VALUES (?, ?, ?, ?, ?, ?, 1, NOW(), NOW())
    `, [username, hashedPassword, name, email || null, role, access_level || role]);
    
    // 비밀번호 변경 로그 기록
    await db.query(`
      INSERT INTO password_change_logs (user_id, changed_by_user_id, changed_at, change_type) 
      VALUES (?, ?, NOW(), 'initial')
    `, [result.insertId, req.user.user_id]);
    
    res.created({ user_id: result.insertId }, '사용자가 성공적으로 생성되었습니다.');
    
  } catch (error) {
    handleDatabaseError(error, '사용자 생성');
  }
});

/**
 * 사용자 수정
 */
exports.updateUser = async (req, res) => {
  try {
    const { id } = req.params;
    const { name, email, role, access_level, is_active } = req.body;
    const db = await getDb();

    // 사용자 존재 확인
    const [user] = await db.query('SELECT user_id FROM users WHERE user_id = ?', [id]);
    if (user.length === 0) {
      return res.status(404).json({
        success: false,
        error: '해당 사용자를 찾을 수 없습니다.'
      });
    }

    // 이메일 중복 확인 (다른 사용자가 사용 중인지)
    if (email) {
      const [existingEmail] = await db.query(
        'SELECT user_id FROM users WHERE email = ? AND user_id != ?',
        [email, id]
      );
      if (existingEmail.length > 0) {
        return res.status(409).json({
          success: false,
          error: '이미 사용 중인 이메일입니다.'
        });
      }
    }

    // 사용자 정보 업데이트
    await db.query(`
      UPDATE users
      SET name = ?, email = ?, role = ?, access_level = ?, is_active = ?, updated_at = NOW()
      WHERE user_id = ?
    `, [name, email || null, role, access_level || role, is_active ? 1 : 0, id]);
    
    res.json({
      success: true,
      message: '사용자 정보가 성공적으로 업데이트되었습니다.'
    });
    
  } catch (error) {
    console.error('사용자 수정 오류:', error);
    res.status(500).json({
      success: false,
      error: '사용자 수정 중 오류가 발생했습니다.'
    });
  }
};

/**
 * 사용자 삭제
 */
exports.deleteUser = async (req, res) => {
  try {
    const { id } = req.params;
    const db = await getDb();
    
    // 자기 자신 삭제 방지
    if (parseInt(id) === req.user.user_id) {
      return res.status(400).json({
        success: false,
        error: '자기 자신은 삭제할 수 없습니다.'
      });
    }
    
    // 사용자 존재 확인
    const [user] = await db.query('SELECT user_id, username FROM users WHERE user_id = ?', [id]);
    if (user.length === 0) {
      return res.status(404).json({
        success: false,
        error: '해당 사용자를 찾을 수 없습니다.'
      });
    }
    
    // 사용자 삭제 (관련 로그는 유지)
    await db.query('DELETE FROM users WHERE user_id = ?', [id]);
    
    res.json({
      success: true,
      message: `사용자 '${user[0].username}'가 성공적으로 삭제되었습니다.`
    });
    
  } catch (error) {
    console.error('사용자 삭제 오류:', error);
    res.status(500).json({
      success: false,
      error: '사용자 삭제 중 오류가 발생했습니다.'
    });
  }
};

/**
 * 사용자 비밀번호 재설정
 */
exports.resetUserPassword = async (req, res) => {
  try {
    const { id } = req.params;
    const { new_password } = req.body;
    const db = await getDb();
    
    if (!new_password || new_password.length < 6) {
      return res.status(400).json({
        success: false,
        error: '비밀번호는 최소 6자 이상이어야 합니다.'
      });
    }
    
    // 사용자 존재 확인
    const [user] = await db.query('SELECT user_id, username FROM users WHERE user_id = ?', [id]);
    if (user.length === 0) {
      return res.status(404).json({
        success: false,
        error: '해당 사용자를 찾을 수 없습니다.'
      });
    }
    
    // 비밀번호 해시화
    const hashedPassword = await bcrypt.hash(new_password, 10);
    
    // 비밀번호 업데이트
    await db.query(`
      UPDATE users 
      SET password = ?, password_changed_at = NOW(), failed_login_attempts = 0, locked_until = NULL
      WHERE user_id = ?
    `, [hashedPassword, id]);
    
    // 비밀번호 변경 로그 기록
    await db.query(`
      INSERT INTO password_change_logs (user_id, changed_by_user_id, changed_at, change_type) 
      VALUES (?, ?, NOW(), 'admin')
    `, [id, req.user.user_id]);
    
    res.json({
      success: true,
      message: `사용자 '${user[0].username}'의 비밀번호가 재설정되었습니다.`
    });
    
  } catch (error) {
    console.error('비밀번호 재설정 오류:', error);
    res.status(500).json({
      success: false,
      error: '비밀번호 재설정 중 오류가 발생했습니다.'
    });
  }
};
