diff --git a/docs/superpowers/specs/2026-10-16-oa-done-bank-receipt-upload-demo.html b/docs/superpowers/specs/2026-10-16-oa-done-bank-receipt-upload-demo.html
new file mode 100644
index 00000000..dc630444
--- /dev/null
+++ b/docs/superpowers/specs/2026-10-16-oa-done-bank-receipt-upload-demo.html
@@ -0,0 +1,664 @@
+
+
+
+
+
+ 已办中心 · 银行回执单上传 Demo
+
+
+
+
+
已办中心
+ Demo · 点击操作列「上传回执」打开弹窗
+
+
+
+
+
+
+ | 序号 |
+ 流程名称 |
+ 申请人 |
+ 申请时间 |
+ 当前节点 |
+ 流程状态 |
+ 操作 |
+
+
+
+
+ | 1 |
+ 费用报销申请 |
+ 张三 |
+ 2026-10-12 14:22 |
+ — |
+ 已完成 |
+
+
+
+
+
+
+ |
+
+
+ | 2 |
+ 付款申请单 |
+ 李四 |
+ 2026-10-10 09:05 |
+ 财务复核 |
+ 进行中 |
+
+
+
+
+
+
+ |
+
+
+
+
+
+
+ 交互说明:
+ 操作列新增「上传回执」→ 弹窗回显该审批实例已上传的银行回执单(多张)→
+ 左侧上传卡片可继续追加 → 支持预览/下载/删除 → 点「确定」保存。
+ 本 Demo 为前端示意,文件不会真正上传到服务器。
+
+
+
+
+
+
+
+
+
银行回执单
+
+
+
支持拖拽或点击上传图片、PDF 等文件,单文件不超过 20MB;可上传多张回执单
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/docs/superpowers/specs/2026-10-16-oa-done-bank-receipt-upload-design.md b/docs/superpowers/specs/2026-10-16-oa-done-bank-receipt-upload-design.md
new file mode 100644
index 00000000..cdb79cec
--- /dev/null
+++ b/docs/superpowers/specs/2026-10-16-oa-done-bank-receipt-upload-design.md
@@ -0,0 +1,190 @@
+# OA 已办中心 · 上传银行回执单
+
+**模块**: OA 审批 · 已办中心
+**日期**: 2026-10-16
+**状态**: 待实现
+**UI Demo**: `docs/superpowers/specs/2026-10-16-oa-done-bank-receipt-upload-demo.html`
+**决策记录**:
+- 实现方案: **方案 A**(`biz_attachment` 挂实例,不改 `oa_instance` 表)
+- 入口仅 `web-admin`【已办中心】;有独立权限才显示按钮
+- 弹窗回显历史多张回执,支持追加、下载、删除;确定时整体覆盖保存
+- 全部已办行均可操作(不按流程类型过滤)
+
+---
+
+## 1. 背景与目标
+
+财务/经办人在审批办结后,需要为流程实例补传银行回执单(可多张)。入口放在【已办中心】操作列,通过弹窗管理该实例的回执附件。
+
+**成功标准**:
+- 拥有权限的用户在已办列表看到「上传回执」,打开弹窗可回显历史并继续上传
+- 无权限用户看不到按钮,且接口拒绝
+- 附件交互与展示对齐 web-admin 附件卡片化规范(Fresh Mint)
+
+---
+
+## 2. 范围
+
+### 2.1 在范围内
+
+| 项 | 说明 |
+|----|------|
+| 入口 | `web-admin/src/views/oa-approval/done/index.vue` 操作列 |
+| 弹窗 | 新组件(建议 `OaBankReceiptDialog.vue`) |
+| 存储 | `biz_attachment`:`business_type=oa_bank_receipt`,`business_id=instance_id` |
+| 上传 | 现有 `fetchUploadAttachment`,`folder=oa-bank-receipt` |
+| API | `GET` / `PUT` `.../instances/{instance_id}/bank-receipts` |
+| 权限 | 按钮级菜单 `perms=oa:done:bank-receipt` + SQL 种子 |
+
+### 2.2 非目标
+
+- 小程序 / H5 已办中心
+- 审批详情页内展示回执
+- 打印 PDF 嵌入回执
+- 按流程类型隐藏按钮
+- 删除时物理删除 MinIO 对象(仅软删 `biz_attachment`)
+- 修改 `oa_instance` 表结构
+
+---
+
+## 3. 交互
+
+1. 操作列在「查看 / 打印」旁增加「上传回执」(图标 + 文案;有权限才渲染)。
+2. 点击打开弹窗(`dialog-form-layout`,无 backdrop blur):
+ - 只读摘要:流程名称、申请人、申请时间、已上传张数
+ - 「银行回执单」附件区:上传卡片在首 + 历史附件卡片;支持拖拽;预览 / 下载 / 删除
+3. 打开时 `GET` 拉取历史;选文件后立即上传 MinIO;点「确定」时 `PUT` 整体覆盖保存。
+4. 取消 / 关闭不提交关联变更(已上传到 MinIO 但未 PUT 的孤儿文件可接受,与现有附件习惯一致)。
+
+UI 布局以 Demo 为准。
+
+---
+
+## 4. 权限模型
+
+| 角色/权限 | 「上传回执」按钮 | GET/PUT |
+|-----------|------------------|---------|
+| 能进已办中心、无 `oa:done:bank-receipt` | 不显示 | 403 |
+| 拥有 `oa:done:bank-receipt` | 显示 | 允许(同租户实例) |
+| 超级管理员 / `menuPermAll` | 显示 | 允许 |
+
+- 权限字符:`oa:done:bank-receipt`
+- 菜单名:已办中心-上传银行回执
+- 挂载:`sys_menu` 按钮级节点(`menu_type=F`),父级为「已办中心」菜单
+- 前端:`useMenuPerm().hasMenuPerm('oa:done:bank-receipt')` 控制按钮显隐
+- 后端:`user_has_menu_perm` **强制**校验;禁止仅靠前端隐藏
+
+---
+
+## 5. 数据与 API
+
+### 5.1 存储
+
+| 字段 | 值 |
+|------|-----|
+| `business_type` | `oa_bank_receipt` |
+| `business_id` | OA 实例 `id`(`instance_id`) |
+| 其它 | 沿用 `biz_attachment` 公共字段;删除 = `del_flag=1` |
+
+不新增业务表,不改 `oa_instance`。
+
+### 5.2 端点
+
+```
+GET /web/admin/oa-approval/instances/{instance_id}/bank-receipts
+PUT /web/admin/oa-approval/instances/{instance_id}/bank-receipts
+```
+
+鉴权:管理端登录 + `oa:done:bank-receipt`;实例须存在且 `tenant_no` 与当前用户一致。
+
+**GET 响应**
+
+```json
+{
+ "items": [
+ {
+ "id": "...",
+ "fileName": "电子回单.pdf",
+ "fileUrl": "oa-bank-receipt/...",
+ "fileType": "application/pdf",
+ "fileSize": 120849,
+ "createTime": "2026-10-16 12:00:00"
+ }
+ ]
+}
+```
+
+排序:`create_time ASC`(稳定回显顺序)。
+
+**PUT body**
+
+```json
+{
+ "items": [
+ {
+ "fileUrl": "oa-bank-receipt/...",
+ "fileName": "电子回单.pdf",
+ "fileType": "application/pdf",
+ "fileSize": 120849
+ }
+ ]
+}
+```
+
+语义:**整体覆盖**——以 body 中的 `fileUrl` 集合为准:
+- 已有且仍在集合中:保留(可更新文件名等展示字段)
+- 集合中新增:创建或绑定 `biz_attachment` 行(`business_type` / `business_id`)
+- 库中已有但不在集合中:软删
+
+允许 `items: []`(清空该实例全部银行回执关联)。
+
+文件二进制上传仍走通用附件上传接口,本 PUT 只维护业务关联。
+
+### 5.3 实例可见性
+
+已办列表本身仅含当前用户办过的任务。本接口在有权限前提下,对**同租户且存在的实例**允许读写回执;不额外校验「当前用户必须是该实例办理人」(避免权限角色无法代传)。若产品后续要求收紧,可再加办理人校验。
+
+---
+
+## 6. 前端实现要点
+
+| 文件 | 职责 |
+|------|------|
+| `done/index.vue` | 操作列按钮 + 打开弹窗;`hasMenuPerm` |
+| `OaBankReceiptDialog.vue`(建议路径 `components/oa-approval/`) | GET 回显、卡片上传、PUT 保存 |
+| `api/oaApproval.ts` | 封装 GET/PUT |
+| `docs/sql/migrations/...` | 按钮菜单种子 |
+
+附件卡片:对齐 `ProtocolFormDialog`「协议附件」与 OpenSpec ui-conventions「附件上传卡片化布局」;单文件 ≤ 20MB;上传中禁止确定。
+
+操作列 `min-width` 在现有基础上加宽,避免按钮被裁切。
+
+---
+
+## 7. 错误处理与边界
+
+| 场景 | 行为 |
+|------|------|
+| 无权限 | 按钮隐藏;API 403 |
+| 实例不存在 / 跨租户 | 400/404,不泄露他租户 |
+| 上传中点确定 | 提示「附件上传中,请稍候」 |
+| 单文件超 20MB | 前端拦截 |
+| PUT 空列表 | 软删全部关联 |
+| 并发保存 | 后写覆盖先写;不做乐观锁 |
+| MinIO 上传失败 | 移除占位项并提示 |
+
+---
+
+## 8. 验收
+
+1. 无 `oa:done:bank-receipt`:看不到按钮;直接调 GET/PUT 被拒。
+2. 有权限:打开可见历史;追加 / 下载 / 删除后确定;再次打开与保存一致。
+3. UI 符合附件卡片规范与 Demo。
+4. 种子 SQL 可执行;角色勾选后刷新菜单权限码即可赋权,无需改代码。
+
+---
+
+## 9. 测试建议
+
+- 后端:无权限 403;有权限 GET 空/非空;PUT 增删改覆盖;跨租户隔离。
+- 前端:权限显隐;上传中拦截;确定后列表与 GET 一致(可用组件/接口 mock)。