Spaces:
Sleeping
Sleeping
File size: 2,115 Bytes
649703e | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 | from pydantic import BaseModel
from datetime import date
from typing import Optional
from enum import Enum
class Cabin(str, Enum):
economy = "economy"
first = "first"
class TripSearchRequest(BaseModel):
origin: str # e.g. "JAX" or "GNV"
destinations: list[str] # e.g. ["HNL", "LAX", "JFK"]
earliest_departure: date
latest_return: date
party_size: int = 2
trip_duration_nights: int = 4
preferred_cabin: Cabin = Cabin.economy
ihg_brands: list[str] = ["Kimpton", "InterContinental", "Hotel Indigo"]
class FlightOption(BaseModel):
destination: str
outbound_date: date
return_date: date
fare_class: str # e.g. "L", "U", "Z"
base_price: float # price for one ticket
companion_taxes: float # taxes the companion pays (~$80)
eligible_for_companion_cert: bool
cabin: Cabin
class HotelOption(BaseModel):
destination: str
property_name: str
brand: str
check_in: date
check_out: date
points_per_night: int
total_points: int # for nights_paid only
nights_paid: int
nights_free: int # from 4th-night-free benefit
cash_rate: Optional[float] = None # nightly cash rate if available
class RestaurantOption(BaseModel):
city: str
name: str
cuisine: str
reservation_date: date
party_size: int
resy_credit_eligible: bool
global_dining_access: bool
class TripResult(BaseModel):
destination: str
flight: FlightOption
hotel: Optional[HotelOption] = None
restaurant: Optional[RestaurantOption] = None
total_cash_out_of_pocket: float
total_points_required: int
benefits_captured: list[str]
score: float # 0–100, higher = better value
class SearchProgress(BaseModel):
step: str # "delta" | "ihg" | "resy" | "done"
message: str
progress: int # 0–100
class SearchResponse(BaseModel):
search_id: str
results: list[TripResult]
|