diff --git a/shared/model/group.ts b/shared/model/group.ts index 7ddae357..807dfcdf 100644 --- a/shared/model/group.ts +++ b/shared/model/group.ts @@ -21,6 +21,18 @@ export interface GroupPanel { meta?: Record; } +export interface GroupRole { + _id: string; + /** + * 权限组名 + */ + name: string; + /** + * 拥有的权限, 是一段字符串 + */ + permissions: string[]; +} + export interface GroupInfo { _id: string; name: string; @@ -28,6 +40,7 @@ export interface GroupInfo { owner: string; members: GroupMember[]; panels: GroupPanel[]; + roles: GroupRole[]; pinnedPanelId?: string; // 被钉选的面板Id } diff --git a/web/src/components/modals/GroupDetail/Role/PermissionItem.tsx b/web/src/components/modals/GroupDetail/Role/PermissionItem.tsx index cd8d1820..25973767 100644 --- a/web/src/components/modals/GroupDetail/Role/PermissionItem.tsx +++ b/web/src/components/modals/GroupDetail/Role/PermissionItem.tsx @@ -4,6 +4,8 @@ import React from 'react'; interface PermissionItemProps { title: string; desc?: string; + checked: boolean; + onChange: (checked: boolean) => void; } export const PermissionItem: React.FC = React.memo( @@ -16,7 +18,7 @@ export const PermissionItem: React.FC = React.memo( - + diff --git a/web/src/components/modals/GroupDetail/Role/RoleItem.tsx b/web/src/components/modals/GroupDetail/Role/RoleItem.tsx index 95fffb3f..0c6ad761 100644 --- a/web/src/components/modals/GroupDetail/Role/RoleItem.tsx +++ b/web/src/components/modals/GroupDetail/Role/RoleItem.tsx @@ -3,6 +3,7 @@ import React from 'react'; export const RoleItem: React.FC<{ active: boolean; + onClick?: () => void; }> = React.memo((props) => { return (
{props.children}
diff --git a/web/src/components/modals/GroupDetail/Role/index.tsx b/web/src/components/modals/GroupDetail/Role/index.tsx index bfb68708..5838b848 100644 --- a/web/src/components/modals/GroupDetail/Role/index.tsx +++ b/web/src/components/modals/GroupDetail/Role/index.tsx @@ -1,20 +1,36 @@ +import { + DefaultFullModalInputEditorRender, + FullModalField, +} from '@/components/FullModal/Field'; import { IconBtn } from '@/components/IconBtn'; import { PillTabPane, PillTabs } from '@/components/PillTabs'; import { UserListItem } from '@/components/UserListItem'; import { Button, Input } from 'antd'; -import React, { useCallback } from 'react'; +import React, { useCallback, useMemo, useState } from 'react'; import { Icon } from 'tailchat-design'; import { t, useGroupInfo, useSearch, useUserInfoList } from 'tailchat-shared'; import { PermissionItem } from './PermissionItem'; import { RoleItem } from './RoleItem'; +import { useModifyPermission } from './useModifyPermission'; + +const permissionList = [ + { + key: 'core.message', + title: t('发送消息'), + desc: t('允许成员在文字频道发送消息'), + default: true, + }, +]; interface GroupPermissionProps { groupId: string; } export const GroupRole: React.FC = React.memo((props) => { const { groupId } = props; + const [roleId, setRoleId] = useState(''); const groupInfo = useGroupInfo(groupId); - const members = groupInfo?.members ?? []; + const roles = groupInfo?.roles ?? []; + const members = (groupInfo?.members ?? []).filter((m) => m.role === roleId); const userInfoList = useUserInfoList(members.map((m) => m.userId)); const { searchText, @@ -25,28 +41,91 @@ export const GroupRole: React.FC = React.memo((props) => { dataSource: userInfoList, filterFn: (item, searchText) => item.nickname.includes(searchText), }); + const currentRoleInfo = useMemo( + () => roles.find((r) => r._id === roleId), + [roleId] + ); + const currentRolePermissions = useMemo( + () => currentRoleInfo?.permissions ?? [], + [roleId] + ); + + const { isEditing, editingPermission, handleSwitchPermission } = + useModifyPermission(currentRolePermissions); const handleAddMember = useCallback(() => {}, []); + const handleResetPermission = useCallback(() => {}, []); + + const handleSavePermission = useCallback(() => {}, []); + + const handleChangeRoleName = useCallback((text) => { + console.log('text', text); + }, []); + return (
{/* 角色列表 */} - {t('所有人')} + setRoleId('')}> + {t('所有人')} + + + {roles.map((r) => ( + setRoleId(r._id)} + > + {r.name} + + ))} {t('添加角色')}
+ + {/* 权限概述 */} + {currentRoleInfo && ( +
+ +
+ )} +
+
+ + +
+ {/* 权限详情 */} - + {permissionList.map((p) => ( + handleSwitchPermission(p.key, checked)} + /> + ))}
- + {/* 管理成员 */}
([]); + const isEditing = useMemo( + () => _isEqual(new Set(originPermission), new Set(editingPermission)), + [originPermission, editingPermission] + ); + + useEffect(() => { + setEditingPermission([...originPermission]); + }, [originPermission]); + + const handleSwitchPermission = useCallback( + (permissionKey: string, enabled: boolean) => { + if (enabled) { + setEditingPermission(_uniq([...editingPermission, permissionKey])); + } else { + setEditingPermission(_without(editingPermission, permissionKey)); + } + }, + [editingPermission] + ); + + return { isEditing, editingPermission, handleSwitchPermission }; +}