neo4j / docs-graphql

GraphQL docs
4 stars 7 forks source link

How to validate the auth token with express middleware #152

Open geetparekh opened 1 month ago

geetparekh commented 1 month ago

This page describes how we can validate the auth token by setting the token field in the context field. The same process however, does not work with the express middleware server that we are using.

Because of that, we had to write a custom function to validate the auth token using jsonwebtoken library:

import JWT from "jsonwebtoken";

app.use('/graphql',
  cors<cors.CorsRequest>(),
  express.json(),
  expressMiddleware(server, {
    context: async ({ req }) => ({
      sessionConfig: {
        jwt: verifyTokenAndReturnPayload(req.headers.authorization)
      }
    })
  }));

/**
 * Verify token and return payload in case of successful verification. 
 * Else throw GraphQLError back as response to the request
 * 
 * @param authHeader 
 * @returns 
 */
function verifyTokenAndReturnPayload(authHeader: string){
  try {
    return JWT.verify(authHeader.split(' ')[1], token_secret);
  } catch (error) {
    console.log(error)
    throwAuthError();
  }
}

/**
 * Throw GraphQLError indicating user authentication failure
 */
function throwAuthError() {
  throw new GraphQLError('User is not authenticated', {
    extensions: {
      code: 'UNAUTHENTICATED',
      http: { status: 401 },
    },
  });
}

I would be happy to contribute this to the library so that the users would not have to write such a function themselves. However, I also feel that there is a missing link or a bug somewhere in the library as the automatic token validation is there with the standalone server, but not with the express middleware server. So, wanted to bring this up and see if we can resolve it.

mjfwebb commented 2 weeks ago

@geetparekh just wondering, since we specifically require the parameter to be named token to do the automatic validation, did you try with token or did you have it as jwt?

In the code, we specifically look for context.token:

https://github.com/neo4j/graphql/blob/4dcaf74879ba31001fef700c47b4e028fa00106a/packages/graphql/src/classes/authorization/Neo4jGraphQLAuthorization.ts#L50-L72