# 行程扭蛋

由 AI 操作的旅行规划与记录组件，提供行程状态、规则校验、变更预览、保存、历史恢复和只读展示。

## Metadata

- HTML: https://glenzli.com/projects/plan-gacha/
- Markdown: https://glenzli.com/projects/plan-gacha.md
- Collection: Projects
- Language: zh-CN
- Published: 2026-07-04
- Updated: 2026-10-08
- Status: active
- Tags: travel, ai, component, itinerary, local-first

## Content

行程扭蛋是以 AI 为操作主体的旅行规划与记录组件。用户在对话中表达出行意图、补充条件和报告变化，AI 助手读取行程、核查信息、提出调整并解释结果；组件提供行程状态、规则校验、变更预览、保存与历史恢复。

2026 年 10 月 8 日，项目的使用方式从独立旅行 App 转向 AI 主导的行程组件。项目继续维护，本站旧独立网页版已下线，完整旧版保存在 [`legacy-web-final`](https://github.com/glenzli/plan-gacha/tree/legacy-web-final)。

  ![行程扭蛋品牌插画：旅行者与装有旅行目的地的扭蛋机](/images/projects/plan-gacha-banner.webp)

## 对话中的行程操作

AI 宿主负责理解意图、研究开放时间与预约条件、选择操作和解释取舍，并通过已有工具访问私有数据、外部服务和存储。组件不内置通用 AI 模型，核心离线运行；地图、天气、账户和订单的查询依赖宿主工具与权限。

一次调整从读取同一权威行程的最新版本开始。AI 将意图转为明确操作，检查受影响的活动、预约、住宿和约束，再展示变更预览。在用户授权范围内，本地行程文件由组件按版本校验保存；Library 等外部存储由宿主对同一文件执行版本校验替换，并读回确认。`stage` 生成的候选本身不代表外部保存成功。

## 组件能力

- **行程与约束**：分别保留原始计划、当前安排和用户报告的实际执行，支持活动增删、移动、重排及时间和地点修改。日期、闭馆、冲突、天气和候选规则用于分析调整，已订、锁定、已确认或已完成的安排受到保护。
- **有来源的记录**：在同一行程中保存事实、偏好、承诺、证据、决定、变更理由和未解决问题，区分预测、正式信息与实际报告。预约或计划记录不能证明实际完成。
- **历史与恢复**：修改带版本、预览标识、幂等回执和理由；支持最新修改的撤销、存储格式迁移，以及显式采用可恢复的历史 checkpoint。更早的完整状态可能需要先前版本。
- **经验复盘**：将亲历观察、调整理由、结果和评价关联到原行程与历史，在明确提供的旧行程中检索经验，并生成需要审阅的攻略草稿。
- **只读展示**：从权威行程派生按日内容、当前与历史路线、按住宿夜晚组织的安排和旅行摘要，供宿主页面或报告呈现。展示刷新与权威存储保存由宿主分别处理。

规则分析用于发现已知冲突和未知项，不能证明现实中的行程可行性。决策期限与提醒对账输出建议或操作描述；通知、购票、预订、取消及退款由宿主另行执行和核实。

## 当前接入方式

| 入口 | 用途 |
| --- | --- |
| [`tripctl` CLI](https://github.com/glenzli/plan-gacha/blob/main/docs/tripctl.md) | AI 操作员的完整行程入口，支持 schema 发现、读取、分析、预览、保存和恢复。 |
| [`tripctl-lib.mjs` / TypeScript library](https://github.com/glenzli/plan-gacha/blob/main/src/tripctl/index.ts) | 直接调用同一核心、schema、文件存储与展示接口。 |
| [操作员 skill](https://github.com/glenzli/plan-gacha/blob/main/skills/plan-gacha-operator/SKILL.md) | 约定意图解释、主动核查、来源与不确定性、授权保存和读回流程。 |
| [stdio MCP](https://github.com/glenzli/plan-gacha/blob/main/docs/planning-tools.md) | 四个无状态 snapshot 工具：`get_context`、`evaluate_plan`、`rank_candidates`、`preview_changes`。调用者提供数据，工具返回分析或候选，不写入行程。 |

源码调用需要 Node.js >=22.13。`npm run build` 构建便携 CLI/library；`dist/tripctl` 包含运行文件、操作员 skill、契约文档和合成示例，运行时无需安装依赖。安装与具体操作见 [README](https://github.com/glenzli/plan-gacha#中文) 和 [CLI 文档](https://github.com/glenzli/plan-gacha/blob/main/docs/tripctl.md)。

## 旧网页版与数据交接

本站不再提供原 React 网页、浏览器同步或 PWA 入口。旧网页的源码、JSON 导入导出、浏览器存储与同步适配器保存在带注释的 [`legacy-web-final`](https://github.com/glenzli/plan-gacha/tree/legacy-web-final) tag 中，也可从 [GitLab 留档](https://gitlab.com/glenzli/plan-gacha/-/tree/legacy-web-final)查看。需要检查或运行旧版时，可在独立目录检出留档，按其中的说明启动。

旧数据默认保存在原浏览器与 origin 的 `localStorage` 中，CLI/MCP 不会自动读取，下线部署也不会自动迁移个人数据。迁移前应从原环境显式导出并保留原始备份，再按实际 schema 准备输入、预览并审阅保存。旅行导出不含独立清单与天气缓存；完整工作区备份包含所有旅行与清单。新检出的旧网页也不会自动读取原浏览器与 origin 的数据。

组件仍提供[宿主只读展示接口](https://github.com/glenzli/plan-gacha/blob/main/docs/presentation-contract.md)。旧网页的 `driveStorage` 是历史同步实现；当前操作员的外部存储流程需要宿主完成版本校验保存与读回，本站项目说明不承担行程存储。
