docs: specify transport plan required brand as preference only
Document that feedback/archive brand qty entry uses any-mode multi-select with preferred-brand preselect, removing the single-brand hard lock. Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
1 parent
6dcc279cc9
commit
b3efbe8781
1 file changed
+98
@@ -0,0 +1,98 @@
|
||||
# 运输计划「指定品牌」回填改为偏好提示设计
|
||||
|
||||
**日期:** 2026-07-31
|
||||
**状态:** 已确认待实现
|
||||
**关联:** 修订 `docs/superpowers/specs/2026-07-31-pl-feedback-brand-qty-design.md` 中 `required`「仅指定品牌可选」硬锁语义
|
||||
**选定方案:** 方案 1 — 回填侧统一按 `any` 规则校验与交互;计划侧仍保留 `brandMode=required` + `brandId`/`brandName` 作偏好展示
|
||||
|
||||
## 背景与目标
|
||||
|
||||
运输计划产品行可选「指定品牌」(`brandMode=required`)。原设计在司机链接、现场链接、归档弹窗等回填路径上硬锁为:只能填写该品牌一行,且数量必须等于实际数量。
|
||||
|
||||
实际业务中,计划指定品牌仅表示偏好/提示;回填时常需按多品牌拆分实装量,且不必强制包含计划指定品牌。
|
||||
|
||||
本变更取消回填硬限制,保留计划侧偏好语义与默认预选。
|
||||
|
||||
## 决策摘要
|
||||
|
||||
| 项 | 决策 |
|
||||
|----|------|
|
||||
| 指定品牌含义 | 计划侧提示/偏好;回填不必包含该品牌 |
|
||||
| 回填交互 | 与「不限品牌」相同:多选芯片、可取消 |
|
||||
| 默认选中 | 打开回填时预选计划指定品牌(数量可改、可取消),仍可再选其他品牌 |
|
||||
| 存库语义 | 不改计划创建:选品牌仍为 `required`+id/name;清空仍为 `any` |
|
||||
| 校验 | `required` 与 `any` 共用:至少一正数量行,合计 = 实际数量 |
|
||||
| 范围外 | 不改表结构、不迁历史、不做「必须包含指定品牌」 |
|
||||
|
||||
## 行为规则
|
||||
|
||||
### 不变
|
||||
|
||||
- 计划 / 报价 / 合同建单:品牌下拉选中 → `brandMode=required` + 快照;清空 → `any`
|
||||
- `brandMode` 为空:回填不展示品牌区,只填总量
|
||||
- 有 `brandMode`(`any` / `required`):至少 1 个品牌 `qty > 0`,且各品牌合计等于该产品实际数量
|
||||
- 现场 / 司机 / 归档三套品牌数量仍互相独立;归档最终量仍为库存入账权威来源
|
||||
|
||||
### 变更后回填规则
|
||||
|
||||
适用范围:司机公开页、现场入/出库公开页、运输计划归档弹窗、管理端司机回传补录、计划详情内现场回传编辑等所有品牌填量入口。
|
||||
|
||||
| 计划约定 | 芯片交互 | 默认选中 | 是否必须包含指定品牌 |
|
||||
|---------|---------|---------|---------------------|
|
||||
| `required` + 某品牌 | 与 `any` 相同:多选可取消 | 预选该偏好品牌(已有已保存明细则优先回显) | 否 |
|
||||
| `any` | 多选 | 仅产品仅有一个启用品牌时预填(现状) | 不适用 |
|
||||
| 无 `brandMode` | 不展示品牌区 | — | — |
|
||||
|
||||
### 展示
|
||||
|
||||
- 计划与回填区可继续展示「指定品牌 · xxx」类提示标签(偏好说明)
|
||||
- `BrandQtyChipsField` 标题统一为「选择品牌并填量」,不再使用「指定品牌填量」以免暗示单品牌锁定
|
||||
|
||||
## 实现要点
|
||||
|
||||
### 后端
|
||||
|
||||
- `backend/app/services/pl_brand_archive.py` → `validate_brand_qty_rows`:删除 `required` 分支中「只能填写该品牌」「单行数量必须等于实际数量」的校验;`required` 与 `any` 均校验正数量合计等于 `actual_qty`
|
||||
- 调用方(归档 `pl_plan_service`、`pl_feedback_brand_qty.require_brand_qtys_if_needed` 等)签名可保持;`required_brand_id` 不再用于硬锁校验(可保留参数以免大范围改签名,或后续清理)
|
||||
- 错误文案:去掉「指定品牌时只能填写该品牌数量」路径
|
||||
|
||||
### 前端
|
||||
|
||||
- `BrandQtyChipsField`:`required` 不再渲染锁定芯片(`chip--locked`);统一走多选芯片;`requiredBrandId` 仅供父级默认预选,组件内不禁止取消
|
||||
- 父级初始化(至少覆盖):
|
||||
- `pl-plan-archive-dialog`
|
||||
- `views/public/pl/transport/index.vue`
|
||||
- `views/public/pl/_shared/PublicIoOrderPage.vue`
|
||||
- `pl-plan-driver-feedback-dialog`
|
||||
- `pl-plan-view-tabs` 内现场品牌编辑
|
||||
- `required` 初始化:`brandOptions` 加载产品全部启用品牌(与 `any` 相同);无已保存明细时 `brandQtyRows` 预填指定品牌一行
|
||||
- 删除归档弹窗 `syncRequiredBrandQty`:不再把实际数量强制同步到唯一指定品牌行;有品牌时实际数量由品牌合计驱动(与现 `any` 一致)
|
||||
|
||||
### 文档 / Demo
|
||||
|
||||
- 修正 `docs/demos/pl-site-driver-brand-qty-demo.html` 中「指定品牌时仅允许该品牌一行」说明
|
||||
- 本文件为权威变更说明;原 `2026-07-31-pl-feedback-brand-qty-design.md` 中 `required` 硬锁描述以本文件为准覆盖
|
||||
|
||||
## 测试
|
||||
|
||||
### 后端
|
||||
|
||||
- `required` + 多品牌合计等于实际数量 → 通过
|
||||
- `required` + 仅非指定品牌且合计正确 → 通过
|
||||
- `required` + 合计 ≠ 实际数量 → 失败
|
||||
- `required` + 完成态无正数量行 → 失败
|
||||
- `any` 原有用例行为不变
|
||||
|
||||
### 前端手工验收
|
||||
|
||||
1. 计划产品指定品牌 → 司机链接可多选、可取消预选并保存成功
|
||||
2. 同上现场链接
|
||||
3. 运输计划归档弹窗同上
|
||||
4. 管理端司机回传补录同上
|
||||
5. `any` / 无品牌产品行为与现网一致
|
||||
|
||||
## 风险
|
||||
|
||||
- 历史已保存回传/归档数据不受影响;仅新提交走新校验
|
||||
- 外部若曾依赖「指定品牌必填该品牌」,需业务知悉;仓库内无额外集成硬依赖
|
||||
- `brandMode=required` 命名与回填行为不完全同义:文档与 UI 提示须写清「仅偏好」
|
||||
Reference in new issue
Block a user