import { emailService } from '../../services/email.service';
import { siteSettingsService } from '../settings/settings.service';
import { env } from '../../config/env';
import { logger } from '../../utils/logger';

export const ticketEmailService = {
  /** Send ticket confirmation email with QR code */
  async sendTicketConfirmation(params: {
    holderEmail: string;
    holderName?: string | null;
    ticketCode: string;
    token: string;
    eventTitle: string;
    eventDate: Date;
    eventStartTime: string;
    eventEndTime: string;
    eventSlug: string;
    venueName?: string | null;
    venueAddress?: string | null;
    tierName: string;
    eventFormat?: string;
  }): Promise<void> {
    try {
      const orgName = await this.getOrgName();
      const baseUrl = env.ADMIN_URL || 'http://localhost:3000';
      const checkinUrl = `${baseUrl}/event/${params.eventSlug}/checkin?token=${encodeURIComponent(params.token)}`;
      const qrImageUrl = `${env.API_URL}/api/qr?text=${encodeURIComponent(checkinUrl)}&size=300`;
      const eventUrl = `${baseUrl}/event/${params.eventSlug}`;
      const ticketUrl = `${baseUrl}/event/${params.eventSlug}/ticket/${params.ticketCode}`;

      const hasOnlineAccess = params.eventFormat === 'ONLINE' || params.eventFormat === 'HYBRID';
      const vars: Record<string, string> = {
        RECIPIENT_NAME: params.holderName || 'Guest',
        EVENT_TITLE: params.eventTitle,
        EVENT_DATE: params.eventDate.toLocaleDateString('en-CA', {
          weekday: 'long', year: 'numeric', month: 'long', day: 'numeric',
        }),
        EVENT_TIME: `${params.eventStartTime} – ${params.eventEndTime}`,
        VENUE_NAME: params.venueName || '',
        VENUE_ADDRESS: params.venueAddress || '',
        TICKET_TIER: params.tierName,
        TICKET_CODE: params.ticketCode,
        QR_IMAGE_URL: qrImageUrl,
        EVENT_URL: eventUrl,
        TICKET_URL: ticketUrl,
        ORGANIZATION_NAME: orgName,
        ONLINE_ACCESS: hasOnlineAccess
          ? 'This event has online access. Visit the event page and enter your ticket code to join the meeting.'
          : '',
      };

      // Try DB template first, fall back to inline template
      const dbTemplate = await emailService['loadTemplateFromDatabase']('ticket-confirmation');

      let html: string, text: string, subject: string;
      if (dbTemplate) {
        html = await emailService.processTemplate(dbTemplate.html, vars);
        text = await emailService.processTextTemplate(dbTemplate.text, vars);
        subject = emailService.processSubject(dbTemplate.subject, vars);
      } else {
        // Inline fallback template
        subject = `Your Ticket: ${params.eventTitle} — ${orgName}`;
        html = this.getDefaultHtmlTemplate(vars);
        text = this.getDefaultTextTemplate(vars);
      }

      await emailService.sendEmail({ to: params.holderEmail, subject, html, text });
      logger.info(`Ticket confirmation sent to ${params.holderEmail} for ${params.ticketCode}`);
    } catch (err) {
      logger.error('Failed to send ticket confirmation email:', err);
    }
  },

  getDefaultHtmlTemplate(vars: Record<string, string>): string {
    const venue = vars.VENUE_NAME
      ? `<p style="margin:0;color:#999">📍 ${vars.VENUE_NAME}${vars.VENUE_ADDRESS ? `, ${vars.VENUE_ADDRESS}` : ''}</p>`
      : '';
    const onlineAccessHtml = vars.ONLINE_ACCESS
      ? `<div style="background:#f3e8ff;padding:15px;border-radius:8px;margin:20px 0;border-left:4px solid #9d4edd"><p style="margin:0;color:#6b21a8">🎥 ${vars.ONLINE_ACCESS}</p></div>`
      : '';

    return `
<!DOCTYPE html>
<html>
<head><meta charset="utf-8"><meta name="viewport" content="width=device-width,initial-scale=1"></head>
<body style="margin:0;padding:0;background:#f5f5f5;font-family:Arial,sans-serif">
<div style="max-width:600px;margin:0 auto;padding:20px">
  <div style="background:#1a1025;color:#fff;padding:30px;border-radius:12px 12px 0 0;text-align:center">
    <h1 style="margin:0;font-size:24px">${vars.EVENT_TITLE}</h1>
    <p style="margin:10px 0 0;opacity:0.8">${vars.EVENT_DATE} at ${vars.EVENT_TIME}</p>
    ${venue}
  </div>
  <div style="background:#fff;padding:30px;border-radius:0 0 12px 12px">
    <p>Hi ${vars.RECIPIENT_NAME},</p>
    <p>Your ticket is confirmed! Here are your details:</p>
    ${onlineAccessHtml}
    <div style="background:#f8f8f8;padding:20px;border-radius:8px;margin:20px 0;text-align:center">
      <p style="margin:0 0 10px;font-size:14px;color:#666">Ticket Code</p>
      <p style="margin:0;font-size:28px;font-weight:bold;letter-spacing:2px;color:#9d4edd">${vars.TICKET_CODE}</p>
      <p style="margin:10px 0 0;font-size:13px;color:#999">${vars.TICKET_TIER}</p>
    </div>
    <div style="text-align:center;margin:20px 0">
      <p style="margin:0 0 10px;font-size:14px;color:#666">Show this QR code at the door:</p>
      <img src="${vars.QR_IMAGE_URL}" alt="Ticket QR Code" width="200" height="200" style="border:1px solid #eee;border-radius:8px">
    </div>
    <div style="text-align:center;margin:20px 0">
      <a href="${vars.TICKET_URL}" style="display:inline-block;background:#9d4edd;color:#fff;padding:12px 24px;border-radius:6px;text-decoration:none;font-weight:bold">View Your Ticket</a>
    </div>
    <hr style="border:none;border-top:1px solid #eee;margin:20px 0">
    <p style="font-size:13px;color:#999;text-align:center">${vars.ORGANIZATION_NAME}</p>
  </div>
</div>
</body>
</html>`;
  },

  getDefaultTextTemplate(vars: Record<string, string>): string {
    const venue = vars.VENUE_NAME
      ? `Venue: ${vars.VENUE_NAME}${vars.VENUE_ADDRESS ? `, ${vars.VENUE_ADDRESS}` : ''}\n`
      : '';
    const onlineAccessText = vars.ONLINE_ACCESS ? `\n${vars.ONLINE_ACCESS}\n` : '';

    return `Your Ticket: ${vars.EVENT_TITLE}

Hi ${vars.RECIPIENT_NAME},

Your ticket is confirmed!

Event: ${vars.EVENT_TITLE}
Date: ${vars.EVENT_DATE}
Time: ${vars.EVENT_TIME}
${venue}Ticket: ${vars.TICKET_TIER}
Code: ${vars.TICKET_CODE}
${onlineAccessText}
View your ticket: ${vars.TICKET_URL}

${vars.ORGANIZATION_NAME}`;
  },

  async getOrgName(): Promise<string> {
    try {
      const settings = await siteSettingsService.get();
      return settings.organizationName || 'Changemaker Lite';
    } catch {
      return 'Changemaker Lite';
    }
  },
};
