Mongoose 部分更新对象

Nor*_*ert 5 javascript mongoose mongodb

我有一个简单的用户模型:

{
  _id: "59d72070d9d03b28934b972b"
  firstName: "first"
  lastName: "last"
  email: "first.last@gmail.com"
  subscriptions: {
    newsletter: true,
    blog: true
  }
}
Run Code Online (Sandbox Code Playgroud)

我正在尝试对对象进行部分更新subscriptions。我正在传递id用户和一个payload对象,该对象可以具有该对象的一个​​或两个属性。假设我只想更新newsletter并将其设置为false. 我会派:

{ id: "59d72070d9d03b28934b972b", payload: { newsletter: false } }
Run Code Online (Sandbox Code Playgroud)

进而:

const user = await User.findByIdAndUpdate(
  args.id,
  { $set: { subscriptions: args.payload } },
  { upsert: true, new: true }
);
Run Code Online (Sandbox Code Playgroud)

这将返回:

subscriptions: {
  newsletter: false
}
Run Code Online (Sandbox Code Playgroud)

有没有办法只在newsletter我只传入newsletter有效负载对象时修改属性而不删除其他属性?我知道在这个例子中我只有两个属性,但随着时间的推移,该对象将不断扩展。

Ber*_*tel 5

要仅更新嵌套字段,请使用{ "subscriptions.newsletter": false }

const user = (await User.findByIdAndUpdate(
    args.id, {
        $set: {
            "subscriptions.newsletter": args.payload
        }
    }, {
        new: true
    }
));
Run Code Online (Sandbox Code Playgroud)

$set如果您的输入可能缺少字段,您可以仅使用您在输入中指定的字段构建动态查询:

async function save(id, query) {
    const user = (await User.findByIdAndUpdate(
        id, {
            $set: query
        }, {
            new: true
        }
    ));
    console.log(user);
}

var id = mongoose.Types.ObjectId("59d91f1a06ecf429c8aae221");
var input = {
    newsletter: false,
    blog: false
};

var query = {};
for (var key in input) {
    query["subscriptions." + key] = input[key];
}

save(id, query);
Run Code Online (Sandbox Code Playgroud)


Nor*_*ert 1

我最终做了以下事情:

const user = await User.findById(args.id);

// merge subscriptions
user.subscriptions = Object.assign({}, user.subscriptions, args.payload);

return user.save();
Run Code Online (Sandbox Code Playgroud)