import type { APIRoute } from 'astro';
import { createClient, SupabaseClient } from '@supabase/supabase-js';

export const prerender = false;

// Initialize Supabase client with service key for admin access
const supabaseUrl = process.env.PUBLIC_SUPABASE_URL || import.meta.env.PUBLIC_SUPABASE_URL || 'https://zctjaivtfyfxokfaemek.supabase.co';
const supabaseServiceKey = process.env.SUPABASE_SERVICE_KEY || import.meta.env.SUPABASE_SERVICE_KEY || '';

let supabase: SupabaseClient | null = null;
try {
  if (supabaseUrl && supabaseServiceKey) {
    supabase = createClient(supabaseUrl, supabaseServiceKey, {
      auth: {
        autoRefreshToken: false,
        persistSession: false
      }
    });
  }
} catch (error) {
  console.error('Supabase initialization failed:', error);
}

export const GET: APIRoute = async ({ request }) => {
  try {
    if (!supabase) {
      return new Response(JSON.stringify({
        success: false,
        error: 'Database not available'
      }), {
        status: 500,
        headers: { 'Content-Type': 'application/json' }
      });
    }

    // Verify user authentication and admin role
    const authHeader = request.headers.get('Authorization');
    if (!authHeader || !authHeader.startsWith('Bearer ')) {
      return new Response(JSON.stringify({
        success: false,
        error: 'Authentication required'
      }), {
        status: 401,
        headers: { 'Content-Type': 'application/json' }
      });
    }

    const token = authHeader.substring(7);
    
    // Create a client with the anon key to validate the user token
    const supabaseAnonKey = process.env.PUBLIC_SUPABASE_ANON_KEY || import.meta.env.PUBLIC_SUPABASE_ANON_KEY || '';
    
    if (!supabaseAnonKey) {
      return new Response(JSON.stringify({
        success: false,
        error: 'Authentication configuration error'
      }), {
        status: 500,
        headers: { 'Content-Type': 'application/json' }
      });
    }
    
    const supabaseUser = createClient(supabaseUrl, supabaseAnonKey);
    
    const { data: { user }, error: authError } = await supabaseUser.auth.getUser(token);
    
    if (authError || !user) {
      return new Response(JSON.stringify({
        success: false,
        error: 'Invalid authentication'
      }), {
        status: 401,
        headers: { 'Content-Type': 'application/json' }
      });
    }

    // Check if user is admin using service key
    const { data: userRecord, error: userError } = await supabase
      .from('users')
      .select('role')
      .eq('id', user.id)
      .single();

    if (userError || !userRecord || userRecord.role !== 'admin') {
      return new Response(JSON.stringify({
        success: false,
        error: 'Admin access required'
      }), {
        status: 403,
        headers: { 'Content-Type': 'application/json' }
      });
    }

    // NOTE: Using service key bypasses RLS, so we have admin access to all data
    
    const searchParams = new URL(request.url).searchParams;
    const metric = searchParams.get('metric');
    const startDate = searchParams.get('start_date');
    const endDate = searchParams.get('end_date');
    const filterType = searchParams.get('filter_type');
    const filterValue = searchParams.get('filter_value');

    let whereClause = '';
    if (startDate && endDate) {
      whereClause = `AND created_at >= '${startDate}' AND created_at <= '${endDate}'`;
    }

    switch (metric) {
      case 'platform_overview':
        return await getPlatformOverview();
      
      case 'revenue_breakdown':
        return await getRevenueBreakdown(whereClause, filterType, filterValue);
      
      case 'organizer_performance':
        return await getOrganizerPerformance(whereClause, filterType, filterValue);
      
      case 'event_analytics':
        return await getEventAnalytics(whereClause, filterType, filterValue);
      
      case 'sales_trends':
        return await getSalesTrends(whereClause, filterType, filterValue);
      
      case 'traffic_analytics':
        return await getTrafficAnalytics(whereClause, filterType, filterValue);
      
      case 'location_analytics':
        return await getLocationAnalytics(whereClause, filterType, filterValue);
      
      case 'ticket_analytics':
        return await getTicketAnalytics(whereClause, filterType, filterValue);
      
      default:
        return await getPlatformOverview();
    }
  } catch (_error) {
    return new Response(JSON.stringify({
      success: false,
      error: 'Access denied or server error'
    }), {
      status: 500,
      headers: { 'Content-Type': 'application/json' }
    });
  }
};

async function getPlatformOverview() {
  try {
    const [
      organizationsResult,
      eventsResult,
      ticketsResult,
      purchasesResult,
      usersResult
    ] = await Promise.all([
      supabase.from('organizations').select('id, name, created_at, platform_fee_percentage, platform_fee_fixed'),
      supabase.from('events').select('id, title, created_at, organization_id, is_published'),
      supabase.from('tickets').select('id, price, created_at, event_id'),
      supabase.from('purchase_attempts').select('id, total_amount, platform_fee, created_at, completed_at, event_id, referral_source, utm_source, utm_campaign, utm_medium, country_code, country_name, region, city, ip_address').not('completed_at', 'is', null),
      supabase.from('users').select('id, created_at, role, organization_id')
    ]);

    const organizations = organizationsResult.data || [];
    const events = eventsResult.data || [];
    const tickets = ticketsResult.data || [];
    const purchases = purchasesResult.data || [];
    const users = usersResult.data || [];

    // Calculate key metrics
    const totalRevenue = purchases.reduce((sum, p) => sum + (p.total_amount || 0), 0);
    const totalPlatformFees = purchases.reduce((sum, p) => sum + (p.platform_fee || 0), 0);
    const totalNetToOrganizers = totalRevenue - totalPlatformFees;
    
    // Month-over-month calculations
    const now = new Date();
    const thisMonth = new Date(now.getFullYear(), now.getMonth(), 1);
    const lastMonth = new Date(now.getFullYear(), now.getMonth() - 1, 1);
    
    const thisMonthPurchases = purchases.filter(p => new Date(p.completed_at) >= thisMonth);
    const lastMonthPurchases = purchases.filter(p => {
      const date = new Date(p.completed_at);
      return date >= lastMonth && date < thisMonth;
    });

    const thisMonthRevenue = thisMonthPurchases.reduce((sum, p) => sum + (p.total_amount || 0), 0);
    const lastMonthRevenue = lastMonthPurchases.reduce((sum, p) => sum + (p.total_amount || 0), 0);
    
    const revenueGrowth = lastMonthRevenue > 0 ? ((thisMonthRevenue - lastMonthRevenue) / lastMonthRevenue) * 100 : 0;

    // Top performing organizers
    const organizerPerformance: Record<string, OrganizerPerformance> = {};
    purchases.forEach(purchase => {
      const event = events.find(e => e.id === purchase.event_id);
      if (event) {
        const orgId = event.organization_id;
        if (!organizerPerformance[orgId]) {
          const org = organizations.find(o => o.id === orgId);
          organizerPerformance[orgId] = {
            name: org?.name || 'Unknown',
            revenue: 0,
            fees: 0,
            events: 0,
            tickets: 0
          };
        }
        organizerPerformance[orgId].revenue += purchase.total_amount || 0;
        organizerPerformance[orgId].fees += purchase.platform_fee || 0;
      }
    });

    // Count events and tickets per organizer
    Object.keys(organizerPerformance).forEach(orgId => {
      organizerPerformance[orgId].events = events.filter(e => e.organization_id === orgId).length;
      organizerPerformance[orgId].tickets = tickets.filter(t => {
        const event = events.find(e => e.id === t.event_id);
        return event?.organization_id === orgId;
      }).length;
    });

    const topOrganizers = Object.values(organizerPerformance)
      .sort((a, b) => b.revenue - a.revenue)
      .slice(0, 10);

    // Traffic source analytics
    interface TrafficSource {
      source: string;
      revenue: number;
      count: number;
      campaign: string | null;
      medium: string | null;
    }
    
    interface GeoData {
      country: string;
      code: string;
      revenue: number;
      count: number;
      cities: Set<string>;
    }
    
    const trafficSources: Record<string, TrafficSource> = {};
    const geoData: Record<string, GeoData> = {};
    
    purchases.forEach(purchase => {
      // Referral source tracking
      const source = purchase.referral_source || purchase.utm_source || 'direct';
      if (!trafficSources[source]) {
        trafficSources[source] = {
          source: source,
          revenue: 0,
          count: 0,
          campaign: purchase.utm_campaign || null,
          medium: purchase.utm_medium || null
        };
      }
      trafficSources[source].revenue += purchase.total_amount || 0;
      trafficSources[source].count++;
      
      // Geographic data tracking
      if (purchase.country_code) {
        const country = purchase.country_name || purchase.country_code;
        if (!geoData[country]) {
          geoData[country] = {
            country: country,
            code: purchase.country_code,
            revenue: 0,
            count: 0,
            cities: new Set()
          };
        }
        geoData[country].revenue += purchase.total_amount || 0;
        geoData[country].count++;
        if (purchase.city) {
          geoData[country].cities.add(purchase.city);
        }
      }
    });

    // Convert traffic sources to array and sort
    const topTrafficSources = Object.values(trafficSources)
      .sort((a, b) => b.revenue - a.revenue)
      .slice(0, 10)
      .map(source => ({
        ...source,
        revenue: source.revenue / 100,
        avgOrderValue: source.count > 0 ? (source.revenue / source.count) / 100 : 0
      }));

    // Convert geo data to array and sort
    const topCountries = Object.values(geoData)
      .sort((a, b) => b.revenue - a.revenue)
      .slice(0, 10)
      .map(geo => ({
        ...geo,
        revenue: geo.revenue / 100,
        avgOrderValue: geo.count > 0 ? (geo.revenue / geo.count) / 100 : 0,
        cityCount: geo.cities.size
      }));

    // Recent activity
    const recentActivity = [
      ...purchases.slice(-5).map(p => ({
        type: 'purchase',
        amount: p.total_amount,
        date: p.completed_at,
        event_id: p.event_id
      })),
      ...events.slice(-5).map(e => ({
        type: 'event',
        title: e.title,
        date: e.created_at,
        organization_id: e.organization_id
      })),
      ...organizations.slice(-3).map(o => ({
        type: 'organization',
        name: o.name,
        date: o.created_at
      }))
    ].sort((a, b) => new Date(b.date) - new Date(a.date)).slice(0, 10);

    return new Response(JSON.stringify({
      success: true,
      data: {
        summary: {
          totalRevenue: totalRevenue / 100,
          totalPlatformFees: totalPlatformFees / 100,
          totalNetToOrganizers: totalNetToOrganizers / 100,
          activeOrganizers: organizations.length,
          totalEvents: events.length,
          publishedEvents: events.filter(e => e.is_published).length,
          totalTickets: tickets.length,
          totalUsers: users.length,
          adminUsers: users.filter(u => u.role === 'admin').length,
          revenueGrowth: revenueGrowth,
          thisMonthRevenue: thisMonthRevenue / 100,
          lastMonthRevenue: lastMonthRevenue / 100
        },
        topOrganizers,
        recentActivity,
        monthlyTrends: getMonthlyTrends(purchases, 6),
        trafficSources: topTrafficSources,
        geoData: topCountries
      }
    }), {
      status: 200,
      headers: { 'Content-Type': 'application/json' }
    });
  } catch (_error) {
    return new Response(JSON.stringify({
      success: false,
      error: 'Failed to load platform overview'
    }), {
      status: 500,
      headers: { 'Content-Type': 'application/json' }
    });
  }
}

async function getRevenueBreakdown(_whereClause: string, _filterType?: string, _filterValue?: string) {
  try {
    const { data: purchases } = await supabase
      .from('purchase_attempts')
      .select('total_amount, platform_fee, completed_at, event_id')
      .not('completed_at', 'is', null);

    const { data: events } = await supabase
      .from('events')
      .select('id, organization_id, title, start_time');

    const { data: organizations } = await supabase
      .from('organizations')
      .select('id, name');

    // Group by organization
    const organizationBreakdown: Record<string, any> = {};
    
    purchases?.forEach(purchase => {
      const event = events?.find(e => e.id === purchase.event_id);
      if (event) {
        const orgId = event.organization_id;
        const org = organizations?.find(o => o.id === orgId);
        
        if (!organizationBreakdown[orgId]) {
          organizationBreakdown[orgId] = {
            name: org?.name || 'Unknown',
            grossRevenue: 0,
            platformFees: 0,
            netRevenue: 0,
            transactionCount: 0,
            events: new Set()
          };
        }
        
        organizationBreakdown[orgId].grossRevenue += purchase.total_amount || 0;
        organizationBreakdown[orgId].platformFees += purchase.platform_fee || 0;
        organizationBreakdown[orgId].netRevenue += (purchase.total_amount || 0) - (purchase.platform_fee || 0);
        organizationBreakdown[orgId].transactionCount++;
        organizationBreakdown[orgId].events.add(event.id);
      }
    });

    // Convert Set to count
    Object.values(organizationBreakdown).forEach((org: any) => {
      org.eventCount = org.events.size;
      delete org.events;
    });

    const breakdown = Object.values(organizationBreakdown)
      .sort((a, b) => b.grossRevenue - a.grossRevenue)
      .map(org => ({
        ...org,
        grossRevenue: org.grossRevenue / 100,
        platformFees: org.platformFees / 100,
        netRevenue: org.netRevenue / 100,
        averageTransactionValue: org.transactionCount > 0 ? (org.grossRevenue / org.transactionCount) / 100 : 0
      }));

    return new Response(JSON.stringify({
      success: true,
      data: {
        breakdown,
        totals: {
          grossRevenue: breakdown.reduce((sum, org) => sum + org.grossRevenue, 0),
          platformFees: breakdown.reduce((sum, org) => sum + org.platformFees, 0),
          netRevenue: breakdown.reduce((sum, org) => sum + org.netRevenue, 0),
          transactionCount: breakdown.reduce((sum, org) => sum + org.transactionCount, 0),
          eventCount: breakdown.reduce((sum, org) => sum + org.eventCount, 0)
        }
      }
    }), {
      status: 200,
      headers: { 'Content-Type': 'application/json' }
    });
  } catch (_error) {
    return new Response(JSON.stringify({
      success: false,
      error: 'Failed to load revenue breakdown'
    }), {
      status: 500,
      headers: { 'Content-Type': 'application/json' }
    });
  }
}

async function getOrganizerPerformance(_whereClause: string, _filterType?: string, _filterValue?: string) {
  try {
    const { data: organizations } = await supabase
      .from('organizations')
      .select('id, name, created_at, platform_fee_percentage, platform_fee_fixed');

    const { data: events } = await supabase
      .from('events')
      .select('id, title, organization_id, created_at, is_published');

    const { data: tickets } = await supabase
      .from('tickets')
      .select('id, event_id, price, created_at');

    const { data: purchases } = await supabase
      .from('purchase_attempts')
      .select('id, event_id, total_amount, platform_fee, completed_at')
      .not('completed_at', 'is', null);

    const performance = organizations?.map(org => {
      const orgEvents = events?.filter(e => e.organization_id === org.id) || [];
      const orgTickets = tickets?.filter(t => {
        const event = events?.find(e => e.id === t.event_id);
        return event?.organization_id === org.id;
      }) || [];
      const orgPurchases = purchases?.filter(p => {
        const event = events?.find(e => e.id === p.event_id);
        return event?.organization_id === org.id;
      }) || [];

      const totalRevenue = orgPurchases.reduce((sum, p) => sum + (p.total_amount || 0), 0);
      const totalFees = orgPurchases.reduce((sum, p) => sum + (p.platform_fee || 0), 0);
      const avgTicketPrice = orgTickets.length > 0 ? 
        orgTickets.reduce((sum, t) => sum + (t.price || 0), 0) / orgTickets.length : 0;

      return {
        id: org.id,
        name: org.name,
        joinDate: org.created_at,
        eventCount: orgEvents.length,
        publishedEvents: orgEvents.filter(e => e.is_published).length,
        ticketsSold: orgTickets.length,
        totalRevenue: totalRevenue / 100,
        platformFees: totalFees / 100,
        netRevenue: (totalRevenue - totalFees) / 100,
        avgTicketPrice,
        avgRevenuePerEvent: orgEvents.length > 0 ? (totalRevenue / orgEvents.length) / 100 : 0,
        customFeePercentage: org.platform_fee_percentage,
        customFeeFixed: org.platform_fee_fixed
      };
    }) || [];

    return new Response(JSON.stringify({
      success: true,
      data: {
        organizers: performance.sort((a, b) => b.totalRevenue - a.totalRevenue),
        summary: {
          totalOrganizers: performance.length,
          averageEventsPerOrganizer: performance.length > 0 ? 
            performance.reduce((sum, o) => sum + o.eventCount, 0) / performance.length : 0,
          averageRevenuePerOrganizer: performance.length > 0 ? 
            performance.reduce((sum, o) => sum + o.totalRevenue, 0) / performance.length : 0,
          topPerformerRevenue: performance.length > 0 ? performance[0].totalRevenue : 0
        }
      }
    }), {
      status: 200,
      headers: { 'Content-Type': 'application/json' }
    });
  } catch (_error) {
    return new Response(JSON.stringify({
      success: false,
      error: 'Failed to load organizer performance'
    }), {
      status: 500,
      headers: { 'Content-Type': 'application/json' }
    });
  }
}

async function getEventAnalytics(_whereClause: string, _filterType?: string, _filterValue?: string) {
  try {
    const { data: events } = await supabase
      .from('events')
      .select('id, title, organization_id, created_at, start_time, is_published, category');

    const { data: tickets } = await supabase
      .from('tickets')
      .select('id, event_id, price, created_at');

    const { data: ticketTypes } = await supabase
      .from('ticket_types')
      .select('id, event_id, name, price, quantity_available, quantity_sold');

    const eventAnalytics = events?.map(event => {
      const eventTickets = tickets?.filter(t => t.event_id === event.id) || [];
      const eventTicketTypes = ticketTypes?.filter(tt => tt.event_id === event.id) || [];

      const totalRevenue = eventTickets.reduce((sum, t) => sum + (t.price || 0), 0);
      const totalCapacity = eventTicketTypes.reduce((sum, tt) => sum + (tt.quantity_available || 0), 0);
      const soldTickets = eventTicketTypes.reduce((sum, tt) => sum + (tt.quantity_sold || 0), 0);

      return {
        id: event.id,
        title: event.title,
        organizationId: event.organization_id,
        createdAt: event.created_at,
        startTime: event.start_time,
        isPublished: event.is_published,
        category: event.category,
        ticketsSold: eventTickets.length,
        totalRevenue,
        totalCapacity,
        soldTickets,
        sellThroughRate: totalCapacity > 0 ? (soldTickets / totalCapacity) * 100 : 0,
        avgTicketPrice: eventTickets.length > 0 ? totalRevenue / eventTickets.length : 0,
        ticketTypeCount: eventTicketTypes.length
      };
    }) || [];

    return new Response(JSON.stringify({
      success: true,
      data: {
        events: eventAnalytics.sort((a, b) => b.totalRevenue - a.totalRevenue),
        summary: {
          totalEvents: eventAnalytics.length,
          publishedEvents: eventAnalytics.filter(e => e.isPublished).length,
          totalTicketsSold: eventAnalytics.reduce((sum, e) => sum + e.ticketsSold, 0),
          totalRevenue: eventAnalytics.reduce((sum, e) => sum + e.totalRevenue, 0),
          avgSellThroughRate: eventAnalytics.length > 0 ? 
            eventAnalytics.reduce((sum, e) => sum + e.sellThroughRate, 0) / eventAnalytics.length : 0,
          avgTicketPrice: eventAnalytics.length > 0 ? 
            eventAnalytics.reduce((sum, e) => sum + e.avgTicketPrice, 0) / eventAnalytics.length : 0
        }
      }
    }), {
      status: 200,
      headers: { 'Content-Type': 'application/json' }
    });
  } catch (_error) {
    return new Response(JSON.stringify({
      success: false,
      error: 'Failed to load event analytics'
    }), {
      status: 500,
      headers: { 'Content-Type': 'application/json' }
    });
  }
}

async function getSalesTrends(_whereClause: string, _filterType?: string, _filterValue?: string) {
  try {
    const { data: purchases } = await supabase
      .from('purchase_attempts')
      .select('total_amount, platform_fee, completed_at')
      .not('completed_at', 'is', null);

    const trends = getMonthlyTrends(purchases || [], 12);

    return new Response(JSON.stringify({
      success: true,
      data: {
        trends,
        summary: {
          totalPeriods: trends.length,
          averageMonthlyRevenue: trends.length > 0 ? 
            trends.reduce((sum, t) => sum + t.revenue, 0) / trends.length : 0,
          averageMonthlyFees: trends.length > 0 ? 
            trends.reduce((sum, t) => sum + t.fees, 0) / trends.length : 0,
          growth: trends.length > 1 ? 
            ((trends[trends.length - 1].revenue - trends[0].revenue) / trends[0].revenue) * 100 : 0
        }
      }
    }), {
      status: 200,
      headers: { 'Content-Type': 'application/json' }
    });
  } catch (_error) {
    return new Response(JSON.stringify({
      success: false,
      error: 'Failed to load sales trends'
    }), {
      status: 500,
      headers: { 'Content-Type': 'application/json' }
    });
  }
}

interface Purchase {
  total_amount?: number;
  platform_fee?: number;
  completed_at: string;
  event_id?: string;
}

interface OrganizerPerformance {
  name: string;
  revenue: number;
  fees: number;
  events: number;
  tickets: number;
}

function getMonthlyTrends(purchases: Purchase[], monthCount: number) {
  const months = [];
  const now = new Date();
  
  for (let i = monthCount - 1; i >= 0; i--) {
    const date = new Date(now.getFullYear(), now.getMonth() - i, 1);
    months.push(date);
  }

  return months.map(month => {
    const nextMonth = new Date(month.getFullYear(), month.getMonth() + 1, 1);
    const monthPurchases = purchases.filter(p => {
      const purchaseDate = new Date(p.completed_at);
      return purchaseDate >= month && purchaseDate < nextMonth;
    });

    const revenue = monthPurchases.reduce((sum, p) => sum + (p.total_amount || 0), 0) / 100;
    const fees = monthPurchases.reduce((sum, p) => sum + (p.platform_fee || 0), 0) / 100;

    return {
      month: month.toLocaleDateString('en-US', { month: 'short', year: 'numeric' }),
      revenue,
      fees,
      transactions: monthPurchases.length,
      avgTransactionValue: monthPurchases.length > 0 ? revenue / monthPurchases.length : 0
    };
  });
}

async function getTrafficAnalytics(_whereClause: string, _filterType?: string, _filterValue?: string) {
  try {
    const { data: purchases } = await supabase
      .from('purchase_attempts')
      .select('total_amount, platform_fee, completed_at, referral_source, utm_source, utm_campaign, utm_medium, utm_term, utm_content')
      .not('completed_at', 'is', null);

    interface TrafficAnalytic {
      source: string;
      revenue: number;
      transactions: number;
      mediums: Set<string>;
      campaigns: Set<string>;
    }
    
    interface CampaignAnalytic {
      source: string;
      campaign: string;
      medium: string;
      revenue: number;
      transactions: number;
    }
    
    const trafficAnalytics: Record<string, TrafficAnalytic> = {};
    const campaignAnalytics: Record<string, CampaignAnalytic> = {};
    
    purchases?.forEach(purchase => {
      const source = purchase.referral_source || purchase.utm_source || 'direct';
      const campaign = purchase.utm_campaign || 'none';
      const medium = purchase.utm_medium || 'none';
      
      // Traffic source analytics
      if (!trafficAnalytics[source]) {
        trafficAnalytics[source] = {
          source: source,
          revenue: 0,
          transactions: 0,
          mediums: new Set(),
          campaigns: new Set()
        };
      }
      
      trafficAnalytics[source].revenue += purchase.total_amount || 0;
      trafficAnalytics[source].transactions++;
      trafficAnalytics[source].mediums.add(medium);
      trafficAnalytics[source].campaigns.add(campaign);
      
      // Campaign analytics
      if (purchase.utm_campaign) {
        const campaignKey = `${source}_${campaign}`;
        if (!campaignAnalytics[campaignKey]) {
          campaignAnalytics[campaignKey] = {
            source: source,
            campaign: campaign,
            medium: medium,
            revenue: 0,
            transactions: 0
          };
        }
        campaignAnalytics[campaignKey].revenue += purchase.total_amount || 0;
        campaignAnalytics[campaignKey].transactions++;
      }
    });

    // Convert to arrays and calculate metrics
    const topSources = Object.values(trafficAnalytics)
      .sort((a, b) => b.revenue - a.revenue)
      .map(source => ({
        ...source,
        revenue: source.revenue / 100,
        avgOrderValue: source.transactions > 0 ? (source.revenue / source.transactions) / 100 : 0,
        mediumCount: source.mediums.size,
        campaignCount: source.campaigns.size
      }));

    const topCampaigns = Object.values(campaignAnalytics)
      .sort((a, b) => b.revenue - a.revenue)
      .slice(0, 20)
      .map(campaign => ({
        ...campaign,
        revenue: campaign.revenue / 100,
        avgOrderValue: campaign.transactions > 0 ? (campaign.revenue / campaign.transactions) / 100 : 0
      }));

    return new Response(JSON.stringify({
      success: true,
      data: {
        sources: topSources,
        campaigns: topCampaigns,
        summary: {
          totalSources: topSources.length,
          totalCampaigns: topCampaigns.length,
          topSourceRevenue: topSources.length > 0 ? topSources[0].revenue : 0,
          topCampaignRevenue: topCampaigns.length > 0 ? topCampaigns[0].revenue : 0
        }
      }
    }), {
      status: 200,
      headers: { 'Content-Type': 'application/json' }
    });
  } catch (_error) {
    return new Response(JSON.stringify({
      success: false,
      error: 'Failed to load traffic analytics'
    }), {
      status: 500,
      headers: { 'Content-Type': 'application/json' }
    });
  }
}

async function getLocationAnalytics(_whereClause: string, _filterType?: string, _filterValue?: string) {
  try {
    const { data: purchases } = await supabase
      .from('purchase_attempts')
      .select('total_amount, platform_fee, completed_at, ip_address, country_code, country_name, region, city, latitude, longitude')
      .not('completed_at', 'is', null);

    interface CountryAnalytic {
      code: string;
      name: string;
      revenue: number;
      transactions: number;
      cities: Set<string>;
      regions: Set<string>;
    }
    
    interface CityAnalytic {
      country: string;
      countryCode: string;
      city: string;
      region: string;
      revenue: number;
      transactions: number;
    }
    
    interface RegionAnalytic {
      country: string;
      countryCode: string;
      region: string;
      revenue: number;
      transactions: number;
      cities: Set<string>;
    }
    
    const countryAnalytics: Record<string, CountryAnalytic> = {};
    const cityAnalytics: Record<string, CityAnalytic> = {};
    const regionAnalytics: Record<string, RegionAnalytic> = {};
    
    purchases?.forEach(purchase => {
      if (purchase.country_code) {
        const countryKey = purchase.country_code;
        const country = purchase.country_name || purchase.country_code;
        
        // Country analytics
        if (!countryAnalytics[countryKey]) {
          countryAnalytics[countryKey] = {
            code: purchase.country_code,
            name: country,
            revenue: 0,
            transactions: 0,
            cities: new Set(),
            regions: new Set()
          };
        }
        
        countryAnalytics[countryKey].revenue += purchase.total_amount || 0;
        countryAnalytics[countryKey].transactions++;
        
        if (purchase.city) {
          countryAnalytics[countryKey].cities.add(purchase.city);
          
          // City analytics
          const cityKey = `${purchase.country_code}_${purchase.city}`;
          if (!cityAnalytics[cityKey]) {
            cityAnalytics[cityKey] = {
              country: country,
              countryCode: purchase.country_code,
              city: purchase.city,
              region: purchase.region,
              revenue: 0,
              transactions: 0
            };
          }
          cityAnalytics[cityKey].revenue += purchase.total_amount || 0;
          cityAnalytics[cityKey].transactions++;
        }
        
        if (purchase.region) {
          countryAnalytics[countryKey].regions.add(purchase.region);
          
          // Region analytics
          const regionKey = `${purchase.country_code}_${purchase.region}`;
          if (!regionAnalytics[regionKey]) {
            regionAnalytics[regionKey] = {
              country: country,
              countryCode: purchase.country_code,
              region: purchase.region,
              revenue: 0,
              transactions: 0,
              cities: new Set()
            };
          }
          regionAnalytics[regionKey].revenue += purchase.total_amount || 0;
          regionAnalytics[regionKey].transactions++;
          if (purchase.city) {
            regionAnalytics[regionKey].cities.add(purchase.city);
          }
        }
      }
    });

    // Convert to arrays and calculate metrics
    const topCountries = Object.values(countryAnalytics)
      .sort((a, b) => b.revenue - a.revenue)
      .map(country => ({
        ...country,
        revenue: country.revenue / 100,
        avgOrderValue: country.transactions > 0 ? (country.revenue / country.transactions) / 100 : 0,
        cityCount: country.cities.size,
        regionCount: country.regions.size
      }));

    const topCities = Object.values(cityAnalytics)
      .sort((a, b) => b.revenue - a.revenue)
      .slice(0, 50)
      .map(city => ({
        ...city,
        revenue: city.revenue / 100,
        avgOrderValue: city.transactions > 0 ? (city.revenue / city.transactions) / 100 : 0
      }));

    const topRegions = Object.values(regionAnalytics)
      .sort((a, b) => b.revenue - a.revenue)
      .slice(0, 30)
      .map(region => ({
        ...region,
        revenue: region.revenue / 100,
        avgOrderValue: region.transactions > 0 ? (region.revenue / region.transactions) / 100 : 0,
        cityCount: region.cities.size
      }));

    return new Response(JSON.stringify({
      success: true,
      data: {
        countries: topCountries,
        cities: topCities,
        regions: topRegions,
        summary: {
          totalCountries: topCountries.length,
          totalCities: topCities.length,
          totalRegions: topRegions.length,
          topCountryRevenue: topCountries.length > 0 ? topCountries[0].revenue : 0,
          topCityRevenue: topCities.length > 0 ? topCities[0].revenue : 0
        }
      }
    }), {
      status: 200,
      headers: { 'Content-Type': 'application/json' }
    });
  } catch (_error) {
    return new Response(JSON.stringify({
      success: false,
      error: 'Failed to load location analytics'
    }), {
      status: 500,
      headers: { 'Content-Type': 'application/json' }
    });
  }
}

async function getTicketAnalytics(_whereClause: string, filterType?: string, filterValue?: string) {
  try {
    const searchParams = new URLSearchParams(_whereClause);
    const startDate = searchParams.get('start_date');
    const endDate = searchParams.get('end_date');
    const minPrice = searchParams.get('min_price');
    const maxPrice = searchParams.get('max_price');
    const _search = searchParams.get('search');
    const page = parseInt(searchParams.get('page') || '1');
    const limit = parseInt(searchParams.get('limit') || '50');
    const offset = (page - 1) * limit;

    // Build where conditions
    const ticketConditions = [];
    if (startDate) ticketConditions.push(`tickets.created_at >= '${startDate}'`);
    if (endDate) ticketConditions.push(`tickets.created_at <= '${endDate}'`);
    if (minPrice) ticketConditions.push(`tickets.price >= ${parseInt(minPrice) * 100}`);
    if (maxPrice) ticketConditions.push(`tickets.price <= ${parseInt(maxPrice) * 100}`);

    // Get tickets with related data
    let ticketsQuery = supabase
      .from('tickets')
      .select(`
        id,
        price,
        created_at,
        used_at,
        refunded_at,
        cancelled_at,
        customer_email,
        customer_name,
        seat_number,
        seat_row,
        qr_code,
        event_id,
        ticket_type_id,
        events (
          id,
          title,
          start_time,
          organization_id,
          organizations (
            id,
            name
          )
        ),
        ticket_types (
          id,
          name,
          description
        )
      `)
      .order('created_at', { ascending: false });

    // Apply filters
    if (filterType === 'event' && filterValue) {
      ticketsQuery = ticketsQuery.eq('event_id', filterValue);
    }
    if (filterType === 'organizer' && filterValue) {
      ticketsQuery = ticketsQuery.eq('events.organization_id', filterValue);
    }
    if (filterType === 'status' && filterValue) {
      switch (filterValue) {
        case 'active': {
          ticketsQuery = ticketsQuery.is('used_at', null).is('refunded_at', null).is('cancelled_at', null);
          break;
        }
        case 'used': {
          ticketsQuery = ticketsQuery.not('used_at', 'is', null);
          break;
        }
        case 'refunded': {
          ticketsQuery = ticketsQuery.not('refunded_at', 'is', null);
          break;
        }
        case 'cancelled': {
          ticketsQuery = ticketsQuery.not('cancelled_at', 'is', null);
          break;
        }
      }
    }

    // Get total count for pagination
    const { count: totalCount } = await ticketsQuery;

    // Get paginated results
    const { data: tickets } = await ticketsQuery
      .range(offset, offset + limit - 1);

    // Calculate statistics
    const stats = {
      total: totalCount || 0,
      used: 0,
      active: 0,
      refunded: 0,
      cancelled: 0,
      totalRevenue: 0,
      averagePrice: 0
    };

    // Get all tickets for statistics (not just the page)
    const { data: allTickets } = await supabase
      .from('tickets')
      .select('price, used_at, refunded_at, cancelled_at');

    allTickets?.forEach(ticket => {
      stats.totalRevenue += ticket.price || 0;
      
      if (ticket.used_at) {
        stats.used++;
      } else if (ticket.refunded_at) {
        stats.refunded++;
      } else if (ticket.cancelled_at) {
        stats.cancelled++;
      } else {
        stats.active++;
      }
    });

    stats.averagePrice = stats.total > 0 ? stats.totalRevenue / stats.total : 0;
    stats.totalRevenue = stats.totalRevenue / 100; // Convert to dollars

    // Format tickets for display
    const formattedTickets = tickets?.map(ticket => ({
      id: ticket.id,
      price: ticket.price / 100,
      createdAt: ticket.created_at,
      usedAt: ticket.used_at,
      refundedAt: ticket.refunded_at,
      cancelledAt: ticket.cancelled_at,
      customerEmail: ticket.customer_email,
      customerName: ticket.customer_name,
      seatNumber: ticket.seat_number,
      seatRow: ticket.seat_row,
      qrCode: ticket.qr_code,
      status: ticket.used_at ? 'used' : 
              ticket.refunded_at ? 'refunded' : 
              ticket.cancelled_at ? 'cancelled' : 'active',
      event: {
        id: ticket.events?.id,
        title: ticket.events?.title,
        startTime: ticket.events?.start_time,
        organizationId: ticket.events?.organization_id,
        organizationName: ticket.events?.organizations?.name
      },
      ticketType: {
        id: ticket.ticket_types?.id,
        name: ticket.ticket_types?.name,
        description: ticket.ticket_types?.description
      }
    })) || [];

    // Get unique events and organizers for filters
    const { data: events } = await supabase
      .from('events')
      .select('id, title, organization_id, organizations(name)')
      .order('title');

    const { data: organizations } = await supabase
      .from('organizations')
      .select('id, name')
      .order('name');

    return new Response(JSON.stringify({
      success: true,
      data: {
        tickets: formattedTickets,
        stats,
        pagination: {
          page,
          limit,
          total: totalCount || 0,
          pages: Math.ceil((totalCount || 0) / limit)
        },
        filters: {
          events: events?.map(e => ({
            id: e.id,
            title: e.title,
            organizationName: e.organizations?.name
          })) || [],
          organizations: organizations?.map(o => ({
            id: o.id,
            name: o.name
          })) || []
        }
      }
    }), {
      status: 200,
      headers: { 'Content-Type': 'application/json' }
    });
  } catch (_error) {
    return new Response(JSON.stringify({
      success: false,
      error: 'Failed to load ticket analytics'
    }), {
      status: 500,
      headers: { 'Content-Type': 'application/json' }
    });
  }
}