google-flights-mcp
# google-flights-mcp
MCP server for Google Flights search via [SerpApi](https://serpapi.com/google-flights-api). Optimized for Business/First class, Star Alliance, multi-city itineraries with EUR pricing.
## Features
- **search_flights** — One-way or round-trip search
- **search_multi_city** — Multi-leg itineraries (2-5 legs)
- **get_booking_options** — Direct airline booking links
- **get_usage** — Monthly API usage tracker
### Defaults
All defaults are configurable via environment variables in your MCP config:
| Env var | Default | Description |
|---------|---------|-------------|
| `SERPAPI_KEY` | *(required)* | Your SerpApi API key |
| `DEFAULT_TRAVEL_CLASS` | `3` | 1=Economy, 2=Premium Economy, 3=Business, 4=First |
| `DEFAULT_AIRLINES` | `STAR_ALLIANCE` | Airline/alliance filter |
| `DEFAULT_CURRENCY` | `EUR` | Price currency |
| `DEFAULT_GL` | `at` | Google locale (affects pricing region) |
| `DEFAULT_HL` | `en` | Language |
| `DEFAULT_ADULTS` | `1` | Number of passengers |
| `DEFAULT_HUBS` | `FRA,ZRH,BRU` | Preferred connection airports |
| `DEFAULT_HOME_AIRPORTS` | `MBA,FRA,ZRH,BRU` | Home airports |
| `MAX_RESULTS` | `8` | Max flight results per search |
| `MONTHLY_LIMIT` | `100` | Monthly search budget |
| `CACHE_TTL_MS` | `3600000` | Cache duration in ms (1hr) |
| `CACHE_DIR` | `.cache` | Cache directory path |
Example with custom settings:
```json
{
"mcpServers": {
"google-flights": {
"command": "node",
"args": ["/path/to/google-flights-mcp/dist/index.js"],
"env": {
"SERPAPI_KEY": "your-key",
"DEFAULT_TRAVEL_CLASS": "1",
"DEFAULT_AIRLINES": "",
"DEFAULT_CURRENCY": "USD",
"DEFAULT_GL": "us"
}
}
}
}
```
## Setup
### 1. Get a SerpApi key
Sign up at [serpapi.com](https://serpapi.com/) — free tier gives 100 searches/month.
### 2. Build
```bash
npm install
npm run build
```
### 3. Configure Claude Desktop
Add to `~/Library/Application Support/Claude/claude_desktop_config.json` (macOS) or equivalent:
```json
{
"mcpServers": {
"google-flights": {
"command": "node",
"args": ["/absolute/path/to/google-flights-mcp/dist/index.js"],
"env": {
"SERPAPI_KEY": "your-key-here"
}
}
}
}
```
### 4. Configure Claude Code
Add to `~/.claude/mcp.json`:
```json
{
"mcpServers": {
"google-flights": {
"command": "node",
"args": ["/absolute/path/to/google-flights-mcp/dist/index.js"],
"env": {
"SERPAPI_KEY": "your-key-here"
}
}
}
}
```
## Usage Examples
### Simple round-trip
> "Find Business class flights from VIE to NRT, departing March 15 returning March 25"
### Multi-city
> "Search multi-city: VIE→NRT March 15, NRT→BKK March 20, BKK→VIE March 25"
### Booking
> "Get booking options for this flight" (uses booking_token from search results)
## Caching
Responses are cached locally for 1 hour (matching SerpApi's server-side cache). Cached searches don't count against the 100/month limit. Cache files stored in `.cache/` directory.
## API Budget
Every tool response includes a usage footer showing current consumption:
```
📊 API Usage: 43/100 searches used (57 remaining) · Resets March 1, 2026
```
Multi-city searches cost 1 API call per leg (a 3-leg trip = 3 searches).
## Development
```bash
npm run dev # Watch mode
npm run build # Build once
npm start # Run server
```
## Testing
One real API call per endpoint to capture fixtures, then mock everything:
```bash
# Capture fixtures (one-time, needs SERPAPI_KEY)
SERPAPI_KEY=xxx npx ts-node test/capture-fixtures.ts
# Run tests (no API key needed)
npm test
```
TDQS
Scored across 4 tools
search_flights and search_multi_city are distinct in scope (simple vs. multi-leg), and get_booking_options and get_usage serve clearly different purposes. Minor potential confusion between search_flights and search_multi_city for 2-leg itineraries, but descriptions provide clear guidance.
All tools follow a consistent snake_case verb_noun pattern (get_booking_options, search_flights, search_multi_city, get_usage). No deviations in convention.
Four tools cover the essential workflow: searching flights (simple and multi-city), booking, and usage monitoring. Each tool is necessary and well-scoped for the purpose.
Covers flight search, booking options, and usage tracking, which are core to the domain. Missing operations like cancellation or booking completion, but booking links are provided for external completion.