276 lines
9.3 KiB
JavaScript
Raw Normal View History

/**
*
* AuthPage
*
*/
import React from 'react';
import PropTypes from 'prop-types';
import { connect } from 'react-redux';
import { bindActionCreators, compose } from 'redux';
2017-11-10 14:20:33 +01:00
import { Link } from 'react-router-dom';
import { FormattedMessage } from 'react-intl';
import { findIndex, get, isBoolean, isEmpty, map, replace } from 'lodash';
2017-11-09 18:07:55 +01:00
import cn from 'classnames';
2017-11-10 14:20:33 +01:00
// Logo
import LogoStrapi from 'assets/images/logo_strapi.png';
// Design
2017-11-09 18:07:55 +01:00
import Button from 'components/Button';
import Input from 'components/InputsIndex';
// Utils
import injectSaga from 'utils/injectSaga';
import injectReducer from 'utils/injectReducer';
import {
2017-12-15 13:24:08 +01:00
hideLoginErrorsInput,
onChangeInput,
2017-11-09 18:07:55 +01:00
setErrors,
setForm,
2017-11-10 14:20:33 +01:00
submit,
} from './actions';
import form from './form.json';
import reducer from './reducer';
import saga from './saga';
import makeSelectAuthPage from './selectors';
import styles from './styles.scss';
export class AuthPage extends React.Component { // eslint-disable-line react/prefer-stateless-function
componentDidMount() {
const params = this.props.location.search ? replace(this.props.location.search, '?code=', '') : this.props.match.params.id;
this.props.setForm(this.props.match.params.authType, params);
}
componentWillReceiveProps(nextProps) {
if (this.props.match.params.authType !== nextProps.match.params.authType) {
const params = nextProps.location.search ? replace(nextProps.location.search, '?code=', '') : nextProps.match.params.id;
this.props.setForm(nextProps.match.params.authType, params);
2017-12-15 13:24:08 +01:00
this.props.hideLoginErrorsInput(false);
2017-11-10 14:20:33 +01:00
}
if (nextProps.submitSuccess) {
switch (this.props.match.params.authType) {
case 'login':
case 'reset-password':
2017-11-10 14:20:33 +01:00
this.props.history.push('/');
break;
case 'register':
2017-11-16 15:51:12 +01:00
this.props.history.push('/');
// NOTE: prepare for comfirm email;
// this.props.history.push(`/plugins/users-permissions/auth/register-success/${this.props.modifiedData.email}`);
2017-11-10 14:20:33 +01:00
break;
default:
}
}
}
2017-11-09 18:07:55 +01:00
handleSubmit = (e) => {
e.preventDefault();
2017-11-10 12:26:51 +01:00
const formErrors = Object.keys(this.props.modifiedData).reduce((acc, key) => {
if (isEmpty(get(this.props.modifiedData, key)) && !isBoolean(get(this.props.modifiedData, key))) {
acc.push({ name: key, errors: [{ id: 'components.Input.error.validation.required' }] });
}
if (!isEmpty(get(this.props.modifiedData, 'password')) && !isEmpty(get(this.props.modifiedData, 'confirmPassword')) && findIndex(acc, ['name', 'confirmPassword']) === -1) {
if (get(this.props.modifiedData, 'password') !== get(this.props.modifiedData, 'confirmPassword')) {
acc.push({ name: 'confirmPassword', errors: [{ id: 'users-permissions.components.Input.error.password.noMatch' }] });
}
}
return acc;
}, []);
this.props.setErrors(formErrors);
2017-11-10 14:20:33 +01:00
if (isEmpty(formErrors)) {
this.props.submit(this.context);
2017-11-10 14:20:33 +01:00
}
2017-11-09 18:07:55 +01:00
}
renderButton = () => {
const { match: { params: { authType } }, submitSuccess } = this.props;
2017-11-09 18:07:55 +01:00
if (this.props.match.params.authType === 'login') {
return (
<div className={cn('col-md-6', styles.loginButton)}>
<Button primary label="users-permissions.Auth.form.button.login" type="submit" />
</div>
);
}
const isEmailForgotSent = authType === 'forgot-password' && submitSuccess;
const label = isEmailForgotSent ? 'users-permissions.Auth.form.button.forgot-password.success' : `users-permissions.Auth.form.button.${this.props.match.params.authType}`;
2017-11-09 18:07:55 +01:00
return (
<div className={cn('col-md-12', styles.buttonContainer)}>
<Button
className={cn(isEmailForgotSent && styles.buttonForgotSuccess)}
2017-12-04 17:32:45 +01:00
label={label}
2017-11-09 18:07:55 +01:00
style={{ width: '100%' }}
primary={!isEmailForgotSent}
2017-11-09 18:07:55 +01:00
type="submit"
/>
</div>
);
}
2017-11-10 14:20:33 +01:00
renderLink = () => {
if (this.props.match.params.authType === 'login') {
return (
<Link to="/plugins/users-permissions/auth/forgot-password">
<FormattedMessage id="users-permissions.Auth.link.forgot-password" />
</Link>
);
}
if (this.props.match.params.authType === 'forgot-password' || this.props.match.params.authType === 'register-success') {
return (
<Link to="/plugins/users-permissions/auth/login">
<FormattedMessage id="users-permissions.Auth.link.ready" />
</Link>
);
}
return <div />;
}
renderInputs = () => {
const { match: { params: { authType } } } = this.props;
const inputs = get(form, ['form', authType]);
return map(inputs, (input, key) => (
<Input
autoFocus={key === 0}
customBootstrapClass={get(input, 'customBootstrapClass')}
didCheckErrors={this.props.didCheckErrors}
errors={get(this.props.formErrors, [findIndex(this.props.formErrors, ['name', input.name]), 'errors'])}
key={get(input, 'name')}
label={authType === 'forgot-password' && this.props.submitSuccess? { id: 'users-permissions.Auth.form.forgot-password.email.label.success' } : get(input, 'label')}
name={get(input, 'name')}
onChange={this.props.onChangeInput}
placeholder={get(input, 'placeholder')}
type={get(input, 'type')}
validations={{ required: true }}
value={get(this.props.modifiedData, get(input, 'name'), get(input, 'value'))}
noErrorsDescription={this.props.noErrorsDescription}
/>
));
}
render() {
const { match: { params: { authType } }, modifiedData, submitSuccess } = this.props;
let divStyle = authType === 'register' ? { marginTop: '3.2rem' } : { marginTop: '.9rem' };
if (authType === 'forgot-password' && submitSuccess) {
divStyle = { marginTop: '.9rem', minHeight: '18.2rem' };
}
return (
<div className={styles.authPage}>
<div className={styles.wrapper}>
2017-11-10 14:20:33 +01:00
<div className={styles.headerContainer}>
{this.props.match.params.authType === 'register' ? (
<FormattedMessage id="users-permissions.Auth.form.header.register" />
) : (
<img src={LogoStrapi} alt="logo" />
)}
</div>
<div className={styles.headerDescription}>
{authType === 'register' && <FormattedMessage id="users-permissions.Auth.header.register.description" />}
2017-11-10 14:20:33 +01:00
</div>
<div
className={cn(
styles.formContainer,
authType === 'forgot-password' && submitSuccess ? styles.borderedSuccess : styles.bordered,
)}
style={divStyle}
>
2017-11-09 18:07:55 +01:00
<form onSubmit={this.handleSubmit}>
<div className="container-fluid">
2017-12-15 13:24:08 +01:00
{this.props.noErrorsDescription && !isEmpty(get(this.props.formErrors, ['0', 'errors', '0', 'id']))? (
<div className={styles.errorsContainer}>
<FormattedMessage id={get(this.props.formErrors, ['0', 'errors', '0', 'id'])} />
</div>
): ''}
2017-11-09 18:07:55 +01:00
<div className="row" style={{ textAlign: 'start' }}>
{!submitSuccess && this.renderInputs()}
{ authType === 'forgot-password' && submitSuccess && (
<div className={styles.forgotSuccess}>
<FormattedMessage id="users-permissions.Auth.form.forgot-password.email.label.success" />
<br />
<p>{get(modifiedData, 'email', '')}</p>
</div>
)}
2017-11-09 18:09:48 +01:00
{this.renderButton()}
2017-11-09 18:07:55 +01:00
</div>
</div>
2017-11-09 18:07:55 +01:00
</form>
</div>
2017-11-10 14:20:33 +01:00
<div className={styles.linkContainer}>
{this.renderLink()}
</div>
</div>
{authType === 'register' && <div className={styles.logoContainer}><img src={LogoStrapi} alt="logo" /></div>}
</div>
);
}
}
AuthPage.contextTypes = {
updatePlugin: PropTypes.func,
};
AuthPage.propTypes = {
2017-11-10 12:26:51 +01:00
didCheckErrors: PropTypes.bool.isRequired,
formErrors: PropTypes.array.isRequired,
2017-12-15 13:24:08 +01:00
hideLoginErrorsInput: PropTypes.func.isRequired,
2017-11-10 14:20:33 +01:00
history: PropTypes.object.isRequired,
location: PropTypes.object.isRequired,
match: PropTypes.object.isRequired,
modifiedData: PropTypes.object.isRequired,
2017-12-15 13:24:08 +01:00
noErrorsDescription: PropTypes.bool.isRequired,
onChangeInput: PropTypes.func.isRequired,
2017-11-09 18:07:55 +01:00
setErrors: PropTypes.func.isRequired,
setForm: PropTypes.func.isRequired,
2017-11-10 14:20:33 +01:00
submit: PropTypes.func.isRequired,
submitSuccess: PropTypes.bool.isRequired,
};
const mapStateToProps = makeSelectAuthPage();
function mapDispatchToProps(dispatch) {
return bindActionCreators(
{
2017-12-15 13:24:08 +01:00
hideLoginErrorsInput,
onChangeInput,
2017-11-09 18:07:55 +01:00
setErrors,
setForm,
2017-11-10 14:20:33 +01:00
submit,
},
dispatch
);
}
const withConnect = connect(mapStateToProps, mapDispatchToProps);
/* Remove this line if the container doesn't have a route and
* check the documentation to see how to create the container's store
*/
const withReducer = injectReducer({ key: 'authPage', reducer });
/* Remove the line below the container doesn't have a route and
* check the documentation to see how to create the container's store
*/
const withSaga = injectSaga({ key: 'authPage', saga });
export default compose(
withReducer,
withSaga,
withConnect,
)(AuthPage);