7
votes

I am trying to authorise my JWT token with passport middleware but the strategy callback function is not getting called.

In my app.js file, I am specifying for my /users routes to use the middleware like so:

app.use('/users', passport.authenticate('jwt', { session: false }), users);

I then have a seperate file ./passport.js (which I have required at the top of my app.js) where I specify my passport strategy:

passport.use(new JWTStrategy({
        jwtFromRequest: ExtractJWT.fromAuthHeaderAsBearerToken(),
        secretOrKey   : 'jwt_secret_key'
    },
    function (jwtPayload, cb) {
        console.log('jwtPayload', jwtPayload)
    }
));

I can't get the console log to run though.

I am using postman to test this and have selected Bearer Token from the authorization options. I can see that this is adding a header to my request.

When I log my request object in my node app, I can see it looks like this:

headers: { 
    authorization: 'Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJfaWQiOiI1YWM0YWI2ZTk1MWJiMjE1M2NhMjc0OWUiLCJmaXJzdF9uYW1lIjoiQW5kcmV3IiwibGFzdF9uYW1lIjoiTWNDYWxsdW0iLCJlbWFpbCI6ImFtY2NhbGx1bTg5QGdtYWlsLmNvbSIsImlhdCI6MTUyMjg0NzEyNSwiZXhwIjoxNTIyODUwNzI1fQ.WH12GJHMGrGsiJNIwUG2Dx_a9cZKjw7_SW8FYlEvLmk',
    accept: '*/*',
    host: 'localhost:3037',
},

So the middleware should detect the bearer token and call the middleware?

Any help would be appreciated

4
So... presuming somewhere you've got the line app.use(passport.initialize())?James
No I don't. I have just got it working. Looks like my secretOrKey in my strategy didn't match my secretOrKey where I create my token. Not sure why it was failing silently but looks like that was causing the issue as it is working now.Stretch0
hmm I was always under the impression passport.initialize() was a requirement when using Express w/ Passport.James
Do you have an example of how / where it's used? Maybe I'm missing something without realisingStretch0
It's still in the docs, see the middleware section.James

4 Answers

6
votes

Turns out my secretOrKey didn't match my secretOrKey where I was creating my JWT token.

I.E passport strategy needs to have the same secretOrKey

passport.use(new JWTStrategy({
        jwtFromRequest: ExtractJWT.fromAuthHeaderAsBearerToken(),
        secretOrKey   : 'jwt_secret_key'
    },
    function (jwtPayload, cb) {
        console.log('jwtPayload', jwtPayload)
    }
));

as

const secretOrKey = 'jwt_secret_key'
const token = jwt.sign(payload, secretOrKey, { expiresIn });
2
votes

Same issue I was facing and I found this on github. https://github.com/themikenicholson/passport-jwt/issues/153

you have to change ExtractJwt.fromAuthHeaderAsBearerToken() to ExtractJwt.fromAuthHeaderWithScheme('jwt') or ExtractJwt.fromAuthHeaderWithScheme('JWT')

0
votes

I would like to share my answer. I spent an hour figuring out this issue, turns out it's my fault in configuring Postman.

So I'm a newbie in node-express, and I made 1 production rest api app already but in this second project, I couldn't figure out the issue.

I'm using constants through config.js so the keys weren't my problem for sure.

So going back to Postman, I checked my old project's postman collection. I checked the Header and it just had single Authorization key. And the value is something like: Bearer xxxxx. And when I went back to my current project, I wondered why my Authorization key has a value of Bearer Bearer xxx...

I figured that I must delete the Bearer thing when using the AUTHORIZATION OAUTH2.0 of Postman. Voila! Work great! I must've forgotten this proper configuration in Postman.

Here's how I setup my JwtStrategy:

// JSON WEB TOKENS STRATEGY
passport.use(new JwtStrategy({
  jwtFromRequest: ExtractJwt.fromAuthHeaderAsBearerToken(),
  secretOrKey: config.JWT_SECRET
}, async (payload, done) => {

  console.log("Find by pk, JWT strategy:", payload.sub)

  db.User.findByPk(payload.sub, {
0
votes

If you are following the documentation for NestJS, something seems to have been left out. Kindly make sure that you are also passing the secret during signing. I have mine in my .env file, thus the code snippet below:

this.jwtService.sign(payload, {secret: `${process.env.SECRET}`}),