summaryrefslogtreecommitdiffstats
path: root/webapp/components/mfa/components/setup.jsx
diff options
context:
space:
mode:
Diffstat (limited to 'webapp/components/mfa/components/setup.jsx')
-rw-r--r--webapp/components/mfa/components/setup.jsx156
1 files changed, 156 insertions, 0 deletions
diff --git a/webapp/components/mfa/components/setup.jsx b/webapp/components/mfa/components/setup.jsx
new file mode 100644
index 000000000..f7a287c15
--- /dev/null
+++ b/webapp/components/mfa/components/setup.jsx
@@ -0,0 +1,156 @@
+// Copyright (c) 2016 Mattermost, Inc. All Rights Reserved.
+// See License.txt for license information.
+
+import {generateMfaSecret, activateMfa} from 'actions/user_actions.jsx';
+
+import UserStore from 'stores/user_store.jsx';
+
+import * as Utils from 'utils/utils.jsx';
+
+import React from 'react';
+import {FormattedMessage, FormattedHTMLMessage} from 'react-intl';
+import {browserHistory} from 'react-router/es6';
+
+export default class Setup extends React.Component {
+ constructor(props) {
+ super(props);
+
+ this.submit = this.submit.bind(this);
+
+ this.state = {secret: '', qrCode: ''};
+ }
+
+ componentDidMount() {
+ const user = UserStore.getCurrentUser();
+ if (!user || user.mfa_active) {
+ browserHistory.push('/');
+ return;
+ }
+
+ generateMfaSecret(
+ (data) => this.setState({secret: data.secret, qrCode: data.qr_code}),
+ (err) => this.setState({serverError: err.message})
+ );
+ }
+
+ submit(e) {
+ e.preventDefault();
+ const code = this.refs.code.value.replace(/\s/g, '');
+ if (!code || code.length === 0) {
+ this.setState({error: Utils.localizeMessage('mfa.setup.codeError', 'Please enter the code from Google Authenticator.')});
+ return;
+ }
+
+ this.setState({error: null});
+
+ activateMfa(
+ code,
+ () => {
+ browserHistory.push('/mfa/confirm');
+ },
+ (err) => {
+ if (err.id === 'ent.mfa.activate.authenticate.app_error') {
+ this.setState({error: Utils.localizeMessage('mfa.setup.badCode', 'Invalid code. If this issue persists, contact your System Administrator.')});
+ return;
+ }
+ this.setState({error: err.message});
+ }
+ );
+ }
+
+ render() {
+ let formClass = 'form-group';
+ let errorContent;
+ if (this.state.error) {
+ errorContent = <div className='form-group has-error'><label className='control-label'>{this.state.error}</label></div>;
+ formClass += ' has-error';
+ }
+
+ let mfaRequired;
+ if (global.window.mm_config.EnforceMultifactorAuthentication) {
+ mfaRequired = (
+ <p>
+ <FormattedHTMLMessage
+ id='mfa.setup.required'
+ defaultMessage='<strong>Multi-factor authentication is required on {siteName}.</strong>'
+ values={{
+ siteName: global.window.mm_config.SiteName
+ }}
+ />
+ </p>
+ );
+ }
+
+ return (
+ <div>
+ <form
+ onSubmit={this.submit}
+ className={formClass}
+ >
+ {mfaRequired}
+ <p>
+ <FormattedHTMLMessage
+ id='mfa.setup.step1'
+ defaultMessage="<strong>Step 1: </strong>On your phone, download Google Authenticator from <a target='_blank' href='https://itunes.apple.com/us/app/google-authenticator/id388497605?mt=8'>iTunes</a> or <a target='_blank' href='https://play.google.com/store/apps/details?id=com.google.android.apps.authenticator2&hl=en'>Google Play</a>"
+ />
+ </p>
+ <p>
+ <FormattedHTMLMessage
+ id='mfa.setup.step2'
+ defaultMessage='<strong>Step 2: </strong>Use Google Authenticator to scan this QR code, or manually type in the secret key'
+ />
+ </p>
+ <div className='form-group'>
+ <div className='col-sm-12'>
+ <img
+ style={{maxHeight: 170}}
+ src={'data:image/png;base64,' + this.state.qrCode}
+ />
+ </div>
+ </div>
+ <br/>
+ <div className='form-group'>
+ <p className='col-sm-12'>
+ <FormattedMessage
+ id='mfa.setup.secret'
+ defaultMessage='Secret: {secret}'
+ values={{
+ secret: this.state.secret
+ }}
+ />
+ </p>
+ </div>
+ <p>
+ <FormattedHTMLMessage
+ id='mfa.setup.step3'
+ defaultMessage='<strong>Step 3: </strong>Enter the code generated by Google Authenticator'
+ />
+ </p>
+ <p>
+ <input
+ ref='code'
+ className='form-control'
+ placeholder={Utils.localizeMessage('mfa.setup.code', 'MFA Code')}
+ autoFocus={true}
+ />
+ </p>
+ {errorContent}
+ <button
+ type='submit'
+ className='btn btn-primary'
+ >
+ <FormattedMessage
+ id='mfa.setup.save'
+ defaultMessage='Save'
+ />
+ </button>
+ </form>
+ </div>
+ );
+ }
+}
+
+Setup.defaultProps = {
+};
+Setup.propTypes = {
+};