Dark Knight
Dark Knight

Reputation: 1083

Generate hashed password in findOneAndUpdate

Here is my query for findOneAndUpdate

  const { email, password, id } = req.body
  Artist.findOneAndUpdate({ _id: id }, { $set: req.body }).then((artist) => {
      return res.json({
        success: true,
        message: "Invitation sent."
      });
  })

And here is my schema

var artistSchema = new mongoose.Schema({
  name: { type: String, default: '' },
  password: { type: String, default: '' }
})
artistSchema.pre('findOneAndUpdate', function (next) {
    console.log('------------->>>>>> findOneAndUpdate: ');
    console.log(this.password) // why undefined?
    next();
});

I want to create a hashed password when user update details

Upvotes: 1

Views: 1295

Answers (3)

The answer: Writeconsole.log(JSON.stringify(this._update));

My solution for check blank password.

userSchema.pre('findOneAndUpdate', function() {
    console.log(JSON.stringify(this._update));
    if (this._update.password.length == 0) {
        this._update = {
            "fullname": this._update.fullname
        };
    }
    else {
        this._update = {
            "fullname": this._update.fullname,
            "password": bcrypt.hashSync(this._update.password, bcrypt.genSaltSync(8), null)
        };
    }
});

Upvotes: 0

musatin
musatin

Reputation: 585

let crypto = require('crypto');
let mongoose = require('../mongoose'),
    Schema = mongoose.Schema;

Then Schema

let schema = new Schema({
    name: { 
        type: String, 
        default: '' 
    },
    hashedPassword: {
        type: String,
        required: true
    },
    salt: {
        type: String,
        required: true
    }
});

Then methods and virtuals

schema.methods.encryptPassword = function(password){
    return crypto.createHmac('sha1', this.salt).update(password).digest('hex');
};

schema.virtual('password').set(function(password){
    this._plainPassword = password;
    this.salt = Math.random() + '';
    this.hashedPassword = this.encryptPassword(password);
}).get(function(){ return this._plainPassword; });

You can check password like that

schema.methods.checkPassword = function(password){
    return this.encryptPassword(password) === this.hashedPassword;
};

Export module

module.exports.Artist = mongoose.model('Artist', schema);

Then just save like before

const { email, password, id } = req.body;
Artist.findOneAndUpdate({ _id: id }, { $set: req.body }).then((artist) => {
  return res.json({
    success: true,
    message: "Invitation sent."
  });
});

But I sugest you also to use statics. For example:

schema.statics.updateUser = function (data){
    // your code
}

And then you can use

Artist.updateUser(req.body).then((res) => {
    // response
})

Upvotes: 0

anttud
anttud

Reputation: 736

const { email, password, id } = req.body;
Artist.findByIdAndUpdate(id, { $set: req.body }).then(artist => {
  return res.json({
    success: true,
    message: "Invitation sent."
  });
});

Example with bcrypt

var artistSchema = new mongoose.Schema({
  name: { type: String, default: "" },
  password: { type: String, default: "" }
});
artistSchema.pre("update", function(next) {
  bcrypt.hash(this.password, 10, function(err, hash) {
    if (err) return next(err);
    this.password = hash;
    next();
  });
});

Upvotes: 2

Related Questions