hapijs / jwt

JWT (JSON Web Token) Authentication
Other
36 stars 25 forks source link

Token missing payload aud value #16

Closed joshuaebowling closed 4 years ago

joshuaebowling commented 4 years ago

Context

How can we help?

sending request with generated token returns the following error:

{
    "statusCode": 401,
    "error": "Unauthorized",
    "message": "Token missing payload aud value",
    "attributes": {
        "error": "Token missing payload aud value"
    }
}

Here's my init (ripped from api.md)

import Hapi from "@hapi/hapi";
const Jwt = require("@hapi/jwt");
import userRoutes from "./routes/user";
import { each } from "lodash";
import config from "config";

const maxTokenSeconds = config.get('auth.maxTokenSeconds')

const init = async () => {

    const server = Hapi.server({
        port: 3000,
        host: 'localhost',
        debug: { request: ['error', 'info', 'warn'] }
    });

    const secret = config.get("auth.secret");
    await server.register(Jwt);
    server.auth.strategy("jwt", "jwt", {
        // provide the shared secret key / json web keyset info
        keys: secret,
        // fields that needs to be verified and respective values
        verify: {
            // audience intended to receive
            aud: "urn:audience:test",
            // issuer of the jwt
            iss: "urn:issuer:test",
            // verify subject of jwt
            sub: false,
            // check expiry - default true
            exp: true,
            // nbf < (nowSec + skewSec)
            nbf: true, // <<<<<<<<< I just set this to true bc TS was complaining that it needed to be bool
            // skew secs
            timeSkewSec: 1,
            // max age (secs) of the JWT allowed
            maxAgeSec: maxTokenSeconds
        },
        // token validation fn gets executed after token signature verification
        validate: (artifacts, request, h) => {
        return {
            isValid: true,
            credentials: { user: artifacts.decoded.payload.user }
        };
        }
    });
    //set the strategy
    server.auth.default("jwt"); 
    each(userRoutes, ur => server.route(ur));
    await server.start();
    console.log('Server running on %s', server.info.uri);
};
// @ts-ignore
process.on('unhandledRejection', (err) => {

    console.log(err);
    // @ts-ignore
    process.exit(1);
});

init();

Additionally, I've tried to set an "aud" property in headers as well as body that match the value in the above code.

Any ideas how I can resolve?

thanks!

devinivy commented 4 years ago

The error you're getting indicates that the token that you're creating and passing to your API is missing an aud claim. I don't see any code here generating a token— can you share or check the code responsible for generating a token and confirm that it includes aud in its payload?

joshuaebowling commented 4 years ago

@devinivy I think you are correct.

    login: {
        method: 'POST',
        path: '/login',
        options: {
            auth: false,
            validate: {
                payload: Joi.object(Domain.Login(Joi)),
                failAction
            }
        },
        handler: async (request, h, err) => {

            var result = await UserService.login(request.payload);
            var token = "";
            if(result.Data) {
                token = Jwt.token.generate({test: 'ok'}, secret);
            }
            return { user: result, token};
        }
    },

I didn't see any parameter in Jwt.token.generate() for aud. I imagined that it used the 'aud' prop from the initial configuration.

devinivy commented 4 years ago

Great, sounds like this is resolved! If there's an improvement to the docs to be made (and I'm sure there is!), a PR would certainly be welcome.

joshuaebowling commented 4 years ago

@devinivy I'm still getting the same error. But I'm definitely not afraid to dig in and see where I'm going wrong. If I think my findings are of value, I'll certainly create a PR.

devinivy commented 4 years ago

Ah, sorry I missed that you were having troubling including the aud claim. It can go right in the payload passed to generate(), e.g. Jwt.token.generate({ aud: 'urn:audience:test', test: 'ok' }, secret).

ujshaikh commented 2 years ago

@devinivy I had used aud I am also still getting the same error I found this helpful, its worked for me https://github.com/hapijs/jwt/issues/15#issuecomment-683755670