Просмотр исходного кода

Moves web password required dialog to react.

j8
damencho 8 лет назад
Родитель
Сommit
61470c0d24

+ 0
- 4
conference.js Просмотреть файл

@@ -387,10 +387,6 @@ class ConferenceConnector {
387 387
         logger.error('CONFERENCE FAILED:', err, ...params);
388 388
         APP.UI.hideRingOverLay();
389 389
         switch (err) {
390
-            // room is locked by the password
391
-        case ConferenceErrors.PASSWORD_REQUIRED:
392
-            APP.UI.emitEvent(UIEvents.PASSWORD_REQUIRED);
393
-            break;
394 390
 
395 391
         case ConferenceErrors.CONNECTION_ERROR:
396 392
             {

+ 0
- 23
modules/UI/invite/Invite.js Просмотреть файл

@@ -47,31 +47,8 @@ class Invite {
47 47
             }
48 48
         });
49 49
 
50
-        this.conference.on(ConferenceEvents.CONFERENCE_JOINED, () => {
51
-            let roomLocker = this.getRoomLocker();
52
-            roomLocker.hideRequirePasswordDialog();
53
-        });
54
-
55 50
         APP.UI.addListener( UIEvents.INVITE_CLICKED,
56 51
                             () => { this.openLinkDialog(); });
57
-
58
-        APP.UI.addListener( UIEvents.PASSWORD_REQUIRED,
59
-            () => {
60
-                let roomLocker = this.getRoomLocker();
61
-                this.setLockedFromElsewhere(true);
62
-                roomLocker.requirePassword().then(() => {
63
-                    let pass = roomLocker.password;
64
-                    // we received that password is required, but user is trying
65
-                    // anyway to login without a password, mark room as not
66
-                    // locked in case he succeeds (maybe someone removed the
67
-                    // password meanwhile), if it is still locked another
68
-                    // password required will be received and the room again
69
-                    // will be marked as locked.
70
-                    if (!pass)
71
-                        this.setLockedFromElsewhere(false);
72
-                    this.conference.join(pass);
73
-                });
74
-            });
75 52
     }
76 53
 
77 54
     /**

+ 0
- 162
modules/UI/invite/RequirePasswordDialog.js Просмотреть файл

@@ -1,162 +0,0 @@
1
-/* global APP */
2
-
3
-import UIUtil from '../util/UIUtil';
4
-
5
-/**
6
- * Show dialog which asks for required conference password.
7
- * @returns {Promise<string>} password or nothing if user canceled
8
- */
9
-export default class RequirePasswordDialog {
10
-    constructor() {
11
-        this.titleKey = 'dialog.passwordRequired';
12
-        this.labelKey = 'dialog.passwordLabel';
13
-        this.errorKey = 'dialog.incorrectPassword';
14
-        this.errorId = 'passwordRequiredError';
15
-        this.inputId = 'passwordRequiredInput';
16
-        this.inputErrorClass = 'error';
17
-        this.isOpened = false;
18
-    }
19
-
20
-    /**
21
-     * Registering dialog listeners
22
-     * @private
23
-     */
24
-    _registerListeners() {
25
-        let el = document.getElementById(this.inputId);
26
-        el.addEventListener('keypress', this._hideError.bind(this));
27
-    }
28
-
29
-    /**
30
-     * Helper method returning dialog body
31
-     * @returns {string}
32
-     * @private
33
-     */
34
-    _getBodyMessage() {
35
-        return (
36
-            `<div class="form-control">
37
-                <label class="input-control__label"
38
-                       data-i18n="${this.labelKey}"></label>
39
-                <input class="input-control__input input-control"
40
-                       name="lockKey" type="text"
41
-                   data-i18n="[placeholder]dialog.password"
42
-                   autofocus id="${this.inputId}">
43
-                <p class="form-control__hint form-control__hint_error hide"
44
-                   id="${this.errorId}"
45
-                   data-i18n="${this.errorKey}"></p>
46
-            </div>`
47
-        );
48
-    }
49
-
50
-    /**
51
-     * Asking for a password
52
-     * @returns {Promise}
53
-     */
54
-    askForPassword() {
55
-        if (!this.isOpened) {
56
-            return this.open();
57
-        }
58
-
59
-        return new Promise((resolve, reject) => {
60
-            this.resolve = resolve;
61
-            this.reject = reject;
62
-            this._showError();
63
-        });
64
-    }
65
-
66
-    /**
67
-     * Opens the dialog
68
-     * @returns {Promise}
69
-     */
70
-    open() {
71
-        let { titleKey } = this;
72
-        let msgString = this._getBodyMessage();
73
-
74
-        return new Promise((resolve, reject) => {
75
-            this.resolve = resolve;
76
-            this.reject = reject;
77
-            let submitFunction = this._submitFunction.bind(this);
78
-            let closeFunction = this._closeFunction.bind(this);
79
-
80
-            this._dialog = APP.UI.messageHandler.openTwoButtonDialog({
81
-                titleKey,
82
-                msgString,
83
-                leftButtonKey: "dialog.Ok",
84
-                submitFunction,
85
-                closeFunction,
86
-                focus: ':input:first'
87
-            });
88
-
89
-            this._registerListeners();
90
-            this.isOpened = true;
91
-        });
92
-    }
93
-
94
-    /**
95
-     * Submit dialog callback
96
-     * @param e - event
97
-     * @param v - value
98
-     * @param m - message
99
-     * @param f - form
100
-     * @private
101
-     */
102
-    _submitFunction(e, v, m, f) {
103
-        e.preventDefault();
104
-        this._processInput(v, f);
105
-    }
106
-
107
-    /**
108
-     * Processing input in dialog
109
-     * @param v - value
110
-     * @param f - form
111
-     * @private
112
-     */
113
-    _processInput(v, f) {
114
-        if (v && f.lockKey) {
115
-            this.resolve(UIUtil.escapeHtml(f.lockKey));
116
-        } else {
117
-            this.reject(APP.UI.messageHandler.CANCEL);
118
-        }
119
-    }
120
-
121
-    /**
122
-     * Close dialog callback
123
-     * @private
124
-     */
125
-    _closeFunction(e, v, m, f) {
126
-        this._processInput(v, f);
127
-        this._hideError();
128
-        this.close();
129
-    }
130
-
131
-    /**
132
-     * Method showing error hint
133
-     * @private
134
-     */
135
-    _showError() {
136
-        let className = this.inputErrorClass;
137
-        let input = document.getElementById(this.inputId);
138
-        document.getElementById(this.errorId).classList.remove('hide');
139
-        input.classList.add(className);
140
-        input.select();
141
-    }
142
-
143
-    /**
144
-     * Method hiding error hint
145
-     * @private
146
-     */
147
-    _hideError() {
148
-        let className = this.inputErrorClass;
149
-        document.getElementById(this.errorId).classList.add('hide');
150
-        document.getElementById(this.inputId).classList.remove(className);
151
-    }
152
-
153
-    /**
154
-     * Close the dialog
155
-     */
156
-    close() {
157
-        if (this._dialog) {
158
-            this._dialog.close();
159
-        }
160
-        this.isOpened = false;
161
-    }
162
-}

+ 0
- 29
modules/UI/invite/RoomLocker.js Просмотреть файл

@@ -1,8 +1,6 @@
1 1
 /* global APP, JitsiMeetJS */
2 2
 const logger = require("jitsi-meet-logger").getLogger(__filename);
3 3
 
4
-import RequirePasswordDialog from './RequirePasswordDialog';
5
-
6 4
 /**
7 5
  * Show notification that user cannot set password for the conference
8 6
  * because server doesn't support that.
@@ -33,7 +31,6 @@ const ConferenceErrors = JitsiMeetJS.errors.conference;
33 31
  */
34 32
 export default function createRoomLocker (room) {
35 33
     let password;
36
-    let requirePasswordDialog = new RequirePasswordDialog();
37 34
     /**
38 35
      * If the room was locked from someone other than us, we indicate it with
39 36
      * this property in order to have correct roomLocker state of isLocked.
@@ -102,31 +99,5 @@ export default function createRoomLocker (room) {
102 99
             password = null;
103 100
         },
104 101
 
105
-        /**
106
-         * Asks user for required conference password.
107
-         */
108
-        requirePassword () {
109
-            return requirePasswordDialog.askForPassword().then(
110
-                newPass => { password = newPass; }
111
-            ).catch(
112
-                reason => {
113
-                    // user canceled, no pass was entered.
114
-                    // clear, as if we use the same instance several times
115
-                    // pass stays between attempts
116
-                    password = null;
117
-                    if (reason !== APP.UI.messageHandler.CANCEL)
118
-                        logger.error(reason);
119
-                }
120
-            );
121
-        },
122
-
123
-        /**
124
-         * Hides require password dialog
125
-         */
126
-        hideRequirePasswordDialog() {
127
-            if (requirePasswordDialog.isOpened) {
128
-                requirePasswordDialog.close();
129
-            }
130
-        }
131 102
     };
132 103
 }

+ 1
- 0
package.json Просмотреть файл

@@ -19,6 +19,7 @@
19 19
     "@atlassian/aui": "6.0.6",
20 20
     "@atlaskit/button": "1.0.3",
21 21
     "@atlaskit/button-group": "1.0.0",
22
+    "@atlaskit/field-text": "2.0.3",
22 23
     "@atlaskit/modal-dialog": "1.2.4",
23 24
     "async": "0.9.0",
24 25
     "autosize": "1.18.13",

+ 2
- 0
react/features/app/components/App.web.js Просмотреть файл

@@ -1,6 +1,8 @@
1 1
 import { appInit } from '../actions';
2 2
 import { AbstractApp } from './AbstractApp';
3 3
 
4
+import '../../room-lock';
5
+
4 6
 /**
5 7
  * Root application component.
6 8
  *

+ 18
- 0
react/features/room-lock/actions.js Просмотреть файл

@@ -1,4 +1,6 @@
1 1
 import { setPassword } from '../base/conference';
2
+import { openDialog } from '../base/dialog';
3
+import { PasswordRequiredPrompt } from './components';
2 4
 
3 5
 import { BEGIN_ROOM_LOCK_REQUEST, END_ROOM_LOCK_REQUEST } from './actionTypes';
4 6
 
@@ -53,3 +55,19 @@ export function endRoomLockRequest(conference, password) {
53 55
         setPassword_.then(endRoomLockRequest_, endRoomLockRequest_);
54 56
     };
55 57
 }
58
+
59
+/**
60
+ * Begins a request to enter password for a specific conference/room.
61
+ *
62
+ * @param {JitsiConference} conference - The JitsiConference
63
+ * requesting password.
64
+ * @protected
65
+ * @returns {{
66
+ *     type: BEGIN_DIALOG_REQUEST,
67
+ *     component: Component,
68
+ *     props: React.PropTypes
69
+ * }}
70
+ */
71
+export function _showPasswordDialog(conference) {
72
+    return openDialog(PasswordRequiredPrompt, { conference });
73
+}

+ 127
- 0
react/features/room-lock/components/PasswordRequiredPrompt.web.js Просмотреть файл

@@ -0,0 +1,127 @@
1
+/* global APP */
2
+import React, { Component } from 'react';
3
+import { connect } from 'react-redux';
4
+import AKFieldText from '@atlaskit/field-text';
5
+
6
+import { setPassword } from '../../base/conference';
7
+import { Dialog } from '../../base/dialog';
8
+import { translate } from '../../base/i18n';
9
+
10
+/**
11
+ * Implements a React Component which prompts the user when a password is
12
+ * required to join a conference.
13
+ */
14
+class PasswordRequiredPrompt extends Component {
15
+    /**
16
+     * PasswordRequiredPrompt component's property types.
17
+     *
18
+     * @static
19
+     */
20
+    static propTypes = {
21
+        /**
22
+         * The JitsiConference which requires a password.
23
+         *
24
+         * @type {JitsiConference}
25
+         */
26
+        conference: React.PropTypes.object,
27
+        dispatch: React.PropTypes.func,
28
+        t: React.PropTypes.func
29
+    }
30
+
31
+    /**
32
+     * Initializes a new PasswordRequiredPrompt instance.
33
+     *
34
+     * @param {Object} props - The read-only properties with which the new
35
+     * instance is to be initialized.
36
+     */
37
+    constructor(props) {
38
+        super(props);
39
+
40
+        this.state = { password: '' };
41
+
42
+        this._onPasswordChanged = this._onPasswordChanged.bind(this);
43
+        this._onSubmit = this._onSubmit.bind(this);
44
+    }
45
+
46
+    /**
47
+     * Implements React's {@link Component#render()}.
48
+     *
49
+     * @inheritdoc
50
+     * @returns {ReactElement}
51
+     */
52
+    render() {
53
+        return (
54
+            <Dialog
55
+                isModal = { true }
56
+                onSubmit = { this._onSubmit }
57
+                titleKey = 'dialog.passwordRequired'
58
+                width = 'small'>
59
+                { this._renderBody() }
60
+            </Dialog>);
61
+    }
62
+
63
+    /**
64
+     * Display component in dialog body.
65
+     *
66
+     * @returns {ReactElement}
67
+     * @protected
68
+     */
69
+    _renderBody() {
70
+        const { t } = this.props;
71
+
72
+        return (
73
+            <div>
74
+                <AKFieldText
75
+                    compact = { true }
76
+                    label = { t('dialog.passwordLabel') }
77
+                    name = 'lockKey'
78
+                    onChange = { this._onPasswordChanged }
79
+                    shouldFitContainer = { true }
80
+                    type = 'text'
81
+                    value = { this.state.password } />
82
+            </div>);
83
+    }
84
+
85
+    /**
86
+     * Notifies this dialog that password has changed.
87
+     *
88
+     * @param {Object} event - The details of the notification/event.
89
+     * @private
90
+     * @returns {void}
91
+     */
92
+    _onPasswordChanged(event) {
93
+        this.setState({ password: event.target.value });
94
+    }
95
+
96
+    /**
97
+     * Dispatches action to submit value from thus dialog.
98
+     *
99
+     * @private
100
+     * @returns {void}
101
+     */
102
+    _onSubmit() {
103
+        const conference = this.props.conference;
104
+
105
+        // we received that password is required, but user is trying
106
+        // anyway to login without a password, mark room as not
107
+        // locked in case he succeeds (maybe someone removed the
108
+        // password meanwhile), if it is still locked another
109
+        // password required will be received and the room again
110
+        // will be marked as locked.
111
+        if (!this.state.password || this.state.password === '') {
112
+            // XXX temporary solution till we move the whole invite logic
113
+            // in react
114
+            APP.conference.invite.setLockedFromElsewhere(false);
115
+        }
116
+
117
+        this.props.dispatch(setPassword(
118
+            conference, conference.join, this.state.password));
119
+
120
+        // we have used the password lets clean it
121
+        this.setState({ password: undefined });
122
+
123
+        return true;
124
+    }
125
+}
126
+
127
+export default translate(connect()(PasswordRequiredPrompt));

+ 0
- 0
react/features/room-lock/components/RoomLockPrompt.web.js Просмотреть файл


+ 1
- 0
react/features/room-lock/components/index.js Просмотреть файл

@@ -1 +1,2 @@
1 1
 export { default as RoomLockPrompt } from './RoomLockPrompt';
2
+export { default as PasswordRequiredPrompt } from './PasswordRequiredPrompt';

+ 1
- 0
react/features/room-lock/index.js Просмотреть файл

@@ -1,4 +1,5 @@
1 1
 export * from './actions';
2 2
 export * from './components';
3 3
 
4
+import './middleware';
4 5
 import './reducer';

+ 36
- 0
react/features/room-lock/middleware.js Просмотреть файл

@@ -0,0 +1,36 @@
1
+/* global APP */
2
+import JitsiMeetJS from '../base/lib-jitsi-meet';
3
+
4
+import { CONFERENCE_FAILED } from '../base/conference';
5
+import { MiddlewareRegistry } from '../base/redux';
6
+import { _showPasswordDialog } from './actions';
7
+
8
+/**
9
+ * Middleware that captures conference failed and checks for password required
10
+ * error and requests a dialog for user to enter password.
11
+ *
12
+ * @param {Store} store - Redux store.
13
+ * @returns {Function}
14
+ */
15
+MiddlewareRegistry.register(store => next => action => {
16
+
17
+    switch (action.type) {
18
+    case CONFERENCE_FAILED: {
19
+        const JitsiConferenceErrors = JitsiMeetJS.errors.conference;
20
+
21
+        if (action.conference
22
+            && JitsiConferenceErrors.PASSWORD_REQUIRED === action.error) {
23
+            // XXX temporary solution till we move the whole invite
24
+            // logic in react
25
+            if (typeof APP !== 'undefined') {
26
+                APP.conference.invite.setLockedFromElsewhere(true);
27
+            }
28
+
29
+            store.dispatch(_showPasswordDialog(action.conference));
30
+        }
31
+        break;
32
+    }
33
+    }
34
+
35
+    return next(action);
36
+});

+ 0
- 5
service/UI/UIEvents.js Просмотреть файл

@@ -150,11 +150,6 @@ export default {
150 150
      */
151 151
     DISPLAY_NAME_CHANGED: "UI.display_name_changed",
152 152
 
153
-    /**
154
-     * Indicates that a password is required for the call.
155
-     */
156
-    PASSWORD_REQUIRED: "UI.password_required",
157
-
158 153
     /**
159 154
      * Show custom popup/tooltip for a specified button.
160 155
      */

Загрузка…
Отмена
Сохранить