Embedded document without Array?

2019-01-23 12:56发布

问题:

I understand how to embed documents in Mongoose, and they seem fairly straightforward if storing as arrays, for which the use case is fairly obvious:

var CommentSchema = new Mongoose.Schema({...});
var BlogPostSchema = new Mongoose.Schema({
    comments : [CommentSchema],
});

But, what I don't see how to do after looking over the documentation forward and backward, is how to store a single sub-document that doesn't need or want to be in an Array.

var UserSchema = new Mongoose.Schema({...});
var BlogPostSchema = new Mongoose.Schema({
    author: ??? // 'UserSchema' and UserSchema do not work here. 
});

Is there any way to make this work? I don't want to just store the ObjectId, but rather, store a complete copy of the User record, but don't need or want an array.

回答1:

You cannot embed schemas in this way, with the reasoning that those child docs would be confused with full documents, see this bug thread, where it is stated:

the reason we haven't added this support in the past is b/c this leaves us wondering if all pre-hooks will be executed the same way for the pseudo-child document as well as it implies that we can call save() on that child.

The answer here is to share not the schema, but just the definition.

var userdef = { name: String };
var UserSchema = new Schema(userdef);
var BlogPostSchema = new Schema({author: userdef});

This would result in a nested user object, without actually nesting the Schema.



回答2:

Just sharing information doesn't support validation bubbling. And you may need validation of UserSchema also.

Instead I recommend array length validation

author: {type:[UserSchema], validate: function (arr) { return arr.length == 1 }},


回答3:

UPDATE:

In case anyone comes across this now, as of Mongoose 4.2.0 single embedded subdocuments exist! :)

http://mongoosejs.com/docs/subdocs.html#single-embedded