Added bcrypt for password hashing

This commit is contained in:
Ritchie Martori 2013-07-15 14:07:17 -07:00
parent 3f7e4b693a
commit aa8d1bb853
4 changed files with 67 additions and 8 deletions

View File

@ -12,6 +12,20 @@
// Class level permissions // Class level permissions
// blog posts
allow: ['owner', 'admin'] to: '*' // allow owner's of posts and admins to do anything
allow: '*' to: ['find', 'read'] // allow everyone to read and find
// comments
allow '*' to: ['find', 'read'] // read aka findById
allow 'user' to: ['create']
allow ['owner', 'admin'] to: '*'
// users only section
allow: '*' to: ['find', 'read', 'create']
allow: 'owner' to: ['*.destroy', '*.save']
// scopes // scopes
// URL level permissions // URL level permissions

View File

@ -2,16 +2,21 @@
* Module Dependencies. * Module Dependencies.
*/ */
var ModelBuilder = require('jugglingdb').ModelBuilder var ModelBuilder = require('jugglingdb').ModelBuilder;
var modeler = new ModelBuilder(); var modeler = new ModelBuilder();
/** /**
* Extends from the built in `asteroid.Model` type. * Define the built in asteroid.Model.
*/ */
var Model = module.exports = modeler.define('model'); var Model = module.exports = modeler.define('model');
Model.shared = true; Model.shared = true;
/*!
* For **remoting**. Construct objects when calling instance methods remotely.
*/
Model.sharedCtor = function (data, id, fn) { Model.sharedCtor = function (data, id, fn) {
var ModelCtor = this; var ModelCtor = this;
@ -87,12 +92,17 @@ Model.afterRemote = function (name, fn) {
} }
/*! /*!
* Setup extended models. * Called when a model is extended.
*/ */
Model.setup = function () { Model.setup = function () {
var ModelCtor = this; var ModelCtor = this;
// each model has its
// own access control
// list
Model.acl = [];
ModelCtor.sharedCtor.accepts = [ ModelCtor.sharedCtor.accepts = [
{arg: 'data', type: 'object', http: {source: 'body'}}, {arg: 'data', type: 'object', http: {source: 'body'}},
{arg: 'id', type: 'any', http: {source: 'url'}} {arg: 'id', type: 'any', http: {source: 'url'}}

View File

@ -5,7 +5,9 @@
var Model = require('../asteroid').Model var Model = require('../asteroid').Model
, asteroid = require('../asteroid') , asteroid = require('../asteroid')
, path = require('path') , path = require('path')
, SALT_WORK_FACTOR = 10
, crypto = require('crypto') , crypto = require('crypto')
, bcrypt = require('bcrypt')
, passport = require('passport') , passport = require('passport')
, LocalStrategy = require('passport-local').Strategy; , LocalStrategy = require('passport-local').Strategy;
@ -128,8 +130,14 @@ User.logout = function (sid, fn) {
*/ */
User.prototype.hasPassword = function (plain, fn) { User.prototype.hasPassword = function (plain, fn) {
// TODO - bcrypt if(this.password && plain) {
fn(null, this.password === plain); bcrypt.compare(plain, this.password, function(err, isMatch) {
if(err) return fn(err);
fn(null, isMatch);
});
} else {
fn(null, false);
}
} }
/** /**
@ -233,6 +241,11 @@ User.confirm = function (uid, token, redirect, fn) {
}); });
} }
User.setter.password = function (plain) {
var salt = bcrypt.genSaltSync(this.constructor.settings.saltWorkFactor || SALT_WORK_FACTOR);
this._password = bcrypt.hashSync(plain, salt);
}
/** /**
* Setup an extended user model. * Setup an extended user model.
*/ */

View File

@ -162,12 +162,34 @@ describe('User', function(){
describe('user.hasPassword(plain, fn)', function(){ describe('user.hasPassword(plain, fn)', function(){
it('Determine if the password matches the stored password.', function(done) { it('Determine if the password matches the stored password.', function(done) {
var u = new User({username: 'foo', password: 'bar'}); var u = new User({username: 'foo', password: 'bar'});
u.hasPassword('bar', function (err, isMatch) { u.hasPassword('bar', function (err, isMatch) {
assert(isMatch, 'password doesnt match'); assert(isMatch, 'password doesnt match');
done(); done();
}); });
}); });
it('should match a password after it is changed', function(done) {
User.create({email: 'foo@baz.net', username: 'bat', password: 'baz'}, function (err, user) {
User.findById(user.id, function (err, foundUser) {
assert(foundUser);
foundUser.hasPassword('baz', function (err, isMatch) {
assert(isMatch);
foundUser.password = 'baz2';
foundUser.save(function (err, updatedUser) {
updatedUser.hasPassword('baz2', function (err, isMatch) {
assert(isMatch);
User.findById(user.id, function (err, uu) {
uu.hasPassword('baz2', function (err, isMatch) {
assert(isMatch);
done();
});
});
});
});
});
});
});
});
}); });
describe('Verification', function(){ describe('Verification', function(){