AI-Travel-Concierge / recommendations_server.py
ABDALLALSWAITI's picture
Upload recommendations_server.py with huggingface_hub
1dd09fc verified
from mcp.server.fastmcp import FastMCP
import random
import urllib.parse
from datetime import datetime, timedelta
mcp = FastMCP("RecommendationsAgent")
# Comprehensive destination database with seasonal info, prices, and highlights
DESTINATIONS = {
# Beach & Relaxation
"maldives": {
"name": "Maldives",
"country": "Maldives",
"type": ["beach", "luxury", "honeymoon", "relaxation"],
"best_months": [1, 2, 3, 4, 11, 12],
"avg_price": {"budget": 150, "moderate": 350, "luxury": 800},
"flight_hours": {"europe": 10, "asia": 5, "americas": 18},
"highlights": ["Overwater villas", "Crystal clear waters", "World-class diving", "Private islands"],
"weather": "Tropical, 27-30°C year-round",
"visa": "Visa on arrival for most nationalities",
"currency": "MVR (USD widely accepted)",
"rating": 4.8,
},
"bali": {
"name": "Bali",
"country": "Indonesia",
"type": ["beach", "culture", "adventure", "budget-friendly"],
"best_months": [4, 5, 6, 7, 8, 9, 10],
"avg_price": {"budget": 50, "moderate": 120, "luxury": 350},
"flight_hours": {"europe": 14, "asia": 5, "americas": 20},
"highlights": ["Rice terraces", "Hindu temples", "Surf beaches", "Yoga retreats"],
"weather": "Tropical, 24-30°C, dry season Apr-Oct",
"visa": "Visa on arrival (30 days)",
"currency": "IDR",
"rating": 4.7,
},
"phuket": {
"name": "Phuket",
"country": "Thailand",
"type": ["beach", "nightlife", "budget-friendly", "family"],
"best_months": [11, 12, 1, 2, 3, 4],
"avg_price": {"budget": 40, "moderate": 100, "luxury": 300},
"flight_hours": {"europe": 11, "asia": 3, "americas": 18},
"highlights": ["Patong Beach", "Island hopping", "Thai cuisine", "Elephant sanctuaries"],
"weather": "Tropical, 25-32°C, dry Nov-Apr",
"visa": "Visa-free for many (30-60 days)",
"currency": "THB",
"rating": 4.5,
},
"cancun": {
"name": "Cancún",
"country": "Mexico",
"type": ["beach", "party", "all-inclusive", "adventure"],
"best_months": [12, 1, 2, 3, 4],
"avg_price": {"budget": 80, "moderate": 180, "luxury": 450},
"flight_hours": {"europe": 10, "asia": 18, "americas": 4},
"highlights": ["Mayan ruins", "Cenotes", "Caribbean beaches", "Nightlife"],
"weather": "Tropical, 24-33°C, dry Nov-Apr",
"visa": "Visa-free for most Western countries",
"currency": "MXN (USD accepted)",
"rating": 4.4,
},
"santorini": {
"name": "Santorini",
"country": "Greece",
"type": ["beach", "romantic", "honeymoon", "culture"],
"best_months": [5, 6, 7, 8, 9, 10],
"avg_price": {"budget": 100, "moderate": 250, "luxury": 600},
"flight_hours": {"europe": 3, "asia": 10, "americas": 12},
"highlights": ["Sunset in Oia", "Blue domed churches", "Volcanic beaches", "Wine tasting"],
"weather": "Mediterranean, 20-30°C, dry May-Oct",
"visa": "Schengen visa / visa-free for many",
"currency": "EUR",
"rating": 4.8,
},
# City Breaks
"dubai": {
"name": "Dubai",
"country": "UAE",
"type": ["luxury", "shopping", "modern", "family"],
"best_months": [11, 12, 1, 2, 3],
"avg_price": {"budget": 100, "moderate": 250, "luxury": 600},
"flight_hours": {"europe": 6, "asia": 4, "americas": 14},
"highlights": ["Burj Khalifa", "Desert safari", "Shopping malls", "Palm Jumeirah"],
"weather": "Desert, 20-25°C winter, 35-45°C summer",
"visa": "Visa on arrival for most nationalities",
"currency": "AED",
"rating": 4.6,
},
"tokyo": {
"name": "Tokyo",
"country": "Japan",
"type": ["culture", "food", "modern", "shopping"],
"best_months": [3, 4, 5, 10, 11],
"avg_price": {"budget": 80, "moderate": 180, "luxury": 450},
"flight_hours": {"europe": 12, "asia": 3, "americas": 12},
"highlights": ["Cherry blossoms", "Shibuya crossing", "Temples", "Food scene"],
"weather": "Temperate, cherry blossoms Mar-Apr",
"visa": "Visa-free for most (90 days)",
"currency": "JPY",
"rating": 4.8,
},
"paris": {
"name": "Paris",
"country": "France",
"type": ["romantic", "culture", "food", "art"],
"best_months": [4, 5, 6, 9, 10],
"avg_price": {"budget": 100, "moderate": 220, "luxury": 500},
"flight_hours": {"europe": 1, "asia": 12, "americas": 8},
"highlights": ["Eiffel Tower", "Louvre", "Café culture", "Fashion"],
"weather": "Temperate, 5-25°C depending on season",
"visa": "Schengen visa / visa-free for many",
"currency": "EUR",
"rating": 4.7,
},
"new_york": {
"name": "New York",
"country": "USA",
"type": ["culture", "shopping", "food", "entertainment"],
"best_months": [4, 5, 6, 9, 10, 12],
"avg_price": {"budget": 150, "moderate": 300, "luxury": 700},
"flight_hours": {"europe": 8, "asia": 14, "americas": 3},
"highlights": ["Broadway", "Central Park", "Statue of Liberty", "Museums"],
"weather": "Continental, hot summers, cold winters",
"visa": "ESTA for visa waiver countries",
"currency": "USD",
"rating": 4.6,
},
"singapore": {
"name": "Singapore",
"country": "Singapore",
"type": ["modern", "food", "family", "shopping"],
"best_months": [2, 3, 4, 5, 6, 7, 8, 9],
"avg_price": {"budget": 100, "moderate": 200, "luxury": 500},
"flight_hours": {"europe": 12, "asia": 2, "americas": 18},
"highlights": ["Marina Bay Sands", "Gardens by the Bay", "Hawker centers", "Sentosa"],
"weather": "Tropical, 25-32°C year-round",
"visa": "Visa-free for most (30-90 days)",
"currency": "SGD",
"rating": 4.7,
},
"barcelona": {
"name": "Barcelona",
"country": "Spain",
"type": ["beach", "culture", "food", "nightlife"],
"best_months": [5, 6, 9, 10],
"avg_price": {"budget": 70, "moderate": 150, "luxury": 350},
"flight_hours": {"europe": 2, "asia": 12, "americas": 9},
"highlights": ["Sagrada Familia", "La Rambla", "Beaches", "Tapas"],
"weather": "Mediterranean, 15-30°C",
"visa": "Schengen visa / visa-free for many",
"currency": "EUR",
"rating": 4.6,
},
"rome": {
"name": "Rome",
"country": "Italy",
"type": ["culture", "history", "food", "romantic"],
"best_months": [4, 5, 6, 9, 10],
"avg_price": {"budget": 80, "moderate": 170, "luxury": 400},
"flight_hours": {"europe": 2, "asia": 11, "americas": 10},
"highlights": ["Colosseum", "Vatican", "Pasta & pizza", "Ancient ruins"],
"weather": "Mediterranean, hot summers, mild winters",
"visa": "Schengen visa / visa-free for many",
"currency": "EUR",
"rating": 4.7,
},
"istanbul": {
"name": "Istanbul",
"country": "Turkey",
"type": ["culture", "history", "food", "shopping"],
"best_months": [4, 5, 9, 10],
"avg_price": {"budget": 50, "moderate": 120, "luxury": 300},
"flight_hours": {"europe": 3, "asia": 5, "americas": 11},
"highlights": ["Hagia Sophia", "Grand Bazaar", "Bosphorus cruise", "Turkish cuisine"],
"weather": "Mediterranean, 5-30°C",
"visa": "e-Visa for most nationalities",
"currency": "TRY",
"rating": 4.6,
},
# Adventure
"cape_town": {
"name": "Cape Town",
"country": "South Africa",
"type": ["adventure", "nature", "wine", "beach"],
"best_months": [11, 12, 1, 2, 3],
"avg_price": {"budget": 60, "moderate": 140, "luxury": 350},
"flight_hours": {"europe": 11, "asia": 13, "americas": 17},
"highlights": ["Table Mountain", "Wine regions", "Safaris nearby", "Cape Peninsula"],
"weather": "Mediterranean, summer Nov-Mar",
"visa": "Visa-free for many (90 days)",
"currency": "ZAR",
"rating": 4.7,
},
"iceland": {
"name": "Reykjavik",
"country": "Iceland",
"type": ["adventure", "nature", "unique"],
"best_months": [6, 7, 8, 9, 12, 1, 2, 3],
"avg_price": {"budget": 150, "moderate": 300, "luxury": 600},
"flight_hours": {"europe": 3, "asia": 14, "americas": 6},
"highlights": ["Northern Lights", "Geysers", "Glaciers", "Blue Lagoon"],
"weather": "Cool, 0-15°C, northern lights Sep-Mar",
"visa": "Schengen visa / visa-free for many",
"currency": "ISK",
"rating": 4.8,
},
"marrakech": {
"name": "Marrakech",
"country": "Morocco",
"type": ["culture", "adventure", "budget-friendly", "unique"],
"best_months": [3, 4, 5, 10, 11],
"avg_price": {"budget": 40, "moderate": 100, "luxury": 300},
"flight_hours": {"europe": 3, "asia": 10, "americas": 10},
"highlights": ["Medina souks", "Jardin Majorelle", "Atlas Mountains", "Riads"],
"weather": "Semi-arid, 10-35°C",
"visa": "Visa-free for many (90 days)",
"currency": "MAD",
"rating": 4.5,
},
# Hidden Gems
"lisbon": {
"name": "Lisbon",
"country": "Portugal",
"type": ["culture", "food", "budget-friendly", "beach"],
"best_months": [4, 5, 6, 9, 10],
"avg_price": {"budget": 60, "moderate": 130, "luxury": 300},
"flight_hours": {"europe": 2, "asia": 14, "americas": 8},
"highlights": ["Trams", "Pastéis de nata", "Sintra", "Alfama"],
"weather": "Mediterranean, mild year-round",
"visa": "Schengen visa / visa-free for many",
"currency": "EUR",
"rating": 4.7,
},
"vietnam": {
"name": "Ho Chi Minh City",
"country": "Vietnam",
"type": ["culture", "food", "budget-friendly", "adventure"],
"best_months": [12, 1, 2, 3, 4],
"avg_price": {"budget": 30, "moderate": 80, "luxury": 200},
"flight_hours": {"europe": 12, "asia": 3, "americas": 18},
"highlights": ["Street food", "Cu Chi Tunnels", "Mekong Delta", "War history"],
"weather": "Tropical, dry season Dec-Apr",
"visa": "e-Visa available",
"currency": "VND",
"rating": 4.5,
},
"budapest": {
"name": "Budapest",
"country": "Hungary",
"type": ["culture", "budget-friendly", "nightlife", "relaxation"],
"best_months": [4, 5, 6, 9, 10],
"avg_price": {"budget": 50, "moderate": 100, "luxury": 250},
"flight_hours": {"europe": 2, "asia": 10, "americas": 10},
"highlights": ["Thermal baths", "Ruin bars", "Parliament", "Danube views"],
"weather": "Continental, -5 to 30°C",
"visa": "Schengen visa / visa-free for many",
"currency": "HUF",
"rating": 4.6,
},
"bucharest": {
"name": "Bucharest",
"country": "Romania",
"type": ["culture", "budget-friendly", "history", "nightlife"],
"best_months": [5, 6, 9, 10],
"avg_price": {"budget": 40, "moderate": 80, "luxury": 200},
"flight_hours": {"europe": 2, "asia": 9, "americas": 11},
"highlights": ["Palace of Parliament", "Old Town", "Day trips to Transylvania", "Vibrant nightlife"],
"weather": "Continental, -5 to 30°C",
"visa": "Visa-free for EU/US/many others",
"currency": "RON",
"rating": 4.4,
},
}
# Current deals and promotions (simulated)
CURRENT_DEALS = [
{"destination": "dubai", "discount": 25, "reason": "Winter Sun Sale", "valid_until": "2025-12-31"},
{"destination": "bali", "discount": 30, "reason": "Early Bird 2026", "valid_until": "2026-01-15"},
{"destination": "maldives", "discount": 20, "reason": "Honeymoon Special", "valid_until": "2026-02-28"},
{"destination": "tokyo", "discount": 15, "reason": "Cherry Blossom Preview", "valid_until": "2026-01-31"},
{"destination": "iceland", "discount": 20, "reason": "Northern Lights Season", "valid_until": "2026-03-31"},
{"destination": "marrakech", "discount": 35, "reason": "Last Minute Deal", "valid_until": "2025-12-15"},
{"destination": "lisbon", "discount": 25, "reason": "Spring Escape", "valid_until": "2026-04-30"},
{"destination": "cancun", "discount": 20, "reason": "All-Inclusive Special", "valid_until": "2026-01-31"},
]
def get_region_from_origin(origin: str) -> str:
"""Determine user's region based on origin city."""
origin_lower = origin.lower()
european_cities = ["london", "paris", "berlin", "madrid", "rome", "amsterdam", "frankfurt", "munich", "vienna", "zurich", "brussels", "dublin", "copenhagen", "stockholm", "oslo", "lisbon", "barcelona", "milan", "prague", "warsaw", "budapest", "bucharest"]
asian_cities = ["tokyo", "singapore", "hong kong", "bangkok", "kuala lumpur", "seoul", "shanghai", "beijing", "mumbai", "delhi", "dubai", "doha", "abu dhabi"]
if any(city in origin_lower for city in european_cities):
return "europe"
elif any(city in origin_lower for city in asian_cities):
return "asia"
else:
return "americas"
def calculate_trip_price(dest_data: dict, budget: str, nights: int, travelers: int, region: str) -> dict:
"""Calculate estimated trip price."""
hotel_per_night = dest_data["avg_price"].get(budget, dest_data["avg_price"]["moderate"])
flight_hours = dest_data["flight_hours"].get(region, 10)
# Estimate flight price based on distance
flight_price = int(flight_hours * 50 * (1.5 if budget == "luxury" else 1.2 if budget == "moderate" else 1))
hotel_total = hotel_per_night * nights
flights_total = flight_price * travelers * 2 # Round trip
activities_est = int(50 * nights * travelers * (2 if budget == "luxury" else 1.5 if budget == "moderate" else 1))
total = hotel_total + flights_total + activities_est
return {
"hotel_per_night": hotel_per_night,
"hotel_total": hotel_total,
"flights_total": flights_total,
"activities_est": activities_est,
"total": total,
"per_person": total // travelers if travelers > 0 else total
}
@mcp.tool()
def get_destination_recommendations(
origin: str = "",
budget: str = "moderate",
travel_month: int = 0,
interests: str = "",
travelers: int = 2,
trip_days: int = 7
) -> str:
"""
Get smart destination recommendations when user doesn't know where to go.
Only needs: origin city, number of travelers, and trip duration.
Everything else is optional and will be used to refine recommendations.
Args:
origin: Departure city (required for flight estimates)
budget: "budget", "moderate", or "luxury" (default: moderate)
travel_month: Month number (1-12), 0 for flexible
interests: Comma-separated interests like "beach,culture,food"
travelers: Number of travelers (default: 2)
trip_days: Trip duration in days (default: 7)
"""
region = get_region_from_origin(origin) if origin else "europe"
interest_list = [i.strip().lower() for i in interests.split(",") if i.strip()] if interests else []
# Score each destination
scored_destinations = []
for dest_key, dest in DESTINATIONS.items():
score = 0
reasons = []
# Check if month is good for this destination
if travel_month > 0:
if travel_month in dest["best_months"]:
score += 30
reasons.append("✅ Perfect weather")
else:
score -= 10
reasons.append("⚠️ Off-season")
else:
score += 15 # Flexible dates bonus
# Check interests match
if interest_list:
matches = sum(1 for interest in interest_list if any(interest in t for t in dest["type"]))
if matches > 0:
score += matches * 20
reasons.append(f"🎯 Matches {matches} interest(s)")
# Budget alignment
dest_budget_level = "luxury" if dest["avg_price"]["moderate"] > 200 else "moderate" if dest["avg_price"]["moderate"] > 100 else "budget"
if budget == dest_budget_level:
score += 20
reasons.append("💰 Perfect for your budget")
elif (budget == "moderate" and dest_budget_level == "budget") or (budget == "luxury" and dest_budget_level != "budget"):
score += 10
# Check for deals
deal = next((d for d in CURRENT_DEALS if d["destination"] == dest_key), None)
if deal:
score += deal["discount"]
reasons.append(f"🔥 {deal['discount']}% OFF - {deal['reason']}")
# Base rating
score += int(dest["rating"] * 10)
# Calculate price
prices = calculate_trip_price(dest, budget, trip_days, travelers, region)
scored_destinations.append({
"key": dest_key,
"data": dest,
"score": score,
"reasons": reasons,
"prices": prices,
"deal": deal
})
# Sort by score
scored_destinations.sort(key=lambda x: x["score"], reverse=True)
# Build results
results = []
results.append("# 🌍 **Personalized Destination Recommendations**")
results.append("")
if origin:
results.append(f"📍 From: **{origin}** | 👥 {travelers} travelers | 📅 {trip_days} days | 💰 {budget.title()} budget")
if travel_month > 0:
month_name = datetime(2025, travel_month, 1).strftime("%B")
results.append(f"🗓️ Travel month: **{month_name}**")
if interest_list:
results.append(f"❤️ Interests: **{', '.join(interest_list)}**")
results.append("")
results.append("---")
# Top 5 recommendations
for i, rec in enumerate(scored_destinations[:5], 1):
dest = rec["data"]
prices = rec["prices"]
deal = rec["deal"]
# Build booking URLs
dest_encoded = urllib.parse.quote(dest["name"])
results.append("")
# Deal badge
if deal:
results.append(f"### {'🥇' if i == 1 else '🥈' if i == 2 else '🥉' if i == 3 else '🏅'} #{i} {dest['name']}, {dest['country']} 🔥 **{deal['discount']}% OFF**")
else:
results.append(f"### {'🥇' if i == 1 else '🥈' if i == 2 else '🥉' if i == 3 else '🏅'} #{i} {dest['name']}, {dest['country']}")
results.append(f"⭐ **{dest['rating']}/5** | {dest['weather']}")
results.append("")
# Highlights
results.append(f"✨ **Highlights:** {' • '.join(dest['highlights'][:4])}")
results.append("")
# Why this destination
if rec["reasons"]:
results.append(f"💡 **Why we recommend:** {' | '.join(rec['reasons'][:3])}")
results.append("")
# Price estimate
original_total = prices["total"]
if deal:
discounted = int(original_total * (1 - deal["discount"] / 100))
results.append(f"💰 **Estimated total:** ~~${original_total:,}~~ → **${discounted:,}** ({travelers} travelers, {trip_days} nights)")
results.append(f" 📦 Flights ~${prices['flights_total']:,} | Hotels ~${prices['hotel_total']:,} | Activities ~${prices['activities_est']:,}")
else:
results.append(f"💰 **Estimated total:** **${original_total:,}** ({travelers} travelers, {trip_days} nights)")
results.append(f" 📦 Flights ~${prices['flights_total']:,} | Hotels ~${prices['hotel_total']:,} | Activities ~${prices['activities_est']:,}")
results.append("")
# Booking links
google_flights = f"https://www.google.com/travel/flights?q={urllib.parse.quote(origin)}%20to%20{dest_encoded}" if origin else f"https://www.google.com/travel/flights?q=flights%20to%20{dest_encoded}"
booking_url = f"https://www.booking.com/searchresults.html?ss={dest_encoded}"
viator_url = f"https://www.viator.com/searchResults/all?text={dest_encoded}"
results.append(f"🔗 [Search Flights]({google_flights}) | [Find Hotels]({booking_url}) | [Book Activities]({viator_url})")
results.append("")
results.append("---")
# Current deals section
results.append("")
results.append("## 🔥 **Current Hot Deals**")
results.append("")
for deal in CURRENT_DEALS[:4]:
dest = DESTINATIONS.get(deal["destination"], {})
if dest:
dest_encoded = urllib.parse.quote(dest["name"])
results.append(f"• **{dest['name']}** - {deal['discount']}% off ({deal['reason']}) - Valid until {deal['valid_until']}")
results.append("")
results.append("---")
results.append("")
results.append("💬 **Tell me more about your preferences and I'll refine these recommendations!**")
results.append("")
results.append("*Examples: 'I want beach and relaxation' or 'Looking for adventure on a budget' or 'Romantic getaway in spring'*")
return "\n".join(results)
@mcp.tool()
def get_destination_details(destination: str) -> str:
"""Get detailed information about a specific destination."""
dest_lower = destination.lower().replace(" ", "_").replace(",", "")
# Try to find the destination
dest = None
dest_key = None
for key, data in DESTINATIONS.items():
if key == dest_lower or data["name"].lower() == destination.lower() or destination.lower() in data["name"].lower():
dest = data
dest_key = key
break
if not dest:
return f"Sorry, I don't have detailed information about {destination}. Try one of our recommended destinations!"
# Check for deals
deal = next((d for d in CURRENT_DEALS if d["destination"] == dest_key), None)
dest_encoded = urllib.parse.quote(dest["name"])
results = []
results.append(f"# 🌍 {dest['name']}, {dest['country']}")
results.append("")
if deal:
results.append(f"## 🔥 **SPECIAL OFFER: {deal['discount']}% OFF** - {deal['reason']}")
results.append(f"*Valid until {deal['valid_until']}*")
results.append("")
results.append(f"⭐ **Rating:** {dest['rating']}/5")
results.append(f"🌡️ **Weather:** {dest['weather']}")
results.append(f"📅 **Best time to visit:** {', '.join([datetime(2025, m, 1).strftime('%B') for m in dest['best_months'][:4]])}")
results.append(f"🛂 **Visa:** {dest['visa']}")
results.append(f"💱 **Currency:** {dest['currency']}")
results.append("")
results.append("## ✨ Highlights")
for highlight in dest["highlights"]:
results.append(f"• {highlight}")
results.append("")
results.append("## 💰 Price Guide (per night)")
results.append(f"• 🎒 Budget: ~${dest['avg_price']['budget']}")
results.append(f"• 🏨 Moderate: ~${dest['avg_price']['moderate']}")
results.append(f"• 👑 Luxury: ~${dest['avg_price']['luxury']}")
results.append("")
results.append("## 🔗 Start Planning")
results.append(f"• [Search Flights](https://www.google.com/travel/flights?q=flights%20to%20{dest_encoded})")
results.append(f"• [Find Hotels](https://www.booking.com/searchresults.html?ss={dest_encoded})")
results.append(f"• [Book Activities](https://www.viator.com/searchResults/all?text={dest_encoded})")
results.append(f"• [Read Reviews](https://www.tripadvisor.com/Search?q={dest_encoded})")
return "\n".join(results)
@mcp.tool()
def search_deals(budget: str = "any", travel_type: str = "any") -> str:
"""Search for current travel deals and promotions."""
results = []
results.append("# 🔥 **Current Travel Deals & Offers**")
results.append("")
results.append("*Limited time offers from our partners*")
results.append("")
results.append("---")
for deal in CURRENT_DEALS:
dest = DESTINATIONS.get(deal["destination"], {})
if not dest:
continue
# Filter by budget if specified
if budget != "any":
dest_budget = "luxury" if dest["avg_price"]["moderate"] > 200 else "moderate" if dest["avg_price"]["moderate"] > 100 else "budget"
if budget != dest_budget:
continue
# Filter by type if specified
if travel_type != "any" and travel_type.lower() not in dest["type"]:
continue
dest_encoded = urllib.parse.quote(dest["name"])
results.append("")
results.append(f"### 🏷️ {dest['name']}, {dest['country']} - **{deal['discount']}% OFF**")
results.append(f"📣 *{deal['reason']}*")
results.append(f"⏰ Valid until: **{deal['valid_until']}**")
results.append("")
results.append(f"✨ {' • '.join(dest['highlights'][:3])}")
results.append(f"💰 From **${int(dest['avg_price']['budget'] * (1 - deal['discount']/100))}/night** (budget) to **${int(dest['avg_price']['luxury'] * (1 - deal['discount']/100))}/night** (luxury)")
results.append("")
results.append(f"🔗 [Book Now](https://www.booking.com/searchresults.html?ss={dest_encoded}) | [See Flights](https://www.google.com/travel/flights?q=flights%20to%20{dest_encoded})")
results.append("")
results.append("---")
if len(results) <= 5:
results.append("")
results.append("No deals match your filters. Try broadening your search!")
results.append("")
results.append("💡 **Tip:** Deals are updated daily. Check back often for new offers!")
return "\n".join(results)
if __name__ == "__main__":
mcp.run()