Passport.js multiple local strategies and req.user <p>The client for my web-app wants to <em>totally</em> separate regular users and admins, hence I'm trying to implement two local strategies for <code>passport.js</code>:</p> <pre><code>passport.use('local', new LocalStrategy({ usernameField: 'email' }, function(email, password, done) { User.findOne({ email: email }, function(err, user) { if (err) return done(err); if (!user) return done(null, false, { message: 'Wrong email or password.' }); if (!user.validPassword(password)) return done(null, false, { message: 'Wrong email or password.' }); done(null, user); }); })); passport.use('admin', new LocalStrategy({ usernameField: 'email' }, function(email, password, done) { Admin.findOne({ email: email }, function(err, admin) { if (err) return done(err); if (!admin) return done(null, false, { message: 'Wrong email or password.' }); if (!admin.validPassword(password)) return done(null, false, { message: 'Wrong email or password.' }); done(null, admin); }); })); passport.serializeUser(function(user, done) { done(null, user.id); }); passport.deserializeUser(function(id, done) { Admin.findById(id, function(err, admin) { if (err) return done(err); if (admin) return done(null, admin); User.findById(id, function(err, user) { done(err, user); }); }); }); </code></pre> <p>And then in my API admin router:</p> <pre><code>router.post('/', function(req, res, next) { if (typeof req.body.email === 'undefined') return res.json({ success: false, message: 'Email not supplied.' }); if (!validator.isEmail(req.body.email)) return res.json({ success: false, message: 'Wrong email format.' }); if (typeof req.body.password === 'undefined') return res.json({ success: false, message: 'Password not supplied.' }); if (req.body.password.length === 0) return res.json({ success: false, message: 'Password not supplied.' }); passport.authenticate('admin', function(err, admin, info) { if (!admin) return res.json({ success: false, message: info.message }); req.logIn(admin, function(err) { if (err) return res.json({ success: false, message: 'Server error.', reason: err }); console.log('user:'); console.log(req.user); // both users and admins go here console.log('admin:'); console.log(req.admin); // undefined res.json({ success: true }); }); })(req, res, next); }); </code></pre> <p>In fact, I was following the answer here: <a href="http://stackoverflow.com/a/21898892/1830420">http://stackoverflow.com/a/21898892/1830420</a>, and Matthew Payne gets two session variables: <code>req.user</code> and <code>req.sponsor</code>. In my case, even if an admin authenticates, it gets written to <code>req.user</code>. Now, trying to implement my client's desire of totally separating users and admins, I want to get <code>req.user</code> and <code>req.admin</code>, but every time it gets written to <code>req.user</code>. I thought changing LocalStrategy name would help, but <code>passport.js</code> seems to ignore both the strategy name <em>and</em> model name.</p> <p>Any help is very much appreciated.</p> <p>P.S. I know I can have everyone in <code>User</code> model and write some middleware to protect certain routes based on roles, but then again, unfortunately, I don't get to choose here.</p>