# 【修改接口·管理后台】订单调整记录：出参枚举新增 TRAVELER_EDIT（出行人资料修改）(#4614)

> **PR**: #4614 | **服务**: hl-order-service-v3 | **更新时间**: 2026-06-29

## 1. 接口背景

「订单调整记录」接口（`GET /v3/admin/order/{id}/adjustment-record`）返回本订单所有调整操作的逐项变更明细。每条记录含 `items[]` 数组，每个变更项有 `type` 字段表示该项变更的类型。

本次在 `type` 枚举中**新增 `TRAVELER_EDIT`（出行人资料修改）**。此前，定制师在「订单调整」中只修改出行人资料字段（证件类型 / 姓名 / 证件号 / 联系电话），不改人数时，调整记录里**不会产生任何变更项**，导致历史操作看不到「改了什么」。本次修复这一缺口，使每次出行人资料编辑都有迹可查。

同时修复了纯重复提交（出行人字段实际无变化）产生 `changeCount=0` 空记录的问题——现在若字段真的未变，不再产生多余的空记录。

## 2. 变更清单

| # | 接口 | 方法 | 路径 | 变更类型 | 说明 |
|---|------|------|------|----------|------|
| 1 | 订单调整记录列表 | GET | `/v3/admin/order/{id}/adjustment-record` | 修改接口 | 出参 `items[].type` 枚举新增 `TRAVELER_EDIT` 取值 |

> 无新增字段、无删除字段、无路径变更，向后兼容。若前端对 `type` 做了穷举 switch / 枚举映射，需补 `TRAVELER_EDIT` 分支。

---

## 3. 接口详情

- **路径**: `GET /v3/admin/order/{id}/adjustment-record`
- **使用场景**: 管理后台订单详情页「调整记录」Tab，展示历次调整操作的变更明细。
- **认证**: 需要管理后台 JWT。
- **幂等性**: GET 只读，无副作用。
- **限流**: 无特殊限流。

---

## 4. 接口入参

### 4.1 路径参数

| 参数 | 类型 | 必填 | 说明 |
|------|------|------|------|
| `id` | Long | ✅ | 订单 ID |

无请求体。

---

## 5. 出参字段

**顶层结构**: `Result<List<AdjustmentRecordVO>>`

**AdjustmentRecordVO**（每条调整记录）

| 字段 | 类型 | 说明 |
|------|------|------|
| `id` | String | 调整记录 ID |
| `operatorName` | String | 操作人姓名 |
| `adjustedAt` | String | 调整时间（ISO 8601） |
| `changeCount` | Integer | 本次调整的变更项数量 |
| `balanceBefore` | String | 调整前应付尾款（字符串，如 `"1000.00"`） |
| `balanceAfter` | String | 调整后应付尾款（字符串） |
| `items` | Array\<ChangeItemVO\> | 变更项明细列表 |

**ChangeItemVO**（单个变更项）

| 字段 | 类型 | 说明 |
|------|------|------|
| `type` | String | 变更类型枚举（见第 6 节） |
| `label` | String | 后端拼好的中文展示名（直接渲染，如 `出行人「张三」资料修改`） |
| `before` | String | 变更前描述（如 `证件类型 身份证；证件号 110***1234`） |
| `after` | String | 变更后描述（如 `证件类型 护照；证件号 E12***5678`） |
| `amountDelta` | String / null | 本项价差（字符串）；`TRAVELER_EDIT` 类型此字段恒为 `null`（资料编辑无价差） |

> `before` / `after` 中的证件号、手机号已由后端脱敏（首 3 末 4，中间全 `*`），前端直接展示即可，无需二次处理。
> 证件类型显示中文名（身份证 / 护照 / 台胞证 / 回乡证…），由后端查数据字典翻译。

---

## 6. 枚举 / 数据字典

### AdjustChangeType（变更类型枚举）

| 枚举值 | 中文说明 | `amountDelta` | 本次状态 |
|--------|----------|---------------|----------|
| `HEADCOUNT` | 人数变更 | 可能有值 | 既有 |
| `DEPART_DATE` | 出发日期调整 | 可能有值 | 既有 |
| `TRIP_DAYS` | 行程天数调整 | 可能有值 | 既有 |
| `EDIT_NODE` | 改项（修改行程节点） | 可能有值 | 既有 |
| `ADD_NODE` | 增项（新增行程节点） | 可能有值 | 既有 |
| `REMOVE_NODE` | 删项（删除行程节点） | 可能有值 | 既有 |
| `HOTEL_REQ` | 酒店需求已调整 | `null` | 既有 |
| `VEHICLE_REQ` | 车辆需求已调整 | `null` | 既有 |
| **`TRAVELER_EDIT`** | **出行人资料修改** | **`null`** | **本次新增** |

> 若前端对 `type` 做了穷举渲染（switch / enum map），需补 `TRAVELER_EDIT` 分支，否则该类变更项在列表中可能不显示或落入 default 样式。

---

## 7. 错误码

本接口为只读查询接口，本次变更不引入新错误码。既有错误码（如订单不存在 `581001`）不变。

---

## 8. 示例

### 8.1 典型成功——包含 TRAVELER_EDIT 变更项

**请求**：
```
GET /v3/admin/order/1234567890/adjustment-record
Authorization: Bearer <管理后台 JWT>
```

**响应**（200，含一条出行人资料修改记录）：
```json
{
  "code": 200,
  "message": "success",
  "data": [
    {
      "id": "9876543210",
      "operatorName": "李顾问",
      "adjustedAt": "2026-06-29T10:30:00",
      "changeCount": 1,
      "balanceBefore": "6000.00",
      "balanceAfter": "6000.00",
      "items": [
        {
          "type": "TRAVELER_EDIT",
          "label": "出行人「张三」资料修改",
          "before": "证件类型 身份证；证件号 110***1234",
          "after": "证件类型 护照；证件号 E12***5678",
          "amountDelta": null
        }
      ]
    }
  ],
  "success": true
}
```

### 8.2 边界情况——同一次调整多字段同时改变

当出行人同时修改了证件类型、证件号、手机号三个字段，`before` / `after` 以分号拼串展示所有变化字段：

```json
{
  "type": "TRAVELER_EDIT",
  "label": "出行人「李四」资料修改",
  "before": "证件类型 身份证；证件号 320***5678；手机号 138***0000",
  "after": "证件类型 台胞证；证件号 TE1***234；手机号 139***9999",
  "amountDelta": null
}
```

> 若出行人只改了一个字段，`before` / `after` 中只出现该字段。

### 8.3 业务失败——订单不存在

**请求**（id 不存在）：
```
GET /v3/admin/order/9999999999/adjustment-record
```

**响应**：
```json
{
  "code": 581001,
  "message": "订单不存在",
  "success": false
}
```

---

## 9. 业务边界

- ✅ `TRAVELER_EDIT` 仅在「出行人资料字段有实际变化」时才产生变更项（证件类型 / 姓名 / 证件号 / 联系电话四字段任一有变化即记录）。
- ❌ 出行人字段与原值完全相同（no-op 重复提交）→ 不产生 `TRAVELER_EDIT` 变更项，也不产生 `changeCount=0` 的空记录（本次同步修复）。
- ❌ 出行人**增减人数**（HEADCOUNT 变更）→ 走 `HEADCOUNT` 类型，不走 `TRAVELER_EDIT`。
- ⚠️ `TRAVELER_EDIT` 的 `amountDelta` 恒为 `null`（资料编辑不涉及价差），`balanceBefore` 与 `balanceAfter` 在该记录下通常相等。
- ⚠️ `before` / `after` 已脱敏：前端直接渲染，无需再次脱敏。

---

## 10. 修改前后对比

### 枚举值变化

| 类型 | 变更 |
|------|------|
| `TRAVELER_EDIT` | **新增**（此前不存在） |
| 其余 8 个取值 | 不变 |

### 行为变化

| 场景 | 修改前 | 修改后 |
|------|--------|--------|
| 出行人只改资料字段、不改人数 | 调整记录无变更项（看不到操作记录） | 产生 `type=TRAVELER_EDIT` 变更项，可追溯 |
| 出行人字段提交但无实际变化（no-op） | 产生 `changeCount=0` 的空记录 | 不产生空记录 |

---

## 11. 影响评估 / 回滚

- **是否破坏向后兼容**: 否。纯新增枚举值 + 新增场景下的数据；不影响既有变更项。
- **前端是否必须同步上线**: 非强制，但**建议尽快补 `TRAVELER_EDIT` 分支**。若前端对 `type` 做穷举渲染而未覆盖此值，出行人资料修改记录会不显示或以 default 样式渲染。
- **回滚方案**: 本次变更在 Service 层追加枚举分支，后端回滚即恢复旧行为（不产生 `TRAVELER_EDIT` 记录）；已写入 DB 的历史记录不会自动清除，但量极少（仅上线后的操作）。前端无需配合回滚。

---

## 12. 注意事项

1. 若前端调整记录组件对 `items[].type` 做 switch 渲染（如显示图标 / 颜色），需新增 `TRAVELER_EDIT` 分支，建议展示样式与 `HOTEL_REQ` / `VEHICLE_REQ`（无价差的信息类变更）一致。
2. `before` / `after` 中的多字段拼接格式为「字段名 原值；字段名 原值」，前端按原文展示即可，无需解析内部结构。
3. 证件号 / 手机号已由后端脱敏，前端**不可**用 `before` / `after` 做业务判断（脱敏后精度已损）。

---

## 13. 关联 / 联系人

### 13.1 链接

- **Issue**: [#4612](https://git.1814.love:8443/wx/HL/issues/4612)
- **PR**: [#4614](https://git.1814.love:8443/wx/HL/pulls/4614)
- **Merge commit**: [1744d31b4](https://git.1814.love:8443/wx/HL/commit/1744d31b4875752d5e74cd5c16f7d787c17eeb68)

### 13.2 联系人

- **后端负责人**: @yst
- **前端对接（管理后台）**: 订单详情·调整记录 Tab
