I tried to update part of a document that has an array. I hear this is a big no-no in mongoose but am unaware how I can force it to update the array. It does it correctly in the code (as in, it updates the value in the locally fetched document,) but when I try to save it via await mongoUser.save(), it is not updated in mongo.
Here is my schema code
const mongoose = require("mongoose");
const UserSchema = new mongoose.Schema({
id: { type: String, required: true},
socialCreditScore: { type: Number, required: true, default: 1000 },
/* A+: 1050
// A: 960 - 1050
// B: 850 - 959
// C: 600 - 849
/ D: 0 - 599 */
isStaff: { type: Boolean, required: true, default: false },
blacklisted: { type: Boolean, required: true, default: false},
guildScores: { type: Array, required: true, strict: false } ,
notifyChange: { type: Boolean, required: true, default: false }
}, {strict: false, timestamps: true })
module.exports = mongoose.model('User', UserSchema);
Here is an example of the locally updated document
{
_id: new ObjectId("61c1218ae82898e9cd7af768"),
id: '945914953495034509',
socialCreditScore: 2100,
isStaff: false,
blacklisted: false,
# Previously: guildScores: [ { id: "...", laborScore: 0 } ]
guildScores: [ { id: '04503405340534545', laborScore: 2000 } ],
notifyChange: false,
createdAt: 2021-12-21T00:36:26.871Z,
updatedAt: 2021-12-21T00:50:27.286Z,
__v: 0
}
Code to update User
const data = await User.find({ id: message.author.id });
const mongoUser = data[0];
// ...
mongoUser.socialCreditScore += socCreditBoost;
const guildScoreData = mongoUser.guildScores.find(guild => guild.id === message.guild.id);
// { id, laborScore }
guildScoreData.laborScore += salary;
console.log(mongoUser);
await mongoUser.save();
EDIT: I've noticed that the socialCreditScore value updates correctly every time I try to update it, however the guildScore does not.
const guildScoreData = mongoUser.guildScores.find(guild => guild.id === message.guild.id);gives you any value? I think the problem might lie in here. You are trying to compareguild.idwhich is a mongo objectId withmessage.guild.idwhich might be a string. If this is not returning the data then try usingguild.id.toString() === message.guild.idconsole.log(guildScoreData)returns: ``` { id: '921069049289523260', laborScore: 0 } ```User.updateMany({ id: message.author.id, }, { $inc: { "guildScores.$[guild].laborScore": salary, "socialCreditScore": socCreditBoost } }, { arrayFilters: [ { "guild.id": message.guild.id, }, ], })