// FIFA's official v3 API (api.fifa.com) — open, no auth, works from the VPS.
// Carries what no other source has officially: confirmed lineups with stable
// player IDs + headshots, typed XY event timelines, attendance, tactics,
// officials. World Cup 2026: IdCompetition=17, IdSeason=285023.
import { cachedFetch } from './fetcher';
import { canonicalTeam } from '../../../src/lib/teams';

const BASE = 'https://api.fifa.com/api/v3';
const SOURCE = 'fifa';
export const FIFA_COMPETITION = '17';
export const FIFA_SEASON = '285023';

const locDesc = (v: unknown): string => {
  const a = v as { Description?: string }[] | undefined;
  return a?.[0]?.Description ?? '';
};

export interface FifaMatchRef {
  idMatch: string;
  idStage: string;
  home: string;
  away: string;
  date: string;
  attendance: number | null;
  officials: unknown[];
  stadium: string;
}

interface RawCalendar {
  Results?: {
    IdMatch?: string;
    IdStage?: string;
    Date?: string;
    Attendance?: string | number | null;
    Officials?: unknown[];
    Stadium?: { Name?: unknown };
    Home?: { TeamName?: unknown };
    Away?: { TeamName?: unknown };
  }[];
}

/** Full tournament calendar window (id map + attendance/officials source). */
export async function fetchFifaCalendar(fromIso: string, toIso: string): Promise<FifaMatchRef[]> {
  const url = `${BASE}/calendar/matches?idCompetition=${FIFA_COMPETITION}&idSeason=${FIFA_SEASON}&from=${encodeURIComponent(fromIso)}&to=${encodeURIComponent(toIso)}&count=120&language=en`;
  const raw = await cachedFetch<RawCalendar>(SOURCE, `fifa:cal:${fromIso.slice(0, 10)}:${toIso.slice(0, 10)}`, url, {
    ttl: 10 * 60_000,
    minInterval: 2_000,
  });
  const out: FifaMatchRef[] = [];
  for (const m of raw.Results ?? []) {
    const home = canonicalTeam(locDesc(m.Home?.TeamName));
    const away = canonicalTeam(locDesc(m.Away?.TeamName));
    if (!m.IdMatch || !m.IdStage || !home || !away) continue;
    out.push({
      idMatch: m.IdMatch,
      idStage: m.IdStage,
      home,
      away,
      date: m.Date ?? '',
      attendance: m.Attendance != null && m.Attendance !== '' ? Number(m.Attendance) : null,
      officials: m.Officials ?? [],
      stadium: locDesc(m.Stadium?.Name),
    });
  }
  return out;
}

/** Rich live payload: confirmed lineups (IdPlayer, shirt numbers, positions),
 *  tactics, match clock. Stored whole — it's the official record. */
export async function fetchFifaLive(idStage: string, idMatch: string, live = false): Promise<unknown> {
  return cachedFetch<unknown>(SOURCE, `fifa:live:${idMatch}`, `${BASE}/live/football/${FIFA_COMPETITION}/${FIFA_SEASON}/${idStage}/${idMatch}?language=en`, {
    ttl: live ? 60_000 : 60 * 60_000,
    minInterval: 2_000,
  });
}

/** Typed event-by-event timeline with pitch coordinates. */
export async function fetchFifaTimeline(idStage: string, idMatch: string, live = false): Promise<unknown> {
  return cachedFetch<unknown>(SOURCE, `fifa:tl:${idMatch}`, `${BASE}/timelines/${FIFA_COMPETITION}/${FIFA_SEASON}/${idStage}/${idMatch}?language=en`, {
    ttl: live ? 60_000 : 60 * 60_000,
    minInterval: 2_000,
  });
}
