-
-
Notifications
You must be signed in to change notification settings - Fork 4k
Description
Prerequisites
- I have written a descriptive issue title
- I have searched existing issues to ensure the bug has not already been reported
Mongoose version
9.1.3
Node.js version
24.13.0
MongoDB server version
7.0.28
Typescript version (if applicable)
No response
Description
When a discriminator schema is created using Base.discriminator() and both base and discriminator schemas share the same specs structure containing nested schemas, the discriminator's _indexes array gets populated with duplicate copies of the base schema's indexes. The number of duplicates equals the number of nested schema paths in the specs.
Steps to Reproduce
In this example: 3 base indexes × 3 nested schema paths = 9 indexes in the discriminator schema.
const mongoose = require('mongoose');
// Shared nested schema
const NESTED_SCHEMA = new mongoose.Schema({
itemId: mongoose.Schema.Types.ObjectId
}, { _id: false });
// Specs used by BOTH base and discriminator
const GENERIC_SPECS = {
parentRef: { type: mongoose.Schema.Types.ObjectId },
createdAt: Date,
externalId: String,
source: NESTED_SCHEMA,
reference: NESTED_SCHEMA,
comments: [{ value: String }] // 3 nested schema paths total
};
function createSchema(collection, specs) {
return new mongoose.Schema(specs, { collection });
}
async function main() {
await mongoose.connect('mongodb://localhost:27017/test');
const baseSchema = createSchema('Item', GENERIC_SPECS);
baseSchema.index({ parentRef: 1, createdAt: -1 });
baseSchema.index({ externalId: 1, parentRef: 1 });
baseSchema.index({ 'source.itemId': 1, parentRef: 1 });
const Base = mongoose.model('Item', baseSchema);
const discSchema = createSchema('Item.typeA', GENERIC_SPECS);
const Child = Base.discriminator('Item.typeA', discSchema, { clone: false });
console.log('Base _indexes:', Base.schema._indexes.length); // 3
console.log('Discriminator _indexes:', discSchema._indexes.length); // 9 (expected: 3)
// Indexes are tripled: [1,2,3, 1,2,3, 1,2,3]
discSchema._indexes.forEach((idx, i) => console.log(i, JSON.stringify(idx[0])));
// This fails because diffIndexes returns 9 duplicate indexes
const { toCreate } = await Child.diffIndexes({ indexOptionsToCreate: true });
await Child.createIndexes({ toCreate });
await mongoose.disconnect();
}
main();Stack Trace
MongoServerError: An existing index has the same name as the requested index. When index names are not specified, they are auto generated and can cause conflicts. Please refer to our documentation. Requested index: { v: 2, key: { parentRef: 1, createdAt: -1 }, name: "parentRef_1_createdAt_-1", partialFilterExpression: { __t: "Item.typeA" } }, existing index: { v: 2, key: { parentRef: 1, createdAt: -1 }, name: "parentRef_1_createdAt_-1" }
at Connection.sendCommand (node_modules/mongodb/lib/cmap/connection.js:320:27)
at process.processTicksAndRejections (node:internal/process/task_queues:103:5)
at async Connection.command (node_modules/mongodb/lib/cmap/connection.js:344:26)
at async Server.command (node_modules/mongodb/lib/sdam/server.js:208:29)
at async tryOperation (node_modules/mongodb/lib/operations/execute_operation.js:215:32)
at async executeOperation (node_modules/mongodb/lib/operations/execute_operation.js:80:16)
at async Collection.createIndex (node_modules/mongodb/lib/collection.js:373:25)
Expected vs Actual
- Expected:
discSchema._indexes.length= 3 - Actual:
discSchema._indexes.length= 9 (multiplied by number of nested schema paths)
Expected Behavior
When creating a discriminator model, the discriminator schema's _indexes array should contain the same number of indexes as the base schema (3 indexes). The diffIndexes() method should return only the indexes that need to be created with discriminator-specific partialFilterExpression, without duplicates.