2026-08-04-oa-assignee-posts-replace-roles-design.md 4.7 KB

OA 审批人选:工作流角色 → 职位(硬切换)

日期: 2026-08-04
范围: 去掉 oa_role / oa_role_user 与【工作流角色】模块;流程审批人/抄送改为选【职位】,运行时按 sys_user_post 展开成员。
方案: 方案 1 — assigneeType: "posts" + postIds

已确认决策

项 结论
历史流程 系统未上线,无历史 flow_tree → 硬切换,不做兼容层
预置 GM/CHAIRMAN 不做;设计器普通多选启用职位
下线范围 彻底去掉:菜单/路由/管理页/API/fetchOaRole*
数据表 一并 DROP oa_role_user、oa_role(增量 SQL)
审批人数据源 仅 sys_user_post(职位成员);禁止用 sys_post_role / sys_role

目标模型

流程节点 approverConfig
  assigneeType / assigneeTypes: "posts"
  postIds: [sys_post.id, ...]
        │
        ▼
sys_user_post(启用职位 + 启用用户)
        │
        ▼
待办 / 抄送人 userId 列表

与权限链分离:

职位 → sys_post_role → sys_role → 菜单/数据权限   (登录 RBAC,本需求不改)
职位 → sys_user_post → 用户                     (本需求:审批人选)

Flow JSON(新约定)

审批节点示例:

{
  "assigneeType": "posts",
  "postIds": ["<sys_post.id>"],
  "signMode": "or"
}

抄送节点:assigneeTypes 可含 "posts"(与 users / dept_leader 等组合),成员来自同一套 postIds(或按现抄送结构对每种类型分字段;实现时与现 oa_roles 写法一一对应替换)。

删除字段/枚举: oa_roles、oaRoleIds、oaRoleCodes、oa_role_ids、oa_role_codes。

后端

新增/改造

位置 变更
crud/user.py 或 crud/post.py list_user_ids_bound_to_posts(db, post_ids, tenant_no):多职位展开用户,过滤职位 status=1/del_flag=0、用户启用
oa_assignee.py assigneeType == "posts" 分支;resolve_source: "posts";删除 oa_roles 分支
oa_publish.py 校验 posts 时 postIds 非空;引用校验查 SysPost;删除 validate_oa_roles_referenced
oa_engine.py 展示标签改职位名称映射;删除 OaRole 查询
oa_approval.py API 删除整个工作流角色路由段
crud/oa_approval.py 删除 PRESET_ROLES / ensure_presets / 角色 CRUD / list_oa_role_user_ids
models.py 删除 OaRole、OaRoleUser(与 drop SQL 同步)

SQL

创建 docs/sql/drop_oa_role.sql:

DROP TABLE IF EXISTS `oa_role_user`;
DROP TABLE IF EXISTS `oa_role`;

菜单:软删或删除「工作流角色」菜单项(oa:roles:list),与项目菜单维护方式一致。

错误语义

  • 发布:未选职位 / 职位不存在或停用 → 明确错误
  • 运行:职位下无有效用户 → 与现「工作流角色成员为空」同等失败(AssigneeResolveError)

前端

位置 变更
FlowDesigner.vue 选项「工作流角色」→「职位」;fetchPostList 加载(仅 status==='1');postIds 多选
flow-tree/types.ts AssigneeType 含 posts;去掉 oa_roles;summarizeApprover 文案「职位」
OaProgressChain.vue posts →「职位」
删除 views/oa-approval/roles/index.vue;路由 oa-approval/roles;oaApproval.ts 中全部 fetchOaRole*
保留 OaPostSelect.vue(表单控件,与审批人选独立)

文档与测试

  • 更新钉钉式 OA 设计文档中「工作流角色」章节为「职位」
  • 需求/OpenSpec 若提及 OA 独立角色作审批人,改为职位
  • 单测:test_oa_assignee.py 改为 posts;去掉「不读 sys_role」之外的 oa_role mocks;test_oa_publish.py 同步
  • ./scripts/update-graph.sh backend(及 frontend)

非目标

  • 职位权限(sys_post_role)行为不变
  • 不种子 GM/CHAIRMAN 职位
  • 不做旧 JSON 兼容读取
  • 不改审批人其它类型:users / dept_leader / direct_supervisor / initiator_select

实现顺序(建议)

  1. 后端:list_user_ids_bound_to_posts + assignee/publish/engine 改 posts
  2. 前端:FlowDesigner + types + 进度文案
  3. 删除角色模块(页/路由/API/CRUD/模型)
  4. drop SQL + 菜单清理 + 文档/单测
  5. 图谱更新

验收

  1. OA 菜单无「工作流角色」
  2. 流程设计审批/抄送可选职位并保存 posts/postIds
  3. 职位已关联用户时,发起后待办落到这些用户
  4. 空成员职位无法正常完成解析(错误可读)
  5. 代码库无 oa_roles / fetchOaRole / OaRole 残留(除历史设计文档归档说明外)