@webex/plugin-meetings 3.0.0-beta.57 → 3.0.0-beta.59
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/breakouts/breakout.js +1 -1
- package/dist/breakouts/index.js +1 -1
- package/dist/constants.js +2 -0
- package/dist/constants.js.map +1 -1
- package/dist/meeting/in-meeting-actions.js +6 -0
- package/dist/meeting/in-meeting-actions.js.map +1 -1
- package/dist/meeting/index.js +1 -0
- package/dist/meeting/index.js.map +1 -1
- package/dist/meeting/util.js +3 -0
- package/dist/meeting/util.js.map +1 -1
- package/dist/meetings/index.js +3 -0
- package/dist/meetings/index.js.map +1 -1
- package/dist/meetings/request.js +2 -0
- package/dist/meetings/request.js.map +1 -1
- package/dist/member/index.js +23 -0
- package/dist/member/index.js.map +1 -1
- package/dist/member/types.js +15 -0
- package/dist/member/types.js.map +1 -0
- package/dist/member/util.js +61 -2
- package/dist/member/util.js.map +1 -1
- package/dist/members/index.js +21 -0
- package/dist/members/index.js.map +1 -1
- package/dist/members/request.js +19 -0
- package/dist/members/request.js.map +1 -1
- package/dist/members/types.js +15 -0
- package/dist/members/types.js.map +1 -0
- package/dist/members/util.js +38 -0
- package/dist/members/util.js.map +1 -1
- package/dist/reconnection-manager/index.js +2 -2
- package/dist/reconnection-manager/index.js.map +1 -1
- package/dist/types/constants.d.ts +2 -0
- package/dist/types/meeting/in-meeting-actions.d.ts +6 -0
- package/dist/types/member/index.d.ts +10 -0
- package/dist/types/member/types.d.ts +21 -0
- package/dist/types/members/index.d.ts +10 -0
- package/dist/types/members/request.d.ts +8 -0
- package/dist/types/members/types.d.ts +24 -0
- package/package.json +18 -18
- package/src/constants.ts +2 -0
- package/src/meeting/in-meeting-actions.ts +12 -0
- package/src/meeting/index.ts +3 -0
- package/src/meeting/util.ts +3 -0
- package/src/meetings/index.ts +31 -23
- package/src/meetings/request.ts +2 -0
- package/src/member/index.ts +22 -0
- package/src/member/types.ts +24 -0
- package/src/member/util.ts +53 -0
- package/src/members/index.ts +27 -0
- package/src/members/request.ts +20 -0
- package/src/members/types.ts +28 -0
- package/src/members/util.ts +39 -1
- package/src/reconnection-manager/index.ts +2 -2
- package/test/unit/spec/meeting/in-meeting-actions.ts +6 -0
- package/test/unit/spec/meeting/utils.js +1 -0
- package/test/unit/spec/member/index.js +24 -0
- package/test/unit/spec/member/util.js +336 -33
- package/test/unit/spec/members/index.js +77 -0
- package/test/unit/spec/members/request.js +21 -0
- package/test/unit/spec/members/utils.js +28 -0
|
@@ -20,6 +20,8 @@ interface IInMeetingActions {
|
|
|
20
20
|
canSetMuted?: boolean;
|
|
21
21
|
canUnsetMuted?: boolean;
|
|
22
22
|
canAssignHost?: boolean;
|
|
23
|
+
canSetPresenter?: boolean;
|
|
24
|
+
canUnsetPresenter?: boolean;
|
|
23
25
|
canStartRecording?: boolean;
|
|
24
26
|
canPauseRecording?: boolean;
|
|
25
27
|
canResumeRecording?: boolean;
|
|
@@ -32,6 +34,7 @@ interface IInMeetingActions {
|
|
|
32
34
|
canStartTranscribing?: boolean;
|
|
33
35
|
canStopTranscribing?: boolean;
|
|
34
36
|
isClosedCaptionActive?: boolean;
|
|
37
|
+
isSaveTranscriptsEnabled?: boolean;
|
|
35
38
|
isWebexAssistantActive?: boolean;
|
|
36
39
|
canViewCaptionPanel?: boolean;
|
|
37
40
|
isRealTimeTranslationEnabled?: boolean;
|
|
@@ -71,6 +74,10 @@ export default class InMeetingActions implements IInMeetingActions {
|
|
|
71
74
|
|
|
72
75
|
canSetMuteOnEntry = null;
|
|
73
76
|
|
|
77
|
+
canSetPresenter = null;
|
|
78
|
+
|
|
79
|
+
canUnsetPresenter = null;
|
|
80
|
+
|
|
74
81
|
canUnsetMuteOnEntry = null;
|
|
75
82
|
|
|
76
83
|
canSetDisallowUnmute = null;
|
|
@@ -97,6 +104,8 @@ export default class InMeetingActions implements IInMeetingActions {
|
|
|
97
104
|
|
|
98
105
|
isClosedCaptionActive = null;
|
|
99
106
|
|
|
107
|
+
isSaveTranscriptsEnabled = null;
|
|
108
|
+
|
|
100
109
|
isWebexAssistantActive = null;
|
|
101
110
|
|
|
102
111
|
canViewCaptionPanel = null;
|
|
@@ -134,6 +143,8 @@ export default class InMeetingActions implements IInMeetingActions {
|
|
|
134
143
|
canSetDisallowUnmute: this.canSetDisallowUnmute,
|
|
135
144
|
canSetMuted: this.canSetMuted,
|
|
136
145
|
canUnsetMuted: this.canUnsetMuted,
|
|
146
|
+
canSetPresenter: this.canSetPresenter,
|
|
147
|
+
canUnsetPresenter: this.canUnsetPresenter,
|
|
137
148
|
canUnsetDisallowUnmute: this.canUnsetDisallowUnmute,
|
|
138
149
|
canStartRecording: this.canStartRecording,
|
|
139
150
|
canPauseRecording: this.canPauseRecording,
|
|
@@ -147,6 +158,7 @@ export default class InMeetingActions implements IInMeetingActions {
|
|
|
147
158
|
canStartTranscribing: this.canStartTranscribing,
|
|
148
159
|
canStopTranscribing: this.canStopTranscribing,
|
|
149
160
|
isClosedCaptionActive: this.isClosedCaptionActive,
|
|
161
|
+
isSaveTranscriptsEnabled: this.isSaveTranscriptsEnabled,
|
|
150
162
|
isWebexAssistantActive: this.isWebexAssistantActive,
|
|
151
163
|
canViewCaptionPanel: this.canViewCaptionPanel,
|
|
152
164
|
isRealTimeTranslationEnabled: this.isRealTimeTranslationEnabled,
|
package/src/meeting/index.ts
CHANGED
|
@@ -2307,6 +2307,9 @@ export default class Meeting extends StatelessWebexPlugin {
|
|
|
2307
2307
|
canStartTranscribing: MeetingUtil.canStartTranscribing(payload.info.userDisplayHints),
|
|
2308
2308
|
canStopTranscribing: MeetingUtil.canStopTranscribing(payload.info.userDisplayHints),
|
|
2309
2309
|
isClosedCaptionActive: MeetingUtil.isClosedCaptionActive(payload.info.userDisplayHints),
|
|
2310
|
+
isSaveTranscriptsEnabled: MeetingUtil.isSaveTranscriptsEnabled(
|
|
2311
|
+
payload.info.userDisplayHints
|
|
2312
|
+
),
|
|
2310
2313
|
isWebexAssistantActive: MeetingUtil.isWebexAssistantActive(payload.info.userDisplayHints),
|
|
2311
2314
|
canViewCaptionPanel: MeetingUtil.canViewCaptionPanel(payload.info.userDisplayHints),
|
|
2312
2315
|
isRealTimeTranslationEnabled: MeetingUtil.isRealTimeTranslationEnabled(
|
package/src/meeting/util.ts
CHANGED
|
@@ -470,6 +470,9 @@ MeetingUtil.endMeetingForAll = (meeting) => {
|
|
|
470
470
|
MeetingUtil.canEnableClosedCaption = (displayHints) =>
|
|
471
471
|
displayHints.includes(DISPLAY_HINTS.CAPTION_START);
|
|
472
472
|
|
|
473
|
+
MeetingUtil.isSaveTranscriptsEnabled = (displayHints) =>
|
|
474
|
+
displayHints.includes(DISPLAY_HINTS.SAVE_TRANSCRIPTS_ENABLED);
|
|
475
|
+
|
|
473
476
|
MeetingUtil.canStartTranscribing = (displayHints) =>
|
|
474
477
|
displayHints.includes(DISPLAY_HINTS.TRANSCRIPTION_CONTROL_START);
|
|
475
478
|
|
package/src/meetings/index.ts
CHANGED
|
@@ -1108,33 +1108,41 @@ export default class Meetings extends WebexPlugin {
|
|
|
1108
1108
|
* @memberof Meetings
|
|
1109
1109
|
*/
|
|
1110
1110
|
public syncMeetings() {
|
|
1111
|
-
return this.request
|
|
1112
|
-
|
|
1113
|
-
|
|
1114
|
-
|
|
1115
|
-
|
|
1116
|
-
|
|
1117
|
-
|
|
1118
|
-
locus
|
|
1119
|
-
|
|
1111
|
+
return this.request
|
|
1112
|
+
.getActiveMeetings()
|
|
1113
|
+
.then((locusArray) => {
|
|
1114
|
+
const activeLocusUrl = [];
|
|
1115
|
+
|
|
1116
|
+
if (locusArray?.loci && locusArray.loci.length > 0) {
|
|
1117
|
+
locusArray.loci.forEach((locus) => {
|
|
1118
|
+
activeLocusUrl.push(locus.url);
|
|
1119
|
+
this.handleLocusEvent({
|
|
1120
|
+
locus,
|
|
1121
|
+
locusUrl: locus.url,
|
|
1122
|
+
});
|
|
1120
1123
|
});
|
|
1121
|
-
}
|
|
1122
|
-
|
|
1123
|
-
|
|
1124
|
-
|
|
1125
|
-
|
|
1126
|
-
|
|
1127
|
-
|
|
1128
|
-
for (const meeting of Object.values(meetingsCollection)) {
|
|
1129
|
-
// @ts-ignore
|
|
1130
|
-
if (!activeLocusUrl.includes(meeting.locusUrl)) {
|
|
1131
|
-
// destroy function also uploads logs
|
|
1124
|
+
}
|
|
1125
|
+
const meetingsCollection = this.meetingCollection.getAll();
|
|
1126
|
+
|
|
1127
|
+
if (Object.keys(meetingsCollection).length > 0) {
|
|
1128
|
+
// Some time the mercury event is missed after mercury reconnect
|
|
1129
|
+
// if sync returns no locus then clear all the meetings
|
|
1130
|
+
for (const meeting of Object.values(meetingsCollection)) {
|
|
1132
1131
|
// @ts-ignore
|
|
1133
|
-
|
|
1132
|
+
if (!activeLocusUrl.includes(meeting.locusUrl)) {
|
|
1133
|
+
// destroy function also uploads logs
|
|
1134
|
+
// @ts-ignore
|
|
1135
|
+
this.destroy(meeting, MEETING_REMOVED_REASON.NO_MEETINGS_TO_SYNC);
|
|
1136
|
+
}
|
|
1134
1137
|
}
|
|
1135
1138
|
}
|
|
1136
|
-
}
|
|
1137
|
-
|
|
1139
|
+
})
|
|
1140
|
+
.catch((error) => {
|
|
1141
|
+
LoggerProxy.logger.error(
|
|
1142
|
+
`Meetings:index#syncMeetings --> failed to sync meetings, ${error}`
|
|
1143
|
+
);
|
|
1144
|
+
throw new Error(error);
|
|
1145
|
+
});
|
|
1138
1146
|
}
|
|
1139
1147
|
|
|
1140
1148
|
/**
|
package/src/meetings/request.ts
CHANGED
|
@@ -23,6 +23,7 @@ export default class MeetingRequest extends StatelessWebexPlugin {
|
|
|
23
23
|
LoggerProxy.logger.error(
|
|
24
24
|
`Meetings:request#getActiveMeetings --> failed to get locus details, ${error}`
|
|
25
25
|
);
|
|
26
|
+
throw new Error(error);
|
|
26
27
|
});
|
|
27
28
|
}
|
|
28
29
|
|
|
@@ -71,6 +72,7 @@ export default class MeetingRequest extends StatelessWebexPlugin {
|
|
|
71
72
|
LoggerProxy.logger.error(
|
|
72
73
|
`Meetings:request#determineRedirections --> failed to get locus details from url: ${url}, reason: ${error}`
|
|
73
74
|
);
|
|
75
|
+
throw new Error(error);
|
|
74
76
|
})
|
|
75
77
|
)
|
|
76
78
|
).then(() => Promise.resolve(responseBody));
|
package/src/member/index.ts
CHANGED
|
@@ -2,6 +2,7 @@
|
|
|
2
2
|
* Copyright (c) 2015-2020 Cisco Systems, Inc. See LICENSE file.
|
|
3
3
|
*/
|
|
4
4
|
import {MEETINGS, _IN_LOBBY_, _NOT_IN_MEETING_, _IN_MEETING_} from '../constants';
|
|
5
|
+
import {IExternalRoles, ParticipantWithRoles} from './types';
|
|
5
6
|
|
|
6
7
|
import MemberUtil from './util';
|
|
7
8
|
|
|
@@ -28,6 +29,7 @@ export default class Member {
|
|
|
28
29
|
isSelf: any;
|
|
29
30
|
isUser: any;
|
|
30
31
|
isVideoMuted: any;
|
|
32
|
+
roles: IExternalRoles;
|
|
31
33
|
name: any;
|
|
32
34
|
participant: any;
|
|
33
35
|
status: any;
|
|
@@ -228,6 +230,14 @@ export default class Member {
|
|
|
228
230
|
* @memberof Member
|
|
229
231
|
*/
|
|
230
232
|
this.isModeratorAssignmentProhibited = null;
|
|
233
|
+
|
|
234
|
+
/**
|
|
235
|
+
* @instance
|
|
236
|
+
* @type {IExternalRoles}
|
|
237
|
+
* @public
|
|
238
|
+
* @memberof Member
|
|
239
|
+
*/
|
|
240
|
+
this.roles = null;
|
|
231
241
|
// TODO: more participant types
|
|
232
242
|
// such as native client, web client, is a device, what type of phone, etc
|
|
233
243
|
this.processParticipant(participant);
|
|
@@ -258,6 +268,7 @@ export default class Member {
|
|
|
258
268
|
this.isModeratorAssignmentProhibited =
|
|
259
269
|
MemberUtil.isModeratorAssignmentProhibited(participant);
|
|
260
270
|
this.processStatus(participant);
|
|
271
|
+
this.processRoles(participant as ParticipantWithRoles);
|
|
261
272
|
// must be done last
|
|
262
273
|
this.isNotAdmitted = MemberUtil.isNotAdmitted(participant, this.isGuest, this.status);
|
|
263
274
|
}
|
|
@@ -427,6 +438,17 @@ export default class Member {
|
|
|
427
438
|
}
|
|
428
439
|
}
|
|
429
440
|
|
|
441
|
+
/**
|
|
442
|
+
* process the roles that have been applied to this member
|
|
443
|
+
* @param {Object} participant
|
|
444
|
+
* @returns {undefined}
|
|
445
|
+
* @private
|
|
446
|
+
* @memberof Member
|
|
447
|
+
*/
|
|
448
|
+
private processRoles(participant: ParticipantWithRoles) {
|
|
449
|
+
this.roles = MemberUtil.extractControlRoles(participant);
|
|
450
|
+
}
|
|
451
|
+
|
|
430
452
|
/**
|
|
431
453
|
* set the type for the member, could be MEETING or CALL
|
|
432
454
|
* @param {String} type
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
export interface IExternalRoles {
|
|
2
|
+
cohost: boolean;
|
|
3
|
+
moderator: boolean;
|
|
4
|
+
presenter: boolean;
|
|
5
|
+
}
|
|
6
|
+
|
|
7
|
+
export enum ServerRoles {
|
|
8
|
+
Cohost = 'COHOST',
|
|
9
|
+
Moderator = 'MODERATOR',
|
|
10
|
+
Presenter = 'PRESENTER',
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
export type ServerRoleShape = {
|
|
14
|
+
type: ServerRoles;
|
|
15
|
+
hasRole: boolean;
|
|
16
|
+
};
|
|
17
|
+
|
|
18
|
+
export type ParticipantWithRoles = {
|
|
19
|
+
controls: {
|
|
20
|
+
role: {
|
|
21
|
+
roles: Array<ServerRoleShape>;
|
|
22
|
+
};
|
|
23
|
+
};
|
|
24
|
+
};
|
package/src/member/util.ts
CHANGED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import {IExternalRoles, ParticipantWithRoles, ServerRoles, ServerRoleShape} from './types';
|
|
1
2
|
import {
|
|
2
3
|
_USER_,
|
|
3
4
|
_RESOURCE_ROOM_,
|
|
@@ -19,6 +20,58 @@ import ParameterError from '../common/errors/parameter';
|
|
|
19
20
|
|
|
20
21
|
const MemberUtil: any = {};
|
|
21
22
|
|
|
23
|
+
/**
|
|
24
|
+
* @param {Object} participant the locus participant
|
|
25
|
+
* @returns {[ServerRoleShape]}
|
|
26
|
+
*/
|
|
27
|
+
MemberUtil.getControlsRoles = (participant: ParticipantWithRoles): Array<ServerRoleShape> =>
|
|
28
|
+
participant?.controls?.role?.roles;
|
|
29
|
+
|
|
30
|
+
/**
|
|
31
|
+
* @param {Object} participant the locus participant
|
|
32
|
+
* @param {ServerRoles} controlRole the search role
|
|
33
|
+
* @returns {Boolean}
|
|
34
|
+
*/
|
|
35
|
+
MemberUtil.hasRole = (participant: any, controlRole: ServerRoles): boolean =>
|
|
36
|
+
MemberUtil.getControlsRoles(participant)?.some(
|
|
37
|
+
(role) => role.type === controlRole && role.hasRole
|
|
38
|
+
);
|
|
39
|
+
|
|
40
|
+
/**
|
|
41
|
+
* @param {Object} participant the locus participant
|
|
42
|
+
* @returns {Boolean}
|
|
43
|
+
*/
|
|
44
|
+
MemberUtil.hasCohost = (participant: ParticipantWithRoles): boolean =>
|
|
45
|
+
MemberUtil.hasRole(participant, ServerRoles.Cohost) || false;
|
|
46
|
+
|
|
47
|
+
/**
|
|
48
|
+
* @param {Object} participant the locus participant
|
|
49
|
+
* @returns {Boolean}
|
|
50
|
+
*/
|
|
51
|
+
MemberUtil.hasModerator = (participant: ParticipantWithRoles): boolean =>
|
|
52
|
+
MemberUtil.hasRole(participant, ServerRoles.Moderator) || false;
|
|
53
|
+
|
|
54
|
+
/**
|
|
55
|
+
* @param {Object} participant the locus participant
|
|
56
|
+
* @returns {Boolean}
|
|
57
|
+
*/
|
|
58
|
+
MemberUtil.hasPresenter = (participant: ParticipantWithRoles): boolean =>
|
|
59
|
+
MemberUtil.hasRole(participant, ServerRoles.Presenter) || false;
|
|
60
|
+
|
|
61
|
+
/**
|
|
62
|
+
* @param {Object} participant the locus participant
|
|
63
|
+
* @returns {IExternalRoles}
|
|
64
|
+
*/
|
|
65
|
+
MemberUtil.extractControlRoles = (participant: ParticipantWithRoles): IExternalRoles => {
|
|
66
|
+
const roles = {
|
|
67
|
+
cohost: MemberUtil.hasCohost(participant),
|
|
68
|
+
moderator: MemberUtil.hasModerator(participant),
|
|
69
|
+
presenter: MemberUtil.hasPresenter(participant),
|
|
70
|
+
};
|
|
71
|
+
|
|
72
|
+
return roles;
|
|
73
|
+
};
|
|
74
|
+
|
|
22
75
|
/**
|
|
23
76
|
* @param {Object} participant the locus participant
|
|
24
77
|
* @returns {Boolean}
|
package/src/members/index.ts
CHANGED
|
@@ -16,6 +16,7 @@ import MembersRequest from './request';
|
|
|
16
16
|
import MembersUtil from './util';
|
|
17
17
|
import {ReceiveSlotManager} from '../multistream/receiveSlotManager';
|
|
18
18
|
import {MediaRequestManager} from '../multistream/mediaRequestManager';
|
|
19
|
+
import {ServerRoleShape} from './types';
|
|
19
20
|
|
|
20
21
|
/**
|
|
21
22
|
* Members Update Event
|
|
@@ -803,6 +804,32 @@ export default class Members extends StatelessWebexPlugin {
|
|
|
803
804
|
return this.membersRequest.muteMember(options);
|
|
804
805
|
}
|
|
805
806
|
|
|
807
|
+
/**
|
|
808
|
+
* Assign role(s) to a member in the meeting
|
|
809
|
+
* @param {String} memberId
|
|
810
|
+
* @param {[ServerRoleShape]} roles - to assign an array of roles
|
|
811
|
+
* @returns {Promise}
|
|
812
|
+
* @public
|
|
813
|
+
* @memberof Members
|
|
814
|
+
*/
|
|
815
|
+
public assignRoles(memberId: string, roles: Array<ServerRoleShape>) {
|
|
816
|
+
if (!this.locusUrl) {
|
|
817
|
+
return Promise.reject(
|
|
818
|
+
new ParameterError(
|
|
819
|
+
'The associated locus url for this meetings members object must be defined.'
|
|
820
|
+
)
|
|
821
|
+
);
|
|
822
|
+
}
|
|
823
|
+
if (!memberId) {
|
|
824
|
+
return Promise.reject(
|
|
825
|
+
new ParameterError('The member id must be defined to assign the roles to a member.')
|
|
826
|
+
);
|
|
827
|
+
}
|
|
828
|
+
const options = MembersUtil.generateRoleAssignmentMemberOptions(memberId, roles, this.locusUrl);
|
|
829
|
+
|
|
830
|
+
return this.membersRequest.assignRolesMember(options);
|
|
831
|
+
}
|
|
832
|
+
|
|
806
833
|
/**
|
|
807
834
|
* Raise or lower the hand of a member in a meeting
|
|
808
835
|
* @param {String} memberId
|
package/src/members/request.ts
CHANGED
|
@@ -85,6 +85,26 @@ export default class MembersRequest extends StatelessWebexPlugin {
|
|
|
85
85
|
return this.request(requestParams);
|
|
86
86
|
}
|
|
87
87
|
|
|
88
|
+
/**
|
|
89
|
+
* Sends a request to the DTMF endpoint to send tones
|
|
90
|
+
* @param {Object} options
|
|
91
|
+
* @param {String} options.locusUrl
|
|
92
|
+
* @param {String} options.memberId ID of PSTN user
|
|
93
|
+
* @returns {Promise}
|
|
94
|
+
*/
|
|
95
|
+
assignRolesMember(options: any) {
|
|
96
|
+
if (!options || !options.locusUrl || !options.memberId) {
|
|
97
|
+
throw new ParameterError(
|
|
98
|
+
'memberId must be defined, and the associated locus url for this meeting object must be defined.'
|
|
99
|
+
);
|
|
100
|
+
}
|
|
101
|
+
|
|
102
|
+
const requestParams = MembersUtil.getRoleAssignmentMemberRequestParams(options);
|
|
103
|
+
|
|
104
|
+
// @ts-ignore
|
|
105
|
+
return this.request(requestParams);
|
|
106
|
+
}
|
|
107
|
+
|
|
88
108
|
raiseOrLowerHandMember(options) {
|
|
89
109
|
if (!options || !options.locusUrl || !options.memberId) {
|
|
90
110
|
throw new ParameterError(
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
export enum ServerRoles {
|
|
2
|
+
Cohost = 'COHOST',
|
|
3
|
+
Moderator = 'MODERATOR',
|
|
4
|
+
Presenter = 'PRESENTER',
|
|
5
|
+
}
|
|
6
|
+
|
|
7
|
+
export type ServerRoleShape = {
|
|
8
|
+
type: ServerRoles;
|
|
9
|
+
hasRole: boolean;
|
|
10
|
+
};
|
|
11
|
+
|
|
12
|
+
export type RoleAssignmentOptions = {
|
|
13
|
+
roles: Array<ServerRoleShape>;
|
|
14
|
+
locusUrl: string;
|
|
15
|
+
memberId: string;
|
|
16
|
+
};
|
|
17
|
+
|
|
18
|
+
export type RoleAssignmentBody = {
|
|
19
|
+
role: {
|
|
20
|
+
roles: Array<ServerRoleShape>;
|
|
21
|
+
};
|
|
22
|
+
};
|
|
23
|
+
|
|
24
|
+
export type RoleAssignmentRequest = {
|
|
25
|
+
method: string;
|
|
26
|
+
uri: string;
|
|
27
|
+
body: RoleAssignmentBody;
|
|
28
|
+
};
|
package/src/members/util.ts
CHANGED
|
@@ -1,5 +1,4 @@
|
|
|
1
1
|
import uuid from 'uuid';
|
|
2
|
-
|
|
3
2
|
import {
|
|
4
3
|
HTTP_VERBS,
|
|
5
4
|
CONTROLS,
|
|
@@ -12,6 +11,8 @@ import {
|
|
|
12
11
|
_REMOVE_,
|
|
13
12
|
} from '../constants';
|
|
14
13
|
|
|
14
|
+
import {RoleAssignmentOptions, RoleAssignmentRequest, ServerRoleShape} from './types';
|
|
15
|
+
|
|
15
16
|
const MembersUtil: any = {};
|
|
16
17
|
|
|
17
18
|
/**
|
|
@@ -152,6 +153,22 @@ MembersUtil.generateRaiseHandMemberOptions = (memberId, status, locusUrl) => ({
|
|
|
152
153
|
locusUrl,
|
|
153
154
|
});
|
|
154
155
|
|
|
156
|
+
/**
|
|
157
|
+
* @param {String} memberId
|
|
158
|
+
* @param {[ServerRoleShape]} roles
|
|
159
|
+
* @param {String} locusUrl
|
|
160
|
+
* @returns {RoleAssignmentOptions}
|
|
161
|
+
*/
|
|
162
|
+
MembersUtil.generateRoleAssignmentMemberOptions = (
|
|
163
|
+
memberId: string,
|
|
164
|
+
roles: Array<ServerRoleShape>,
|
|
165
|
+
locusUrl: string
|
|
166
|
+
): RoleAssignmentOptions => ({
|
|
167
|
+
memberId,
|
|
168
|
+
roles,
|
|
169
|
+
locusUrl,
|
|
170
|
+
});
|
|
171
|
+
|
|
155
172
|
MembersUtil.generateLowerAllHandsMemberOptions = (requestingParticipantId, locusUrl) => ({
|
|
156
173
|
requestingParticipantId,
|
|
157
174
|
locusUrl,
|
|
@@ -173,6 +190,27 @@ MembersUtil.getMuteMemberRequestParams = (options) => {
|
|
|
173
190
|
};
|
|
174
191
|
};
|
|
175
192
|
|
|
193
|
+
/**
|
|
194
|
+
* @param {RoleAssignmentOptions} options
|
|
195
|
+
* @returns {RoleAssignmentRequest} the request parameters (method, uri, body) needed to make a addMember request
|
|
196
|
+
*/
|
|
197
|
+
MembersUtil.getRoleAssignmentMemberRequestParams = (
|
|
198
|
+
options: RoleAssignmentOptions
|
|
199
|
+
): RoleAssignmentRequest => {
|
|
200
|
+
const body = {role: {roles: []}};
|
|
201
|
+
options.roles.forEach((role) => {
|
|
202
|
+
body.role.roles.push({type: role.type, hasRole: role.hasRole});
|
|
203
|
+
});
|
|
204
|
+
|
|
205
|
+
const uri = `${options.locusUrl}/${PARTICIPANT}/${options.memberId}/${CONTROLS}`;
|
|
206
|
+
|
|
207
|
+
return {
|
|
208
|
+
method: HTTP_VERBS.PATCH,
|
|
209
|
+
uri,
|
|
210
|
+
body,
|
|
211
|
+
};
|
|
212
|
+
};
|
|
213
|
+
|
|
176
214
|
MembersUtil.getRaiseHandMemberRequestParams = (options) => {
|
|
177
215
|
const body = {
|
|
178
216
|
hand: {
|
|
@@ -452,10 +452,10 @@ export default class ReconnectionManager {
|
|
|
452
452
|
// So that on rejoin it known what parametrs it was using
|
|
453
453
|
if (!this.meeting || !this.webex.meetings.getMeetingByType(_ID_, this.meeting.id)) {
|
|
454
454
|
LoggerProxy.logger.info(
|
|
455
|
-
'ReconnectionManager:index#executeReconnection --> Meeting got deleted due to inactivity or ended remotely
|
|
455
|
+
'ReconnectionManager:index#executeReconnection --> Meeting got deleted due to inactivity or ended remotely.'
|
|
456
456
|
);
|
|
457
457
|
|
|
458
|
-
throw new Error('Unable to rejoin a meeting already ended or inactive
|
|
458
|
+
throw new Error('Unable to rejoin a meeting already ended or inactive.');
|
|
459
459
|
}
|
|
460
460
|
|
|
461
461
|
LoggerProxy.logger.info(
|
|
@@ -10,6 +10,8 @@ describe('plugin-meetings', () => {
|
|
|
10
10
|
canLock: null,
|
|
11
11
|
canUnlock: null,
|
|
12
12
|
canAssignHost: null,
|
|
13
|
+
canSetPresenter: null,
|
|
14
|
+
canUnsetPresenter: null,
|
|
13
15
|
canStartRecording: null,
|
|
14
16
|
canPauseRecording: null,
|
|
15
17
|
canResumeRecording: null,
|
|
@@ -28,6 +30,7 @@ describe('plugin-meetings', () => {
|
|
|
28
30
|
canStartTranscribing: null,
|
|
29
31
|
canStopTranscribing: null,
|
|
30
32
|
isClosedCaptionActive: null,
|
|
33
|
+
isSaveTranscriptsEnabled: null,
|
|
31
34
|
isWebexAssistantActive: null,
|
|
32
35
|
canViewCaptionPanel: null,
|
|
33
36
|
isRealTimeTranslationEnabled: null,
|
|
@@ -57,6 +60,8 @@ describe('plugin-meetings', () => {
|
|
|
57
60
|
'canLock',
|
|
58
61
|
'canUnlock',
|
|
59
62
|
'canAssignHost',
|
|
63
|
+
'canSetPresenter',
|
|
64
|
+
'canUnsetPresenter',
|
|
60
65
|
'canStartRecording',
|
|
61
66
|
'canPauseRecording',
|
|
62
67
|
'canResumeRecording',
|
|
@@ -72,6 +77,7 @@ describe('plugin-meetings', () => {
|
|
|
72
77
|
'canEnableClosedCaption',
|
|
73
78
|
'canStopTranscribing',
|
|
74
79
|
'isClosedCaptionActive',
|
|
80
|
+
'isSaveTranscriptsEnabled',
|
|
75
81
|
'isWebexAssistantActive',
|
|
76
82
|
'canViewCaptionPanel',
|
|
77
83
|
'isRealTimeTranslationEnabled',
|
|
@@ -389,6 +389,7 @@ describe('plugin-meetings', () => {
|
|
|
389
389
|
});
|
|
390
390
|
|
|
391
391
|
[
|
|
392
|
+
{functionName: 'isSaveTranscriptsEnabled', displayHint: 'SAVE_TRANSCRIPTS_ENABLED'},
|
|
392
393
|
{functionName: 'canEnableClosedCaption', displayHint: 'CAPTION_START'},
|
|
393
394
|
{functionName: 'canStartTranscribing', displayHint: 'TRANSCRIPTION_CONTROL_START'},
|
|
394
395
|
{functionName: 'canStopTranscribing', displayHint: 'TRANSCRIPTION_CONTROL_STOP'},
|
|
@@ -19,4 +19,28 @@ describe('member', () => {
|
|
|
19
19
|
|
|
20
20
|
assert.calledOnceWithExactly(MemberUtil.isHandRaised, participant);
|
|
21
21
|
});
|
|
22
|
+
|
|
23
|
+
describe('roles', () => {
|
|
24
|
+
it('checks that processParticipant calls processRoles', () => {
|
|
25
|
+
const participant = {};
|
|
26
|
+
|
|
27
|
+
const member = new Member({});
|
|
28
|
+
|
|
29
|
+
sinon.spy(member, 'processRoles');
|
|
30
|
+
member.processParticipant(participant);
|
|
31
|
+
|
|
32
|
+
assert.calledOnceWithExactly(member.processRoles, participant);
|
|
33
|
+
});
|
|
34
|
+
|
|
35
|
+
it('checks that processRoles calls extractControlRoles', () => {
|
|
36
|
+
const participant = {};
|
|
37
|
+
|
|
38
|
+
const member = new Member({});
|
|
39
|
+
|
|
40
|
+
sinon.spy(MemberUtil, 'extractControlRoles');
|
|
41
|
+
member.processParticipant(participant);
|
|
42
|
+
|
|
43
|
+
assert.calledOnceWithExactly(MemberUtil.extractControlRoles, participant);
|
|
44
|
+
});
|
|
45
|
+
})
|
|
22
46
|
});
|