【问题标题】:How to save array data in nodejs using mongoose?如何使用猫鼬在nodejs中保存数组数据?
【发布时间】:2017-07-23 15:44:53
【问题描述】:

我被困在 mongoDb 中保存数据。这里数据在数组中,如果 mongodb 没有,我需要插入数据。请看代码:-

var contactPersonData = [{
    Name: 'Mr. Bah',
    Organization: 'Ashima Limited - Point 2'
}, {
    Name: 'Mr. Sel',
    Organization: 'Ashima Limited - Point 2'
}, {
    Name: 'Mr.ATEL',
    Organization: 'Ashima Limited - Point 2'
}, {
    Name: 'ANISH',
    Organization: 'Ashima Limited - Point 2'
}, {
    Name: 'sunny ji',
    Organization: 'Ashima Limited - Point 2'
}, {
    Name: 'ashish',
    Organization: 'Ashima Limited - Point 2'
}]
console.log('filedata', contactPersonData);
var escapeData = [];
var tempArr = [];

function saveContact(personObj, mainCallback) {
    var tempC = personObj['Organization'].trim();
    var insertData = {};
    Contact.findOne({ companyName: tempC })
        .exec(function(err, contact) {
            if (err)
                return mainCallback(err);
            console.log('find com', contact)
            if (contact) {
                //document exists
                mainCallback(null, insertData);
            } else {
                var newContact = new Contact({ companyName: tempC, createdBy: '58ae5d18ba71d4056f30f7b1' });
                newContact.save(function(err, contact) {
                    if (err)
                        return mainCallback(err);
                    console.log('new contact', contact)
                    insertData.contactId = contact._id;
                    insertData.name = personObj['Name'];
                    insertData.email = personObj['Email'];
                    insertData.contactNumber = { number: personObj['Phone'] };
                    insertData.designation = personObj['Designation'];
                    tempArr.push(insertData);
                    mainCallback(null, insertData);
                })
            }

        });
}
async.map(contactPersonData, saveContact, function(err, result) {
        console.log(err)
        console.log(result)
    },
    function(err) {
        if (err)
            return next(err);
        res.status(200).json({ unsaved: escapeData })

    })

根据上面的代码,它必须插入六个文档而不是一个。我认为上面的迭代不等待完成前一个。因此,if 条件始终为false 并执行else

【问题讨论】:

    标签: node.js mongoose promise async-await async.js


    【解决方案1】:

    您的saveContact() 功能很好。您获得 6 个文档而不是 1 个文档的原因是 async.map() 并行运行您的代码。所有 6 个请求都是并行发出的,而不是一个接一个。

    来自async.map() 函数的文档 -

    请注意,由于此函数将 iteratee 并行应用于每个项目,因此无法保证 iteratee 函数将按顺序完成。

    因此,在您的数据库中创建文档之前,所有查询都已运行,并且所有 6 个查询都无法找到该文档,因为它仍在创建过程中。因此,您的 saveContact() 方法会创建所有 6 个文档。

    如果您再次运行您的代码,则不会再形成任何文档,因为到那时您的文档就会形成。

    您应该尝试使用async.mapSeries() 运行您的代码以串行处理您的请求。只需在上面的代码中将map() 替换为mapSeries()。这样,它将等待一个请求完成,然后执行另一个请求,结果只会创建一个文档。更多关于async.mapSeries()here

    【讨论】:

    • 没有任何async.serial() 方法。有async.series() 方法,但我不明白如何使用循环运行此方法,即上述问题中的contactPersonData
    【解决方案2】:

    你好像用错了async.map()

    首先,async.map() 只有 3 个参数(即 colliterateecallback),那么为什么会有 4 个参数?在您的情况下,coll 是您的 contactPersonDataiteratee 是您的 saveContact 函数,callback 是匿名函数。

    其次,使用async.map() 的全部意义在于创建一个新数组。你不是那样使用它,而是更像async.each()

    第三,您可能应该按顺序而不是并行循环遍历元素。因此,您应该使用async.mapSeries() 而不是async.map()

    以下是我将如何修改/缩短您的代码:

    var contactPersonData = [{
        Name: 'Mr. Bah',
        Organization: 'Ashima Limited - Point 2'
    }, {
        Name: 'Mr. Sel',
        Organization: 'Ashima Limited - Point 2'
    }, {
        Name: 'Mr.ATEL',
        Organization: 'Ashima Limited - Point 2'
    }, {
        Name: 'ANISH',
        Organization: 'Ashima Limited - Point 2'
    }, {
        Name: 'sunny ji',
        Organization: 'Ashima Limited - Point 2'
    }, {
        Name: 'ashish',
        Organization: 'Ashima Limited - Point 2'
    }];
    
    function saveContact(personObj, mainCallback) {
        var tempC = personObj.Organization.trim();
        Contact.findOne({ companyName: tempC }, function (err, contact) {
            if (err)
                return mainCallback(err);
            console.log('found contact', contact);
            // document exists, so mark it as complete and pass the old item
            if (contact) 
                return mainCallback(null, contact);
            // document does not exist, so add it
            contact = new Contact({ companyName: tempC, createdBy: '58ae5d18ba71d4056f30f7b1' });
            contact.save(function (err, contact) {
                if (err)
                    return mainCallback(err);
                console.log('created new contact', contact)
                // mark it as complete and pass a new/transformed item
                mainCallback(null, {
                    contactId: contact._id,
                    name: personObj.Name,
                    email: personObj.Email, // ??
                    contactNumber: { number: personObj.Phone }, // ??
                    designation: personObj.Designation // ??
                });
            });
        });
    };
    
    async.mapSeries(contactPersonData, saveContact, function (err, contacts) {
        if (err)
            return next(err);
        // at this point, contacts will have an array of your old and new/transformed items
        console.log('transformed contacts', contacts);
        res.json({ unsaved: contacts });
    });
    

    ?? cmets 而言,这意味着您的contactPersonData 中没有这些属性,因此将是undefined

    【讨论】:

      猜你喜欢
      • 2018-05-21
      • 1970-01-01
      • 2017-08-31
      • 1970-01-01
      • 2016-05-03
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2016-05-05
      相关资源
      最近更新 更多