Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion client/sidebar/header/actions/CreateRoomList.js
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ import { useAtLeastOnePermission, usePermission } from '../../../contexts/Author
import { useSetting } from '../../../contexts/SettingsContext';
import { useSetModal } from '../../../contexts/ModalContext';
import CreateChannel from '../CreateChannel';
import CreateTeamModal from '../../../views/teams/modals/CreateTeamModal';
import CreateTeamModal from '../../../views/teams/CreateTeamModal';
import CreateRoomListItem from './CreateRoomListItem';

const CREATE_CHANNEL_PERMISSIONS = ['create-c', 'create-p'];
Expand Down
67 changes: 67 additions & 0 deletions client/views/hooks/useMembersList.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,67 @@
import { useCallback, useMemo, useState } from 'react';

import { getConfig } from '../../../app/ui-utils/client/config';
import { IUser } from '../../../definition/IUser';
import { useMethod } from '../../contexts/ServerContext';
import { useScrollableRecordList } from '../../hooks/lists/useScrollableRecordList';
import { useComponentDidUpdate } from '../../hooks/useComponentDidUpdate';
import { RecordList } from '../../lib/lists/RecordList';

type MembersListOptions = {
rid: string;
type: 'all' | 'autoJoin';
limit: number;
debouncedText: string;
}

export const useMembersList = (
options: MembersListOptions,
): {
membersList: RecordList<IUser>;
initialItemCount: number;
reload: () => void;
loadMoreItems: (start: number, end: number) => void;
} => {
const getUsersMethod = useMethod('getUsersOfRoom');
const [membersList, setMembersList] = useState(() => new RecordList<IUser>());
const reload = useCallback(() => setMembersList(new RecordList<IUser>()), []);

useComponentDidUpdate(() => {
options && reload();
}, [options, reload]);

const fetchData = useCallback(
async (start, end) => {
const { records, total } = await getUsersMethod(
options.rid,
options.type,
{
limit: end - start,
skip: start,
},
options.debouncedText,
);

return {
items: records.map((members: any) => {
members._updatedAt = new Date(members._updatedAt);
return members;
}),
itemCount: total,
};
},
[getUsersMethod, options],
);

const { loadMoreItems, initialItemCount } = useScrollableRecordList(membersList, fetchData, useMemo(() => {
const filesListSize = getConfig('teamsChannelListSize');
return filesListSize ? parseInt(filesListSize, 10) : undefined;
}, []));

return {
reload,
membersList,
loadMoreItems,
initialItemCount,
};
};
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
import React from 'react';
import { Box } from '@rocket.chat/fuselage';

import { useTranslation } from '../../../../contexts/TranslationContext';
import GenericModal from '../../../../components/GenericModal';
import TeamAutocomplete from '../../TeamAutocomplete';
import { useTranslation } from '../../../../../contexts/TranslationContext';
import GenericModal from '../../../../../components/GenericModal';
import TeamAutocomplete from '../../../../teams/contextualBar/TeamAutocomplete';


const StepOne = ({
Expand Down
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
import React from 'react';
import { Box } from '@rocket.chat/fuselage';

import { useTranslation } from '../../../../contexts/TranslationContext';
import GenericModal from '../../../../components/GenericModal';
import { useTranslation } from '../../../../../contexts/TranslationContext';
import GenericModal from '../../../../../components/GenericModal';

const StepTwo = ({
onClose,
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import React from 'react';

import GenericModal from '../../../components/GenericModal';
import { useTranslation } from '../../../contexts/TranslationContext';
import GenericModal from '../../../../components/GenericModal';
import { useTranslation } from '../../../../contexts/TranslationContext';

const ChannelToTeamModal = ({
onClose,
Expand Down
4 changes: 2 additions & 2 deletions client/views/room/contextualBar/Info/RoomInfo/RoomInfo.js
Original file line number Diff line number Diff line change
Expand Up @@ -16,8 +16,8 @@ import { RoomManager } from '../../../../../../app/ui-utils/client/lib/RoomManag
import { usePermission } from '../../../../../contexts/AuthorizationContext';
import WarningModal from '../../../../admin/apps/WarningModal';
import MarkdownText from '../../../../../components/MarkdownText';
import ChannelToTeamModal from '../../../../teams/modals/ChannelToTeamModal/ChannelToTeamModal';
import ConvertToTeamModal from '../../../../teams/modals/ConvertToTeamModal';
import ChannelToTeamModal from '../ChannelToTeamModal/ChannelToTeamModal';
import ConvertToTeamModal from '../ConvertToTeamModal';
import { useTabBarClose } from '../../../providers/ToolboxProvider';
import { useEndpointActionExperimental } from '../../../../../hooks/useEndpointAction';
import InfoPanel, { RetentionPolicyCallout } from '../../../../InfoPanel';
Expand Down
24 changes: 6 additions & 18 deletions client/views/room/contextualBar/RoomMembers/AddUsers/AddUsers.js
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import React, { useState } from 'react';
import React from 'react';
import { Field, Button } from '@rocket.chat/fuselage';
import { useMutableCallback } from '@rocket.chat/fuselage-hooks';

Expand All @@ -16,7 +16,6 @@ export const AddUsers = ({
onClickSave,
value,
onChange,
errors,
}) => {
const t = useTranslation();

Expand All @@ -30,10 +29,7 @@ export const AddUsers = ({
<VerticalBar.ScrollableContent>
<Field >
<Field.Label flexGrow={0}>{t('Choose_users')}</Field.Label>
<UserAutoCompleteMultiple errors={errors.users} value={value} onChange={onChange} placeholder={t('Choose_users')} />
{errors.users && <Field.Error>
{errors.users}
</Field.Error>}
<UserAutoCompleteMultiple value={value} onChange={onChange} placeholder={t('Choose_users')} />
</Field>
</VerticalBar.ScrollableContent>
<VerticalBar.Footer>
Expand All @@ -46,10 +42,10 @@ export const AddUsers = ({
export default ({
rid,
onClickBack,
reload,
}) => {
const t = useTranslation();
const dispatchToastMessage = useToastMessageDispatch();
const [errors, setErrors] = useState({});

const onClickClose = useTabBarClose();
const saveAction = useMethod('addUsersToRoom');
Expand All @@ -69,21 +65,14 @@ export default ({
});

const handleSave = useMutableCallback(async () => {
if (users.length < 1) {
return setErrors({
users: t('Select_at_least_one_user'),
});
}

try {
await saveAction({ rid, users });
dispatchToastMessage({ type: 'success', message: t('Users_added') });
onClickBack();
} catch (e) {
dispatchToastMessage({ type: 'error', message: e });
reload();
} catch ({ message }) {
dispatchToastMessage({ type: 'error', message });
}

setErrors({});
});

return (
Expand All @@ -93,7 +82,6 @@ export default ({
onClickSave={handleSave}
value={users}
onChange={onChangeUsers}
errors={errors}
/>
);
};
Original file line number Diff line number Diff line change
Expand Up @@ -23,14 +23,14 @@ export const InviteUsers = ({
const { copy } = useClipboardWithToast(linkText);

return (
<Box position='absolute' h='full' w='full'>
<>
<VerticalBar.Header>
{onClickBack && <VerticalBar.Back onClick={onClickBack} />}
<VerticalBar.Text>{t('Invite_Users')}</VerticalBar.Text>
{onClickClose && <VerticalBar.Close onClick={onClickClose} />}
</VerticalBar.Header>

<VerticalBar.Content>
<VerticalBar.ScrollableContent>
<Field>
<Field.Label flexGrow={0}>{t('Invite_Link')}</Field.Label>
<Field.Row>
Expand All @@ -45,8 +45,8 @@ export const InviteUsers = ({
<Box pb='x16'>
{onClickEdit && <Button onClick={onClickEdit}>{t('Edit_Invite')}</Button>}
</Box>
</VerticalBar.Content>
</Box>
</VerticalBar.ScrollableContent>
</>
);
};

Expand Down
48 changes: 21 additions & 27 deletions client/views/room/contextualBar/RoomMembers/List/RoomMembers.js
Original file line number Diff line number Diff line change
Expand Up @@ -22,23 +22,23 @@ import memoize from 'memoize-one';
import { useTranslation } from '../../../../../contexts/TranslationContext';
import { useUserRoom } from '../../../../../contexts/UserContext';
import VerticalBar from '../../../../../components/VerticalBar';
import { useMethod } from '../../../../../contexts/ServerContext';
import { AsyncStatePhase } from '../../../../../hooks/useAsyncState';
import { useAtLeastOnePermission } from '../../../../../contexts/AuthorizationContext';
import { useDataWithLoadMore } from '../../hooks/useDataWithLoadMore';
import { MemberItem } from './components/MemberItem';
import UserInfoWithData from '../../UserInfo';
import InviteUsers from '../InviteUsers/InviteUsers';
import AddUsers from '../AddUsers/AddUsers';
import { useTabBarClose } from '../../../providers/ToolboxProvider';
import ScrollableContentWrapper from '../../../../../components/ScrollableContentWrapper';
import { useMembersList } from '../../../../hooks/useMembersList';
import { useRecordList } from '../../../../../hooks/lists/useRecordList';

export const createItemData = memoize((onClickView, rid) => ({
onClickView,
rid,
}));

const DefaultRow = React.memo(({ user, data, index }) => {
const DefaultRow = React.memo(({ user, data, index, reload }) => {
const { onClickView, rid } = data;

if (!user) {
Expand All @@ -53,6 +53,7 @@ const DefaultRow = React.memo(({ user, data, index }) => {
status={user.status}
name={user.name}
onClickView={onClickView}
reload={reload}
/>;
});

Expand All @@ -72,6 +73,7 @@ export const RoomMembers = ({
loadMoreItems,
renderRow: Row = DefaultRow,
rid,
reload,
}) => {
const t = useTranslation();
const inputRef = useAutoFocus(true);
Expand All @@ -82,7 +84,7 @@ export const RoomMembers = ({
], [t]);

const itemData = createItemData(onClickView, rid);
const lm = useMutableCallback((start) => loadMoreItems(start + 1, Math.min(50, start + 1 - members.length)));
const lm = useMutableCallback((start) => !loading && loadMoreItems(start));

return (
<>
Expand All @@ -107,15 +109,16 @@ export const RoomMembers = ({
</Box>
</Box>

{ error && <Box pi='x24' pb='x12'><Callout type='danger'>
{error}
</Callout></Box> }

{loading && <Box pi='x24' pb='x12'><Throbber size='x12' /></Box>}

{error && <Box pi='x24' pb='x12'><Callout type='danger'>
{error.message}
</Callout></Box>}

{!loading && members.length <= 0 && <Box pi='x24' pb='x12'>{t('No_results_found')}</Box>}

{!loading && members.length > 0 && (
<Box pi='x24' pb='x12'>
<Box pi='x18' pb='x12'>
<Box is='span' color='info' fontScale='p1'>
{t('Showing')}: <Box is='span' color='default' fontScale='p2'>{members.length}</Box>
</Box>
Expand Down Expand Up @@ -145,6 +148,7 @@ export const RoomMembers = ({
data={itemData}
user={data}
index={index}
reload={reload}
/>}
/>}
</Box>
Expand All @@ -162,11 +166,6 @@ export const RoomMembers = ({

RoomMembers.Option = MemberItem;

const useGetUsersOfRoom = (params) => {
const method = useMethod('getUsersOfRoom');
return useDataWithLoadMore(useCallback((args) => method(...args), [method]), params);
};

export default ({
rid,
}) => {
Expand All @@ -179,10 +178,11 @@ export default ({
const [type, setType] = useLocalStorage('members-list-type', 'online');
const [text, setText] = useState('');

const debouncedText = useDebouncedValue(text, 500);
const params = useMemo(() => [rid, type === 'all', { limit: 50 }, debouncedText], [rid, type, debouncedText]);
const debouncedText = useDebouncedValue(text, 800);

const { membersList, loadMoreItems, reload } = useMembersList(useMemo(() => ({ rid, type: type === 'all', limit: 50, debouncedText }), [rid, type, debouncedText]));

const { value, phase, more, error } = useGetUsersOfRoom(params);
const { phase, items, itemCount: total } = useRecordList(membersList);

const canAddUsers = useAtLeastOnePermission(useMemo(() => [room.t === 'p' ? 'add-user-to-any-p-room' : 'add-user-to-any-c-room', 'add-user-to-joined-room'], [room.t]), rid);

Expand All @@ -208,12 +208,6 @@ export default ({

const handleBack = useCallback(() => setState({}), [setState]);

const loadMoreItems = useCallback((start, end) => more(([rid, type, , filter]) => [rid, type, { skip: start, limit: end - start }, filter], (prev, next) => ({
total: next.total,
finished: next.records.length < 50,
records: [...prev.records, ...next.records],
})), [more]);

if (state.tab === 'UserInfo') {
return <UserInfoWithData rid={rid} onClickClose={onClickClose} onClickBack={handleBack} username={state.username} />;
}
Expand All @@ -223,7 +217,7 @@ export default ({
}

if (state.tab === 'AddUsers') {
return <AddUsers onClickClose={onClickClose} rid={rid} onClickBack={handleBack} />;
return <AddUsers onClickClose={onClickClose} rid={rid} onClickBack={handleBack} reload={reload} />;
}

return (
Expand All @@ -232,16 +226,16 @@ export default ({
loading={phase === AsyncStatePhase.LOADING}
type={type}
text={text}
error={error}
setType={setType}
setText={handleTextChange}
members={value?.records}
total={value?.total}
members={items}
total={total}
onClickClose={onClickClose}
onClickView={viewUser}
onClickAdd={canAddUsers && addUser}
onClickInvite={canAddUsers && createInvite}
loadMoreItems={loadMoreItems}
reload={reload}
/>
);
};
Loading