【问题标题】:Incorrect result is returned in the callback回调中返回不正确的结果
【发布时间】:2018-12-23 13:48:21
【问题描述】:

您好,我想合并这两个集合并发送合并后的结果。我做了以下。我正在使用 mongoclient。

> module.exports = function (context, req) {
> 
>     //making the connection
>     var response;
>     //check for the request method
> 
>     if (req.method !== 'GET') {
>         response = {
>             status: 500,
>             body: {
>                 "code": 500,
>                 "message": "Invalid request. Please check the request method or parameter"
>             },
>             headers: {
>                 'Content-Type': 'application/json'
>             }
>         }
>         context.done(null, response);
>         return;
>     } //end of if
> 
>     mongoClient.connect(dbUrl, function (err, client) {
>         assert.equal(null, err);
>         var database = client.db(databaseConfig.mLabDbName);
>         var response;
>         var getUserIdParams = req.query.userId
>         var index = req.query.index;
>         var noOfResults = mapResultsWithIndex(index)
> 
> 
>         getSubByUId(database, context, getUserIdParams, function (res, err) {
> 
>             // console.log("response from the callback", res)
> 
> 
>         getForms(database, context, res, function (result) {
>                 console.log("response from secondcallback", result)
> 
> 
>                 //closing the connection
>                 client.close();
> 
>                 if (err) {
>                     console.log("an error in getting the result");
>                     response = {
>                         status: 500,
>                         body: {
>                             code: 500,
>                             message: "Error in getting the forms"
>                         },
>                         headers: {
>                             'Content-Type': 'application/json'
>                         }
>                     }
>                 } //end of error
>                 else {
>                     if (result.length > 0) {
>                         console.log("got the data");
>                         response = {
>                             status: 200,
>                             body: {
>                                 code: 200,
>                                 result: result
>                             },
>                             headers: {
>                                 'Content-Type': 'application/json'
>                             }
>                         }
>                     } else {
>                         console.log("did not get the data");
>                         response = {
>                             status: 204,
>                             body: {
>                                 code: 204,
>                                 message: "No submissions found for the user id"
>                             },
>                             headers: {
>                                 'Content-Type': 'application/json'
>                             }
>                         }
>                     }
> 
>                 }
> 
>                  context.done(null, response)
>             })
>            
> 
>         }) //end of subId
> 
>     }) //closing mongodb connection }; //closing function
> 

我的主要职能是:

var getForms = function (db, context, array, callback) {
    let newArray = [];
    // console.log("array uuuuu", array)
    for (let i = 0; i < array.length; i++) {
        db.collection('forms').find({_id:ObjectID(array[i].formId)}).toArray(function (err, res) {
            console.log("rskkkk",res.length)
            res.forEach(doc => {
                newArray.push({
                    "subId": array[i]._id,
                    "formId": array[i].formId,
                    "userId": array[i].userId,
                    "formDescription": array[i].formDescription,
                    "formFields": array[i].formFields,
                    "createdAt": array[i].createdAt,
                    "data": array[i].data,
                    "imageformedarray": doc.imageUploadedarray
                })

            })
            callback(newArray);
            console.log("new array is", newArray.length);

        })


    }



}

var getSubByUId = function (db, context, getUserIdParams, callback) {
    let arr = [],
        type;
    var getSubmissions = db.collection('user-submission').find({
        userId: getUserIdParams
    });
    getSubmissions.toArray(function (err, res) {
        res.forEach(doc => {
            var value = doc.createdAt
            if (doc.hasOwnProperty("updatedAt")) {
                value = doc.updatedAt
            }
            if ((typeof (doc.formFields)) === "string") {
                console.log("string")
                type = JSON.parse(doc.formFields)
                // type = doc.data().formFields
            } else {
                type = doc.formFields
            }

            arr.push({
                "subId": doc._id,
                "formId": doc.formId,
                "userId": doc.userId,
                "formDescription": doc.formDescription,
                "formFields": type,
                "createdAt": value,
                "data": doc

            })
        });
        // console.log("arr is", arr);
        callback(arr, err)

    })

}

我想返回整个数组,但它只返回第一个循环中的结果。当我将 getForms 的回调移动到它所在的位置时,它返回带有空值的结果。 请帮忙。

【问题讨论】:

  • 我对mongodb不熟悉。但是我想问一下你是否看到callback(newArray)之前的数组中的所有元素以及回调的样子?可能会将所有元素添加到新数组并考虑在完成循环后调用回调?只是一个想法。
  • @Bala 如果我在循环完成后调用它,newArray 将变为 null
  • 你也可以在这里发布回调函数吗?我们有 2 个函数 getForms 和 getSubByUId。但我们对 getSubByUId 感兴趣?根据描述,问题似乎只出在 getForms 上?
  • 调用context.done 会终止函数的执行。你不能循环调用它。
  • @ahemlsayed 同意,那么我应该如何返回值?他们还有其他更好的方法吗,因为我不知道。

标签: node.js mongodb azure azure-functions


【解决方案1】:

当您使用 for 循环迭代数组时,您正在触发 getForms 方法的回调。这是将控制权传递给回调,然后回调处理 context.done 的函数,该函数将始终输出第一个元素。

按原样,此代码还将导致对 context.done 的多次调用,每次函数执行只应调用一次。 请记住,context.done 的定义是 context.done([err],[propertyBag]),它需要一个对象作为输出。

更多参考请查看:https://docs.microsoft.com/en-us/azure/azure-functions/functions-reference-node

除了将functions.json 输出绑定设置为:

{
  "type": "http",
  "direction": "out",
  "name": "$return"
}

现在,如果您将 callback(newArray) 移到 for loop 之外,您应该会看到预期的结果。

【讨论】:

  • 代码正在按照您的描述工作,即它多次调用context.done,并且第一次调用 context.done() 它返回响应。现在,如果我将 callback(newArray) 移到 for 循环之外,这个 newArray 将变为 null,并返回 null 值。
  • 我使用functions.json 设置改进了答案,允许您直接从上下文调用的输出中使用。
  • 我已经添加了$return,但仍然面临同样的问题。
  • $return 允许你直接从函数返回一个值,否则它使用属性包。默认配置是使用res,这样您就可以编写context.res.body= [1,2],然后编写context.done(null),输出将是[1,2],这可能会更好地映射到您现有的代码
猜你喜欢
  • 2012-04-11
  • 2016-02-06
  • 2017-05-09
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2014-11-03
  • 2021-10-07
  • 2013-02-16
相关资源
最近更新 更多