Ticket generation updates

This commit is contained in:
Stephanos A
2026-07-22 10:29:48 +03:00
parent 0d8e122de7
commit 838cedae0d
3 changed files with 41 additions and 27 deletions

View File

@@ -373,33 +373,37 @@ export class TicketsService {
await this.prisma.ticket.deleteMany({ where: { bookingId } });
// Generate one ticket per unique passenger (grouped by passengerName)
// Generate one ticket per passenger per leg.
// Round-trip / transit bookings have seats on multiple legs — each leg needs its own
// ticket so the voucher can match by (passengerName, leg) and gate scanners can
// validate each leg independently.
const tickets = [];
// Group seats by passenger
const passengerSeatsMap = new Map<string, any[]>();
// Group seats by (passengerName, leg)
const passengerLegSeatsMap = new Map<string, any[]>();
for (const bookingSeat of (booking as any).seats) {
const key = bookingSeat.passengerName;
if (!passengerSeatsMap.has(key)) {
passengerSeatsMap.set(key, []);
const key = `${bookingSeat.passengerName}|${bookingSeat.leg ?? 1}`;
if (!passengerLegSeatsMap.has(key)) {
passengerLegSeatsMap.set(key, []);
}
passengerSeatsMap.get(key)!.push(bookingSeat);
passengerLegSeatsMap.get(key)!.push(bookingSeat);
}
// Create one ticket per passenger
for (const [passengerName, passengerSeats] of passengerSeatsMap.entries()) {
// Use first seat for primary data
const primarySeat = passengerSeats[0];
const barcodePayload = `${booking.bookingRef}${primarySeat.seatId.substring(0, 8).toUpperCase()}`;
// Create one ticket per (passenger, leg)
for (const [key, legSeats] of passengerLegSeatsMap.entries()) {
const [passengerName] = key.split('|');
const primarySeat = legSeats[0];
const leg = primarySeat.leg ?? 1;
const barcodePayload = `${booking.bookingRef}${primarySeat.seatId.substring(0, 8).toUpperCase()}L${leg}`;
// Re-encode QR with ticketNumber included
const qrDataWithTicket = JSON.stringify({
ref: booking.bookingRef,
ticketNumber: barcodePayload,
type: booking.bookingType,
passenger: passengerName,
seats: passengerSeats.map(ps => ({
leg,
seats: legSeats.map(ps => ({
seat: ps.seat?.seatNumber,
coach: ps.seat?.coach?.number,
leg: ps.leg || 1,
@@ -414,7 +418,7 @@ export class TicketsService {
bookingRef: booking.bookingRef,
passengerName,
seatId: primarySeat.seatId,
leg: primarySeat.leg || 1,
leg,
scheduleId: primarySeat.scheduleId || booking.scheduleId,
qrPayload: qrPayloadFinal,
barcodePayload,