Meteor:更新MongoDB中指定数组索引中的元素

时间:2018-04-11 08:58:45

标签: javascript arrays mongodb meteor

所以我来自一个纯粹的javascript背景,我正在制作一个流星项目,我有以下MongoDB集合,名为" Semaines":

{
    _id: /*random ID*/,
    id_utilisateur: /*user ID*/,
    isCreated: true,
    jours: {
        lundi: [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0],
        mardi: [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0],
        mercredi: [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0],
        jeudi: [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0],
        vendredi: [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0],
        samedi: [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0],
        dimanche: [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0],
    }
}

使用以下方法,我想在指定日期和索引(此处代表小时)更新元素:

    //sent values are : idUt = Meteor.userId(), day = "vendredi", hour = 0, score = 10
    'semaines.updateTable'(idUt, day, hour, score){
        check(idUt, String);
        check(day, String);
        check(hour, Number);
        check(score, Number);
        Semaines.update({id_utilisateur: idUt},{$set : {"jours.$[day].$[hour]": score}});
    }

这似乎不起作用。我认为这是因为查询实际上是,我发送的值是:

    $set : {jours.vendredi.0 : 10}

这显然不起作用,但我没有看到我的查询如何成为这个,我认为这将起作用:

    $set : {jours.vendredi[0] : 10}

1 个答案:

答案 0 :(得分:0)

流星解决方案> 1.6.2 / Mongo> 3.6 - 使用arrayFilter:

您要做的是在查询中使用computed properties{[keyVar]: val})并嵌套它。

您还需要使用arrayFilter来定位数组的特定索引

Semaines.update(
  { id_utilisateur: idUt },
  { $set : { jours: { [day]: { "$[index]": score } } } },
  { arrayFilters: [ { index: hour } ] },
);

因为它当前是这个文字字符串:"jours.$[day].$[hour]"

我不确定Meteor Collections是否会通过这样的选项,所以你可能需要获取原始的mongo集合:

Semaines.rawCollection().update(
  { id_utilisateur: idUt },
  { $set : { jours: { [day]: { "$[index]": score } } } },
  { arrayFilters: [ { index: hour } ] },
);

流星的解决方案< 1.6.2 / Mongo< 3.6 - 替换阵列

如果无法访问Mongo 3.6中更强大的运算符,我们就可以在javascript中自行完成工作了:

'semaines.updateTable'(idUt, day, hour, score){
    check(idUt, String);
    check(day, String);
    check(hour, Number);
    check(score, Number);
    const doc = Semaines.findOne({ id_utilisateur: idUt });
    const array = doc.jours[day];
    array[hour] = score;
    Semaines.update(
        { id_utilisateur: idUt },
        // Replace the entire jours object with a clone and modify day
        { $set : { jours: { ...doc.jours, [day]: array } } },
    );
}

注意:虽然Mongo 3.4对$position有一个$push选项,但它没有$pull的选项,所以我们不能只替换该元素