website refactor
This commit is contained in:
@@ -175,6 +175,22 @@
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"/drivers/{driverId}/liveries": {
|
||||||
|
"get": {
|
||||||
|
"responses": {
|
||||||
|
"200": {
|
||||||
|
"description": "List of driver liveries",
|
||||||
|
"content": {
|
||||||
|
"application/json": {
|
||||||
|
"schema": {
|
||||||
|
"$ref": "#/components/schemas/GetDriverLiveriesOutputDTO"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
"/drivers/{driverId}/races/{raceId}/registration-status": {
|
"/drivers/{driverId}/races/{raceId}/registration-status": {
|
||||||
"get": {
|
"get": {
|
||||||
"responses": {
|
"responses": {
|
||||||
|
|||||||
@@ -20,6 +20,7 @@ import { CompleteOnboardingInputDTO } from './dtos/CompleteOnboardingInputDTO';
|
|||||||
import { CompleteOnboardingOutputDTO } from './dtos/CompleteOnboardingOutputDTO';
|
import { CompleteOnboardingOutputDTO } from './dtos/CompleteOnboardingOutputDTO';
|
||||||
import { DriversLeaderboardDTO } from './dtos/DriversLeaderboardDTO';
|
import { DriversLeaderboardDTO } from './dtos/DriversLeaderboardDTO';
|
||||||
import { DriverStatsDTO } from './dtos/DriverStatsDTO';
|
import { DriverStatsDTO } from './dtos/DriverStatsDTO';
|
||||||
|
import { GetDriverLiveriesOutputDTO } from './dtos/GetDriverLiveriesOutputDTO';
|
||||||
import { GetDriverOutputDTO } from './dtos/GetDriverOutputDTO';
|
import { GetDriverOutputDTO } from './dtos/GetDriverOutputDTO';
|
||||||
import { GetDriverProfileOutputDTO } from './dtos/GetDriverProfileOutputDTO';
|
import { GetDriverProfileOutputDTO } from './dtos/GetDriverProfileOutputDTO';
|
||||||
import { DriverRegistrationStatusDTO } from './dtos/DriverRegistrationStatusDTO';
|
import { DriverRegistrationStatusDTO } from './dtos/DriverRegistrationStatusDTO';
|
||||||
@@ -43,6 +44,7 @@ describe('DriverController', () => {
|
|||||||
getDriver: vi.fn(),
|
getDriver: vi.fn(),
|
||||||
getDriverProfile: vi.fn(),
|
getDriverProfile: vi.fn(),
|
||||||
updateDriverProfile: vi.fn(),
|
updateDriverProfile: vi.fn(),
|
||||||
|
getDriverLiveries: vi.fn(),
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
@@ -170,6 +172,19 @@ describe('DriverController', () => {
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
describe('getDriverLiveries', () => {
|
||||||
|
it('should return driver liveries', async () => {
|
||||||
|
const driverId = 'driver-123';
|
||||||
|
const liveries: GetDriverLiveriesOutputDTO = { liveries: [] };
|
||||||
|
service.getDriverLiveries.mockResolvedValue(liveries);
|
||||||
|
|
||||||
|
const result = await controller.getDriverLiveries(driverId);
|
||||||
|
|
||||||
|
expect(service.getDriverLiveries).toHaveBeenCalledWith(driverId);
|
||||||
|
expect(result).toEqual(liveries);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
describe('auth guards (HTTP)', () => {
|
describe('auth guards (HTTP)', () => {
|
||||||
let app: any;
|
let app: any;
|
||||||
|
|
||||||
|
|||||||
@@ -12,6 +12,7 @@ import { CompleteOnboardingOutputDTO } from './dtos/CompleteOnboardingOutputDTO'
|
|||||||
import { DriverRegistrationStatusDTO } from './dtos/DriverRegistrationStatusDTO';
|
import { DriverRegistrationStatusDTO } from './dtos/DriverRegistrationStatusDTO';
|
||||||
import { DriversLeaderboardDTO } from './dtos/DriversLeaderboardDTO';
|
import { DriversLeaderboardDTO } from './dtos/DriversLeaderboardDTO';
|
||||||
import { DriverStatsDTO } from './dtos/DriverStatsDTO';
|
import { DriverStatsDTO } from './dtos/DriverStatsDTO';
|
||||||
|
import { GetDriverLiveriesOutputDTO } from './dtos/GetDriverLiveriesOutputDTO';
|
||||||
import { GetDriverOutputDTO } from './dtos/GetDriverOutputDTO';
|
import { GetDriverOutputDTO } from './dtos/GetDriverOutputDTO';
|
||||||
import { GetDriverProfileOutputDTO } from './dtos/GetDriverProfileOutputDTO';
|
import { GetDriverProfileOutputDTO } from './dtos/GetDriverProfileOutputDTO';
|
||||||
|
|
||||||
@@ -111,5 +112,13 @@ export class DriverController {
|
|||||||
return await this.driverService.updateDriverProfile(driverId, body.bio, body.country);
|
return await this.driverService.updateDriverProfile(driverId, body.bio, body.country);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Public()
|
||||||
|
@Get(':driverId/liveries')
|
||||||
|
@ApiOperation({ summary: 'Get driver liveries' })
|
||||||
|
@ApiResponse({ status: 200, description: 'List of driver liveries', type: GetDriverLiveriesOutputDTO })
|
||||||
|
async getDriverLiveries(@Param('driverId') driverId: string): Promise<GetDriverLiveriesOutputDTO> {
|
||||||
|
return await this.driverService.getDriverLiveries(driverId);
|
||||||
|
}
|
||||||
|
|
||||||
// Add other Driver endpoints here based on other presenters
|
// Add other Driver endpoints here based on other presenters
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -3,6 +3,7 @@ import { Provider } from '@nestjs/common';
|
|||||||
// Import core interfaces
|
// Import core interfaces
|
||||||
import { DriverExtendedProfileProvider } from '@core/racing/application/ports/DriverExtendedProfileProvider';
|
import { DriverExtendedProfileProvider } from '@core/racing/application/ports/DriverExtendedProfileProvider';
|
||||||
import { IDriverRepository } from '@core/racing/domain/repositories/IDriverRepository';
|
import { IDriverRepository } from '@core/racing/domain/repositories/IDriverRepository';
|
||||||
|
import { ILiveryRepository } from '@core/racing/domain/repositories/ILiveryRepository';
|
||||||
import { IRaceRegistrationRepository } from '@core/racing/domain/repositories/IRaceRegistrationRepository';
|
import { IRaceRegistrationRepository } from '@core/racing/domain/repositories/IRaceRegistrationRepository';
|
||||||
import type { ITeamMembershipRepository } from '@core/racing/domain/repositories/ITeamMembershipRepository';
|
import type { ITeamMembershipRepository } from '@core/racing/domain/repositories/ITeamMembershipRepository';
|
||||||
import type { ITeamRepository } from '@core/racing/domain/repositories/ITeamRepository';
|
import type { ITeamRepository } from '@core/racing/domain/repositories/ITeamRepository';
|
||||||
@@ -15,6 +16,7 @@ import type { MediaResolverPort } from '@core/ports/media/MediaResolverPort';
|
|||||||
// Import use cases
|
// Import use cases
|
||||||
import { CompleteDriverOnboardingUseCase } from '@core/racing/application/use-cases/CompleteDriverOnboardingUseCase';
|
import { CompleteDriverOnboardingUseCase } from '@core/racing/application/use-cases/CompleteDriverOnboardingUseCase';
|
||||||
import { GetDriversLeaderboardUseCase } from '@core/racing/application/use-cases/GetDriversLeaderboardUseCase';
|
import { GetDriversLeaderboardUseCase } from '@core/racing/application/use-cases/GetDriversLeaderboardUseCase';
|
||||||
|
import { GetDriverLiveriesUseCase } from '@core/racing/application/use-cases/GetDriverLiveriesUseCase';
|
||||||
import { GetProfileOverviewUseCase } from '@core/racing/application/use-cases/GetProfileOverviewUseCase';
|
import { GetProfileOverviewUseCase } from '@core/racing/application/use-cases/GetProfileOverviewUseCase';
|
||||||
import { GetTotalDriversUseCase } from '@core/racing/application/use-cases/GetTotalDriversUseCase';
|
import { GetTotalDriversUseCase } from '@core/racing/application/use-cases/GetTotalDriversUseCase';
|
||||||
import { IsDriverRegisteredForRaceUseCase } from '@core/racing/application/use-cases/IsDriverRegisteredForRaceUseCase';
|
import { IsDriverRegisteredForRaceUseCase } from '@core/racing/application/use-cases/IsDriverRegisteredForRaceUseCase';
|
||||||
@@ -26,6 +28,7 @@ import { InMemoryImageServiceAdapter } from '@adapters/media/ports/InMemoryImage
|
|||||||
import { InMemoryNotificationPreferenceRepository } from '@adapters/notifications/persistence/inmemory/InMemoryNotificationPreferenceRepository';
|
import { InMemoryNotificationPreferenceRepository } from '@adapters/notifications/persistence/inmemory/InMemoryNotificationPreferenceRepository';
|
||||||
import { InMemoryDriverExtendedProfileProvider } from '@adapters/racing/ports/InMemoryDriverExtendedProfileProvider';
|
import { InMemoryDriverExtendedProfileProvider } from '@adapters/racing/ports/InMemoryDriverExtendedProfileProvider';
|
||||||
import { InMemoryDriverRatingProvider } from '@adapters/racing/ports/InMemoryDriverRatingProvider';
|
import { InMemoryDriverRatingProvider } from '@adapters/racing/ports/InMemoryDriverRatingProvider';
|
||||||
|
import { InMemoryLiveryRepository } from '@adapters/racing/persistence/inmemory/InMemoryLiveryRepository';
|
||||||
// Import new use cases
|
// Import new use cases
|
||||||
import { RankingUseCase } from '@core/racing/application/use-cases/RankingUseCase';
|
import { RankingUseCase } from '@core/racing/application/use-cases/RankingUseCase';
|
||||||
import { DriverStatsUseCase } from '@core/racing/application/use-cases/DriverStatsUseCase';
|
import { DriverStatsUseCase } from '@core/racing/application/use-cases/DriverStatsUseCase';
|
||||||
@@ -47,6 +50,7 @@ import { DriverProfilePresenter } from './presenters/DriverProfilePresenter';
|
|||||||
import { DriverRegistrationStatusPresenter } from './presenters/DriverRegistrationStatusPresenter';
|
import { DriverRegistrationStatusPresenter } from './presenters/DriverRegistrationStatusPresenter';
|
||||||
import { DriversLeaderboardPresenter } from './presenters/DriversLeaderboardPresenter';
|
import { DriversLeaderboardPresenter } from './presenters/DriversLeaderboardPresenter';
|
||||||
import { DriverStatsPresenter } from './presenters/DriverStatsPresenter';
|
import { DriverStatsPresenter } from './presenters/DriverStatsPresenter';
|
||||||
|
import { GetDriverLiveriesPresenter } from './presenters/GetDriverLiveriesPresenter';
|
||||||
|
|
||||||
import {
|
import {
|
||||||
DRIVER_REPOSITORY_TOKEN,
|
DRIVER_REPOSITORY_TOKEN,
|
||||||
@@ -58,9 +62,11 @@ import {
|
|||||||
TEAM_REPOSITORY_TOKEN,
|
TEAM_REPOSITORY_TOKEN,
|
||||||
TEAM_MEMBERSHIP_REPOSITORY_TOKEN,
|
TEAM_MEMBERSHIP_REPOSITORY_TOKEN,
|
||||||
SOCIAL_GRAPH_REPOSITORY_TOKEN,
|
SOCIAL_GRAPH_REPOSITORY_TOKEN,
|
||||||
|
LIVERY_REPOSITORY_TOKEN,
|
||||||
LOGGER_TOKEN,
|
LOGGER_TOKEN,
|
||||||
GET_DRIVERS_LEADERBOARD_USE_CASE_TOKEN,
|
GET_DRIVERS_LEADERBOARD_USE_CASE_TOKEN,
|
||||||
GET_TOTAL_DRIVERS_USE_CASE_TOKEN,
|
GET_TOTAL_DRIVERS_USE_CASE_TOKEN,
|
||||||
|
GET_DRIVER_LIVERIES_USE_CASE_TOKEN,
|
||||||
COMPLETE_DRIVER_ONBOARDING_USE_CASE_TOKEN,
|
COMPLETE_DRIVER_ONBOARDING_USE_CASE_TOKEN,
|
||||||
IS_DRIVER_REGISTERED_FOR_RACE_USE_CASE_TOKEN,
|
IS_DRIVER_REGISTERED_FOR_RACE_USE_CASE_TOKEN,
|
||||||
UPDATE_DRIVER_PROFILE_USE_CASE_TOKEN,
|
UPDATE_DRIVER_PROFILE_USE_CASE_TOKEN,
|
||||||
@@ -112,6 +118,7 @@ export const DriverProviders: Provider[] = createLoggedProviders([
|
|||||||
},
|
},
|
||||||
inject: [MEDIA_RESOLVER_TOKEN],
|
inject: [MEDIA_RESOLVER_TOKEN],
|
||||||
},
|
},
|
||||||
|
GetDriverLiveriesPresenter,
|
||||||
|
|
||||||
// Logger
|
// Logger
|
||||||
{
|
{
|
||||||
@@ -189,6 +196,11 @@ export const DriverProviders: Provider[] = createLoggedProviders([
|
|||||||
useFactory: (logger: Logger) => new InMemoryNotificationPreferenceRepository(logger),
|
useFactory: (logger: Logger) => new InMemoryNotificationPreferenceRepository(logger),
|
||||||
inject: [LOGGER_TOKEN],
|
inject: [LOGGER_TOKEN],
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
provide: LIVERY_REPOSITORY_TOKEN,
|
||||||
|
useFactory: (logger: Logger) => new InMemoryLiveryRepository(logger),
|
||||||
|
inject: [LOGGER_TOKEN],
|
||||||
|
},
|
||||||
|
|
||||||
// Use cases
|
// Use cases
|
||||||
{
|
{
|
||||||
@@ -258,4 +270,10 @@ export const DriverProviders: Provider[] = createLoggedProviders([
|
|||||||
RANKING_SERVICE_TOKEN,
|
RANKING_SERVICE_TOKEN,
|
||||||
],
|
],
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
provide: GET_DRIVER_LIVERIES_USE_CASE_TOKEN,
|
||||||
|
useFactory: (liveryRepository: ILiveryRepository, logger: Logger) =>
|
||||||
|
new GetDriverLiveriesUseCase(liveryRepository, logger),
|
||||||
|
inject: [LIVERY_REPOSITORY_TOKEN, LOGGER_TOKEN],
|
||||||
|
},
|
||||||
], initLogger);
|
], initLogger);
|
||||||
|
|||||||
@@ -317,4 +317,41 @@ describe('DriverService', () => {
|
|||||||
expect(getProfileOverviewUseCase.execute).toHaveBeenCalledWith({ driverId: 'd1' });
|
expect(getProfileOverviewUseCase.execute).toHaveBeenCalledWith({ driverId: 'd1' });
|
||||||
expect(driverProfilePresenter.getResponseModel).toHaveBeenCalled();
|
expect(driverProfilePresenter.getResponseModel).toHaveBeenCalled();
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('getDriverLiveries executes use case and returns presenter model', async () => {
|
||||||
|
const getDriverLiveriesUseCase = { execute: vi.fn(async () => Result.ok(undefined)) };
|
||||||
|
const getDriverLiveriesPresenter = {
|
||||||
|
present: vi.fn(),
|
||||||
|
getResponseModel: vi.fn(() => ({ liveries: [] }))
|
||||||
|
};
|
||||||
|
const driverPresenter = {
|
||||||
|
setMediaResolver: vi.fn(),
|
||||||
|
setBaseUrl: vi.fn(),
|
||||||
|
present: vi.fn(),
|
||||||
|
getResponseModel: vi.fn(() => null)
|
||||||
|
};
|
||||||
|
|
||||||
|
const service = new DriverService(
|
||||||
|
{ execute: vi.fn() } as any,
|
||||||
|
{ execute: vi.fn() } as any,
|
||||||
|
getDriverLiveriesUseCase as any,
|
||||||
|
{ execute: vi.fn() } as any,
|
||||||
|
{ execute: vi.fn() } as any,
|
||||||
|
{ execute: vi.fn() } as any,
|
||||||
|
{ findById: vi.fn() } as any,
|
||||||
|
logger as any,
|
||||||
|
{ getResponseModel: vi.fn(() => ({ items: [] })) } as any,
|
||||||
|
{ getResponseModel: vi.fn(() => ({ totalDrivers: 0 })) } as any,
|
||||||
|
{ getResponseModel: vi.fn(() => ({ success: true })) } as any,
|
||||||
|
{ getResponseModel: vi.fn(() => ({ isRegistered: false })) } as any,
|
||||||
|
driverPresenter as any,
|
||||||
|
{ getResponseModel: vi.fn(() => ({ profile: {} })) } as any,
|
||||||
|
getDriverLiveriesPresenter as any,
|
||||||
|
);
|
||||||
|
|
||||||
|
await expect(service.getDriverLiveries('d1')).resolves.toEqual({ liveries: [] });
|
||||||
|
expect(getDriverLiveriesUseCase.execute).toHaveBeenCalledWith({ driverId: 'd1' });
|
||||||
|
expect(getDriverLiveriesPresenter.present).toHaveBeenCalled();
|
||||||
|
expect(getDriverLiveriesPresenter.getResponseModel).toHaveBeenCalled();
|
||||||
|
});
|
||||||
});
|
});
|
||||||
@@ -6,11 +6,13 @@ import { DriverRegistrationStatusDTO } from './dtos/DriverRegistrationStatusDTO'
|
|||||||
import { DriversLeaderboardDTO } from './dtos/DriversLeaderboardDTO';
|
import { DriversLeaderboardDTO } from './dtos/DriversLeaderboardDTO';
|
||||||
import { DriverStatsDTO } from './dtos/DriverStatsDTO';
|
import { DriverStatsDTO } from './dtos/DriverStatsDTO';
|
||||||
import { GetDriverOutputDTO } from './dtos/GetDriverOutputDTO';
|
import { GetDriverOutputDTO } from './dtos/GetDriverOutputDTO';
|
||||||
|
import { GetDriverLiveriesOutputDTO } from './dtos/GetDriverLiveriesOutputDTO';
|
||||||
import { GetDriverProfileOutputDTO } from './dtos/GetDriverProfileOutputDTO';
|
import { GetDriverProfileOutputDTO } from './dtos/GetDriverProfileOutputDTO';
|
||||||
import { GetDriverRegistrationStatusQueryDTO } from './dtos/GetDriverRegistrationStatusQueryDTO';
|
import { GetDriverRegistrationStatusQueryDTO } from './dtos/GetDriverRegistrationStatusQueryDTO';
|
||||||
|
|
||||||
// Use cases
|
// Use cases
|
||||||
import { CompleteDriverOnboardingUseCase } from '@core/racing/application/use-cases/CompleteDriverOnboardingUseCase';
|
import { CompleteDriverOnboardingUseCase } from '@core/racing/application/use-cases/CompleteDriverOnboardingUseCase';
|
||||||
|
import { GetDriverLiveriesUseCase } from '@core/racing/application/use-cases/GetDriverLiveriesUseCase';
|
||||||
import { GetDriversLeaderboardUseCase } from '@core/racing/application/use-cases/GetDriversLeaderboardUseCase';
|
import { GetDriversLeaderboardUseCase } from '@core/racing/application/use-cases/GetDriversLeaderboardUseCase';
|
||||||
import { GetProfileOverviewUseCase } from '@core/racing/application/use-cases/GetProfileOverviewUseCase';
|
import { GetProfileOverviewUseCase } from '@core/racing/application/use-cases/GetProfileOverviewUseCase';
|
||||||
import { GetTotalDriversUseCase } from '@core/racing/application/use-cases/GetTotalDriversUseCase';
|
import { GetTotalDriversUseCase } from '@core/racing/application/use-cases/GetTotalDriversUseCase';
|
||||||
@@ -24,6 +26,7 @@ import { DriverProfilePresenter } from './presenters/DriverProfilePresenter';
|
|||||||
import { DriverRegistrationStatusPresenter } from './presenters/DriverRegistrationStatusPresenter';
|
import { DriverRegistrationStatusPresenter } from './presenters/DriverRegistrationStatusPresenter';
|
||||||
import { DriversLeaderboardPresenter } from './presenters/DriversLeaderboardPresenter';
|
import { DriversLeaderboardPresenter } from './presenters/DriversLeaderboardPresenter';
|
||||||
import { DriverStatsPresenter } from './presenters/DriverStatsPresenter';
|
import { DriverStatsPresenter } from './presenters/DriverStatsPresenter';
|
||||||
|
import { GetDriverLiveriesPresenter } from './presenters/GetDriverLiveriesPresenter';
|
||||||
|
|
||||||
// Tokens
|
// Tokens
|
||||||
import type { IDriverRepository } from '@core/racing/domain/repositories/IDriverRepository';
|
import type { IDriverRepository } from '@core/racing/domain/repositories/IDriverRepository';
|
||||||
@@ -31,6 +34,7 @@ import type { Logger } from '@core/shared/application';
|
|||||||
import {
|
import {
|
||||||
COMPLETE_DRIVER_ONBOARDING_USE_CASE_TOKEN,
|
COMPLETE_DRIVER_ONBOARDING_USE_CASE_TOKEN,
|
||||||
DRIVER_REPOSITORY_TOKEN,
|
DRIVER_REPOSITORY_TOKEN,
|
||||||
|
GET_DRIVER_LIVERIES_USE_CASE_TOKEN,
|
||||||
GET_DRIVERS_LEADERBOARD_USE_CASE_TOKEN,
|
GET_DRIVERS_LEADERBOARD_USE_CASE_TOKEN,
|
||||||
GET_PROFILE_OVERVIEW_USE_CASE_TOKEN,
|
GET_PROFILE_OVERVIEW_USE_CASE_TOKEN,
|
||||||
GET_TOTAL_DRIVERS_USE_CASE_TOKEN,
|
GET_TOTAL_DRIVERS_USE_CASE_TOKEN,
|
||||||
@@ -46,6 +50,8 @@ export class DriverService {
|
|||||||
private readonly getDriversLeaderboardUseCase: GetDriversLeaderboardUseCase,
|
private readonly getDriversLeaderboardUseCase: GetDriversLeaderboardUseCase,
|
||||||
@Inject(GET_TOTAL_DRIVERS_USE_CASE_TOKEN)
|
@Inject(GET_TOTAL_DRIVERS_USE_CASE_TOKEN)
|
||||||
private readonly getTotalDriversUseCase: GetTotalDriversUseCase,
|
private readonly getTotalDriversUseCase: GetTotalDriversUseCase,
|
||||||
|
@Inject(GET_DRIVER_LIVERIES_USE_CASE_TOKEN)
|
||||||
|
private readonly getDriverLiveriesUseCase: GetDriverLiveriesUseCase,
|
||||||
@Inject(COMPLETE_DRIVER_ONBOARDING_USE_CASE_TOKEN)
|
@Inject(COMPLETE_DRIVER_ONBOARDING_USE_CASE_TOKEN)
|
||||||
private readonly completeDriverOnboardingUseCase: CompleteDriverOnboardingUseCase,
|
private readonly completeDriverOnboardingUseCase: CompleteDriverOnboardingUseCase,
|
||||||
@Inject(IS_DRIVER_REGISTERED_FOR_RACE_USE_CASE_TOKEN)
|
@Inject(IS_DRIVER_REGISTERED_FOR_RACE_USE_CASE_TOKEN)
|
||||||
@@ -65,6 +71,7 @@ export class DriverService {
|
|||||||
private readonly driverRegistrationStatusPresenter?: DriverRegistrationStatusPresenter,
|
private readonly driverRegistrationStatusPresenter?: DriverRegistrationStatusPresenter,
|
||||||
private readonly driverPresenter?: DriverPresenter,
|
private readonly driverPresenter?: DriverPresenter,
|
||||||
private readonly driverProfilePresenter?: DriverProfilePresenter,
|
private readonly driverProfilePresenter?: DriverProfilePresenter,
|
||||||
|
private readonly getDriverLiveriesPresenter?: GetDriverLiveriesPresenter,
|
||||||
) {
|
) {
|
||||||
// Presenters are configured by providers, no need to configure here
|
// Presenters are configured by providers, no need to configure here
|
||||||
}
|
}
|
||||||
@@ -175,4 +182,15 @@ export class DriverService {
|
|||||||
}
|
}
|
||||||
return this.driverProfilePresenter!.getResponseModel();
|
return this.driverProfilePresenter!.getResponseModel();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
async getDriverLiveries(driverId: string): Promise<GetDriverLiveriesOutputDTO> {
|
||||||
|
this.logger.debug(`[DriverService] Fetching driver liveries for driverId: ${driverId}`);
|
||||||
|
|
||||||
|
const result = await this.getDriverLiveriesUseCase.execute({ driverId });
|
||||||
|
if (result.isErr()) {
|
||||||
|
throw new Error(result.unwrapErr().details.message);
|
||||||
|
}
|
||||||
|
await this.getDriverLiveriesPresenter!.present(result);
|
||||||
|
return this.getDriverLiveriesPresenter!.getResponseModel()!;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
@@ -11,6 +11,7 @@ import { SOCIAL_GRAPH_REPOSITORY_TOKEN } from '../../persistence/social/SocialPe
|
|||||||
|
|
||||||
export const TEAM_MEMBERSHIP_REPOSITORY_TOKEN = 'ITeamMembershipRepository';
|
export const TEAM_MEMBERSHIP_REPOSITORY_TOKEN = 'ITeamMembershipRepository';
|
||||||
export { SOCIAL_GRAPH_REPOSITORY_TOKEN };
|
export { SOCIAL_GRAPH_REPOSITORY_TOKEN };
|
||||||
|
export const LIVERY_REPOSITORY_TOKEN = 'ILiveryRepository';
|
||||||
export const LOGGER_TOKEN = 'Logger';
|
export const LOGGER_TOKEN = 'Logger';
|
||||||
|
|
||||||
// New tokens for clean architecture
|
// New tokens for clean architecture
|
||||||
@@ -24,10 +25,12 @@ export const COMPLETE_DRIVER_ONBOARDING_USE_CASE_TOKEN = 'CompleteDriverOnboardi
|
|||||||
export const IS_DRIVER_REGISTERED_FOR_RACE_USE_CASE_TOKEN = 'IsDriverRegisteredForRaceUseCase';
|
export const IS_DRIVER_REGISTERED_FOR_RACE_USE_CASE_TOKEN = 'IsDriverRegisteredForRaceUseCase';
|
||||||
export const UPDATE_DRIVER_PROFILE_USE_CASE_TOKEN = 'UpdateDriverProfileUseCase';
|
export const UPDATE_DRIVER_PROFILE_USE_CASE_TOKEN = 'UpdateDriverProfileUseCase';
|
||||||
export const GET_PROFILE_OVERVIEW_USE_CASE_TOKEN = 'GetProfileOverviewUseCase';
|
export const GET_PROFILE_OVERVIEW_USE_CASE_TOKEN = 'GetProfileOverviewUseCase';
|
||||||
|
export const GET_DRIVER_LIVERIES_USE_CASE_TOKEN = 'GetDriverLiveriesUseCase';
|
||||||
|
|
||||||
export const GET_DRIVERS_LEADERBOARD_OUTPUT_PORT_TOKEN = 'GetDriversLeaderboardOutputPort_TOKEN';
|
export const GET_DRIVERS_LEADERBOARD_OUTPUT_PORT_TOKEN = 'GetDriversLeaderboardOutputPort_TOKEN';
|
||||||
export const GET_TOTAL_DRIVERS_OUTPUT_PORT_TOKEN = 'GetTotalDriversOutputPort_TOKEN';
|
export const GET_TOTAL_DRIVERS_OUTPUT_PORT_TOKEN = 'GetTotalDriversOutputPort_TOKEN';
|
||||||
export const COMPLETE_DRIVER_ONBOARDING_OUTPUT_PORT_TOKEN = 'CompleteDriverOnboardingOutputPort_TOKEN';
|
export const COMPLETE_DRIVER_ONBOARDING_OUTPUT_PORT_TOKEN = 'CompleteDriverOnboardingOutputPort_TOKEN';
|
||||||
export const IS_DRIVER_REGISTERED_FOR_RACE_OUTPUT_PORT_TOKEN = 'IsDriverRegisteredForRaceOutputPort_TOKEN';
|
export const IS_DRIVER_REGISTERED_FOR_RACE_OUTPUT_PORT_TOKEN = 'IsDriverRegisteredForRaceOutputPort_TOKEN';
|
||||||
export const UPDATE_DRIVER_PROFILE_OUTPUT_PORT_TOKEN = 'UpdateDriverProfileOutputPort_TOKEN';
|
export const UPDATE_DRIVER_PROFILE_OUTPUT_PORT_TOKEN = 'UpdateDriverProfileOutputPort_TOKEN';
|
||||||
export const GET_PROFILE_OVERVIEW_OUTPUT_PORT_TOKEN = 'GetProfileOverviewOutputPort_TOKEN';
|
export const GET_PROFILE_OVERVIEW_OUTPUT_PORT_TOKEN = 'GetProfileOverviewOutputPort_TOKEN';
|
||||||
|
export const GET_DRIVER_LIVERIES_OUTPUT_PORT_TOKEN = 'GetDriverLiveriesOutputPort_TOKEN';
|
||||||
@@ -0,0 +1,23 @@
|
|||||||
|
import { ApiProperty } from '@nestjs/swagger';
|
||||||
|
|
||||||
|
class LiveryDTO {
|
||||||
|
@ApiProperty()
|
||||||
|
id!: string;
|
||||||
|
|
||||||
|
@ApiProperty()
|
||||||
|
name!: string;
|
||||||
|
|
||||||
|
@ApiProperty()
|
||||||
|
imageUrl!: string;
|
||||||
|
|
||||||
|
@ApiProperty()
|
||||||
|
createdAt!: string;
|
||||||
|
|
||||||
|
@ApiProperty()
|
||||||
|
isActive!: boolean;
|
||||||
|
}
|
||||||
|
|
||||||
|
export class GetDriverLiveriesOutputDTO {
|
||||||
|
@ApiProperty({ type: [LiveryDTO] })
|
||||||
|
liveries!: LiveryDTO[];
|
||||||
|
}
|
||||||
@@ -0,0 +1,70 @@
|
|||||||
|
import { describe, it, expect, beforeEach } from 'vitest';
|
||||||
|
import { Result } from '@core/shared/application/Result';
|
||||||
|
import { GetDriverLiveriesPresenter } from './GetDriverLiveriesPresenter';
|
||||||
|
import { DriverLivery } from '@core/racing/domain/entities/DriverLivery';
|
||||||
|
|
||||||
|
describe('GetDriverLiveriesPresenter', () => {
|
||||||
|
let presenter: GetDriverLiveriesPresenter;
|
||||||
|
|
||||||
|
beforeEach(() => {
|
||||||
|
presenter = new GetDriverLiveriesPresenter();
|
||||||
|
});
|
||||||
|
|
||||||
|
describe('present', () => {
|
||||||
|
it('should map core result to API response model correctly', () => {
|
||||||
|
const mockLiveries: DriverLivery[] = [
|
||||||
|
DriverLivery.create({
|
||||||
|
id: 'livery1',
|
||||||
|
driverId: 'driver1',
|
||||||
|
gameId: 'game1',
|
||||||
|
carId: 'car1',
|
||||||
|
uploadedImageUrl: 'http://example.com/livery1.png',
|
||||||
|
createdAt: new Date('2023-01-01'),
|
||||||
|
}),
|
||||||
|
DriverLivery.create({
|
||||||
|
id: 'livery2',
|
||||||
|
driverId: 'driver1',
|
||||||
|
gameId: 'game1',
|
||||||
|
carId: 'car2',
|
||||||
|
uploadedImageUrl: 'http://example.com/livery2.png',
|
||||||
|
createdAt: new Date('2023-01-02'),
|
||||||
|
}),
|
||||||
|
];
|
||||||
|
|
||||||
|
const result = Result.ok(mockLiveries);
|
||||||
|
presenter.present(result);
|
||||||
|
|
||||||
|
const response = presenter.getResponseModel();
|
||||||
|
|
||||||
|
expect(response).toEqual({
|
||||||
|
liveries: [
|
||||||
|
{
|
||||||
|
id: 'livery1',
|
||||||
|
name: 'Livery for car1',
|
||||||
|
imageUrl: 'http://example.com/livery1.png',
|
||||||
|
createdAt: '2023-01-01T00:00:00.000Z',
|
||||||
|
isActive: true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: 'livery2',
|
||||||
|
name: 'Livery for car2',
|
||||||
|
imageUrl: 'http://example.com/livery2.png',
|
||||||
|
createdAt: '2023-01-02T00:00:00.000Z',
|
||||||
|
isActive: false,
|
||||||
|
},
|
||||||
|
],
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should handle empty liveries array', () => {
|
||||||
|
const result = Result.ok([]);
|
||||||
|
presenter.present(result);
|
||||||
|
|
||||||
|
const response = presenter.getResponseModel();
|
||||||
|
|
||||||
|
expect(response).toEqual({
|
||||||
|
liveries: [],
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
@@ -0,0 +1,33 @@
|
|||||||
|
import { Result } from '@core/shared/application/Result';
|
||||||
|
import type { DriverLivery } from '@core/racing/domain/entities/DriverLivery';
|
||||||
|
import type { GetDriverLiveriesOutputDTO } from '../dtos/GetDriverLiveriesOutputDTO';
|
||||||
|
|
||||||
|
export class GetDriverLiveriesPresenter {
|
||||||
|
private responseModel: GetDriverLiveriesOutputDTO | null = null;
|
||||||
|
|
||||||
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||||
|
async present(result: Result<DriverLivery[], any>): Promise<void> {
|
||||||
|
if (result.isErr()) {
|
||||||
|
const error = result.unwrapErr();
|
||||||
|
throw new Error(error.details?.message ?? 'Failed to get driver liveries');
|
||||||
|
}
|
||||||
|
|
||||||
|
const liveries = result.unwrap();
|
||||||
|
|
||||||
|
const dto: GetDriverLiveriesOutputDTO = {
|
||||||
|
liveries: liveries.map((livery, index) => ({
|
||||||
|
id: livery.id,
|
||||||
|
name: `Livery for ${livery.carId.toString()}`, // Simple name generation
|
||||||
|
imageUrl: livery.uploadedImageUrl.toString(),
|
||||||
|
createdAt: livery.createdAt.toISOString(),
|
||||||
|
isActive: index === 0, // First livery is active by default
|
||||||
|
})),
|
||||||
|
};
|
||||||
|
|
||||||
|
this.responseModel = dto;
|
||||||
|
}
|
||||||
|
|
||||||
|
getResponseModel(): GetDriverLiveriesOutputDTO | null {
|
||||||
|
return this.responseModel;
|
||||||
|
}
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user