import type { FraudAdapter, EarnCtx, FraudSignal, AdapterConfig } from '../types.js';
import { eq } from 'drizzle-orm';
import { referrals, orderLine } from '@/server/db/schema.js';
import { sql } from 'drizzle-orm';
import { asReferralId } from '@/server/platform-seams/ids.js';

export const velocityConversionAdapter: FraudAdapter<EarnCtx> = {
  key: 'velocity-conversion',
  points: ['EARN'],
  async evaluate(ctx: EarnCtx, cfg: AdapterConfig): Promise<FraudSignal | null> {
    const minMinutes = (cfg.params?.['minMinutesToConvert'] as number | undefined) ?? 5;
    const maxConversionRateThreshold =
      (cfg.params?.['maxConversionRatePct'] as number | undefined) ?? 80;
    const conversionWindowDays = (cfg.params?.['conversionWindowDays'] as number | undefined) ?? 7;

    // Time-to-convert: referral bind → first purchase
    const [ref] = await ctx.db
      .select({ createdAt: referrals.createdAt })
      .from(referrals)
      .where(eq(referrals.id, asReferralId(ctx.referralId)))
      .limit(1);

    const [purch] = await ctx.db
      .select({ createdAt: orderLine.createdAt })
      .from(orderLine)
      .where(eq(orderLine.id, ctx.purchaseId))
      .limit(1);

    if (ref?.createdAt && purch?.createdAt) {
      const diffMinutes = (purch.createdAt.getTime() - ref.createdAt.getTime()) / 60_000;
      if (diffMinutes < minMinutes) {
        return {
          adapter: 'velocity-conversion',
          action: 'flag',
          codes: ['FAST_CONVERSION'],
          detail: { diffMinutes: Math.round(diffMinutes), threshold: minMinutes },
        };
      }
    }

    // Per-link conversion-rate anomaly over a SETTLED trailing window.
    // Both clicks and conversions come from referral_link_stats_daily (single population),
    // summed over [CURRENT_DATE - conversionWindowDays, CURRENT_DATE - 1] — settled days only,
    // so the un-rolled-up current day is never read.
    const result = (await ctx.db.execute(sql`
      SELECT
        COALESCE(SUM(ls.clicks), 0)  AS clicks,
        COALESCE(SUM(ls.signups), 0) AS conversions
      FROM referral_links rl
      JOIN referral_link_stats_daily ls ON ls.link_id = rl.id
      WHERE rl.owner_user_id = ${ctx.referrerUserId}
        AND ls.day BETWEEN (CURRENT_DATE - ${conversionWindowDays}::int) AND (CURRENT_DATE - 1)
    `)) as { rows: Array<{ conversions: string; clicks: string }> };

    const row = result.rows[0] as { conversions: string; clicks: string } | undefined;
    if (row && Number(row.clicks) > 0) {
      const rate = (Number(row.conversions) / Number(row.clicks)) * 100;
      if (rate > maxConversionRateThreshold) {
        return {
          adapter: 'velocity-conversion',
          action: 'hold',
          codes: ['HIGH_CONVERSION_RATE'],
          detail: { ratePct: Math.round(rate), threshold: maxConversionRateThreshold },
        };
      }
    }

    return null;
  },
};
