Still celebrating National IT Professionals Day with 3 months of free Premium Membership. Use Code ITDAY17

x
?
Solved

express passportjs confusion

Posted on 2017-08-10
5
Low Priority
?
47 Views
Last Modified: 2017-08-13
Hello All,

I am reading a book called express.js Blueprints.  I am trying to wrap my mind around understanding authentication using passport.  serializing and deserializing is not registering to me.  I have just started learning node and express js so that's a big reason why.

Here's a code from the book on setting up passport.  Starting with line 5, can someone please break down what's happening?  Where is the "user" parameter coming from in the serializeUser function?  Where did "user.id" come from?

var passport = require('passport');
var LocalStrategy = require('passport-local').Strategy;
var User = require('mongoose').model('User');

passport.serializeUser(function(user, done) {
done(null, user.id);
});
passport.deserializeUser(function(id, done) {
User.findById(id, done);
});

passport.use(new LocalStrategy(function(email, password, done) {
User.findOne({
email: email
}, function(err, user) {
if (err) return done(err);
if (!user) {
return authFail(done);
}
if (!user.validPassword(password)) {
return authFail(done);
}
return done(null, user);
});
}));

Open in new window

0
Comment
Question by:Isaac
[X]
Welcome to Experts Exchange

Add your voice to the tech community where 5M+ people just like you are talking about what matters.

  • Help others & share knowledge
  • Earn cash & points
  • Learn & ask questions
  • 3
  • 2
5 Comments
 
LVL 5

Author Comment

by:Isaac
ID: 42250410
I am even looking at the code on passport.js site 'Configure' section.
How does the username and password get passed to the function?

var passport = require('passport')
  , LocalStrategy = require('passport-local').Strategy;

passport.use(new LocalStrategy(
  function(username, password, done) {
    User.findOne({ username: username }, function (err, user) {
      if (err) { return done(err); }
      if (!user) {
        return done(null, false, { message: 'Incorrect username.' });
      }
      if (!user.validPassword(password)) {
        return done(null, false, { message: 'Incorrect password.' });
      }
      return done(null, user);
    });
  }
));

Open in new window

0
 
LVL 59

Expert Comment

by:Julian Hansen
ID: 42250594
In answer to your first question

The serialize and deserialize functions are used to save user data to passport and retrieve it again. When you login the user object (details associated with your user) are only available at authentication time. That means if you want to get user info relating to the user account after login you need to save those values in the session (or query them each time which would require you save at least a unique ID linked to the user).
The serialize method is where you tell passport what data you want it to save in the session relating to the user. The deserialize function is where you ask passport to give that data back to you.

It is explained in detail in the docs here http://passportjs.org/docs#sessions

With reference to your second question - the username and password is handled differently depending on the strategy you use. In the case of one of the in-built strategies passport handles that for you. In the case of a custom strategy you setup a form with username and password fields and then create a route that sends this to passport.

You can read more about this here http://passportjs.org/docs#configuration
0
 
LVL 5

Author Comment

by:Isaac
ID: 42250971
Where does the 'user.id' come from?  

passport.serializeUser(function(user, done) {
done(null, user.id);
});

Open in new window

Is it checking the database?  I don't have a 'user' field in my mongo db.
I'm trying to use 'local-strategy' and 'passport-local-mongoose'.
0
 
LVL 5

Author Comment

by:Isaac
ID: 42250983
>>When you login the user object (details associated with your user) are only available at authentication time.

Is the user object created when they try to sign into the database?
0
 
LVL 59

Accepted Solution

by:
Julian Hansen earned 1000 total points
ID: 42251019
Where does the 'user.id' come from?  
From your user object
Is the user object created when they try to sign into the database?
No they don't try sign into the database - you write the code to do that and populate your user object with the data you retrieve.

Going from the beginning
They provide different "strategies" for authentication. The in built ones will allow you to authorize with Google / Facebook / GitHub etc. With these inbuilt functions they handle the authentication for you.

If you have your own database then you have to create your own local (custom) strategy. In this scenario you get your own user object - in the source code above refer line 3

var User = require('mongoose').model('User');

Open in new window


Then on line 4 of your second post - you create a LocalStrategy
passport.use(new LocalStrategy(

Open in new window

The function takes a username, password and a done callback.
You use the User object you created in line 3 to find the user based on the username / password. If success you tell passport it was successful if fail you tell passport it failed through the done() callback.

So
Get user object
Passport accepts form submission and through your LocalStrategy setup calls your callback with the name and password it got from the form along with a callback (done) that you call when the user is authenticated
In addition passport creates a serialize and deserialize interface for you to save and restore your user object from the session.

When a user hits your site - if a session is in progress then passport will deserialize your user object for you so that it is available to use in the session.
1

Featured Post

Concerto Cloud for Software Providers & ISVs

Can Concerto Cloud Services help you focus on evolving your application offerings, while delivering the best cloud experience to your customers? From DevOps to revenue models and customer support, the answer is yes!

Learn how Concerto can help you.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

This article shows how to get a list of available printers for display in a drop-down list, and then to use the selected printer to print an Access report or a Word document filled with Access data, using different syntax as needed for working with …
In this blog post, we’ll look at how using thread_statistics can cause high memory usage.
This is a high-level webinar that covers the history of enterprise open source database use. It addresses both the advantages companies see in using open source database technologies, as well as the fears and reservations they might have. In this…
In this video, Percona Solution Engineer Rick Golba discuss how (and why) you implement high availability in a database environment. To discuss how Percona Consulting can help with your design and architecture needs for your database and infrastr…

715 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question