Validate sign up form and check for email and username uniqueness.
This commit is contained in:
parent
ae5ffe0cd1
commit
bc7dc27443
|
@ -35,6 +35,12 @@ class User {
|
|||
return $user->rowCount() > 0;
|
||||
}
|
||||
|
||||
public function usernameExists ($username) {
|
||||
$query = 'SELECT * FROM users WHERE username=?';
|
||||
$user = $this->db->query($query, array($username));
|
||||
return $user->rowCount() > 0;
|
||||
}
|
||||
|
||||
public function create ($email, $password) {
|
||||
$insert_user_query = 'INSERT INTO users (email, password) VALUES (?, ?)';
|
||||
$password_hash = password_hash($password, PASSWORD_DEFAULT);
|
||||
|
|
|
@ -55,6 +55,34 @@ switch ($action) {
|
|||
'error' => true,
|
||||
), 400);
|
||||
}
|
||||
case 'check-email': {
|
||||
if (isset($request['email'])) {
|
||||
$user = new User();
|
||||
$email_exists = $user->emailExists($request['email']);
|
||||
return Response::json(array(
|
||||
'data' => $email_exists,
|
||||
'error' => false,
|
||||
), 200);
|
||||
}
|
||||
return Response::json(array(
|
||||
'data' => 'Could not check: required information missing',
|
||||
'error' => true,
|
||||
), 400);
|
||||
}
|
||||
case 'check-username': {
|
||||
if (isset($request['username'])) {
|
||||
$user = new User();
|
||||
$username_exists = $user->usernameExists($request['username']);
|
||||
return Response::json(array(
|
||||
'data' => $username_exists,
|
||||
'error' => false,
|
||||
), 200);
|
||||
}
|
||||
return Response::json(array(
|
||||
'data' => 'Could not check: required information missing',
|
||||
'error' => true,
|
||||
), 400);
|
||||
}
|
||||
case 'get-all-dictionary-names': {
|
||||
if ($token !== false) {
|
||||
$user = new User();
|
||||
|
|
|
@ -36,7 +36,8 @@ export class LoginForm extends Component {
|
|||
signupConfirmError: '',
|
||||
signupEmailChecking: false,
|
||||
signupUsernameChecking: false,
|
||||
takenUsernames: [],
|
||||
signupEmailIsUnique: true,
|
||||
signupUsernameIsUnique: true,
|
||||
};
|
||||
}
|
||||
|
||||
|
@ -48,9 +49,9 @@ export class LoginForm extends Component {
|
|||
const requiredFields = ['loginEmail', 'loginPassword', 'signupEmail', 'signupPassword', 'signupConfirm'];
|
||||
const {value, checked} = event.target;
|
||||
const fieldUpdate = {};
|
||||
const errorFieldName = `${field}Error`;
|
||||
let isValid = true;
|
||||
if (requiredFields.includes(field)) {
|
||||
const errorFieldName = `${field}Error`;
|
||||
if (value === '') {
|
||||
isValid = false;
|
||||
fieldUpdate[errorFieldName] = 'This field must not be blank';
|
||||
|
@ -67,47 +68,53 @@ export class LoginForm extends Component {
|
|||
}
|
||||
}
|
||||
|
||||
if (field === 'signupUsername') {
|
||||
if (value !== '' && /[^a-zA-Z0-9]+/g.test(value)) {
|
||||
isValid = false;
|
||||
fieldUpdate[errorFieldName] = 'Please use only letters and numbers';
|
||||
}
|
||||
}
|
||||
|
||||
if (isValid) {
|
||||
fieldUpdate[field] = (field === 'signupAllowEmail') ? checked : value;
|
||||
fieldUpdate[errorFieldName] = '';
|
||||
}
|
||||
fieldUpdate[field] = (field === 'signupAllowEmail') ? checked : value;
|
||||
this.setState(fieldUpdate);
|
||||
}
|
||||
|
||||
checkFieldUnique (field, event) {
|
||||
const uniqueFields = ['signupEmail', 'signupUsername'];
|
||||
const {value} = event.target;
|
||||
const fieldUpdate = {};
|
||||
let isUnique = true;
|
||||
if (uniqueFields.includes(field)) {
|
||||
const errorFieldName = `${field}Error`;
|
||||
|
||||
request('check-email', value, (response) => {
|
||||
|
||||
const errorFieldName = `${field}Error`;
|
||||
if (field === 'signupEmail') {
|
||||
this.setState({ signupEmailChecking: true }, () => {
|
||||
request('check-email', { email: value }, (response) => {
|
||||
const { data, error } = response;
|
||||
fieldUpdate['signupEmailChecking'] = false;
|
||||
if (error) {
|
||||
console.error(data);
|
||||
} else {
|
||||
fieldUpdate['signupEmailIsUnique'] = !data;
|
||||
}
|
||||
}).then(() => {
|
||||
this.setState(fieldUpdate);
|
||||
});
|
||||
});
|
||||
} else if (field === 'signupUsername') {
|
||||
this.setState({ signupUsernameChecking: true }, () => {
|
||||
request('check-username', { username: value }, (response) => {
|
||||
const { data, error } = response;
|
||||
fieldUpdate['signupUsernameChecking'] = false;
|
||||
if (error) {
|
||||
console.error(data);
|
||||
} else {
|
||||
fieldUpdate['signupUsernameIsUnique'] = !data;
|
||||
}
|
||||
}).then(() => {
|
||||
this.setState(fieldUpdate);
|
||||
});
|
||||
});
|
||||
|
||||
if (value === '') {
|
||||
isUnique = false;
|
||||
fieldUpdate[errorFieldName] = 'This field must not be blank';
|
||||
} else if (field.includes('Email') && !/.+@.+/g.test(value)) {
|
||||
isUnique = false;
|
||||
fieldUpdate[errorFieldName] = 'The email address you entered looks wrong';
|
||||
} else if (field === 'signupPassword' && value.length < 6) {
|
||||
isUnique = false;
|
||||
fieldUpdate[errorFieldName] = 'Please make your password at least 6 characters long';
|
||||
} else if ((field === 'signupPassword' && value !== this.state.signupConfirm)
|
||||
|| (field === 'signupConfirm' && value !== this.state.signupPassword)) {
|
||||
isUnique = false;
|
||||
fieldUpdate[errorFieldName] = 'Your passwords must match';
|
||||
}
|
||||
}
|
||||
|
||||
if (field === 'signupUsername' && value !== '') {
|
||||
if (this.state.takenUsernames.length < 1) {
|
||||
fetch()
|
||||
}
|
||||
}
|
||||
|
||||
this.setState(fieldUpdate);
|
||||
}
|
||||
|
||||
render () {
|
||||
|
@ -181,9 +188,20 @@ export class LoginForm extends Component {
|
|||
<label className='label'>
|
||||
Email Address<sup>*</sup>
|
||||
</label>
|
||||
<div className='control'>
|
||||
<input className='input' type='email' value={this.state.signupEmail}
|
||||
onInput={(event) => this.updateField('signupEmail', event)} />
|
||||
<div className={`control ${this.state.signupEmailChecking && 'is-loading'}`}>
|
||||
<input className={`input ${(this.state.signupEmailError !== '' || !this.state.signupEmailIsUnique) && 'is-danger'}`}
|
||||
type='email' value={this.state.signupEmail}
|
||||
onInput={(event) => this.updateField('signupEmail', event)}
|
||||
onBlur={(event) => this.checkFieldUnique('signupEmail', event)} />
|
||||
{
|
||||
(this.state.signupEmailError !== '' || !this.state.signupEmailIsUnique)
|
||||
? (
|
||||
<div className='help is-danger'>
|
||||
{!this.state.signupEmailIsUnique && <p>This email address is already in use</p>}
|
||||
{this.state.signupEmailError}
|
||||
</div>
|
||||
) : null
|
||||
}
|
||||
</div>
|
||||
</div>
|
||||
<div className='field'>
|
||||
|
@ -193,9 +211,20 @@ export class LoginForm extends Component {
|
|||
<div className='help'>
|
||||
This is your unique identifier that appears in the URL if you ever decide to share your dictionaries publicly.
|
||||
</div>
|
||||
<div className='control'>
|
||||
<input className='input' type='text' value={this.state.signupUsername}
|
||||
onInput={(event) => this.updateField('signupUsername', event)} />
|
||||
<div className={`control ${this.state.signupUsernameChecking && 'is-loading'}`}>
|
||||
<input className={`input ${!this.state.signupUsernameIsUnique && 'is-danger'}`}
|
||||
type='text' value={this.state.signupUsername}
|
||||
onInput={(event) => this.updateField('signupUsername', event)}
|
||||
onBlur={(event) => this.checkFieldUnique('signupUsername', event)} />
|
||||
{
|
||||
(this.state.signupUsernameError !== '' || !this.state.signupUsernameIsUnique)
|
||||
? (
|
||||
<div className='help is-danger'>
|
||||
{!this.state.signupUsernameIsUnique && <p>This username address is already in use</p>}
|
||||
{this.state.signupUsernameError}
|
||||
</div>
|
||||
) : null
|
||||
}
|
||||
</div>
|
||||
</div>
|
||||
<div className='field'>
|
||||
|
@ -206,7 +235,8 @@ export class LoginForm extends Component {
|
|||
This is the name we greet you with and what we display if you ever decide to share your dictionaries publicly.
|
||||
</div>
|
||||
<div className='control'>
|
||||
<input className='input' type='text' value={this.state.signupPublicName}
|
||||
<input className='input'
|
||||
type='text' value={this.state.signupPublicName}
|
||||
onInput={(event) => this.updateField('signupPublicName', event)} />
|
||||
</div>
|
||||
</div>
|
||||
|
@ -215,8 +245,17 @@ export class LoginForm extends Component {
|
|||
Password<sup>*</sup>
|
||||
</label>
|
||||
<div className='control'>
|
||||
<input className='input' type='password' value={this.state.signupPassword}
|
||||
<input className={`input ${this.state.signupPasswordError !== '' && 'is-danger'}`}
|
||||
type='password' value={this.state.signupPassword}
|
||||
onInput={(event) => this.updateField('signupPassword', event)} />
|
||||
{
|
||||
this.state.signupPasswordError !== ''
|
||||
? (
|
||||
<div className='help is-danger'>
|
||||
{this.state.signupPasswordError}
|
||||
</div>
|
||||
) : null
|
||||
}
|
||||
</div>
|
||||
</div>
|
||||
<div className='field'>
|
||||
|
@ -224,8 +263,17 @@ export class LoginForm extends Component {
|
|||
Confirm Password<sup>*</sup>
|
||||
</label>
|
||||
<div className='control'>
|
||||
<input className='input' type='password' value={this.state.signupConfirm}
|
||||
<input className={`input ${this.state.signupConfirmError !== '' && 'is-danger'}`}
|
||||
type='password' value={this.state.signupConfirm}
|
||||
onInput={(event) => this.updateField('signupConfirm', event)} />
|
||||
{
|
||||
this.state.signupConfirmError !== ''
|
||||
? (
|
||||
<div className='help is-danger'>
|
||||
{this.state.signupConfirmError}
|
||||
</div>
|
||||
) : null
|
||||
}
|
||||
</div>
|
||||
</div>
|
||||
<div className='field'>
|
||||
|
|
Loading…
Reference in New Issue