diff --git a/src/typings/entities/role.d.ts b/src/typings/entities/role.d.ts index d62e397..913c992 100644 --- a/src/typings/entities/role.d.ts +++ b/src/typings/entities/role.d.ts @@ -30,9 +30,9 @@ namespace Entity { */ status?: number /** - * 显示顺序 + * 数据范围(1:全部数据权限 2:自定数据权限 3:本部门数据权限 4:本部门及以下数据权限 5:仅本人数据权限) */ - sort: number + dataScope: number /** * 创建时间 */ @@ -41,6 +41,8 @@ namespace Entity { * 更新时间 */ updateTime?: string + menus?: Entity.Menu[] + depts?: Entity.Dept[] [property: string]: any } } diff --git a/src/views/system/role/columns.tsx b/src/views/system/role/columns.tsx index f724443..a5c3da7 100644 --- a/src/views/system/role/columns.tsx +++ b/src/views/system/role/columns.tsx @@ -1,7 +1,7 @@ import type { DataTableColumns } from 'naive-ui' import { NButton, NPopconfirm, NSpace, NSwitch } from 'naive-ui' import type { ProSearchFormColumns } from 'pro-naive-ui' -import { renderProCopyableText, renderProDateText } from 'pro-naive-ui' +import { renderProCopyableText, renderProTags } from 'pro-naive-ui' export const searchColumns: ProSearchFormColumns = [ { @@ -51,11 +51,25 @@ export function createRoleColumns(actions: RoleColumnActions): DataTableColumns< key: 'roleKey', render: row => renderProCopyableText(row.roleKey), }, + { + title: '数据范围', + align: 'center', + key: 'dataScope', + render: (row) => { + const dataScopeMap: Record = { + 1: '全部数据权限', + 2: '自定数据权限', + 3: '本部门数据权限', + 4: '本部门及以下数据权限', + 5: '仅本人数据权限', + } + return renderProTags(dataScopeMap[row.dataScope]) + }, + }, { title: '备注', align: 'center', key: 'remark', - width: 200, }, { title: '状态', @@ -80,9 +94,6 @@ export function createRoleColumns(actions: RoleColumnActions): DataTableColumns< align: 'center', key: 'createTime', width: 200, - render: row => renderProDateText(row.createTime, { - pattern: 'datetime', - }), }, { title: '操作', diff --git a/src/views/system/role/components/RoleModal.vue b/src/views/system/role/components/RoleModal.vue index c768d37..2f27d2b 100644 --- a/src/views/system/role/components/RoleModal.vue +++ b/src/views/system/role/components/RoleModal.vue @@ -2,6 +2,8 @@ import { useBoolean } from '@/hooks' import { createRole, getRoleById, updateRole } from '@/api' import { createProModalForm } from 'pro-naive-ui' +import TreeDeptSelect from './TreeDeptSelect.vue' +import TreeMenuSelect from './TreeMenuSelect.vue' interface Props { modalName?: string @@ -17,16 +19,18 @@ const emit = defineEmits<{ const { bool: submitLoading, setTrue: startLoading, setFalse: endLoading } = useBoolean(false) -const modalForm = createProModalForm>({ +const modalForm = createProModalForm & { deptIds?: number[], menuIds?: number[] }>({ omitEmptyString: false, initialValues: { status: 0, + dataScope: 1, }, onSubmit: submitModal, }) type ModalType = 'add' | 'edit' const modalType = shallowRef('add') + const modalTitle = computed(() => { const titleMap: Record = { add: '添加', @@ -37,11 +41,10 @@ const modalTitle = computed(() => { async function openModal(type: ModalType = 'add', data?: Partial) { modalType.value = type - modalForm.open() + const handlers = { async add() { - // 使用默认值 }, async edit() { if (!data) @@ -49,6 +52,9 @@ async function openModal(type: ModalType = 'add', data?: Partial) { const { data: role } = await getRoleById(data.id!) modalForm.values.value = role + // 设置已选中的菜单和部门 + modalForm.values.value.menuIds = role.menus?.map(menu => menu.id) || [] + modalForm.values.value.deptIds = role.depts?.map(dept => dept.id) || [] }, } await handlers[type]() @@ -99,7 +105,7 @@ defineExpose({ :title="modalTitle" :form="modalForm" :loading="submitLoading" - width="600px" + width="800px" >
+ + + + + + + + + +import { getDeptOptions } from '@/api' + +const deptOptions = ref([]) + +const checkedKeys = defineModel('value', { default: () => [] }) +const expandedKeys = ref([]) +const cascade = ref(true) +const isExpanded = ref(false) +const isAllSelected = ref(false) + +// 获取所有节点keys的辅助函数 +function getAllKeys(nodes: any[]): number[] { + let keys: number[] = [] + nodes.forEach((node) => { + keys.push(node.value) + if (node.children && node.children.length > 0) { + keys = keys.concat(getAllKeys(node.children)) + } + }) + return keys +} + +// checkbox更新回调函数 +function handleExpandedChange(expanded: boolean) { + if (expanded) { + expandedKeys.value = getAllKeys(deptOptions.value) + } + else { + expandedKeys.value = [] + } +} + +function handleAllSelectedChange(selected: boolean) { + if (selected) { + checkedKeys.value = getAllKeys(deptOptions.value) + } + else { + checkedKeys.value = [] + } +} + +// 加载部门数据 +async function loadDeptOptions() { + try { + const { data } = await getDeptOptions() + deptOptions.value = data + } + catch (error) { + console.error('加载部门数据失败:', error) + deptOptions.value = [] + } +} + +// 组件挂载时加载数据 +onMounted(() => { + loadDeptOptions() +}) + + + diff --git a/src/views/system/role/components/TreeMenuSelect.vue b/src/views/system/role/components/TreeMenuSelect.vue new file mode 100644 index 0000000..645354d --- /dev/null +++ b/src/views/system/role/components/TreeMenuSelect.vue @@ -0,0 +1,87 @@ + + + diff --git a/src/views/system/user/components/UserModal.vue b/src/views/system/user/components/UserModal.vue index 01c9502..7d0ab7c 100644 --- a/src/views/system/user/components/UserModal.vue +++ b/src/views/system/user/components/UserModal.vue @@ -1,6 +1,6 @@