fix:填写人功能

This commit is contained in:
大黑 2025-12-23 14:05:23 +08:00
parent 0b25c98276
commit df23f924e0
11 changed files with 1916 additions and 2435 deletions

Binary file not shown.

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View File

@ -20,10 +20,16 @@
<div class="header-right">
<el-button
v-if="flowStatus === 'APPROVING'"
type="primary"
@click="handleApprove"
@click="handleReject"
>
审批
退回
</el-button>
<el-button
v-if="flowStatus === 'APPROVING'"
type="primary"
@click="handleSubmit"
>
提交
</el-button>
</div>
</div>
@ -156,30 +162,23 @@
<!-- 审批弹窗 -->
<el-dialog
title="审核"
:title="approvalDialogTitle"
:visible.sync="approvalDialogVisible"
width="500px"
:close-on-click-modal="false"
append-to-body
@close="handleApprovalDialogClose"
>
<el-form ref="approvalForm" :model="approvalFormData" label-width="80px">
<el-form-item label="审核">
<el-radio-group v-model="approvalFormData.result">
<el-radio label="PASS">
通过
</el-radio>
<el-radio label="REJECT">
退回
</el-radio>
</el-radio-group>
</el-form-item>
<el-form-item label="备注">
<el-form ref="approvalForm" :model="approvalFormData" :rules="approvalFormRules" label-width="80px">
<el-form-item
:label="approvalActionType === 'reject' ? '退回意见:' : '提交意见:'"
prop="opinion"
>
<el-input
v-model="approvalFormData.opinion"
type="textarea"
:rows="4"
placeholder="请输入备注"
:placeholder="approvalActionType === 'reject' ? '请输入退回意见' : '请输入提交意见'"
/>
</el-form-item>
</el-form>
@ -221,11 +220,18 @@ export default {
changeTablePageNumber: 1,
changeTablePageSize: 10,
approvalDialogVisible: false,
approvalActionType: '', // 'reject' 'submit'
approvalDialogTitle: '审核',
approvalFormData: {
result: '',
opinion: ''
},
approvalSubmitting: false
approvalSubmitting: false,
approvalFormRules: {
opinion: [
{ required: true, message: '请输入意见', trigger: 'blur' }
]
}
}
},
computed: {
@ -543,9 +549,26 @@ export default {
return formattedStep
})
},
handleApprove() {
handleReject() {
this.approvalActionType = 'reject'
this.approvalDialogTitle = '退回'
this.approvalFormData = {
result: '',
result: 'REJECT',
opinion: ''
}
this.approvalDialogVisible = true
//
this.$nextTick(() => {
if (this.$refs.approvalForm) {
this.$refs.approvalForm.clearValidate()
}
})
},
handleSubmit() {
this.approvalActionType = 'submit'
this.approvalDialogTitle = '提交'
this.approvalFormData = {
result: 'PASS',
opinion: ''
}
this.approvalDialogVisible = true
@ -558,6 +581,8 @@ export default {
},
handleApprovalDialogClose() {
this.approvalDialogVisible = false
this.approvalActionType = ''
this.approvalDialogTitle = '审核'
this.approvalFormData = {
result: '',
opinion: ''
@ -568,49 +593,50 @@ export default {
}
},
handleApprovalSubmit() {
//
if (!this.approvalFormData.result) {
this.$message.warning('请选择审核结果(通过或退回)')
return
}
//
this.$refs.approvalForm.validate((valid) => {
if (!valid) {
return false
}
if (!this.detail || !this.detail.flowId) {
this.$message.error('缺少审批信息')
return
}
if (!this.detail || !this.detail.flowId) {
this.$message.error('缺少审批信息')
return
}
//
const submitData = {
flowId: this.detail.flowId,
userId: getUserId(),
result: this.approvalFormData.result, // 'PASS' 'REJECT'
opinion: this.approvalFormData.opinion || ''
}
//
const submitData = {
flowId: this.detail.flowId,
userId: getUserId(),
result: this.approvalFormData.result, // 'PASS' 'REJECT'
opinion: this.approvalFormData.opinion || ''
}
this.approvalSubmitting = true
const request = {
...api.HANDLE_APPROVAL,
params: submitData
}
this.approvalSubmitting = true
const request = {
...api.HANDLE_APPROVAL,
params: submitData
}
this.$request(request)
.asyncThen((resp) => {
this.handleApprovalDialogClose()
//
this.getApprovalSpet()
this.getApprovalChange()
//
this.$emit('refresh')
this.approvalSubmitting = false
})
.asyncErrorCatch((err) => {
console.error('审批提交失败:', err)
this.$message.error('审批提交失败,请重试')
this.approvalSubmitting = false
})
.finally(() => {
this.approvalSubmitting = false
})
this.$request(request)
.asyncThen((resp) => {
this.handleApprovalDialogClose()
//
this.getApprovalSpet()
this.getApprovalChange()
//
this.$emit('refresh')
this.approvalSubmitting = false
})
.asyncErrorCatch((err) => {
console.error('审批提交失败:', err)
this.$message.error('审批提交失败,请重试')
this.approvalSubmitting = false
})
.finally(() => {
this.approvalSubmitting = false
})
})
}
}
}

View File

@ -51,13 +51,13 @@
/>
</el-select>
</el-form-item>
<el-form-item v-if="dispatchType !== 'update_param'" label="部门:" prop="department">
<el-form-item label="部门:" prop="department">
<el-select
v-model="formData.department"
placeholder="请选择部门"
clearable
style="width: 100%"
:disabled="!formData.subsystem"
:disabled="dispatchType === 'update_param' ? (!formData.subsystem || !formData.partsName) : !formData.subsystem"
@change="handleDepartmentChange"
>
<el-option
@ -77,22 +77,13 @@
style="width: 100%"
/>
</el-form-item>
<el-form-item v-if="dispatchType === 'update_param'" label="现填写人:">
<el-input
v-model="formData.currentFillerName"
disabled
placeholder="暂无填写人"
readonly
style="width: 100%"
/>
</el-form-item>
<el-form-item :label="dispatchType === 'update_param' ? '填写人:' : '责任人:'" prop="userId">
<el-form-item :label="dispatchType === 'update_param' ? '人员:' : '责任人:'" prop="userId">
<el-select
v-model="formData.userId"
:placeholder="dispatchType === 'update_param' ? '请输入填写人姓名进行搜索' : '请输入责任人姓名进行搜索'"
:placeholder="dispatchType === 'update_param' ? '请输入人员姓名进行搜索' : '请输入责任人姓名进行搜索'"
style="width: 100%"
clearable
:disabled="dispatchType === 'update_param' ? !formData.partsName : !formData.department"
:disabled="!formData.department"
filterable
remote
reserve-keyword
@ -190,19 +181,18 @@ export default {
{ required: true, message: '请选择子系统', trigger: 'change' }
],
userId: [
{ required: true, message: this.dispatchType === 'update_param' ? '请选择填写人' : '请选择责任人', trigger: 'change' }
{ required: true, message: this.dispatchType === 'update_param' ? '请选择' : '请选择责任人', trigger: 'change' }
]
}
//
rules.department = [
{ required: true, message: '请选择部门', trigger: 'change' }
]
//
if (this.dispatchType === 'update_param') {
rules.partsName = [
{ required: true, message: '请选择零部件名称', trigger: 'change' }
]
} else {
//
rules.department = [
{ required: true, message: '请选择部门', trigger: 'change' }
]
}
return rules
}
@ -355,8 +345,8 @@ export default {
partsNameSet.add(paramPartsName)
}
}
//
if (this.dispatchType !== 'update_param' && param.department) {
//
if (param.department) {
departmentSet.add(param.department)
}
}
@ -371,11 +361,10 @@ export default {
partsNamesArray.unshift('/')
}
this.availablePartsNames = partsNamesArray
}
//
if (this.dispatchType !== 'update_param') {
//
//
this.availableDepartments = []
} else {
//
this.availableDepartments = Array.from(departmentSet).map((dept) => ({
department: dept
}))
@ -387,32 +376,29 @@ export default {
},
//
handlePartsNameChange(partsName) {
//
//
this.formData.department = ''
this.formData.currentFillerId = ''
this.formData.currentFillerName = ''
this.formData.userId = ''
this.formData.userNumber = ''
this.formData.username = ''
this.availableDepartments = []
this.userOptions = []
//
//
if (partsName && this.formData.subsystem) {
this.findCurrentFiller()
} else {
this.formData.currentFillerId = ''
this.formData.currentFillerName = ''
this.filterDepartmentsByPartsName()
}
},
//
findCurrentFiller() {
//
filterDepartmentsByPartsName() {
if (!this.formData.subsystem || !this.formData.partsName) {
this.formData.currentFillerId = ''
this.formData.currentFillerName = ''
this.availableDepartments = []
return
}
// versionData
const currentVersionData = this.versionData[this.currentVersionId] || {}
let foundFiller = null
const departmentSet = new Set()
// partsName
Object.keys(currentVersionData).forEach((dataPartsName) => {
@ -424,36 +410,17 @@ export default {
if (
param.subsystemName === this.formData.subsystem &&
paramPartsName === this.formData.partsName &&
param.filledByUserId
param.department
) {
// 使
if (!foundFiller) {
foundFiller = {
userId: param.filledByUserId,
username: param.filledBy || ''
}
}
departmentSet.add(param.department)
}
})
})
if (foundFiller) {
// fillerPersons
const fillerPerson = this.fillerPersons.find(
(p) => p.userId === foundFiller.userId || p.id === foundFiller.userId
)
if (fillerPerson) {
this.formData.currentFillerId = fillerPerson.userId || fillerPerson.id || ''
this.formData.currentFillerName = fillerPerson.userName || foundFiller.username || ''
} else {
this.formData.currentFillerId = foundFiller.userId || ''
this.formData.currentFillerName = foundFiller.username || ''
}
} else {
//
this.formData.currentFillerId = ''
this.formData.currentFillerName = ''
}
//
this.availableDepartments = Array.from(departmentSet).map((dept) => ({
department: dept
}))
},
//
handleDepartmentChange(department) {
@ -494,18 +461,10 @@ export default {
},
// /
handleRemoteSearch(query) {
//
if (this.dispatchType === 'update_param') {
if (!this.formData.partsName) {
this.userOptions = []
return
}
} else {
//
if (!this.formData.department) {
this.userOptions = []
return
}
//
if (!this.formData.department) {
this.userOptions = []
return
}
if (!query || query.trim() === '') {
if (this.formData.userId) {
@ -609,7 +568,7 @@ export default {
return
}
if (!this.formData.userId) {
const fieldName = this.dispatchType === 'update_param' ? '填写人' : '责任人'
const fieldName = this.dispatchType === 'update_param' ? '' : '责任人'
this.$message.warning(`请选择${fieldName}`)
return
}
@ -626,6 +585,7 @@ export default {
const confirmData = {
subsystem: this.formData.subsystem,
partsName: this.formData.partsName,
department: this.formData.department,
userId: this.formData.userId, // userId
userNumber: this.formData.userNumber || this.formData.userId, // userNumber使 userId
username: this.formData.username || ''

View File

@ -19,8 +19,11 @@
</div>
</div>
<div class="header-right">
<el-button type="primary" size="small" @click="handleApprove">
审批
<el-button size="small" @click="handleReject">
退回
</el-button>
<el-button type="primary" size="small" @click="handleSubmit">
提交
</el-button>
</div>
</div>
@ -137,7 +140,7 @@
<!-- 审批弹窗 -->
<el-dialog
title="审批"
:title="approvalDialogTitle"
:visible.sync="approvalDialogVisible"
width="500px"
:close-on-click-modal="false"
@ -150,22 +153,15 @@
:rules="approvalFormRules"
label-width="80px"
>
<el-form-item label="审批结果" prop="operator">
<el-radio-group v-model="approvalFormData.operator">
<el-radio label="同意">
同意
</el-radio>
<el-radio label="拒绝">
拒绝
</el-radio>
</el-radio-group>
</el-form-item>
<el-form-item label="说明" prop="comment">
<el-form-item
:label="approvalActionType === 'reject' ? '退回意见:' : '提交意见:'"
prop="comment"
>
<el-input
v-model="approvalFormData.comment"
type="textarea"
:rows="4"
placeholder="请输入审批说明"
:placeholder="approvalActionType === 'reject' ? '请输入退回意见' : '请输入提交意见'"
/>
</el-form-item>
</el-form>
@ -214,6 +210,8 @@ export default {
changeTablePageSize: 10,
activitiRecordDTOS: [], //
approvalDialogVisible: false,
approvalActionType: '', // 'reject' 'submit'
approvalDialogTitle: '审批',
approvalFormData: {
operator: '同意',
comment: ''
@ -329,8 +327,7 @@ export default {
},
approvalFormRules() {
return {
operator: [{ required: true, message: '请选择审批结果', trigger: 'change' }],
comment: [{ required: true, message: '请输入审批说明', trigger: 'blur' }]
comment: [{ required: true, message: '请输入意见', trigger: 'blur' }]
}
}
},
@ -572,8 +569,24 @@ export default {
handleBack() {
this.$emit('close')
},
handleApprove() {
//
handleReject() {
this.approvalActionType = 'reject'
this.approvalDialogTitle = '退回'
this.approvalFormData = {
operator: '拒绝',
comment: ''
}
this.approvalDialogVisible = true
//
this.$nextTick(() => {
if (this.$refs.approvalForm) {
this.$refs.approvalForm.clearValidate()
}
})
},
handleSubmit() {
this.approvalActionType = 'submit'
this.approvalDialogTitle = '提交'
this.approvalFormData = {
operator: '同意',
comment: ''
@ -589,55 +602,64 @@ export default {
handleApprovalSubmit() {
//
this.$refs.approvalForm.validate((valid) => {
if (valid) {
if (!this.detail || !this.detail.id) {
this.$message.error('缺少审批数据')
return
}
const approvalId = this.detail.id
if (!approvalId) {
this.$message.error('缺少审批ID无法提交审批')
return
}
//
// """PASS""""REJECT"
const operator = this.approvalFormData.operator === '同意' ? 'PASS' : 'REJECT'
const submitData = {
approvalId: approvalId,
operator: operator,
comment: this.approvalFormData.comment,
userId: getUserId()
}
//
const request = {
...api.HANDLE_ENGINE_CHECK,
params: submitData
}
this.approvalSubmitting = true
this.$request(request)
.asyncThen((resp) => {
console.log('审批提交成功')
this.approvalDialogVisible = false
this.approvalSubmitting = false
//
this.getApprovalDetail()
})
.asyncErrorCatch((err) => {
console.error('审批提交失败:', err)
this.$message.error(err.message || '审批提交失败,请重试')
this.approvalSubmitting = false
})
if (!valid) {
return false
}
if (!this.detail || !this.detail.id) {
this.$message.error('缺少审批数据')
return
}
const approvalId = this.detail.id
if (!approvalId) {
this.$message.error('缺少审批ID无法提交审批')
return
}
//
// operator退 'REJECT' 'PASS'
const operator = this.approvalActionType === 'reject' ? 'REJECT' : 'PASS'
const submitData = {
approvalId: approvalId,
operator: operator,
comment: this.approvalFormData.comment,
userId: getUserId()
}
//
const request = {
...api.HANDLE_ENGINE_CHECK,
params: submitData
}
this.approvalSubmitting = true
this.$request(request)
.asyncThen((resp) => {
console.log('审批提交成功')
this.handleApprovalDialogClose()
//
this.getApprovalDetail()
//
this.$emit('refresh')
this.approvalSubmitting = false
})
.asyncErrorCatch((err) => {
console.error('审批提交失败:', err)
this.$message.error(err.message || '审批提交失败,请重试')
this.approvalSubmitting = false
})
.finally(() => {
this.approvalSubmitting = false
})
})
},
handleApprovalDialogClose() {
//
this.approvalDialogVisible = false
this.approvalActionType = ''
this.approvalDialogTitle = '审批'
this.approvalFormData = {
operator: '同意',
comment: ''

View File

@ -88,14 +88,14 @@
clearable
class="tree-search"
></el-input>
<div class="tree-actions">
<!-- <div class="tree-actions">
<el-button size="mini" @click="handleExpandAllSecondLevel">
一键展开
</el-button>
<el-button size="mini" @click="handleCollapseAllSecondLevel">
一键收起
</el-button>
</div>
</div> -->
<el-tree
ref="paramTree"
:data="treeData"
@ -1450,9 +1450,9 @@ export default {
//
if (this.dispatchType === 'update_param') {
const { subsystem, partsName, userId, userNumber, username } = change
console.log(change, 'change', subsystem, partsName, userId, userNumber, username)
if (!subsystem || !partsName || !userId) {
const { subsystem, partsName, department, userId, userNumber, username } = change
console.log(change, 'change', subsystem, partsName, department, userId, userNumber, username)
if (!subsystem || !partsName || !department || !userId) {
this.$message({
type: 'warning',
message: '缺少必要参数'
@ -1480,11 +1480,12 @@ export default {
// 使param.partsName使dataPartsName
const paramPartsName = param.partsName || dataPartsName
//
//
// partsName '/' partsName '/'
if (
param.subsystemName === subsystem &&
paramPartsName === partsName
paramPartsName === partsName &&
param.department === department
) {
//
param.filledBy = userId // IDuserId

View File

@ -49,14 +49,14 @@
下载导入模板
</el-button>
<el-button
v-if="shouldShowButtons"
class="right-button"
@click="handleMaintainParams"
>
维护参数
</el-button>
<el-button
v-if="shouldShowButtonsNew"
class="right-button-primary"
type="primary"
@click="handleInitiateApproval"

View File

@ -120,23 +120,18 @@
<el-tree
ref="permissionTree"
:key="'permission-tree-' + dialogVisible"
:data="[]"
:data="treeData"
node-key="id"
:props="{ children: 'children', label: 'label', isLeaf: 'isLeaf' }"
:props="{ children: 'children', label: 'label' }"
:filter-node-method="filterTreeNode"
:default-expand-all="false"
:lazy="true"
:load="loadNode"
class="permission-tree"
>
<span slot-scope="{ node, data }" class="custom-tree-node">
<span class="node-label">
{{ node.label }}
<!-- <span v-if="data.type === 'menu'" class="type-tag menu-tag">菜单</span>
<span v-if="data.type === 'subsystem'" class="type-tag subsystem-tag">子系统</span>
<span v-if="data.type === 'parameter'" class="type-tag parameter-tag">参数类型</span> -->
</span>
<span v-if="data.type === 'subsystem' || data.type === 'parameter'" class="permission-checkboxes">
<span v-if="data.type === 'subsystem' || data.type === 'parts'" class="permission-checkboxes">
<el-checkbox
v-model="data.permissions.view"
size="small"
@ -335,7 +330,7 @@ export default {
formData: {
roleName: '',
rowId: '',
permissions: [] // [{ menuId, menuName, subsystem, parameter, view, edit }]
permissions: [] // [{ roleId, subsystem, parameterName, parameterId, parameterPer, userId }]
},
formRules: {
roleName: [
@ -362,21 +357,11 @@ export default {
{ required: true, message: '请输入角色描述', trigger: 'blur' }
]
},
//
menuTreeData: [],
//
subsystemList: [],
// ->
treeData: [],
treeFilterText: '',
//
nodeMap: {},
//
pendingPermissions: [],
//
menuList: [
'模板管理',
'玉柴发动机数据',
'竞品发动机数据'
],
//
personConfigDialogVisible: false,
personConfigSubmitting: false,
@ -442,31 +427,6 @@ export default {
computed: {
dialogTitle() {
return this.dialogMode === 'add' ? '新增' : '修改'
},
//
// nodeMap
allParameterNodes() {
const nodes = []
// nodeMap
Object.keys(this.nodeMap).forEach(nodeId => {
const node = this.nodeMap[nodeId]
if (node && node.type === 'parameter') {
//
if (!node.permissions) {
this.$set(node, 'permissions', { view: false, edit: false })
}
nodes.push({
id: node.id,
menuName: node.menuName || '',
subsystem: node.subsystem || '',
parameter: node.parameter || node.label || '',
parameterType: node.parameterType || node.label || '',
parameterId: node.parameterId || '', // ID
permissions: node.permissions //
})
}
})
return nodes
}
},
watch: {
@ -476,7 +436,6 @@ export default {
},
mounted() {
this.loadPermissionData()
this.loadParamList()
this.loadDepartmentList()
this.getUserSelfRole()
},
@ -507,9 +466,11 @@ export default {
},
//
validatePermissions(rule, value, callback) {
//
const hasParameterPermission = this.allParameterNodes.some(node => {
return node.permissions.view || node.permissions.edit
//
const hasPartsPermission = Object.keys(this.nodeMap).some(nodeId => {
const node = this.nodeMap[nodeId]
return node && node.type === 'parts' && node.permissions &&
(node.permissions.view || node.permissions.edit)
})
//
@ -519,240 +480,162 @@ export default {
(node.permissions.view || node.permissions.edit)
})
if (!hasParameterPermission && !hasSubsystemPermission) {
if (!hasPartsPermission && !hasSubsystemPermission) {
callback(new Error('请至少分配一个权限'))
} else {
callback()
}
},
//
loadParamList() {
// ->
loadTreeData() {
const request = {
...api.GET_ALL_SYSTEM_ROLE_LIST,
...api.GET_ENGINE_DETAIL_QUERY,
disableSuccessMsg: true
}
this.$request(request)
.asyncThen((resp) => {
//
if (resp && resp.data) {
//
let subsystemList = []
if (Array.isArray(resp.data)) {
subsystemList = resp.data
} else if (typeof resp.data === 'object') {
// { result: [...] } { data: [...] }
subsystemList = resp.data.result || resp.data.data || Object.keys(resp.data) || []
// { "": ["1", "2", ...] }
const data = resp.data
let treeDataResult = []
if (typeof data === 'object' && !Array.isArray(data)) {
treeDataResult = this.convertObjectToTree(data)
} else if (Array.isArray(data)) {
//
treeDataResult = this.formatTreeData(data)
} else {
treeDataResult = []
}
//
this.subsystemList = subsystemList
this.treeData = treeDataResult
} else {
this.subsystemList = []
this.treeData = []
}
this.buildMenuTree()
})
.asyncErrorCatch((err) => {
console.error('加载子系统列表失败:', err)
this.subsystemList = []
this.buildMenuTree()
console.error('获取树数据失败:', err)
this.$message.error('获取树数据失败')
this.treeData = []
})
},
// ->
//
buildMenuTree() {
//
this.nodeMap = {}
//
// 6 -> ->
//
// : { "": ["1", "2", ...] }
convertObjectToTree(data) {
const treeData = []
this.nodeMap = {} //
// 使
this.menuList.forEach((menuName, menuIdx) => {
const menuId = `menu-${menuIdx}`
const menuNode = {
id: menuId,
label: menuName,
type: 'menu',
children: null, // null
isLeaf: false // el-tree
Object.keys(data).forEach((subsystemName, subsystemIdx) => {
const subsystemId = `subsystem-${subsystemIdx}`
const children = []
const seenLabels = new Set() // label
//
this.nodeMap[subsystemId] = {
id: subsystemId,
label: subsystemName,
type: 'subsystem',
subsystem: subsystemName,
permissions: {
view: false,
edit: false
}
}
//
this.nodeMap[menuId] = menuNode
treeData.push(menuNode)
// label `/`
if (Array.isArray(data[subsystemName])) {
data[subsystemName].forEach((partsName, partsIdx) => {
// `/`
if (partsName === '/') {
return
}
// label
if (seenLabels.has(partsName)) {
return
}
seenLabels.add(partsName)
const partsId = `${subsystemId}-parts-${partsIdx}`
const partsNode = {
id: partsId,
label: partsName,
type: 'parts',
subsystem: subsystemName,
partsName: partsName,
permissions: {
view: false,
edit: false
}
}
children.push(partsNode)
//
this.nodeMap[partsId] = {
id: partsId,
label: partsName,
type: 'parts',
subsystem: subsystemName,
partsName: partsName,
permissions: {
view: false,
edit: false
}
}
})
}
treeData.push({
id: subsystemId,
label: subsystemName,
type: 'subsystem',
subsystem: subsystemName,
permissions: {
view: false,
edit: false
},
children: children
})
})
this.menuTreeData = treeData
return treeData
},
// id label label
formatTreeData(data) {
return data.map((item, index) => {
const node = {
id: item.id || item.key || `node-${index}`,
label: item.label || item.name || item.title || '',
type: item.type || 'subsystem',
subsystem: item.subsystem || item.label || '',
permissions: item.permissions || { view: false, edit: false }
}
if (item.children && item.children.length > 0) {
// label
const seenLabels = new Set()
const uniqueChildren = []
item.children.forEach((child) => {
const childLabel = child.label || child.name || child.title || ''
if (childLabel !== '/' && !seenLabels.has(childLabel)) {
seenLabels.add(childLabel)
uniqueChildren.push({
id: child.id || `${node.id}-parts-${uniqueChildren.length}`,
label: childLabel,
type: 'parts',
subsystem: node.subsystem,
partsName: childLabel,
permissions: child.permissions || { view: false, edit: false }
})
}
})
//
node.children = uniqueChildren
}
return node
})
},
//
filterTreeNode(value, data) {
if (!value) return true
return data.label && data.label.indexOf(value) !== -1
},
//
loadNode(node, resolve) {
// level === 0
if (node.level === 0) {
//
if (!this.menuTreeData || this.menuTreeData.length === 0) {
this.buildMenuTree()
}
resolve(this.menuTreeData || [])
return
}
//
if (node.data.type === 'menu') {
this.loadMenuSubsystemsForLazy(node.data, resolve)
return
}
//
if (node.data.type === 'subsystem') {
this.loadSubsystemParametersForLazy(node.data, resolve)
return
}
//
resolve([])
},
//
loadMenuSubsystemsForLazy(menuNode, resolve) {
//
if (!Array.isArray(this.subsystemList) || this.subsystemList.length === 0) {
resolve([])
return
}
//
const subsystemNodes = []
this.subsystemList.forEach((subsystemName, subIdx) => {
//
const subsystemNameStr = typeof subsystemName === 'string'
? subsystemName
: (subsystemName.name || subsystemName.subsystemName || subsystemName.label || '')
if (!subsystemNameStr) {
return
}
const subsystemId = `${menuNode.id}-subsystem-${subIdx}`
const subsystemNode = {
id: subsystemId,
label: subsystemNameStr,
type: 'subsystem',
menuName: menuNode.label,
subsystem: subsystemNameStr,
permissions: {
view: false,
edit: false
},
children: null, // null
isLeaf: false // el-tree
}
subsystemNodes.push(subsystemNode)
//
this.nodeMap[subsystemId] = subsystemNode
})
// resolve
resolve(subsystemNodes)
},
//
loadSubsystemParametersForLazy(subsystemNode, resolve) {
if (!subsystemNode.subsystem) {
console.warn('子系统节点缺少子系统名称')
resolve([])
return
}
const request = {
...api.GET_SUB_SYSTEM_DATA_LIST,
params: {
subsystem: subsystemNode.subsystem
},
disableSuccessMsg: true
}
this.$request(request)
.asyncThen((resp) => {
//
let parameterList = []
if (resp && resp.data) {
if (Array.isArray(resp.data)) {
parameterList = resp.data
} else if (resp.data.result && Array.isArray(resp.data.result)) {
parameterList = resp.data.result
} else if (resp.data.data && Array.isArray(resp.data.data)) {
parameterList = resp.data.data
}
}
//
const parameterNodes = []
const seenTypes = new Set() //
parameterList.forEach((param, paramIdx) => {
//
const paramName = typeof param === 'string'
? param
: (param.name || param.parameterName || param.parameterType || param.label || '')
// ID id parameterId
const parameterId = typeof param === 'object' && param !== null
? (param.id || param.parameterId || '')
: ''
if (!paramName || seenTypes.has(paramName)) {
return
}
seenTypes.add(paramName)
const paramTypeId = `${subsystemNode.id}-param-${paramIdx}`
const paramTypeNode = {
id: paramTypeId,
label: paramName,
type: 'parameter',
menuName: subsystemNode.menuName,
subsystem: subsystemNode.subsystem,
parameter: paramName,
parameterName: paramName, //
parameterType: paramName,
parameterId: parameterId, // ID
permissions: {
view: false,
edit: false
},
isLeaf: true, //
children: null //
}
parameterNodes.push(paramTypeNode)
//
this.nodeMap[paramTypeId] = paramTypeNode
//
this.applyPendingPermissionsToNode(paramTypeNode)
})
// resolve
resolve(parameterNodes)
// 使 $nextTick
this.$nextTick(() => {
//
parameterNodes.forEach(node => {
this.applyPendingPermissionsToNode(node)
})
//
if (parameterNodes.length > 0) {
this.updateSubsystemPermissionFromChildren(parameterNodes[0])
}
})
})
.asyncErrorCatch((err) => {
console.error('加载子系统参数失败:', err)
this.$message.error('加载参数类型失败')
//
resolve([])
})
},
//
handlePermissionChange(data, permissionType) {
//
@ -761,11 +644,11 @@ export default {
this.$set(this.nodeMap[data.id].permissions, permissionType, data.permissions[permissionType])
}
// /
// /
if (data.type === 'subsystem') {
this.updateSubsystemChildParameters(data, permissionType)
} else if (data.type === 'parameter') {
//
this.updateSubsystemChildParts(data, permissionType)
} else if (data.type === 'parts') {
//
this.updateSubsystemPermissionFromChildren(data)
}
@ -776,32 +659,32 @@ export default {
}
})
},
//
updateSubsystemChildParameters(subsystemNode, permissionType) {
//
updateSubsystemChildParts(subsystemNode, permissionType) {
const subsystemId = subsystemNode.id
const newValue = subsystemNode.permissions[permissionType]
//
//
Object.keys(this.nodeMap).forEach(nodeId => {
const node = this.nodeMap[nodeId]
if (node && node.type === 'parameter' && node.id && node.id.startsWith(subsystemId + '-param-')) {
if (node && node.type === 'parts' && node.id && node.id.startsWith(subsystemId + '-parts-')) {
//
if (!node.permissions) {
this.$set(node, 'permissions', { view: false, edit: false })
}
//
//
this.$set(node.permissions, permissionType, newValue)
}
})
},
//
updateSubsystemPermissionFromChildren(parameterNode) {
if (!parameterNode || !parameterNode.id) {
//
updateSubsystemPermissionFromChildren(partsNode) {
if (!partsNode || !partsNode.id) {
return
}
//
const subsystemId = parameterNode.id.split('-param-')[0]
//
const subsystemId = partsNode.id.split('-parts-')[0]
const subsystemNode = this.nodeMap[subsystemId]
if (!subsystemNode || subsystemNode.type !== 'subsystem') {
@ -813,26 +696,26 @@ export default {
this.$set(subsystemNode, 'permissions', { view: false, edit: false })
}
//
const childParameterNodes = []
//
const childPartsNodes = []
Object.keys(this.nodeMap).forEach(nodeId => {
const node = this.nodeMap[nodeId]
if (node && node.type === 'parameter' && node.id && node.id.startsWith(subsystemId + '-param-')) {
childParameterNodes.push(node)
if (node && node.type === 'parts' && node.id && node.id.startsWith(subsystemId + '-parts-')) {
childPartsNodes.push(node)
}
})
if (childParameterNodes.length === 0) {
if (childPartsNodes.length === 0) {
return
}
//
const allViewSelected = childParameterNodes.every(node => node.permissions && node.permissions.view)
const noneViewSelected = childParameterNodes.every(node => !node.permissions || !node.permissions.view)
//
const allViewSelected = childPartsNodes.every(node => node.permissions && node.permissions.view)
const noneViewSelected = childPartsNodes.every(node => !node.permissions || !node.permissions.view)
//
const allEditSelected = childParameterNodes.every(node => node.permissions && node.permissions.edit)
const noneEditSelected = childParameterNodes.every(node => !node.permissions || !node.permissions.edit)
const allEditSelected = childPartsNodes.every(node => node.permissions && node.permissions.edit)
const noneEditSelected = childPartsNodes.every(node => !node.permissions || !node.permissions.edit)
//
if (allViewSelected) {
@ -945,10 +828,8 @@ export default {
}
//
this.resetAllPermissions()
//
if (!this.menuTreeData || this.menuTreeData.length === 0) {
this.buildMenuTree()
}
//
this.loadTreeData()
// key
this.dialogVisible = true
//
@ -973,7 +854,7 @@ export default {
}
this.$request(request)
.asyncThen((resp) => {
// [{ roleId, menuName, parameterId, parameterPer, userId }]
// [{ roleId, subsystem, parameterName, parameterId, parameterPer, userId }]
let permissions = []
if (resp && resp.data) {
if (Array.isArray(resp.data)) {
@ -988,9 +869,6 @@ export default {
//
if (permissions.length > 0) {
this.setPermissionsFromData(permissions)
} else {
//
this.pendingPermissions = []
}
})
.asyncErrorCatch((err) => {
@ -1427,26 +1305,28 @@ export default {
if (node && node.permissions) {
node.permissions.view = false
node.permissions.edit = false
} else if (node && (node.type === 'subsystem' || node.type === 'parameter')) {
} else if (node && (node.type === 'subsystem' || node.type === 'parts')) {
//
this.$set(node, 'permissions', { view: false, edit: false })
}
})
},
// menuPath
// menuPath : "/" -> ""
// menuList menuPath
extractMenuNameFromPath(menuPath) {
if (!menuPath) return ''
// menuList
for (const menuName of this.menuList) {
if (menuPath.includes(menuName)) {
return menuName
//
const resetNodePermissions = (nodes) => {
if (Array.isArray(nodes)) {
nodes.forEach(node => {
if (node.permissions) {
node.permissions.view = false
node.permissions.edit = false
} else if (node.type === 'subsystem' || node.type === 'parts') {
this.$set(node, 'permissions', { view: false, edit: false })
}
if (node.children && Array.isArray(node.children)) {
resetNodePermissions(node.children)
}
})
}
}
// "/"
const parts = menuPath.split('/')
return parts.length > 0 ? parts[parts.length - 1].trim() : menuPath.trim()
resetNodePermissions(this.treeData)
},
//
setPermissionsFromData(permissions) {
@ -1458,14 +1338,8 @@ export default {
//
this.resetAllPermissions()
//
this.pendingPermissions = permArray
//
//
const processedPerms = permArray.map(perm => {
// menuPath menuList
const menuName = this.extractMenuNameFromPath(perm.menuPath || '')
// parameterPer
let isView = false
let isEdit = false
@ -1480,66 +1354,72 @@ export default {
return {
...perm,
menuName: menuName, //
view: isView,
edit: isEdit
}
})
// menuNamesubsystemparameterName
//
const parameterPermMap = new Map()
// subsystem parameterName
//
const subsystemPermMap = new Map()
processedPerms.forEach(perm => {
const key = `${perm.menuName || ''}_${perm.subsystem || ''}_${perm.parameterName || ''}`
if (!parameterPermMap.has(key)) {
parameterPermMap.set(key, {
menuName: perm.menuName,
subsystem: perm.subsystem,
parameterName: perm.parameterName,
const subsystem = perm.subsystem || ''
const parameterName = perm.parameterName || ''
if (!subsystemPermMap.has(subsystem)) {
subsystemPermMap.set(subsystem, new Map())
}
const partsPermMap = subsystemPermMap.get(subsystem)
// 使 parameterName
const key = parameterName
if (!partsPermMap.has(key)) {
partsPermMap.set(key, {
subsystem: subsystem,
partsName: parameterName,
view: false,
edit: false
})
}
const paramPerm = parameterPermMap.get(key)
const partsPerm = partsPermMap.get(key)
if (perm.view) {
paramPerm.view = true
partsPerm.view = true
}
if (perm.edit) {
paramPerm.edit = true
partsPerm.edit = true
}
})
//
parameterPermMap.forEach((paramPerm, key) => {
Object.keys(this.nodeMap).forEach(nodeId => {
const node = this.nodeMap[nodeId]
if (node && node.type === 'parameter') {
// menuPath
const menuMatch = paramPerm.menuName && node.menuName && paramPerm.menuName === node.menuName
// subsystem
const subsystemMatch = paramPerm.subsystem && node.subsystem && paramPerm.subsystem === node.subsystem
// parameterName
const parameterNameMatch = paramPerm.parameterName && (node.parameterName || node.label) &&
paramPerm.parameterName === (node.parameterName || node.label)
subsystemPermMap.forEach((partsPermMap, subsystem) => {
partsPermMap.forEach((partsPerm, partsName) => {
Object.keys(this.nodeMap).forEach(nodeId => {
const node = this.nodeMap[nodeId]
if (node && node.type === 'parts') {
//
const subsystemMatch = partsPerm.subsystem && node.subsystem && partsPerm.subsystem === node.subsystem
// 使 parameterName
const partsNameMatch = partsPerm.partsName && (node.partsName || node.label) &&
partsPerm.partsName === (node.partsName || node.label)
if (menuMatch && subsystemMatch && parameterNameMatch) {
//
if (!node.permissions) {
this.$set(node, 'permissions', { view: false, edit: false })
if (subsystemMatch && partsNameMatch) {
//
if (!node.permissions) {
this.$set(node, 'permissions', { view: false, edit: false })
}
//
const newPermissions = {
view: node.permissions.view || partsPerm.view,
edit: node.permissions.edit || partsPerm.edit
}
this.$set(node, 'permissions', newPermissions)
console.log('设置零部件节点权限:', node.id, node.label, {
subsystem: node.subsystem,
partsName: node.partsName || node.label
}, newPermissions)
}
//
const newPermissions = {
view: node.permissions.view || paramPerm.view,
edit: node.permissions.edit || paramPerm.edit
}
this.$set(node, 'permissions', newPermissions)
console.log('设置已加载节点权限:', node.id, node.label, {
menuName: node.menuName,
subsystem: node.subsystem,
parameterName: node.parameterName || node.label
}, newPermissions)
}
}
})
})
})
@ -1548,85 +1428,19 @@ export default {
Object.keys(this.nodeMap).forEach(nodeId => {
const node = this.nodeMap[nodeId]
if (node && node.type === 'subsystem') {
//
const childParameterNode = Object.keys(this.nodeMap).find(id => {
//
const childPartsNode = Object.keys(this.nodeMap).find(id => {
const childNode = this.nodeMap[id]
return childNode && childNode.type === 'parameter' && childNode.id && childNode.id.startsWith(nodeId + '-param-')
return childNode && childNode.type === 'parts' && childNode.id && childNode.id.startsWith(nodeId + '-parts-')
})
if (childParameterNode) {
this.updateSubsystemPermissionFromChildren(this.nodeMap[childParameterNode])
if (childPartsNode) {
this.updateSubsystemPermissionFromChildren(this.nodeMap[childPartsNode])
}
}
})
})
console.log('权限数据已保存,待应用权限数量:', this.pendingPermissions.length, '处理后的权限:', processedPerms)
},
//
applyPendingPermissionsToNode(node) {
if (!node || node.type !== 'parameter' || !this.pendingPermissions || this.pendingPermissions.length === 0) {
return
}
//
const matchingPerms = this.pendingPermissions.filter(perm => {
// menuPath
const permMenuName = this.extractMenuNameFromPath(perm.menuPath || '')
// menuPath
const menuMatch = permMenuName && node.menuName && permMenuName === node.menuName
// subsystem
const subsystemMatch = perm.subsystem && node.subsystem && perm.subsystem === node.subsystem
// parameterName
const parameterNameMatch = perm.parameterName && (node.parameterName || node.label) &&
perm.parameterName === (node.parameterName || node.label)
return menuMatch && subsystemMatch && parameterNameMatch
})
if (matchingPerms.length > 0) {
//
if (!node.permissions) {
this.$set(node, 'permissions', { view: false, edit: false })
}
// parameterPer "" "" 1 2
let hasView = false
let hasEdit = false
matchingPerms.forEach(perm => {
const parameterPer = perm.parameterPer
if (typeof parameterPer === 'string') {
if (parameterPer === '查看') {
hasView = true
} else if (parameterPer === '编辑') {
hasEdit = true
}
} else if (typeof parameterPer === 'number') {
if (parameterPer === 1) {
hasView = true
} else if (parameterPer === 2) {
hasEdit = true
}
}
})
// 使 $set
const newPermissions = {
view: hasView,
edit: hasEdit
}
// nodeMap
if (this.nodeMap[node.id]) {
this.$set(this.nodeMap[node.id], 'permissions', newPermissions)
}
//
this.$set(node, 'permissions', newPermissions)
console.log('应用权限到节点:', node.id, node.label, {
menuName: node.menuName,
subsystem: node.subsystem,
parameterName: node.parameterName || node.label
}, newPermissions, '匹配的权限:', matchingPerms)
}
console.log('权限数据已设置,处理后的权限:', processedPerms)
},
//
collectPermissions() {
@ -1634,48 +1448,51 @@ export default {
const roleId = this.formData.rowId || ''
const userId = getUserId()
//
//
//
//
Object.keys(this.nodeMap).forEach(nodeId => {
const node = this.nodeMap[nodeId]
if (node && node.type === 'parameter') {
if (node && node.type === 'parts') {
//
const nodePermissions = node.permissions || { view: false, edit: false }
//
const subsystemId = node.id.split('-param-')[0]
//
const subsystemId = node.id.split('-parts-')[0]
const subsystemNode = this.nodeMap[subsystemId]
const subsystemPermissions = subsystemNode && subsystemNode.permissions
? subsystemNode.permissions
: { view: false, edit: false }
//
//
const shouldCollectView = nodePermissions.view || subsystemPermissions.view
const shouldCollectEdit = nodePermissions.edit || subsystemPermissions.edit
// parameterPer = 1
// 使 partsName parameterName
if (shouldCollectView) {
permissions.push({
roleId: roleId,
menuName: node.menuName || '',
parameterId: node.parameterId || '',
subsystem: node.subsystem || '',
parameterName: node.partsName || node.label || '',
parameterId: '',
parameterPer: 1, // 1
userId: userId
})
}
// parameterPer = 2
// parameterPer = 2
if (shouldCollectEdit) {
permissions.push({
roleId: roleId,
menuName: node.menuName || '',
parameterId: node.parameterId || '',
parameterPer: 2, // 2
subsystem: node.subsystem || '',
parameterName: node.partsName || node.label || '',
parameterId: '',
parameterPer: 2, // 2
userId: userId
})
}
}
})
console.log('收集到的权限:', permissions, 'nodeMap中的参数节点数量:', Object.keys(this.nodeMap).filter(id => this.nodeMap[id] && this.nodeMap[id].type === 'parameter').length)
console.log('收集到的权限:', permissions, 'nodeMap中的零部件节点数量:', Object.keys(this.nodeMap).filter(id => this.nodeMap[id] && this.nodeMap[id].type === 'parts').length)
return permissions
},
//
@ -1688,7 +1505,6 @@ export default {
}
this.treeFilterText = ''
this.resetAllPermissions()
this.pendingPermissions = [] //
if (this.$refs.form) {
this.$refs.form.clearValidate()
}