crypto pbkdf2 is not called - node.js

I have written an function to hashpasswords with crypto.obkdf2. This function was working fine, but for some reason he doesn't anymore.
EDIT
In a controller I want to create an user with the user.service:
account.controller:
userService.createAccount(details, true, function(err, result){
if(err){
res.status(500).json({message: err});
}else{
//account is created, details are mailed, now we can set the user on the order
user = result;
}
})
The service does a few checks and call the user.register function
user.service
function createAccount (details, generatePassword, callback){
console.log("createAccount");
//generate password, save details + password, mail details, send results back in callback
//if(generatePassword){
// details.password = random(10);
//}
details.password = '7eb4f68ea4';
var userData = _.pick(details, 'firstName', 'lastNamePrefix', 'lastName','email','gender', 'password');
userData.verificationCode = random(8);
userData.userName = userData.email;
console.log("userdate", userData);
User.register(userData, function(err, user){
console.log("register user", err);
if(err && (11000 == err.code || 11001 == err.code)) {
console.log("E-mailadres already in use");
return callback("E-mailadres already in use");
}
if (err) {
console.log("Something went terribly wrong...", err);
return callback("Something went wrong: " + err)
}
var options = {
to: user.email,
subject: 'Uw account op Prisma Note',
template: 'new-account'
}
//Mail sturen met activatielink na aanmaken
mailService.mail(options, user, null, function(err, data){
console.log("sendmail!");
if (err) {
console.log("error sending mail", err);
return callback("Error sending mail: " + err.message);
}else{
console.log("hier!", user);
return callback(null, user);
}
});
})
}
The user.modal contains the register function:
user.model
User.statics.register = function(opts, callback) {
console.log("register!");
var self = this;
var data = _.cloneDeep(opts);
passwordService.hash(opts.password, function(err, hashedPassword, salt) {
if (err) {
console.log("passwordsrv", err);
return callback(err, null);
}
data.password = hashedPassword;
data.passwordSalt = salt;
self.model('User').create(data, function(err, user) {
if (err) {
console.log("createuser", err);
return callback(err, null);
}
user.password = undefined;
user.passwordSalt = undefined;
callback(err, user);
})
})
}
And finally, the code comes to the passwordService
password.service
var LEN = 256;
var SALT_LEN = 64;
var ITERATIONS = 10000;
var DIGEST = 'sha256';
function hashPassword(password, salt, callback){
console.log("hashPassword");
var len = LEN /2;
if (3 === arguments.length) {
crypto.pbkdf2(password, salt, ITERATIONS, len, DIGEST, function(err, derivedKey) {
if (err) {
console.log("crypto err", err);
return callback(err);
}
return callback(null, derivedKey.toString('hex'));
})
} else {
console.log("pwdsrv");
callback = salt;
crypto.randomBytes(SALT_LEN / 2, function(err, salt) {
if (err) {
console.log("randombyte", err);
return callback(err);
}
salt = salt.toString('hex');
console.log("hier");
console.log(password, salt, ITERATIONS, len, DIGEST);
//password = '7eb4f68ea4'
//salt = '21aaac28b8411326b8df5b8b60476904f58d40f972a2f5d698ec4d0fb57dc315'
//ITERATIONS = 10000
//len = 128
//DIGEST = 'sha256'
crypto.pbkdf2(password, salt, ITERATIONS, len, DIGEST, function(err, derivedKey) {
console.log("hjioo");
if (err) {
console.log("pbkdf2", err);
return callback(err);
}
console.log("hier");
callback(null, derivedKey.toString('hex'), salt);
})
})
}
}
This function is called from our 'user model'. That model has an User.statics.register function what we can call. After a lot of debugging lines I have found out the code stops at (in my tested cases) crypto.pbkdf2(password, salt, ITERATIONS, len, DIGEST, function(err, derivedKey) in the else of the function. The log before this function show the content of the variables, but I can't see the logs in the function.
I have no idea, why this is stopped working. We have updated our node.JS version, but since this is an node module, that must be no problem.
Can somebody help me to solve this problem, so our users can register again?
The mailservice, which you can see in the service, sends an email via Amazon SES, I think it is not relevant to post that code.

Related

error while hashing password using bcrypt in NodeJs and Typescript

I need help with my codes. I have successfully sent the hashed password to the database, but the login/authentication part where the "compare" is done isn't working. Its mostly saying password is undefined.
Here is the logic.
const salt = bcrypt.genSaltSync(10);
let tohash;
function hashPass(password) {
tohash = bcrypt.hashSync(password, salt, function (err, hash) {
if (err) return err;
user.password = hash;
});
console.log('Password is ' + password);
console.log('Tohash is ' + tohash);
return { tohash: tohash };
}
function correctpass(password, user) {
console.log('Tohash here is ' + tohash);
let deHash = bcrypt.compare(password, user.password, function (err, result) {
console.log('Password is ' + password);
if (err) {
console.log('Incorrect password');
}
console.log('Correct Password');
return result;
});
return { deHash: deHash };
}
export { hashPass };
export { correctpass };
Here is where the invocation is done using Sequelize
const unHash = correctpass(password);
try {
user.findOne({
where: {
id : 55,
email: "preciousegunjobi05#yahoo.com",
//password: isPasswordCorrect.password.toString(),
password: unHash.deHash(req.body.password),
user_type: "tutor"
}
}).then(userdetails => {
res.send(userdetails);
console.log("data is " + userdetails);

Setting a function callback fram an async request

Good Morning All,
I have been looking for an answer to this on the boards, but my noob brain just can't make sense of it.
i have this function in models/user.js
module.exports.getUserByUsername = function(username, callback){
var retUser = new User;
sql.connect(dbConfig, function(err) {
if (err) {
console.log(err);
callback();
}
// create Request object
var request = new sql.Request();
request.input('ip_username', sql.NVarChar, username)
// query to the database and get the records
request.query('select * from [portal_users] where username = #ip_username', function(err, recordset) {
if (err) {
console.log(err);
return;
} else {
var user = new User(recordset.recordset[0].username,recordset.recordset[0].password,recordset.recordset[0].email,recordset.recordset[0].name);
user.addID(recordset.recordset[0].id);
retUser = user;
}
callback();
// send records as a response
//res.send(recordset);
});
});
function callback() {
sql.close();
return retUser;
};
}
and this code in my routes/user.js
passport.use(new LocalStrategy(
function(username, password, done) {
User.getUserByUsername(username, function(err, user){
if(err) throw err;
if(!user){
return done(null, false, {message: 'Unknown User'});
}
User.comparePassword(password, user.password, function(err, isMatch){
if(err) throw err;
if(isMatch){
return done(null, user);
} else {
return done(null, false, {message: 'Invalid password'});
}
});
});
}));
I have been modifying an example from GITHUB that uses mongoDB for the DB connection, but I would like to use MS SQL. The function is successfully calling the database and returning the correct values. However I don't know how to initiate the callback so I can pass the retUser object back to the original function for processing and logging in.
I did for a moment try to do this by not using the callback and using a standard return type of function, however I quickly realised that given the async nature this wouldn't work.
any help here would be greatly appreciated.
Thanks
OK I managed to figure it out using this post:
Node.js npm mssql function returning undefined
my new code is:
module.exports.getUserByUsername = function(username, callback){
var connection = new sql.ConnectionPool(dbConfig, function(err) {
if (err) {
console.log(err);
callback(err);
return
}
// create Request object
var request = new sql.Request(connection);
request.input('ip_username', sql.NVarChar, username)
// query to the database and get the records
request.query('select * from [portal_users] where username = #ip_username', function(err, recordset) {
if (err) {
console.log(err);
callback(err,recordset);
return;
} else {
var user = new User(recordset.recordset[0].username,recordset.recordset[0].password.replace(/ /g,''),recordset.recordset[0].email,recordset.recordset[0].name);
user.addID(recordset.recordset[0].id);
callback(err,user);
}
sql.close();
// send records as a response
//res.send(recordset);
});
});
}

How to encrypt password(hashing) using bcrypt or anyother method in meteor(In case of no account-password package)?

I am new to the meteor. I just created simple meteor app in which I want to save the user password as hashed string, not the plain password and I don't want to use accounts-password package. Following is my meteor method which one I am using for User insertion process.
Meteor.methods({'addRecord':function(user) {
var checkCollection = Users.findOne({},{sort:{userId:-1}});
if(typeof checkCollection != 'undefined' || checkCollection){
currentId = Users.findOne({},{sort:{userId:-1}}).userId || "1";
user.userId = (currentId * 1) + 1;
bcrypt.genSalt(10, Meteor.bindEnvironment(function (err, salt) {
if (err)
return
bcrypt.hash(user.password, salt, Meteor.bindEnvironment(function (err, hash) {
if (err)
return;
user.password = hash;
Users.insert(user);
}));
}));
return user.userId;
}
else {
user.userId = "1";
Users.insert(user);
}
return 1;
}
});
and following is my code in user signup route:
Meteor.call("addRecord", newuser, function(err, result) {
if(result) {
console.log("Successfully added new record with auto_inc id " + result);
Utility.response(context, 200, {
'success': true,
'error': false,
'successText': 'Signup successful!'
});
} else {
console.log(err);
Utility.response(context, 200, {
'success': false,
'error': true,
'successText': 'Signup failed!'
});
}
});
but the code is not working, passwords get saved as same plain text.

Save password hash only when password is present

I have a form where users can create a room with an optional password field. I want to save the password only if the password field contains something ( is not empty). I have hash middleware that hash the password before saving it to mongodb. Even if the password field is empty it is saving a hash value. I tried to add a condition to check if there is a value only then to proceed with the hashing but this does not seem to work.
Here is my post :
exports.postCreateRooms = function(req, res, next) {
req.assert('workspace', 'Please enter a board name').notEmpty();
var errors = req.validationErrors();
var enableVideo;
if (errors) {
req.flash('errors', errors);
return res.redirect('/dashboard');
}
var url = uuid.v4();
var room = new Room({
roomUrl: url,
roomName: req.body.workspace,
owner:req.user._id,
ownerEmail:req.user.email,
dateCreated: Date(),
lastUpdated: Date(),
users: [req.user._id]
});
if (req.body.password != ''){
room.password = req.body.password;
}
room.save(function(err) {
if (err) {
return next(err);
}
res.redirect('/board='+room.roomUrl);
});
};
here is my hash middleware :
roomSchema.pre('save', function(next) {
var room = this;
if(room.password){
bcrypt.genSalt(10, function(err, salt) {
if (err) {
return next(err);
}
bcrypt.hash(room.password, salt, null, function(err, hash) {
if (err) {
return next(err);
}
room.password = hash;
next();
});
});
}
});
What happens when you have the check in place?
From what I can see, you need a next() call outside of your if block in the middleware, so it knows to proceed even if there isn't a password specified.
It would look like
roomSchema.pre('save', function(next) {
var room = this;
if(room.password){
return bcrypt.genSalt(10, function(err, salt) {
if (err) {
return next(err);
}
bcrypt.hash(room.password, salt, null, function(err, hash) {
if (err) {
return next(err);
}
room.password = hash;
next();
});
});
}
next();
});

Why is the functions execute in finally in node js

In here my req.body.newTransactionPassword="1234";
i want encrypt that value but case is function is execute finally.I want get it into my order.Is that possible ..?
console.log("1");
var nwtp=req.body.newTransactionPassword;
var setPassword = function(nwtp,cb){
console.log("2");
bcrypt.genSalt( 10, function(err, salt) {
bcrypt.hash(nwtp, salt, function(err, hash) {
if (err) {
console.log(err);
return cb(err);
} else {
nwtp = hash;
console.log(nwtp);
return nwtp;
}
});
});
}
setPassword(nwtp);
console.log(nwtp);
console.log("3");
out put is
1
2
1234
3
$2a$10$kVmybMj7SsD5ip11lCU3AOFd4ZdKL6/0DzKADYcplIDx9qdZJAy/a
can i get it into that order..?
1
2
$2a$10$kVmybMj7SsD5ip11lCU3AOFd4ZdKL6/0DzKADYcplIDx9qdZJAy/a
3
$2a$10$kVmybMj7SsD5ip11lCU3AOFd4ZdKL6/0DzKADYcplIDx9qdZJAy/a
You should use async library https://github.com/caolan/async
Then, your code might look like this
var saltResult = null;
var hashResult = null;
async.series([
function(next) {
bcrypt.genSalt( 10, function(err, salt) {
saltResult = salt;
next(err);
});
},
function(next) {
bcrypt.hash(nwtp, saltResult, function(err, hash) {
hashResult = hash;
next(err);
});
}],
function(err) {
// your final processing here
}
);

Resources