/**
 * WhatsApp Account Controller
 * API endpoints for WhatsApp Business account management
 *
 * @module WhatsApp
 * @prefix /api/v1/whatsapp/accounts
 */

import { Router, Request, Response, NextFunction } from 'express';
import {
  WhatsAppAccountService,
  CreateAccountDto,
  UpdateAccountDto,
  ServiceContext,
} from '../services';

const router = Router();
const accountService = new WhatsAppAccountService();

function getServiceContext(req: Request): ServiceContext {
  const tenantId = req.headers['x-tenant-id'] as string;
  const userId = (req as any).user?.id;
  return { tenantId, userId };
}

/**
 * GET /api/v1/whatsapp/accounts
 * List all WhatsApp accounts for the tenant
 */
router.get('/', async (req: Request, res: Response, next: NextFunction) => {
  try {
    const ctx = getServiceContext(req);
    if (!ctx.tenantId) {
      return res.status(400).json({ error: 'X-Tenant-Id header required' });
    }

    const { status, phoneNumber } = req.query;

    const accounts = await accountService.findAll(ctx, {
      status: status as any,
      phoneNumber: phoneNumber as string,
    });

    return res.json({
      success: true,
      data: accounts,
      count: accounts.length,
    });
  } catch (error) {
    return next(error);
  }
});

/**
 * GET /api/v1/whatsapp/accounts/active
 * Get active WhatsApp accounts
 */
router.get('/active', async (req: Request, res: Response, next: NextFunction) => {
  try {
    const ctx = getServiceContext(req);
    if (!ctx.tenantId) {
      return res.status(400).json({ error: 'X-Tenant-Id header required' });
    }

    const accounts = await accountService.findActive(ctx);
    return res.json({ success: true, data: accounts });
  } catch (error) {
    return next(error);
  }
});

/**
 * GET /api/v1/whatsapp/accounts/statistics
 * Get account statistics
 */
router.get('/statistics', async (req: Request, res: Response, next: NextFunction) => {
  try {
    const ctx = getServiceContext(req);
    if (!ctx.tenantId) {
      return res.status(400).json({ error: 'X-Tenant-Id header required' });
    }

    const stats = await accountService.getStatistics(ctx);
    return res.json({ success: true, data: stats });
  } catch (error) {
    return next(error);
  }
});

/**
 * GET /api/v1/whatsapp/accounts/:id
 * Get account by ID
 */
router.get('/:id', async (req: Request, res: Response, next: NextFunction) => {
  try {
    const ctx = getServiceContext(req);
    if (!ctx.tenantId) {
      return res.status(400).json({ error: 'X-Tenant-Id header required' });
    }

    const account = await accountService.findById(ctx, req.params.id);
    if (!account) {
      return res.status(404).json({ error: 'Account not found' });
    }

    return res.json({ success: true, data: account });
  } catch (error) {
    return next(error);
  }
});

/**
 * GET /api/v1/whatsapp/accounts/:id/can-send
 * Check if account can send messages
 */
router.get('/:id/can-send', async (req: Request, res: Response, next: NextFunction) => {
  try {
    const ctx = getServiceContext(req);
    if (!ctx.tenantId) {
      return res.status(400).json({ error: 'X-Tenant-Id header required' });
    }

    const canSend = await accountService.canSendMessage(ctx, req.params.id);
    return res.json({ success: true, data: { canSend } });
  } catch (error) {
    return next(error);
  }
});

/**
 * POST /api/v1/whatsapp/accounts
 * Create a new WhatsApp account
 */
router.post('/', async (req: Request, res: Response, next: NextFunction) => {
  try {
    const ctx = getServiceContext(req);
    if (!ctx.tenantId) {
      return res.status(400).json({ error: 'X-Tenant-Id header required' });
    }

    const data: CreateAccountDto = req.body;

    if (!data.name || !data.phoneNumber || !data.phoneNumberId || !data.businessAccountId) {
      return res.status(400).json({
        error: 'name, phoneNumber, phoneNumberId, and businessAccountId are required',
      });
    }

    const existing = await accountService.findByPhoneNumber(ctx, data.phoneNumber);
    if (existing) {
      return res.status(409).json({ error: 'Account with this phone number already exists' });
    }

    const account = await accountService.create(ctx, data);
    return res.status(201).json({ success: true, data: account });
  } catch (error) {
    return next(error);
  }
});

/**
 * PATCH /api/v1/whatsapp/accounts/:id
 * Update account
 */
router.patch('/:id', async (req: Request, res: Response, next: NextFunction) => {
  try {
    const ctx = getServiceContext(req);
    if (!ctx.tenantId) {
      return res.status(400).json({ error: 'X-Tenant-Id header required' });
    }

    const data: UpdateAccountDto = req.body;
    const account = await accountService.update(ctx, req.params.id, data);

    if (!account) {
      return res.status(404).json({ error: 'Account not found' });
    }

    return res.json({ success: true, data: account });
  } catch (error) {
    return next(error);
  }
});

/**
 * POST /api/v1/whatsapp/accounts/:id/activate
 * Activate account
 */
router.post('/:id/activate', async (req: Request, res: Response, next: NextFunction) => {
  try {
    const ctx = getServiceContext(req);
    if (!ctx.tenantId) {
      return res.status(400).json({ error: 'X-Tenant-Id header required' });
    }

    const account = await accountService.activate(ctx, req.params.id);
    if (!account) {
      return res.status(404).json({ error: 'Account not found' });
    }

    return res.json({ success: true, data: account });
  } catch (error) {
    return next(error);
  }
});

/**
 * POST /api/v1/whatsapp/accounts/:id/suspend
 * Suspend account
 */
router.post('/:id/suspend', async (req: Request, res: Response, next: NextFunction) => {
  try {
    const ctx = getServiceContext(req);
    if (!ctx.tenantId) {
      return res.status(400).json({ error: 'X-Tenant-Id header required' });
    }

    const account = await accountService.suspend(ctx, req.params.id);
    if (!account) {
      return res.status(404).json({ error: 'Account not found' });
    }

    return res.json({ success: true, data: account });
  } catch (error) {
    return next(error);
  }
});

/**
 * POST /api/v1/whatsapp/accounts/:id/disconnect
 * Disconnect account
 */
router.post('/:id/disconnect', async (req: Request, res: Response, next: NextFunction) => {
  try {
    const ctx = getServiceContext(req);
    if (!ctx.tenantId) {
      return res.status(400).json({ error: 'X-Tenant-Id header required' });
    }

    const account = await accountService.disconnect(ctx, req.params.id);
    if (!account) {
      return res.status(404).json({ error: 'Account not found' });
    }

    return res.json({ success: true, data: account });
  } catch (error) {
    return next(error);
  }
});

/**
 * POST /api/v1/whatsapp/accounts/:id/reset-limit
 * Reset daily message limit
 */
router.post('/:id/reset-limit', async (req: Request, res: Response, next: NextFunction) => {
  try {
    const ctx = getServiceContext(req);
    if (!ctx.tenantId) {
      return res.status(400).json({ error: 'X-Tenant-Id header required' });
    }

    await accountService.resetDailyLimit(ctx, req.params.id);
    return res.json({ success: true, message: 'Daily limit reset' });
  } catch (error) {
    return next(error);
  }
});

/**
 * DELETE /api/v1/whatsapp/accounts/:id
 * Delete account
 */
router.delete('/:id', async (req: Request, res: Response, next: NextFunction) => {
  try {
    const ctx = getServiceContext(req);
    if (!ctx.tenantId) {
      return res.status(400).json({ error: 'X-Tenant-Id header required' });
    }

    const deleted = await accountService.delete(ctx, req.params.id);
    if (!deleted) {
      return res.status(404).json({ error: 'Account not found' });
    }

    return res.json({ success: true, message: 'Account deleted' });
  } catch (error) {
    return next(error);
  }
});

export default router;
