mongoose 8.16.1 → 8.16.2

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.
@@ -506,14 +506,15 @@ function _next(ctx, cb) {
506
506
  return _nextDoc(ctx, doc, null, callback);
507
507
  }
508
508
 
509
- ctx.query.model.populate(doc, ctx._pop).then(
510
- doc => {
511
- _nextDoc(ctx, doc, ctx._pop, callback);
512
- },
513
- err => {
514
- callback(err);
509
+ _nextDoc(ctx, doc, ctx._pop, (err, doc) => {
510
+ if (err != null) {
511
+ return callback(err);
515
512
  }
516
- );
513
+ ctx.query.model.populate(doc, ctx._pop).then(
514
+ doc => callback(null, doc),
515
+ err => callback(err)
516
+ );
517
+ });
517
518
  },
518
519
  error => {
519
520
  callback(error);
package/lib/model.js CHANGED
@@ -3454,35 +3454,36 @@ Model.bulkWrite = async function bulkWrite(ops, options) {
3454
3454
  });
3455
3455
  }
3456
3456
  } else {
3457
- let remaining = validations.length;
3458
- let validOps = [];
3457
+ let validOpIndexes = [];
3459
3458
  let validationErrors = [];
3460
3459
  const results = [];
3461
- await new Promise((resolve) => {
3462
- if (validations.length === 0) {
3463
- return resolve();
3464
- }
3465
- for (let i = 0; i < validations.length; ++i) {
3466
- validations[i]((err) => {
3467
- if (err == null) {
3468
- validOps.push(i);
3469
- } else {
3470
- validationErrors.push({ index: i, error: err });
3471
- results[i] = err;
3472
- }
3473
- if (--remaining <= 0) {
3460
+ if (validations.length > 0) {
3461
+ validOpIndexes = await Promise.all(ops.map((op, i) => {
3462
+ if (i >= validations.length) {
3463
+ return i;
3464
+ }
3465
+ return new Promise((resolve) => {
3466
+ validations[i]((err) => {
3467
+ if (err == null) {
3468
+ resolve(i);
3469
+ } else {
3470
+ validationErrors.push({ index: i, error: err });
3471
+ results[i] = err;
3472
+ }
3474
3473
  resolve();
3475
- }
3474
+ });
3476
3475
  });
3477
- }
3478
- });
3476
+ }));
3477
+ validOpIndexes = validOpIndexes.filter(index => index != null);
3478
+ } else {
3479
+ validOpIndexes = ops.map((op, i) => i);
3480
+ }
3479
3481
 
3480
3482
  validationErrors = validationErrors.
3481
3483
  sort((v1, v2) => v1.index - v2.index).
3482
3484
  map(v => v.error);
3483
3485
 
3484
- const validOpIndexes = validOps;
3485
- validOps = validOps.sort().map(index => ops[index]);
3486
+ const validOps = validOpIndexes.sort().map(index => ops[index]);
3486
3487
 
3487
3488
  if (validOps.length === 0) {
3488
3489
  if (options.throwOnValidationError && validationErrors.length) {
@@ -45,7 +45,7 @@ Object.defineProperty(SchemaStringOptions.prototype, 'enum', opts);
45
45
  Object.defineProperty(SchemaStringOptions.prototype, 'match', opts);
46
46
 
47
47
  /**
48
- * If truthy, Mongoose will add a custom setter that lowercases this string
48
+ * If truthy, Mongoose will add a [custom setter](https://mongoosejs.com/docs/api/schematype.html#SchemaType.prototype.set()) that lowercases this string
49
49
  * using JavaScript's built-in `String#toLowerCase()`.
50
50
  *
51
51
  * @api public
@@ -58,7 +58,7 @@ Object.defineProperty(SchemaStringOptions.prototype, 'match', opts);
58
58
  Object.defineProperty(SchemaStringOptions.prototype, 'lowercase', opts);
59
59
 
60
60
  /**
61
- * If truthy, Mongoose will add a custom setter that removes leading and trailing
61
+ * If truthy, Mongoose will add a [custom setter](https://mongoosejs.com/docs/api/schematype.html#SchemaType.prototype.set()) that removes leading and trailing
62
62
  * whitespace using [JavaScript's built-in `String#trim()`](https://masteringjs.io/tutorials/fundamentals/trim-string).
63
63
  *
64
64
  * @api public
@@ -124,6 +124,19 @@ SchemaMixed.prototype.castForQuery = function($cond, val) {
124
124
  return val;
125
125
  };
126
126
 
127
+ /**
128
+ * Returns this schema type's representation in a JSON schema.
129
+ *
130
+ * @param [options]
131
+ * @param [options.useBsonType=false] If true, return a representation with `bsonType` for use with MongoDB's `$jsonSchema`.
132
+ * @returns {Object} JSON schema properties
133
+ */
134
+
135
+ // eslint-disable-next-line no-unused-vars
136
+ SchemaMixed.prototype.toJSONSchema = function toJSONSchema(_options) {
137
+ return {};
138
+ };
139
+
127
140
  /*!
128
141
  * Module exports.
129
142
  */
package/lib/schemaType.js CHANGED
@@ -695,10 +695,13 @@ SchemaType.prototype.transform = function(fn) {
695
695
  * console.log(user.email); // 'avenue@q.com'
696
696
  * User.updateOne({ _id: _id }, { $set: { email: 'AVENUE@Q.COM' } }); // update to 'avenue@q.com'
697
697
  *
698
+ * // Setters also transform query filters
699
+ * const user = await User.find({ email: 'AVENUE@Q.COM' }); // query for 'avenue@q.com'
700
+ *
698
701
  * As you can see above, setters allow you to transform the data before it
699
702
  * stored in MongoDB, or before executing a query.
700
703
  *
701
- * _NOTE: we could have also just used the built-in `lowercase: true` SchemaType option instead of defining our own function._
704
+ * _NOTE: we could have also just used the built-in [`lowercase: true` SchemaType option](https://mongoosejs.com/docs/api/schemastringoptions.html#SchemaStringOptions.prototype.lowercase) instead of defining our own function._
702
705
  *
703
706
  * new Schema({ email: { type: String, lowercase: true }})
704
707
  *
@@ -1779,8 +1782,8 @@ SchemaType.prototype._duplicateKeyErrorMessage = null;
1779
1782
  * @returns {Object} JSON schema properties
1780
1783
  */
1781
1784
 
1782
- SchemaType.prototype.toJSONSchema = function toJSONSchema() {
1783
- throw new Error('Converting unsupported SchemaType to JSON Schema: ' + this.instance);
1785
+ SchemaType.prototype.toJSONSchema = function toJSONSchema(_options) { // eslint-disable-line no-unused-vars
1786
+ throw new Error(`Converting unsupported SchemaType to JSON Schema: ${this.instance} at path "${this.path}"`);
1784
1787
  };
1785
1788
 
1786
1789
  /**
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "mongoose",
3
3
  "description": "Mongoose MongoDB ODM",
4
- "version": "8.16.1",
4
+ "version": "8.16.2",
5
5
  "author": "Guillermo Rauch <guillermo@learnboost.com>",
6
6
  "keywords": [
7
7
  "mongodb",
@@ -29,9 +29,9 @@
29
29
  "sift": "17.1.3"
30
30
  },
31
31
  "devDependencies": {
32
- "@babel/core": "7.27.4",
32
+ "@babel/core": "7.27.7",
33
33
  "@babel/preset-env": "7.27.2",
34
- "@mongodb-js/mongodb-downloader": "^0.3.9",
34
+ "@mongodb-js/mongodb-downloader": "^0.4.2",
35
35
  "@typescript-eslint/eslint-plugin": "^8.19.1",
36
36
  "@typescript-eslint/parser": "^8.19.1",
37
37
  "acquit": "1.4.0",
@@ -42,7 +42,7 @@
42
42
  "babel-loader": "8.2.5",
43
43
  "broken-link-checker": "^0.7.8",
44
44
  "buffer": "^5.6.0",
45
- "cheerio": "1.0.0",
45
+ "cheerio": "1.1.0",
46
46
  "crypto-browserify": "3.12.1",
47
47
  "dox": "1.0.0",
48
48
  "eslint": "8.57.1",
@@ -56,7 +56,7 @@
56
56
  "markdownlint-cli2": "^0.18.1",
57
57
  "marked": "15.0.12",
58
58
  "mkdirp": "^3.0.1",
59
- "mocha": "11.5.0",
59
+ "mocha": "11.7.1",
60
60
  "moment": "2.30.1",
61
61
  "mongodb-memory-server": "10.1.4",
62
62
  "mongodb-runner": "^5.8.2",
@@ -64,7 +64,7 @@
64
64
  "nyc": "15.1.0",
65
65
  "pug": "3.0.3",
66
66
  "q": "1.5.1",
67
- "sinon": "20.0.0",
67
+ "sinon": "21.0.0",
68
68
  "stream-browserify": "3.0.0",
69
69
  "tsd": "0.32.0",
70
70
  "typescript": "5.8.3",
package/types/index.d.ts CHANGED
@@ -206,7 +206,7 @@ declare module 'mongoose' {
206
206
  [k: string]: string;
207
207
  }
208
208
 
209
- export interface ToObjectOptions<THydratedDocumentType = HydratedDocument<unknown>> {
209
+ export interface ToObjectOptions<RawDocType = unknown, THydratedDocumentType = HydratedDocument<RawDocType>> {
210
210
  /** if `options.virtuals = true`, you can set `options.aliases = false` to skip applying aliases. This option is a no-op if `options.virtuals = false`. */
211
211
  aliases?: boolean;
212
212
  /** if true, replace any conventionally populated paths with the original id in the output. Has no affect on virtual populated paths. */
@@ -224,7 +224,7 @@ declare module 'mongoose' {
224
224
  /** if set, mongoose will call this function to allow you to transform the returned object */
225
225
  transform?: boolean | ((
226
226
  doc: THydratedDocumentType,
227
- ret: Record<string, any>,
227
+ ret: Default__v<Require_id<RawDocType>>,
228
228
  options: ToObjectOptions<THydratedDocumentType>
229
229
  ) => any);
230
230
  /** If true, omits fields that are excluded in this document's projection. Unless you specified a projection, this will omit any field that has `select: false` in the schema. */
@@ -505,7 +505,7 @@ declare module 'mongoose' {
505
505
  requiredPaths(invalidate?: boolean): string[];
506
506
 
507
507
  /** Sets a schema option. */
508
- set<K extends keyof SchemaOptions>(key: K, value: SchemaOptions[K], _tags?: any): this;
508
+ set<K extends keyof SchemaOptions>(key: K, value: SchemaOptions<DocType>[K], _tags?: any): this;
509
509
 
510
510
  /** Adds static "class" methods to Models compiled from this schema. */
511
511
  static<K extends keyof TStaticMethods>(name: K, fn: TStaticMethods[K]): this;
@@ -519,7 +519,7 @@ declare module 'mongoose' {
519
519
  toJSONSchema(options?: { useBsonType?: boolean }): Record<string, any>;
520
520
 
521
521
  /** Creates a virtual type with the given name. */
522
- virtual<T = HydratedDocument<DocType, TVirtuals & TInstanceMethods, TQueryHelpers>>(
522
+ virtual<T = THydratedDocumentType>(
523
523
  name: keyof TVirtuals | string,
524
524
  options?: VirtualTypeOptions<T, DocType>
525
525
  ): VirtualType<T>;
@@ -146,14 +146,14 @@ declare module 'mongoose' {
146
146
  */
147
147
  strictQuery?: boolean | 'throw';
148
148
  /** Exactly the same as the toObject option but only applies when the document's toJSON method is called. */
149
- toJSON?: ToObjectOptions<THydratedDocumentType>;
149
+ toJSON?: ToObjectOptions<DocType, THydratedDocumentType>;
150
150
  /**
151
151
  * Documents have a toObject method which converts the mongoose document into a plain JavaScript object.
152
152
  * This method accepts a few options. Instead of applying these options on a per-document basis, we may
153
153
  * declare the options at the schema level and have them applied to all of the schema's documents by
154
154
  * default.
155
155
  */
156
- toObject?: ToObjectOptions<THydratedDocumentType>;
156
+ toObject?: ToObjectOptions<DocType, THydratedDocumentType>;
157
157
  /**
158
158
  * By default, if you have an object with key 'type' in your schema, mongoose will interpret it as a
159
159
  * type declaration. However, for applications like geoJSON, the 'type' property is important. If you want to
@@ -196,13 +196,13 @@ declare module 'mongoose' {
196
196
  /** Attaches a validator that succeeds if the data string matches the given regular expression, and fails otherwise. */
197
197
  match?: RegExp | [RegExp, string] | readonly [RegExp, string];
198
198
 
199
- /** If truthy, Mongoose will add a custom setter that lowercases this string using JavaScript's built-in `String#toLowerCase()`. */
199
+ /** If truthy, Mongoose will add a [custom setter](https://mongoosejs.com/docs/api/schematype.html#SchemaType.prototype.set()) that lowercases this string using JavaScript's built-in `String#toLowerCase()`. */
200
200
  lowercase?: boolean;
201
201
 
202
- /** If truthy, Mongoose will add a custom setter that removes leading and trailing whitespace using JavaScript's built-in `String#trim()`. */
202
+ /** If truthy, Mongoose will add a [custom setter](https://mongoosejs.com/docs/api/schematype.html#SchemaType.prototype.set()) that removes leading and trailing whitespace using JavaScript's built-in `String#trim()`. */
203
203
  trim?: boolean;
204
204
 
205
- /** If truthy, Mongoose will add a custom setter that uppercases this string using JavaScript's built-in `String#toUpperCase()`. */
205
+ /** If truthy, Mongoose will add a [custom setter](https://mongoosejs.com/docs/api/schematype.html#SchemaType.prototype.set()) that uppercases this string using JavaScript's built-in `String#toUpperCase()`. */
206
206
  uppercase?: boolean;
207
207
 
208
208
  /** If set, Mongoose will add a custom validator that ensures the given string's `length` is at least the given number. */