flight-deals-mcp
flight-deals-mcp
A local MCP server for discovering and re-verifying domestic flight options in mainland China.
中文: 本地运行的 Python MCP Server。面向支持 MCP 的 AI 客户端,用于比较中国大陆境内低价航班方案,并在购买前重新核验价格与可售状态。
仓库:https://github.com/Relyonyou/flight-deals-mcp
本项目仍是 MVP,尚未通过生产验收。报价、库存、乘客适用性和票规必须在购买前重新核验。正式 Key 下已完成 24/24 路线矩阵的基准搜索 + 购买前核验 + HTTPS 短链可达(baseline-only);登录后购买页与扩展策略的人工验收仍待执行。详见 验收矩阵。
导航:MVP 范围 · 快速开始 · 如何获取正式 API Key · MCP 客户端配置 · 使用方式 · 测试与构建 · 安全与隐私 · 贡献与许可证
MVP 范围
当前固定搜索意图:
维度 | 约束 |
航线 | 中国大陆境内民航 |
行程 | 单程 |
乘客 | 1 名成人(项目意图;见下) |
舱位 | 经济舱 |
城市 | 随包静态表约 31 个主要城市,见 |
不在静态表内的城市不会生成扩展候选。这是有意收窄,不等于覆盖全部大陆民航城市。
服务会向上游发送出发地、目的地、日期,以及经济舱、单程等上游支持的约束。官方 @fly-ai/flyai-cli 1.0.16 的 search_flight schema 不提供乘客人数参数。因此「1 名成人」是本项目固定意图,实际报价依赖上游默认语义,购买页必须再次确认该价格适用于 1 名成人。项目不会向上游编造 adult_count 等不存在的字段。
本项目不会创建订单、收款、支付、出票、退改签,也不代替航空公司或售票平台的最终页面。即使首次搜索刚完成,购买前也必须调用 verify_flight_option;只有外部售票页当时显示的价格、库存和规则才是最终依据。
功能概览
仅暴露两个 MCP 工具:
工具 | 作用 |
| 查询直飞/官方联程基准,并在约束内尝试扩展策略 |
| 购买前按 |
默认数据路径:official_cli(官方 FlyAI CLI)。另有实验性 direct_mcp(Bearer 直连,未作正式验收)。
策略说明
直飞 / 官方联程:低风险基准,以数据源返回的完整报价为准。
日期浮动:可搜索原日期前后各 1 天(
date_flex_days仅允许0或1)。同城机场:比较同一城市不同机场;注意地面交通时间与费用。
自拼中转:两张彼此独立的机票,可能更便宜,但无联程保护;前序延误、行李再托运、误机损失通常由旅客自行承担。
隐藏城市:仅在
risk_preference=exploratory且不托运行李时可能出现,并固定标为高风险。航变可能绕过真实目的地,弃乘可能影响后续票联,航司可能重新计价,行李可能被运到票面终点。不是默认推荐,也不保证更便宜或可实际使用。
扩展策略只是候选。coverage.completed / failed / skipped 说明实际完成、失败与跳过的搜索;部分结果 ≠ 覆盖整个市场。搜索总预算默认 60 秒(search_timeout_seconds);超时不等于确认无航班。
快速开始
需要:
Python 3.12(项目约束
>=3.12,<3.13)Node.js + npm(
official_cli模式)官方 CLI:
@fly-ai/flyai-cli@1.0.16
git clone https://github.com/Relyonyou/flight-deals-mcp.git
Set-Location flight-deals-mcp
uv sync
npm install --global '@fly-ai/flyai-cli@1.0.16' --registry https://registry.npmjs.org/
# 正式 Key 申请与配置见下文「如何获取正式 API Key」
flyai config set FLYAI_API_KEY 你的正式Key
# Windows 若遇执行策略问题,可用:flyai.cmd config set FLYAI_API_KEY 你的正式Key
uv run flight-deals-mcpflight-deals-mcp 是 stdio Server:启动后安静等待 MCP 客户端属正常现象。不要在同一终端输入聊天文字;Ctrl+C 停止。
查询本机 uv 绝对路径(写入客户端配置时用):
(Get-Command uv).SourceWindows 上建议用 flyai.cmd(PowerShell 可能拦截 flyai.ps1)。确认:
where.exe node
where.exe flyai.cmd
flyai.cmd --help如何获取正式 API Key
正式 Key 由 飞猪 AI 开放平台 发放,不由本仓库生成。官方说明见:
快速开始(含「前往控制台获取正式 API Key」):https://flyai.open.fliggy.com/docs/quickstart
推广者入驻(申请加入 / 实名 / 协议):https://flyai.open.fliggy.com/docs/partner
建议步骤(以官网当前流程为准,页面文案可能调整):
使用淘宝账号打开并登录 飞猪 AI 开放平台。
如需推广者能力,按官网「立即申请加入」完成实名认证并签署推广协议(详见 入驻指南)。
在平台控制台获取正式 API Key(官网快速开始写明:安装后前往控制台领取)。
仅在本机配置,不要写入 Git、Issue、PR 或聊天记录:
flyai config set FLYAI_API_KEY 你的正式Key
# Windows 若遇执行策略问题:
flyai.cmd config set FLYAI_API_KEY 你的正式Key配置后完全重启 MCP 客户端(Codex / Claude Desktop 等),再调用本项目的搜索工具。
说明:
未配置 Key 时,官方 CLI 仍可能进入体验调用;额度与稳定性有限,正式使用请配置 Key。
本项目默认
official_cli:Key 交给官方 CLI 本地配置即可,不必写进 Codexconfig.toml。控制台入口、领取按钮名称以飞猪官网为准;若与上文不一致,以 快速开始 为准。
安装与数据源
推荐:official_cli + 正式 Key
先按上一节在控制台拿到 Key,再执行:
$env:FLIGHT_PROVIDER_MODE = 'official_cli' # 默认,可省略
flyai config set FLYAI_API_KEY 你的正式KeyKey 由官方 CLI 本地配置管理;不要写进仓库、客户端明文配置或对话历史。配置后重启 MCP 客户端,并确保客户端子进程 PATH 能解析到 node 与 flyai.cmd。
无 Key 体验路径
安装官方 CLI 后,不设 Key 也可能获得有限体验调用。额度、稳定性、返回范围均可能受限,不是官方稳定服务承诺,仅适合本地试用。
Windows 上 CLI 有时会先输出业务成功 JSON(status: 0),随后 Node 退出码为 1。本项目接受该成功业务载荷,并把非零退出保留为警告;业务 status 非 0 仍按失败处理。
实验性:direct_mcp
direct_mcp 是实验性、未实测的标准 Bearer-Key 直连路径,不是当前推荐或已验收的生产路径。
$env:FLIGHT_PROVIDER_MODE = 'direct_mcp'
$env:FLYAI_API_KEY = '你的正式Key'
$env:FLYAI_MCP_URL = 'https://flyai.open.fliggy.com/mcp'无正式 Key 时该模式拒绝启动。优先使用官方 CLI + 正式 Key。不要从 CLI 提取私有签名或未公开请求头。
接入 MCP 客户端
下文用 <MCP存放路径>、<uv绝对路径> 表示本机路径,请自行替换。
Codex(推荐关注)
Codex 使用 [mcp_servers.<id>](config.toml)或 codex mcp add,不使用 Claude Desktop 风格的 mcpServers JSON。
CLI 注册
codex mcp add flight-deals --env FLIGHT_PROVIDER_MODE=official_cli -- '<uv绝对路径>' --directory '<MCP存放路径>' run flight-deals-mcp~/.codex/config.toml(Windows 建议写法)
Codex 默认不把完整用户环境交给 stdio MCP。在 Windows 上若只配 FLIGHT_PROVIDER_MODE,子进程经常找不到 node / flyai.cmd,或家庭目录/系统变量缺失,表现为「官方数据源在 60 秒预算内超时」(本机直接跑 CLI 往往数秒就有结果)。请显式配置 Path、USERPROFILE、SystemRoot 等,并将客户端 tool_timeout_sec 设为大于 Server 的 60 秒总预算(建议 90~120)。
[mcp_servers.flight-deals]
command = '<uv绝对路径>'
args = ["--directory", "<MCP存放路径>", "run", "flight-deals-mcp"]
cwd = "<MCP存放路径>"
startup_timeout_sec = 90
tool_timeout_sec = 120
env_vars = [
"USERPROFILE", "HOME", "APPDATA", "LOCALAPPDATA",
"TEMP", "TMP", "SystemRoot", "SYSTEMROOT", "ComSpec",
"USERNAME", "USERDOMAIN", "PATHEXT", "NUMBER_OF_PROCESSORS",
]
[mcp_servers.flight-deals.env]
FLIGHT_PROVIDER_MODE = "official_cli"
USERPROFILE = '<你的用户目录>'
HOME = '<你的用户目录>'
APPDATA = '<你的用户目录>\\AppData\\Roaming'
LOCALAPPDATA = '<你的用户目录>\\AppData\\Local'
TEMP = '<你的用户目录>\\AppData\\Local\\Temp'
TMP = '<你的用户目录>\\AppData\\Local\\Temp'
SystemRoot = 'C:\\Windows'
SYSTEMROOT = 'C:\\Windows'
ComSpec = 'C:\\Windows\\System32\\cmd.exe'
PATHEXT = '.COM;.EXE;.BAT;.CMD;.VBS;.JS;.WS;.MSC'
# 必须能解析到 uv、node.exe、flyai.cmd
Path = '<uv所在目录>;<Node安装目录>;<npm全局目录>;C:\\Windows\\System32;C:\\Windows'保存后完全退出并重启 Codex。应只发现 find_flight_options 与 verify_flight_option。
超时专项排查(含本机对照命令与决策树): docs/codex-timeout-troubleshooting.md
Claude Desktop / 通用 JSON stdio
{
"mcpServers": {
"flight-deals": {
"command": "<uv绝对路径>",
"args": [
"--directory",
"<MCP存放路径>",
"run",
"flight-deals-mcp"
],
"env": {
"FLIGHT_PROVIDER_MODE": "official_cli"
}
}
}
}JSON 中反斜杠需写成 \\。Codex 不使用上述 JSON;Codex 请用上一节的 CLI 或 TOML。其他客户端的具体配置文件位置由客户端决定。
推荐使用方式
自然语言搜索示例
可直接复制到已接入本 MCP 的 AI 客户端:
固定日期(建议首次先用这个,降低超时与风控概率):
用 flight-deals 搜索 2026-08-12 北京到杭州,日期不要浮动,不托运行李,最长 10 小时,风险偏好 balanced。
日期前后浮动 1 天:
搜索 2026-08-12 北京到杭州,前后可浮动 1 天,不托运行李,最长 10 小时,风险偏好 balanced。
需要托运行李(会排除不兼容方案,含隐藏城市):
搜索 2026-08-12 上海到成都,不浮动日期,需要托运行李,最长 12 小时,风险偏好 conservative。
风险偏好场景:
偏好 | 适用 |
| 默认更稳妥;偏直飞/官方联程 |
| 可接受有限扩展(如日期浮动、自拼等,仍受规则约束) |
| 才可能看到隐藏城市等高风险候选;须保留完整风险提示 |
购买前核验示例
选出方案后:
购买前用刚才的
search_id和该方案的option_id调用 verify_flight_option 重新核验。
核验会重新访问数据源,不会把缓存旧价冒充实时价。核验后仍须自行打开最新 HTTPS 购买链接,确认:1 名成人适用、航班、日期、机场、经济舱、行李、退改规则与总价。上游无乘客人数入参,此步不可省略。
MCP 工具参数示例
以下仅为参数对象示意,不是完整 JSON-RPC 信封;价格/ID 亦为示意。
find_flight_options:
{
"origin_city": "北京",
"destination_city": "杭州",
"departure_date": "2026-08-12",
"date_flex_days": 0,
"checked_baggage": false,
"max_duration_hours": 10,
"risk_preference": "balanced"
}verify_flight_option:
{
"search_id": "00000000-0000-4000-8000-000000000000",
"option_id": "example-option-id"
}以上两个值是示意 ID,实际调用必须使用 find_flight_options 返回的值。
示例不代表当前价格、库存或链接有效。
结果解读
search_id:本次搜索快照标识,核验时必填。option_id:候选方案标识。baseline:基准报价(通常来自直飞/官方联程筛选)。options:可比较候选列表(含风险字段)。coverage:哪些策略完成 / 失败 / 跳过。warnings:超时、部分失败等提示。
部分策略超时或失败 ≠ 整个搜索失败,更 ≠ 市场上无航班。 隐藏城市必须保留完整风险提示,且不适用于托运行李场景。
数据与缓存
内容 | 位置 |
机场 / 城市静态表 |
|
隐藏城市后续目的地表 |
|
搜索快照 SQLite | 进程工作目录下 |
通过客户端 cwd 或 uv --directory <MCP存放路径> 固定工作目录后,缓存落在 <MCP存放路径>/.local/flight-deals.db。过期快照仅用于核验时定位旧方案并比较变化;当前报价仍会重新查询。
缓存含路线与报价,可能反映出行意图。不要提交、上传或随意分享 .local/。该目录已在 .gitignore 中忽略。
验收与项目进度
当前结论(2026-07-28)
项 | 状态 |
MVP 实现(双工具 MCP) | 完成 |
最终审查 Important / Minor 修复 | 完成 |
正式 Key + | 完成 |
同矩阵:购买前核验 + HTTPS 短链可达 | 完成 |
登录后购买页人工核对 / 单成人适用性 | 未完成 |
日期浮动 / 自拼 / 隐藏城市等扩展策略矩阵 | 未覆盖 |
生产验收 | 未通过 |
明细与复现:docs/acceptance/manual-route-matrix.md
本地批量烟雾(注意上游风控,勿把 Key 与原始结果入库):
uv run python scripts/smoke_matrix_batch.py
$env:SMOKE_MATRIX_IDS = '1,2,3'
uv run python scripts/smoke_matrix_batch.py本阶段相关文档
设计 / 计划:
docs/superpowers/specs/、docs/superpowers/plans/数据源决策:
docs/data-access-decision.mdCodex 超时排查:
docs/codex-timeout-troubleshooting.md换机交接(开发用,含本机路径):
HANDOFF.md
常见问题
正式 API Key 从哪里获取?
见上文 如何获取正式 API Key。入口是 飞猪 AI 开放平台,在控制台领取后执行 flyai config set FLYAI_API_KEY ...。本仓库不发放、不代理 Key。
客户端找不到 uv
(Get-Command uv).Source把绝对路径写入 TOML/JSON 的 command,保存后彻底重启客户端。
flyai CLI is not installed
npm install --global '@fly-ai/flyai-cli@1.0.16' --registry https://registry.npmjs.org/
where.exe flyai.cmd客户端仍找不到时:检查 MCP 子进程 Path 是否包含 npm 全局目录与 Node 安装目录,然后完全重启客户端。
FLYAI_API_KEY is required
当前为实验性 direct_mcp。改回 official_cli 并用 flyai.cmd config set 配置 Key。
Codex / 客户端报「60 秒预算超时」「未获得航班结果」
优先阅读:docs/codex-timeout-troubleshooting.md。
要点:
文案中的 60 秒多为 Server 搜索总预算,不是「确认无航班」。
先在本机跑通
flyai.cmd search-flight;若本机秒级成功、仅客户端超时,重点查 MCP 环境变量与 Windows 沙箱出网。首次搜索建议
date_flex_days=0;通了再加浮动。
没有结果或只有部分策略
查看 coverage 与 warnings。体验额度、风控、上游空结果均可能发生。可缩小浮动、稍后重试,或为 CLI 配置正式 Key。
修改配置后仍用旧环境
MCP 客户端通常只在启动 Server 时读取 env。改 TOML/JSON 后须完全退出客户端再打开,不要只关聊天窗口。
SQLite 被占用或缓存异常
停止所有本项目 MCP 进程后,备份并删除 <MCP存放路径>/.local/flight-deals.db;下次启动会重建。
测试与构建
uv run pytest -v
uv run ruff check .
uv build仅跑产品验收层断言:
uv run pytest tests/test_acceptance.py -v自动化测试通过 不等于 24 条路线已完成人工购买页核对,也不等于生产验收通过。
安全与隐私
Key 只通过环境变量或官方 CLI 本地配置注入;不写入源码、测试、日志或 MCP 业务输出。
含真实 Key 的客户端配置视为秘密,勿提交 Git、勿发 Issue/PR。
不收集乘机人身份,不接收支付信息,无下单能力。
购买链接经 HTTPS 校验,但 HTTPS ≠ 页面一定可靠;仍需核对域名与页面内容。
不绕过验证码、登录、限流或平台访问控制。
默认仅本地
stdio,不监听公网端口。分享日志或缓存前,检查是否暴露行程意图或凭据。
安全问题请优先通过 GitHub Security Advisory 私密报告(若仓库已启用)。
贡献与许可证
欢迎通过 Issue 和 Pull Request 改进项目。提交前请阅读贡献指南; 安全问题请按安全政策私下报告,并遵守 社区行为准则。
本项目采用 MIT License。
贡献前请勿提交:.local/、真实 Key、未脱敏行程日志、个人绝对路径配置。Issue / PR 中同样不要粘贴密钥。
文档索引
文档 | 说明 |
24 行人工核对矩阵与执行状态 | |
Codex 60 秒超时排查 | |
数据访问路径决策 | |
docs/superpowers/specs/2026-07-24-domestic-flight-deals-mcp-design.md | 产品设计规格 |
换机开发交接 |