Skip to content

Commit

Permalink
Merge pull request #14383 from Automattic/vkarpov15/gh-14113-2
Browse files Browse the repository at this point in the history
perf(document+schema): small optimizations to make `init()` faster
  • Loading branch information
vkarpov15 committed Mar 1, 2024
2 parents 222ad3b + 92112dd commit d14d25b
Show file tree
Hide file tree
Showing 2 changed files with 16 additions and 12 deletions.
25 changes: 13 additions & 12 deletions lib/document.js
Original file line number Diff line number Diff line change
Expand Up @@ -741,7 +741,7 @@ function init(self, obj, doc, opts, prefix) {
if (i === '__proto__' || i === 'constructor') {
return;
}
path = prefix + i;
path = prefix ? prefix + i : i;
schemaType = docSchema.path(path);

// Should still work if not a model-level discriminator, but should not be
Expand All @@ -751,38 +751,39 @@ function init(self, obj, doc, opts, prefix) {
return;
}

if (!schemaType && utils.isPOJO(obj[i])) {
const value = obj[i];
if (!schemaType && utils.isPOJO(value)) {
// assume nested object
if (!doc[i]) {
doc[i] = {};
if (!strict && !(i in docSchema.tree) && !(i in docSchema.methods) && !(i in docSchema.virtuals)) {
self[i] = doc[i];
}
}
init(self, obj[i], doc[i], opts, path + '.');
init(self, value, doc[i], opts, path + '.');
} else if (!schemaType) {
doc[i] = obj[i];
doc[i] = value;
if (!strict && !prefix) {
self[i] = obj[i];
self[i] = value;
}
} else {
// Retain order when overwriting defaults
if (doc.hasOwnProperty(i) && obj[i] !== void 0) {
if (doc.hasOwnProperty(i) && value !== void 0) {
delete doc[i];
}
if (obj[i] === null) {
if (value === null) {
doc[i] = schemaType._castNullish(null);
} else if (obj[i] !== undefined) {
const wasPopulated = obj[i].$__ == null ? null : obj[i].$__.wasPopulated;
} else if (value !== undefined) {
const wasPopulated = value.$__ == null ? null : value.$__.wasPopulated;

if (schemaType && !wasPopulated) {
try {
if (opts && opts.setters) {
// Call applySetters with `init = false` because otherwise setters are a noop
const overrideInit = false;
doc[i] = schemaType.applySetters(obj[i], self, overrideInit);
doc[i] = schemaType.applySetters(value, self, overrideInit);
} else {
doc[i] = schemaType.cast(obj[i], self, true);
doc[i] = schemaType.cast(value, self, true);
}
} catch (e) {
self.invalidate(e.path, new ValidatorError({
Expand All @@ -794,7 +795,7 @@ function init(self, obj, doc, opts, prefix) {
}));
}
} else {
doc[i] = obj[i];
doc[i] = value;
}
}
// mark as hydrated
Expand Down
3 changes: 3 additions & 0 deletions lib/schema.js
Original file line number Diff line number Diff line change
Expand Up @@ -955,6 +955,9 @@ reserved.collection = 1;

Schema.prototype.path = function(path, obj) {
if (obj === undefined) {
if (this.paths[path] != null) {
return this.paths[path];
}
// Convert to '.$' to check subpaths re: gh-6405
const cleanPath = _pathToPositionalSyntax(path);
let schematype = _getPath(this, path, cleanPath);
Expand Down

0 comments on commit d14d25b

Please sign in to comment.