diff --git a/client/packages/lowcoder/src/pages/setting/permission/groupUsersPermission.tsx b/client/packages/lowcoder/src/pages/setting/permission/groupUsersPermission.tsx index c8270eeb4d..1ce0155300 100644 --- a/client/packages/lowcoder/src/pages/setting/permission/groupUsersPermission.tsx +++ b/client/packages/lowcoder/src/pages/setting/permission/groupUsersPermission.tsx @@ -1,9 +1,9 @@ import { GroupRoleInfo, GroupUser, OrgGroup, TacoRoles } from "constants/orgConstants"; import { User } from "constants/userConstants"; -import { AddIcon, ArrowIcon, CustomSelect, PackUpIcon, SuperUserIcon } from "lowcoder-design"; +import { AddIcon, ArrowIcon, CustomSelect, PackUpIcon, Search, SuperUserIcon } from "lowcoder-design"; import { trans } from "i18n"; import ProfileImage from "pages/common/profileImage"; -import React, { useMemo } from "react"; +import React, { useCallback, useEffect, useMemo, useState } from "react"; import { useDispatch } from "react-redux"; import { deleteGroupUserAction, @@ -20,7 +20,6 @@ import { GroupNameView, HeaderBack, LAST_ADMIN_QUIT, - PermissionHeaderWrapper, QuestionTooltip, RoleSelectSubTitle, RoleSelectTitle, @@ -31,6 +30,8 @@ import { import history from "util/history"; import { PERMISSION_SETTING } from "constants/routesURL"; import Column from "antd/es/table/Column"; +import { debounce } from "lodash"; +import { fetchGroupUsrPagination } from "@lowcoder-ee/util/pagination/axios"; const StyledAddIcon = styled(AddIcon)` g path { @@ -38,6 +39,26 @@ const StyledAddIcon = styled(AddIcon)` } `; +const PermissionHeaderWrapper = styled.div` + display: flex; + align-items: center; + justify-content: space-between; + width: 100%; + margin-bottom: 16px; +`; + +const OptionsHeader = styled.div` + display: flex; + align-items: center; + gap: 12px; +`; + +type ElementsState = { + elements: any[]; + total: number; + role: string; +}; + type GroupPermissionProp = { group: OrgGroup; orgId: string; @@ -47,11 +68,24 @@ type GroupPermissionProp = { setModify?: any; modify?: boolean; loading?: boolean; + setElements: React.Dispatch>; }; -function GroupUsersPermission(props: GroupPermissionProp) { - // const { Column } = TableStyled; - const { group, orgId, groupUsers, currentUserGroupRole, currentUser, setModify, modify, loading } = props; +const GroupUsersPermission: React.FC = (props) => { + const { + group, + orgId, + groupUsers, + currentUserGroupRole, + currentUser, + setModify, + modify, + loading, + setElements + } = props; + const [searchValue, setSearchValue] = useState("") + const dispatch = useDispatch(); + const adminCount = groupUsers.filter((user) => isGroupAdmin(user.role)).length; const sortedGroupUsers = useMemo(() => { return [...groupUsers].sort((a, b) => { @@ -64,7 +98,31 @@ function GroupUsersPermission(props: GroupPermissionProp) { } }); }, [groupUsers]); - const dispatch = useDispatch(); + + const debouncedFetchPotentialMembers = useCallback( + debounce((searchVal: string) => { + fetchGroupUsrPagination({groupId: group.groupId, search: searchVal}) + .then(result => { + if (result.success) { + setElements({ + elements: result.data || [], + total: result.total || 0, + role: result.visitorRole || "" + }); + } + }) + }, 500), [dispatch] + ); + + useEffect(() => { + if (searchValue.length > 2 || searchValue === "") { + debouncedFetchPotentialMembers(searchValue); + } + return () => { + debouncedFetchPotentialMembers.cancel(); + }; + }, [searchValue, debouncedFetchPotentialMembers]); + return ( <> @@ -78,19 +136,31 @@ function GroupUsersPermission(props: GroupPermissionProp) { )} {isGroupAdmin(currentUserGroupRole) && !group.syncGroup && ( - }> - {trans("memberSettings.addMember")} - - } - style={{ marginLeft: "auto" }} - /> + + setSearchValue(e.target.value)} + style={{ + width: "20%", + minWidth: "160px", + height: "32px", + marginTop: 'auto' + }} + /> + }> + {trans("memberSettings.addMember")} + + } + /> + )} ({ elements: [], total: 0, role: "" }); - const [group, setGrouop] = useState(); - const [orgMemberElements, setOrgMemberElements] = useState({ elements: [], total: 0 }) + const [group, setGroup] = useState(); const [currentPage, setCurrentPage] = useState(1); const [pageSize, setPageSize] = useState(10); const [modify, setModify] = useState(false); @@ -44,7 +47,11 @@ export default function PermissionSetting(props: {currentPageProp: number, pageS } ).then(result => { if (result.success && !!result.data){ - setGrouop(result.data.find(group => group.groupId === selectKey)) + if(selectKey === GroupUserKey.USERS) { + setGroup(result.data.find(group => group.groupName == GroupUserKey.ALL_USERS)) + } else { + setGroup(result.data.find(group => group.groupId === selectKey)) + } } else console.error("ERROR: fetchFolderElements", result.error) @@ -53,13 +60,13 @@ export default function PermissionSetting(props: {currentPageProp: number, pageS ) useEffect( () => { - if (selectKey !== "users" && selectKey) { + if (selectKey && group) { setLoading(true); setError(null); fetchGroupUsrPagination( { - groupId: selectKey, + groupId: selectKey === GroupUserKey.USERS ? group.groupId : selectKey, pageNum: currentPage, pageSize: pageSize, } @@ -79,33 +86,8 @@ export default function PermissionSetting(props: {currentPageProp: number, pageS setLoading(false); setError("Failed to load group users. Please try again."); }); - } else { - setLoading(true); - setError(null); - - fetchOrgUsrPagination( - { - orgId: orgId, - pageNum: currentPage, - pageSize: pageSize, - } - ).then(result => { - setLoading(false); - if (result.success){ - setOrgMemberElements({ - elements: result.data || [], - total: result.total || 0 - }); - } - else { - setError("Failed to load organization users. Please try again."); - } - }).catch(err => { - setLoading(false); - setError("Failed to load organization users. Please try again."); - }); - } - }, [currentPage, pageSize, modify, selectKey, orgId]); + } + }, [currentPage, pageSize, modify, selectKey, orgId, group]); if (!orgId) { return null; @@ -118,36 +100,23 @@ export default function PermissionSetting(props: {currentPageProp: number, pageS {error} )} - - {selectKey === "users" ? ( + {elements && + group && ( <> - - + - ) : ( - group && ( - <> - - - - ) - )} + )} ); } \ No newline at end of file diff --git a/client/packages/lowcoder/src/util/pagination/type.ts b/client/packages/lowcoder/src/util/pagination/type.ts index 3c449b7e11..870b35f0d9 100644 --- a/client/packages/lowcoder/src/util/pagination/type.ts +++ b/client/packages/lowcoder/src/util/pagination/type.ts @@ -87,6 +87,7 @@ export interface fetchGroupUserRequestType { groupId: string; pageNum?: number; pageSize?: number; + search?: string } export interface fetchQueryLibraryPaginationRequestType {