diff --git a/apps/edr-freight-api/src/modules/bookings/booking-transition.service.ts b/apps/edr-freight-api/src/modules/bookings/booking-transition.service.ts index 149875e6e..181c47b2d 100644 --- a/apps/edr-freight-api/src/modules/bookings/booking-transition.service.ts +++ b/apps/edr-freight-api/src/modules/bookings/booking-transition.service.ts @@ -927,13 +927,6 @@ export class BookingTransitionService { "OPERATION_CHANGES_REQUESTED", ]); - // A company sitting on another unpaid hold commits nothing new — this is - // the moment export capacity locks, so the lock applies here too. - // Government bookings allocate without paying and are exempt. - if (!booking.isGovernment) { - await this.bookingsService.assertNoUnpaidHold(booking.companyId); - } - // A bare initiated instance (clearance-first flow) carries no cargo or // price — it must go through the contract completion endpoint, which // persists cargo, prices, invoices and only then lands here itself. diff --git a/apps/edr-freight-api/src/modules/bookings/bookings.repository.ts b/apps/edr-freight-api/src/modules/bookings/bookings.repository.ts index 185a6aaa7..35f84e419 100644 --- a/apps/edr-freight-api/src/modules/bookings/bookings.repository.ts +++ b/apps/edr-freight-api/src/modules/bookings/bookings.repository.ts @@ -1396,16 +1396,6 @@ export class BookingsRepository extends BaseRepository { .getMany(); } - /** Open unpaid holds (wagons reserved, pay window running) for a company. */ - countUnpaidHoldsForCompany(companyId: string): Promise { - return this.repository.count({ - where: { - companyId, - status: In(['SELECTED_FOR_BATCH', 'AWAITING_PAYMENT']), - }, - }); - } - /** Bookings currently reserved (SELECTED_FOR_BATCH) against a schedule. */ findReservedForSchedule(scheduleId: string): Promise { return this.repository diff --git a/apps/edr-freight-api/src/modules/bookings/bookings.service.ts b/apps/edr-freight-api/src/modules/bookings/bookings.service.ts index ed134d683..12c56ac13 100644 --- a/apps/edr-freight-api/src/modules/bookings/bookings.service.ts +++ b/apps/edr-freight-api/src/modules/bookings/bookings.service.ts @@ -917,24 +917,6 @@ export class BookingsService { return result.booking; } - /** - * A company with an open unpaid hold (SELECTED_FOR_BATCH — wagons reserved, - * pay window running) may not take more capacity until it pays or the hold - * dies: otherwise one customer can lock a train's wagons over and over - * without ever paying. EXPIRED / CANCELLED holds free the lock. - */ - async assertNoUnpaidHold(companyId?: string | null): Promise { - if (!companyId) return; - const holds = - await this.bookingsRepository.countUnpaidHoldsForCompany(companyId); - if (holds > 0) { - throw new ConflictException( - 'You already have a booking waiting for payment. Pay it or cancel it ' + - 'before making a new booking.', - ); - } - } - /** Create a new freight booking. */ async create( dto: CreateBookingDto, @@ -997,10 +979,6 @@ export class BookingsService { companyId = company.id; } - // Government bookings allocate without paying, so the unpaid-hold lock - // only applies to commercial companies. - if (!isGovernment) await this.assertNoUnpaidHold(companyId); - if (dto.trainScheduleId) { // Staff manual pin: the schedule must be OPEN and on the same route. const schedule = await this.dataSource diff --git a/apps/edr-freight-api/src/modules/contracts/contract-booking.service.ts b/apps/edr-freight-api/src/modules/contracts/contract-booking.service.ts index 8da28e400..7e0a23e3f 100644 --- a/apps/edr-freight-api/src/modules/contracts/contract-booking.service.ts +++ b/apps/edr-freight-api/src/modules/contracts/contract-booking.service.ts @@ -109,23 +109,6 @@ export class ContractBookingService { private readonly bookingTransitionService: BookingTransitionService, ) {} - /** - * Mirrors BookingsService.assertNoUnpaidHold for the contract booking paths: - * a company sitting on an unpaid hold (SELECTED_FOR_BATCH) books nothing new - * until it pays or the hold dies. - */ - private async assertNoUnpaidHold(companyId?: string | null): Promise { - if (!companyId) return; - const holds = - await this.bookingsRepository.countUnpaidHoldsForCompany(companyId); - if (holds > 0) { - throw new ConflictException( - 'You already have a booking waiting for payment. Pay it or cancel it ' + - 'before making a new booking.', - ); - } - } - async createUnderContract( contractId: string, dto: CreateBookingUnderContractDto, @@ -186,8 +169,6 @@ export class ContractBookingService { // remainder; the customer cannot start any other booking on the contract. // If the remainder splits again the same rule repeats until the cap is // exhausted and the contract completes. - await this.assertNoUnpaidHold(contract.companyId); - if (contract.contractKind === 'ONE_TIME') { if (await this.hasSplitBooking(contractId)) { await this.assertExactRemainder(contract, dto); @@ -475,7 +456,6 @@ export class ContractBookingService { ); } } - await this.assertNoUnpaidHold(contract.companyId); const route = await this.resolveRoute(contract, dto.contractRouteId);