From b60a50dca557482ba2c9dfbea4f58c223e6e7eaf Mon Sep 17 00:00:00 2001 From: Lxq <19852720163@163.com> Date: Thu, 18 Dec 2025 15:15:45 +0800 Subject: [PATCH 1/3] =?UTF-8?q?=E4=B8=BB=E7=95=8C=E9=9D=A2+=E7=B3=BB?= =?UTF-8?q?=E7=BB=9F=E7=AE=A1=E7=90=86?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- rc_autoplc_front/.env.development | 2 +- rc_autoplc_front/.env.production | 2 +- rc_autoplc_front/src/api/position.ts | 2 +- rc_autoplc_front/src/router/index.ts | 50 +-- rc_autoplc_front/src/views/Layout.vue | 191 ++++++++++ .../src/views/manage-log/index.vue | 336 +++++++++--------- 6 files changed, 383 insertions(+), 200 deletions(-) create mode 100644 rc_autoplc_front/src/views/Layout.vue diff --git a/rc_autoplc_front/.env.development b/rc_autoplc_front/.env.development index 8aaa774..4d37822 100644 --- a/rc_autoplc_front/.env.development +++ b/rc_autoplc_front/.env.development @@ -1 +1 @@ -VITE_API_URL=http://192.168.110.204:9090 +VITE_API_URL=http://223.71.122.54:9090 diff --git a/rc_autoplc_front/.env.production b/rc_autoplc_front/.env.production index 8aaa774..4d37822 100644 --- a/rc_autoplc_front/.env.production +++ b/rc_autoplc_front/.env.production @@ -1 +1 @@ -VITE_API_URL=http://192.168.110.204:9090 +VITE_API_URL=http://223.71.122.54:9090 diff --git a/rc_autoplc_front/src/api/position.ts b/rc_autoplc_front/src/api/position.ts index 50053d7..c131d2a 100644 --- a/rc_autoplc_front/src/api/position.ts +++ b/rc_autoplc_front/src/api/position.ts @@ -25,7 +25,7 @@ export function positionupd(data: any) { export function positionlist(data: any) { return request({ - url: '/position/listPpage', + url: '/position/listPage', method: 'get', params: data, }) diff --git a/rc_autoplc_front/src/router/index.ts b/rc_autoplc_front/src/router/index.ts index f1a2835..ab5d519 100644 --- a/rc_autoplc_front/src/router/index.ts +++ b/rc_autoplc_front/src/router/index.ts @@ -5,28 +5,34 @@ const router = createRouter({ routes: [ { path: '/', - name: 'user', - component: () => import('../views/user/index.vue'), - }, - { - path: '/role', - name: 'role', - component: () => import('../views/role/index.vue'), - }, - { - path: '/department', - name: 'department', - component: () => import('../views/department/index.vue'), - }, - { - path: '/position', - name: 'position', - component: () => import('../views/position/index.vue'), - }, - { - path: '/manage-log', - name: 'manage-log', - component: () => import('../views/manage-log/index.vue'), + component: () => import('../views/Layout.vue'), + children: [ + { + path: '/user', + name: 'user', + component: () => import('../views/user/index.vue'), + }, + { + path: '/role', + name: 'role', + component: () => import('../views/role/index.vue'), + }, + { + path: '/department', + name: 'department', + component: () => import('../views/department/index.vue'), + }, + { + path: '/position', + name: 'position', + component: () => import('../views/position/index.vue'), + }, + { + path: '/manage-log', + name: 'manage-log', + component: () => import('../views/manage-log/index.vue'), + }, + ], }, ], }) diff --git a/rc_autoplc_front/src/views/Layout.vue b/rc_autoplc_front/src/views/Layout.vue new file mode 100644 index 0000000..df964a6 --- /dev/null +++ b/rc_autoplc_front/src/views/Layout.vue @@ -0,0 +1,191 @@ + + + + + + diff --git a/rc_autoplc_front/src/views/manage-log/index.vue b/rc_autoplc_front/src/views/manage-log/index.vue index d662b3b..8451ae8 100644 --- a/rc_autoplc_front/src/views/manage-log/index.vue +++ b/rc_autoplc_front/src/views/manage-log/index.vue @@ -1,20 +1,28 @@ @@ -220,9 +246,11 @@ import { onMounted, reactive, ref, computed } from 'vue' import type { FormInstance, FormRules } from 'element-plus' import { ElMessage, ElMessageBox } from 'element-plus' -import { useradd, userbyid, userdel, userlist, userupd } from '@/api/user' -import { departtree } from '@/api/department' -import { positionselect } from '@/api/position' +import { useradd, userbyid, userdel, userlist, userupd } from '@/api/system/user' +import { departtree } from '@/api/system/department' +import { positionselect } from '@/api/system/position' +import { userRoleAdd, userRoleByUserId, userRoleDel } from '@/api/system/user-role' +import { rleselect } from '@/api/system/role' interface UserItem { id?: number | string @@ -253,6 +281,12 @@ interface PositionItem { posiCode?: string } +interface RoleItem { + id?: number | string + roleName?: string + roleCode?: string +} + const loading = ref(false) const submitLoading = ref(false) const tableData = ref([]) @@ -261,6 +295,12 @@ const deptTreeData = ref([]) const positionOptions = ref([]) const deptMap = ref>(new Map()) const posMap = ref>(new Map()) +const roleDialogVisible = ref(false) +const assignRoleLoading = ref(false) +const roleOptions = ref([]) +const selectedRoleIds = ref<(number | string)[]>([]) +const currentAssignUserId = ref(null) +const originalUserRoles = ref([]) // 保存用户原有的角色关联列表 const queryForm = reactive({ userName: '', @@ -638,9 +678,128 @@ const handleDelete = (row: UserItem) => { .catch(() => {}) } +// 加载角色列表 +const loadRoleList = async () => { + try { + const res: any = await rleselect({}) + const data = Array.isArray(res?.data) ? res.data : Array.isArray(res) ? res : [] + roleOptions.value = data + } catch (error) { + console.error('load role list error', error) + ElMessage.error('加载角色列表失败') + roleOptions.value = [] + } +} + +// 打开角色分配弹框 +const openRoleDialog = async (row: UserItem) => { + if (!row.id) { + ElMessage.warning('缺少用户ID') + return + } + currentAssignUserId.value = row.id + selectedRoleIds.value = [] + roleDialogVisible.value = true + + // 确保角色列表已加载 + if (roleOptions.value.length === 0) { + await loadRoleList() + } + + // 获取用户已有的角色 + try { + const res: any = await userRoleByUserId(row.id) + const data = res?.data ?? res ?? {} + + // 兼容多种返回格式 + const userRoles = Array.isArray(data) + ? data + : Array.isArray(data.data) + ? data.data + : Array.isArray(data.records) + ? data.records + : Array.isArray(data.list) + ? data.list + : [] + + // 保存原有的角色关联列表(包含ID) + originalUserRoles.value = userRoles + + // 提取已有角色的ID列表 + if (Array.isArray(userRoles) && userRoles.length > 0) { + selectedRoleIds.value = userRoles + .map((item: any) => item.roleId) + .filter((id: any) => id !== undefined && id !== null) + } else { + selectedRoleIds.value = [] + originalUserRoles.value = [] + } + } catch (error) { + console.error('load user roles error', error) + // 如果获取失败,不影响弹框打开,只是不预选角色 + originalUserRoles.value = [] + } +} + +// 分配角色 +const handleAssignRole = async () => { + if (!currentAssignUserId.value) { + ElMessage.warning('缺少用户ID') + return + } + + assignRoleLoading.value = true + try { + // 获取原有的角色ID列表 + const originalRoleIds = originalUserRoles.value + .map((item: any) => item.roleId) + .filter((id: any) => id !== undefined && id !== null) + + // 计算需要新增的角色(新选中但原来没有的) + const rolesToAdd = selectedRoleIds.value.filter( + (roleId) => !originalRoleIds.includes(roleId) + ) + + // 计算需要删除的角色(原来有但现在未选中的) + const rolesToDelete = originalUserRoles.value.filter( + (item: any) => !selectedRoleIds.value.includes(item.roleId) + ) + + // 执行新增操作 + const addPromises = rolesToAdd.map((roleId) => { + return userRoleAdd({ + userId: currentAssignUserId.value, + roleId: roleId, + remark: '', + }) + }) + + // 执行删除操作 + const deletePromises = rolesToDelete.map((item: any) => { + if (item.id) { + return userRoleDel(item.id) + } + return Promise.resolve() + }) + + // 等待所有操作完成 + await Promise.all([...addPromises, ...deletePromises]) + + ElMessage.success('分配角色成功') + roleDialogVisible.value = false + } catch (error: any) { + console.error('assign role error', error) + const errorMsg = error?.message || error?.msg || '分配角色失败' + ElMessage.error(errorMsg) + } finally { + assignRoleLoading.value = false + } +} + onMounted(() => { loadDeptTree() loadPositionList() + loadRoleList() loadList() })