Files
gridpilot.gg/apps/website/lib/builders/view-data/LeagueStandingsViewDataBuilder.ts
2026-01-14 13:27:26 +01:00

75 lines
2.5 KiB
TypeScript

import type { LeagueStandingsViewData, StandingEntryData, DriverData, LeagueMembershipData } from '@/lib/view-data/LeagueStandingsViewData';
import type { LeagueStandingDTO } from '@/lib/types/generated/LeagueStandingDTO';
import type { LeagueMemberDTO } from '@/lib/types/generated/LeagueMemberDTO';
interface LeagueStandingsApiDto {
standings: LeagueStandingDTO[];
}
interface LeagueMembershipsApiDto {
members: LeagueMemberDTO[];
}
/**
* LeagueStandingsViewDataBuilder
*
* Transforms API DTOs into LeagueStandingsViewData for server-side rendering.
* Deterministic; side-effect free; no HTTP calls.
*/
export class LeagueStandingsViewDataBuilder {
static build(
standingsDto: LeagueStandingsApiDto,
membershipsDto: LeagueMembershipsApiDto,
leagueId: string
): LeagueStandingsViewData {
const standings = standingsDto.standings || [];
const members = membershipsDto.members || [];
// Convert LeagueStandingDTO to StandingEntryData
const standingData: StandingEntryData[] = standings.map(standing => ({
driverId: standing.driverId,
position: standing.position,
totalPoints: standing.points,
racesFinished: standing.races,
racesStarted: standing.races,
avgFinish: null, // Not in DTO
penaltyPoints: 0, // Not in DTO
bonusPoints: 0, // Not in DTO
}));
// Extract unique drivers from standings
const driverMap = new Map<string, DriverData>();
standings.forEach(standing => {
if (standing.driver && !driverMap.has(standing.driver.id)) {
const driver = standing.driver;
driverMap.set(driver.id, {
id: driver.id,
name: driver.name,
avatarUrl: null, // DTO may not have this
iracingId: driver.iracingId,
rating: undefined,
country: driver.country,
});
}
});
const driverData: DriverData[] = Array.from(driverMap.values());
// Convert LeagueMemberDTO to LeagueMembershipData
const membershipData: LeagueMembershipData[] = members.map(member => ({
driverId: member.driverId,
leagueId: leagueId,
role: (member.role as LeagueMembershipData['role']) || 'member',
joinedAt: member.joinedAt,
status: 'active' as const,
}));
return {
standings: standingData,
drivers: driverData,
memberships: membershipData,
leagueId,
currentDriverId: null, // Would need to get from auth
isAdmin: false, // Would need to check permissions
};
}
}