如何生成一个唯一的 id 并将其保存到 passportJS 中的 mongoDB?
How to generate a unique id and save it to mongoDB in passportJS?
我正在使用passportJS,在我的回调中我想进行以下操作。
1) 生成随机字符串
2) 检查数据库是否存在该id,如果存在则重新生成id直到它是唯一的。
3) 保存用户模型(使用唯一的 id)。
我尝试编写多个函数,但似乎 newUser
对象在函数内部未定义!
这是我在猫鼬模型中使用的函数。
userSchema.methods.generateVci = function(length, characters){
var string = '';
for(var i = length; i > 0; --i){
string += characters[Math.round(Math.random() * (characters.length - 1))];
}
return string;
};
userSchema.statics.validateVci = function(uniquekey){
this.find({}, function(err,user){
for(var i = 0; i < user.length; ++i){
var uservci = user[i].local.vci;
if(uservci == uniquekey){
console.log('false');
return false;
}
}
console.log('true');
return true;
});
};
passport.use('local-signup', new LocalStrategy({
// by default, local strategy uses username and password, we will override with email
usernameField : 'email',
passwordField : 'password',
passReqToCallback : true // allows us to pass back the entire request to the callback
},
function(req, email, password, done) {
// find a user whose email is the same as the forms email
// we are checking to see if the user trying to login already exists
User.findOne({ 'local.email' : email }, function(err, user) {
// if there are any errors, return the error
if (err)
return done(err);
// check to see if theres already a user with that email
if (user) {
return done(null, false, req.flash('signupMessage', 'That email is already taken.'));
} else {
var generatedVciKey = newUser.generateVci(32, '0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ');
var isvalidvci = User.validateVci(generatedVciKey);
if(isvalidvci){
var newUser = new User();
newUser.local.email = email;
newUser.local.password = newUser.generateHash(password);
newUser.local.vci = generatedVciKey;
}
// save the user
newUser.save(function(err) {
if (err)
throw err;
return done(null, newUser);
});
}
});
}));
如果你能告诉我一种编写某种递归函数的方法,passportjs 只会在生成唯一(与数据库核对)id 时保存用户模型。唯一 ID 必须一次又一次地重新生成,直到它与数据库中的任何其他 ID 真正唯一。我不知道如何执行此操作,因为当我编写函数时,passportjs 回调中的变量似乎未定义。
你真的需要这样做吗?您可以使用 node-uuid 生成唯一标识符。所以你生成非唯一id的概率可以忽略不计低
我重写了这个 generateVci 但你真的应该像有人建议的那样使用 node-uuid
userSchema.methods.generateVci = function(length, characters) {
return characters.split('').map(function() {
var randomKey = Math.round(Math.random() * (characters.length - 1));
return characters[randomKey];
}).join('').substring(0, length);
};
您的 validateVCI 是异步的,因此您必须传递回调或其他方式是使用 promises
userSchema.statics.validateVci = function(uniquekey, cb){
this.find({}, function(err, users){
if (err) {
return cb(err);
}
var isInvalid = users.reduce(function(invalid, user) {
if (invalid) {
return true;
}
return user.local.vci === uniquekey;
}, false);
if (isInvalid) {
return cb(null, false);
}
console.log('true');
return cb(null, true);
});
};
您应该使 vci 字段在您的数据库中是唯一的...
因此,当您尝试创建具有相同 vci 的用户时,它会失败
function createUser(email, password, done) {
var generatedVciKey = newUser.generateVci(32, '0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ');
User.validateVci(generatedVciKey, function(isInvalid) {
if (isInvalid) {
return createUser(email, password, done)
}
var newUser = new User();
newUser.local.email = email;
newUser.local.password = newUser.generateHash(password);
newUser.local.vci = generatedVciKey;
// save the user, or try again on error
newUser.save(function(err) {
if (err) {
return createUser(email, password, done);
}
done(null, newUser);
});
});
}
passport.use('local-signup', new LocalStrategy({
// by default, local strategy uses username and password, we will override with email
usernameField : 'email',
passwordField : 'password',
passReqToCallback : true // allows us to pass back the entire request to the callback
}, function(req, email, password, done) {
// find a user whose email is the same as the forms email
// we are checking to see if the user trying to login already exists
User.findOne({ 'local.email' : email }, function(err, user) {
// if there are any errors, return the error
if (err)
return done(err);
if (user) {
return done(null, false, req.flash('signupMessage', 'That email is already taken.'));
}
createUser(email, password, done);
});
}));
我正在使用passportJS,在我的回调中我想进行以下操作。
1) 生成随机字符串
2) 检查数据库是否存在该id,如果存在则重新生成id直到它是唯一的。
3) 保存用户模型(使用唯一的 id)。
我尝试编写多个函数,但似乎 newUser
对象在函数内部未定义!
这是我在猫鼬模型中使用的函数。
userSchema.methods.generateVci = function(length, characters){
var string = '';
for(var i = length; i > 0; --i){
string += characters[Math.round(Math.random() * (characters.length - 1))];
}
return string;
};
userSchema.statics.validateVci = function(uniquekey){
this.find({}, function(err,user){
for(var i = 0; i < user.length; ++i){
var uservci = user[i].local.vci;
if(uservci == uniquekey){
console.log('false');
return false;
}
}
console.log('true');
return true;
});
};
passport.use('local-signup', new LocalStrategy({
// by default, local strategy uses username and password, we will override with email
usernameField : 'email',
passwordField : 'password',
passReqToCallback : true // allows us to pass back the entire request to the callback
},
function(req, email, password, done) {
// find a user whose email is the same as the forms email
// we are checking to see if the user trying to login already exists
User.findOne({ 'local.email' : email }, function(err, user) {
// if there are any errors, return the error
if (err)
return done(err);
// check to see if theres already a user with that email
if (user) {
return done(null, false, req.flash('signupMessage', 'That email is already taken.'));
} else {
var generatedVciKey = newUser.generateVci(32, '0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ');
var isvalidvci = User.validateVci(generatedVciKey);
if(isvalidvci){
var newUser = new User();
newUser.local.email = email;
newUser.local.password = newUser.generateHash(password);
newUser.local.vci = generatedVciKey;
}
// save the user
newUser.save(function(err) {
if (err)
throw err;
return done(null, newUser);
});
}
});
}));
如果你能告诉我一种编写某种递归函数的方法,passportjs 只会在生成唯一(与数据库核对)id 时保存用户模型。唯一 ID 必须一次又一次地重新生成,直到它与数据库中的任何其他 ID 真正唯一。我不知道如何执行此操作,因为当我编写函数时,passportjs 回调中的变量似乎未定义。
你真的需要这样做吗?您可以使用 node-uuid 生成唯一标识符。所以你生成非唯一id的概率可以忽略不计低
我重写了这个 generateVci 但你真的应该像有人建议的那样使用 node-uuid
userSchema.methods.generateVci = function(length, characters) {
return characters.split('').map(function() {
var randomKey = Math.round(Math.random() * (characters.length - 1));
return characters[randomKey];
}).join('').substring(0, length);
};
您的 validateVCI 是异步的,因此您必须传递回调或其他方式是使用 promises
userSchema.statics.validateVci = function(uniquekey, cb){
this.find({}, function(err, users){
if (err) {
return cb(err);
}
var isInvalid = users.reduce(function(invalid, user) {
if (invalid) {
return true;
}
return user.local.vci === uniquekey;
}, false);
if (isInvalid) {
return cb(null, false);
}
console.log('true');
return cb(null, true);
});
};
您应该使 vci 字段在您的数据库中是唯一的... 因此,当您尝试创建具有相同 vci 的用户时,它会失败
function createUser(email, password, done) {
var generatedVciKey = newUser.generateVci(32, '0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ');
User.validateVci(generatedVciKey, function(isInvalid) {
if (isInvalid) {
return createUser(email, password, done)
}
var newUser = new User();
newUser.local.email = email;
newUser.local.password = newUser.generateHash(password);
newUser.local.vci = generatedVciKey;
// save the user, or try again on error
newUser.save(function(err) {
if (err) {
return createUser(email, password, done);
}
done(null, newUser);
});
});
}
passport.use('local-signup', new LocalStrategy({
// by default, local strategy uses username and password, we will override with email
usernameField : 'email',
passwordField : 'password',
passReqToCallback : true // allows us to pass back the entire request to the callback
}, function(req, email, password, done) {
// find a user whose email is the same as the forms email
// we are checking to see if the user trying to login already exists
User.findOne({ 'local.email' : email }, function(err, user) {
// if there are any errors, return the error
if (err)
return done(err);
if (user) {
return done(null, false, req.flash('signupMessage', 'That email is already taken.'));
}
createUser(email, password, done);
});
}));