Moduł uwierzytelniający "paszport" wymaga metody FindOrCreate w celu zalogowania. Używam mangusty, aby uratować moje użytkowników z następującym schematem:Jak radzić sobie z asynchronizacją. Metoda findOrCreate dla paszportu i mangusty
var UserSchema = new Schema({
firstname: String,
lastname: String,
email: String,
accounts: []
});
Tablica posiada rachunki obiektów, które reprezentują konta Facebook, jak {provider: "facebook", uid: "someFacebookId"}
.
Moja strategia uwierzytelniania wygląda następująco:
// Authentication Strategy
passport.use(new FacebookStrategy({
clientID: CONFIG.fb.appId,
clientSecret: CONFIG.fb.appSecret,
callbackURL: CONFIG.fb.callbackURL
},
function(accessToken, refreshToken, profile, done) {
// asynchronous verification, for effect...
process.nextTick(function() {
User.find({ 'accounts.uid': profile.id, 'accounts.provider': 'facebook' }, function(err, olduser) {
if(olduser._id) {
console.log('User: ' + olduser.firstname + ' ' + olduser.lastname + ' found and logged in!');
done(null, olduser);
} else {
var newuser = new User();
var account = {provider: "facebook", uid: profile.id};
newuser.accounts.push(account);
newuser.firstname = profile.name.givenName;
newuser.lastname = profile.name.familyName;
newuser.email = "TBD...";
newuser.save(function(err) {
if(err) { throw err; }
console.log('New user: ' + newuser.firstname + ' ' + newuser.lastname + ' created and logged in!');
done(null, newuser);
});
}
});
});
}
));
Problem: Po kwerend mojej bazy danych (User.find(...)
) Funkcja zwrotna jest wykonywana natychmiast, nie czekając na moja baza odpowiedzieć. Powoduje to niezdefiniowanie obiektu. Dostaję dublikację tego samego użytkownika do mojej bazy danych za każdym razem, gdy ten użytkownik próbuje się zalogować.
Jak poprawnie obsłużyć to asynchroniczne wywołanie zwrotne?
Wiem, że nie jest to bezpośrednio związane z pytaniem, ale czy nie jest to, że zapytanie jest trochę niebezpieczne? Poszukuje użytkownika z dowolnymi kontami o danej wartości iz każdym kontem. Dostarcza "facebook". Ale co zmusza ich do tego samego elementu listy kont? To znaczy, co jeśli inny użytkownik miał pasujący identyfikator uid z innym dostawcą? – StevenC
Zakładam, że szuka kombinacji obu wartości, które powinny być unikalne. – Sven
To założenie jest niebezpieczne. Ponieważ znalezienie w tablicy kont jest takie samo, jeśli użytkownik ma konto na Facebooku i konto * DOWOLNE * ma ten identyfikator. Jeśli ktoś ma serwer OpenAuth, może zalogować się jako dowolny użytkownik, zwracając numer, którego chciał. – tangxinfa