Skip to content

Commit

Permalink
Merge pull request #14099 from csy1204/fix/gh-14098
Browse files Browse the repository at this point in the history
fix(populate): fix curPath to update appropriately
  • Loading branch information
vkarpov15 committed Nov 22, 2023
1 parent b7a63de commit a848de0
Show file tree
Hide file tree
Showing 2 changed files with 54 additions and 1 deletion.
3 changes: 2 additions & 1 deletion lib/helpers/populate/assignVals.js
Expand Up @@ -144,7 +144,7 @@ module.exports = function assignVals(o) {

const parts = _path.split('.');
let cur = docs[i];
const curPath = parts[0];
let curPath = parts[0];
for (let j = 0; j < parts.length - 1; ++j) {
// If we get to an array with a dotted path, like `arr.foo`, don't set
// `foo` on the array.
Expand All @@ -167,6 +167,7 @@ module.exports = function assignVals(o) {
cur[parts[j]] = {};
}
cur = cur[parts[j]];
curPath += parts[j + 1] ? `.${parts[j + 1]}` : '';
// If the property in MongoDB is a primitive, we won't be able to populate
// the nested path, so skip it. See gh-7545
if (typeof cur !== 'object') {
Expand Down
52 changes: 52 additions & 0 deletions test/model.populate.test.js
Expand Up @@ -8259,6 +8259,58 @@ describe('model: populate:', function() {
assert.deepEqual(populatedRides[1].files, []);
});

it('doesnt insert empty document when lean populating a path within an underneath non-existent document array (gh-14098)', async function() {
const userSchema = new mongoose.Schema({
fullName: String,
company: String
});
const User = db.model('User', userSchema);

const fileSchema = new mongoose.Schema({
_id: String,
uploaderId: {
type: mongoose.ObjectId,
ref: 'User'
}
}, { toObject: { virtuals: true }, toJSON: { virtuals: true } });
fileSchema.virtual('uploadedBy', {
ref: 'User',
localField: 'uploaderId',
foreignField: '_id',
justOne: true
});

const contentSchema = new mongoose.Schema({
memo: String,
files: { type: [fileSchema], default: [] }
}, { toObject: { virtuals: true }, toJSON: { virtuals: true }, _id: false });

const postSchema = new mongoose.Schema({
title: String,
content: { type: contentSchema }
}, { toObject: { virtuals: true }, toJSON: { virtuals: true } });
const Post = db.model('Test1', postSchema);

const user = await User.create({ fullName: 'John Doe', company: 'GitHub' });
await Post.create([
{ title: 'London-Paris' },
{
title: 'Berlin-Moscow',
content: {
memo: 'Not Easy',
files: [{ _id: '123', uploaderId: user._id }]
}
}
]);
await Post.updateMany({}, { $unset: { 'content.files': 1 } });
const populatedRides = await Post.find({}).populate({
path: 'content.files.uploadedBy',
justOne: true
}).lean();
assert.equal(populatedRides[0].content.files, undefined);
assert.equal(populatedRides[1].content.files, undefined);
});

it('sets empty array if populating undefined path (gh-8455)', async function() {
const TestSchema = new Schema({
thingIds: [mongoose.ObjectId]
Expand Down

0 comments on commit a848de0

Please sign in to comment.