Pasaport serileştirmesini anlama


337

Passport'un serileştirme ve serileştirme yöntemlerinin iş akışını bir iş adamına nasıl açıklarsınız?

  1. Nerede gelmez user.idpeşine passport.serializeUseradı olmuştur?

  2. Ondan passport.deserializeUserhemen sonra iş akışına sığacak şekilde mi arıyoruz ?

    // used to serialize the user for the session
    passport.serializeUser(function(user, done) {
        done(null, user.id); 
       // where is this user.id going? Are we supposed to access this anywhere?
    });
    
    // used to deserialize the user
    passport.deserializeUser(function(id, done) {
        User.findById(id, function(err, user) {
            done(err, user);
        });
    });
    

Hala kafamı etrafına sarmaya çalışıyorum. Tam bir çalışma uygulaması var ve herhangi bir tür hatalarla karşılaşmıyorum.

Burada tam olarak ne olduğunu anlamak istedim.

Herhangi bir yardım takdir.

Yanıtlar:


452
  1. Nerede gelmez user.idpeşine passport.serializeUseradı olmuştur?

Kullanıcı kimliği ( doneişlevin ikinci argümanı olarak sağladığınız ) oturumda kaydedilir ve daha sonra tüm nesneyi deserializeUserişlev aracılığıyla almak için kullanılır .

serializeUseroturumda kullanıcı nesnesinin hangi verilerinin saklanacağını belirler. SerializeUser yönteminin sonucu oturuma eklenir req.session.passport.user = {}. Burada, örneğin (kullanıcı kimliğini anahtar olarak sağladığımız gibi)req.session.passport.user = {id: 'xyz'}

  1. Ondan passport.deserializeUserhemen sonra iş akışına sığacak şekilde mi arıyoruz ?

İlk argümanı deserializeUser, doneişleve verilen kullanıcı nesnesinin anahtarına karşılık gelir (bkz. 1.). Böylece tüm nesneniz bu anahtar yardımı ile alınır. Bu anahtar kullanıcı kimliğidir (anahtar, kullanıcı nesnesinin herhangi bir anahtarı olabilir, yani ad, e-posta vb.). Bu deserializeUseranahtarda, bellek dizisi / veritabanı veya herhangi bir veri kaynağı ile eşleştirilir.

Alınan nesne istek nesnesine şu şekilde eklenir: req.user

Görsel Akış

passport.serializeUser(function(user, done) {
    done(null, user.id);
});              
                  
                 
                 └─────────────────┬──→ saved to session
                                       req.session.passport.user = {id: '..'}
                                   
                                              
passport.deserializeUser(function(id, done) {
                   ┌───────────────┘
                   
                    
    User.findById(id, function(err, user) {
        done(err, user);
    });            └──────────────→ user object attaches to the request as req.user   
});

2
Yani olarak user.idkaydedilir req.session.passport.userveya userkendisi olarak depolanırreq.session.passport.user
Anubhav

@AB Deserialize yöntemine ilk parametre olarak geçirilen kimliğinden kullanıcı bulmak için kod yazdım. Ancak her istekte kullanıcı db'den alıyor. Bu db için performans kaybı yapar. Oturumda var olup olmadığını kontrol etmek için işlevi serileştirmek için başka ne yazmalıyım?
uzay95

2
@AB uzay95'e ne önerdiğini anlamıyorum. Yani oturumumda sadece user._id var. Ama her istek üzerine, ben veritabanı aka findUserByID serisini kaldırmak için bu kimliği kullanmak zorunda ve req.user içine koyacağız. Her talepte böyle bir arama yapmaktan nasıl kaçınırım?
Zanko

10
@Zanko Tüm kullanıcı nesnesini oturum verilerine koyabilirsiniz, ancak bu genellikle iyi bir fikir değildir çünkü başka yan etkileri olabilir. Örneğin, kullanıcı kullanıcı adını güncellediğinde, oturum verilerini de güncellemeniz gerekir, aksi takdirde "bozuk yeniden adlandırma özelliği" nedeniyle bilet alırsınız. Bu nispeten zararsız bir örnek. Aynı şey izin bitleri veya eşit hassas verilerle de olabilir (Hata ...). Çoğunlukla yinelenen verileriniz varsa her zaman karşılaştığınız sorunlar. TL; DR - Yapma.
Max Truxa

1
Yanılmıyorsam ise req.session.passport.user = {id: '..'}diyagram parçası hafifçe kapalı ve olması gerektiği req.session.passport.user = 785352yerine, nerede 785352olduğunu user.id. Bunu kanıtlamak için konsol günlüğünde sorun yaşıyorum, ancak mantıklı geliyor gibi görünüyor. Aradığınızda done(null, user.id);, ikinci argümanı - user.idbu durumda - alıp atamak req.session.passport.useryerine atamak mantıklı olacaktır req.session.passport.user.id. Çünkü ya onun yerine geçersen user? req.sesssion.passport.user.id = userhiç mantıklı değil.
Adam Zerner

21

Koa ve koa pasaportu kullanan herkes için :

SerializeUser yönteminde ayarlanan kullanıcının anahtarının (genellikle bu kullanıcı için benzersiz bir kimlik) depolanacağını bilin:

this.session.passport.user

done(null, user)DeserializeUser içinde ayarladığınızda, burada 'kullanıcı' veritabanınızdan bazı kullanıcı nesneleridir:

this.req.user VEYA this.passport.user

herhangi bir nedenle this.user, deserializeUser yönteminde done (null, user) çağrısı yaptığınızda Koa içeriği hiçbir zaman ayarlanmaz.

Böylece, bu.user içine koymak için app.use (passport.session ()) çağrısından sonra kendi ara katman yazılımınızı yazabilirsiniz:

app.use(function * setUserInContext (next) {
  this.user = this.req.user
  yield next
})

SerializeUser ve deserializeUser'ın nasıl çalıştığından emin değilseniz, sadece beni heyecanlandırın. @yvanscher


Burada nekropostlama için özür dilerim, ama şimdi serileştirme açıklamasını okuduktan sonra bir endişem var. Burada SO hakkında bir soru gönderdim: stackoverflow.com/questions/54154047/…
Peter Kellner

Süper yararlı, ancak yine de kullanıcıyı diğer yollardan okurken bazı sorunlar yaşıyor. Burada birisi bana yardım edebilir mi? stackoverflow.com/questions/60709882/…
Harry Lincoln
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.