Trip Decider is an evidence-constrained agent for real-world travel decisions.
一个先核验现实事实、再决定哪些内容可以进入行程的旅行决策 Agent。
它不把模型记忆当作交通事实,也不生成“看起来合理”的攻略来填空:
- 用 12306 核验铁路车次、时刻与票价;
- 用高德核验地点身份、POI、路线与当地交通;
- 把事实逐字段记录为
sourced / estimated / conflicting / unknown,并在读取时计算新鲜度; - 产出可执行行程,也能审计其他 AI、攻略或人工排出的行程。
模型或 MCP 宿主可以理解需求、调用工具和推进任务,但模型不是事实来源。
Unknown stays unknown. Conflicts stay visible. Freshness is evaluated at read time. Verification > generation.
当前版本:0.1.0 release baseline。
一份外部行程曾声称:G1992 从上饶到武汉,15:35 发车,二等座 ¥340。 trip-decider 在 2026-08-04 20:08–20:09(+08:00)查询 12306 后观测到:
| 断言 | 12306 观测值 | 判定 |
|---|---|---|
| 15:35 发车,¥340 | 15:02 发车,¥202.5 | conflicting |
它没有“挑一个更像真的”,而是保留断言与观测值,并指出发车时间相差 33 分钟、
票价相差 ¥137.5。同批另外三条没有查到支持证据,被标为 unknown,而不是“错误”。
这是一个历史实查快照,不是今天仍有效的时刻表;现在使用前必须重新查询。完整记录见 第三方行程 vs 12306 实查。
普通生成式行程会写“下午前往景区,车程约 1 小时”。trip-decider 要么给出可核验的 交通方式、上下车点、班次、费用与返程边界,要么明确告诉你缺什么、何时重查、向谁确认。
当前完整端到端真实复测主要覆盖武汉 → 婺源及上饶区域,包括 Claude Desktop / MCP 宿主调用、真实 12306 核验、高德地点与当地交通采集,以及发布前重复 soak。 这不是全国可用性声明。
当前明确不支持或覆盖不足:
- 航班规划和长途公路尚未形成统一支持路径;
- 酒店实时成交价与库存没有稳定来源;
- 景点开放时间与门票覆盖不完整;
- 天气尚未接入;
- 不提供订票、订房、账户或消费级托管服务;
- runtime persistence formats before v2 are not supported.
更多边界见 KNOWN_ISSUES.md。
flowchart TD
U[User] --> H[LLM / MCP Host]
U --> W[Standalone deterministic parser]
H --> I[Travel Intent]
W --> I
I --> C[Evidence Collection]
P[12306 / AMap / user-supplied evidence] --> C
C --> F[Field-level Facts]
F --> E[support × freshness]
E --> G[Decision Gates]
G --> R[Planner]
R --> O[Executable Plan / Audit Report]
LLM / MCP Host 只位于意图理解和工具编排路径,不位于 truth-source 路径;Standalone Web 则通过确定性规则提取明确输入。 权威决策链是:
evidence -> support × freshness -> decision gates -> planner
详细模块边界见 CURRENT_ARCHITECTURE.md。
系统把模糊需求收敛成结构化 intent,确认后再进行目的地候选发现、铁路查询、地点与 POI 核验、当地交通拼接、预算与返程边界检查。候选目录只能提出“值得查什么”,不能 证明可达;是否进入计划由事实级证据和 decision gates 决定。
计划包含逐日事件、交通段、预算状态、未知项和恢复动作。修改节奏或约束时会生成新 PlanVersion;新版本失败不会覆盖已经安装的可用版本。
把其他 AI、攻略或人工行程中的铁路断言交给 trip-decider,它会逐条给出三档结果:
| 结果 | 含义 |
|---|---|
sourced / supported |
当前查询得到的事实与断言一致 |
conflicting |
查到了,但观测值与断言不一致;两边都保留 |
unknown / unsupported |
当前没有找到足够证据,或查询/输入条件不足 |
Unsupported does not mean false. 超出预售期、站名不完整、网络失败或当前线路未查到, 都不能被偷换成“这趟车不存在”。
来源不只贴在整份文档上。车次、发车时间、票价、路线时长、POI 身份等字段分别保留 来源、采集时刻、支持状态与计划依赖;一个字段有据,不会自动替同一段里的其他字段背书。
事实支持度与时效是两条独立轴:
- Support:
sourced、estimated、conflicting、unknown; - Freshness:
fresh、stale、undated。
Support 随证据保存;freshness 根据 retrieved_at 和读取时刻重新计算。昨天可信的班次
不会因为曾经写入磁盘,就永远显示为今天仍可信。完整规则见
evidence axes 与
freshness policy。
系统区分“已核实不存在”、当前未找到、采集超时、来源冲突、内部错误,以及动作仍在
执行。blocked 不是一句模糊失败:读取结果必须给出 recovery / next_action,说明
系统会重试、用户需要补什么,或哪个冲突需要选择。
这不是一次 prompt -> answer 调用。运行过程包含:
intent -> confirmation -> execution -> blocked/completed -> revision
任务状态、事件、证据和 PlanVersion 都可恢复;界面只是读取同一份 read model,不拥有 另一套事实或规划状态。
下面仍使用上面的真实 G1992 核验快照,展示一条事实怎样被消费:
Fact: G1992 departure_at = 2026-08-14 15:02
Source: China Railway 12306
Observed support: sourced
Retrieved: 2026-08-04 20:08–20:09 +08:00
Freshness then: fresh
Compared claim: departure_at = 15:35; fare = ¥340
Decision: conflicting
Decision dependency: external itinerary's return rail leg; refetch before relying on it
Freshness then 只描述当次读取。今天再打开这条记录,它只是历史证据,不能直接进入新计划。
Claude、Codex 或其他 MCP-capable host 负责理解自然语言、选择工具、跟随 next_call
推进 runtime,并把结果解释给用户。trip-decider 负责状态、provider 调用、事实、证据判定、
规划和核验。这是完整的 Agent 使用方式;宿主的语言模型仍然不是 truth source。
MCP 配置见 使用说明。
本地 Web 使用确定性的结构化提取规则读取显式日期、地点、人数、预算和偏好,然后调用 同一套 application/query services 与 read model。它没有隐藏的模型调用。
Standalone Web intentionally does not require a model API.
支持 Python >=3.11,<3.12。锁定依赖和一键启动脚本目前在 Windows PowerShell 验证。
py -3.11 -m venv .venv
.\.venv\Scripts\python.exe -m pip install --requirement .\requirements-dev.lock启动 standalone Web(真实地点和路线查询需要高德 Web 服务 key):
$env:AMAP_WEB_SERVICE_KEY = "<your-amap-web-service-key>"
.\scripts\run_product.ps1浏览器会打开 http://127.0.0.1:8765/。凭据只通过进程环境传入,不要写进仓库、日志或截图。
| 层级 | 作用 | 执行方式 |
|---|---|---|
| Offline CI | 确定性回归;pytest、Ruff、Pyright;不需要凭据 | 每个 PR 和 main push |
| Live smoke | 检查当前 12306 / 高德响应能否通过真实采集和动作循环 | 有凭据、有网络时人工执行 |
| Soak | 在真实 provider 时序和数据波动下重复走到明确终态 | 发布门,不进入普通 CI |
仓库已有两次可追溯的 20 轮 soak 记录,两次均为 0 个探针失败;其中终态包含“需要用户 补证据”和“无可行候选”,不等于 40 轮都生成了计划。详见 soak gate report。
完整命令、边界和不过度解读方式见 docs/verification.md。
- README(你正在读的这份产品与技术概览)
- CURRENT_ARCHITECTURE.md(当前模块和数据流)
- docs/verification.md(离线、live smoke、soak 的边界)
- docs/usage.md(Web 与 MCP 使用方式)
- docs/contracts/(证据与可靠性契约)
PLAN.md、docs/audit/ 与 docs/field-reports/ 保留工程决策和实测历史,但不是理解产品
的前置阅读。
MIT License · © 2026 Hugin-Z