@qite/tide-booking-component 1.4.53 → 1.4.55

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@qite/tide-booking-component",
3
- "version": "1.4.53",
3
+ "version": "1.4.55",
4
4
  "description": "React Booking wizard & Booking product component for Tide",
5
5
  "main": "build/build-cjs/index.js",
6
6
  "types": "build/build-cjs/src/index.d.ts",
@@ -28,7 +28,7 @@
28
28
  "devDependencies": {
29
29
  "@jsonurl/jsonurl": "^1.1.4",
30
30
  "@popperjs/core": "^2.10.2",
31
- "@qite/tide-client": "^1.1.138",
31
+ "@qite/tide-client": "^1.1.141",
32
32
  "@reduxjs/toolkit": "^2.8.2",
33
33
  "@rollup/plugin-commonjs": "^19.0.1",
34
34
  "@rollup/plugin-json": "^4.1.0",
@@ -2,12 +2,13 @@ import React, { useEffect, useState } from 'react';
2
2
  import LanguageSwitcher from '../components/LanguageSwitcher';
3
3
  import Icon from '../components/icon';
4
4
  import { NavbarProps, NavItem } from '../navbar/types';
5
+ import { getTranslations } from '../../shared/utils/localization-util';
5
6
 
6
7
  const Navbar: React.FC<NavbarProps> = ({ currentPath, logo, topLinks, items, language, languages, onLanguageChange, onSearch }) => {
7
8
  const [menuOpen, setMenuOpen] = useState(false);
8
9
  const [query, setQuery] = useState('');
9
10
  const [activeMobileGroup, setActiveMobileGroup] = useState<string>();
10
-
11
+ const translations = getTranslations(language.code ?? 'en-GB');
11
12
  const normalizePath = (path: string) => path.replace(/\/+$/, '');
12
13
 
13
14
  useEffect(() => {
@@ -221,7 +222,7 @@ const Navbar: React.FC<NavbarProps> = ({ currentPath, logo, topLinks, items, lan
221
222
  type="search"
222
223
  value={query}
223
224
  onChange={(e) => setQuery(e.target.value)}
224
- placeholder="Search…"
225
+ placeholder={translations.NAVBAR.SEARCH}
225
226
  autoComplete="off"
226
227
  />
227
228
  <button type="button" className="nav__search__clear" aria-label="Clear search" onClick={() => setQuery('')}>
@@ -99,7 +99,6 @@ const QSMContainer: React.FC = () => {
99
99
 
100
100
  // Filter out undefined fields before passing to addSearchFieldsToPayload
101
101
  const searchFields = [departureAirport, destinationAirport, returnAirport, destination].filter((field): field is BaseFieldConfig => field !== undefined);
102
-
103
102
  addSearchFieldsToPayload(payload, searchFields, qsmState);
104
103
  onSubmit(payload);
105
104
  console.log('Submitted QSM data:', payload);
@@ -219,40 +218,39 @@ const QSMContainer: React.FC = () => {
219
218
  </button>
220
219
  </div>
221
220
  <div className="qsm__filter">
222
- {qsmType === 'hotel' ||
223
- (qsmType == 'hotel-flight' && (
224
- <div className="radiobutton-group qsm__filter__inputgroup">
225
- <div className="radiobutton">
226
- <label className="radiobutton__label">
227
- <input
228
- type="radio"
229
- name="numberOfAccommodations"
230
- // onChange={handleMainBookerChange}
231
- // onBlur={formik.handleBlur}
232
- value=""
233
- checked={true}
234
- readOnly
235
- className="radiobutton__input"
236
- />
237
- <span>{translations.QSM.ONE_ACCOMMODATION}</span>
238
- </label>
239
- </div>
240
- <div className="radiobutton">
241
- <label className="radiobutton__label">
242
- <input
243
- type="radio"
244
- name="numberOfAccommodations"
245
- // onChange={handleMainBookerChange}
246
- // onBlur={formik.handleBlur}
247
- value=""
248
- className="radiobutton__input"
249
- disabled={true}
250
- />
251
- <span>{translations.QSM.MULTIPLE_ACCOMMODATIONS}</span>
252
- </label>
253
- </div>
221
+ {(qsmType === 'hotel' || qsmType === 'hotel-flight') && (
222
+ <div className="radiobutton-group qsm__filter__inputgroup">
223
+ <div className="radiobutton">
224
+ <label className="radiobutton__label">
225
+ <input
226
+ type="radio"
227
+ name="numberOfAccommodations"
228
+ // onChange={handleMainBookerChange}
229
+ // onBlur={formik.handleBlur}
230
+ value=""
231
+ checked={true}
232
+ readOnly
233
+ className="radiobutton__input"
234
+ />
235
+ <span>{translations.QSM.ONE_ACCOMMODATION}</span>
236
+ </label>
237
+ </div>
238
+ <div className="radiobutton">
239
+ <label className="radiobutton__label">
240
+ <input
241
+ type="radio"
242
+ name="numberOfAccommodations"
243
+ // onChange={handleMainBookerChange}
244
+ // onBlur={formik.handleBlur}
245
+ value=""
246
+ className="radiobutton__input"
247
+ disabled={true}
248
+ />
249
+ <span>{translations.QSM.MULTIPLE_ACCOMMODATIONS}</span>
250
+ </label>
254
251
  </div>
255
- ))}
252
+ </div>
253
+ )}
256
254
  {qsmType === 'flight' && (
257
255
  <div className="radiobutton-group qsm__filter__inputgroup">
258
256
  {allowOneWay && (
@@ -44,7 +44,9 @@ const mapSearchResult = (searchResult: BookingPackageItem, cmsItem: any, languag
44
44
  image: cmsItem?.content?.images?.thumbnailPicture?.url,
45
45
  description: cmsItem?.content?.descriptions?.introductionTitle || '',
46
46
  location:
47
- searchResult.locationName && searchResult.countryName ? `${searchResult.locationName}, ${searchResult.countryName}` : cmsItem?.parentItem?.name || '',
47
+ searchResult.locationName || searchResult.regionName
48
+ ? `${searchResult.locationName || searchResult.regionName}${searchResult.countryName && `, ${searchResult.countryName}`}`
49
+ : cmsItem?.parentItem?.name || '',
48
50
  price: formatPrice(searchResult.price, searchResult.currencyCode, languageCode),
49
51
  ctaText: translations?.SRP.VIEW_DETAILS,
50
52
  days: calculateNights(searchResult.stayFromDate, searchResult.stayToDate, translations),
@@ -2,7 +2,6 @@ import React, { useContext, useEffect, useRef, useState } from 'react';
2
2
  import { useDispatch, useSelector } from 'react-redux';
3
3
  import { SearchResultsRootState } from '../../store/search-results-store';
4
4
  import SearchResultsConfigurationContext from '../../search-results-configuration-context';
5
-
6
5
  import {
7
6
  resetFilters,
8
7
  setSortKey,
@@ -13,10 +12,9 @@ import {
13
12
  setEntry,
14
13
  setFlyInIsOpen
15
14
  } from '../../store/search-results-slice';
16
- import { Filter, SortingOption } from '../../types';
15
+ import { Filter, SortByType } from '../../types';
17
16
  import useMediaQuery from '../../../shared/utils/use-media-query-util';
18
17
  import ItemPicker from '../item-picker';
19
-
20
18
  import { TideClientConfig, details, detailsWL, getEntryLight, search } from '@qite/tide-client';
21
19
  import {
22
20
  BookingPackageDestination,
@@ -42,6 +40,7 @@ import FlightResults from '../flight/flight-results';
42
40
  import { getTranslations } from '../../../shared/utils/localization-util';
43
41
  import { FlightSearchProvider } from '../flight/flight-search-context';
44
42
  import FlightResultsContainer from './flight-search-results';
43
+ import Filters from '../filters/filters';
45
44
 
46
45
  const SearchResultsContainer: React.FC = () => {
47
46
  const dispatch = useDispatch();
@@ -63,10 +62,11 @@ const SearchResultsContainer: React.FC = () => {
63
62
 
64
63
  const panelRef = useRef<HTMLDivElement | null>(null);
65
64
 
66
- const sortingOptions: SortingOption[] = [
67
- { key: 'price-asc', label: translations.SRP.PRICE_ASC },
68
- { key: 'price-desc', label: translations.SRP.PRICE_DESC },
69
- { key: 'departure-date', label: translations.SRP.DEPARTURE_ASC }
65
+ const sortByTypes: SortByType[] = [
66
+ { direction: 'asc', label: 'price' } as SortByType,
67
+ { direction: 'desc', label: 'price' } as SortByType,
68
+ { direction: 'asc', label: 'departure' } as SortByType,
69
+ { direction: 'desc', label: 'departure' } as SortByType
70
70
  ];
71
71
 
72
72
  const handleFlyInToggle = (isOpen: boolean) => {
@@ -144,7 +144,7 @@ const SearchResultsContainer: React.FC = () => {
144
144
  return searchRequest;
145
145
  };
146
146
 
147
- const buildSearchFromQueryParams = (params: URLSearchParams): BookingPackageRequest<BookingPackageSearchRequest> => {
147
+ const buildSearchFromQueryParams = (params: URLSearchParams): BookingPackageRequest<BookingPackageSearchRequest> | null => {
148
148
  let from = getDateFromParams(params, 'fromDate');
149
149
  let to = getDateFromParams(params, 'toDate');
150
150
  const rooms = getRoomsFromParams(params, 'rooms');
@@ -157,11 +157,9 @@ const SearchResultsContainer: React.FC = () => {
157
157
 
158
158
  // temp hardcoded params
159
159
  if (!from || !to) {
160
- from = '2026-04-07';
161
- to = '2026-04-13';
162
- }
163
- if (!country && !region && !oord && !city) {
164
- region = 1;
160
+ console.error('Missing fromDate or toDate in query params, using default values');
161
+
162
+ return null;
165
163
  }
166
164
 
167
165
  if (typeof window !== 'undefined') {
@@ -206,14 +204,14 @@ const SearchResultsContainer: React.FC = () => {
206
204
  toDate: to,
207
205
  earliestFromOffset: 0,
208
206
  latestToOffset: 0,
209
- includeFlights: true,
210
- regimeCodes:
211
- filters
212
- .find((f) => f.property === 'regime')
213
- ?.options?.filter((o) => o.isChecked)
214
- .flatMap((o) => o.value.toString()) || [],
215
- minPrice: filters.find((f) => f.property === 'price')?.selectedMin,
216
- maxPrice: filters.find((f) => f.property === 'price')?.selectedMax,
207
+ includeFlights: context!.type === 'hotel-flight' ? true : false,
208
+ // regimeCodes:
209
+ // filters
210
+ // .find((f) => f.property === 'regime')
211
+ // ?.options?.filter((o) => o.isChecked)
212
+ // .flatMap((o) => o.value.toString()) || [],
213
+ // minPrice: filters.find((f) => f.property === 'price')?.selectedMin,
214
+ // maxPrice: filters.find((f) => f.property === 'price')?.selectedMax,
217
215
  useExactDates: true,
218
216
  onlyCachedResults: false,
219
217
  includeAllAllotments: true,
@@ -290,7 +288,7 @@ const SearchResultsContainer: React.FC = () => {
290
288
 
291
289
  // seperate Search
292
290
  useEffect(() => {
293
- const runHotelFlightSearch = async () => {
291
+ const runHotelSearch = async () => {
294
292
  dispatch(setIsLoading(true));
295
293
  try {
296
294
  if (!context) {
@@ -315,7 +313,13 @@ const SearchResultsContainer: React.FC = () => {
315
313
  dispatch(setEntry({ entry: entryLight }));
316
314
  searchRequest = buildSearchFromEntry(entryLight);
317
315
  } else {
318
- searchRequest = buildSearchFromQueryParams(params);
316
+ const rq = buildSearchFromQueryParams(params);
317
+
318
+ if (!rq) {
319
+ throw new Error('Invalid search parameters');
320
+ }
321
+
322
+ searchRequest = rq;
319
323
  }
320
324
 
321
325
  const packageSearchResults = await search(config, searchRequest);
@@ -350,8 +354,8 @@ const SearchResultsContainer: React.FC = () => {
350
354
  };
351
355
 
352
356
  if (!context?.showMockup) {
353
- if (context?.type === 'hotel-flight') {
354
- runHotelFlightSearch();
357
+ if (context?.type === 'hotel-flight' || context?.type === 'hotel') {
358
+ runHotelSearch();
355
359
  }
356
360
  }
357
361
  }, [location.search, searchTrigger]);
@@ -393,7 +397,7 @@ const SearchResultsContainer: React.FC = () => {
393
397
  productCode: selectedItem.code,
394
398
  fromDate: selectedItem.fromDate,
395
399
  toDate: selectedItem.toDate,
396
- includeFlights: true,
400
+ includeFlights: context!.type === 'hotel-flight' ? true : false,
397
401
  includeHotels: true,
398
402
  includePaxTypes: true,
399
403
  checkExternalAvailability: true,
@@ -434,24 +438,26 @@ const SearchResultsContainer: React.FC = () => {
434
438
  <FlyIn srpType={context.type} isOpen={flyInIsOpen} setIsOpen={handleFlyInToggle} onPanelRef={(el) => (panelRef.current = el)} />
435
439
  </FlightSearchProvider>
436
440
  )}
437
- {context.type === 'hotel-flight' && (
441
+ {(context.type === 'hotel-flight' || context.type === 'hotel' || context.type === 'roundTrip') && (
438
442
  <>
439
- {/* {context.showFilters && (
440
- <Filters
441
- filters={filters}
442
- isOpen={filtersOpen}
443
- handleSetIsOpen={() => setFiltersOpen(!filtersOpen)}
444
- handleApplyFilters={() => setSearchTrigger((prev) => prev + 1)}
445
- isLoading={isLoading}
446
- />
447
- )} */}
448
- <Itinerary isOpen={itineraryOpen} handleSetIsOpen={() => setItineraryOpen(!itineraryOpen)} isLoading={isLoading} />
443
+ {context.type != 'hotel-flight' && context.showFilters && (
444
+ <Filters
445
+ filters={filters}
446
+ isOpen={filtersOpen}
447
+ handleSetIsOpen={() => setFiltersOpen(!filtersOpen)}
448
+ handleApplyFilters={() => setSearchTrigger((prev) => prev + 1)}
449
+ isLoading={isLoading}
450
+ />
451
+ )}
452
+ {context.type === 'hotel-flight' && (
453
+ <Itinerary isOpen={itineraryOpen} handleSetIsOpen={() => setItineraryOpen(!itineraryOpen)} isLoading={isLoading} />
454
+ )}
449
455
  {/* ---------------- Results ---------------- */}
450
456
  <div className="search__results">
451
457
  {isMobile && (
452
458
  <div className="search__result-row">
453
459
  <div className="search__results__actions">
454
- {context.showFilters && (
460
+ {context.type != 'hotel-flight' && context.showFilters && (
455
461
  <div className="cta cta--filter" onClick={() => setFiltersOpen(true)}>
456
462
  <Icon name="ui-filter" className="mobile-filters-button__icon" height={16} />
457
463
  {translations.SRP.FILTERS}
@@ -464,9 +470,9 @@ const SearchResultsContainer: React.FC = () => {
464
470
  </div>
465
471
  )}
466
472
  </div>
467
- {sortingOptions && sortingOptions.length > 0 && (
473
+ {sortByTypes && sortByTypes.length > 0 && (
468
474
  <ItemPicker
469
- items={sortingOptions}
475
+ items={sortByTypes}
470
476
  selection={sortKey || undefined}
471
477
  label={translations.SRP.SORTBY}
472
478
  placeholder={translations.SRP.SORTBY}
@@ -476,7 +482,6 @@ const SearchResultsContainer: React.FC = () => {
476
482
  )}
477
483
  </div>
478
484
  )}
479
-
480
485
  <div className="search__result-row">
481
486
  <span className="search__result-row-text">
482
487
  {!isLoading && (
@@ -485,10 +490,10 @@ const SearchResultsContainer: React.FC = () => {
485
490
  </>
486
491
  )}
487
492
  </span>
488
- {!isMobile && sortingOptions && sortingOptions.length > 0 && (
493
+ {!isMobile && sortByTypes && sortByTypes.length > 0 && (
489
494
  <div className="search__result-row-filter">
490
495
  <ItemPicker
491
- items={sortingOptions}
496
+ items={sortByTypes}
492
497
  selection={sortKey || undefined}
493
498
  label={translations.SRP.SORTBY}
494
499
  placeholder={translations.SRP.SORTBY}
@@ -504,13 +509,13 @@ const SearchResultsContainer: React.FC = () => {
504
509
 
505
510
  {context.showRoundTripResults && context.showMockup && <RoundTripResults />}
506
511
 
507
- {context.showFlightResults && bookingPackageDetails?.outwardFlights && (
512
+ {context.type === 'hotel-flight' && context.showFlightResults && bookingPackageDetails?.outwardFlights && (
508
513
  <FlightResults flights={bookingPackageDetails?.outwardFlights} isDeparture={true} />
509
514
  )}
510
515
 
511
516
  {context.showHotelAccommodationResults && <HotelAccommodationResults isLoading={isLoading} context={context} />}
512
517
 
513
- {context.showFlightResults && bookingPackageDetails?.returnFlights && (
518
+ {context.type === 'hotel-flight' && context.showFlightResults && bookingPackageDetails?.returnFlights && (
514
519
  <FlightResults flights={bookingPackageDetails?.returnFlights} isDeparture={false} />
515
520
  )}
516
521
  </div>
@@ -1,5 +1,5 @@
1
1
  import React, { ReactNode } from 'react';
2
- import { Filter, SearchResult, SearchResultsConfiguration, SortingOption } from '../../types';
2
+ import { Filter, SearchResult, SearchResultsConfiguration } from '../../types';
3
3
  import SearchResults from '../..';
4
4
  import { Footer, Navbar } from '../../../../src';
5
5
  import { TideLogo, language, languages, topLinks, navItems } from '../../../../src/content/navbar/placeholderData';
@@ -249,6 +249,9 @@
249
249
  "LABEL_CREATING": "جارٍ إنشاء العرض…",
250
250
  "LABEL_PRINTING": "جارٍ إنشاء ملف PDF…"
251
251
  },
252
+ "NAVBAR": {
253
+ "SEARCH": "بحث"
254
+ },
252
255
  "QSM": {
253
256
  "MULTIDESTINATION": "وجهات متعددة",
254
257
  "PACKAGES": "باقات",
@@ -249,6 +249,9 @@
249
249
  "LABEL_CREATING": "Genererer tilbud…",
250
250
  "LABEL_PRINTING": "Genererer PDF…"
251
251
  },
252
+ "NAVBAR": {
253
+ "SEARCH": "Søg"
254
+ },
252
255
  "QSM": {
253
256
  "MULTIDESTINATION": "Flere destinationer",
254
257
  "PACKAGES": "Pakkerejser",
@@ -249,6 +249,9 @@
249
249
  "LABEL_CREATING": "Angebot wird erstellt…",
250
250
  "LABEL_PRINTING": "PDF wird erstellt…"
251
251
  },
252
+ "NAVBAR": {
253
+ "SEARCH": "Suche"
254
+ },
252
255
  "QSM": {
253
256
  "MULTIDESTINATION": "Mehrere Reiseziele",
254
257
  "PACKAGES": "Reisepakete",
@@ -253,6 +253,9 @@
253
253
  "LABEL_CREATING": "Generating offer…",
254
254
  "LABEL_PRINTING": "Generating PDF…"
255
255
  },
256
+ "NAVBAR": {
257
+ "SEARCH": "SEARCH"
258
+ },
256
259
  "QSM": {
257
260
  "MULTIDESTINATION": "Multidestination",
258
261
  "PACKAGES": "Packages",
@@ -249,6 +249,9 @@
249
249
  "LABEL_CREATING": "Generando presupuesto…",
250
250
  "LABEL_PRINTING": "Generando PDF…"
251
251
  },
252
+ "NAVBAR": {
253
+ "SEARCH": "Buscar"
254
+ },
252
255
  "QSM": {
253
256
  "MULTIDESTINATION": "Multidestino",
254
257
  "PACKAGES": "Paquetes",
@@ -253,6 +253,9 @@
253
253
  "LABEL_CREATING": "Génération du devis…",
254
254
  "LABEL_PRINTING": "Génération du PDF…"
255
255
  },
256
+ "NAVBAR": {
257
+ "SEARCH": "Rechercher"
258
+ },
256
259
  "QSM": {
257
260
  "MULTIDESTINATION": "Multi-destinations",
258
261
  "PACKAGES": "Forfaits",
@@ -249,6 +249,9 @@
249
249
  "LABEL_CREATING": "Génération du devis…",
250
250
  "LABEL_PRINTING": "Génération du PDF…"
251
251
  },
252
+ "NAVBAR": {
253
+ "SEARCH": "Rechercher"
254
+ },
252
255
  "QSM": {
253
256
  "MULTIDESTINATION": "Multi-destinations",
254
257
  "PACKAGES": "Forfaits",
@@ -249,6 +249,9 @@
249
249
  "LABEL_CREATING": "Búið til tilboð…",
250
250
  "LABEL_PRINTING": "Búið til PDF…"
251
251
  },
252
+ "NAVBAR": {
253
+ "SEARCH": "Leita"
254
+ },
252
255
  "QSM": {
253
256
  "MULTIDESTINATION": "Margir áfangastaðir",
254
257
  "PACKAGES": "Pakkar",
@@ -249,6 +249,9 @@
249
249
  "LABEL_CREATING": "Generazione del preventivo…",
250
250
  "LABEL_PRINTING": "Generazione del PDF…"
251
251
  },
252
+ "NAVBAR": {
253
+ "SEARCH": "Cerca"
254
+ },
252
255
  "QSM": {
253
256
  "MULTIDESTINATION": "Multidestinazione",
254
257
  "PACKAGES": "Pacchetti",
@@ -249,6 +249,9 @@
249
249
  "LABEL_CREATING": "見積もりを生成中…",
250
250
  "LABEL_PRINTING": "PDFを生成中…"
251
251
  },
252
+ "NAVBAR": {
253
+ "SEARCH": "検索"
254
+ },
252
255
  "QSM": {
253
256
  "MULTIDESTINATION": "複数都市",
254
257
  "PACKAGES": "パッケージ",
@@ -253,6 +253,9 @@
253
253
  "LABEL_CREATING": "Offerte genereren...",
254
254
  "LABEL_PRINTING": "PDF genereren..."
255
255
  },
256
+ "NAVBAR": {
257
+ "SEARCH": "Zoeken"
258
+ },
256
259
  "QSM": {
257
260
  "MULTIDESTINATION": "Meerdere bestemmingen",
258
261
  "PACKAGES": "Pakketten",
@@ -249,6 +249,9 @@
249
249
  "LABEL_CREATING": "Offerte genereren…",
250
250
  "LABEL_PRINTING": "PDF genereren…"
251
251
  },
252
+ "NAVBAR": {
253
+ "SEARCH": "Zoeken"
254
+ },
252
255
  "QSM": {
253
256
  "MULTIDESTINATION": "Meerdere bestemmingen",
254
257
  "PACKAGES": "Pakketten",
@@ -249,6 +249,9 @@
249
249
  "LABEL_CREATING": "Genererer tilbud…",
250
250
  "LABEL_PRINTING": "Genererer PDF…"
251
251
  },
252
+ "NAVBAR": {
253
+ "SEARCH": "Søk"
254
+ },
252
255
  "QSM": {
253
256
  "MULTIDESTINATION": "Flere destinasjoner",
254
257
  "PACKAGES": "Pakker",
@@ -249,6 +249,9 @@
249
249
  "LABEL_CREATING": "Generowanie oferty…",
250
250
  "LABEL_PRINTING": "Generowanie PDF…"
251
251
  },
252
+ "NAVBAR": {
253
+ "SEARCH": "Szukaj"
254
+ },
252
255
  "QSM": {
253
256
  "MULTIDESTINATION": "Wiele kierunków",
254
257
  "PACKAGES": "Pakiety",
@@ -249,6 +249,9 @@
249
249
  "LABEL_CREATING": "A gerar orçamento…",
250
250
  "LABEL_PRINTING": "A gerar PDF…"
251
251
  },
252
+ "NAVBAR": {
253
+ "SEARCH": "Pesquisar"
254
+ },
252
255
  "QSM": {
253
256
  "MULTIDESTINATION": "Multidestino",
254
257
  "PACKAGES": "Pacotes",
@@ -249,6 +249,9 @@
249
249
  "LABEL_CREATING": "Skapar offert…",
250
250
  "LABEL_PRINTING": "Skapar PDF…"
251
251
  },
252
+ "NAVBAR": {
253
+ "SEARCH": "Sök"
254
+ },
252
255
  "QSM": {
253
256
  "MULTIDESTINATION": "Flera destinationer",
254
257
  "PACKAGES": "Paket",