请求在 Graphql 解析器中未定义,但在中间件中包含一些值。 (节点,快递)

Posted

技术标签:

【中文标题】请求在 Graphql 解析器中未定义,但在中间件中包含一些值。 (节点,快递)【英文标题】:Request is undefined in Graphql Resolver but contains some value in Middleware. (Node, Express) 【发布时间】:2020-04-26 22:31:27 【问题描述】:

我正在尝试使用 jwt 令牌对 User 进行身份验证,并将 userId 和身份验证检查添加到请求(req)中,如中间件文件所示,这里是 req.isAuth 返回 true

问题是相同的req 在 Graphql 的 Resolver 中是 undefined 的,因此不再授予 api 使用权限。

任何帮助将不胜感激。 谢谢

app.js

const express = require('express');
const bodyParser = require('body-parser');
const graphqlHttp = require('express-graphql');
const mongoose = require('mongoose');

const isAuth = require('./middleware/is-auth');

const graphQlSchema = require('./graphql/schema/index');
const graphQlResolvers = require('./graphql/resolvers/index');

const app = express();

app.use(bodyParser.json());
app.use(isAuth);

app.use((req, res, next)=>
    console.log(req);
    res.setHeader('Access-Control-Allow-Origin','*');
    res.setHeader('Access-Control-Allow-Methods', 'POST,GET,OPTIONS');
    res.setHeader('Access-Control-Allow-Headers', 'Content-Type,Authorization');
    if (req.method === 'OPTIONS')
        return res.sendStatus(200);
    
    next();

);

app.use('/graphql', graphqlHttp(
    schema: graphQlSchema,
    rootValue: graphQlResolvers,
    graphiql: true
));

mongoose.set('useCreateIndex', true);

mongoose.connect(`mongodb+srv://user:password@clusterName.mongodb.net/project-name?retryWrites=true&w=majority`,  useNewUrlParser: true, useUnifiedTopology: true ).then(() =>
    app.listen(process.env.PORT || 3002);
).catch(err => 
    console.log(err);
);

中间件 is-auth.js

const jwt = require('jsonwebtoken');

module.exports = (req, res, next) => 
    const authHeader = req.get('Authorization');
    if(!authHeader)
        req.isAuth = false;
        return next();
    
    const token = authHeader.split(' ')[1];

    if(!token || token === '')
        req.isAuth = false;
        return next();
    
    let decodedToken;
    try 

        decodedToken = jwt.verify(token, 'supersecret');
    catch(err)
        req.isAuth = false;
        return next();
    

    if(!decodedToken)
        req.isAuth = false;
        return next();
    
    req.isAuth = true;
    req.userId = decodedToken.userId;
    console.log(req.isAuth); // returns TRUE
    next();

GraphQl-Resolver

const User = require('../../models/user');
const Post = require('../../models/post');
const Comment = require('../../models/comment');

const jwt = require('jsonwebtoken');

module.exports = 
    fetchPosts: async (req) => 
        console.log(req.isAuth); // This returns Undefined
        if(!req.isAuth)
            throw new Error("Not Authorised to access this feature");
        
        try
            const userId = req.userId; //"5e0edd18845b912b244a1990";

            const following = await User.findOne(_id: userId);

            const postList =  new Array;

            await Promise.all(following.map( async eachUser => 
                const createdPosts = await User.findOne(_id: eachUser);
                await Promise.all(createdPosts.map(async eachPost => 
                    const postDetail = await Post.findOne(_id: eachPost);

                    await postList.push(postDetail);
                ));
            ));

            return postList;
        catch(err)
            throw(err);
        

    ,

【问题讨论】:

【参考方案1】:

我自己解决了。

问题发生在仅传递 req 作为参数时。

解决方案: 同时传递 argsreq 解决了这个问题。

【讨论】:

以上是关于请求在 Graphql 解析器中未定义,但在中间件中包含一些值。 (节点,快递)的主要内容,如果未能解决你的问题,请参考以下文章

正确声明 GraphQL Yoga 提供的 Prisma 字段但在解析器中不需要的方法

如何在nestjs graphql中实现用户保护

如何知道 Sangria GraphQL 中对象解析器中的请求字段

NestJS 5 GraphQL 错误查询在解析器中定义,但不在模式中

解析器中的 AppSync GraphQL 变异服务器逻辑

在 GraphQL 解析器中链接集合