ad/tests/integration/ad/ad.repository.spec.ts

317 lines
8.1 KiB
TypeScript

import {
AD_MESSAGE_PUBLISHER,
AD_REPOSITORY,
OUTPUT_DATETIME_TRANSFORMER,
TIMEZONE_FINDER,
TIME_CONVERTER,
} from '@modules/ad/ad.di-tokens';
import { AdMapper } from '@modules/ad/ad.mapper';
import { AdEntity } from '@modules/ad/core/domain/ad.entity';
import { CreateAdProps, Frequency } from '@modules/ad/core/domain/ad.types';
import { AdRepository } from '@modules/ad/infrastructure/ad.repository';
import { OutputDateTimeTransformer } from '@modules/ad/infrastructure/output-datetime-transformer';
import { PrismaService } from '@modules/ad/infrastructure/prisma.service';
import { TimeConverter } from '@modules/ad/infrastructure/time-converter';
import { TimezoneFinder } from '@modules/ad/infrastructure/timezone-finder';
import { ConfigModule } from '@nestjs/config';
import { EventEmitterModule } from '@nestjs/event-emitter';
import { Test } from '@nestjs/testing';
describe('Ad Repository', () => {
let prismaService: PrismaService;
let adRepository: AdRepository;
const executeInsertCommand = async (table: string, object: any) => {
const command = `INSERT INTO ${table} ("${Object.keys(object).join(
'","',
)}") VALUES (${Object.values(object).join(',')})`;
await prismaService.$executeRawUnsafe(command);
};
const getSeed = (index: number, uuid: string): string => {
return `'${uuid.slice(0, -2)}${index.toString(16).padStart(2, '0')}'`;
};
const baseUuid = {
uuid: 'be459a29-7a41-4c0b-b371-abe90bfb6f00',
};
const baseScheduleUuid = {
uuid: 'bad5e786-3b15-4e51-a8fc-926fa9327ff1',
};
const baseOriginWaypointUuid = {
uuid: 'bad5e786-3b15-4e51-a8fc-926fa9327ff1',
};
const baseDestinationWaypointUuid = {
uuid: '4d200eb6-7389-487f-a1ca-dbc0e40381c9',
};
const baseUserUuid = {
userUuid: "'113e0000-0000-4000-a000-000000000000'",
};
const driverAd = {
driver: 'true',
passenger: 'false',
seatsProposed: 3,
seatsRequested: 1,
strict: 'false',
};
const punctualAd = {
frequency: `'PUNCTUAL'`,
fromDate: `'2023-01-01'`,
toDate: `'2023-01-01'`,
};
const schedulePunctualAd = {
day: 0,
time: `'07:00'`,
margin: 900,
};
const originWaypoint = {
position: 0,
lat: 43.7102,
lon: 7.262,
locality: "'Nice'",
postalCode: "'06000'",
country: "'France'",
};
const destinationWaypoint = {
position: 1,
lat: 43.2965,
lon: 5.3698,
locality: "'Marseille'",
postalCode: "'13000'",
country: "'France'",
};
const createPunctualDriverAds = async (nbToCreate = 10) => {
const adToCreate = {
...baseUuid,
...baseUserUuid,
...driverAd,
...punctualAd,
};
for (let i = 0; i < nbToCreate; i++) {
adToCreate.uuid = getSeed(i, baseUuid.uuid);
await executeInsertCommand('ad', adToCreate);
await executeInsertCommand('schedule_item', {
uuid: getSeed(i, baseScheduleUuid.uuid),
adUuid: adToCreate.uuid,
...schedulePunctualAd,
});
await executeInsertCommand('waypoint', {
uuid: getSeed(i, baseOriginWaypointUuid.uuid),
adUuid: adToCreate.uuid,
...originWaypoint,
});
await executeInsertCommand('waypoint', {
uuid: getSeed(i, baseDestinationWaypointUuid.uuid),
adUuid: adToCreate.uuid,
...destinationWaypoint,
});
}
};
const mockMessagePublisher = {
publish: jest.fn().mockImplementation(),
};
const mockLogger = {
log: jest.fn(),
warn: jest.fn(),
error: jest.fn(),
};
beforeAll(async () => {
const module = await Test.createTestingModule({
imports: [
EventEmitterModule.forRoot(),
ConfigModule.forRoot({ isGlobal: true }),
],
providers: [
PrismaService,
AdMapper,
{
provide: AD_REPOSITORY,
useClass: AdRepository,
},
{
provide: AD_MESSAGE_PUBLISHER,
useValue: mockMessagePublisher,
},
{
provide: TIMEZONE_FINDER,
useClass: TimezoneFinder,
},
{
provide: TIME_CONVERTER,
useClass: TimeConverter,
},
{
provide: OUTPUT_DATETIME_TRANSFORMER,
useClass: OutputDateTimeTransformer,
},
],
})
// disable logging
.setLogger(mockLogger)
.compile();
prismaService = module.get<PrismaService>(PrismaService);
adRepository = module.get<AdRepository>(AD_REPOSITORY);
});
afterAll(async () => {
await prismaService.$disconnect();
});
beforeEach(async () => {
await prismaService.ad.deleteMany();
});
describe('findOneById', () => {
it('should return an ad', async () => {
await createPunctualDriverAds(1);
const result = await adRepository.findOneById(baseUuid.uuid, {
waypoints: true,
schedule: true,
});
expect(result.id).toBe(baseUuid.uuid);
});
});
describe('create', () => {
it('should create a punctual ad', async () => {
const beforeCount = await prismaService.ad.count();
const createAdProps: CreateAdProps = {
userId: 'b4b56444-f8d3-4110-917c-e37bba77f383',
driver: true,
passenger: false,
frequency: Frequency.PUNCTUAL,
fromDate: '2023-02-01',
toDate: '2023-02-01',
schedule: [
{
day: 3,
time: '12:05',
margin: 900,
},
],
seatsProposed: 3,
seatsRequested: 1,
strict: false,
waypoints: [
{
position: 0,
address: {
locality: 'Nice',
postalCode: '06000',
country: 'France',
coordinates: {
lat: 43.7102,
lon: 7.262,
},
},
},
{
position: 1,
address: {
locality: 'Marseille',
postalCode: '13000',
country: 'France',
coordinates: {
lat: 43.2965,
lon: 5.3698,
},
},
},
],
pause: false,
};
const adToCreate: AdEntity = AdEntity.create(createAdProps);
await adRepository.insert(adToCreate);
const afterCount = await prismaService.ad.count();
expect(afterCount - beforeCount).toBe(1);
});
it('should create a recurrent ad', async () => {
const beforeCount = await prismaService.ad.count();
const createAdProps: CreateAdProps = {
userId: 'b4b56444-f8d3-4110-917c-e37bba77f383',
driver: true,
passenger: false,
frequency: Frequency.RECURRENT,
fromDate: '2023-02-01',
toDate: '2024-01-31',
schedule: [
{
day: 1,
time: '08:00',
margin: 900,
},
{
day: 2,
time: '08:00',
margin: 900,
},
{
day: 3,
time: '09:00',
margin: 900,
},
{
day: 4,
time: '08:00',
margin: 900,
},
{
day: 5,
time: '08:00',
margin: 900,
},
],
seatsProposed: 3,
seatsRequested: 1,
strict: false,
waypoints: [
{
position: 0,
address: {
locality: 'Nice',
postalCode: '06000',
country: 'France',
coordinates: {
lat: 43.7102,
lon: 7.262,
},
},
},
{
position: 1,
address: {
locality: 'Marseille',
postalCode: '13000',
country: 'France',
coordinates: {
lat: 43.2965,
lon: 5.3698,
},
},
},
],
pause: false,
};
const adToCreate: AdEntity = AdEntity.create(createAdProps);
await adRepository.insert(adToCreate);
const afterCount = await prismaService.ad.count();
expect(afterCount - beforeCount).toBe(1);
});
});
});