# 接口文档:团期日历数据 > **日期**: 2026-03-27 > **类型**: 📖 接口文档补充(非新增接口,已有接口的完整使用说明) > **涉及服务**: hl-product-service、hl-mp-service > **接口状态**: ✅ 已上线可用 --- ## 一、功能说明 此接口为 **GROUP(小蒙马拼团)产品** 提供团期日历数据,供小程序端日历选择器展示。 **核心能力**: - 返回指定产品所有**可报名**团期(状态为 ENROLLING 或 CONFIRMED) - 只返回**今天及以后**的出发日期(历史团期自动过滤) - 每个团期包含:出发日期、起步价、定金金额、剩余名额、剩余房间数、是否已成团 - 起步价来源于**价格日历**(product_price_calendar 表的成人售价) - 定金计算规则:固定金额优先,否则用 `起步价 × 定金比例%`(向上取整) --- ## 二、接口清单 | # | 接口 | 方法 | 路径 | 说明 | |---|------|------|------|------| | 1 | 团期日历(内部) | GET | `/internal/product/{productId}/batches/calendar` | 服务间调用 | | 2 | 团期日历(C端) | GET | `/mp/product/{productId}/batches/calendar` | 小程序直接调用(经网关) | > 两个接口返回数据完全相同,区别仅在路由层: > - **内部接口**:hl-mp-service 通过 Feign 调用 hl-product-service > - **C端接口**:小程序通过网关 `/mp/product/...` 直接请求 --- ## 三、接口详细定义 ### GET `/mp/product/{productId}/batches/calendar` > **前端应调用此路径**(经网关转发),不要直接调用 internal 路径 #### 使用场景 小程序 GROUP 产品详情页,展示**团期日历选择器**,用户选择出发日期后进入报价流程。 #### 请求参数 | 参数 | 位置 | 类型 | 必填 | 说明 | |------|------|------|------|------| | productId | path | Long | ✅ | 产品ID(必须是 GROUP 类型产品) | #### 请求示例 ``` GET /mp/product/1903770276454400001/batches/calendar ``` #### 响应示例 ```json { "code": 200, "message": "操作成功", "data": [ { "departureDate": "2026-05-01", "batchId": "1903770276454400101", "batchLabel": "五一团", "batchName": "2026年五一黄金周第一批", "batchStatus": "ENROLLING", "startingPrice": 12800.00, "enrolledCount": 15, "remainingSlots": 15, "maxRooms": 15, "bookedRooms": 5, "remainingRooms": 10, "isConfirmed": false, "depositAmount": 3999.00 }, { "departureDate": "2026-05-08", "batchId": "1903770276454400102", "batchLabel": "五一加开团", "batchName": "2026年五一黄金周第二批", "batchStatus": "CONFIRMED", "startingPrice": 11800.00, "enrolledCount": 28, "remainingSlots": 2, "maxRooms": 15, "bookedRooms": 13, "remainingRooms": 2, "isConfirmed": true, "depositAmount": 3540.00 } ] } ``` --- ## 四、响应字段说明 | 字段 | 类型 | 说明 | |------|------|------| | `departureDate` | String (yyyy-MM-dd) | 出发日期 | | `batchId` | String | 批次ID(雪花ID字符串) | | `batchLabel` | String | 批次标签(短名,如"五一团") | | `batchName` | String | 批次全称 | | `batchStatus` | String | 批次状态,见下方枚举 | | `startingPrice` | BigDecimal | 起步价(元),来自价格日历的成人售价。**可能为 null**(价格日历未配置时) | | `enrolledCount` | Integer | 已报名人数 | | `remainingSlots` | Integer | 剩余名额 = maxParticipants - enrolledCount | | `maxRooms` | Integer | 总房间数 | | `bookedRooms` | Integer | 已预订房间数 | | `remainingRooms` | Integer | 剩余房间数 = maxRooms - bookedRooms | | `isConfirmed` | Boolean | 是否已成团(batchStatus == "CONFIRMED" 时为 true) | | `depositAmount` | BigDecimal | 定金金额(元/人)。**可能为 null**(未配置定金且无起步价时) | --- ## 五、枚举/字典值 ### batchStatus 批次状态(本接口只返回前两种) | 值 | 中文 | 说明 | |----|------|------| | `ENROLLING` | 报名中 | ✅ 本接口会返回,可正常报名 | | `CONFIRMED` | 已成团 | ✅ 本接口会返回,已达成团人数,仍可继续报名 | | `PENDING` | 待开放 | ❌ 不会返回 | | `FULL` | 已满员 | ❌ 不会返回 | | `DEPARTED` | 已出发 | ❌ 不会返回 | | `COMPLETED` | 已完成 | ❌ 不会返回 | | `CANCELLED` | 已取消 | ❌ 不会返回 | --- ## 六、业务规则 1. **过滤条件**:只返回 `batchStatus IN ('ENROLLING', 'CONFIRMED')` 且 `departureDate >= 今天` 的团期 2. **排序**:按出发日期升序 → 排序号升序 3. **起步价来源**:从 `product_price_calendar` 表查询对应日期的 `adult_sell_price`,状态必须为 AVAILABLE 4. **定金计算**: - 如果产品配置了固定定金金额(`deposit_amount > 0`)→ 直接使用 - 否则用 `起步价 × deposit_ratio / 100`,向上取整(RoundingMode.UP) - 两者都没有配置时 → depositAmount 为 null 5. **非 GROUP 产品调用此接口**:返回空数组 `[]`(不会报错) --- ## 七、调用位置(后端内部使用情况) 此接口在后端有 **3 处调用**,前端了解即可: | 调用位置 | 场景 | 说明 | |----------|------|------| | `MpProductController.java:97` | 产品列表接口 | GROUP 产品列表自动追加 `batches` 字段 | | `ProductAggregationService.java:174` | 产品详情聚合 | GROUP 产品详情页异步加载团期 | | `MpProductFeignClient.java:57` | Feign 声明 | hl-mp-service → hl-product-service 的 Feign 调用声明 | ### 前端调用建议 **场景1:产品列表页** - GROUP 产品列表接口 `GET /mp/product/list` 已自动包含 `batches` 字段(数组),无需单独调用 **场景2:产品详情页** - 产品详情聚合接口 `GET /mp/product/{id}/detail` 已自动包含 `batches` 字段,无需单独调用 **场景3:需要单独刷新团期** - 用户在详情页停留较久需要刷新团期时,可单独调用 `GET /mp/product/{productId}/batches/calendar` --- ## 八、前端实现建议 ``` ┌─────────────────────────────────────────────┐ │ 团期日历选择器 │ │ │ │ ┌─────┐ ┌─────┐ ┌─────┐ ┌─────┐ ┌─────┐ │ │ │ 4/28│ │ 4/29│ │ 4/30│ │ 5/01│ │ 5/02│ │ │ │ │ │ │ │ │ │五一团│ │ │ │ │ │ │ │ │ │ │ │¥12800│ │ │ │ │ │ — │ │ — │ │ — │ │剩15位│ │ — │ │ │ └─────┘ └─────┘ └─────┘ └─────┘ └─────┘ │ │ │ │ 选中团期信息: │ │ ┌──────────────────────────────────────┐ │ │ │ 五一团 · 2026-05-01出发 │ │ │ │ 起步价 ¥12,800/人 定金 ¥3,999/人 │ │ │ │ 剩余 15 名额 · 剩余 10 间房 │ │ │ │ 🔴 报名中(未成团) │ │ │ └──────────────────────────────────────┘ │ │ │ │ [ 立即报名 ] │ └─────────────────────────────────────────────┘ ``` **展示建议**: - 日历格子:有团期的日期高亮显示,无团期的日期置灰 - `isConfirmed = true` → 显示 "已成团" 绿色标签 - `isConfirmed = false` → 显示 "报名中" 橙色标签 - `remainingSlots <= 3` → 显示 "仅剩X位" 红色提示 - `remainingRooms <= 2` → 显示 "房间紧张" 提示 - `startingPrice` 为 null → 显示 "价格待定" - `depositAmount` 不为 null → 显示 "定金 ¥xxx/人" - `batchLabel` 作为日历格子内的短标签显示 --- *📖 此文档为已有接口的详细说明,无代码变更*