import type { WizardCar, WizardInput, CarFilters, Car } from "@/lib/types";
import { primaryCarField } from "@/lib/carFieldUtils";

const MAX_RAW_SCORE = 110;

/** Mirror backend rule-based scoring (car_wizard._score), normalized to 0–100. */
export function computeWizardMatchScore(
  car: WizardCar,
  budgetMin: number,
  budgetMax: number,
  fuelTypes: string[],
  bodyTypes: string[],
  familySize: number,
): number {
  let score = 0;
  const budgetMid = (budgetMin + budgetMax) / 2;
  const price = car.priceMin ?? 0;

  if (budgetMid > 0) {
    const pctDiff = Math.abs(price - budgetMid) / budgetMid;
    score += Math.max(0, 40 - pctDiff * 40);
  }

  score += ((car.rating ?? 0) / 5) * 20;

  const fuel = primaryCarField(car.fuelType).toLowerCase();
  if (!fuelTypes.length || fuelTypes.some((f) => f.toLowerCase() === fuel)) {
    score += 20;
  }

  const body = primaryCarField(car.bodyType).toLowerCase();
  if (!bodyTypes.length || bodyTypes.some((b) => b.toLowerCase() === body)) {
    score += 15;
  }

  const seating = car.specs?.seatingCapacity ?? 5;
  if (familySize <= 2) {
    score += 10;
  } else if (familySize <= 4) {
    score += seating >= 4 ? 15 : 5;
  } else if (familySize <= 6) {
    score += seating >= 5 ? 15 : 0;
  } else {
    score += seating >= 7 ? 15 : 0;
  }

  return Math.min(100, Math.round((score / MAX_RAW_SCORE) * 100));
}

export type MatchScoreTier = "excellent" | "good" | "fair" | "low";

export function getMatchScoreTier(score: number): MatchScoreTier {
  if (score >= 90) return "excellent";
  if (score >= 75) return "good";
  if (score >= 60) return "fair";
  return "low";
}

export const MATCH_SCORE_STYLES: Record<
  MatchScoreTier,
  { bar: string; text: string; bg: string }
> = {
  excellent: { bar: "bg-emerald-500", text: "text-emerald-700", bg: "bg-emerald-50" },
  good:      { bar: "bg-blue-500",    text: "text-blue-700",    bg: "bg-blue-50" },
  fair:      { bar: "bg-orange-500",  text: "text-orange-700",  bg: "bg-orange-50" },
  low:       { bar: "bg-gray-400",    text: "text-gray-600",    bg: "bg-gray-50" },
};

export function deriveMatchReasons(
  car: WizardCar,
  budgetMin: number,
  budgetMax: number,
  fuelTypes: string[],
  bodyTypes: string[],
  familySize: number,
): string[] {
  const reasons: string[] = [];
  const price = car.priceMin ?? 0;

  if (price >= budgetMin * 0.85 && price <= budgetMax * 1.05) {
    reasons.push("Fits your budget");
  }

  const fuel = primaryCarField(car.fuelType).toLowerCase();
  if (!fuelTypes.length || fuelTypes.some((f) => f.toLowerCase() === fuel)) {
    reasons.push("Matches preferred fuel type");
  }

  const body = primaryCarField(car.bodyType).toLowerCase();
  if (!bodyTypes.length || bodyTypes.some((b) => b.toLowerCase() === body)) {
    reasons.push(`Ideal ${car.bodyType || "body"} for your needs`);
  }

  const seating = car.specs?.seatingCapacity ?? 5;
  if (familySize <= 2) {
    reasons.push("Compact and easy to drive");
  } else if (familySize <= 4 && seating >= 4) {
    reasons.push("Suitable for family size");
  } else if (familySize <= 6 && seating >= 5) {
    reasons.push("Suitable for family size");
  } else if (familySize >= 7 && seating >= 7) {
    reasons.push("Suitable for family size");
  }

  if ((car.rating ?? 0) >= 4.0) {
    reasons.push("High safety rating");
  } else if ((car.specs?.airbags ?? 0) >= 6) {
    reasons.push("Strong passive safety");
  }

  return reasons.slice(0, 4);
}

export function carToWizardCar(car: {
  id: string;
  name: string;
  brand: string;
  model?: string;
  priceMin: number;
  priceMax: number;
  fuelType: string;
  bodyType: string;
  transmission?: string;
  slug?: string;
  rating?: number;
  reviewCount?: number;
  primaryImage?: string | null;
  imageGallery?: WizardCar["imageGallery"];
  imageUrl?: string;
  images?: { url: string; isPrimary?: boolean }[];
  specs?: WizardCar["specs"];
}): WizardCar {
  return {
    id: car.id,
    name: car.name,
    brand: car.brand,
    model: car.model,
    priceMin: car.priceMin,
    priceMax: car.priceMax,
    fuelType: car.fuelType,
    bodyType: car.bodyType,
    transmission: car.transmission,
    slug: car.slug,
    rating: car.rating,
    reviewCount: car.reviewCount,
    primaryImage: car.primaryImage,
    imageGallery: car.imageGallery,
    imageUrl: car.imageUrl,
    specs: car.specs,
  };
}

export async function buildFallbackMatches(
  input: WizardInput,
  fetchCarsFn: (filters: CarFilters) => Promise<{ cars: Car[] }>,
): Promise<{ car: WizardCar; reason: string; pros: string[]; cons: string[] }[]> {
  const attempts: CarFilters[] = [
    {
      priceMin: input.budgetMin * 0.7,
      priceMax: input.budgetMax * 1.3,
      fuelType: input.fuelTypes.length ? input.fuelTypes : undefined,
      bodyType: input.bodyTypes.length ? input.bodyTypes : undefined,
      seating: input.familySize >= 7 ? 7 : input.familySize >= 5 ? 5 : undefined,
      limit: 12,
      sortBy: "rating",
    },
    {
      priceMin: input.budgetMin * 0.5,
      priceMax: input.budgetMax * 1.5,
      limit: 12,
      sortBy: "rating",
    },
    { limit: 12, sortBy: "rating" },
  ];

  for (const filters of attempts) {
    const { cars } = await fetchCarsFn(filters);
    if (!cars.length) continue;

    const scored = cars
      .map((c) => {
        const wc = carToWizardCar(c);
        return {
          car: wc,
          score: computeWizardMatchScore(
            wc,
            input.budgetMin,
            input.budgetMax,
            input.fuelTypes,
            input.bodyTypes,
            input.familySize,
          ),
        };
      })
      .sort((a, b) => b.score - a.score)
      .slice(0, 6);

    return scored.map(({ car, score }) => ({
      car,
      reason: `Nearest match at ${score}% based on your preferences.`,
      pros: deriveMatchReasons(
        car,
        input.budgetMin,
        input.budgetMax,
        input.fuelTypes,
        input.bodyTypes,
        input.familySize,
      ),
      cons: [],
    }));
  }

  return [];
}
