Mongoose: Unable to set default document for singleNestedDocument

Created on 7 Jun 2020  路  3Comments  路  Source: Automattic/mongoose

Do you want to request a feature or report a bug?
Bug
What is the current behavior?
Creating single nested schema with default values and setting default schema on the parent schema throws error MongooseError: Cannot set default value of pathtestSchemato a mongoose Schema instance.
This was working for Mongoose 4.7.2

If the current behavior is a bug, please provide the steps to reproduce.

var testSchema = new mongoose.Schema({
    some_key: {
        some_nested_key: {
            type: String,
            required: true,
            default: "default_value"
        }
    }
}, {
    _id: false
});

var parentSchema = new mongoose.Schema(
        test: {
            type: testSchema,
            required: true,
            default: testSchema
        }
);

What is the expected behavior?

Creating a new parentSchema with undefined testSchema should create a default testSchema with its default values that is set.

What are the versions of Node.js, Mongoose and MongoDB you are using? Note that "latest" is not a version.
Node: 8.11.0
Mongoose: 5.9.18
MongoDB: 3.6.17

help

Most helpful comment

Setting default: testSchema is a risky antipattern, and using it reflects a concerning lack of understanding Mongoose fundamentals. default: testSchema means you want test to default to a Mongoose schema instance. So, for example, if testSchema = new Schema({ tree: Mixed }), then test will default to an object with a complex property tree.

Replace with default: () => ({}) and you'll get exactly the behavior you described.

I'll ask SO to take the offending SO answer down.

All 3 comments

@litty-tt I ran into this issue as well. It looks like the latest version where setting a schema as a default works is version 5.9.9.

Looking at the diff between 5.9.9 and 5.9.10, and commit https://github.com/Automattic/mongoose/commit/32c5ed0945c89fd208e1f9d4439bdad3f216c16c in particular, it looks Mongoose intentionally disallows setting schemas as defaults now:

if (val != null && val.instanceOfSchema) {
    throw new MongooseError('Cannot set default value of path `' + this.path +
        '` to a mongoose Schema instance.');
}

This arose as a result of issue https://github.com/Automattic/mongoose/issues/8751, at the end of which @vkarpov15 suggests the following in https://github.com/Automattic/mongoose/issues/8751#issuecomment-618720048:

export const propertySchema = new mongoose.Schema({
  address: {
    type: addressSchema,
    default: () => ({}),
  },
});

Mongoose will take care of casting empty object against addressSchema.

Setting default: testSchema is a risky antipattern, and using it reflects a concerning lack of understanding Mongoose fundamentals. default: testSchema means you want test to default to a Mongoose schema instance. So, for example, if testSchema = new Schema({ tree: Mixed }), then test will default to an object with a complex property tree.

Replace with default: () => ({}) and you'll get exactly the behavior you described.

I'll ask SO to take the offending SO answer down.

That gave me the expected result. Thank you

Was this page helpful?
0 / 5 - 0 ratings