resolve manual DTOs
This commit is contained in:
@@ -9,6 +9,8 @@ import { CompleteOnboardingOutputDTO } from './dtos/CompleteOnboardingOutputDTO'
|
||||
import { GetDriverRegistrationStatusQueryDTO } from './dtos/GetDriverRegistrationStatusQueryDTO';
|
||||
import { DriverRegistrationStatusDTO } from './dtos/DriverRegistrationStatusDTO';
|
||||
import { DriverDTO } from './dtos/DriverDTO';
|
||||
import { GetDriverOutputDTO } from './dtos/GetDriverOutputDTO';
|
||||
import { GetDriverProfileOutputDTO } from './dtos/GetDriverProfileOutputDTO';
|
||||
|
||||
@ApiTags('drivers')
|
||||
@Controller('drivers')
|
||||
@@ -31,9 +33,9 @@ export class DriverController {
|
||||
|
||||
@Get('current')
|
||||
@ApiOperation({ summary: 'Get current authenticated driver' })
|
||||
@ApiResponse({ status: 200, description: 'Current driver data', type: DriverDTO })
|
||||
@ApiResponse({ status: 200, description: 'Current driver data', type: GetDriverOutputDTO })
|
||||
@ApiResponse({ status: 404, description: 'Driver not found' })
|
||||
async getCurrentDriver(@Req() req: Request): Promise<DriverDTO | null> {
|
||||
async getCurrentDriver(@Req() req: Request): Promise<GetDriverOutputDTO | null> {
|
||||
// Assuming userId is available from the request (e.g., via auth middleware)
|
||||
const userId = req['user']?.userId;
|
||||
if (!userId) {
|
||||
@@ -64,13 +66,29 @@ export class DriverController {
|
||||
return this.driverService.getDriverRegistrationStatus({ driverId, raceId });
|
||||
}
|
||||
|
||||
@Get(':driverId')
|
||||
@ApiOperation({ summary: 'Get driver by ID' })
|
||||
@ApiResponse({ status: 200, description: 'Driver data', type: GetDriverOutputDTO })
|
||||
@ApiResponse({ status: 404, description: 'Driver not found' })
|
||||
async getDriver(@Param('driverId') driverId: string): Promise<GetDriverOutputDTO | null> {
|
||||
return this.driverService.getDriver(driverId);
|
||||
}
|
||||
|
||||
@Get(':driverId/profile')
|
||||
@ApiOperation({ summary: 'Get driver profile with full details' })
|
||||
@ApiResponse({ status: 200, description: 'Driver profile data', type: GetDriverProfileOutputDTO })
|
||||
@ApiResponse({ status: 404, description: 'Driver not found' })
|
||||
async getDriverProfile(@Param('driverId') driverId: string): Promise<GetDriverProfileOutputDTO> {
|
||||
return this.driverService.getDriverProfile(driverId);
|
||||
}
|
||||
|
||||
@Put(':driverId/profile')
|
||||
@ApiOperation({ summary: 'Update driver profile' })
|
||||
@ApiResponse({ status: 200, description: 'Driver profile updated', type: DriverDTO })
|
||||
@ApiResponse({ status: 200, description: 'Driver profile updated', type: GetDriverOutputDTO })
|
||||
async updateDriverProfile(
|
||||
@Param('driverId') driverId: string,
|
||||
@Body() body: { bio?: string; country?: string },
|
||||
): Promise<DriverDTO | null> {
|
||||
): Promise<GetDriverOutputDTO | null> {
|
||||
return this.driverService.updateDriverProfile(driverId, body.bio, body.country);
|
||||
}
|
||||
|
||||
|
||||
@@ -5,6 +5,8 @@ import { CompleteOnboardingInputDTO } from './dtos/CompleteOnboardingInputDTO';
|
||||
import { CompleteOnboardingOutputDTO } from './dtos/CompleteOnboardingOutputDTO';
|
||||
import { GetDriverRegistrationStatusQueryDTO } from './dtos/GetDriverRegistrationStatusQueryDTO';
|
||||
import { DriverRegistrationStatusDTO } from './dtos/DriverRegistrationStatusDTO';
|
||||
import { GetDriverOutputDTO } from './dtos/GetDriverOutputDTO';
|
||||
import { GetDriverProfileOutputDTO } from './dtos/GetDriverProfileOutputDTO';
|
||||
|
||||
// Use cases
|
||||
import { GetDriversLeaderboardUseCase } from '@core/racing/application/use-cases/GetDriversLeaderboardUseCase';
|
||||
@@ -76,7 +78,7 @@ export class DriverService {
|
||||
return presenter.viewModel;
|
||||
}
|
||||
|
||||
async getCurrentDriver(userId: string): Promise<DriverDTO | null> {
|
||||
async getCurrentDriver(userId: string): Promise<GetDriverOutputDTO | null> {
|
||||
this.logger.debug(`[DriverService] Fetching current driver for userId: ${userId}`);
|
||||
|
||||
const driver = await this.driverRepository.findById(userId);
|
||||
@@ -86,11 +88,15 @@ export class DriverService {
|
||||
|
||||
return {
|
||||
id: driver.id,
|
||||
iracingId: driver.iracingId.value,
|
||||
name: driver.name.value,
|
||||
country: driver.country.value,
|
||||
bio: driver.bio?.value,
|
||||
joinedAt: driver.joinedAt.toISOString(),
|
||||
};
|
||||
}
|
||||
|
||||
async updateDriverProfile(driverId: string, bio?: string, country?: string): Promise<DriverDTO | null> {
|
||||
async updateDriverProfile(driverId: string, bio?: string, country?: string): Promise<GetDriverOutputDTO | null> {
|
||||
this.logger.debug(`[DriverService] Updating driver profile for driverId: ${driverId}`);
|
||||
|
||||
const result = await this.updateDriverProfileUseCase.execute({ driverId, bio, country });
|
||||
@@ -101,4 +107,40 @@ export class DriverService {
|
||||
|
||||
return result.value;
|
||||
}
|
||||
|
||||
async getDriver(driverId: string): Promise<GetDriverOutputDTO | null> {
|
||||
this.logger.debug(`[DriverService] Fetching driver for driverId: ${driverId}`);
|
||||
|
||||
const driver = await this.driverRepository.findById(driverId);
|
||||
if (!driver) {
|
||||
return null;
|
||||
}
|
||||
|
||||
return {
|
||||
id: driver.id,
|
||||
iracingId: driver.iracingId.value,
|
||||
name: driver.name.value,
|
||||
country: driver.country.value,
|
||||
bio: driver.bio?.value,
|
||||
joinedAt: driver.joinedAt.toISOString(),
|
||||
};
|
||||
}
|
||||
|
||||
async getDriverProfile(driverId: string): Promise<GetDriverProfileOutputDTO> {
|
||||
this.logger.debug(`[DriverService] Fetching driver profile for driverId: ${driverId}`);
|
||||
|
||||
// TODO: Implement proper driver profile fetching with all the detailed data
|
||||
// For now, return a placeholder structure
|
||||
return {
|
||||
currentDriver: null,
|
||||
stats: null,
|
||||
finishDistribution: null,
|
||||
teamMemberships: [],
|
||||
socialSummary: {
|
||||
friendsCount: 0,
|
||||
friends: [],
|
||||
},
|
||||
extendedProfile: null,
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
21
apps/api/src/domain/driver/dtos/DriverDTO.ts
Normal file
21
apps/api/src/domain/driver/dtos/DriverDTO.ts
Normal file
@@ -0,0 +1,21 @@
|
||||
import { ApiProperty } from '@nestjs/swagger';
|
||||
|
||||
export class DriverDTO {
|
||||
@ApiProperty()
|
||||
id: string;
|
||||
|
||||
@ApiProperty()
|
||||
iracingId: string;
|
||||
|
||||
@ApiProperty()
|
||||
name: string;
|
||||
|
||||
@ApiProperty()
|
||||
country: string;
|
||||
|
||||
@ApiProperty({ required: false })
|
||||
bio?: string;
|
||||
|
||||
@ApiProperty()
|
||||
joinedAt: string;
|
||||
}
|
||||
21
apps/api/src/domain/driver/dtos/GetDriverOutputDTO.ts
Normal file
21
apps/api/src/domain/driver/dtos/GetDriverOutputDTO.ts
Normal file
@@ -0,0 +1,21 @@
|
||||
import { ApiProperty } from '@nestjs/swagger';
|
||||
|
||||
export class GetDriverOutputDTO {
|
||||
@ApiProperty()
|
||||
id: string;
|
||||
|
||||
@ApiProperty()
|
||||
iracingId: string;
|
||||
|
||||
@ApiProperty()
|
||||
name: string;
|
||||
|
||||
@ApiProperty()
|
||||
country: string;
|
||||
|
||||
@ApiProperty()
|
||||
bio?: string;
|
||||
|
||||
@ApiProperty()
|
||||
joinedAt: string;
|
||||
}
|
||||
226
apps/api/src/domain/driver/dtos/GetDriverProfileOutputDTO.ts
Normal file
226
apps/api/src/domain/driver/dtos/GetDriverProfileOutputDTO.ts
Normal file
@@ -0,0 +1,226 @@
|
||||
import { ApiProperty } from '@nestjs/swagger';
|
||||
|
||||
export class DriverProfileDriverSummaryDTO {
|
||||
@ApiProperty()
|
||||
id: string;
|
||||
|
||||
@ApiProperty()
|
||||
name: string;
|
||||
|
||||
@ApiProperty()
|
||||
country: string;
|
||||
|
||||
@ApiProperty()
|
||||
avatarUrl: string;
|
||||
|
||||
@ApiProperty({ nullable: true })
|
||||
iracingId: string | null;
|
||||
|
||||
@ApiProperty()
|
||||
joinedAt: string;
|
||||
|
||||
@ApiProperty({ nullable: true })
|
||||
rating: number | null;
|
||||
|
||||
@ApiProperty({ nullable: true })
|
||||
globalRank: number | null;
|
||||
|
||||
@ApiProperty({ nullable: true })
|
||||
consistency: number | null;
|
||||
|
||||
@ApiProperty({ nullable: true })
|
||||
bio: string | null;
|
||||
|
||||
@ApiProperty({ nullable: true })
|
||||
totalDrivers: number | null;
|
||||
}
|
||||
|
||||
export class DriverProfileStatsDTO {
|
||||
@ApiProperty()
|
||||
totalRaces: number;
|
||||
|
||||
@ApiProperty()
|
||||
wins: number;
|
||||
|
||||
@ApiProperty()
|
||||
podiums: number;
|
||||
|
||||
@ApiProperty()
|
||||
dnfs: number;
|
||||
|
||||
@ApiProperty({ nullable: true })
|
||||
avgFinish: number | null;
|
||||
|
||||
@ApiProperty({ nullable: true })
|
||||
bestFinish: number | null;
|
||||
|
||||
@ApiProperty({ nullable: true })
|
||||
worstFinish: number | null;
|
||||
|
||||
@ApiProperty({ nullable: true })
|
||||
finishRate: number | null;
|
||||
|
||||
@ApiProperty({ nullable: true })
|
||||
winRate: number | null;
|
||||
|
||||
@ApiProperty({ nullable: true })
|
||||
podiumRate: number | null;
|
||||
|
||||
@ApiProperty({ nullable: true })
|
||||
percentile: number | null;
|
||||
|
||||
@ApiProperty({ nullable: true })
|
||||
rating: number | null;
|
||||
|
||||
@ApiProperty({ nullable: true })
|
||||
consistency: number | null;
|
||||
|
||||
@ApiProperty({ nullable: true })
|
||||
overallRank: number | null;
|
||||
}
|
||||
|
||||
export class DriverProfileFinishDistributionDTO {
|
||||
@ApiProperty()
|
||||
totalRaces: number;
|
||||
|
||||
@ApiProperty()
|
||||
wins: number;
|
||||
|
||||
@ApiProperty()
|
||||
podiums: number;
|
||||
|
||||
@ApiProperty()
|
||||
topTen: number;
|
||||
|
||||
@ApiProperty()
|
||||
dnfs: number;
|
||||
|
||||
@ApiProperty()
|
||||
other: number;
|
||||
}
|
||||
|
||||
export class DriverProfileTeamMembershipDTO {
|
||||
@ApiProperty()
|
||||
teamId: string;
|
||||
|
||||
@ApiProperty()
|
||||
teamName: string;
|
||||
|
||||
@ApiProperty({ nullable: true })
|
||||
teamTag: string | null;
|
||||
|
||||
@ApiProperty()
|
||||
role: string;
|
||||
|
||||
@ApiProperty()
|
||||
joinedAt: string;
|
||||
|
||||
@ApiProperty()
|
||||
isCurrent: boolean;
|
||||
}
|
||||
|
||||
export class DriverProfileSocialFriendSummaryDTO {
|
||||
@ApiProperty()
|
||||
id: string;
|
||||
|
||||
@ApiProperty()
|
||||
name: string;
|
||||
|
||||
@ApiProperty()
|
||||
country: string;
|
||||
|
||||
@ApiProperty()
|
||||
avatarUrl: string;
|
||||
}
|
||||
|
||||
export class DriverProfileSocialSummaryDTO {
|
||||
@ApiProperty()
|
||||
friendsCount: number;
|
||||
|
||||
@ApiProperty({ type: [DriverProfileSocialFriendSummaryDTO] })
|
||||
friends: DriverProfileSocialFriendSummaryDTO[];
|
||||
}
|
||||
|
||||
export type DriverProfileSocialPlatform = 'twitter' | 'youtube' | 'twitch' | 'discord';
|
||||
|
||||
export type DriverProfileAchievementRarity = 'common' | 'rare' | 'epic' | 'legendary';
|
||||
|
||||
export class DriverProfileAchievementDTO {
|
||||
@ApiProperty()
|
||||
id: string;
|
||||
|
||||
@ApiProperty()
|
||||
title: string;
|
||||
|
||||
@ApiProperty()
|
||||
description: string;
|
||||
|
||||
@ApiProperty({ enum: ['trophy', 'medal', 'star', 'crown', 'target', 'zap'] })
|
||||
icon: 'trophy' | 'medal' | 'star' | 'crown' | 'target' | 'zap';
|
||||
|
||||
@ApiProperty({ enum: DriverProfileAchievementRarity })
|
||||
rarity: DriverProfileAchievementRarity;
|
||||
|
||||
@ApiProperty()
|
||||
earnedAt: string;
|
||||
}
|
||||
|
||||
export class DriverProfileSocialHandleDTO {
|
||||
@ApiProperty({ enum: DriverProfileSocialPlatform })
|
||||
platform: DriverProfileSocialPlatform;
|
||||
|
||||
@ApiProperty()
|
||||
handle: string;
|
||||
|
||||
@ApiProperty()
|
||||
url: string;
|
||||
}
|
||||
|
||||
export class DriverProfileExtendedProfileDTO {
|
||||
@ApiProperty({ type: [DriverProfileSocialHandleDTO] })
|
||||
socialHandles: DriverProfileSocialHandleDTO[];
|
||||
|
||||
@ApiProperty({ type: [DriverProfileAchievementDTO] })
|
||||
achievements: DriverProfileAchievementDTO[];
|
||||
|
||||
@ApiProperty()
|
||||
racingStyle: string;
|
||||
|
||||
@ApiProperty()
|
||||
favoriteTrack: string;
|
||||
|
||||
@ApiProperty()
|
||||
favoriteCar: string;
|
||||
|
||||
@ApiProperty()
|
||||
timezone: string;
|
||||
|
||||
@ApiProperty()
|
||||
availableHours: string;
|
||||
|
||||
@ApiProperty()
|
||||
lookingForTeam: boolean;
|
||||
|
||||
@ApiProperty()
|
||||
openToRequests: boolean;
|
||||
}
|
||||
|
||||
export class GetDriverProfileOutputDTO {
|
||||
@ApiProperty({ type: DriverProfileDriverSummaryDTO, nullable: true })
|
||||
currentDriver: DriverProfileDriverSummaryDTO | null;
|
||||
|
||||
@ApiProperty({ type: DriverProfileStatsDTO, nullable: true })
|
||||
stats: DriverProfileStatsDTO | null;
|
||||
|
||||
@ApiProperty({ type: DriverProfileFinishDistributionDTO, nullable: true })
|
||||
finishDistribution: DriverProfileFinishDistributionDTO | null;
|
||||
|
||||
@ApiProperty({ type: [DriverProfileTeamMembershipDTO] })
|
||||
teamMemberships: DriverProfileTeamMembershipDTO[];
|
||||
|
||||
@ApiProperty({ type: DriverProfileSocialSummaryDTO })
|
||||
socialSummary: DriverProfileSocialSummaryDTO;
|
||||
|
||||
@ApiProperty({ type: DriverProfileExtendedProfileDTO, nullable: true })
|
||||
extendedProfile: DriverProfileExtendedProfileDTO | null;
|
||||
}
|
||||
Reference in New Issue
Block a user