Skip to main content
Glama

Flight Simulator MCP Server

by jabir366
server.py•16.6 kB
#!/usr/bin/env python3 """ Enhanced Flight Simulation MCP Server A comprehensive MCP server for airline booking operations using FastMCP """ import os import sys from datetime import datetime from typing import Dict, List, Optional, Any from dotenv import load_dotenv # Add src to path for imports sys.path.insert(0, os.path.dirname(os.path.abspath(__file__))) from fastmcp import FastMCP from data.mock_data import db from models import ( FlightSearchRequest, SeatClass, BookingRequest, CheckInRequest, SeatSelection, FlightStatus ) # Load environment variables load_dotenv() # Initialize FastMCP server mcp = FastMCP( name=os.getenv("MCP_SERVER_NAME", "flight-simulator"), version=os.getenv("MCP_SERVER_VERSION", "0.1.0") ) # Configure server settings mcp.description = "Enhanced flight booking and management system with real-time tracking" mcp.author = "Flight Sim MCP Team" # ============== FLIGHT SEARCH TOOLS ============== @mcp.tool() async def search_flights( origin: str, destination: str, departure_date: str, return_date: Optional[str] = None, passengers: int = 1, seat_class: str = "economy", nonstop_only: bool = False, max_price: Optional[float] = None, preferred_airlines: Optional[List[str]] = None ) -> Dict[str, Any]: """ Search for available flights between airports. Args: origin: Origin airport code (3 letters, e.g., 'SFO') destination: Destination airport code (3 letters, e.g., 'JFK') departure_date: Departure date in YYYY-MM-DD format return_date: Optional return date for round trips in YYYY-MM-DD format passengers: Number of passengers (1-9) seat_class: Class of service (economy, premium_economy, business, first) nonstop_only: Only show nonstop flights max_price: Maximum price per person preferred_airlines: List of preferred airline codes Returns: Dictionary containing search results with outbound and return flights """ try: # Parse dates dep_date = datetime.strptime(departure_date, "%Y-%m-%d") ret_date = datetime.strptime(return_date, "%Y-%m-%d") if return_date else None # Validate seat class seat_class_enum = SeatClass(seat_class.lower()) # Search outbound flights outbound_flights = db.search_flights( origin=origin.upper(), destination=destination.upper(), departure_date=dep_date, passengers=passengers, seat_class=seat_class_enum ) # Filter by preferences if max_price: outbound_flights = [f for f in outbound_flights if getattr(f.price, seat_class.lower()) <= max_price] if preferred_airlines: outbound_flights = [f for f in outbound_flights if any(airline in f.airline for airline in preferred_airlines)] # Search return flights if needed return_flights = [] if ret_date: return_flights = db.search_flights( origin=destination.upper(), destination=origin.upper(), departure_date=ret_date, passengers=passengers, seat_class=seat_class_enum ) if max_price: return_flights = [f for f in return_flights if getattr(f.price, seat_class.lower()) <= max_price] if preferred_airlines: return_flights = [f for f in return_flights if any(airline in f.airline for airline in preferred_airlines)] return { "success": True, "search_id": f"SRCH-{datetime.now().strftime('%Y%m%d%H%M%S')}", "outbound_flights": [f.dict() for f in outbound_flights[:10]], # Limit to 10 results "return_flights": [f.dict() for f in return_flights[:10]] if return_flights else None, "total_results": len(outbound_flights), "search_criteria": { "origin": origin.upper(), "destination": destination.upper(), "departure_date": departure_date, "return_date": return_date, "passengers": passengers, "seat_class": seat_class } } except Exception as e: return { "success": False, "error": str(e), "error_type": type(e).__name__ } @mcp.tool() async def get_flight_details(flight_id: str) -> Dict[str, Any]: """ Get detailed information about a specific flight. Args: flight_id: The unique flight identifier Returns: Detailed flight information including real-time status """ try: flight = db.get_flight(flight_id) if not flight: return { "success": False, "error": f"Flight {flight_id} not found" } # Add additional details flight_dict = flight.dict() flight_dict["airport_info"] = { "origin": db.airports.get(flight.origin).dict() if flight.origin in db.airports else None, "destination": db.airports.get(flight.destination).dict() if flight.destination in db.airports else None } return { "success": True, "flight": flight_dict } except Exception as e: return { "success": False, "error": str(e), "error_type": type(e).__name__ } # ============== BOOKING MANAGEMENT TOOLS ============== @mcp.tool() async def create_booking( flight_id: str, passengers: List[Dict[str, str]], seat_class: str = "economy", payment_token: str = "mock-payment-token", add_insurance: bool = False, special_requests: Optional[str] = None ) -> Dict[str, Any]: """ Book a flight for one or more passengers. Args: flight_id: The flight to book passengers: List of passenger details with first_name, last_name, email, phone seat_class: Class of service (economy, business, first) payment_token: Payment authorization token add_insurance: Whether to add travel insurance special_requests: Any special requests or notes Returns: Booking confirmation with PNR and booking details """ try: seat_class_enum = SeatClass(seat_class.lower()) booking = db.create_booking( flight_id=flight_id, passengers=passengers, seat_class=seat_class_enum, payment_token=payment_token ) if not booking: return { "success": False, "error": "Unable to create booking. Flight may be full or not found." } return { "success": True, "booking": booking.dict(), "confirmation_message": f"Booking confirmed! Your PNR is {booking.pnr}", "next_steps": [ "Check in online 24 hours before departure", "Arrive at airport 2 hours before domestic flights", "Bring valid ID and this confirmation" ] } except Exception as e: return { "success": False, "error": str(e), "error_type": type(e).__name__ } @mcp.tool() async def get_booking(booking_id: str, email: Optional[str] = None) -> Dict[str, Any]: """ Retrieve booking details using booking ID. Args: booking_id: The booking ID or PNR email: Email for verification (optional) Returns: Complete booking information """ try: booking = db.get_booking(booking_id) if not booking: return { "success": False, "error": f"Booking {booking_id} not found" } # Get associated flight details flight = db.get_flight(booking.flight_id) return { "success": True, "booking": booking.dict(), "flight": flight.dict() if flight else None } except Exception as e: return { "success": False, "error": str(e), "error_type": type(e).__name__ } @mcp.tool() async def cancel_booking(booking_id: str, reason: Optional[str] = None) -> Dict[str, Any]: """ Cancel an existing booking. Args: booking_id: The booking to cancel reason: Optional cancellation reason Returns: Cancellation confirmation and refund information """ try: booking = db.get_booking(booking_id) if not booking: return { "success": False, "error": f"Booking {booking_id} not found" } # Update booking status booking.status = "cancelled" # Calculate refund based on time until flight flight = db.get_flight(booking.flight_id) if flight: time_until_flight = flight.departure - datetime.now() if time_until_flight.days > 7: refund_percentage = 0.9 # 90% refund elif time_until_flight.days > 1: refund_percentage = 0.5 # 50% refund else: refund_percentage = 0 # No refund else: refund_percentage = 0.9 refund_amount = booking.total_price * refund_percentage return { "success": True, "booking_id": booking_id, "status": "cancelled", "refund_amount": refund_amount, "refund_percentage": refund_percentage * 100, "reason": reason, "message": f"Booking {booking_id} has been cancelled. Refund of ${refund_amount:.2f} will be processed." } except Exception as e: return { "success": False, "error": str(e), "error_type": type(e).__name__ } # ============== CHECK-IN AND SERVICE TOOLS ============== @mcp.tool() async def check_in( booking_id: str, passenger_ids: Optional[List[str]] = None, seat_preferences: Optional[List[Dict[str, str]]] = None ) -> Dict[str, Any]: """ Perform online check-in for a booking. Args: booking_id: The booking to check in passenger_ids: Specific passengers to check in (optional, defaults to all) seat_preferences: Seat selection preferences per passenger Returns: Check-in confirmation with boarding passes """ try: booking = db.get_booking(booking_id) if not booking: return { "success": False, "error": f"Booking {booking_id} not found" } flight = db.get_flight(booking.flight_id) if not flight: return { "success": False, "error": "Associated flight not found" } # Check if within check-in window (24 hours) time_until_flight = flight.departure - datetime.now() if time_until_flight.total_seconds() > 86400: # 24 hours return { "success": False, "error": f"Check-in opens 24 hours before departure. Please try again after {(flight.departure - timedelta(days=1)).strftime('%Y-%m-%d %H:%M')}" } # Generate boarding passes boarding_passes = [] for i, passenger in enumerate(booking.passengers): if passenger_ids and passenger.id not in passenger_ids: continue # Assign seat row = 12 + i seat_letter = ['A', 'B', 'C', 'D', 'E', 'F'][i % 6] seat = f"{row}{seat_letter}" boarding_pass = { "passenger_name": f"{passenger.first_name} {passenger.last_name}", "flight_number": flight.flight_number, "origin": flight.origin, "destination": flight.destination, "departure_time": flight.departure.isoformat(), "boarding_time": (flight.departure - timedelta(minutes=30)).isoformat(), "gate": flight.gate, "seat": seat, "boarding_group": "B" if booking.seat_class == SeatClass.ECONOMY else "A", "barcode": f"BP{booking_id}{passenger.id}" } boarding_passes.append(boarding_pass) # Update passenger seat passenger.seat_number = seat # Update booking status booking.status = "checked_in" return { "success": True, "booking_id": booking_id, "boarding_passes": boarding_passes, "message": "Check-in completed successfully!", "reminders": [ f"Arrive at gate {flight.gate} by {(flight.departure - timedelta(minutes=30)).strftime('%H:%M')}", "Boarding begins 30 minutes before departure", "Have your ID and boarding pass ready" ] } except Exception as e: return { "success": False, "error": str(e), "error_type": type(e).__name__ } # ============== RESOURCES ============== @mcp.resource("flight://airports/{code}") async def get_airport_info(code: str) -> Dict[str, Any]: """Get detailed information about an airport.""" airport = db.airports.get(code.upper()) if not airport: return {"error": f"Airport {code} not found"} return airport.dict() @mcp.resource("flight://status/{flight_id}") async def get_flight_status(flight_id: str) -> Dict[str, Any]: """Get real-time flight status.""" flight = db.get_flight(flight_id) if not flight: return {"error": f"Flight {flight_id} not found"} return { "flight_id": flight_id, "status": flight.status.value, "departure": flight.departure.isoformat(), "arrival": flight.arrival.isoformat(), "gate": flight.gate, "terminal": flight.terminal, "last_updated": datetime.now().isoformat() } # ============== PROMPTS ============== @mcp.prompt() async def find_best_flight( travel_details: str, preferences: str ) -> str: """ AI-assisted flight search based on natural language preferences. Args: travel_details: Natural language description of travel plans preferences: User preferences for the flight Returns: Structured prompt for optimal flight search """ return f"""Based on the travel details: "{travel_details}" and preferences: "{preferences}", I'll help you find the best flight options. To search effectively, I'll need to: 1. Extract origin and destination cities 2. Identify travel dates 3. Determine number of passengers 4. Understand your priorities (price, time, airline preference) Let me search for flights that match your criteria...""" @mcp.prompt() async def handle_disruption( booking_info: str, disruption_type: str ) -> str: """ Help passengers handle flight disruptions like delays or cancellations. Args: booking_info: Current booking details disruption_type: Type of disruption (delay, cancellation, etc.) Returns: Assistance prompt for handling the disruption """ return f"""I understand your flight has been affected by a {disruption_type}. Let me help you with: 1. Checking alternate flight options 2. Understanding your passenger rights 3. Processing rebooking or refunds 4. Arranging accommodation if needed Based on your booking ({booking_info}), here are your options...""" # ============== IMPORT ADDITIONAL TOOLS AND RESOURCES ============== # Import all tools to register them with the MCP server import tools.tracking import tools.services import tools.group # Import and register all resources from resources.flight_resources import register_resources register_resources(mcp) # Import all prompts import prompts.templates # ============== MAIN ENTRY POINT ============== if __name__ == "__main__": # Run the server mcp.run()

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/jabir366/MCPFligh'

If you have feedback or need assistance with the MCP directory API, please join our Discord server