瀏覽代碼

Coding style/naming: invite & invitee(s)

Hristo Terezov, Chris Cordle, and I/Lyubomir Marinov agreed that we'd
try to use "invite" & "invitee(s)" in Web/React's iframe API,
mobile/react-native's SDK invite API, and internally for the purposes of
consistency, ease of understanding, etc.
j8
Lyubo Marinov 7 年之前
父節點
當前提交
520bb8bd22

+ 14
- 9
modules/API/API.js 查看文件

@@ -1,12 +1,12 @@
1 1
 // @flow
2 2
 
3 3
 import * as JitsiMeetConferenceEvents from '../../ConferenceEvents';
4
-import { parseJWTFromURLParams } from '../../react/features/base/jwt';
5 4
 import {
6 5
     createApiEvent,
7 6
     sendAnalytics
8 7
 } from '../../react/features/analytics';
9
-import { sendInvitesForItems } from '../../react/features/invite';
8
+import { parseJWTFromURLParams } from '../../react/features/base/jwt';
9
+import { invite } from '../../react/features/invite';
10 10
 import { getJitsiMeetTransport } from '../transport';
11 11
 
12 12
 import { API_ID } from './constants';
@@ -114,15 +114,20 @@ function initCommands() {
114 114
         switch (name) {
115 115
         case 'invite':
116 116
             APP.store.dispatch(
117
-                sendInvitesForItems(request.invitees))
118
-                .then(failedInvites => {
119
-                    const failed = failedInvites.length === 0;
117
+                invite(request.invitees))
118
+                .then(failedInvitees => {
119
+                    let error;
120
+                    let result;
121
+
122
+                    if (failedInvitees.length) {
123
+                        error = new Error('One or more invites failed!');
124
+                    } else {
125
+                        result = true;
126
+                    }
120 127
 
121 128
                     callback({
122
-                        result: failed ? undefined : true,
123
-                        error: failed
124
-                            ? new Error('One or more invites failed!')
125
-                            : undefined
129
+                        error,
130
+                        result
126 131
                     });
127 132
                 });
128 133
             break;

+ 79
- 76
react/features/invite/actions.js 查看文件

@@ -33,66 +33,25 @@ export function beginAddPeople() {
33 33
 }
34 34
 
35 35
 /**
36
- * Sends AJAX requests for dial-in numbers and conference ID.
37
- *
38
- * @returns {Function}
39
- */
40
-export function updateDialInNumbers() {
41
-    return (dispatch: Dispatch<*>, getState: Function) => {
42
-        const state = getState();
43
-        const { dialInConfCodeUrl, dialInNumbersUrl, hosts }
44
-            = state['features/base/config'];
45
-        const mucURL = hosts && hosts.muc;
46
-
47
-        if (!dialInConfCodeUrl || !dialInNumbersUrl || !mucURL) {
48
-            // URLs for fetching dial in numbers not defined
49
-            return;
50
-        }
51
-
52
-        const { room } = state['features/base/conference'];
53
-
54
-        Promise.all([
55
-            getDialInNumbers(dialInNumbersUrl),
56
-            getDialInConferenceID(dialInConfCodeUrl, room, mucURL)
57
-        ])
58
-            .then(([ dialInNumbers, { conference, id, message } ]) => {
59
-                if (!conference || !id) {
60
-                    return Promise.reject(message);
61
-                }
62
-
63
-                dispatch({
64
-                    type: UPDATE_DIAL_IN_NUMBERS_SUCCESS,
65
-                    conferenceID: id,
66
-                    dialInNumbers
67
-                });
68
-            })
69
-            .catch(error => {
70
-                dispatch({
71
-                    type: UPDATE_DIAL_IN_NUMBERS_FAILED,
72
-                    error
73
-                });
74
-            });
75
-    };
76
-}
77
-
78
-/**
79
- * Send invites for a list of items (may be a combination of users, rooms, phone
80
- * numbers, and video rooms).
36
+ * Invites (i.e. sends invites to) an array of invitees (which may be a
37
+ * combination of users, rooms, phone numbers, and video rooms).
81 38
  *
82
- * @param  {Array<Object>} invites - Items for which invites should be sent.
83
- * @returns {Promise} Promise containing the list of invites that were not sent.
39
+ * @param  {Array<Object>} invitees - The recepients to send invites to.
40
+ * @returns {Promise<Array<Object>>} A {@code Promise} resolving with an array
41
+ * of invitees who were not invited (i.e. invites were not sent to them).
84 42
  */
85
-export function sendInvitesForItems(invites: Array<Object>) {
43
+export function invite(invitees: Array<Object>) {
86 44
     return (
87 45
             dispatch: Dispatch<*>,
88 46
             getState: Function): Promise<Array<Object>> => {
89 47
         let allInvitePromises = [];
90
-        let invitesLeftToSend = [ ...invites ];
48
+        let invitesLeftToSend = [ ...invitees ];
49
+
91 50
         const state = getState();
92 51
         const { conference } = state['features/base/conference'];
93 52
         const { inviteServiceUrl } = state['features/base/config'];
94 53
         const inviteUrl = getInviteURL(state);
95
-        const jwt = state['features/base/jwt'].jwt;
54
+        const { jwt } = state['features/base/jwt'];
96 55
 
97 56
         // First create all promises for dialing out.
98 57
         if (conference) {
@@ -105,54 +64,98 @@ export function sendInvitesForItems(invites: Array<Object>) {
105 64
                 const numberToInvite = getDigitsOnly(item.number);
106 65
 
107 66
                 return conference.dial(numberToInvite)
108
-                     .then(() => {
109
-                         invitesLeftToSend
110
-                             = invitesLeftToSend.filter(invite =>
111
-                                 invite !== item);
112
-                     })
113
-                     .catch(error => logger.error(
114
-                         'Error inviting phone number:', error));
67
+                    .then(() => {
68
+                        invitesLeftToSend
69
+                            = invitesLeftToSend.filter(
70
+                                invitee => invitee !== item);
71
+                    })
72
+                    .catch(error =>
73
+                        logger.error('Error inviting phone number:', error));
115 74
             });
116 75
 
117 76
             allInvitePromises = allInvitePromises.concat(phoneInvitePromises);
118 77
         }
119 78
 
120
-        const usersAndRooms = invitesLeftToSend.filter(item =>
121
-            item.type === 'user' || item.type === 'room');
79
+        const usersAndRooms
80
+            = invitesLeftToSend.filter(
81
+                ({ type }) => type === 'user' || type === 'room');
122 82
 
123 83
         if (usersAndRooms.length) {
124 84
             // Send a request to invite all the rooms and users. On success,
125 85
             // filter all rooms and users from {@link invitesLeftToSend}.
126
-            const peopleInvitePromise = invitePeopleAndChatRooms(
127
-                inviteServiceUrl,
128
-                inviteUrl,
129
-                jwt,
130
-                usersAndRooms)
86
+            const peopleInvitePromise
87
+                = invitePeopleAndChatRooms(
88
+                    inviteServiceUrl,
89
+                    inviteUrl,
90
+                    jwt,
91
+                    usersAndRooms)
131 92
                 .then(() => {
132
-                    invitesLeftToSend = invitesLeftToSend.filter(item =>
133
-                        item.type !== 'user' && item.type !== 'room');
93
+                    invitesLeftToSend
94
+                        = invitesLeftToSend.filter(
95
+                            ({ type }) => type !== 'user' && type !== 'room');
134 96
                 })
135
-                .catch(error => logger.error(
136
-                    'Error inviting people:', error));
97
+                .catch(error => logger.error('Error inviting people:', error));
137 98
 
138 99
             allInvitePromises.push(peopleInvitePromise);
139 100
         }
140 101
 
141
-        // Sipgw calls are fire and forget. Invite them to the conference
142
-        // then immediately remove them from {@link invitesLeftToSend}.
143
-        const vrooms = invitesLeftToSend.filter(item =>
144
-            item.type === 'videosipgw');
102
+        // Sipgw calls are fire and forget. Invite them to the conference, then
103
+        // immediately remove them from invitesLeftToSend.
104
+        const vrooms
105
+            = invitesLeftToSend.filter(({ type }) => type === 'videosipgw');
145 106
 
146 107
         conference
147 108
             && vrooms.length > 0
148 109
             && dispatch(inviteVideoRooms(conference, vrooms));
149 110
 
150
-        invitesLeftToSend = invitesLeftToSend.filter(item =>
151
-            item.type !== 'videosipgw');
111
+        invitesLeftToSend
112
+            = invitesLeftToSend.filter(({ type }) => type !== 'videosipgw');
152 113
 
153 114
         return (
154 115
             Promise.all(allInvitePromises)
155
-                .then(() => invitesLeftToSend)
156
-        );
116
+                .then(() => invitesLeftToSend));
117
+    };
118
+}
119
+
120
+/**
121
+ * Sends AJAX requests for dial-in numbers and conference ID.
122
+ *
123
+ * @returns {Function}
124
+ */
125
+export function updateDialInNumbers() {
126
+    return (dispatch: Dispatch<*>, getState: Function) => {
127
+        const state = getState();
128
+        const { dialInConfCodeUrl, dialInNumbersUrl, hosts }
129
+            = state['features/base/config'];
130
+        const mucURL = hosts && hosts.muc;
131
+
132
+        if (!dialInConfCodeUrl || !dialInNumbersUrl || !mucURL) {
133
+            // URLs for fetching dial in numbers not defined
134
+            return;
135
+        }
136
+
137
+        const { room } = state['features/base/conference'];
138
+
139
+        Promise.all([
140
+            getDialInNumbers(dialInNumbersUrl),
141
+            getDialInConferenceID(dialInConfCodeUrl, room, mucURL)
142
+        ])
143
+            .then(([ dialInNumbers, { conference, id, message } ]) => {
144
+                if (!conference || !id) {
145
+                    return Promise.reject(message);
146
+                }
147
+
148
+                dispatch({
149
+                    type: UPDATE_DIAL_IN_NUMBERS_SUCCESS,
150
+                    conferenceID: id,
151
+                    dialInNumbers
152
+                });
153
+            })
154
+            .catch(error => {
155
+                dispatch({
156
+                    type: UPDATE_DIAL_IN_NUMBERS_FAILED,
157
+                    error
158
+                });
159
+            });
157 160
     };
158 161
 }

+ 12
- 19
react/features/invite/components/AddPeopleDialog.web.js 查看文件

@@ -11,11 +11,8 @@ import { Dialog, hideDialog } from '../../base/dialog';
11 11
 import { translate } from '../../base/i18n';
12 12
 import { MultiSelectAutocomplete } from '../../base/react';
13 13
 
14
-import {
15
-    getInviteResultsForQuery,
16
-    getInviteTypeCounts
17
-} from '../functions';
18
-import { sendInvitesForItems } from '../actions';
14
+import { invite } from '../actions';
15
+import { getInviteResultsForQuery, getInviteTypeCounts } from '../functions';
19 16
 
20 17
 const logger = require('jitsi-meet-logger').getLogger(__filename);
21 18
 
@@ -68,7 +65,7 @@ class AddPeopleDialog extends Component<*, *> {
68 65
         dialOutEnabled: PropTypes.bool,
69 66
 
70 67
         /**
71
-         * The redux dispatch method.
68
+         * The redux {@code dispatch} function.
72 69
          */
73 70
         dispatch: PropTypes.func,
74 71
 
@@ -282,8 +279,8 @@ class AddPeopleDialog extends Component<*, *> {
282 279
      */
283 280
     _onSubmit() {
284 281
         const { inviteItems } = this.state;
285
-        const items = inviteItems.map(item => item.item);
286
-        const inviteTypeCounts = getInviteTypeCounts(items);
282
+        const invitees = inviteItems.map(({ item }) => item);
283
+        const inviteTypeCounts = getInviteTypeCounts(invitees);
287 284
 
288 285
         sendAnalytics(createInviteDialogEvent(
289 286
             'clicked', 'inviteButton', {
@@ -301,7 +298,7 @@ class AddPeopleDialog extends Component<*, *> {
301 298
 
302 299
         const { dispatch } = this.props;
303 300
 
304
-        dispatch(sendInvitesForItems(items))
301
+        dispatch(invite(invitees))
305 302
             .then(invitesLeftToSend => {
306 303
                 // If any invites are left that means something failed to send
307 304
                 // so treat it as an error.
@@ -322,15 +319,12 @@ class AddPeopleDialog extends Component<*, *> {
322 319
                         addToCallError: true
323 320
                     });
324 321
 
325
-                    const unsentInviteIDs = invitesLeftToSend.map(invite =>
326
-                        invite.id || invite.number
327
-                    );
328
-
329
-                    const itemsToSelect = inviteItems.filter(invite =>
330
-                        unsentInviteIDs.includes(
331
-                            invite.item.id || invite.item.number
332
-                        )
333
-                    );
322
+                    const unsentInviteIDs
323
+                        = invitesLeftToSend.map(invitee =>
324
+                            invitee.id || invitee.number);
325
+                    const itemsToSelect
326
+                        = inviteItems.filter(({ item }) =>
327
+                            unsentInviteIDs.includes(item.id || item.number));
334 328
 
335 329
                     if (this._multiselect) {
336 330
                         this._multiselect.setSelectedItems(itemsToSelect);
@@ -431,7 +425,6 @@ class AddPeopleDialog extends Component<*, *> {
431 425
             _peopleSearchQueryTypes,
432 426
             _peopleSearchUrl
433 427
         } = this.props;
434
-
435 428
         const options = {
436 429
             dialOutAuthUrl: _dialOutAuthUrl,
437 430
             addPeopleEnabled,

+ 63
- 57
react/features/invite/functions.js 查看文件

@@ -76,9 +76,8 @@ export function getDialInNumbers(url: string): Promise<*> {
76 76
 /**
77 77
  * Removes all non-numeric characters from a string.
78 78
  *
79
- * @param {string} text - The string from which to remove all characters
80
- * except numbers.
81
- * @private
79
+ * @param {string} text - The string from which to remove all characters except
80
+ * numbers.
82 81
  * @returns {string} A string with only numbers.
83 82
  */
84 83
 export function getDigitsOnly(text: string = ''): string {
@@ -126,8 +125,8 @@ export type GetInviteResultsOptions = {
126 125
  * Combines directory search with phone number validation to produce a single
127 126
  * set of invite search results.
128 127
  *
129
- * @param  {string} query - Text to search.
130
- * @param  {GetInviteResultsOptions} options - Options to use when searching.
128
+ * @param {string} query - Text to search.
129
+ * @param {GetInviteResultsOptions} options - Options to use when searching.
131 130
  * @returns {Promise<*>}
132 131
  */
133 132
 export function getInviteResultsForQuery(
@@ -166,19 +165,18 @@ export function getInviteResultsForQuery(
166 165
         let numberToVerify = text;
167 166
 
168 167
         // When the number to verify does not start with a +, we assume no
169
-        // proper country code has been entered. In such a case, prepend 1
170
-        // for the country code. The service currently takes care of
171
-        // prepending the +.
168
+        // proper country code has been entered. In such a case, prepend 1 for
169
+        // the country code. The service currently takes care of prepending the
170
+        // +.
172 171
         if (!hasCountryCode && !text.startsWith('1')) {
173 172
             numberToVerify = `1${numberToVerify}`;
174 173
         }
175 174
 
176
-        // The validation service works properly when the query is digits
177
-        // only so ensure only digits get sent.
175
+        // The validation service works properly when the query is digits only
176
+        // so ensure only digits get sent.
178 177
         numberToVerify = getDigitsOnly(numberToVerify);
179 178
 
180
-        phoneNumberPromise
181
-            = checkDialNumber(numberToVerify, dialOutAuthUrl);
179
+        phoneNumberPromise = checkDialNumber(numberToVerify, dialOutAuthUrl);
182 180
     } else {
183 181
         phoneNumberPromise = Promise.resolve({});
184 182
     }
@@ -190,18 +188,16 @@ export function getInviteResultsForQuery(
190 188
             ];
191 189
 
192 190
             /**
193
-             * This check for phone results is for the day the call to
194
-             * searching people might return phone results as well. When
195
-             * that day comes this check will make it so the server checks
196
-             * are honored and the local appending of the number is not
197
-             * done. The local appending of the phone number can then be
198
-             * cleaned up when convenient.
191
+             * This check for phone results is for the day the call to searching
192
+             * people might return phone results as well. When that day comes
193
+             * this check will make it so the server checks are honored and the
194
+             * local appending of the number is not done. The local appending of
195
+             * the phone number can then be cleaned up when convenient.
199 196
              */
200
-            const hasPhoneResult = peopleResults.find(
201
-                result => result.type === 'phone');
197
+            const hasPhoneResult
198
+                = peopleResults.find(result => result.type === 'phone');
202 199
 
203
-            if (!hasPhoneResult
204
-                    && typeof phoneResults.allow === 'boolean') {
200
+            if (!hasPhoneResult && typeof phoneResults.allow === 'boolean') {
205 201
                 results.push({
206 202
                     allowed: phoneResults.allow,
207 203
                     country: phoneResults.country,
@@ -216,6 +212,28 @@ export function getInviteResultsForQuery(
216 212
         });
217 213
 }
218 214
 
215
+/**
216
+ * Helper for determining how many of each type of user is being invited. Used
217
+ * for logging and sending analytics related to invites.
218
+ *
219
+ * @param {Array} inviteItems - An array with the invite items, as created in
220
+ * {@link _parseQueryResults}.
221
+ * @returns {Object} An object with keys as user types and values as the number
222
+ * of invites for that type.
223
+ */
224
+export function getInviteTypeCounts(inviteItems: Array<Object> = []) {
225
+    const inviteTypeCounts = {};
226
+
227
+    inviteItems.forEach(({ type }) => {
228
+        if (!inviteTypeCounts[type]) {
229
+            inviteTypeCounts[type] = 0;
230
+        }
231
+        inviteTypeCounts[type]++;
232
+    });
233
+
234
+    return inviteTypeCounts;
235
+}
236
+
219 237
 /**
220 238
  * Sends a post request to an invite service.
221 239
  *
@@ -223,8 +241,8 @@ export function getInviteResultsForQuery(
223 241
  * invitation.
224 242
  * @param {string} inviteUrl - The url to the conference.
225 243
  * @param {string} jwt - The jwt token to pass to the search service.
226
- * @param {Immutable.List} inviteItems - The list of the "user" or "room"
227
- * type items to invite.
244
+ * @param {Immutable.List} inviteItems - The list of the "user" or "room" type
245
+ * items to invite.
228 246
  * @returns {Promise} - The promise created by the request.
229 247
  */
230 248
 export function invitePeopleAndChatRooms( // eslint-disable-line max-params
@@ -282,24 +300,37 @@ export function isAddPeopleEnabled(state: Object): boolean {
282 300
  * @returns {boolean} Indication of whether dial out is currently enabled.
283 301
  */
284 302
 export function isDialOutEnabled(state: Object): boolean {
303
+    const participant = getLocalParticipant(state);
285 304
     const { conference } = state['features/base/conference'];
286 305
     const { isGuest } = state['features/base/jwt'];
287 306
     const { enableUserRolesBasedOnToken } = state['features/base/config'];
288
-    const participant = getLocalParticipant(state);
307
+    let dialOutEnabled
308
+        = participant && participant.role === PARTICIPANT_ROLE.MODERATOR
309
+            && conference && conference.isSIPCallingSupported()
310
+            && (!enableUserRolesBasedOnToken || !isGuest);
311
+
312
+    if (dialOutEnabled) {
313
+        // XXX The mobile/react-native app is capable of disabling of dial-out.
314
+        // Anyway, the Web/React app does not have that capability so default
315
+        // appropriately.
316
+        const { app } = state['features/app'];
317
+
318
+        dialOutEnabled = app && app.props.dialoOutEnabled;
319
+
320
+        return (
321
+            (typeof dialOutEnabled === 'undefined') || Boolean(dialOutEnabled));
322
+    }
289 323
 
290
-    return participant && participant.role === PARTICIPANT_ROLE.MODERATOR
291
-                && conference && conference.isSIPCallingSupported()
292
-                && (!enableUserRolesBasedOnToken || !isGuest);
324
+    return false;
293 325
 }
294 326
 
295 327
 /**
296 328
  * Checks whether a string looks like it could be for a phone number.
297 329
  *
298
- * @param {string} text - The text to check whether or not it could be a
299
- * phone number.
300
- * @private
301
- * @returns {boolean} True if the string looks like it could be a phone
330
+ * @param {string} text - The text to check whether or not it could be a phone
302 331
  * number.
332
+ * @private
333
+ * @returns {boolean} True if the string looks like it could be a phone number.
303 334
  */
304 335
 function isMaybeAPhoneNumber(text: string): boolean {
305 336
     if (!isPhoneNumberRegex().test(text)) {
@@ -365,28 +396,3 @@ export function searchDirectory( // eslint-disable-line max-params
365 396
                 return Promise.reject(error);
366 397
             });
367 398
 }
368
-
369
-/**
370
- * Helper for determining how many of each type of user is being invited.
371
- * Used for logging and sending analytics related to invites.
372
- *
373
- * @param {Array} inviteItems - An array with the invite items, as created
374
- * in {@link _parseQueryResults}.
375
- * @private
376
- * @returns {Object} An object with keys as user types and values as the
377
- * number of invites for that type.
378
- */
379
-export function getInviteTypeCounts(inviteItems: Array<Object> = []) {
380
-    const inviteTypeCounts = {};
381
-
382
-    inviteItems.forEach(({ type }) => {
383
-
384
-        if (!inviteTypeCounts[type]) {
385
-            inviteTypeCounts[type] = 0;
386
-        }
387
-
388
-        inviteTypeCounts[type]++;
389
-    });
390
-
391
-    return inviteTypeCounts;
392
-}

+ 3
- 4
react/features/invite/middleware.native.js 查看文件

@@ -6,6 +6,7 @@ import { NativeEventEmitter, NativeModules } from 'react-native';
6 6
 import { MiddlewareRegistry } from '../base/redux';
7 7
 import { APP_WILL_MOUNT, APP_WILL_UNMOUNT } from '../app';
8 8
 
9
+import { invite } from './actions';
9 10
 import {
10 11
     BEGIN_ADD_PEOPLE,
11 12
     _SET_EMITTER_SUBSCRIPTIONS
@@ -15,7 +16,6 @@ import {
15 16
     isAddPeopleEnabled,
16 17
     isDialOutEnabled
17 18
 } from './functions';
18
-import { sendInvitesForItems } from './actions';
19 19
 import './middleware.any';
20 20
 
21 21
 /**
@@ -133,8 +133,7 @@ function _beginAddPeople({ getState }, next, action) {
133 133
  * @param {Object} event - The details of the event.
134 134
  * @returns {void}
135 135
  */
136
-function _onInvite(
137
-        { addPeopleControllerScope, externalAPIScope, invitees }) {
136
+function _onInvite({ addPeopleControllerScope, externalAPIScope, invitees }) {
138 137
     const { dispatch, getState } = this; // eslint-disable-line no-invalid-this
139 138
 
140 139
     // If there are multiple JitsiMeetView instances alive, they will all get
@@ -145,7 +144,7 @@ function _onInvite(
145 144
         return;
146 145
     }
147 146
 
148
-    dispatch(sendInvitesForItems(invitees))
147
+    dispatch(invite(invitees))
149 148
         .then(failedInvitees =>
150 149
             Invite.inviteSettled(
151 150
                 externalAPIScope,

Loading…
取消
儲存