feat: turn search_trips into the website's travel search
This commit is contained in:
1 parent
bfdedefae3
commit
4ab2714bde
12 files changed
+693
-151
No files matched your search
@@ -0,0 +1,41 @@
|
||||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace App\Enum;
|
||||
|
||||
/**
|
||||
* The accommodation type of a TYPO3 hotel record (`type` in the content feed), as the
|
||||
* website's travel search filters it ("Unterkunft"). Values and labels follow the website's
|
||||
* Hotel::$typeLabels.
|
||||
*/
|
||||
enum HotelType: int
|
||||
{
|
||||
case HolidayFlat = 1;
|
||||
case SportsClub = 2;
|
||||
case Apartment = 3;
|
||||
case GuestHouse = 4;
|
||||
case Pension = 5;
|
||||
|
||||
public function label(): string
|
||||
{
|
||||
return match ($this) {
|
||||
self::HolidayFlat => 'Ferienwohnung',
|
||||
self::SportsClub => 'Sportclub',
|
||||
self::Apartment => 'Apartment',
|
||||
self::GuestHouse => 'Gästehaus',
|
||||
self::Pension => 'Pension',
|
||||
};
|
||||
}
|
||||
|
||||
public static function fromLabel(string $label): ?self
|
||||
{
|
||||
foreach (self::cases() as $case) {
|
||||
if (0 === strcasecmp($case->label(), trim($label))) {
|
||||
return $case;
|
||||
}
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,59 @@
|
||||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace App\Enum;
|
||||
|
||||
/**
|
||||
* Room type as the website's travel search filters it ("Zimmerarten").
|
||||
*
|
||||
* Taken from the room's capacity, as TYPO3's RoomTypeResolver does since the room-code
|
||||
* mapping was retired: `maxPax` 1-8 maps directly, 9 and up is "9er+". A bed shared with
|
||||
* other customers is sold per bed (`maxPax` 1), so it is recognised by its label instead;
|
||||
* without that, a bed in a dorm would count as an Einzelzimmer.
|
||||
*/
|
||||
enum RoomType: string
|
||||
{
|
||||
case ForOne = 'EZ';
|
||||
case ForTwo = 'DZ';
|
||||
case ForThree = '3er';
|
||||
case ForFour = '4er';
|
||||
case ForFive = '5er';
|
||||
case ForSix = '6er';
|
||||
case ForSeven = '7er';
|
||||
case ForEight = '8er';
|
||||
case ForNinePlus = '9er+';
|
||||
case WithOthers = 'mit anderen';
|
||||
|
||||
/** The "Babypreis 0-2 Jährige" row: priced like a room, but not one. */
|
||||
public const BABY_CODE = 'Baby';
|
||||
|
||||
/** Label phrases (lower case) that mark a bed shared with other customers. */
|
||||
private const WITH_OTHERS_MARKERS = ['bett im', 'mit ander'];
|
||||
|
||||
/**
|
||||
* Null for the baby row, which is not a room.
|
||||
*/
|
||||
public static function classify(?string $code, ?string $label, ?int $maxPax, ?int $minPax): ?self
|
||||
{
|
||||
if (self::BABY_CODE === trim((string) $code)) {
|
||||
return null;
|
||||
}
|
||||
|
||||
$label = mb_strtolower((string) $label);
|
||||
foreach (self::WITH_OTHERS_MARKERS as $marker) {
|
||||
if (str_contains($label, $marker)) {
|
||||
return self::WithOthers;
|
||||
}
|
||||
}
|
||||
|
||||
$pax = ($maxPax ?? 0) > 0 ? (int) $maxPax : (int) $minPax;
|
||||
|
||||
return match (true) {
|
||||
$pax >= 9 => self::ForNinePlus,
|
||||
$pax >= 1 => [1 => self::ForOne, self::ForTwo, self::ForThree, self::ForFour, self::ForFive, self::ForSix, self::ForSeven, self::ForEight][$pax],
|
||||
// No usable occupancy: TYPO3 files it under "mit anderen" as well.
|
||||
default => self::WithOthers,
|
||||
};
|
||||
}
|
||||
}
|
||||
Reference in new issue
Block a user