I am using mongodb 3.6 and have below validator for the students
collection:
rs1:PRIMARY> db.getCollectionInfos({name: 'students'})
[
{
"name" : "students",
"type" : "collection",
"options" : {
"validator" : {
"$jsonSchema" : {
"properties" : {
"name" : {
"bsonType" : "string",
"description" : "name"
},
"age" : {
"bsonType" : "int",
"minimum" : 10,
"maximum" : 30
}
},
"required" : [
"name",
"age"
],
"bsonType" : "object"
}
},
"validationLevel" : "strict",
"validationAction" : "error"
},
"info" : {
"readOnly" : false,
"uuid" : BinData(4,"111r7z+rQpGoebZ1jAHO4g==")
},
"idIndex" : {
"v" : 2,
"key" : {
"_id" : 1
},
"name" : "_id_",
"ns" : "test.students"
}
}
]
it requires two properties name
and age
. Name must be a string and age must be between 10 and 30. But why does below insert fail?
rs1:PRIMARY> db.students.insert({age: 11, name: 'Mike'})
WriteResult({
"nInserted" : 0,
"writeError" : {
"code" : 121,
"errmsg" : "Document failed validation"
}
})
Best Answer
As I am able to see you are getting the insert
writeError
withError code : 121
like thatAs per MongoDB blog documentation of
@Jai Hirsch
here for MongoDB document validation. Sometimes you want completely free form documents and sometimes you don’t. In the3.2 release of MongoDB
the idea ofdocument validation
was introduced. One area I have encountered problems in the past is with dates being inserted using different data types.Example: (command line notation used for brevity) The first team was using numeric dates:
The second team was using string format:
The third team was using ISO dates:
The communication issues that lead to this problem is a story for another time, but needless to say a fair amount of data cleanup was required to fix the issue as the primary application that read the data was expecting an ISO date. The code issue was solved by using a shared library that defined the database mapping object. Now let’s take a look at how document validation could be used to solve this problem.
We will create a collection with the following command:
With the collection created with the validator one can now only insert using the new Date() format:
The numeric and string inserts will give the following error:
likewise almost every developer new to
MongoDB
will make this "mistake" on the command line like:One would think that they have inserted a document containing the integer number
two
into the collection, when in fact the document now contains a floating-point value.I can attest to the pain this can cause (especially if you are using a strongly typed language such as
JAVA
).We can use the validator to safeguard against this:
The preceding insert will now give us the
121 error code
and you need to use theNumberInt constructor
: