mirror of
https://github.com/mmumshad/ansible-playable.git
synced 2025-03-09 23:38:54 +00:00
Initial Commit
This commit is contained in:
commit
c92f737237
273 changed files with 16964 additions and 0 deletions
258
server/api/user/user.model.js
Normal file
258
server/api/user/user.model.js
Normal file
|
@ -0,0 +1,258 @@
|
|||
'use strict';
|
||||
/*eslint no-invalid-this:0*/
|
||||
import crypto from 'crypto';
|
||||
mongoose.Promise = require('bluebird');
|
||||
import mongoose, {Schema} from 'mongoose';
|
||||
import {registerEvents} from './user.events';
|
||||
|
||||
const authTypes = ['github', 'twitter', 'facebook', 'google'];
|
||||
|
||||
var UserSchema = new Schema({
|
||||
name: String,
|
||||
email: {
|
||||
type: String,
|
||||
lowercase: true,
|
||||
required() {
|
||||
if(authTypes.indexOf(this.provider) === -1) {
|
||||
return true;
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
},
|
||||
role: {
|
||||
type: String,
|
||||
default: 'user'
|
||||
},
|
||||
password: {
|
||||
type: String,
|
||||
required() {
|
||||
if(authTypes.indexOf(this.provider) === -1) {
|
||||
return true;
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
},
|
||||
provider: String,
|
||||
salt: String,
|
||||
facebook: {},
|
||||
google: {},
|
||||
github: {}
|
||||
});
|
||||
|
||||
/**
|
||||
* Virtuals
|
||||
*/
|
||||
|
||||
// Public profile information
|
||||
UserSchema
|
||||
.virtual('profile')
|
||||
.get(function() {
|
||||
return {
|
||||
name: this.name,
|
||||
role: this.role
|
||||
};
|
||||
});
|
||||
|
||||
// Non-sensitive info we'll be putting in the token
|
||||
UserSchema
|
||||
.virtual('token')
|
||||
.get(function() {
|
||||
return {
|
||||
_id: this._id,
|
||||
role: this.role
|
||||
};
|
||||
});
|
||||
|
||||
/**
|
||||
* Validations
|
||||
*/
|
||||
|
||||
// Validate empty email
|
||||
UserSchema
|
||||
.path('email')
|
||||
.validate(function(email) {
|
||||
if(authTypes.indexOf(this.provider) !== -1) {
|
||||
return true;
|
||||
}
|
||||
return email.length;
|
||||
}, 'Email cannot be blank');
|
||||
|
||||
// Validate empty password
|
||||
UserSchema
|
||||
.path('password')
|
||||
.validate(function(password) {
|
||||
if(authTypes.indexOf(this.provider) !== -1) {
|
||||
return true;
|
||||
}
|
||||
return password.length;
|
||||
}, 'Password cannot be blank');
|
||||
|
||||
// Validate email is not taken
|
||||
UserSchema
|
||||
.path('email')
|
||||
.validate(function(value) {
|
||||
if(authTypes.indexOf(this.provider) !== -1) {
|
||||
return true;
|
||||
}
|
||||
|
||||
return this.constructor.findOne({ email: value }).exec()
|
||||
.then(user => {
|
||||
if(user) {
|
||||
if(this.id === user.id) {
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
})
|
||||
.catch(function(err) {
|
||||
throw err;
|
||||
});
|
||||
}, 'The specified email address is already in use.');
|
||||
|
||||
var validatePresenceOf = function(value) {
|
||||
return value && value.length;
|
||||
};
|
||||
|
||||
/**
|
||||
* Pre-save hook
|
||||
*/
|
||||
UserSchema
|
||||
.pre('save', function(next) {
|
||||
// Handle new/update passwords
|
||||
if(!this.isModified('password')) {
|
||||
return next();
|
||||
}
|
||||
|
||||
if(!validatePresenceOf(this.password)) {
|
||||
if(authTypes.indexOf(this.provider) === -1) {
|
||||
return next(new Error('Invalid password'));
|
||||
} else {
|
||||
return next();
|
||||
}
|
||||
}
|
||||
|
||||
// Make salt with a callback
|
||||
this.makeSalt((saltErr, salt) => {
|
||||
if(saltErr) {
|
||||
return next(saltErr);
|
||||
}
|
||||
this.salt = salt;
|
||||
this.encryptPassword(this.password, (encryptErr, hashedPassword) => {
|
||||
if(encryptErr) {
|
||||
return next(encryptErr);
|
||||
}
|
||||
this.password = hashedPassword;
|
||||
return next();
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
/**
|
||||
* Methods
|
||||
*/
|
||||
UserSchema.methods = {
|
||||
/**
|
||||
* Authenticate - check if the passwords are the same
|
||||
*
|
||||
* @param {String} password
|
||||
* @param {Function} callback
|
||||
* @return {Boolean}
|
||||
* @api public
|
||||
*/
|
||||
authenticate(password, callback) {
|
||||
if(!callback) {
|
||||
return this.password === this.encryptPassword(password);
|
||||
}
|
||||
|
||||
this.encryptPassword(password, (err, pwdGen) => {
|
||||
if(err) {
|
||||
return callback(err);
|
||||
}
|
||||
|
||||
if(this.password === pwdGen) {
|
||||
return callback(null, true);
|
||||
} else {
|
||||
return callback(null, false);
|
||||
}
|
||||
});
|
||||
},
|
||||
|
||||
/**
|
||||
* Make salt
|
||||
*
|
||||
* @param {Number} [byteSize] - Optional salt byte size, default to 16
|
||||
* @param {Function} callback
|
||||
* @return {String}
|
||||
* @api public
|
||||
*/
|
||||
makeSalt(...args) {
|
||||
let byteSize;
|
||||
let callback;
|
||||
let defaultByteSize = 16;
|
||||
|
||||
if(typeof args[0] === 'function') {
|
||||
callback = args[0];
|
||||
byteSize = defaultByteSize;
|
||||
} else if(typeof args[1] === 'function') {
|
||||
callback = args[1];
|
||||
} else {
|
||||
throw new Error('Missing Callback');
|
||||
}
|
||||
|
||||
if(!byteSize) {
|
||||
byteSize = defaultByteSize;
|
||||
}
|
||||
|
||||
return crypto.randomBytes(byteSize, (err, salt) => {
|
||||
if(err) {
|
||||
return callback(err);
|
||||
} else {
|
||||
return callback(null, salt.toString('base64'));
|
||||
}
|
||||
});
|
||||
},
|
||||
|
||||
/**
|
||||
* Encrypt password
|
||||
*
|
||||
* @param {String} password
|
||||
* @param {Function} callback
|
||||
* @return {String}
|
||||
* @api public
|
||||
*/
|
||||
encryptPassword(password, callback) {
|
||||
if(!password || !this.salt) {
|
||||
if(!callback) {
|
||||
return null;
|
||||
} else {
|
||||
return callback('Missing password or salt');
|
||||
}
|
||||
}
|
||||
|
||||
var defaultIterations = 10000;
|
||||
var defaultKeyLength = 64;
|
||||
var salt = new Buffer(this.salt, 'base64');
|
||||
|
||||
if(!callback) {
|
||||
// eslint-disable-next-line no-sync
|
||||
return crypto.pbkdf2Sync(password, salt, defaultIterations,
|
||||
defaultKeyLength, 'sha1')
|
||||
.toString('base64');
|
||||
}
|
||||
|
||||
return crypto.pbkdf2(password, salt, defaultIterations, defaultKeyLength,
|
||||
'sha1', (err, key) => {
|
||||
if(err) {
|
||||
return callback(err);
|
||||
} else {
|
||||
return callback(null, key.toString('base64'));
|
||||
}
|
||||
});
|
||||
}
|
||||
};
|
||||
|
||||
registerEvents(UserSchema);
|
||||
export default mongoose.model('User', UserSchema);
|
Loading…
Add table
Add a link
Reference in a new issue