# 镜框尺寸与产品尺寸兼容处理方案

## 一、背景

`2027-07-30会议纪要-整理版.md` 中提出：镜框尺寸信息需要提供给镜片加工商，包括镜片宽度、鼻梁宽度、镜腿长度，示例格式为 `54□18-135`。

现有产品模型中已经存在 `product.l`、`product.w`、`product.h`、`box_l`、`box_w`、`box_h`、`inner_box_l`、`inner_box_w`、`inner_box_h` 等尺寸字段。这些字段当前主要服务产品本体尺寸、包装尺寸、标签打印、物流计费、仓储和发货场景。

两类尺寸虽然都叫“尺寸”，但业务语义不同，不能直接复用同一组字段。

## 二、核心结论

镜框尺寸不应覆盖或复用原产品尺寸字段。

推荐采用三层数据模型兼容：

1. `product` 原尺寸字段继续表示通用产品、包装、物流尺寸。
2. 眼镜行业属性通过 `product` 表新增 `frame_*` 字段维护镜框加工尺寸。
3. 订单履约时将当时的镜框尺寸写入部件参数快照，供供应商加工和历史追溯使用。

## 三、尺寸语义拆分

### 1. 原产品尺寸

原产品尺寸继续使用现有字段：

| 字段 | 语义 | 使用场景 |
| --- | --- | --- |
| `product.l` / `product.w` / `product.h` | 产品本体长宽高 | 商品资料、标签、基础展示 |
| `box_l` / `box_w` / `box_h` | 外箱尺寸 | 物流计费、装箱、仓储 |
| `inner_box_l` / `inner_box_w` / `inner_box_h` | 内盒尺寸 | 包装、供应商发货、标签 |

这些字段不参与镜片加工参数计算，也不用于生成 `54□18-135`。

### 2. 镜框尺寸

镜框尺寸是眼镜行业专属属性，主要服务镜片加工商和定制履约。

推荐字段：

| 字段 | 说明 | 示例 |
| --- | --- | --- |
| `frame_lens_width` | 镜片宽度 | `54` |
| `frame_lens_height` | 镜片高度 | `40` |
| `frame_width` | 镜框宽度 | `138` |
| `frame_bridge_width` | 中梁宽度 | `18` |
| `frame_temple_length` | 镜腿长度 | `135` |
| `frame_lens_diagonal` | 镜片斜对角线 | `56` |
| `frame_size_display` | 标准展示格式 | `54□18-135` |
| `frame_size_unit` | 单位 | `mm` |

## 四、推荐数据结构

### 1. 产品眼镜属性字段

镜框尺寸和颜色直接通过 `product` 表新增字段维护，不再新增 `optical_product_profile`，也不再复用 `product_extra`。

```text
product.frame_*  # 镜框行业字段
```

约定固定字段：

| 字段 | 说明 |
| --- | --- |
| `frame_lens_width` | 镜片宽度 |
| `frame_lens_height` | 镜片高度 |
| `frame_width` | 镜框宽度 |
| `frame_bridge_width` | 中梁宽度 |
| `frame_temple_length` | 镜腿长度 |
| `frame_lens_diagonal` | 镜片斜对角线 |
| `frame_size_display` | 镜框尺寸展示，如 `54□18-135` |
| `frame_size_unit` | 尺寸单位，默认 `mm` |
| `frame_color` | 镜框颜色 |

说明：

- `frame_size_display` 可由三个数值字段自动生成，也允许人工维护。
- 这些字段作为定制项目固定业务字段使用，直接参与产品维护、订单快照、供应商展示。

### 2. 订单部件参数快照

下单生成定制履约部件时，在 `custom_item_component.params_snapshot` 中保存当时的镜框尺寸。

仅 `component_type = frame` 的部件写入镜框尺寸：

```json
{
  "frame": {
    "product_id": 123,
    "sku": "FRAME-001",
    "color": "Black",
    "size": {
      "lens_width": 54,
      "lens_height": 40,
      "frame_width": 138,
      "bridge_width": 18,
      "temple_length": 135,
      "lens_diagonal": 56,
      "lens_max_width": 56,
      "display": "54□18-135",
      "unit": "mm"
    }
  }
}
```

订单快照的作用：

- 保证历史订单不受产品资料后续变更影响。
- 供应商加工单展示以订单快照为准。
- 重做、补发、售后追溯时能够看到原始加工参数。

## 五、读取优先级

供应商端、委外单、生产履约页面展示镜框尺寸时，按以下优先级取值：

```text
custom_item_component.params_snapshot.frame.size
  -> product.frame_*
  -> 空值/待补充
```

不要回退到 `product.l`、`product.w`、`product.h` 作为镜框尺寸。

原因：

- 产品长宽高和镜框加工尺寸不是同一计量对象。
- 错用后会影响镜片加工准确性。
- 物流包装字段后续可能由仓库或包材维护，不能污染生产加工参数。

## 六、写入流程建议

### 1. ERP 创建或维护产品

维护两组信息：

- 基础产品尺寸：继续填写 `product.l/w/h`、包装尺寸、重量等。
- 眼镜行业属性：填写镜片宽度、鼻梁宽度、镜腿长度、颜色等。

### 2. Shopify 产品同步

同步 Shopify 时：

- 商品展示需要镜框尺寸时，使用 `product.frame_size_display`。
- 物流、重量、包装信息仍使用原产品尺寸和重量字段。
- 不建议把 Shopify 展示尺寸反写到 `product.l/w/h`。

### 3. Shopify 订单同步

订单同步生成定制履约时：

1. 根据销售明细识别镜框产品。
2. 读取产品 `frame_*` 字段。
3. 生成 `custom_item_component(component_type = frame)`。
4. 将镜框尺寸写入 `params_snapshot.frame.size`。
5. 镜片委外单创建时，从订单部件快照读取并传递给供应商。

### 4. 手工订单或补录

如果订单生成时产品镜框字段缺失：

- 允许人工在履约部件上补录镜框尺寸。
- 补录值写入 `custom_item_component.params_snapshot`。
- 是否反向更新产品字段由前端提供选项，默认不自动反写。

## 七、前端展示建议

### 产品维护页

产品页可分组展示：

- 基础尺寸：长、宽、高、外箱、内盒、重量。
- 眼镜属性：镜片宽度、鼻梁宽度、镜腿长度、镜框尺寸展示、颜色。

避免都叫“尺寸”，建议文案区分为：

- `产品尺寸`
- `包装尺寸`
- `镜框尺寸`

### 供应商端

镜片加工供应商只展示必要字段：

- 镜框 SKU / 型号
- 镜框颜色
- 镜框尺寸：`54□18-135`
- 左右眼镜片参数
- 加工要求和备注

不展示原产品长宽高、包装尺寸、销售价格等无关或敏感字段。

## 八、兼容历史数据

历史产品没有镜框尺寸时：

1. 不迁移 `product.l/w/h` 到镜框尺寸字段。
2. 可通过 Excel 批量导入补充产品 `frame_*` 字段。
3. 已生成订单如果缺失快照，可在履约部件上人工补录。
4. 已完成订单原则上保持历史数据不变，仅在售后或重做需要时补录。

## 九、实施顺序

1. 在 `product` 表新增镜框尺寸和颜色固定字段。
2. 产品维护接口支持 `frame_*` 字段读写。
3. Shopify 产品同步增加镜框尺寸展示映射。
4. Shopify 订单同步生成 `frame` 部件时写入尺寸快照。
5. 委外单和供应商端从部件快照读取镜框尺寸。
6. 增加历史产品批量导入或补录能力。

## 十、最终口径

原产品尺寸管包装、物流和通用产品资料。

镜框尺寸管镜片加工和眼镜行业展示。

订单快照管历史追溯和供应商履约。

三者并存，不互相覆盖。
