create or replace function public.update_profile_subscription_status()
returns trigger as $$
declare
  v_user_id uuid;
  v_plan subscription_plan;
  v_customer_id text;
  v_old_plan subscription_plan;
  v_has_trialing boolean;
  v_has_active boolean;
  v_subscription_status text;
  v_period_end timestamp;
begin
  raise notice '==================== TRIGGER START ====================';
  raise notice 'Table: %, Operation: %, Time: %', TG_TABLE_NAME, TG_OP, now();
  
  -- Get customer ID based on which table triggered this
  if TG_TABLE_NAME = 'subscriptions' then
    v_customer_id := new.customer;
    v_subscription_status := new.status::text;
    raise notice 'Source: subscriptions table';
    raise notice '  - Subscription ID: %', new.id;
    raise notice '  - Customer ID: %', v_customer_id;
    raise notice '  - Status: %', v_subscription_status;
    raise notice '  - Cancel at period end: %', new.cancel_at_period_end;
  elsif TG_TABLE_NAME = 'subscription_items' then
    -- Get customer ID from the subscription
    select customer, status::text into v_customer_id, v_subscription_status
    from stripe.subscriptions
    where id = new.subscription;
    raise notice 'Source: subscription_items table';
    raise notice '  - Subscription Item ID: %', new.id;
    raise notice '  - Subscription ID: %', new.subscription;
    raise notice '  - Customer ID: %', v_customer_id;
    raise notice '  - Price ID: %', new.price;
    raise notice '  - Period Start: %', to_timestamp(new.current_period_start);
    raise notice '  - Period End: %', to_timestamp(new.current_period_end);
  else
    raise notice 'Unknown table: %, skipping', TG_TABLE_NAME;
    return new;
  end if;
  
  -- Skip if no customer_id found
  if v_customer_id is null then
    raise notice 'SKIP: No customer_id found';
    raise notice '==================== TRIGGER END (SKIPPED) ====================';
    return new;
  end if;
  
  -- Extract user_id from customer metadata
  select (metadata->>'user_id')::uuid into v_user_id
  from stripe.customers
  where id = v_customer_id;
  
  raise notice 'Customer metadata lookup:';
  raise notice '  - User ID: %', v_user_id;
  
  -- Skip if no user_id found
  if v_user_id is null then
    raise notice 'SKIP: No user_id in customer metadata';
    raise notice '==================== TRIGGER END (SKIPPED) ====================';
    return new;
  end if;
  
  -- Get current plan from profile
  select plan into v_old_plan
  from public.profiles
  where id = v_user_id;
  
  raise notice 'Profile lookup:';
  raise notice '  - Current plan: %', v_old_plan;
  
  -- Check for trialing subscription with detailed logging
  raise notice 'Checking for TRIALING subscription...';
  select exists(
    select 1
    from stripe.subscriptions s
    inner join stripe.customers c on c.id = s.customer
    inner join stripe.subscription_items si on si.subscription = s.id
    where (c.metadata->>'user_id')::uuid = v_user_id
      and s.status::text = 'trialing'
      and si.current_period_end is not null
      and to_timestamp(si.current_period_end) > now()
  ) into v_has_trialing;
  
  raise notice '  - Has trialing: %', v_has_trialing;
  
  -- Check for active/past_due subscription with detailed logging
  raise notice 'Checking for ACTIVE/PAST_DUE subscription...';
  select exists(
    select 1
    from stripe.subscriptions s
    inner join stripe.customers c on c.id = s.customer
    inner join stripe.subscription_items si on si.subscription = s.id
    where (c.metadata->>'user_id')::uuid = v_user_id
      and s.status::text in ('active', 'past_due')
      and si.current_period_end is not null
      and to_timestamp(si.current_period_end) > now()
  ) into v_has_active;
  
  raise notice '  - Has active/past_due: %', v_has_active;
  
  -- Show what subscriptions exist for this user
  raise notice 'All subscriptions for user %:', v_user_id;
  for v_subscription_status, v_period_end in
    select 
      s.status::text,
      to_timestamp(si.current_period_end)
    from stripe.subscriptions s
    inner join stripe.customers c on c.id = s.customer
    left join stripe.subscription_items si on si.subscription = s.id
    where (c.metadata->>'user_id')::uuid = v_user_id
  loop
    raise notice '  - Status: %, Period End: %', v_subscription_status, v_period_end;
  end loop;
  
  -- Determine the user's current plan
  raise notice 'Calculating new plan...';
  select 
    case
      when exists(
        select 1
        from stripe.subscriptions s
        inner join stripe.customers c on c.id = s.customer
        inner join stripe.subscription_items si on si.subscription = s.id
        where (c.metadata->>'user_id')::uuid = v_user_id
          and s.status::text = 'trialing'
          and si.current_period_end is not null
          and to_timestamp(si.current_period_end) > now()
      ) then 'trial'::subscription_plan
      when exists(
        select 1
        from stripe.subscriptions s
        inner join stripe.customers c on c.id = s.customer
        inner join stripe.subscription_items si on si.subscription = s.id
        where (c.metadata->>'user_id')::uuid = v_user_id
          and s.status::text in ('active', 'past_due')
          and si.current_period_end is not null
          and to_timestamp(si.current_period_end) > now()
      ) then 'standard'::subscription_plan
      else 'none'::subscription_plan
    end into v_plan;
  
  raise notice '  - Calculated plan: %', v_plan;
  raise notice '  - Plan change: % → %', v_old_plan, v_plan;
  
  -- Update the user's profile
  if v_old_plan is distinct from v_plan then
    raise notice 'UPDATING profile...';
    update public.profiles
    set plan = v_plan
    where id = v_user_id;
    raise notice 'Profile UPDATED successfully';
  else
    raise notice 'No plan change needed, skipping update';
  end if;
  
  raise notice '==================== TRIGGER END (SUCCESS) ====================';
  return new;
end;
$$ language plpgsql security definer;