import type { RaceRegistrationRepository } from '@core/racing/domain/repositories/RaceRegistrationRepository'; import type { RaceRepository } from '@core/racing/domain/repositories/RaceRepository'; import type { Logger } from '@core/shared/domain/Logger'; import { Result } from '@core/shared/domain/Result'; import type { ApplicationErrorCode } from '@core/shared/errors/ApplicationErrorCode'; export type WithdrawFromRaceInput = { raceId: string; driverId: string; }; export type WithdrawFromRaceResult = { raceId: string; driverId: string; status: 'withdrawn'; }; export type WithdrawFromRaceErrorCode = | 'RACE_NOT_FOUND' | 'REGISTRATION_NOT_FOUND' | 'WITHDRAWAL_NOT_ALLOWED' | 'REPOSITORY_ERROR'; /** * Use Case: Withdraw a driver from a race. */ export class WithdrawFromRaceUseCase { constructor( private readonly raceRepository: RaceRepository, private readonly registrationRepository: RaceRegistrationRepository, private readonly logger: Logger, ) {} async execute(input: WithdrawFromRaceInput): Promise< Result> > { const { raceId, driverId } = input; try { const race = await this.raceRepository.findById(raceId); if (!race) { return Result.err({ code: 'RACE_NOT_FOUND', details: { message: `Race ${raceId} not found`, }, }); } const isRegistered = await this.registrationRepository.isRegistered(raceId, driverId); if (!isRegistered) { return Result.err({ code: 'REGISTRATION_NOT_FOUND', details: { message: `Driver ${driverId} is not registered for race ${raceId}`, }, }); } if (!race.isUpcoming()) { return Result.err({ code: 'WITHDRAWAL_NOT_ALLOWED', details: { message: 'Withdrawal is not allowed for this race', }, }); } await this.registrationRepository.withdraw(raceId, driverId); const result: WithdrawFromRaceResult = { raceId, driverId, status: 'withdrawn', }; return Result.ok(result); } catch (error) { const message = error instanceof Error ? error.message : 'Failed to withdraw from race'; this.logger.error('WithdrawFromRaceUseCase.execute failed', error instanceof Error ? error : undefined); return Result.err({ code: 'REPOSITORY_ERROR', details: { message, }, }); } } }