Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Payload error in jsonwebtoken

I am making a web application using nodejs and angular cli I'm using JWT to authenticate my login function . But when I process it threw this error

Error: Expected "payload" to be a plain object. at validate (D:\Mean_Projects\meanauthapp\node_modules\jsonwebtoken\sign.js:34:11) at validatePayload (D:\Mean_Projects\meanauthapp\node_modules\jsonwebtoken\sign.js:56:10) at Object.module.exports [as sign] (D:\Mean_Projects\meanauthapp\node_modules\jsonwebtoken\sign.js:108:7) at User.comparePassword (D:\Mean_Projects\meanauthapp\routes\users.js:86:27) at bcrypt.compare (D:\Mean_Projects\meanauthapp\models\user.js:53:9) at D:\Mean_Projects\meanauthapp\node_modules\bcryptjs\dist\bcrypt.js:297:21 at D:\Mean_Projects\meanauthapp\node_modules\bcryptjs\dist\bcrypt.js:1353:21 at Immediate.next [as _onImmediate] (D:\Mean_Projects\meanauthapp\node_modules\bcryptjs\dist\bcrypt.js:1233:21) at runCallback (timers.js:785:20) at tryOnImmediate (timers.js:747:5) at processImmediate [as _immediateCallback] (timers.js:718:5)

Here my passport code

    const JwtStrategy= require('passport-jwt').Strategy;     const ExtractJwt=require('passport-jwt').ExtractJwt;     const User= require('../models/user');     const config=require('../config/database');             module.exports=function(passport){     let opts={};     opts.jwtFromRequest=ExtractJwt.fromAuthHeader();     opts.secretOrKey=config.secret;     opts.issuer = 'accounts.examplesoft.com';     opts.audience = 'yoursite.net';     passport.use(new JwtStrategy(opts,(jwt_payload,done)=>{         console.log(jwt_payload);         User.getUserById(jwt_payload._doc._id,(err,user)=>{             if(err){                 return done(err,false);             }             if(user){                 return done(null,user);             }             else{                 return done(null,false);             }         });     })); } 

My code for authenticate and get profile

// Authenticate router.post('/authenticate', (req, res, next) => {   const username = req.body.username;   const password = req.body.password;    User.getUserByUsername(username, (err, user) => {     if(err) throw err;     if(!user){       return res.json({success: false, msg: 'User not found'});     }      User.comparePassword(password, user.password, (err, isMatch) => {       if(err) throw err;       if(isMatch){         const token = jwt.sign(user, config.secret, {           expiresIn: 604800 // 1 week         });          res.json({           success: true,           token: 'JWT '+token,           user: {             id: user._id,             name: user.name,             username: user.username,             email: user.email           }         });       } else {         return res.json({success: false, msg: 'Wrong password'});       }     });   }); });  // Profile router.get('/profile', passport.authenticate('jwt', {session:false}), (req, res, next) => {   res.json({user: req.user}); }); 
like image 856
every Bit Avatar asked Nov 05 '17 02:11

every Bit


People also ask

What is payload in Jsonwebtoken?

Payload. The second part of the token is the payload, which contains the claims. Claims are statements about an entity (typically, the user) and additional data. There are three types of claims: registered, public, and private claims.

What is a JWT error?

This error occurs if the JSON Web Token (JWT) specified in the <Source> element of the Decode JWT policy is malformed, invalid or otherwise not decodable. A properly structured JWT should contain a header, payload and signature in the following format: header.

What does Jsonwebtoken verify return?

jwt.verify(token, secretOrPublicKey, [options, callback]) (Synchronous) If a callback is not supplied, function acts synchronously. Returns the payload decoded if the signature is valid and optional expiration, audience, or issuer are valid. If not, it will throw the error.


1 Answers

It fails at the line

const token = jwt.sign(user, config.secret, { 

With error "Expected "payload" to be a plain object"

Your user object is initialized here:

User.getUserByUsername(username, (err, user) 

Which I assume is mongoosejs object, which contains many methods and is not "serializable". You could handle this by passing a plain object, by either using .lean() from mongoose or plain toJSON method:

const token = jwt.sign(user.toJSON(), config.secret, {   expiresIn: 604800 // 1 week }); 
like image 71
Zilvinas Avatar answered Sep 17 '22 23:09

Zilvinas