Passport.js is not passing user to request in req.login()

17,639

I solved the problem by juggling around with the tutorial I started with when I first learned how to use the Passport middleware. Turns out I was doing the configuring wrong: My code used to be like this in the server file:

pass = require("passport");
app.use(pass.initialize());
app.use(pass.session());
require("./app/config/passport.js")(pass);

when it should have been this:

pass = require("passport");
require("./app/config/passport.js")(pass);
app.use(pass.initialize());
app.use(pass.session());

Either I missed the part in the documentation where it's specified that configuration must come before initialization or it's simply written off as a trivial thing to remark. Either way, I solved my problem.

Share:
17,639
Eduardo de Luna
Author by

Eduardo de Luna

Updated on July 26, 2022

Comments

  • Eduardo de Luna
    Eduardo de Luna almost 2 years

    My passport.js configuration goes like so:

    const Local = require("passport-local").Strategy;
    const USMODEL = require("../models/user.js");
    passport.serializeUser(function(user, done) {
        console.log("SERIALIZING USER");
        done(null, user.id);
    });
    passport.deserializeUser(function(id, done) {
        console.log("DESUSER", id);
        var US = mongoose.model("RegUser", USMODEL);
        US.findById(id, function(err, user) {
            done(err, id);
        });
    });
    passport.use("local-login", new Local({
        usernameField: "email",
        passwordField: "password",
        passReqToCallback: true
    
    },function(req, email, password, done) {
        var US = mongoose.model("RegUser", USMODEL);
        US.findOne({"email": email}, function(err, user){
            if(err) throw err;
            if(!user) return done(null, false);
            if(!user.validPassword(password)) {
                console.log("password not valid");
                return done(null, false);
            }
            return done(null, user);
        });
    }));
    

    I'm changing the mongoose model within each function because I juggle with multiple collections at a time and I like to have complete control of what's going on.

    My router.js file has the following paths that make use of the passport middleware:

    app.get("/user/login", function(req, res) {
        res.render("signin");
    });
    app.post('/user/login', function (req, res){
        passport.authenticate('local-login', function(err, user, info){
            if (err) return res.redirect("/");
            if (!user) return res.redirect('/');
    
            else {
                req.login(user, function(err) {
                  if (err) return next(err);
                  console.log("Request Login supossedly successful.");
                  return res.redirect('/admin/filter');
                });
            }
        })(req, res);
    });
    

    Which, upon successful authentication, redirects to /admin/filter in the same router that goes like so.

    app.get("/admin/filter", isLoggedIn, function(req, res){
    //rendering stuff here
    });
    

    Now, the admin/filter request goes past a middleware called isLoggedIn which, in theory protects my endpoints. It goes like so:

    function isLoggedIn(req, res, next) {
    console.log("This is the authentication middleware, is req authenticated?");
    console.log(req.isAuthenticated());
    console.log("Does req.user exist?")
    console.log(req.user);
    return next();
    }
    

    Now, you would expect that because I called req.login and I got redirected to my endpoint of choice, the request would be authenticated. This is not the case.

    Request Login supossedly successful.
    This is the authentication middleware, is req authenticated?
    false
    Does req.user exist?
    undefined
    

    I can't seem to find the source of my problem. Everything checks out, as the strategy is being invoked, as well as the callback function and req.login which would render, in theory, a req.user object with data in it. One odd thing I've observed is that I don't see the passport.deserializeUser() method in action. Ever. But that could be tangential to the problem. Passport is definitely using my strategy and rendering a user object, but somehow this same object is not going into the request. Do you have any suggestion or idea about what is going on?