前言
MongoDB 是 schema free 的,也就是说不同的 document 可以允许有不同的结构,最大程度降低了关系型数据库中的 DDL 对数据库的影响。 尽管 MongoDB 中的模式十分灵活,我们依旧希望 document 中的字段类型统一,理由如下:
- 不一致的字段类型可能会带来数据统计误差。
- 随着应用不断升级迭代,不一致的字段可能会让维护,优化变的复杂。
基于如上原因,MongoDB 在 3.2 版本中发布了 Document Validation 特性,支持在创建集合时指定 Validator 来对数据进行相关约束。在 3.6 版本中,MongoDB 引入了 JSON Schema,提供了通用的词法规则来实现对字段类型,数值等进行约束。
如何使用
如下的示例展示了使用 JSON Schema 对 集合进行约束
db.createCollection("userinfo", {
validator: {
$jsonSchema: {
bsonType: "object",
required: [ "name", "birthday", "interests" ],
properties: {
name: {
bsonType: "string",
description: "must be a string and is required"
},
birthday: {
bsonType: "int",
minimum: 1860,
maximum: 3017,
description: "must be an integer in [ 1860, 3017 ] and is required"
},
interests: {
enum: [ "Math", "English", "games", "History", null ],
description: "can only be one of the enum values and is required"
}
}
}
},
validationAction:"error"
})
```
`
上述内容的说明如下:
1. $jsonSchema 包含了元数据的结构体,其中定义了 name, birthday, interests 三个字段为必选项
2. properties 部分定义了 相关字段的类型,其中我们定义了 birthday 必须要在 1860 ~ 3017 之间
3. validationAction = error 表示如果数据不符合规则时直接报错。
尝试向集合中写入不符合要求的文档会出现 **Document failed validation** 报错:
````undefined
rs-mongo-replica-cn01f91c9e400b64:PRIMARY> db.userinfo.insert({name:"rudonx",birthday:NumberInt(1998),interests:'CS'});
WriteResult({
"nInserted" : 0,
"writeError" : {
"code" : 121,
"errmsg" : "Document failed validation"
}
})
```
`
同时对于已经存在的集合,可以通过方式添加约束:
````undefined
db.runCommand( {
collMod: "contacts",
validator: { $jsonSchema: {
bsonType: "object",
required: [ "phone", "name" ],
properties: {
phone: {
bsonType: "string",
description: "must be a string and is required"
},
name: {
bsonType: "string",
description: "must be a string and is required"
}
}
} },
validationLevel: "moderate"
} )
```
`
说明如下:
1. collMod:指定需要添加约束的集合名称
2. validationLevel 有 strict 和 moderate 两种级别可选。关于参数的更对解释,您可以参考文档[1]。
需要注意的是,不论是新增还是修改 validator,都不会更改现有数据,也就是说集合中可能依然存在违反约束的旧数据。
同时,由于在写入数据时多了校验的操作,在性能上会有性能损失。
# 使用限制
1. 不可以在 admin,local,config 数据库中使用 validator
2. 不能对 system.* 这类 collections 进行 validation设置
# 参考文档
[1] [https://www.mongodb.com/docs/manual/core/schema-validation/](https://www.mongodb.com/docs/manual/core/schema-validation/)