Files
shanxia2.0/docs/web-admin-ui-pattern-index.md
T
2026-05-26 19:04:27 +08:00

510 lines
19 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# web-admin 界面模式索引
> **用途**:新功能开发前,按「功能特征 → 模式编号 → 参考页」快速选型,保证 UI 与交互一次做对。
> **视觉权威**:`docs/web-admin-ui-spec-fresh-mint.md`
> **弹窗/列表细则**:`.cursor/rules/web-admin-crud-dialog.mdc`
> **Tag 映射**:`web-admin/src/utils/status-tag-registry.ts` + OpenSpec `ui-conventions` §状态标签注册表
> **OpenSpec**:`openspec/changes/zkxw-engineering-standards/specs/ui-conventions/spec.md` §「界面模式索引与参考页选型」
---
## 一、怎么用(30 秒选型)
```
1. 看下方「功能特征 → 模式」决策表,确定模式编号(如 P01、P12)
2. 打开该模式的「标准写法」+「参考页面」
3. 复制页面骨架,替换 API / 字段 / menuCode
4. 枚举字段进 status-tag-registry.ts
```
**官方 Demo 模板(侧栏 Demo 菜单,永远优先对照):**
| 模式 | Hash | 源码 |
|------|------|------|
| 标准列表 CRUD | `/#/demo/unit` | `web-admin/src/views/system/unit/index.vue` |
| 复杂业务列表 | `/#/demo/order` | `web-admin/src/views/system/order/index.vue` |
| 商品类 + 查看弹窗 | `/#/demo/product` | `web-admin/src/views/system/product/index.vue` |
| 树形主数据 | `/#/demo/category` | `web-admin/src/views/system/category/index.vue` |
| 用户类 CRUD | `/#/demo/user` | `web-admin/src/views/system/user/index.vue` |
| 工作台说明 | `/#/demo/console` | `web-admin/src/views/dashboard/console/index.vue` |
---
## 二、功能特征 → 模式(决策表)
| 你的功能长什么样 | 选模式 | 首选参考 |
|----------------|--------|----------|
| 单表主数据,增删改查 + 分页 + 关键词筛选 | **P01** | `/#/demo/unit` → `basic-info/customer` |
| 列表有多种状态,操作按钮随状态变化 | **P02** | `/#/demo/order` → `cell-storage/protocol-audit` |
| 树形结构,父子级联,无分页 | **P03** | `/#/demo/category` → `system/dept` |
| 左侧组织/分类树 + 右侧分页列表 | **P04** | `/#/demo/user` → `system/user` |
| 同一页上下两块表(类型 + 明细) | **P05** | `system/dict` |
| 主表列表 + 弹窗内维护子表 | **P06** | `basic-info/collection-region` |
| 批量生成编号/编码 + 下发/收回 | **P07** | `basic-info/sample-code` |
| 列表顶部 Tab 按状态切换(非路由 Tab) | **P08** | `cell-storage/payment-info` |
| 只读查看,字段分 Section 展示 | **P09** | `SystemViewDialog` → `system/express` |
| 只读查看,业务字段多、需 Tab/KPI | **P10** | `ProtocolViewDialog` / `DonationViewDialog` |
| 简单审核/状态变更(单表单 560px) | **P11** | `ProtocolAuditDialog` |
| 多分区大表单(Tab 锚点 + 子表行) | **P12** | `ProtocolFormDialog` / `DonationFormDialog` |
| 财务/业务确认(只读明细 + 上传附件) | **P13** | `cell-storage/payment-confirm` |
| 主表 + 嵌套配置大弹窗(子资源 CRUD) | **P14** | `basic-info/insurance-company` |
| 主表 + 多 Tab 维护渠道/协议等子模块 | **P15** | `pilot-service/channel` |
| 三栏:资源库 \| 步骤列表 \| 步骤详情 | **P16** | `production/process-route` |
| 工单列表 + 派发/执行弹窗链 | **P17** | `production/production-work-order` |
| 任务执行(虚拟步骤 + 步骤状态机) | **P18** | `TaskExecutionDialog` + `useTaskStepEditor` |
| 主数据 + append-to-body 选择器弹窗 | **P19** | `production/process` |
| 库存主数据 + 入库/出库 + 流水只读页 | **P20** | `production/consumable` + `cell-storage/material-stock-log` |
| 工单/任务(质检域,配置检测项) | **P21** | `quality-inspection/qc-work-order` |
| 审核列表 + 专用审核弹窗 | **P22** | `quality-inspection/storage-release-review` |
| 接收/登记类(关联协议样本) | **P23** | `quality-inspection/sample-reception` |
| 工作流配置 / 待办 / 审批 | **P24** | `system/workflow/*` |
| 独立详情页(非弹窗) | **P25** | `system/user/detail` |
| 角色/权限扩展(多弹窗:菜单树/数据范围) | **P26** | `system/role` |
| 衍生列表(跳转主业务查看弹窗) | **P27** | `cell-storage/storage-cert` |
---
## 三、模式详解(标准写法 + 参考)
### P01 标准列表 CRUD
**适用**:字典类主数据、配置项、简单业务实体(客户、耗材、站点…)
**页面结构**:
```
page-head → panel → filter-block → list-toolbar → list-table → pagination
+ el-dialog.dialog-form-layout(新增/编辑)
+ SystemViewDialog(查看)
```
**标准写法要点**:
- 工具栏:「已选 N 项」→ 唯一 `type="primary"` 新增 → 批量删除
- 表格:`list-table` + `stripe` + `row-key="id"` + 双击查看
- 弹窗:`label-position="top"`、`form-grid-2`、Close/Check 底栏
- 状态列:`<el-tag size="small">` + `status-tag-registry`
**参考页面**:
| 业务 | Hash | 源码 | 后端 API |
|------|------|------|----------|
| Demo 模板 | `/#/demo/unit` | `views/system/unit/index.vue` | `admin.py` item-units |
| 客户管理 | `/#/basic-info/customer` | `views/basic-info/customer/index.vue` | `basic_info.py` customers |
| 耗材管理 | `/#/production/consumable` | `views/production/consumable/index.vue` | `production.py` consumables |
| 快递公司 | `/#/system/express` | `views/system/express/index.vue` | `admin.py` |
| 洁净室 | `/#/operations/clean-room` | `views/operations/clean-room/index.vue` | `operations.py` |
| 市场物料 | `/#/cell-storage/material` | `views/cell-storage/material/index.vue` | `material.py` |
**前端 API 模式**:`fetchXxxList` / `fetchCreateXxx` / `fetchUpdateXxx` / `fetchDeleteXxx`(`src/api/admin.ts` 或域文件)
---
### P02 复杂业务列表
**适用**:多状态枚举、操作列按钮随状态/角色变化、业务 Tag 丰富
**在 P01 基础上增加**:
- 筛选区含状态/类型下拉
- 操作列多种按钮(查看/编辑/提交/作废…)
- 可能挂多个业务弹窗(审核、状态变更)
**参考页面**:
| 业务 | Hash | 源码 |
|------|------|------|
| Demo 模板 | `/#/demo/order` | `views/system/order/index.vue` |
| 协议单管理 | `/#/cell-storage/protocol-audit` | `views/cell-storage/protocol-audit/index.vue` |
| 捐赠协议管理 | `/#/research-donation/audit` | `views/research-donation/audit/index.vue` |
| 入库生产工单 | `/#/production/production-work-order` | `views/production/production-work-order/index.vue` |
| 入库质检工单 | `/#/quality-inspection/qc-work-order` | `views/quality-inspection/qc-work-order/index.vue` |
| 生产任务 | `/#/production/production-task` | `views/production/production-task/index.vue` |
| 请假申请 | `/#/workflow/leave` | `views/system/leave/index.vue` |
---
### P03 树形主数据
**适用**:组织、菜单、分类等父子层级;整表树展示;软删级联子节点
**标准写法**:
- `el-table` + `:tree-props="{ children: 'children' }"`
- 工具栏:全部展开/折叠
- **无分页**
- 下拉/选中显示本级名;表格/导出显示全路径(`tree-path.ts`,分隔符 ` / `)
**参考页面**:
| 业务 | Hash | 源码 |
|------|------|------|
| Demo 模板 | `/#/demo/category` | `views/system/category/index.vue` |
| 组织管理 | `/#/system/dept` | `views/system/dept/index.vue` |
| 菜单管理 | `/#/system/menu` | `views/system/menu/index.vue` |
---
### P04 左树右表
**适用**:按组织/部门筛选用户或业务数据
**参考**:`/#/demo/user` → `views/system/user/index.vue`
**要点**:左侧 `el-tree` 选组织;右侧标准 P01 列表
**路径展示**:`buildPathLabelMapFromTreeRoots`
---
### P05 主从双表(同页)
**适用**:主实体 + 从实体,选中主表行后在同页下方展示从表
**参考**:`/#/system/dict` → `views/system/dict/index.vue`
**特征**:上下两套 toolbar + table;从表依赖主表选中行
---
### P06 主从弹窗(子表在 Dialog)
**适用**:主表字段少,子表在「配置」弹窗内 CRUD(非树形)
**参考**:`/#/basic-info/collection-region` → `views/basic-info/collection-region/index.vue`
**后端**:主资源 + 嵌套路由 `/{id}/hospitals`
**注意**:不要用树 UI;子表用嵌套 `el-table`
---
### P07 号池 / 批量运维
**适用**:预生成编号/编码、批量下发给用户、批量收回
**参考**:
| 业务 | Hash | 源码 |
|------|------|------|
| 样本编码 | `/#/basic-info/sample-code` | `views/basic-info/sample-code/index.vue` |
| 采集协议号 | `/#/basic-info/collection-protocol-no` | `views/basic-info/collection-protocol-no/index.vue` |
**标准写法**:
- 批量生成弹窗:前缀/中间段/序号范围
- 批量下发:选用户 + `issuedUserId` 校验
- API:`/batch-generate`、`/batch-issue`、`/batch-revoke`;超时 `120_000`
---
### P08 状态 Tab 列表
**适用**:同一业务实体按状态分视图(缴费状态、待办/已办…)
**参考**:`/#/cell-storage/payment-info` → `views/cell-storage/payment-info/index.vue`
**写法**:`region-tabs` 切换 `payStatus` 筛选;每 Tab 可不同批量操作
**类似**:`payment-confirm`(pending/confirmed)、`refund-confirm`
---
### P09 标准查看弹窗(SystemViewDialog)
**适用**:字段 ≤ 20 个、分 1–3 个 Section、无复杂 Tab
**组件**:`web-admin/src/components/business/system-view-dialog/index.vue`
**标准写法**:
```typescript
const viewSections = computed(() => [{
title: '基本信息',
fields: [
{ label: '名称', value: d.name },
{ label: '状态', value: enableStatusLabel(d.status), tagType: enableStatusTagType(d.status) }
]
}])
```
**参考**:`system/express`、`basic-info/customer`、`production/consumable-pack`(查看)
---
### P10 业务专用查看弹窗
**适用**:字段极多、多 Tab、KPI 摘要、审核历史、附件区、跨模块信息卡片
**参考**:
| 业务 | 组件 |
|------|------|
| 采集协议 | `cell-storage/protocol/ProtocolViewDialog.vue` |
| 科研捐赠 | `research-donation/list/DonationViewDialog.vue` |
| 渠道信息 | `pilot-service/channel/ChannelViewDialog.vue` |
| 入库放行 | `quality-inspection/storage-release-review/StorageReleaseViewDialog.vue` |
| 质检任务 | `components/business/qc-task-view-dialog/index.vue` |
**写法**:与编辑弹窗 **同 Tab/section 命名**;只读块复用 `ProtocolAttachmentReadonly` 等
---
### P11 轻量业务弹窗(560px)
**适用**:审核结论、状态变更、单字段确认
**参考**:
- `ProtocolAuditDialog.vue` — 审核通过/退回
- `ProtocolStatusChangeDialog.vue` — 生效/过期/作废/转科研
- `DonationAuditDialog.vue` / `DonationStatusChangeDialog.vue`
---
### P12 重表单弹窗(Tab 分区)
**适用**:主从多表一次保存、样本/当事人/缴费等分区、行内子表
**参考**:
- `cell-storage/protocol/ProtocolFormDialog.vue`(1380px,Sticky Tab)
- `research-donation/list/DonationFormDialog.vue`
**标准写法**:
- `DialogFormBody` + `detail-tabs` + `scrollToSection`
- `form-grid--col4` / `col2`;`scroll-to-error`
- 附件:`upload-card`(140×96)+ `fetchUploadAttachment`
- **独立组件文件**,不要堆在 `index.vue`
---
### P13 财务 / 业务确认弹窗
**适用**:只读业务明细 + 财务填写确认字段 + 附件上传
**参考**:
- `/#/cell-storage/payment-confirm` + `protocol-finance-confirm-fields`
- `/#/cell-storage/refund-confirm`
- 组件:`components/business/protocol-payment-detail-readonly`
- 组件:`components/business/protocol-finance-confirm-fields`
---
### P14 主表 + 嵌套配置大弹窗
**适用**:主实体简单,子资源(险种/开票/价格)在独立大弹窗维护
**参考**:`/#/basic-info/insurance-company` → `views/basic-info/insurance-company/index.vue`
**后端**:`/{id}/project-prices`、`/{id}/invoices`
---
### P15 主表 + 多 Tab 子模块页内/弹窗
**适用**:一个主实体关联多种子业务(开票、地址、协议…)
**参考**:`/#/pilot-service/channel` → `views/pilot-service/channel/index.vue` + `ChannelViewDialog.vue`
**类似**:`pilot-service/checkup-institution`(体检机构 + 套餐面板)
---
### P16 三栏工艺编辑器
**适用**:从资源库拖拽到步骤列表,右侧编辑步骤详情子表
**样式**:`web-admin/src/styles/_route-config.scss`
**布局类**:`.route-config-body` = 左 `.route-config-left` | 中 `.route-config-center` | 右 `.route-config-right`
**参考**:
- 原型(逻辑内联):`production/process-route/index.vue`
- 复用版:`production-work-order/DispatchTaskDialog.vue`(phase=edit)
- 右栏面板:`StepDetailPanel.vue`
---
### P17 工单列表 + 任务弹窗链
**适用**:接收/触发自动生成工单 → 派发任务 → 列表查看任务 → 完成工单
**参考**:`/#/production/production-work-order`
**子组件**:`DispatchTaskDialog`、`EditTaskInfoDialog`、任务列表内嵌 dialog
**后端**:`production-work-order.ts` + `production_task.py`
---
### P18 任务执行(Composable 驱动)
**适用**:步骤状态机、虚拟步骤(原材料/产出)、执行态只读/编辑切换
**参考**:
- `TaskExecutionDialog.vue`
- `useTaskStepEditor.ts`(核心 composable)
- `TaskInputEnhancedTable.vue`、`TaskOutputList.vue`
**质检类似**:`/#/quality-inspection/qc-task`(配置+执行,无三栏拖拽)
---
### P19 主数据 + 选择器子弹窗
**适用**:编辑主实体时从另一张表多选关联(试剂、耗材、产出物)
**参考**:`/#/production/process` → `process/index.vue`
**写法**:主弹窗 1200px + `append-to-body` 选择弹窗 1000px
**类似**:`consumable-pack/index.vue`、`cell-product/index.vue`
---
### P20 库存 + 流水
**适用**:主数据 CRUD + 入库/出库 + 独立流水只读列表页
**参考**:
- 主数据+出入库:`/#/production/consumable`
- 流水只读:`/#/cell-storage/material-stock-log`、`/#/quality-inspection/qc-material-usage`
---
### P21 质检工单 / 任务
**适用**:样本接收后自动生成工单,配置检测项,执行任务
**参考**:
- 工单:`/#/quality-inspection/qc-work-order`
- 任务:`/#/quality-inspection/qc-task`
- API:`qc-work-order.ts`、`qc-task.ts`
---
### P22 审核列表 + 专用审核弹窗
**适用**:待审核列表,打开专用 Dialog 填写结论
**参考**:`/#/quality-inspection/storage-release-review`
**组件**:`StorageReleaseReviewDialog.vue`、`StorageReleaseViewDialog.vue`
---
### P23 接收 / 登记
**适用**:关联协议/样本编码,填写接收结论,触发下游工单
**参考**:`/#/quality-inspection/sample-reception`
**跨表键**:`tenant_no` + `sample_code`(不用 protocol_sample_id)
---
### P24 工作流
**适用**:流程配置、待办、已办、我的申请、业务表单驱动审批
**参考**:
- 流程配置:`/#/workflow/process` + `FlowDesigner.vue`
- 待办/已办:`task-pending`、`task-completed` + `ApprovalDialog`
- API:`src/api/workflow.ts`、`src/api/leave.ts`
---
### P25 独立详情页
**适用**:信息量大、需独立 URL、非弹窗场景
**参考**:`/#/system/user/detail` → `views/system/user/detail.vue`(`isHide: true` 路由)
---
### P26 权限扩展 CRUD
**适用**:除 CRUD 外还有菜单树勾选、数据范围配置
**参考**:`/#/system/role` → `views/system/role/index.vue`
**额外弹窗**:菜单配置 `el-tree`、数据权限选部门/用户
---
### P27 衍生列表(跳转主业务查看)
**适用**:从主业务派生的列表页,查看时打开主业务 ViewDialog
**参考**:
- `/#/cell-storage/storage-cert` → `ProtocolViewDialog`(`show-storage-cert`)
- `/#/cell-storage/fullmoon-todo` → `ProtocolViewDialog`(`show-fullmoon-insurance`)
---
## 四、全站页面 → 模式速查
| 页面 | 模式 |
|------|------|
| demo/unit, tenant, site, post, express, customer, cell-sample-type, consumable, reagent, process-category, output-type, qc-material, lab-test-item, third-party-company, material, clean-room, storage-facility, pilot-service/*-type/spec | P01 |
| demo/order, protocol-audit, donation/audit, production-work-order, qc-work-order, production-task, leave, exhibition-appointment, infusion-schedule-management | P02 |
| demo/category, dept, menu | P03 |
| demo/user, user | P04 |
| dict | P05 |
| collection-region | P06 |
| sample-code, collection-protocol-no | P07 |
| payment-info, payment-confirm, refund-confirm | P08 |
| 多数页的查看 | P09 |
| protocol/ProtocolViewDialog, DonationViewDialog, ChannelViewDialog, StorageReleaseViewDialog | P10 |
| ProtocolAuditDialog, ProtocolStatusChangeDialog, DonationAuditDialog | P11 |
| ProtocolFormDialog, DonationFormDialog | P12 |
| payment-confirm, refund-confirm | P13 |
| insurance-company | P14 |
| channel, checkup-institution | P15 |
| process-route, DispatchTaskDialog(edit) | P16 |
| production-work-order | P17 |
| TaskExecutionDialog, qc-task(执行) | P18 |
| process, consumable-pack, cell-product, sop | P19 |
| consumable + material-stock-log / qc-material-usage | P20 |
| qc-work-order, qc-task | P21 |
| storage-release-review | P22 |
| sample-reception | P23 |
| workflow/* | P24 |
| user/detail | P25 |
| role | P26 |
| storage-cert, fullmoon-todo | P27 |
| protocol(录入) | P01 + P12 |
| demo/product | P01 + 专用 product-view-dialog |
---
## 五、标准写法 Checklist(所有模式通用)
### 页面骨架
- [ ] `page-container` → `page-head` → `section.panel`
- [ ] 单 `panel-top` 标题;筛选区无重复标题
- [ ] 工具栏「已选 N 项」在最前;仅一个主色实心按钮
- [ ] `list-table` + `stripe`;操作列 `fixed="right"` min-width ≥ 260
### 弹窗
- [ ] `dialog-form-layout` + `align-center` + `label-position="top"`
- [ ] 长表单 `scroll-to-error`;底栏 Close/Check 图标间距 6px
- [ ] 无 backdrop blur
### Tag / 枚举
- [ ] 先注册 `status-tag-registry.ts`
- [ ] 表格 + SystemViewDialog 的 `tagType` 均用 registry getter
### 前后端衔接
- [ ] `sqxp.ts` 添加路由 + `menuCode`
- [ ] 后端 `require_menu_code`(GET)/ `require_admin_or_super_admin`(写)
- [ ] API 函数 + `api.d.ts` 类型
- [ ] crud `_row_to_dict` camelCase;软删 `del_flag`
---
## 六、选型流程图
```mermaid
flowchart TD
A[新功能需求] --> B{是否树形主数据?}
B -->|是| P03[P03 树表 / P04 左树右表]
B -->|否| C{是否多 Tab 大表单?}
C -->|是| P12[P12 重表单 / P10 查看]
C -->|否| D{是否工单/任务流?}
D -->|是| P17[P17/P18 工单任务]
D -->|否| E{是否有子表/号池/审核?}
E -->|号池| P07
E -->|子表弹窗| P06/P14/P15
E -->|状态 Tab| P08
E -->|审核| P11/P22
E -->|三栏编辑| P16
E -->|否| F{操作是否随状态变化?}
F -->|是| P02
F -->|否| P01
```
---
## 七、维护说明
- **新增页面后**:在本文件 §四 补充「页面 → 模式」映射
- **新增模式后**:在 §二决策表 + §三详解 补充,并同步更新 OpenSpec `ui-conventions/spec.md`「界面模式索引与参考页选型」Requirement
- **Cursor / AI 检索关键词**:界面模式、UI pattern、参考页、模板页、P01、标准列表