Skip to content

Commit

Permalink
feat(WebexParticipantRoster): add participant roster component
Browse files Browse the repository at this point in the history
  • Loading branch information
smiller3 authored and lalli-flores committed Jul 1, 2020
1 parent 69d46d5 commit d53a34e
Show file tree
Hide file tree
Showing 7 changed files with 129 additions and 0 deletions.
25 changes: 25 additions & 0 deletions src/components/WebexParticipantRoster/WebexParticipantRoster.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
import React from 'react';
import PropTypes from 'prop-types';
import {List} from '@momentum-ui/react';

import WebexParticipant from '../WebexParticipant/WebexParticipant';
import useParticipants from '../hooks/useParticipants';

/**
* Displays the roster of Webex meeting or room participants.
*
* @param {string} props.location the roster of Webex meeting or room participants.
*
* @returns {object} JSX of the component
*/
export default function WebexParticipantRoster({destination}) {
const participants = useParticipants(destination);

const participantList = participants.map((participant) => <WebexParticipant personID={participant.personID} />);

return <List>{participantList}</List>;
}

WebexParticipantRoster.propTypes = {
destination: PropTypes.string.isRequired,
};
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
import React from 'react';
import {storiesOf} from '@storybook/react';

import jsonData from '../../data';
import {WebexJSONAdapter} from '../../adapters';

import WebexParticipantRoster from './WebexParticipantRoster';

import {WebexDataProvider} from '..';

// Setup for the stories
const stories = storiesOf('Webex Participant Roster', module);
const webexAdapter = new WebexJSONAdapter(jsonData);

// Stories
stories.add('default', () => (
<WebexDataProvider adapter={webexAdapter}>
<WebexParticipantRoster destination="default_membership" />
</WebexDataProvider>
));
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
import React from 'react';

import WebexParticipantRoster from './WebexParticipantRoster';

jest.mock('../hooks/usePerson');

describe('Webex Participant Roster component', () => {
describe('snapshot', () => {
test('matches snapshot of webex participant roster', () => {
expect(shallow(<WebexParticipantRoster destination="default_membership" />)).toMatchSnapshot();
});
});
});
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
// Jest Snapshot v1, https://goo.gl/fbAQLP

exports[`Webex Participant Roster component snapshot matches snapshot of webex participant roster 1`] = `
<List
active={null}
className=""
focus={null}
focusFirst={true}
focusFirstQuery=""
focusQuery=""
id={null}
itemRole="listitem"
onSelect={null}
role="list"
shouldFocusActive={false}
shouldFocusInitial={true}
shouldLoop={true}
tabType="vertical"
trackActive={true}
type={null}
wrap={false}
/>
`;
12 changes: 12 additions & 0 deletions src/components/hooks/__mocks__/useParticipants.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
import {useContext} from 'react';

export default function useParticipants(membershipID) {
const datasource = useContext();
let participants = {...datasource.membershipsAdapter[membershipID]};

if (!(membershipID in datasource.membershipsAdapter)) {
participants = [];
}

return participants;
}
34 changes: 34 additions & 0 deletions src/components/hooks/useParticipants.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
import {useEffect, useContext, useState} from 'react';

import {AdapterContext} from '../../components/';

/**
* Custom hook that returns a list of participant IDs given a membership ID.
*
* @param {string} membershipID ID of the room/meeting that contains the participants
* @returns {Array.<Person>} List of the person IDs from the participants
*/
export default function useParticipants(membershipID) {
const [participants, setParticipants] = useState([]);
const {membershipsAdapter} = useContext(AdapterContext);

useEffect(() => {
const onError = (error) => {
setParticipants([]);

// eslint-disable-next-line no-console
console.error(error.message);
};
const onMembers = (data) => {
setParticipants(data.members);
};

const subscription = membershipsAdapter.getMembers(membershipID).subscribe(onMembers, onError);

return () => {
subscription.unsubscribe();
};
}, [membershipsAdapter, membershipID]);

return participants;
}
2 changes: 2 additions & 0 deletions src/components/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -10,3 +10,5 @@ export {default as WebexMeetingControl} from './WebexMeetingControl/WebexMeeting
export {default as WebexMeetingControls, MeetingContext} from './WebexMeetingControl/WebexMeetingControls';
export {default as WebexMeetingInfo} from './WebexMeetingInfo/WebexMeetingInfo';
export {default as WebexRemoteMedia} from './WebexRemoteMedia/WebexRemoteMedia';
export {default as WebexParticipant} from './WebexParticipant/WebexParticipant';
export {default as WebexParticipantRoster} from './WebexParticipantRoster/WebexParticipantRoster';

0 comments on commit d53a34e

Please sign in to comment.