'How can I set a session key from inside a GraphQL resolver in NestJS?
I'm discovering Nest.js and I want to setup a cookie based authentication system with GraphQL.
I already installed express-session middleware, here is the configuration:
main.ts
app.use(
session({
store: new redisStore({
client: redis
} as any),
name: 'qid',
secret: SESSION_SECRET,
resave: false,
saveUninitialized: false,
cookie: {
httpOnly: true,
secure: !isDev,
maxAge: 1000 * 60 * 60 * 24 * 7 * 365
}
})
)
it works fine because when I do :
app.use((req: any, res: any, next: any) => {
// Debug purpose
req.session.userId = '42'
next()
})
The cookie is added.
Right now I have two mutations, register and login.
In the login mutation (or in the userService), after I found a user I want to do something like req.session.userId = user.id
but I can't find a way to do this.
I tried to add @Context() ctx
to my mutation.
If I console log ctx, it contains everything I expect (req.session.id for example)
But if I do ctx.req.session.userId = 'something'
, the cookie is not set!
Here is my mutation:
user.resolver.ts
@Mutation('login')
async login(
@Args('email') email: string,
@Args('password') password: string,
@Context() ctx: any
) {
console.log(ctx.req.session.id) // Show the actual session id
ctx.req.session.userId = 'something' // Do not set any cookie
return await this.userService.login(email, password)
}
}
I am totally lost and I really need help, I'd love to understand what's happening. I know I'm probably doing this totally wrong but I'm new to both Nest and GraphQL..
Thank you guys...
Solution 1:[1]
I found the problem after many days ... and it was...
GraphQL Playground -> Settings -> add "request.credentials": "include" (and no "omit")
Hope it will help someone..
Solution 2:[2]
for this, it's better to do the configuration in the GraphQL config file instead of the client side
graphql.config.ts
import { ApolloDriverConfig, ApolloDriver } from '@nestjs/apollo';
import { join } from 'path';
export const GraphQLConfig: ApolloDriverConfig = {
driver: ApolloDriver,
debug: true,
autoSchemaFile: join(process.cwd(), 'src/schema.gql'),
playground: {
settings: {
'editor.theme': 'light', // use value dark if you want a dark theme in the playground
'request.credentials': 'include',
},
},
};
and assign the config file to the module directory
user.module.ts
import { Module } from '@nestjs/common';
import { GraphQLModule } from '@nestjs/graphql';
import { TypeOrmModule } from '@nestjs/typeorm';
import { GraphQLConfig } from 'src/config/graphql.config';
import { UserEntity } from 'src/entity/user.entity';
import { UserResolver } from './user.resolver';
import { UserService } from './user.service';
@Module({
imports: [
TypeOrmModule.forFeature([UserEntity]),
GraphQLModule.forRoot(GraphQLConfig),
],
providers: [UserService, UserResolver],
})
export class UserModule {}
and it will automatically enable credentials value to be "include" from "omit"
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
Solution | Source |
---|---|
Solution 1 | Mika Void |
Solution 2 | Raj Gohil |