Skip to main content
Glama
google-flights-mcp

google-flights-mcp

google-flights-mcp

MCP server for searching Google Flights prices and schedules from Claude.

Two interchangeable data sources behind one interface (google_flights_mcp/providers/base.py):

  • fast-flights (default) — scrapes Google Flights' internal protobuf search API directly. No API key, works out of the box.

  • SerpApi — used automatically when a SERPAPI_KEY environment variable is set. Adds flight numbers, layover detail, and carbon emissions.

Tools

  • search_flights — origin (default LIS), destination, departure_date, optional return_date, passenger counts, cabin_class, currency (default EUR), max_stops, sort_by. Returns a price-ranked list: price, airline(s), departure/arrival times, duration, stops, and a Google Flights link.

  • cheapest_dates — cheapest day(s) to fly in a date window (max 21 days), price-calendar style. Runs one search per day — see "Known limitations" below.

  • airport_search — resolve a city or airport name ("Lisbon") to an IATA code (LIS), backed by the offline airportsdata package.

Related MCP server: Google Flights MCP Server

Known limitations

  • Round trips: for return_date searches, both providers return outbound flight options annotated with an estimated round-trip total price (paired with the cheapest matching return) — not a separately priced return leg. stops/duration/legs describe the outbound flight only. Open the result's booking_link on Google Flights to pick the exact return.

  • cheapest_dates: neither fast-flights nor SerpApi's Google Flights engine expose a real bulk price-calendar endpoint, so this runs one search_flights call per candidate day. Capped at a 21-day window to keep that bounded.

  • EU/UK cookie-consent wall: Google shows a cookie-consent interstitial to requests from those regions before returning real results. The fast-flights provider detects this and auto-submits "Reject all" (the privacy-preserving option) before retrying — see providers/fast_flights_provider.py if this ever needs updating for a change on Google's side.

Install

Quickest (needs uv): no clone needed, it runs straight from PyPI.

claude mcp add google-flights -- uvx google-flights-search-mcp

For Claude Desktop, use "command": "uvx", "args": ["google-flights-search-mcp"].

From source:

Requires Python 3.11+ and uv.

git clone https://github.com/ThiagoJacobLannes/google-flights-mcp
cd google-flights-mcp
uv sync --extra dev

On Windows, if you keep code in a cloud-synced folder (Google Drive, OneDrive), create the venv outside it — sync clients drop desktop.ini marker files into folders, which can crash packages on startup:

uv venv C:\dev\google-flights-mcp-venv
uv pip install --python C:\dev\google-flights-mcp-venv -e ".[dev]"

The command paths below assume that venv location; adjust to wherever yours lives.

Add to Claude Desktop

Merge claude_desktop_config.snippet.json into your Claude Desktop config (%APPDATA%\Claude\claude_desktop_config.json):

{
  "mcpServers": {
    "google-flights": {
      "command": "C:\\dev\\google-flights-mcp-venv\\Scripts\\python.exe",
      "args": ["-m", "google_flights_mcp.server"]
    }
  }
}

Restart Claude Desktop after editing. To use SerpApi instead of the default scraper, add an env block:

{
  "mcpServers": {
    "google-flights": {
      "command": "C:\\dev\\google-flights-mcp-venv\\Scripts\\python.exe",
      "args": ["-m", "google_flights_mcp.server"],
      "env": { "SERPAPI_KEY": "your-serpapi-key" }
    }
  }
}

Get a key at serpapi.com (free tier available).

Other env vars: GOOGLE_FLIGHTS_DEFAULT_ORIGIN (default LIS), GOOGLE_FLIGHTS_DEFAULT_CURRENCY (default EUR).

Running over HTTP (for a remote connector)

C:\dev\google-flights-mcp-venv\Scripts\python.exe -m google_flights_mcp.server --http

Or set MCP_TRANSPORT=streamable-http. Configure the bind address with MCP_HOST (default 127.0.0.1) and MCP_PORT (default 8000); the server listens at http://<host>:<port>/mcp. Put this behind whatever reverse proxy / auth you use for your other remote connectors before exposing it beyond localhost.

Smoke test

Real network call (no mocks) — searches LIS → GRU about a month out:

C:\dev\google-flights-mcp-venv\Scripts\python.exe tools\google-flights-mcp\examples\smoke_test.py

Tests

C:\dev\google-flights-mcp-venv\Scripts\python.exe -m pytest tools\google-flights-mcp\tests

These are unit tests against the provider abstraction (factory selection, passenger validation, the shared cheapest_dates day-loop, airport resolution) — no network access required.

Available Tools

3 tools
cheapest_datesA

Find the cheapest day(s) to fly within a date window (price-calendar style).

Runs one search per candidate departure day in the window (capped at 21 days — neither of this server's data sources expose a real bulk price-calendar endpoint) and returns each day's cheapest fare, sorted by price ascending.

Args: destination: Destination airport IATA code. start_date: First candidate departure date, YYYY-MM-DD. end_date: Last candidate departure date, YYYY-MM-DD (inclusive; max 21 days after start_date). origin: Origin airport IATA code. Defaults to Lisbon (LIS). trip_length: Nights for a round trip, applied to every departure day in the window. Omit to price one-way fares. adults, children, infants: Passenger counts (see search_flights). cabin_class: "economy" | "premium" | "business" | "first". currency: ISO currency code. Defaults to EUR. max_stops: Maximum stops to allow. Omit to allow any.

NameRequiredDescriptionDefault
adultsNo
originNoLIS
infantsNo
childrenNo
currencyNoEUR
end_dateYes
max_stopsNo
start_dateYes
cabin_classNoeconomy
destinationYes
trip_lengthNo

TDQS

A4.2/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

No annotations exist, so the description carries the full burden and does substantial work: it discloses that one underlying search is issued per candidate day (up to 21), explains why no true bulk endpoint exists, and states results are sorted ascending by price. It stops short of describing failure handling when some of the ~21 sub-searches error out or the latency cost of a full 21-day window.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness4/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Front-loaded with the purpose and the key mechanism before the args list, and the parenthetical about the missing bulk endpoint is justified rather than padding. The Args block is long but each line adds format or default information, so little is wasted.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

For an 11-parameter tool with no annotations and no output schema, the description covers inputs thoroughly and hints at the return shape ('each day's cheapest fare, sorted by price ascending'). With no output schema, a clearer sketch of the response fields (day, fare, currency, stops) would close the remaining gap.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters5/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema coverage is 0% and the description fully compensates: every one of the 11 parameters gets format or defaults (IATA codes, YYYY-MM-DD, EUR default, LIS origin default), plus semantics the schema cannot express — end_date is inclusive, trip_length applies to every departure day and omission means one-way, max_stops omission means unrestricted.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose4/5

Does the description clearly state what the tool does and how it differs from similar tools?

States a specific verb and resource: find the cheapest day(s) to fly within a date window, with 'price-calendar style' framing that makes the scan-over-a-window shape unmistakable. It never explicitly contrasts itself with search_flights (the obvious alternative for a known-date lookup), so an agent must infer the boundary rather than read it.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Usage context is clear: use it when the departure date is flexible and you want the cheapest day inside a window, with an explicit 21-day cap on the window. No exclusion statement tells the agent when to prefer search_flights instead.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

search_flightsA

Search flight prices and options on Google Flights.

Args: destination: Destination airport IATA code (e.g. "GRU"). If you only have a city name, call airport_search first. departure_date: Outbound date, YYYY-MM-DD. origin: Origin airport IATA code. Defaults to Lisbon (LIS) if omitted. return_date: Return date YYYY-MM-DD to search a round trip; omit for one-way. For round trips, each result's price is Google's estimated round-trip total for that outbound flight paired with its cheapest matching return — stops/duration/legs describe the outbound only. Open booking_link to pick the exact return flight. adults: Number of adult passengers (default 1). children: Number of child passengers (default 0). infants: Number of lap infants, under 2 with no own seat (default 0). cabin_class: "economy" | "premium" | "business" | "first". currency: ISO currency code. Defaults to EUR. max_stops: Maximum stops to allow (0 = nonstop only, 1 = up to one stop, etc.). Omit to allow any number of stops. sort_by: "price" (default, ascending) or "duration" (ascending).

NameRequiredDescriptionDefault
adultsNo
originNoLIS
infantsNo
sort_byNoprice
childrenNo
currencyNoEUR
max_stopsNo
cabin_classNoeconomy
destinationYes
return_dateNo
departure_dateYes

TDQS

A4.5/5.0
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

With no annotations, the description carries the full burden and does well: it explains the non-obvious round-trip pricing semantics, that stops/duration/legs describe only the outbound flight, and that booking_link is needed to choose the exact return. It still lacks details on errors, rate limits, or whether results are live/cached, but it is unusually transparent for a search tool.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

The purpose is front-loaded, and the remaining text is a compact parameter reference with no filler. Given 11 parameters and a nuanced round-trip pricing caveat, the length is justified.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

No output schema or annotations exist, so the description must explain both input and output expectations. It does well on inputs and hints at result fields (price, stops, duration, legs, booking_link), but it could more fully describe the return shape and any search limitations.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters5/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema description coverage is 0%, so the description must compensate, and it does: every one of the 11 parameters is documented with meaning, defaults, and examples, including IATA code examples, date format, passenger types, enum values, and max_stops semantics.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description opens with a specific verb and resource: 'Search flight prices and options on Google Flights.' It also distinguishes one sibling by directing city-only callers to airport_search, so an agent can identify the tool's scope immediately.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

It gives a clear usage rule: if you only have a city name, call airport_search first. However, it does not explain when to use this tool versus cheapest_dates, which is likely the relevant alternative for flexible-date searches.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

Tool Schema Changelog

Recent tool additions, removals, and schema changes observed during successful MCP inspections.

  1. 3 tool updatesv0.1.0
    • First observedairport_search
    • First observedcheapest_dates
    • First observedsearch_flights

TDQS

A4/5.0

Scored across 3 tools

Disambiguation5/5

Each tool targets a clearly different task: airport_search resolves names to IATA codes, search_flights prices a specific itinerary, and cheapest_dates scans a date window. The descriptions even cross-reference each other (e.g. 'call airport_search first'), leaving no realistic chance of misselection.

Naming Consistency4/5

All names use snake_case and are readable, but the grammatical pattern varies: search_flights is verb_noun, cheapest_dates is adjective_noun, and airport_search is noun_verb. Minor deviation only, since each name still telegraphs its function.

Tool Count4/5

Three tools is lean but each earns its place — resolution, point search, and date-window scan are the minimal viable set for a flight-fare lookup server. It is slightly under-scoped (no detail/booking step) but not thin enough to be a mismatch.

Completeness4/5

The core read-only workflow (resolve airport -> search fares -> find cheapest dates) is fully covered, including round trips, passengers, cabin class, and stop filters. Gaps exist around retrieving a specific itinerary's details, booking, or multi-city searches, but agents can work around them via the booking link.

Maintenance

ActivityMaintained
ResponsivenessSyncing

Related MCP Connectors

Related MCP Servers