Merged in chore/SW-2878-extract-booking-confirmation-pag (pull request #2779)

Chore/SW-2878 extract booking confirmation pag

* chore(SW-2878): Moved booking confirmation page to booking-flow package

* chore(SW-2878): Fixed promo styles as per design

* chore(SW-2878): Kept tiny duplicate function to avoid export from booking-flow package


Approved-by: Anton Gunnarsson
This commit is contained in:
Hrishikesh Vaipurkar
2025-09-10 07:50:48 +00:00
parent c6da0fb8cb
commit a5790ee454
77 changed files with 410 additions and 371 deletions

View File

@@ -0,0 +1,137 @@
"use client"
import { CurrencyEnum } from "@scandic-hotels/common/constants/currency"
import { dt } from "@scandic-hotels/common/dt"
import PriceDetailsModal from "../../../components/PriceDetailsModal"
import { useBookingConfirmationStore } from "../../../stores/booking-confirmation"
import { mapToPrice } from "./mapToPrice"
import type { Price } from "../../../types/price"
export default function PriceDetails() {
const { bookingCode, currency, fromDate, rooms, vat, toDate } =
useBookingConfirmationStore((state) => ({
bookingCode: state.bookingCode ?? undefined,
currency: state.currencyCode,
fromDate: state.fromDate,
rooms: state.rooms,
toDate: state.toDate,
vat: state.vat,
}))
if (!rooms[0]) {
return null
}
const checkInDate = dt(fromDate).format("YYYY-MM-DD")
const checkOutDate = dt(toDate).format("YYYY-MM-DD")
const nights = dt(toDate)
.startOf("day")
.diff(dt(fromDate).startOf("day"), "days")
const totalPrice = rooms.reduce<Price>(
(total, room) => {
if (!room) {
return total
}
if (room.cheques) {
// CorporateCheque Booking
total.local.currency = CurrencyEnum.CC
total.local.price = total.local.price + room.cheques
} else if (room.roomPoints) {
// Redemption Booking
total.local.currency = CurrencyEnum.POINTS
total.local.price = total.local.price + room.roomPoints
} else if (room.vouchers) {
// Vouchers Booking
total.local.currency = CurrencyEnum.Voucher
total.local.price = total.local.price + room.vouchers
} else {
// Price Booking
total.local.price = total.local.price + room.totalPrice
}
// Corporate Cheque
if (room.cheques) {
if (room.roomPrice) {
total.local.additionalPrice =
(total.local.additionalPrice || 0) + room.totalPrice
total.local.additionalPriceCurrency = currency
} else {
const pkgsSum = room.packages.reduce(
(total, pkg) => total + pkg.totalPrice,
0
)
total.local.additionalPrice =
(total.local.additionalPrice || 0) + pkgsSum
const pkgsCurrency = room.packages.find(
(pkg) => pkg.currency
)?.currency
if (!total.local.additionalPriceCurrency) {
total.local.additionalPriceCurrency = pkgsCurrency ?? currency
}
}
}
// Redemption
if (room.roomPoints) {
if (room.roomPrice) {
total.local.additionalPrice =
(total.local.additionalPrice || 0) + room.totalPrice
total.local.additionalPriceCurrency = currency
} else {
const pkgsSum = room.packages.reduce(
(total, pkg) => total + pkg.totalPrice,
0
)
total.local.additionalPrice =
(total.local.additionalPrice || 0) + pkgsSum
const pkgsCurrency = room.packages.find(
(pkg) => pkg.currency
)?.currency
if (!total.local.additionalPriceCurrency) {
total.local.additionalPriceCurrency = pkgsCurrency ?? currency
}
}
}
// Voucher
if (room.vouchers && room.packages) {
const pkgsSum = room.packages.reduce(
(total, pkg) => total + pkg.totalPrice,
0
)
total.local.additionalPrice =
(total.local.additionalPrice || 0) + pkgsSum
const pkgsCurrency = room.packages.find((pkg) => pkg.currency)?.currency
if (!total.local.additionalPriceCurrency) {
total.local.additionalPriceCurrency = pkgsCurrency ?? currency
}
}
return total
},
{
local: {
currency,
price: 0,
},
requested: undefined,
}
)
const mappedRooms = mapToPrice(rooms, nights)
return (
<PriceDetailsModal
bookingCode={bookingCode}
fromDate={checkInDate}
rooms={mappedRooms}
toDate={checkOutDate}
totalPrice={totalPrice}
vat={vat}
defaultCurrency={currency}
/>
)
}

View File

@@ -0,0 +1,127 @@
import { BreakfastPackageEnum } from "@scandic-hotels/trpc/enums/breakfast"
import { ChildBedMapEnum } from "@scandic-hotels/trpc/enums/childBedMapEnum"
import { PackageTypeEnum } from "@scandic-hotels/trpc/enums/packages"
import {
type BreakfastPackage,
breakfastPackageSchema,
packageSchema,
} from "@scandic-hotels/trpc/routers/hotels/schemas/packages"
import type { Package } from "@scandic-hotels/trpc/types/packages"
import type { Room } from "../../../types/stores/booking-confirmation"
export function mapToPrice(rooms: (Room | null)[], nights: number) {
return rooms
.filter((room): room is Room => !!room)
.map((room) => {
let price
if (room.cheques) {
price = {
corporateCheque: {
additionalPricePerStay: room.roomPrice ? room.roomPrice : undefined,
currency: room.roomPrice ? room.currencyCode : undefined,
numberOfCheques: room.cheques,
},
}
} else if (room.roomPoints) {
price = {
redemption: {
additionalPricePerStay: room.roomPrice ? room.roomPrice : undefined,
currency: room.roomPrice ? room.currencyCode : undefined,
pointsPerNight: room.roomPoints / nights,
pointsPerStay: room.roomPoints,
},
}
} else if (room.vouchers) {
price = {
voucher: {
numberOfVouchers: room.vouchers,
},
}
} else {
price = {
regular: {
currency: room.currencyCode,
pricePerNight: room.roomPrice / nights,
pricePerStay: room.roomPrice,
},
}
}
let breakfast:
| false
| undefined
| Omit<BreakfastPackage, "requestedPrice">
if (room.breakfast) {
const breakfastPackage = breakfastPackageSchema.safeParse({
code: room.breakfast?.code,
description: room.breakfast?.description,
localPrice: {
currency: room.breakfast?.currency,
price: room.breakfast?.unitPrice,
totalPrice: room.breakfast?.totalPrice,
},
packageType:
room.breakfast?.code === BreakfastPackageEnum.REGULAR_BREAKFAST
? PackageTypeEnum.BreakfastAdult
: "",
requestedPrice: {
currency: room.breakfast?.currency,
price: room.breakfast?.unitPrice,
totalPrice: room.breakfast?.totalPrice,
},
})
if (breakfastPackage.success) {
breakfast = breakfastPackage.data
}
}
if (!room.breakfastIncluded && !breakfast) {
breakfast = false
}
const packages = room.roomFeatures
?.map((featPkg) => {
const pkg = packageSchema.safeParse({
code: featPkg.code,
description: featPkg.description,
inventories: [],
localPrice: {
currency: featPkg.currency,
price: featPkg.unitPrice,
totalPrice: featPkg.totalPrice,
},
requestedPrice: {
currency: featPkg.currency,
price: featPkg.unitPrice,
totalPrice: featPkg.totalPrice,
},
})
if (pkg.success) {
return pkg.data
}
return null
})
.filter((pkg): pkg is Package => !!pkg)
return {
...room,
adults: room.adults,
bedType: {
description: room.bedDescription,
roomTypeCode: room.roomTypeCode || "",
type: room.bedType,
},
breakfast,
breakfastIncluded: room.rateDefinition.breakfastIncluded,
childrenInRoom: room.childrenAges?.map((age) => ({
age,
bed: ChildBedMapEnum.UNKNOWN,
})),
packages,
price,
roomType: room.name,
}
})
}