与Mongoose进行多对多的映射

我的devise中有FlashcardSchemas和PackageSchemas。 一个flashcard可以属于不同的包,一个包可以包含不同的flashcard。

下面你可以看到我的mongoose模式定义的精简版本:

// package-schema.js var Schema = mongoose.Schema, ObjectId = Schema.ObjectId; var PackageSchema = new Schema({ id : ObjectId, title : { type: String, required: true }, flashcards : [ FlashcardSchema ] }); var exports = module.exports = mongoose.model('Package', PackageSchema); // flashcard-schema.js var Schema = mongoose.Schema, ObjectId = Schema.ObjectId; var FlashcardSchema = new Schema({ id : ObjectId, type : { type: String, default: '' }, story : { type: String, default: '' }, packages : [ PackageSchema ] }); var exports = module.exports = mongoose.model('Flashcard', FlashcardSchema); 

从上面的注释中可以看出,这两个模式定义属于单独的文件并相互引用。

我收到一个exception,说明PackageSchema没有按预期定义。 我如何能与mongoose绘制多对多的关系?

你正在做的是正确的,但是问题是你必须将PackageSchema包含在flashcard-schema.js中,反之亦然。 否则,这些文件不知道你在引用什么

 var Schema = mongoose.Schema, ObjectId = Schema.ObjectId; PackageSchema = require('./path/to/package-schema.js') var FlashcardSchema = new Schema({ id : ObjectId, type : { type: String, default: '' }, story : { type: String, default: '' }, packages : [ PackageSchema ] }); 

我是node,mongoDB和mongoose的新手,但我认为正确的做法是:

 var PackageSchema = new Schema({ id: ObjectId, title: { type: String, required: true }, flashcards: [ {type : mongoose.Schema.ObjectId, ref : 'Flashcard'} ] }); var FlashcardSchema = new Schema({ id: ObjectId, type: { type: String, default: '' }, story: { type: String, default: '' }, packages: [ {type : mongoose.Schema.ObjectId, ref : 'Package'} ] }); 

这样,您只存储对象引用而不是embedded对象。

你正在考虑像关系数据存储一样。 如果这就是你想要的,使用MySQL(或其他RDBMS)

否则,是的,可以使用第三个模式,但不要忘记,它仍然只是每个对象的ID(没有连接,记住),所以你仍然必须在单独的查询中检索每个其他项目。

您可以使用Schema.add()方法来避免前向引用问题。

这个(未经testing的)解决scheme将模式放在一个.js文件中

车型/ index.js

 var Schema = mongoose.Schema, ObjectId = Schema.ObjectId; // avoid forward referencing var PackageSchema = new Schema(); var FlashcardSchema = new Schema(); PackageSchema.add({ id : ObjectId, title : { type: String, required: true }, flashcards : [ FlashcardSchema ] }); FlashcardSchema.add({ id : ObjectId, type : { type: String, default: '' }, story : { type: String, default: '' }, packages : [ PackageSchema ] }); // Exports both types module.exports = { Package: mongoose.model('Package', PackageSchema), Flashcard: mongoose.model('Flashcard', FlashcardSchema) }; 
 https://www.npmjs.com/package/mongoose-relationship ##Many-To-Many with Multiple paths var mongoose = require("mongoose"), Schema = mongoose.Schema, relationship = require("mongoose-relationship"); var ParentSchema = new Schema({ children:[{ type:Schema.ObjectId, ref:"Child" }] }); var Parent = mongoose.models("Parent", ParentSchema); var OtherParentSchema = new Schema({ children:[{ type:Schema.ObjectId, ref:"Child" }] }); var OtherParent = mongoose.models("OtherParent", OtherParentSchema); var ChildSchema = new Schema({ parents: [{ type:Schema.ObjectId, ref:"Parent", childPath:"children" }] otherParents: [{ type:Schema.ObjectId, ref:"OtherParent", childPath:"children" }] }); ChildSchema.plugin(relationship, { relationshipPathName:['parents', 'otherParents'] }); var Child = mongoose.models("Child", ChildSchema) var parent = new Parent({}); parent.save(); var otherParent = new OtherParent({}); otherParent.save(); var child = new Child({}); child.parents.push(parent); child.otherParents.push(otherParent); child.save() //both parent and otherParent children property will now contain the child's id child.remove()