嗨,我只想在密码更改时使用哈希密码保存,所以我在预保存中使用了 isModified 函数,但即使我更改了密码,它也总是返回 false。我尝试这样做的原因是因为我不想在更改其他属性时更改并保存我的密码。
router.post('/changepw', isAuthenticated, function (req, res, next) {
User.findOneAndUpdate({_id: req.user._id}, {$set: req.body},{ new: true }, function (err, user){
if (err) {
return err;
}
else {
if (req.body.password) {
user.password = req.body.password;
user.save();
} else {
}
}
res.redirect('/profile');
});
});
就像这里,当我更改我的毕业值时,我不想更改我的密码。
router.post('/edit', isAuthenticated, function (req, res, next) {
User.findOneAndUpdate({
_id: req.user._id
}, {
$set: {
name: req.body.name,
phone: req.body.phone,
classc: req.body.classc,
major: req.body.major,
minor: req.body.minor,
linkedin: req.body.linkedin,
bio: req.body.bio
}
}, {
new: true
}, function (err, user, done) {
if (err) {
return err;
} else {
if (typeof req.body.graduated == 'undefined') {
user.graduated = false;
} else if (typeof req.body.graduated == 'string') {
user.graduated = true;
}
user.save();
}
res.redirect('/profile');
});
});
userSchema.pre('save', function(next) {
console.log(this.isModified('password'));
if(this.password && this.isModified('password')){
this.password = bcrypt.hashSync(this.password, bcrypt.genSaltSync(8),null);
}
next()
});
有什么建议吗?
请注意,当您使用
findAndUpdate()
方法时,不会触发预保存挂钩。使用新的钩子检查 Mongoose 文档:http://mongoosejs.com/docs/middleware.html#notes.
试试这个
userSchema.pre('save', async function (next) {
// Only run this function if password was moddified (not on other update functions)
if (!this.isModified('password')) return next();
// Hash password with strength of 12
this.password = await bcrypt.hash(this.password, 12);
//remove the confirm field
this.passwordConfirm = undefined;
});
findOneAndUpdate()
已经更新了user
,因此在您提供的回调函数中user
已经是最新的。当您在该回调中调用 user.save()
时,将调用 pre save()
钩子,但 isModified('password')
将为 false。
如果您使用
req.body
提供新密码,该密码将以未散列的方式存储在数据库中,因为“Pre 和 post save()
钩子不会在 update()
、findOneAndUpdate()
等上执行”。 (参见文档)。如果你再比较req.body
和user
中的密码,它们将是相同的,你无法决定是否用save()
触发哈希函数。
保留之前的
save()
挂钩,并以 findById()
和 save()
的组合进行更新:
User.findById(req.user._id, (err, user) => {
if (err)
handleYourErrorAndLeave(err)
// Update all user attributes which are different or missing from user with values from req.body
Object.assign(user, req.body)
// Save the updated user object.
// pre save() hook will be triggered and isModified('password') should be correct
user.save()
.then(savedUser => {
res.redirect('/profile')
})
})
最好从模型中操纵密码。您可以在此处根据需要更新或持续更新密码以及其他值。
// Encrypt password before saving into database
userSchema.pre("save", async
function(next) {
if (!this.isModified("password")) {
return next();
}
const salt = await bcrypt.genSalt(10);
const hashedPassword = await bcrypt.hash(this.password, salt);
this.password = hashedPassword;
next();
});