Feat/SW-2271 hotel list filtering

* feat(SW-2271): Changes to hotel data types in preperation for filtering
* feat(SW-2271): Added filter and sort functionality

Approved-by: Matilda Landström
This commit is contained in:
Erik Tiekstra
2025-07-04 09:27:20 +00:00
parent 82e21af0d4
commit fa7214cb58
58 changed files with 1572 additions and 450 deletions

View File

@@ -48,8 +48,11 @@ import type {
RoomsAvailabilityOutputSchema,
} from "../../types/availability"
import type { BedTypeSelection } from "../../types/bedTypeSelection"
import type { Room as RoomCategory } from "../../types/hotel"
import type { DestinationPagesHotelData, HotelInput } from "../../types/hotel"
import type {
HotelInput,
HotelListingHotelData,
Room as RoomCategory,
} from "../../types/hotel"
import type {
CitiesGroupedByCountry,
CityLocation,
@@ -348,13 +351,15 @@ export async function getHotelsByHotelIds({
hotelIds,
lang,
serviceToken,
contentType = "hotel",
}: {
hotelIds: string[]
lang: Lang
serviceToken: string
contentType?: "hotel" | "restaurant" | "meeting"
}) {
const cacheClient = await getCacheClient()
const cacheKey = `${lang}:getHotelsByHotelIds:hotels:${hotelIds.sort().join(",")}`
const cacheKey = `${lang}:getHotelsByHotelIds:hotels:${contentType}:${hotelIds.sort().join(",")}`
return await cacheClient.cacheOrGet(
cacheKey,
@@ -362,7 +367,7 @@ export async function getHotelsByHotelIds({
const hotelPages = await getHotelPageUrls(lang)
const chunkedHotelIds = chunk(hotelIds, 10)
const hotels: DestinationPagesHotelData[] = []
const hotels: HotelListingHotelData[] = []
for (const hotelIdChunk of chunkedHotelIds) {
const chunkedHotels = await Promise.all(
hotelIdChunk.map(async (hotelId) => {
@@ -378,22 +383,59 @@ export async function getHotelsByHotelIds({
const hotelPage = hotelPages.find(
(page) => page.hotelId === hotelId
)
const { hotel, cities } = hotelResponse
const data: DestinationPagesHotelData = {
const { hotel, cities, additionalData } = hotelResponse
const content = {
description: hotel.hotelContent?.texts.descriptions?.short,
galleryImages: hotel.galleryImages,
url: hotelPage?.url ?? "",
openInNewTab: false,
}
if (contentType === "restaurant") {
const restaurantDescription =
additionalData?.restaurantsOverviewPage
.restaurantsContentDescriptionShort
const restaurantImages =
additionalData.restaurantImages?.heroImages
if (restaurantDescription) {
content.description = restaurantDescription
}
if (restaurantImages && restaurantImages.length > 0) {
content.galleryImages = restaurantImages
}
} else if (contentType === "meeting") {
const meetingDescription =
hotel.hotelContent.texts.meetingDescription?.short
const meetingImages =
additionalData?.conferencesAndMeetings?.heroImages
if (meetingDescription) {
content.description = meetingDescription
}
if (meetingImages && meetingImages.length > 0) {
content.galleryImages = meetingImages
}
}
const data: HotelListingHotelData = {
hotel: {
id: hotel.id,
galleryImages: hotel.galleryImages,
countryCode: hotel.countryCode,
galleryImages: content.galleryImages,
name: hotel.name,
tripadvisor: hotel.ratings?.tripAdvisor?.rating,
detailedFacilities: hotel.detailedFacilities || [],
tripadvisor: hotel.ratings?.tripAdvisor?.rating || null,
detailedFacilities: hotel.detailedFacilities.sort(
(a, b) => b.sortOrder - a.sortOrder
),
location: hotel.location,
hotelType: hotel.hotelType,
type: hotel.type,
address: hotel.address,
cityIdentifier: cities?.[0]?.cityIdentifier,
hotelDescription: hotel.hotelContent?.texts.descriptions?.short,
cityIdentifier: cities[0]?.cityIdentifier || null,
description: content.description || null,
},
url: hotelPage?.url ?? "",
url: content.url,
meetingUrl: additionalData.meetingRooms.meetingOnlineLink || null,
}
return data
@@ -402,9 +444,7 @@ export async function getHotelsByHotelIds({
hotels.push(...chunkedHotels)
}
return hotels.filter(
(hotel): hotel is DestinationPagesHotelData => !!hotel
)
return hotels.filter((hotel): hotel is HotelListingHotelData => !!hotel)
},
"1d"
)