import { serve } from "https://deno.land/std@0.168.0/http/server.ts";
import { createClient } from "https://esm.sh/@supabase/supabase-js@2.57.4";
import { edgeLogger } from '../_shared/logger.ts';

const corsHeaders = {
  'Access-Control-Allow-Origin': '*',
  'Access-Control-Allow-Headers': 'authorization, x-client-info, apikey, content-type',
};

// Simple request tracking
const startRequest = () => ({ requestId: crypto.randomUUID(), start: Date.now() });
const endRequest = (tracking: { start: number }) => Date.now() - tracking.start;

serve(async (req) => {
  const tracking = startRequest();
  
  if (req.method === 'OPTIONS') {
    return new Response(null, { headers: corsHeaders });
  }

  try {
    const supabaseUrl = Deno.env.get('SUPABASE_URL')!;
    const supabaseServiceKey = Deno.env.get('SUPABASE_SERVICE_ROLE_KEY')!;
    const supabase = createClient(supabaseUrl, supabaseServiceKey);

    const event = await req.json();

    edgeLogger.info('Received Novu webhook event', { 
      action: 'novu_webhook', 
      eventType: event.type, 
      requestId: tracking.requestId 
    });

    // Handle different webhook events
    switch (event.type) {
      case 'notification.sent':
        await handleNotificationSent(supabase, event);
        break;
      case 'notification.delivered':
        await handleNotificationDelivered(supabase, event);
        break;
      case 'notification.read':
        await handleNotificationRead(supabase, event);
        break;
      case 'notification.failed':
        await handleNotificationFailed(supabase, event);
        break;
      default:
        edgeLogger.warn('Unhandled Novu event type', { 
          action: 'novu_webhook', 
          eventType: event.type, 
          requestId: tracking.requestId 
        });
    }

    const duration = endRequest(tracking);

    return new Response(
      JSON.stringify({ success: true, requestId: tracking.requestId }),
      {
        headers: { 
          ...corsHeaders, 
          'Content-Type': 'application/json',
          'X-Request-ID': tracking.requestId 
        },
        status: 200,
      }
    );
  } catch (error: any) {
    const duration = endRequest(tracking);
    edgeLogger.error('Error processing webhook', { 
      action: 'novu_webhook', 
      error: error?.message, 
      requestId: tracking.requestId, 
      duration 
    });
    
    return new Response(
      JSON.stringify({
        success: false,
        error: error.message,
        requestId: tracking.requestId
      }),
      {
        headers: { 
          ...corsHeaders, 
          'Content-Type': 'application/json',
          'X-Request-ID': tracking.requestId 
        },
        status: 500,
      }
    );
  }
});

async function handleNotificationSent(supabase: any, event: any) {
  const { transactionId, channel } = event.data;
  
  await supabase
    .from('notification_logs')
    .update({ status: 'sent' })
    .eq('novu_transaction_id', transactionId);
}

async function handleNotificationDelivered(supabase: any, event: any) {
  const { transactionId } = event.data;
  
  await supabase
    .from('notification_logs')
    .update({ 
      status: 'delivered',
      delivered_at: new Date().toISOString(),
    })
    .eq('novu_transaction_id', transactionId);
}

async function handleNotificationRead(supabase: any, event: any) {
  const { transactionId } = event.data;
  
  await supabase
    .from('notification_logs')
    .update({ 
      read_at: new Date().toISOString(),
    })
    .eq('novu_transaction_id', transactionId);
}

async function handleNotificationFailed(supabase: any, event: any) {
  const { transactionId, error } = event.data;
  
  await supabase
    .from('notification_logs')
    .update({ 
      status: 'failed',
      error_message: error,
    })
    .eq('novu_transaction_id', transactionId);
}
