/** * 共享的预测单操作按钮可见性逻辑 * 3 角色 × 9 状态矩阵,detailStore 和 ActionButtons 组件共同消费 */ export type Role = 'salesman' | 'planner' | 'manager' /** 所有可能的操作 key */ export type ActionKey = | 'detail' | 'edit' | 'submit' | 'delete' | 'discard' | 'withdraw' | 'resubmit' | 'change' | 'convert' | 'review' | 'approve-change' export interface ActionOptions { /** 是否已有单号(草稿有单号→作废,无单号→删除) */ hasForecastOrderNo?: boolean /** 是否存在未完成的变更单 */ hasPendingChange?: boolean /** 是否在详情视图(详情页不需要 'detail' 操作) */ isDetailView?: boolean } /** * 根据状态和角色返回可用的操作 key 列表 */ export function getAvailableActions( status: string, role: Role, options: ActionOptions = {}, ): ActionKey[] { const { hasForecastOrderNo = false, hasPendingChange = false, isDetailView = false, } = options const actions: ActionKey[] = [] // 所有角色、所有状态都可以查看详情(详情视图下不添加) if (!isDetailView) { actions.push('detail') } // ============================================================ // 业务员 (salesman) // ============================================================ if (role === 'salesman') { switch (status) { case 'DRAFT': actions.push('edit') // 详情视图不显示「提交」—— 提交应走编辑→表单→提交流程 if (!isDetailView) { actions.push('submit') } if (hasForecastOrderNo) { actions.push('discard') } else { actions.push('delete') } break case 'SUBMITTED': actions.push('withdraw') break case 'REJECTED': actions.push('resubmit', 'discard') break case 'PLAN_RECEIVED': case 'SCHEDULED': case 'PARTIAL_CONVERTED': // 存在未完成变更单时,不显示「发起变更」 if (!hasPendingChange) { actions.push('change') } break default: // FULL_CONVERTED, RELEASED, DISCARDED — 仅详情 break } // SCHEDULED / PARTIAL_CONVERTED 额外显示转订单 if (status === 'SCHEDULED' || status === 'PARTIAL_CONVERTED') { actions.push('convert') } } // ============================================================ // 计划员 (planner) // ============================================================ else if (role === 'planner') { if (status === 'SUBMITTED') { actions.push('review') } } // ============================================================ // 销售经理 (manager) // ============================================================ else if (role === 'manager') { if (hasPendingChange) { actions.push('approve-change') } } return actions }