hoping someone can help a noob with some async javascript issues.
I am attempting to secure a GraphQL server instance using Passport and the passport-azure-ad strategy. I can see from logs that the incoming Access Token is validated correctly and all of the passport code is working as expected.
const passport = require('passport');
const OIDCBearerStrategy = require('passport-azure-ad').BearerStrategy;
...
// Setting up the Strategy and verify function
const bearerStrategy = new OIDCBearerStrategy(options, (token, done) => {
if (!token.scp.includes('check-this-scope')) {
return done(null, false, { message: 'User not authorized to access resource' });
}
return done(null, token);
});
passport.use('oauth-bearer', bearerStrategy);
...
const server = new ApolloServer({
typeDefs,
resolvers,
context: async (context) => {
passport.authenticate('oauth-bearer', (authErr, authUser, authInfo) => {
if (!authUser) context.authErr = authErr || authInfo;
else context.user = authUser;
})(context.req, context.res);
return context;
},
});
The authErr and authUser params are correctly being passed to the custom callback, however the context is returned before the callback is executed.
Ideally I would like to if (!user) throw new AuthenticationError('you must be logged in');
in the context block if the user is not available, however due to the asynchronous nature of the code I don't have access to it.
How can I make the code in the context wait until the custom passport.authenticate callback has executed? Or alternatively is there a better way for me to do this? I am new to apollo server, passport and even working with node, so I wouldn't be surprised if I was doing something wrong.
Right now it seems that my setting of context.user
isn't even available in the context delivered to the resolvers.
Thanks in advance.