Dataset/JS/ReactSignUp/signup.js (131 lines of code) (raw):

import React, { PropTypes } from 'react'; import { bindActionCreators } from 'redux'; import DocumentTitle from 'react-document-title'; import { Link } from 'react-router'; import { reduxForm } from 'redux-form'; import validator from 'validator'; import { Button } from 'react-bootstrap'; import * as api from '../api'; import { auth } from '../actions'; import { getTitle } from './utils'; import { FormGroup } from '../components/form'; import Icon from '../components/icon'; const validate = values => { const { name, email, password } = values; const errors = {}; if (!name || name.length < 3 || name.length > 60) { errors.name = 'Name must be between 3 and 60 characters in length'; } if (!email || !validator.isEmail(email)) { errors.email = 'A valid email address is required'; } if (!password || password.length < 6) { errors.password = 'Password must be at least 6 characters'; } return errors; }; const asyncValidate = values => { const checkName = () => { if (!values.name) return false; return api.isName(values.name) .then(result => { if (result.data) { return { name: 'This name is already in use' }; } }); }; const checkEmail = () => { if (!values.email) return false; return api.isEmail(values.email) .then(result => { if (result.data) { return { email: 'This email is already in use' }; } }); }; return Promise.all([ checkEmail(), checkName(), ]) .then(errors => { return errors.reduce((res, error) => { if (error) { return Object.assign({}, res, error); } return res; }, {}); }); }; export class Signup extends React.Component { constructor(props) { super(props); const { dispatch } = this.props; this.actions = bindActionCreators(auth, dispatch); } handleSubmit(values) { const { name, email, password } = values; return new Promise((resolve, reject) => { api.signup(name, email, password) .then(result => { this.actions.signupComplete(result.data); resolve(); }, error => { reject(error.data); }); }); } render() { const { fields: { name, email, password }, handleSubmit, submitting, } = this.props; const onSubmit = handleSubmit(this.handleSubmit.bind(this)); return ( <DocumentTitle title={getTitle('Signup')}> <div> <h2>Join PodBaby today.</h2> <hr /> <p className="lead"> As a member you can subscribe to podcast feeds and keep track of your favorite episodes. </p> <form className="form-horizontal" onSubmit={onSubmit}> <FormGroup field={name}> <input type="text" className="form-control" placeholder="Name" {...name} /> </FormGroup> <FormGroup field={email}> <input type="email" className="form-control" placeholder="Email address" {...email} /> </FormGroup> <FormGroup field={password}> <input type="password" className="form-control" placeholder="Password" {...password} /> </FormGroup> <Button bsStyle="primary" disabled={submitting} onClick={onSubmit} className="form-control" type="submit" ><Icon icon="sign-in" /> Signup </Button> </form> <p><Link to="/login/">Already a member? Log in here.</Link></p> </div> </DocumentTitle> ); } } Signup.propTypes = { fields: PropTypes.object.isRequired, handleSubmit: PropTypes.func.isRequired, submitting: PropTypes.bool.isRequired, asyncValidating: PropTypes.bool.isRequired, dispatch: PropTypes.func.isRequired, }; const fields = ['name', 'email', 'password']; const asyncBlurFields = ['name', 'email']; export default reduxForm({ form: 'signup', fields, validate, asyncValidate, asyncBlurFields })(Signup);