feat: add department filter in settings user management

This commit is contained in:
Your Name 2026-03-28 11:15:10 +08:00
parent 7b343534ee
commit c76551bef2

View File

@ -421,16 +421,35 @@
/>
<div class="user-search-toolbar">
<a-input-search
v-model:value="userManagementSearchKeyword"
allow-clear
placeholder="搜索姓名、用户名、手机号、邮箱、部门"
style="width: 320px"
>
<template #prefix>
<Icon name="search" size="sm" />
</template>
</a-input-search>
<div class="user-search-filters">
<a-input-search
v-model:value="userManagementSearchKeyword"
allow-clear
placeholder="搜索姓名、用户名、手机号、邮箱、部门"
style="width: 320px"
>
<template #prefix>
<Icon name="search" size="sm" />
</template>
</a-input-search>
<a-select
v-model:value="userManagementDeptFilter"
allow-clear
show-search
placeholder="按部门筛选"
style="width: 220px"
:filter-option="filterUserDepartmentOption"
>
<a-select-option value="unassigned">未分配部门</a-select-option>
<a-select-option
v-for="dept in userManagementDepartmentOptions"
:key="dept.id"
:value="dept.id"
>
{{ dept.deptName }}
</a-select-option>
</a-select>
</div>
<span class="user-search-count">
共 {{ filteredUsersList.length }} 位用户
</span>
@ -3419,6 +3438,7 @@ const selectedUser = ref<User | null>(null)
const transferDeptId = ref<number | null>(null)
const allUsers = ref<User[]>([])
const userManagementSearchKeyword = ref('')
const userManagementDeptFilter = ref<number | string>()
const offboardingPreviewLoading = ref(false)
const offboardingExecuting = ref(false)
const offboardingPreview = ref<UserOffboardingPreview | null>(null)
@ -3815,26 +3835,51 @@ const allUsersList = computed(() => {
const filteredUsersList = computed(() => {
const keyword = userManagementSearchKeyword.value.trim().toLowerCase()
if (!keyword) {
return allUsersList.value
}
const deptFilter = userManagementDeptFilter.value
return allUsersList.value.filter((user) => {
const searchFields = [
const matchesKeyword = !keyword || [
user.id,
user.realName,
user.username,
user.phone,
user.email,
user.deptName
]
].some((field) => String(field || '').toLowerCase().includes(keyword))
return searchFields.some((field) =>
String(field || '').toLowerCase().includes(keyword)
)
const matchesDept = !deptFilter
|| (deptFilter === 'unassigned'
? !user.deptId
: user.deptId === deptFilter)
return matchesKeyword && matchesDept
})
})
const userManagementDepartmentOptions = computed(() => {
const seenDeptIds = new Set<number>()
const options: Array<{ id: number; deptName: string }> = []
allUsersList.value.forEach((user) => {
if (!user.deptId || !user.deptName || seenDeptIds.has(user.deptId)) {
return
}
seenDeptIds.add(user.deptId)
options.push({
id: user.deptId,
deptName: user.deptName
})
})
return options.sort((a, b) => a.deptName.localeCompare(b.deptName))
})
const filterUserDepartmentOption = (input: string, option: any) => {
const searchText = input.toLowerCase()
const optionLabel = String(option?.children || '').toLowerCase()
return optionLabel.includes(searchText)
}
// 格式化时间
const formatUserTime = (time: string | undefined) => {
if (!time) return '--'
@ -6931,6 +6976,13 @@ watch(activeTab, (value) => {
flex-wrap: wrap;
}
.user-search-filters {
display: flex;
align-items: center;
gap: 12px;
flex-wrap: wrap;
}
.user-search-count {
color: $text-tertiary;
font-size: $font-size-sm;