diff --git a/docs/superpowers/specs/2026-08-11-ticket-home-api-design.md b/docs/superpowers/specs/2026-08-11-ticket-home-api-design.md new file mode 100644 index 0000000..ad1bbc8 --- /dev/null +++ b/docs/superpowers/specs/2026-08-11-ticket-home-api-design.md @@ -0,0 +1,68 @@ +# TicketHome 首页接口接入设计 + +## 目标 + +在 `src/pages-service/tickets/index.vue` 中调用 `scenicProductHome`,使用固定参数: + +```js +{ scenicId: 20260811 } +``` + +以接口返回的数据替换票务首页现有的 `SCENIC_SPOT`、`GROUPS` 和 `ticketStore.products` 静态数据。本次只接入首页接口,不修改商品详情、预订、订单等后续页面的数据来源。 + +## 数据流与组件边界 + +- `index.vue` 负责请求、保存首页数据以及加载和失败状态。 +- 请求成功且 `code === 0`、`data` 为对象时,将 `data` 原样保存,不创建字段映射或首页 DTO 适配器。 +- `TicketHome.vue` 直接使用接口字段,不再依赖静态数据字段名: + - 景区:`scenicId`、`scenicName`、`subtitle`、`levelText`、`address`、`phone`、`longitude`、`latitude`、`coverImage`、`mediaList` + - 分类:`categories` 中的 `categoryId`、`categoryName`、`title`、`subtitle`、`defaultFlag` + - 商品:`products.records` 中的 `commodityId`、`categoryId`、`saleTargetKey`、`title`、`image`、`tags`、`displayPrice`、`salesText`、`detailRouteType`、`bookingFeatureFlags` + - 默认分类:`selectedCategoryId` +- `index.vue` 通过单个 `homeData` prop 将接口 `data` 传给 `TicketHome.vue`,避免将接口结果拆分或转换成旧的 `scenicSpot/groups/products` props。 +- `TicketHome.vue` 按商品的 `categoryId` 过滤每个分类下的首屏商品,并以 `commodityId` 作为商品点击事件参数。 + +## 展示规则 + +- 景区头图使用 `coverImage`,景区名称使用 `scenicName`。 +- 等级和副标题使用 `levelText` 与 `subtitle`;任一字段为空时不渲染多余分隔符。 +- 分类导航和分组标题使用 `categoryName`,分类说明使用分类 `subtitle`;分类 `title` 作为辅助标签,仅在非空时展示。 +- 商品卡展示 `image`、`title`、`tags`、`displayPrice` 和 `salesText`。 +- 接口中的字段为空时使用空态或隐藏对应可选内容,不回填旧静态文案或图片。 +- 电话和导航继续使用现有交互;经纬度为空或非法时沿用“暂无导航坐标”提示。 +- 左右分类滚动联动保持不变。初始高亮优先使用 `selectedCategoryId`,无有效匹配时使用第一个分类。 + +## 加载、失败与空数据 + +- 页面首次加载时请求一次 `scenicProductHome`。 +- 加载期间显示明确的加载状态,不渲染静态首页。 +- 请求失败、业务 `code !== 0` 或 `data` 无效时显示错误状态和重试入口,并使用接口 `msg` 或通用错误文案说明失败原因。 +- 请求成功但分类或商品为空时,仍渲染景区信息,由 `TicketHome.vue` 展示对应空状态。 +- 重试只重新请求首页接口,不重复导航或重置其他票务 store 状态。 + +## 测试与验证 + +- 先扩展 `view-contract.test.mjs`,验证: + - `index.vue` 调用 `scenicProductHome({ scenicId: 20260811 })`。 + - 首页不再导入或传入 `SCENIC_SPOT`、`GROUPS`、`ticketStore.products`。 + - `TicketHome.vue` 使用接口原始字段及 `products.records`。 + - 分类商品通过 `categoryId` 关联,商品事件使用 `commodityId`。 + - 页面包含加载、失败和重试状态。 +- 确认新增测试先因功能未实现而失败,再实施最小代码使其通过。 +- 实现后运行: + + ```bash + node --test src/pages-service/tickets/view-contract.test.mjs + node --test src/pages-service/tickets/model.test.mjs + git diff --check + ``` + +本次变更不涉及依赖、配置或微信小程序编译能力,因此不默认运行生产构建。 + +## 非目标 + +- 不调用 `scenicCategoryProductsList` 或 `scenicProductCardContext`。 +- 不把首页卡片数据写入现有 Pinia 票务 store。 +- 不把首页简略商品数据转换为详情页所需的旧商品模型。 +- 不调整商品详情、预订、订单、退款和凭证页的数据结构。 +- 不修改接口文件或当前客户配置。