Repository navigation
fix: chat user group add member #7816
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -17,8 +17,8 @@ import type { | |
| const prefix = '/system/chat_user' | ||
|
|
||
| /** 获取对话用户。 */ | ||
| const getChatUser = () => { | ||
| return get<ChatUserBase[]>(`${prefix}/list`) | ||
| const getChatUser = (query?: Dict<unknown>) => { | ||
| return get<ChatUserBase[]>(`${prefix}/list`, query) | ||
| } | ||
|
|
||
| /** 获取对话用户分页列表。 */ | ||
|
Contributor
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. No syntax irregularity in this small diff. The change is backward-compatible for normal callers, but there are a few points to verify:
Minor naming suggestion: Recommended implementation, assuming interface ChatUserListQuery {
keyword?: string
page?: number
pageSize?: number
}
const getChatUser = (query?: ChatUserListQuery) => {
return get<ChatUserBase[]>(`${prefix}/list`, query)
} |
||
|
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -17,18 +17,24 @@ const userOptions = ref<ChatUserBase[]>([]) | |
| const memberForm = reactive<{ userIds: string[] }>({ userIds: [] }) | ||
| const formRules: FormRules = { userIds: [{ required: true, message: '请选择对话用户', trigger: 'change' }] } | ||
|
|
||
| function open() { | ||
| visible.value = true | ||
| function loadUserOptions(keyword = '') { | ||
| optionsLoading.value = true | ||
| return ChatUserApi.getChatUser() | ||
| return ChatUserApi.getChatUser(keyword ? { nick_name: keyword } : undefined) | ||
| .then((users) => { | ||
| userOptions.value = users | ||
| const selectedUserIds = new Set(memberForm.userIds) | ||
| const selectedUserOptions = userOptions.value.filter(({ id }) => selectedUserIds.has(id)) | ||
| userOptions.value = [...new Map([...selectedUserOptions, ...users].map((user) => [user.id, user])).values()] | ||
| }) | ||
| .finally(() => { | ||
| optionsLoading.value = false | ||
| }) | ||
| } | ||
|
|
||
| function open() { | ||
| visible.value = true | ||
| return loadUserOptions() | ||
| } | ||
|
|
||
| function submit() { | ||
| const groupId = props.currentGroup?.id | ||
| if (!groupId) return | ||
|
|
@@ -64,7 +70,17 @@ defineExpose({ open }) | |
| <MkDialog v-model="visible" title="添加成员" @closed="resetData"> | ||
| <el-form ref="formRef" :model="memberForm" :rules="formRules" label-position="top" require-asterisk-position="right" @submit.prevent> | ||
| <el-form-item label="对话用户" prop="userIds"> | ||
| <el-select v-model="memberForm.userIds" class="w-full" filterable multiple :loading="optionsLoading" placeholder="请选择用户名或姓名"> | ||
| <el-select | ||
| v-model="memberForm.userIds" | ||
| class="w-full" | ||
| filterable | ||
| multiple | ||
| :loading="optionsLoading" | ||
| remote | ||
| :remote-method="loadUserOptions" | ||
| :reserve-keyword="false" | ||
| placeholder="请选择用户名或姓名" | ||
| > | ||
| <el-option v-for="user in userOptions" :key="user.id" :label="user.nick_name" :value="user.id" /> | ||
| </el-select> | ||
| </el-form-item> | ||
|
Contributor
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Here is a review of the provided code changes, focusing on logic, potential bugs, and optimization. 1. Race Condition in
|
||
|
|
||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The change is functionally reasonable, but there are several issues and improvements to consider:
Potential issues
Silent truncation to 200 records
query_set[:200]silently limits results.list()behavior and can break callers expecting all users.limit/offsetor page/page_size) and return metadata if needed.Case-sensitive / inconsistent nickname search
nick_name__containsis case-sensitive on PostgreSQL, but may behave differently on MySQL/SQLite depending on collation.nick_name__icontainsfor consistent case-insensitive matching.No input normalization or validation
if nick_name:skips empty string but not whitespace-only values.nick_namecan trigger an expensive search.Performance risk with
containsnick_name__containsusually generatesLIKE '%value%', which cannot use a normal B-tree index efficiently.istartswithif prefix search is acceptable,create_timeis indexed because oforder_by("-create_time").Non-deterministic ordering when
create_timevalues tiePossible N+1 queries
ChatUserInstanceSerializerincludes related fields, add appropriateselect_related()/prefetch_related().Minor style points
query_setis usually namedqueryset.limitto prevent abuse.Suggested revised version
Overall: the change works, but the hard-coded 200 limit and case-sensitive search are the main concerns. Add pagination, use
icontains, normalize input, and verify indexing/performance for nickname searches.