Declaring defaults in your schema - 图1mongoose

Declaring defaults in your schema - 图2mongoose

[

Declaring defaults in your schema ](#declaring-defaults-in-your-schema)

Your schemas can define default values for certain paths. If you create a new document without that path set, the default will kick in.

  1. var schema = new Schema({
  2. name: String,
  3. role: { type: String, default: 'guitarist' }
  4. });
  5. var Person = db.model('Person', schema);
  6. var axl = new Person({ name: 'Axl Rose', role: 'singer' });
  7. assert.equal(axl.role, 'singer');
  8. var slash = new Person({ name: 'Slash' });
  9. assert.equal(slash.role, 'guitarist');
  10. var izzy = new Person({ name: 'Izzy', role: undefined });
  11. assert.equal(izzy.role, 'guitarist');
  12. Person.create(axl, slash, function(error) {
  13. assert.ifError(error);
  14. Person.find({ role: 'guitarist' }, function(error, docs) {
  15. assert.ifError(error);
  16. assert.equal(docs.length, 1);
  17. assert.equal(docs[0].name, 'Slash');
  18. });
  19. });

[

Default functions ](#default-functions)

You can also set the default schema option to a function. Mongoose will execute that function and use the return value as the default.

  1. var schema = new Schema({
  2. title: String,
  3. date: {
  4. type: Date,
  5. // `Date.now()` returns the current unix timestamp as a number
  6. default: Date.now
  7. }
  8. });
  9. var BlogPost = db.model('BlogPost', schema);
  10. var post = new BlogPost({title: '5 Best Arnold Schwarzenegger Movies'});
  11. // The post has a default Date set to now
  12. assert.ok(post.date.getTime() >= Date.now() - 1000);
  13. assert.ok(post.date.getTime() <= Date.now());

[

The setDefaultsOnInsert option ](#the-setdefaultsoninsert-option)

By default, mongoose only applies defaults when you create a new document. It will not set defaults if you use update() and findOneAndUpdate(). However, mongoose 4.x lets you opt-in to this behavior using the setDefaultsOnInsert option.

Important

The setDefaultsOnInsert option relies on the MongoDB $setOnInsert operator. The $setOnInsert operator was introduced in MongoDB 2.4. If you're using MongoDB server < 2.4.0, do not use setDefaultsOnInsert.

  1. var schema = new Schema({
  2. title: String,
  3. genre: {type: String, default: 'Action'}
  4. });
  5. var Movie = db.model('Movie', schema);
  6. var query = {};
  7. var update = {title: 'The Terminator'};
  8. var options = {
  9. // Return the document after updates are applied
  10. new: true,
  11. // Create a document if one isn't found. Required
  12. // for `setDefaultsOnInsert`
  13. upsert: true,
  14. setDefaultsOnInsert: true
  15. };
  16. Movie.
  17. findOneAndUpdate(query, update, options, function (error, doc) {
  18. assert.ifError(error);
  19. assert.equal(doc.title, 'The Terminator');
  20. assert.equal(doc.genre, 'Action');
  21. });

[

Default functions and this ](#default-functions-and-this)

Unless it is running on a query with setDefaultsOnInsert, a default function's this refers to the document.

  1. const schema = new Schema({
  2. title: String,
  3. released: Boolean,
  4. releaseDate: {
  5. type: Date,
  6. default: function() {
  7. if (this.released) {
  8. return Date.now();
  9. }
  10. return null;
  11. }
  12. }
  13. });
  14. const Movie = db.model('Movie', schema);
  15. const movie1 = new Movie({ title: 'The Terminator', released: true });
  16. // The post has a default Date set to now
  17. assert.ok(movie1.releaseDate.getTime() >= Date.now() - 1000);
  18. assert.ok(movie1.releaseDate.getTime() <= Date.now());
  19. const movie2 = new Movie({ title: 'The Legend of Conan', released: false });
  20. // Since `released` is false, the default function will return null
  21. assert.strictEqual(movie2.releaseDate, null);