【问题标题】:Inserting a nested object in meteor在流星中插入嵌套对象
【发布时间】:2016-05-11 01:48:46
【问题描述】:

我将此文档保存在我的 mongo 集合中,名为 exam

// meteor:PRIMARY> db.exam.find()
{
    "_id" : "RLvWTcsrbRXJeTqdB",
    "examschoolid" : "5FF2JRddZdtTHuwkx",
    "examsubjects" : [
        {
            "subject" : "Z4eLrwGwqG4pw4HKX"
        },
        {
            "subject" : "fFcWby8ArpboizcT9"
        }
    ],
    "examay" : "NrsP4srFGfkc5cJkz",
    "examterm" : "5A5dNTgAkdRr5j53j",
    "examclass" : "gYF2wE4wBCRy9a3ZC",
    "examname" : "First",
    "examdate" : ISODate("2016-05-07T22:41:00Z"),
    "examresultsstatus" : "notreleased"
}

我正在尝试从此文档中选择数据并使用此代码将其保存到另一个文档中。目的是让上面文档中的 examsubjects 值成为我要插入的文档中的键。

'click .reactive-table tr': function() {
    Session.set('selectedPersonId', this._id);
    var cursor = Exam.find({ _id:
            Session.get("selectedPersonId")}).fetch();
    cursor.forEach(function(doc){
        for (i = 0; i < doc.examsubjects.length; i++) {
            for (var prop in doc.examsubjects[i]) {
                console.log("obj." + prop + " = " + doc.examsubjects[i][prop]);
                var subj = doc.examsubjects[i][prop];
                Told.insert({
                    examschoolid:"sms",
                    examname:doc.examname,
                    examsubjects: [{subj : "0"}],
                    examay:doc.examay,
                    examterm:doc.examterm,
                    examclass:doc.examclass,
                    examdate:doc.examdate
                });
            }
        }
    });
},

当代码运行时,保存主题值的变量subj 只是插入了不知道它是这样的变量的 subj

{
    "_id" : "5yjwFanBAupgu9GHq",
    "examschoolid" : "sms",
    "examname" : "First",
    "examsubjects" : [
        {
            "subj" : "0"
        }
    ],
    "examay" : "NrsP4srFGfkc5cJkz",
    "examterm" : "5A5dNTgAkdRr5j53j",
    "examclass" : "gYF2wE4wBCRy9a3ZC",
    "examdate" : ISODate("2016-05-07T22:41:00Z")
}

为什么变量不被视为变量?

编辑

'click .reactive-table tr': function() {
    Session.set('selectedPersonId', this._id);
    var cursor = Exam.find({ _id: Session.get("selectedPersonId")}).fetch();
    cursor.forEach(function(doc){

        var sq = function(){
            for (i = 0; i < doc.examsubjects.length; i++) {
                for (var prop in doc.examsubjects[i]) {
                    const subj = doc.examsubjects[i][prop];
                    let subject = {};
                    subject[subj] = "0";
                    return [subject];

                }
            }
        }
        console.log(sq());
        Told.insert({
            examschoolid:"sms",
            examname:doc.examname,
            examsubjects: sq(),
            examay:doc.examay,
            examterm:doc.examterm,
            examclass:doc.examclass,
            examdate:doc.examdate
        });

    });
    //Uncaught TypeError: cursor.count is not a function
},

更新后的代码几乎可以工作,但只插入了 1 条记录。

【问题讨论】:

  • 您要创建多少个文档?每个doc.examsubjects 对象一个?此外,我建议在跳入 Meteor 的“更深的水域”之前学习 JavaScript 的基础知识。
  • 我在插入时想要"examsubjects" : [ { "Z4eLrwGwqG4pw4HKX" : "0", "fFcWby8ArpboizcT9" : "0" } ]这种格式的数据。
  • examsubjects 是否有除subject 以外的任何属性?
  • 没关系,我正在努力。

标签: javascript mongodb meteor


【解决方案1】:

这就是 JSON 的工作原理,它从字面上获取键。使用 ES6 括号表示法修复它:

examsubjects: [{
  [subj] : "0"
}],

【讨论】:

  • 不错。假设 OP 使用的是 ES2015,我会选择这个。
【解决方案2】:

这是因为它被视为文字对象中的键。

如果您想将subj 的值作为您的键,则需要使用括号表示法,预先创建对象:

const subj = doc.examsubjects[i][prop];
let subject = {};
subject[subj] = "0";

Told.insert({
    examschoolid:"sms",
    examname:doc.examname,
    examsubjects: [subject],
    ...
});

【讨论】:

  • 此代码有效,但就像我的第一个对象一样,所有科目都应参加考试科目"examsubjects" : [ { "subject" : "Z4eLrwGwqG4pw4HKX" }, { "subject" : "fFcWby8ArpboizcT9" } ], 该代码创建两个文档而不是examsubjects 下的两个记录
  • 所以在循环之后执行插入。现在您正在插入循环本身,每个insert 创建一个单独的对象。将它们添加到数组中(您可能可以使用Array.map())并插入一次。
  • 不是你这样做的方式,我也不推荐这种方法。创建数组非常简单。也不是你没有在任何地方声明i