Initial commit: Holiday Travel App with resort comparison, trip management, and multi-provider search

This commit is contained in:
2025-10-29 16:22:35 -04:00
commit 74f8e268c3
167 changed files with 18721 additions and 0 deletions

244
search-interactive.ps1 Normal file
View File

@@ -0,0 +1,244 @@
# Interactive Holiday Travel Search Script
# Run this with: .\search-interactive.ps1
Write-Host "`n========================================" -ForegroundColor Cyan
Write-Host " Holiday Travel Deal Finder" -ForegroundColor Cyan
Write-Host "========================================`n" -ForegroundColor Cyan
# 1. Origin
Write-Host "Where are you leaving from?" -ForegroundColor Yellow
Write-Host "(Enter IATA airport code, e.g., YOW, YYZ, YUL, YVR)" -ForegroundColor Gray
$origin = Read-Host "Origin"
$origin = $origin.ToUpper().Trim()
# 2. Destinations
Write-Host "`nWhere do you want to go?" -ForegroundColor Yellow
Write-Host "(Enter one or more IATA codes, separated by commas)" -ForegroundColor Gray
Write-Host "Examples: CUN,PUJ,MBJ (Caribbean) or LHR,CDG,FCO (Europe)" -ForegroundColor Gray
$destinationsInput = Read-Host "Destinations"
$destinations = $destinationsInput.Split(',') | ForEach-Object { $_.ToUpper().Trim() } | Where-Object { $_ -ne "" }
# 3. Travel Dates
Write-Host "`nWhen do you want to travel?" -ForegroundColor Yellow
Write-Host "Earliest departure date (YYYY-MM-DD):" -ForegroundColor Gray
$startDate = Read-Host "Start date"
Write-Host "Latest return date (YYYY-MM-DD):" -ForegroundColor Gray
$endDate = Read-Host "End date"
# 4. Trip Length
Write-Host "`nHow long do you want to stay?" -ForegroundColor Yellow
$minNights = Read-Host "Minimum nights"
$maxNights = Read-Host "Maximum nights"
# 5. Budget
Write-Host "`nWhat's your budget?" -ForegroundColor Yellow
Write-Host "(Leave blank for no budget limit)" -ForegroundColor Gray
$budgetInput = Read-Host "Budget (CAD)"
$budget = if ($budgetInput -eq "") { $null } else { [int]$budgetInput }
# 6. Flight Preferences
Write-Host "`nFlight preferences:" -ForegroundColor Yellow
$nonStopInput = Read-Host "Non-stop flights only? (y/n)"
$nonStop = $nonStopInput -eq "y"
# 7. Features & Amenities
Write-Host "`n========================================" -ForegroundColor Cyan
Write-Host " Destination Features" -ForegroundColor Cyan
Write-Host "========================================`n" -ForegroundColor Cyan
Write-Host "Rate the importance of these features (0-10):" -ForegroundColor Yellow
Write-Host "0 = Not important, 10 = Must have" -ForegroundColor Gray
$features = @{}
Write-Host "`nBeach access:" -ForegroundColor Yellow
$features.beach = [int](Read-Host "Rating (0-10)")
Write-Host "`nSwimming pool:" -ForegroundColor Yellow
$features.pool = [int](Read-Host "Rating (0-10)")
Write-Host "`nGolf course nearby:" -ForegroundColor Yellow
$features.golf = [int](Read-Host "Rating (0-10)")
Write-Host "`nSpa & wellness:" -ForegroundColor Yellow
$features.spa = [int](Read-Host "Rating (0-10)")
Write-Host "`nFood & dining options:" -ForegroundColor Yellow
$features.food = [int](Read-Host "Rating (0-10)")
Write-Host "`nNightlife & entertainment:" -ForegroundColor Yellow
$features.nightlife = [int](Read-Host "Rating (0-10)")
Write-Host "`nShopping:" -ForegroundColor Yellow
$features.shopping = [int](Read-Host "Rating (0-10)")
Write-Host "`nCultural attractions:" -ForegroundColor Yellow
$features.culture = [int](Read-Host "Rating (0-10)")
Write-Host "`nOutdoor activities (hiking, water sports):" -ForegroundColor Yellow
$features.outdoor = [int](Read-Host "Rating (0-10)")
Write-Host "`nFamily-friendly:" -ForegroundColor Yellow
$features.family = [int](Read-Host "Rating (0-10)")
# 8. Search Sources
Write-Host "`n========================================" -ForegroundColor Cyan
Write-Host " Search Sources" -ForegroundColor Cyan
Write-Host "========================================`n" -ForegroundColor Cyan
Write-Host "Which sources do you want to search?" -ForegroundColor Yellow
$sources = @()
$useDeals = Read-Host "Deal sites (YOWDeals, etc)? (y/n)"
if ($useDeals -eq "y") { $sources += "Deals" }
$useSky = Read-Host "Skyscanner? (y/n)"
if ($useSky -eq "y") { $sources += "Skyscanner" }
$useGoogle = Read-Host "Google Flights? (y/n)"
if ($useGoogle -eq "y") { $sources += "GoogleFlights" }
$useAC = Read-Host "Air Canada? (y/n)"
if ($useAC -eq "y") { $sources += "AirCanada" }
if ($sources.Count -eq 0) {
$sources = @("Deals", "Skyscanner", "GoogleFlights", "AirCanada")
Write-Host "No sources selected, using all sources." -ForegroundColor Gray
}
# Summary
Write-Host "`n========================================" -ForegroundColor Cyan
Write-Host " Search Summary" -ForegroundColor Cyan
Write-Host "========================================`n" -ForegroundColor Cyan
Write-Host "From: $origin" -ForegroundColor White
Write-Host "To: $($destinations -join ', ')" -ForegroundColor White
Write-Host "Dates: $startDate to $endDate" -ForegroundColor White
Write-Host "Stay: $minNights-$maxNights nights" -ForegroundColor White
if ($budget) { Write-Host "Budget: `$$budget CAD" -ForegroundColor White }
Write-Host "Non-stop only: $nonStop" -ForegroundColor White
Write-Host "Sources: $($sources -join ', ')" -ForegroundColor White
Write-Host "`nTop priorities:" -ForegroundColor Yellow
$topFeatures = $features.GetEnumerator() | Sort-Object Value -Descending | Select-Object -First 3
foreach ($feature in $topFeatures) {
if ($feature.Value -gt 0) {
$bar = "" * $feature.Value
Write-Host " $($feature.Key): $bar $($feature.Value)/10" -ForegroundColor Green
}
}
# Confirm
Write-Host "`n========================================`n" -ForegroundColor Cyan
$confirm = Read-Host "Search now? (y/n)"
if ($confirm -ne "y") {
Write-Host "Search cancelled." -ForegroundColor Red
exit
}
# Build the search payload
$searchData = @{
origin = $origin
destinations = $destinations
startDate = $startDate
endDate = $endDate
tripLengthMin = [int]$minNights
tripLengthMax = [int]$maxNights
currency = "CAD"
nonStopOnly = $nonStop
sources = $sources
preferences = $features
}
if ($budget) {
$searchData.budget = $budget
}
$jsonPayload = $searchData | ConvertTo-Json -Depth 3
Write-Host "`nSearching for deals..." -ForegroundColor Yellow
Write-Host "(This may take 10-30 seconds)`n" -ForegroundColor Gray
try {
# Send the request
$response = Invoke-RestMethod -Uri "http://localhost:4000/api/search" -Method POST -Body $jsonPayload -ContentType "application/json"
$resultCount = $response.results.Count
Write-Host "✓ Found $resultCount results!`n" -ForegroundColor Green
if ($resultCount -eq 0) {
Write-Host "No deals found matching your criteria. Try:" -ForegroundColor Yellow
Write-Host " - Expanding your date range" -ForegroundColor Gray
Write-Host " - Increasing your budget" -ForegroundColor Gray
Write-Host " - Adding more destinations" -ForegroundColor Gray
Write-Host " - Removing the non-stop requirement`n" -ForegroundColor Gray
exit
}
# Display results
Write-Host "========================================" -ForegroundColor Cyan
Write-Host " Top Deals" -ForegroundColor Cyan
Write-Host "========================================`n" -ForegroundColor Cyan
# Show top 10 deals
$topDeals = $response.results | Select-Object -First 10
$index = 1
foreach ($deal in $topDeals) {
Write-Host "[$index] " -NoNewline -ForegroundColor Cyan
Write-Host $deal.title -ForegroundColor White
if ($deal.price) {
Write-Host " Price: " -NoNewline -ForegroundColor Gray
Write-Host "`$$($deal.price) $($deal.currency)" -ForegroundColor Green
}
if ($deal.nights) {
Write-Host " Duration: $($deal.nights) nights" -ForegroundColor Gray
}
if ($deal.startDate -and $deal.endDate) {
Write-Host " Dates: $($deal.startDate)$($deal.endDate)" -ForegroundColor Gray
}
Write-Host " Source: $($deal.source)" -ForegroundColor Gray
Write-Host " Link: " -NoNewline -ForegroundColor Gray
Write-Host $deal.link -ForegroundColor Blue
if ($deal.score) {
Write-Host " Score: $($deal.score)" -ForegroundColor DarkGray
}
Write-Host ""
$index++
}
if ($resultCount -gt 10) {
Write-Host "... and $($resultCount - 10) more results`n" -ForegroundColor Gray
}
# Export options
Write-Host "========================================`n" -ForegroundColor Cyan
$export = Read-Host "Export all results to CSV? (y/n)"
if ($export -eq "y") {
$filename = "travel_deals_$(Get-Date -Format 'yyyy-MM-dd_HHmmss').csv"
$response.results | Export-Csv -Path $filename -NoTypeInformation
Write-Host "✓ Exported to $filename" -ForegroundColor Green
}
# Open in browser option
$openBrowser = Read-Host "Open top deal in browser? (y/n)"
if ($openBrowser -eq "y") {
$topDeal = $response.results | Select-Object -First 1
Start-Process $topDeal.link
Write-Host "✓ Opening in browser..." -ForegroundColor Green
}
Write-Host "`nHappy travels! ✈️🏖️`n" -ForegroundColor Cyan
} catch {
Write-Host "✗ Error searching for deals:" -ForegroundColor Red
Write-Host $_.Exception.Message -ForegroundColor Red
Write-Host "`nMake sure the server is running on http://localhost:4000" -ForegroundColor Yellow
Write-Host "Run: npm run dev`n" -ForegroundColor Gray
}