mongoose 9.7.1 → 9.7.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/eslint.config.mjs +4 -1
- package/lib/document.js +9 -3
- package/lib/schema.js +11 -7
- package/lib/types/documentArray/methods/index.js +117 -3
- package/package.json +4 -3
- package/types/models.d.ts +9 -40
package/eslint.config.mjs
CHANGED
package/lib/document.js
CHANGED
|
@@ -1948,7 +1948,9 @@ Document.prototype.get = function(path, type, options) {
|
|
|
1948
1948
|
|
|
1949
1949
|
// Fast path if we know we're just accessing top-level path on the document:
|
|
1950
1950
|
// just get the schema path, avoid `$__path()` because that does string manipulation
|
|
1951
|
-
let schema = noDottedPath ?
|
|
1951
|
+
let schema = noDottedPath ?
|
|
1952
|
+
Object.hasOwn(this.$__schema.paths, path) ? this.$__schema.paths[path] : undefined :
|
|
1953
|
+
this.$__path(path);
|
|
1952
1954
|
if (schema == null) {
|
|
1953
1955
|
schema = this.$__schema.virtualpath(path);
|
|
1954
1956
|
|
|
@@ -1958,7 +1960,7 @@ Document.prototype.get = function(path, type, options) {
|
|
|
1958
1960
|
}
|
|
1959
1961
|
|
|
1960
1962
|
if (noDottedPath) {
|
|
1961
|
-
let obj = this._doc[path];
|
|
1963
|
+
let obj = Object.hasOwn(this._doc, path) ? this._doc[path] : undefined;
|
|
1962
1964
|
if (adhoc) {
|
|
1963
1965
|
obj = adhoc.cast(obj);
|
|
1964
1966
|
}
|
|
@@ -1985,6 +1987,10 @@ Document.prototype.get = function(path, type, options) {
|
|
|
1985
1987
|
}
|
|
1986
1988
|
|
|
1987
1989
|
for (let i = 0, l = pieces.length; i < l; i++) {
|
|
1990
|
+
if (specialProperties.has(pieces[i])) {
|
|
1991
|
+
return undefined;
|
|
1992
|
+
}
|
|
1993
|
+
|
|
1988
1994
|
if (obj?._doc) {
|
|
1989
1995
|
obj = obj._doc;
|
|
1990
1996
|
}
|
|
@@ -2006,7 +2012,7 @@ Document.prototype.get = function(path, type, options) {
|
|
|
2006
2012
|
|
|
2007
2013
|
if (schema != null && options.getters !== false) {
|
|
2008
2014
|
obj = schema.applyGetters(obj, this);
|
|
2009
|
-
} else if (this.$__schema.nested
|
|
2015
|
+
} else if (Object.hasOwn(this.$__schema.nested, path) && options.virtuals) {
|
|
2010
2016
|
// Might need to apply virtuals if this is a nested path
|
|
2011
2017
|
return applyVirtuals(this, clone(obj) || {}, { path: path });
|
|
2012
2018
|
}
|
package/lib/schema.js
CHANGED
|
@@ -1268,7 +1268,7 @@ reserved.collection = 1;
|
|
|
1268
1268
|
|
|
1269
1269
|
Schema.prototype.path = function(path, obj) {
|
|
1270
1270
|
if (obj === undefined) {
|
|
1271
|
-
if (this.paths
|
|
1271
|
+
if (Object.hasOwn(this.paths, path)) {
|
|
1272
1272
|
return this.paths[path];
|
|
1273
1273
|
}
|
|
1274
1274
|
// Convert to '.$' to check subpaths re: gh-6405
|
|
@@ -1296,9 +1296,15 @@ Schema.prototype.path = function(path, obj) {
|
|
|
1296
1296
|
: undefined;
|
|
1297
1297
|
}
|
|
1298
1298
|
|
|
1299
|
+
const subpaths = path.indexOf('.') === -1 ? [path] : path.split('.');
|
|
1300
|
+
const last = subpaths.pop();
|
|
1301
|
+
if (utils.specialProperties.has(last)) {
|
|
1302
|
+
throw new MongooseError('Cannot set special property `' + last + '` on a schema');
|
|
1303
|
+
}
|
|
1304
|
+
|
|
1299
1305
|
// some path names conflict with document methods
|
|
1300
|
-
const firstPieceOfPath =
|
|
1301
|
-
if (reserved
|
|
1306
|
+
const firstPieceOfPath = subpaths.length === 0 ? last : subpaths[0];
|
|
1307
|
+
if (Object.hasOwn(reserved, firstPieceOfPath) && !this.options.suppressReservedKeysWarning) {
|
|
1302
1308
|
const errorMessage = `\`${firstPieceOfPath}\` is a reserved schema pathname and may break some functionality. ` +
|
|
1303
1309
|
'You are allowed to use it, but use at your own risk. ' +
|
|
1304
1310
|
'To disable this warning pass `suppressReservedKeysWarning` as a schema option.';
|
|
@@ -1311,8 +1317,6 @@ Schema.prototype.path = function(path, obj) {
|
|
|
1311
1317
|
}
|
|
1312
1318
|
|
|
1313
1319
|
// update the tree
|
|
1314
|
-
const subpaths = path.split(/\./);
|
|
1315
|
-
const last = subpaths.pop();
|
|
1316
1320
|
let branch = this.tree;
|
|
1317
1321
|
let fullPath = '';
|
|
1318
1322
|
|
|
@@ -1536,7 +1540,7 @@ function getMapPath(schema, path) {
|
|
|
1536
1540
|
} else if (val.schema && path.startsWith(cleanPath + '.')) {
|
|
1537
1541
|
let remnant = path.slice(cleanPath.length + 1);
|
|
1538
1542
|
remnant = remnant.slice(remnant.indexOf('.') + 1);
|
|
1539
|
-
return val.schema.
|
|
1543
|
+
return val.schema.path(remnant);
|
|
1540
1544
|
} else if (val.$isSchemaMap && path.startsWith(cleanPath + '.')) {
|
|
1541
1545
|
let remnant = path.slice(cleanPath.length + 1);
|
|
1542
1546
|
remnant = remnant.slice(remnant.indexOf('.') + 1);
|
|
@@ -3026,7 +3030,7 @@ Schema.prototype._getPathType = function(path) {
|
|
|
3026
3030
|
};
|
|
3027
3031
|
}
|
|
3028
3032
|
return { schema: foundschema, pathType: 'real' };
|
|
3029
|
-
} else if (p === parts.length && schema.nested
|
|
3033
|
+
} else if (p === parts.length && Object.hasOwn(schema.nested, trypath)) {
|
|
3030
3034
|
return { schema: schema, pathType: 'nested' };
|
|
3031
3035
|
}
|
|
3032
3036
|
}
|
|
@@ -12,6 +12,7 @@ const arrayPathSymbol = require('../../../helpers/symbols').arrayPathSymbol;
|
|
|
12
12
|
const arraySchemaSymbol = require('../../../helpers/symbols').arraySchemaSymbol;
|
|
13
13
|
const documentArrayParent = require('../../../helpers/symbols').documentArrayParent;
|
|
14
14
|
|
|
15
|
+
const _baseReverse = Array.prototype.reverse;
|
|
15
16
|
const _baseToString = Array.prototype.toString;
|
|
16
17
|
|
|
17
18
|
const methods = {
|
|
@@ -211,7 +212,7 @@ const methods = {
|
|
|
211
212
|
},
|
|
212
213
|
|
|
213
214
|
/**
|
|
214
|
-
* Wraps [`Array#push`](https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Array/push) with proper change tracking.
|
|
215
|
+
* Wraps [`Array#push`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/push) with proper change tracking.
|
|
215
216
|
*
|
|
216
217
|
* @param {...object} [args]
|
|
217
218
|
* @api public
|
|
@@ -220,8 +221,37 @@ const methods = {
|
|
|
220
221
|
*/
|
|
221
222
|
|
|
222
223
|
push() {
|
|
224
|
+
const shouldReindex = _shouldReindexAfterPush(arguments);
|
|
223
225
|
const ret = ArrayMethods.push.apply(this, arguments);
|
|
224
226
|
|
|
227
|
+
if (shouldReindex) {
|
|
228
|
+
_updateSubdocIndexes(this);
|
|
229
|
+
}
|
|
230
|
+
_updateParentPopulated(this);
|
|
231
|
+
|
|
232
|
+
return ret;
|
|
233
|
+
},
|
|
234
|
+
|
|
235
|
+
/**
|
|
236
|
+
* Wraps [`Array#pop`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/pop) with proper change tracking.
|
|
237
|
+
* @api private
|
|
238
|
+
*/
|
|
239
|
+
|
|
240
|
+
pop() {
|
|
241
|
+
const ret = ArrayMethods.pop.apply(this, arguments);
|
|
242
|
+
|
|
243
|
+
_updateParentPopulated(this);
|
|
244
|
+
|
|
245
|
+
return ret;
|
|
246
|
+
},
|
|
247
|
+
|
|
248
|
+
/*!
|
|
249
|
+
* ignore
|
|
250
|
+
*/
|
|
251
|
+
|
|
252
|
+
$pop() {
|
|
253
|
+
const ret = ArrayMethods.$pop.apply(this, arguments);
|
|
254
|
+
|
|
225
255
|
_updateParentPopulated(this);
|
|
226
256
|
|
|
227
257
|
return ret;
|
|
@@ -239,32 +269,96 @@ const methods = {
|
|
|
239
269
|
pull() {
|
|
240
270
|
const ret = ArrayMethods.pull.apply(this, arguments);
|
|
241
271
|
|
|
272
|
+
_updateSubdocIndexes(this);
|
|
242
273
|
_updateParentPopulated(this);
|
|
243
274
|
|
|
244
275
|
return ret;
|
|
245
276
|
},
|
|
246
277
|
|
|
247
278
|
/**
|
|
248
|
-
* Wraps [`Array#shift`](https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Array/
|
|
279
|
+
* Wraps [`Array#shift`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/shift) with proper change tracking.
|
|
249
280
|
* @api private
|
|
250
281
|
*/
|
|
251
282
|
|
|
252
283
|
shift() {
|
|
253
284
|
const ret = ArrayMethods.shift.apply(this, arguments);
|
|
254
285
|
|
|
286
|
+
_updateSubdocIndexes(this);
|
|
287
|
+
_updateParentPopulated(this);
|
|
288
|
+
|
|
289
|
+
return ret;
|
|
290
|
+
},
|
|
291
|
+
|
|
292
|
+
/*!
|
|
293
|
+
* ignore
|
|
294
|
+
*/
|
|
295
|
+
|
|
296
|
+
$shift() {
|
|
297
|
+
const ret = ArrayMethods.$shift.apply(this, arguments);
|
|
298
|
+
|
|
299
|
+
_updateSubdocIndexes(this);
|
|
255
300
|
_updateParentPopulated(this);
|
|
256
301
|
|
|
257
302
|
return ret;
|
|
258
303
|
},
|
|
259
304
|
|
|
260
305
|
/**
|
|
261
|
-
* Wraps [`Array#splice`](https://developer.mozilla.org/en/JavaScript/Reference/Global_Objects/Array/splice) with proper change tracking and casting.
|
|
306
|
+
* Wraps [`Array#splice`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/splice) with proper change tracking and casting.
|
|
262
307
|
* @api private
|
|
263
308
|
*/
|
|
264
309
|
|
|
265
310
|
splice() {
|
|
266
311
|
const ret = ArrayMethods.splice.apply(this, arguments);
|
|
267
312
|
|
|
313
|
+
_updateSubdocIndexes(this);
|
|
314
|
+
_updateParentPopulated(this);
|
|
315
|
+
|
|
316
|
+
return ret;
|
|
317
|
+
},
|
|
318
|
+
|
|
319
|
+
/**
|
|
320
|
+
* Wraps [`Array#reverse`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/reverse)
|
|
321
|
+
* with proper change tracking.
|
|
322
|
+
* @api private
|
|
323
|
+
*/
|
|
324
|
+
|
|
325
|
+
reverse() {
|
|
326
|
+
_baseReverse.call(this.__array);
|
|
327
|
+
this._registerAtomic('$set', this);
|
|
328
|
+
|
|
329
|
+
_updateSubdocIndexes(this);
|
|
330
|
+
_updateParentPopulated(this);
|
|
331
|
+
|
|
332
|
+
return this;
|
|
333
|
+
},
|
|
334
|
+
|
|
335
|
+
/**
|
|
336
|
+
* Wraps [`Array#sort`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/sort)
|
|
337
|
+
* with proper change tracking.
|
|
338
|
+
*
|
|
339
|
+
* @param {Function} [compareFunction]
|
|
340
|
+
* @api private
|
|
341
|
+
*/
|
|
342
|
+
|
|
343
|
+
sort() {
|
|
344
|
+
const ret = ArrayMethods.sort.apply(this, arguments);
|
|
345
|
+
|
|
346
|
+
_updateSubdocIndexes(this);
|
|
347
|
+
_updateParentPopulated(this);
|
|
348
|
+
|
|
349
|
+
return ret;
|
|
350
|
+
},
|
|
351
|
+
|
|
352
|
+
/**
|
|
353
|
+
* Wraps [`Array#unshift`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/unshift)
|
|
354
|
+
* with proper change tracking.
|
|
355
|
+
* @api private
|
|
356
|
+
*/
|
|
357
|
+
|
|
358
|
+
unshift() {
|
|
359
|
+
const ret = ArrayMethods.unshift.apply(this, arguments);
|
|
360
|
+
|
|
361
|
+
_updateSubdocIndexes(this);
|
|
268
362
|
_updateParentPopulated(this);
|
|
269
363
|
|
|
270
364
|
return ret;
|
|
@@ -389,6 +483,26 @@ const methods = {
|
|
|
389
483
|
|
|
390
484
|
module.exports = methods;
|
|
391
485
|
|
|
486
|
+
/*!
|
|
487
|
+
* ignore
|
|
488
|
+
*/
|
|
489
|
+
|
|
490
|
+
function _updateSubdocIndexes(arr) {
|
|
491
|
+
const rawArray = utils.isMongooseArray(arr) ? arr.__array : arr;
|
|
492
|
+
|
|
493
|
+
for (let i = 0; i < rawArray.length; ++i) {
|
|
494
|
+
if (typeof rawArray[i]?.$setIndex === 'function') {
|
|
495
|
+
rawArray[i].$setIndex(i);
|
|
496
|
+
}
|
|
497
|
+
}
|
|
498
|
+
}
|
|
499
|
+
|
|
500
|
+
function _shouldReindexAfterPush(args) {
|
|
501
|
+
return args[0] != null &&
|
|
502
|
+
utils.hasUserDefinedProperty(args[0], '$each') &&
|
|
503
|
+
args[0].$position != null;
|
|
504
|
+
}
|
|
505
|
+
|
|
392
506
|
/**
|
|
393
507
|
* If this is a document array, each element may contain single
|
|
394
508
|
* populated paths, so we need to modify the top-level document's
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "mongoose",
|
|
3
3
|
"description": "Mongoose MongoDB ODM",
|
|
4
|
-
"version": "9.7.
|
|
4
|
+
"version": "9.7.3",
|
|
5
5
|
"author": "Guillermo Rauch <guillermo@learnboost.com>",
|
|
6
6
|
"keywords": [
|
|
7
7
|
"mongodb",
|
|
@@ -20,6 +20,7 @@
|
|
|
20
20
|
"type": "commonjs",
|
|
21
21
|
"license": "MIT",
|
|
22
22
|
"dependencies": {
|
|
23
|
+
"@standard-schema/spec": "^1.1.0",
|
|
23
24
|
"kareem": "3.3.0",
|
|
24
25
|
"mongodb": "~7.2",
|
|
25
26
|
"mpath": "0.9.0",
|
|
@@ -43,8 +44,8 @@
|
|
|
43
44
|
"eslint-plugin-mocha-no-only": "1.2.0",
|
|
44
45
|
"express": "5.2.1",
|
|
45
46
|
"fs-extra": "~11.3.0",
|
|
46
|
-
"globals": "^17.4.0",
|
|
47
47
|
"glob": "^13.0.6",
|
|
48
|
+
"globals": "^17.4.0",
|
|
48
49
|
"highlight.js": "11.11.1",
|
|
49
50
|
"linkinator": "7.x",
|
|
50
51
|
"lodash.isequal": "4.5.0",
|
|
@@ -86,7 +87,7 @@
|
|
|
86
87
|
"docs:prepare:publish:6x": "git checkout 6.x && git merge 6.x && npm run docs:clean:stable && env DOCS_DEPLOY=true npm run docs:generate && mv ./docs/6.x ./tmp && git checkout gh-pages && npm run docs:copy:tmp:6x",
|
|
87
88
|
"docs:prepare:publish:7x": "env DOCS_DEPLOY=true npm run docs:generate && git checkout gh-pages && rm -rf ./docs/7.x && mv ./tmp ./docs/7.x",
|
|
88
89
|
"docs:prepare:publish:8x": "env DOCS_DEPLOY=true npm run docs:generate && git checkout gh-pages && rm -rf ./docs/8.x && mv ./tmp ./docs/8.x",
|
|
89
|
-
"docs:check-links": "linkinator http://127.0.0.1:8089 --silent --recurse --skip cdn.carbonads.com --skip m.servedby-buysellads.com --skip \"127\\.0\\.0\\.1:8089
|
|
90
|
+
"docs:check-links": "linkinator http://127.0.0.1:8089 --silent --recurse --skip cdn.carbonads.com --skip m.servedby-buysellads.com --skip \"127\\.0\\.0\\.1:8089/docs/\\d+.x\"",
|
|
90
91
|
"docs:update-mongodb-links": "node ./scripts/update-mongodb-links.js",
|
|
91
92
|
"lint": "eslint .",
|
|
92
93
|
"lint-js": "eslint . --ext .js --ext .cjs",
|
package/types/models.d.ts
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
declare module 'mongoose' {
|
|
2
2
|
import mongodb = require('mongodb');
|
|
3
|
+
import { StandardSchemaV1 as StandardSchemaV1Spec, StandardTypedV1 as StandardTypedV1Spec } from '@standard-schema/spec';
|
|
3
4
|
|
|
4
5
|
export interface DiscriminatorOptions {
|
|
5
6
|
value?: string | number | ObjectId;
|
|
@@ -108,40 +109,8 @@ declare module 'mongoose' {
|
|
|
108
109
|
*/
|
|
109
110
|
type pathsToValidate = PathsToValidate;
|
|
110
111
|
|
|
111
|
-
export
|
|
112
|
-
|
|
113
|
-
readonly version: 1;
|
|
114
|
-
readonly vendor: 'mongoose';
|
|
115
|
-
readonly validate: (
|
|
116
|
-
value: unknown,
|
|
117
|
-
options?: Options | undefined
|
|
118
|
-
) => Result<Output> | Promise<Result<Output>>;
|
|
119
|
-
}
|
|
120
|
-
|
|
121
|
-
export interface Options {
|
|
122
|
-
readonly libraryOptions?: Record<string, unknown> | undefined;
|
|
123
|
-
}
|
|
124
|
-
|
|
125
|
-
export type Result<Output> = SuccessResult<Output> | FailureResult;
|
|
126
|
-
|
|
127
|
-
export interface SuccessResult<Output> {
|
|
128
|
-
readonly value: Output;
|
|
129
|
-
readonly issues?: undefined;
|
|
130
|
-
}
|
|
131
|
-
|
|
132
|
-
export interface FailureResult {
|
|
133
|
-
readonly issues: ReadonlyArray<Issue>;
|
|
134
|
-
}
|
|
135
|
-
|
|
136
|
-
export interface Issue {
|
|
137
|
-
readonly message: string;
|
|
138
|
-
readonly path?: ReadonlyArray<PropertyKey | PathSegment> | undefined;
|
|
139
|
-
}
|
|
140
|
-
|
|
141
|
-
export interface PathSegment {
|
|
142
|
-
readonly key: PropertyKey;
|
|
143
|
-
}
|
|
144
|
-
}
|
|
112
|
+
export import StandardTypedV1 = StandardTypedV1Spec;
|
|
113
|
+
export import StandardSchemaV1 = StandardSchemaV1Spec;
|
|
145
114
|
|
|
146
115
|
interface SaveOptions extends
|
|
147
116
|
SessionOption {
|
|
@@ -270,7 +239,7 @@ declare module 'mongoose' {
|
|
|
270
239
|
base: Mongoose;
|
|
271
240
|
|
|
272
241
|
/** Standard Schema adapter for validating input with this model's schema. */
|
|
273
|
-
readonly '~standard': StandardSchemaV1.Props<TRawDocType
|
|
242
|
+
readonly '~standard': StandardSchemaV1.Props<Default__v<Require_id<TRawDocType>, ObtainSchemaGeneric<TSchema, 'TSchemaOptions'>>>;
|
|
274
243
|
|
|
275
244
|
/**
|
|
276
245
|
* If this is a discriminator model, `baseModelName` is the name of
|
|
@@ -684,11 +653,11 @@ declare module 'mongoose' {
|
|
|
684
653
|
*/
|
|
685
654
|
useConnection(connection: Connection): this;
|
|
686
655
|
|
|
687
|
-
/** Casts and validates the given object against this model's schema, passing the given `context` to custom validators. */
|
|
688
|
-
validate(): Promise<
|
|
689
|
-
validate(obj: any): Promise<
|
|
690
|
-
validate(obj: any, pathsOrOptions: PathsToValidate): Promise<
|
|
691
|
-
validate(obj: any, pathsOrOptions: { pathsToSkip?: pathsToSkip }): Promise<
|
|
656
|
+
/** Casts and validates the given object against this model's schema, returning the casted-and-validated copy of `obj`, passing the given `context` to custom validators. */
|
|
657
|
+
validate(): Promise<TRawDocType>;
|
|
658
|
+
validate(obj: any): Promise<TRawDocType>;
|
|
659
|
+
validate(obj: any, pathsOrOptions: PathsToValidate): Promise<TRawDocType>;
|
|
660
|
+
validate(obj: any, pathsOrOptions: { pathsToSkip?: pathsToSkip }): Promise<TRawDocType>;
|
|
692
661
|
|
|
693
662
|
/** Watches the underlying collection for changes using [MongoDB change streams](https://www.mongodb.com/docs/manual/changeStreams/). */
|
|
694
663
|
watch<ResultType extends mongodb.Document = any, ChangeType extends mongodb.ChangeStreamDocument = any>(pipeline?: Array<Record<string, unknown>>, options?: mongodb.ChangeStreamOptions & { hydrate?: boolean }): mongodb.ChangeStream<ResultType, ChangeType>;
|