dark mode default, basic tournament stats/podium
This commit is contained in:
@@ -19,7 +19,7 @@ interface AuthData {
|
|||||||
|
|
||||||
export const defaultAuthData: AuthData = {
|
export const defaultAuthData: AuthData = {
|
||||||
user: undefined,
|
user: undefined,
|
||||||
metadata: { accentColor: "blue", colorScheme: "auto" },
|
metadata: { accentColor: "blue", colorScheme: "dark" },
|
||||||
roles: [],
|
roles: [],
|
||||||
phone: ""
|
phone: ""
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -1,16 +1,13 @@
|
|||||||
import { Title, AppShell, Flex } from "@mantine/core";
|
import { Title, AppShell, Flex, Box, Paper } from "@mantine/core";
|
||||||
import { HeaderConfig } from "../types/header-config";
|
import { HeaderConfig } from "../types/header-config";
|
||||||
import useRouterConfig from "../hooks/use-router-config";
|
|
||||||
import BackButton from "./back-button";
|
import BackButton from "./back-button";
|
||||||
|
|
||||||
interface HeaderProps extends HeaderConfig {}
|
interface HeaderProps extends HeaderConfig {}
|
||||||
|
|
||||||
const Header = ({ collapsed, title }: HeaderProps) => {
|
const Header = ({ collapsed, title, withBackButton }: HeaderProps) => {
|
||||||
const { header } = useRouterConfig();
|
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<AppShell.Header id='app-header' display={collapsed ? 'none' : 'block'}>
|
<AppShell.Header id='app-header' display={collapsed ? 'none' : 'block'}>
|
||||||
{ header.withBackButton && <BackButton /> }
|
{ withBackButton && <BackButton /> }
|
||||||
<Flex justify='center' align='center' h='100%' px='md'>
|
<Flex justify='center' align='center' h='100%' px='md'>
|
||||||
<Title order={2}>{title}</Title>
|
<Title order={2}>{title}</Title>
|
||||||
</Flex>
|
</Flex>
|
||||||
|
|||||||
@@ -78,8 +78,7 @@ const EmojiBar = ({
|
|||||||
{visibleReactions.map((reaction) => (
|
{visibleReactions.map((reaction) => (
|
||||||
<Button
|
<Button
|
||||||
key={reaction.emoji}
|
key={reaction.emoji}
|
||||||
variant={hasReacted(reaction) ? "filled" : "light"}
|
variant={"light"}
|
||||||
color="gray"
|
|
||||||
bd={hasReacted(reaction) ? "1px solid var(--mantine-primary-color-filled)" : undefined}
|
bd={hasReacted(reaction) ? "1px solid var(--mantine-primary-color-filled)" : undefined}
|
||||||
size="compact-xs"
|
size="compact-xs"
|
||||||
radius="xl"
|
radius="xl"
|
||||||
@@ -109,8 +108,7 @@ const EmojiBar = ({
|
|||||||
|
|
||||||
{hasGrouped && (
|
{hasGrouped && (
|
||||||
<Button
|
<Button
|
||||||
variant={userHasReactedToGrouped ? "filled" : "light"}
|
variant={"light"}
|
||||||
color="gray"
|
|
||||||
bd={userHasReactedToGrouped ? "1px solid var(--mantine-primary-color-filled)" : undefined}
|
bd={userHasReactedToGrouped ? "1px solid var(--mantine-primary-color-filled)" : undefined}
|
||||||
size="compact-xs"
|
size="compact-xs"
|
||||||
radius="xl"
|
radius="xl"
|
||||||
|
|||||||
@@ -1,48 +1,27 @@
|
|||||||
import {
|
import {
|
||||||
Badge,
|
|
||||||
Card,
|
Card,
|
||||||
Text,
|
Text,
|
||||||
Stack,
|
Stack,
|
||||||
Group,
|
Group,
|
||||||
Box,
|
|
||||||
ThemeIcon,
|
|
||||||
UnstyledButton,
|
UnstyledButton,
|
||||||
|
Badge,
|
||||||
} from "@mantine/core";
|
} from "@mantine/core";
|
||||||
import { Tournament } from "@/features/tournaments/types";
|
import { TournamentInfo } from "@/features/tournaments/types";
|
||||||
import { useMemo } from "react";
|
|
||||||
import {
|
import {
|
||||||
TrophyIcon,
|
TrophyIcon,
|
||||||
CalendarIcon,
|
CrownIcon,
|
||||||
MapPinIcon,
|
MedalIcon,
|
||||||
UsersIcon,
|
|
||||||
} from "@phosphor-icons/react";
|
} from "@phosphor-icons/react";
|
||||||
import { useNavigate } from "@tanstack/react-router";
|
import { useNavigate } from "@tanstack/react-router";
|
||||||
import Avatar from "@/components/avatar";
|
import Avatar from "@/components/avatar";
|
||||||
|
|
||||||
interface TournamentCardProps {
|
interface TournamentCardProps {
|
||||||
tournament: Tournament;
|
tournament: TournamentInfo;
|
||||||
}
|
}
|
||||||
|
|
||||||
export const TournamentCard = ({ tournament }: TournamentCardProps) => {
|
export const TournamentCard = ({ tournament }: TournamentCardProps) => {
|
||||||
const navigate = useNavigate();
|
const navigate = useNavigate();
|
||||||
|
|
||||||
const displayDate = useMemo(() => {
|
|
||||||
if (!tournament.start_time) return null;
|
|
||||||
const date = new Date(tournament.start_time);
|
|
||||||
if (isNaN(date.getTime())) return null;
|
|
||||||
return date.toLocaleDateString(undefined, {
|
|
||||||
month: "short",
|
|
||||||
day: "numeric",
|
|
||||||
year: "numeric",
|
|
||||||
});
|
|
||||||
}, [tournament.start_time]);
|
|
||||||
|
|
||||||
const enrollmentDeadline = tournament.enroll_time
|
|
||||||
? new Date(tournament.enroll_time)
|
|
||||||
: new Date(tournament.start_time);
|
|
||||||
const isEnrollmentOpen = enrollmentDeadline > new Date();
|
|
||||||
const enrolledTeamsCount = tournament.teams?.length || 0;
|
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<UnstyledButton
|
<UnstyledButton
|
||||||
w="100%"
|
w="100%"
|
||||||
@@ -93,31 +72,62 @@ export const TournamentCard = ({ tournament }: TournamentCardProps) => {
|
|||||||
<Text fw={600} size="lg" lineClamp={2}>
|
<Text fw={600} size="lg" lineClamp={2}>
|
||||||
{tournament.name}
|
{tournament.name}
|
||||||
</Text>
|
</Text>
|
||||||
{displayDate && (
|
{(tournament.first_place || tournament.second_place || tournament.third_place) && (
|
||||||
<Group gap="xs">
|
<Stack gap={6} >
|
||||||
<ThemeIcon
|
{tournament.first_place && (
|
||||||
size="sm"
|
<Badge
|
||||||
variant="light"
|
size="md"
|
||||||
radius="sm"
|
radius="md"
|
||||||
color="gray"
|
variant="filled"
|
||||||
>
|
color="yellow"
|
||||||
<CalendarIcon size={12} />
|
leftSection={
|
||||||
</ThemeIcon>
|
<CrownIcon size={16} />
|
||||||
<Text size="sm" c="dimmed">
|
}
|
||||||
{displayDate}
|
style={{
|
||||||
</Text>
|
textTransform: 'none',
|
||||||
</Group>
|
fontWeight: 600,
|
||||||
|
color: 'white',
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
{tournament.first_place.name}
|
||||||
|
</Badge>
|
||||||
|
)}
|
||||||
|
{tournament.second_place && (
|
||||||
|
<Badge
|
||||||
|
size="md"
|
||||||
|
radius="md"
|
||||||
|
color="gray"
|
||||||
|
variant="filled"
|
||||||
|
leftSection={
|
||||||
|
<MedalIcon size={16} />
|
||||||
|
}
|
||||||
|
style={{
|
||||||
|
textTransform: 'none',
|
||||||
|
fontWeight: 500,
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
{tournament.second_place.name}
|
||||||
|
</Badge>
|
||||||
|
)}
|
||||||
|
{tournament.third_place && (
|
||||||
|
<Badge
|
||||||
|
size="md"
|
||||||
|
radius="md"
|
||||||
|
color="orange"
|
||||||
|
variant="filled"
|
||||||
|
leftSection={
|
||||||
|
<MedalIcon size={16} />
|
||||||
|
}
|
||||||
|
style={{
|
||||||
|
textTransform: 'none',
|
||||||
|
fontWeight: 500,
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
{tournament.third_place.name}
|
||||||
|
</Badge>
|
||||||
|
)}
|
||||||
|
</Stack>
|
||||||
)}
|
)}
|
||||||
|
|
||||||
<Group gap="xs">
|
|
||||||
<ThemeIcon size="sm" variant="light" radius="sm" color="gray">
|
|
||||||
<UsersIcon size={12} />
|
|
||||||
</ThemeIcon>
|
|
||||||
<Text size="sm" c="dimmed">
|
|
||||||
{enrolledTeamsCount} team
|
|
||||||
{enrolledTeamsCount !== 1 ? "s" : ""}
|
|
||||||
</Text>
|
|
||||||
</Group>
|
|
||||||
</Stack>
|
</Stack>
|
||||||
</Group>
|
</Group>
|
||||||
</Group>
|
</Group>
|
||||||
|
|||||||
@@ -2,6 +2,22 @@ import { TeamInfo } from "@/features/teams/types";
|
|||||||
import { Match } from "@/features/matches/types";
|
import { Match } from "@/features/matches/types";
|
||||||
import { z } from "zod";
|
import { z } from "zod";
|
||||||
|
|
||||||
|
export interface TournamentTeamStats {
|
||||||
|
id: string;
|
||||||
|
team_id: string;
|
||||||
|
tournament_id: string;
|
||||||
|
team_name: string;
|
||||||
|
matches: number;
|
||||||
|
wins: number;
|
||||||
|
losses: number;
|
||||||
|
total_cups_made: number;
|
||||||
|
total_cups_against: number;
|
||||||
|
margin_of_victory: number;
|
||||||
|
margin_of_loss: number;
|
||||||
|
win_percentage: number;
|
||||||
|
avg_cups_per_match: number;
|
||||||
|
}
|
||||||
|
|
||||||
export interface TournamentInfo {
|
export interface TournamentInfo {
|
||||||
id: string;
|
id: string;
|
||||||
name: string;
|
name: string;
|
||||||
@@ -9,6 +25,9 @@ export interface TournamentInfo {
|
|||||||
start_time?: string;
|
start_time?: string;
|
||||||
end_time?: string;
|
end_time?: string;
|
||||||
logo?: string;
|
logo?: string;
|
||||||
|
first_place?: TeamInfo;
|
||||||
|
second_place?: TeamInfo;
|
||||||
|
third_place?: TeamInfo;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface Tournament {
|
export interface Tournament {
|
||||||
@@ -25,6 +44,10 @@ export interface Tournament {
|
|||||||
updated: string;
|
updated: string;
|
||||||
teams?: TeamInfo[];
|
teams?: TeamInfo[];
|
||||||
matches?: Match[];
|
matches?: Match[];
|
||||||
|
first_place?: TeamInfo;
|
||||||
|
second_place?: TeamInfo;
|
||||||
|
third_place?: TeamInfo;
|
||||||
|
team_stats?: TournamentTeamStats[];
|
||||||
}
|
}
|
||||||
|
|
||||||
export const tournamentInputSchema = z.object({
|
export const tournamentInputSchema = z.object({
|
||||||
|
|||||||
@@ -55,7 +55,7 @@ const MantineProvider = ({ children }: { children: React.ReactNode }) => {
|
|||||||
setIsHydrated(true);
|
setIsHydrated(true);
|
||||||
}, []);
|
}, []);
|
||||||
|
|
||||||
const colorScheme = isHydrated ? metadata.colorScheme || "auto" : "auto";
|
const colorScheme = isHydrated ? metadata.colorScheme || "dark" : "dark";
|
||||||
const primaryColor = isHydrated ? metadata.accentColor || "blue" : "blue";
|
const primaryColor = isHydrated ? metadata.accentColor || "blue" : "blue";
|
||||||
|
|
||||||
return (
|
return (
|
||||||
|
|||||||
@@ -9,16 +9,24 @@ import type { Team } from "@/features/teams/types";
|
|||||||
import PocketBase from "pocketbase";
|
import PocketBase from "pocketbase";
|
||||||
import { transformFreeAgent, transformTournament, transformTournamentInfo } from "@/lib/pocketbase/util/transform-types";
|
import { transformFreeAgent, transformTournament, transformTournamentInfo } from "@/lib/pocketbase/util/transform-types";
|
||||||
import { transformTeam } from "@/lib/pocketbase/util/transform-types";
|
import { transformTeam } from "@/lib/pocketbase/util/transform-types";
|
||||||
import { getFreeAgents } from "@/features/tournaments/server";
|
|
||||||
import { PlayerInfo } from "@/features/players/types";
|
import { PlayerInfo } from "@/features/players/types";
|
||||||
|
|
||||||
export function createTournamentsService(pb: PocketBase) {
|
export function createTournamentsService(pb: PocketBase) {
|
||||||
return {
|
return {
|
||||||
async getTournament(id: string, isAdmin: boolean = false): Promise<Tournament> {
|
async getTournament(id: string, isAdmin: boolean = false): Promise<Tournament> {
|
||||||
const result = await pb.collection("tournaments").getOne(id, {
|
const [tournamentResult, teamStatsResult] = await Promise.all([
|
||||||
expand: "teams, teams.players, matches, matches.tournament, matches.home, matches.away, matches.home.players, matches.away.players",
|
pb.collection("tournaments").getOne(id, {
|
||||||
});
|
expand: "teams, teams.players, matches, matches.tournament, matches.home, matches.away, matches.home.players, matches.away.players",
|
||||||
return transformTournament(result, isAdmin);
|
}),
|
||||||
|
pb.collection("team_stats_per_tournament").getFullList({
|
||||||
|
filter: `tournament_id = "${id}"`,
|
||||||
|
sort: "-wins,-total_cups_made"
|
||||||
|
})
|
||||||
|
]);
|
||||||
|
|
||||||
|
tournamentResult.team_stats = teamStatsResult;
|
||||||
|
|
||||||
|
return transformTournament(tournamentResult, isAdmin);
|
||||||
},
|
},
|
||||||
async getMostRecentTournament(): Promise<Tournament> {
|
async getMostRecentTournament(): Promise<Tournament> {
|
||||||
const result = await pb
|
const result = await pb
|
||||||
@@ -29,17 +37,35 @@ export function createTournamentsService(pb: PocketBase) {
|
|||||||
sort: "-created",
|
sort: "-created",
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
|
|
||||||
|
const teamStatsResult = await pb.collection("team_stats_per_tournament").getFullList({
|
||||||
|
filter: `tournament_id = "${result.id}"`,
|
||||||
|
sort: "-wins,-total_cups_made"
|
||||||
|
});
|
||||||
|
|
||||||
|
result.team_stats = teamStatsResult;
|
||||||
|
|
||||||
return transformTournament(result);
|
return transformTournament(result);
|
||||||
},
|
},
|
||||||
async listTournaments(): Promise<TournamentInfo[]> {
|
async listTournaments(): Promise<TournamentInfo[]> {
|
||||||
const result = await pb
|
const result = await pb
|
||||||
.collection("tournaments")
|
.collection("tournaments")
|
||||||
.getFullList({
|
.getFullList({
|
||||||
fields: "id,name,location,start_time,end_time,logo",
|
expand: "teams,teams.players,matches",
|
||||||
sort: "-created",
|
sort: "-created",
|
||||||
});
|
});
|
||||||
|
|
||||||
return result.map(transformTournamentInfo);
|
const tournamentsWithStats = await Promise.all(result.map(async (tournament) => {
|
||||||
|
const teamStats = await pb.collection("team_stats_per_tournament").getFullList({
|
||||||
|
filter: `tournament_id = "${tournament.id}"`,
|
||||||
|
sort: "-wins,-total_cups_made"
|
||||||
|
});
|
||||||
|
|
||||||
|
tournament.team_stats = teamStats;
|
||||||
|
return tournament;
|
||||||
|
}));
|
||||||
|
|
||||||
|
return tournamentsWithStats.map(transformTournamentInfo);
|
||||||
},
|
},
|
||||||
async createTournament(data: TournamentInput): Promise<Tournament> {
|
async createTournament(data: TournamentInput): Promise<Tournament> {
|
||||||
const result = await pb
|
const result = await pb
|
||||||
|
|||||||
@@ -57,12 +57,58 @@ export const transformMatch = (record: any, isAdmin: boolean = false): Match =>
|
|||||||
}
|
}
|
||||||
|
|
||||||
export const transformTournamentInfo = (record: any): TournamentInfo => {
|
export const transformTournamentInfo = (record: any): TournamentInfo => {
|
||||||
|
// Check if tournament is complete by looking at matches
|
||||||
|
const matches = record.expand?.matches || [];
|
||||||
|
// Filter out bye matches (tbd status with bye=true) when checking completion
|
||||||
|
const nonByeMatches = matches.filter((match: any) => !(match.status === 'tbd' && match.bye === true));
|
||||||
|
const isComplete = nonByeMatches.length > 0 && nonByeMatches.every((match: any) => match.status === 'ended');
|
||||||
|
|
||||||
|
let first_place: TeamInfo | undefined = undefined;
|
||||||
|
let second_place: TeamInfo | undefined = undefined;
|
||||||
|
let third_place: TeamInfo | undefined = undefined;
|
||||||
|
|
||||||
|
if (isComplete) {
|
||||||
|
const teams = record.expand?.teams || [];
|
||||||
|
const teamMap = new Map<string, TeamInfo>(teams.map((team: any) => [team.id, transformTeamInfo(team)]));
|
||||||
|
|
||||||
|
const winnersMatches = matches.filter((match: any) => !match.is_losers_bracket);
|
||||||
|
const finalsMatch = winnersMatches.reduce((highest: any, current: any) =>
|
||||||
|
(!highest || current.lid > highest.lid) ? current : highest, null);
|
||||||
|
|
||||||
|
const losersMatches = matches.filter((match: any) => match.is_losers_bracket);
|
||||||
|
const losersFinale = losersMatches.reduce((highest: any, current: any) =>
|
||||||
|
(!highest || current.lid > highest.lid) ? current : highest, null);
|
||||||
|
|
||||||
|
if (finalsMatch && finalsMatch.status === 'ended') {
|
||||||
|
const finalsWinner = (finalsMatch.home_cups > finalsMatch.away_cups) ? finalsMatch.home : finalsMatch.away;
|
||||||
|
const finalsLoser = (finalsMatch.home_cups > finalsMatch.away_cups) ? finalsMatch.away : finalsMatch.home;
|
||||||
|
|
||||||
|
const finalsWinnerId = typeof finalsWinner === 'string' ? finalsWinner : finalsWinner?.id;
|
||||||
|
const finalsLoserId = typeof finalsLoser === 'string' ? finalsLoser : finalsLoser?.id;
|
||||||
|
|
||||||
|
first_place = finalsWinnerId ? teamMap.get(finalsWinnerId) || undefined : undefined;
|
||||||
|
second_place = finalsLoserId ? teamMap.get(finalsLoserId) || undefined : undefined;
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
if (losersFinale && losersFinale.status === 'ended') {
|
||||||
|
const losersFinaleLoser = (losersFinale.home_cups > losersFinale.away_cups) ? losersFinale.away : losersFinale.home;
|
||||||
|
|
||||||
|
const losersFinaleloserId = typeof losersFinaleLoser === 'string' ? losersFinaleLoser : losersFinaleLoser?.id;
|
||||||
|
third_place = losersFinaleloserId ? teamMap.get(losersFinaleloserId) || undefined : undefined;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return {
|
return {
|
||||||
id: record.id,
|
id: record.id,
|
||||||
name: record.name,
|
name: record.name,
|
||||||
location: record.location,
|
location: record.location,
|
||||||
start_time: record.start_time,
|
start_time: record.start_time,
|
||||||
|
end_time: record.end_time,
|
||||||
logo: record.logo,
|
logo: record.logo,
|
||||||
|
first_place,
|
||||||
|
second_place,
|
||||||
|
third_place,
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -150,6 +196,59 @@ export function transformTournament(record: any, isAdmin: boolean = false): Tour
|
|||||||
)
|
)
|
||||||
?.map((match: any) => transformMatch(match, isAdmin)) ?? [];
|
?.map((match: any) => transformMatch(match, isAdmin)) ?? [];
|
||||||
|
|
||||||
|
const team_stats = record.team_stats?.map((stat: any) => ({
|
||||||
|
id: stat.id,
|
||||||
|
team_id: stat.team_id,
|
||||||
|
tournament_id: stat.tournament_id,
|
||||||
|
team_name: stat.team_name,
|
||||||
|
matches: stat.matches,
|
||||||
|
wins: stat.wins,
|
||||||
|
losses: stat.losses,
|
||||||
|
total_cups_made: stat.total_cups_made,
|
||||||
|
total_cups_against: stat.total_cups_against,
|
||||||
|
margin_of_victory: stat.margin_of_victory,
|
||||||
|
margin_of_loss: stat.margin_of_loss,
|
||||||
|
win_percentage: (stat.wins / stat.matches) * 100,
|
||||||
|
avg_cups_per_match: stat.total_cups_made / stat.matches,
|
||||||
|
})) ?? [];
|
||||||
|
|
||||||
|
const nonByeMatches = matches.filter((match: any) => !(match.status === 'tbd' && match.bye === true));
|
||||||
|
const isComplete = nonByeMatches.length > 0 && nonByeMatches.every((match: any) => match.status === 'ended');
|
||||||
|
|
||||||
|
let first_place: TeamInfo | undefined = undefined;
|
||||||
|
let second_place: TeamInfo | undefined = undefined;
|
||||||
|
let third_place: TeamInfo | undefined = undefined;
|
||||||
|
|
||||||
|
if (isComplete) {
|
||||||
|
const teamMap = new Map<string, TeamInfo>(teams.map((team: any) => [team.id, team]));
|
||||||
|
|
||||||
|
const winnersMatches = matches.filter((match: any) => !match.is_losers_bracket);
|
||||||
|
const finalsMatch = winnersMatches.reduce((highest: any, current: any) =>
|
||||||
|
(!highest || current.lid > highest.lid) ? current : highest, null);
|
||||||
|
|
||||||
|
const losersMatches = matches.filter((match: any) => match.is_losers_bracket);
|
||||||
|
const losersFinale = losersMatches.reduce((highest: any, current: any) =>
|
||||||
|
(!highest || current.lid > highest.lid) ? current : highest, null);
|
||||||
|
|
||||||
|
if (finalsMatch && finalsMatch.status === 'ended') {
|
||||||
|
const finalsWinner = (finalsMatch.home_cups > finalsMatch.away_cups) ? finalsMatch.home : finalsMatch.away;
|
||||||
|
const finalsLoser = (finalsMatch.home_cups > finalsMatch.away_cups) ? finalsMatch.away : finalsMatch.home;
|
||||||
|
|
||||||
|
const finalsWinnerId = typeof finalsWinner === 'string' ? finalsWinner : finalsWinner?.id;
|
||||||
|
const finalsLoserId = typeof finalsLoser === 'string' ? finalsLoser : finalsLoser?.id;
|
||||||
|
|
||||||
|
first_place = finalsWinnerId ? teamMap.get(finalsWinnerId) || undefined : undefined;
|
||||||
|
second_place = finalsLoserId ? teamMap.get(finalsLoserId) || undefined : undefined;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (losersFinale && losersFinale.status === 'ended') {
|
||||||
|
const losersFinaleLoser = (losersFinale.home_cups > losersFinale.away_cups) ? losersFinale.away : losersFinale.home;
|
||||||
|
|
||||||
|
const losersFinaleloserId = typeof losersFinaleLoser === 'string' ? losersFinaleLoser : losersFinaleLoser?.id;
|
||||||
|
third_place = losersFinaleloserId ? teamMap.get(losersFinaleloserId) || undefined : undefined;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return {
|
return {
|
||||||
id: record.id,
|
id: record.id,
|
||||||
name: record.name,
|
name: record.name,
|
||||||
@@ -163,7 +262,11 @@ export function transformTournament(record: any, isAdmin: boolean = false): Tour
|
|||||||
created: record.created,
|
created: record.created,
|
||||||
updated: record.updated,
|
updated: record.updated,
|
||||||
teams,
|
teams,
|
||||||
matches
|
matches,
|
||||||
|
first_place,
|
||||||
|
second_place,
|
||||||
|
third_place,
|
||||||
|
team_stats,
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user