Files
wm-projekt/lib/types.ts
2026-07-01 16:40:51 -05:00

86 lines
2.8 KiB
TypeScript

// Datenmodell für die WM-Seite. Bewusst entkoppelt von den Feed-Formaten:
// Adapter (siehe lib/feeds.ts) übersetzen FIFA & Polymarket in diese Typen.
export type GroupId =
| "A" | "B" | "C" | "D" | "E" | "F"
| "G" | "H" | "I" | "J" | "K" | "L";
export const GROUP_IDS: GroupId[] = [
"A", "B", "C", "D", "E", "F", "G", "H", "I", "J", "K", "L",
];
export interface Team {
id: string; // stabile ID aus dem Feed
name: string; // Originalname aus dem Feed (englisch)
code: string; // 3-Buchstaben-Code, z.B. GER
group: GroupId;
crest?: string | null; // URL zur Flagge / zum Wappen (veraltet)
localisedName: string; // Lokalisierter Anzeigename (z.B. "Deutschland")
localisedNames?: { de: string; en: string };
}
export function teamName(team: Team | undefined, locale: string): string {
if (!team) return "—";
if (locale === "en") return team.localisedNames?.en ?? team.name ?? "—";
return team.localisedNames?.de ?? team.name ?? "—";
}
export type MatchStatus =
| "SCHEDULED" | "LIVE" | "IN_PLAY" | "PAUSED" | "FINISHED" | "POSTPONED";
export interface GoalEvent {
scorer: string; // Torschützen-Name
minute: string; // Spielminute (z.B. "72", "90+1")
team: "home" | "away";
}
export interface Match {
id: string;
group: GroupId | null; // null = K.o.-Spiel
stage: "GROUP" | "R32" | "R16" | "QF" | "SF" | "3RD" | "FINAL";
matchNumber: number; // FIFA-Spielnummer (1..104)
utcDate: string;
status: MatchStatus;
minute: number | null;
homeTeamId: string | null;
awayTeamId: string | null;
homeScore: number | null;
awayScore: number | null;
homePenalty?: number | null; // Elfmeterschießen (FIFA-API)
awayPenalty?: number | null;
winnerTeamId?: string | null; // FIFA-Winner (auch bei Elfmeterschießen)
// Wahrscheinlichkeiten 0..1 (Polymarket), falls vorhanden
prob?: { home: number; draw: number; away: number } | null;
venue?: string | null; // Austragungsort (veraltet)
stadiumName?: string | null; // FIFA-Stadionname
stadiumCity?: string | null; // FIFA-Stadt
attendance?: number | null; // Zuschauerzahl
goals?: GoalEvent[] | null; // Torereignisse
}
// Eine berechnete Tabellenzeile innerhalb einer Gruppe.
export interface StandingRow {
teamId: string;
played: number;
won: number;
drawn: number;
lost: number;
goalsFor: number;
goalsAgainst: number;
goalDiff: number;
points: number;
rank: number; // 1..4 innerhalb der Gruppe
}
export interface GroupTable {
group: GroupId;
rows: StandingRow[]; // sortiert, rank gesetzt
}
// Eintrag in der gruppenübergreifenden Drittplatzierten-Tabelle.
export interface ThirdPlaceRow extends StandingRow {
group: GroupId;
qualifies: boolean; // true für die besten 8
overallRank: number; // 1..12
}