Schema Types
SchemaType
s take care of validation, casting, defaults, and other general options in our models. We can specify our types one of two ways:
// directly without options
var Person = new Schema({
title : String
});
// or with options
var Person = new Schema({
title : { type: String, lowercase: true }
});
In the example above we specified the lowercase
option for strings which will lowercase the string whenever it is set. Options are functions that are called on each SchemaType. Each SchemaType
has its own set of custom options.
Available Schema Types
String
lowercase
: {Boolean}Creates a setter which calls
.toLowerCase()
on the valueuppercase
: {Boolean}Creates a setter which calls
.toUpperCase()
on the valuetrim
: {Boolean}Creates a setter which calls
.trim()
on the valuematch
: {RegExp}Creates a RegExp based validator. The value being set is
.test()
ed against the RegExp. If it does not pass, validation will fail.enum
: {Array}Creates an enum validator. If the value being set is not in this array, validation will fail.
Number
min
: {Number}Creates a validator which checks that the value being set is not less than the value specified.
max
: {Number}Creates a validator which checks that the value being set is not greater than the value specified.
Date
- no custom options
Boolean
- no custom options
Buffer (v2.x only)
- no custom options
ObjectId
To specify a type of ObjectId
, use Schema.ObjectId
in your declaration.
var mongoose = require('mongoose');
var Schema = mongoose.Schema;
var Car = new Schema({ driver: Schema.ObjectId })
- no custom options
Mixed
An "anything goes" SchemaType
, its flexibility comes at a trade-off of it being harder to maintain. Mixed
is available either through Schema.Types.Mixed
or by passing an empty object literal. The following are equivalent:
var Any = new Schema({ any: {} });
var Any = new Schema({ any: Schema.Types.Mixed });
Since it is a schema-less type, you can change the value to anything else you like, but Mongoose loses the ability to auto detect/save those changes. To "tell" Mongoose that the value of a Mixed
type has changed, call the .markModified(path)
method of the document passing the path to the Mixed
type you just changed.
person.anything = { x: [3, 4, { y: "changed" }] };
person.markModified('anything');
person.save(); // anything will now get saved
- no custom options
Array
Creates an array of SchemaTypes
or Embedded Documents.
var ToySchema = new Schema({ name: String });
var ToyBox = new Schema({
toys: [ToySchema]
, buffers: [Buffer]
, string: [String]
, numbers: [Number]
... etc
});
Note: specifying an empty array is equivalent to [Mixed]
. The following all create arrays of Mixed
:
var Empty1 = new Schema({ any: [] });
var Empty2 = new Schema({ any: Array });
var Empty3 = new Schema({ any: [Schema.Types.Mixed] });
var Empty4 = new Schema({ any: [{}] });
- no custom options
Additional options
Besides the options listed above, all SchemaTypes share the following additional options.
default
: {Function|value} - Determines the default value for the path. All values are casted. If using a function, the value it returns will be casted as the default value.required
: {Boolean} - If true, creates a validation rule requiring this path be set before saving occurs.select
: {Boolean} - Specifies default path selection behavior. In other words, you can specify if this path should be included or excluded from query results by default.// Excluding `bio` from query results by default var Person = new Schema({ bio: { type: String, select: false }}) var P = db.model('Person', Person); P.findOne(function (err, p) { console.log(p.bio) // undefined }); // Including `name` in query results by default var Person = new Schema({ name: { type: String, select: true } , age: Number }) var P = db.model('Person', Person); P.findOne().select('age').exec(function (err, p) { console.log(p.isSelected('age')) // true console.log(p.isSelected('name')) // true }); // can also be overridden on a query by query basis var Person = new Schema({ bio: { type: String, select: false }}) var P = db.model('Person', Person); P.findOne().select('bio').exec(callback); // bio will be selected
get
: {Function} - Adds a getter for this path. See the getters / setters docs for more detail.set
: {Function} - Adds a setter for this path. See the getters / setters docs for more detail.index
: {Boolean|Object} - Tells Mongoose to ensure an index is created for this path. An object can be passed as well.var Person = new Schema({ name: { type: String, index: true }}) var name = { type: String, index: { unique: true }} var Person = new Schema({ name: name })
Note: if the index already exists on the db, it will not be replaced.
unique
: {Boolean} - Tells Mongoose to ensure a unique index is created for this path. The following are equivalent:var Person = new Schema({ name: { type: String, unique: true }}) var name = { type: String, index: { unique: true }} var Person = new Schema({ name: name })
Note: if the index already exists on the db, it will not be replaced.
sparse
: {Boolean} - Tells Mongoose to ensure a sparse index is created for this path. The following are equivalent:var Person = new Schema({ name: { type: String, sparse: true }}) var name = { type: String, index: { sparse: true }} var Person = new Schema({ name: name })
Note: if the index already exists on the db, it will not be replaced.
validate
: {Function|RegExp|Array} - Creates a validator for this path.// passing a function function hasNumber (v) { return v.length && /\d/.test(v); } var street = { type: String, validate: hasNumber } var Person = new Schema({ street: street }); // passing a RegExp var street = { type: String, validate: /\d/ } var Person = new Schema({ street: street }); // passing an array var street = { type: String , validate: [hasNumber, 'street number required'] } var Person = new Schema({ street: street }) // or var street = { type: String , validate: [/\d/, 'street number required'] } var Person = new Schema({ street: street });
For more detail about validation including async validation, see the validation page.
Alternate options definition
Instead of defining options when instanciating your Schema
we can also access keys through the path
function and add options there:
Person.path('age').max(400);
Person.path('meta.birth').set(function (v) {
// this is a setter
});
Person.path('title').validate(function (v) {
return v.length > 50;
});