// @desc    Save FCM device token
// @route   POST /api/user/device-token
export const saveDeviceToken = async (req: Request, res: Response): Promise<void> => {
  try {
    const { token, platform } = req.body as { token?: string; platform?: 'android' | 'ios' | 'web' };
    if (!token) {
      sendResponse(res, 400, 'Device token is required');
      return;
    }
    await userService.saveDeviceToken(req.user!.id, token, platform || 'android');
    sendResponse(res, 200, 'Device token saved successfully');
  } catch (error) { handleError(res, error); }
};

// @desc    Remove FCM device token
// @route   DELETE /api/user/device-token
export const removeDeviceToken = async (req: Request, res: Response): Promise<void> => {
  try {
    const { token } = req.body as { token?: string };
    if (!token) {
      sendResponse(res, 400, 'Device token is required');
      return;
    }
    await userService.removeDeviceToken(req.user!.id, token);
    sendResponse(res, 200, 'Device token removed successfully');
  } catch (error) { handleError(res, error); }
};

// @desc    Get all active user names
// @route   GET /api/user/active-users/names
export const getActiveUserNames = async (_req: Request, res: Response): Promise<void> => {
  try {
    const names = await userService.getActiveUserNames();
    sendResponse(res, 200, 'Active user names fetched', { count: names.length, names });
  } catch (error) { handleError(res, error); }
};
import { Request, Response } from 'express';
import * as userService from '../services/userService';
import * as certificateService from '../services/certificateService';
import { sendResponse, handleError } from '../utils/apiResponse';

// @desc    Get current logged-in user
// @route   GET /api/user/me
export const getMe = async (req: Request, res: Response): Promise<void> => {
  try {
    const user = await userService.getUserById(req.user!.id);
    sendResponse(res, 200, 'User profile fetched', { user });
  } catch (error) { handleError(res, error); }
};

// @desc    Update user profile
// @route   PUT /api/user/me
export const updateMe = async (req: Request, res: Response): Promise<void> => {
  try {
    const body = req.body as Record<string, unknown>;
    if (body.phone !== undefined) {
      const phone = String(body.phone).trim();
      // Accept only 10 digit numbers
      if (!/^\d{10}$/.test(phone)) {
        sendResponse(res, 400, 'Phone number must be exactly 10 digits');
        return;
      }
      // Reject all identical digits
      if (/^([0-9])\1{9}$/.test(phone)) {
        sendResponse(res, 400, 'Phone number cannot be all identical digits');
        return;
      }
      // Reject all zeros
      if (phone === '0000000000') {
        sendResponse(res, 400, 'Phone number cannot be all zeros');
        return;
      }
      // Reject common fake/test numbers
      const fakeNumbers = [
        '1234567890', '1111111111', '2222222222', '3333333333', '4444444444',
        '5555555555', '6666666666', '7777777777', '8888888888', '9999999999',
        '0123456789', '9876543210'
      ];
      if (fakeNumbers.includes(phone)) {
        sendResponse(res, 400, 'Phone number is not allowed');
        return;
      }
      // Reject sequential ascending/descending
      if ('0123456789'.includes(phone) || '9876543210'.includes(phone)) {
        sendResponse(res, 400, 'Phone number cannot be sequential');
        return;
      }
      body.phone = phone;
    }
    const user = await userService.updateUser(req.user!.id, body);
    sendResponse(res, 200, 'Profile updated', { user });
  } catch (error) { handleError(res, error); }
};

// @desc    Upload avatar
// @route   PUT /api/user/avatar
export const uploadAvatar = async (req: Request, res: Response): Promise<void> => {
  try {
    if (!req.file) { sendResponse(res, 400, 'No image uploaded'); return; }
    const user = await userService.uploadAvatar(req.user!.id, req.file.buffer, req.file.mimetype);
    sendResponse(res, 200, 'Avatar uploaded', { avatar: user?.avatar, user });
  } catch (error) { handleError(res, error); }
};

// @desc    Get user dashboard
// @route   GET /api/user/dashboard
export const getDashboard = async (req: Request, res: Response): Promise<void> => {
  try {
    const dashboard = await userService.getDashboard(req.user!.id);
    sendResponse(res, 200, 'Dashboard fetched', { ...dashboard });
  } catch (error) { handleError(res, error); }
};

// @desc    Get leaderboard
// @route   GET /api/user/leaderboard?period=today|weekly|monthly|all-time
export const getLeaderboard = async (req: Request, res: Response): Promise<void> => {
  try {
    const period = (req.query.period as string) || 'all-time';
    if (!['today', 'weekly', 'monthly', 'all-time'].includes(period)) {
      sendResponse(res, 400, 'Invalid period. Use today, weekly, monthly, or all-time');
      return;
    }
    const leaderboard = await userService.getLeaderboard(req.user!.id, period);
    sendResponse(res, 200, 'Leaderboard fetched', { leaderboard });
  } catch (error) { handleError(res, error); }
};

// @desc    Change password
// @route   PUT /api/user/change-password
export const changePassword = async (req: Request, res: Response): Promise<void> => {
  try {
    const { current_password, new_password } = req.body as { current_password?: string; new_password?: string };
    if (!current_password || !new_password) {
      sendResponse(res, 400, 'Please provide current_password and new_password');
      return;
    }
    await userService.changePassword(req.user!.id, current_password, new_password);
    sendResponse(res, 200, 'Password updated successfully');
  } catch (error) { handleError(res, error); }
};

// @desc    Delete own account
// @route   DELETE /api/user/me
export const deleteMe = async (req: Request, res: Response): Promise<void> => {
  try {
    await userService.deleteUser(req.user!.id);
    sendResponse(res, 200, 'Account deleted successfully');
  } catch (error) { handleError(res, error); }
};

// @desc    Submit certificate request
// @route   POST /api/user/certificates/requests
export const submitCertificateRequest = async (req: Request, res: Response): Promise<void> => {
  try {
    const { certificate_id, title, description, issuer, issue_date, completion_date } = req.body as {
      certificate_id?: string;
      title?: string;
      description?: string;
      issuer?: string;
      issue_date?: string;
      completion_date?: string;
    };

    if (!certificate_id || !title || !issuer || !issue_date) {
      sendResponse(res, 400, 'Please provide certificate_id, title, issuer and issue_date');
      return;
    }

    if (!req.file) {
      sendResponse(res, 400, 'Certificate file is required');
      return;
    }

    const request = await certificateService.submitCertificateRequest(
      req.user!.id,
      { certificate_id, title, description, issuer, issue_date, completion_date },
      { buffer: req.file.buffer, mimetype: req.file.mimetype },
    );

    sendResponse(res, 201, 'Certificate request submitted', { request });
  } catch (error) { handleError(res, error); }
};

// @desc    Get my certificate requests
// @route   GET /api/user/certificates/requests
export const getMyCertificateRequests = async (req: Request, res: Response): Promise<void> => {
  try {
    const status = req.query.status as 'pending' | 'approved' | 'rejected' | undefined;
    if (status && !['pending', 'approved', 'rejected'].includes(status)) {
      sendResponse(res, 400, 'Invalid status. Use pending, approved, or rejected');
      return;
    }
    const page = Math.max(1, parseInt(req.query.page as string) || 1);
    const limit = Math.min(50, Math.max(1, parseInt(req.query.limit as string) || 10));
    const { requests, pagination } = await certificateService.getMyCertificateRequests(req.user!.id, status, page, limit);
    sendResponse(res, 200, 'Certificate requests fetched', { count: requests.length, requests }, pagination);
  } catch (error) { handleError(res, error); }
};

// @desc    Get my approved certificates
// @route   GET /api/user/certificates
export const getMyCertificates = async (req: Request, res: Response): Promise<void> => {
  try {
    const page = Math.max(1, parseInt(req.query.page as string) || 1);
    const limit = Math.min(50, Math.max(1, parseInt(req.query.limit as string) || 10));
    const { certificates, pagination } = await certificateService.getMyApprovedCertificates(req.user!.id, page, limit);
    sendResponse(res, 200, 'Certificates fetched', { count: certificates.length, certificates }, pagination);
  } catch (error) { handleError(res, error); }
};
