JSON SCHEMA笔记(一)概念与关键字(json schema用途)
在实际业务中,后端存在某些参数极为复杂的接口,这时候可以把所有的参数都用JSON接收。但是,JSON校验就成了一个棘手的问题,手写校验复杂且繁琐。
任何数据都可能有两个验证阶段:
架构级别
:json结构可以通过JSON Schema验证语义级别
:json的语义需要转换成实际的业务实体来进行校验
而JSON Schema 是用于验证 JSON 数据结构的强大工具,通过它可以快速验证复杂的JSON结构。JSON Schema本身是用JSON编写的,用于“描述其他数据结构”的声明性格式。
一、基本
1. 相关概念
JSON实例:表示数据模型解释文档,根据JSON Schema解释的 JSON 值称为“实例”;用JSON的话说就是
value格式、取值相同
JSON实例相等:当且仅当两个 JSON 实例属于相同类型且具有相同值时,才称它们相等;
可以将 JSON Schema 与 JSON Schema 数据模型的超集一起使用,其中实例可能在六种 JSON 数据类型中的任何一种之外。
JSON Schema:JSON Schema 文档,或简称为 schema,是定义JSON元数据的JSON 文档;JSON元数据通过关键字(keyword)定义了Json数据需要满足的规范,规范包括了
成员
、结构
、类型
、约束
等
注:对象必须具有相同数量的成员,对象中的属性是无序的,无法定义多个具有相同KEY的属性,而仅仅是格式上的差异(缩进、放置逗号、尾随零)无关紧要。
注2:由于一个对象不能有两个具有相同键的属性,因此尝试在单个对象中定义具有相同键的两个属性的 JSON 文档的行为是undefined的。
注3:模式本身可以被解释为一个实例,但应该总是被赋予媒体类型“application/schema+json”而不是“application/schema-instance+json”。“application/schema+json”媒体类型被定义为提供“application/schema-instance+json”提供的片段标识符语法和语义的超集。
2. JSON Schema Documents的组成
JSON关键字:应用于实例的对象属性称为关键字或模式关键字
identifiers(身份标志):URI
assertions(断言):应用于实例,判断状态,产生布尔类型结果
annotations(注释)
applicators:将一个或多个子模式应用于实例中的特定位置,并组合或修改它们的结果
reserved locations:不直接影响结果,但为特定目的预留位置以确保互操作性
Boolean JSON Schemas:用于阐明模式作者的意图并促进模式处理优化
true:表示空模式{}
false:表示模式{ "not": {} }
Schema Vocabularies:模式词汇表,或简称为词汇表,是一组关键字、语法和语义;
定义词汇表通常是为了特定目的组织起来的;
可以定义词汇表是必需或可选的
Meta-Schemas(元模式):用于描述模式的模式,用于验证JSON模式并指定使用的词汇表
Root Schema and Subschemas and Resources(根模式、子模式和资源)
例如:
{ "title": "root", // 文档的根模式 "items": { // 包含子模式 "title": "array item" } }复制代码
二、关键字
Json Schema中的常用的关键字可以分为类型关键字、通用关键字以及schema组合
1. 类型关键字
string
相关属性:
minLength
maxLength
pattern
format
"regex"
"json-pointer"
"relative-json-pointer"
"uri-template"
"uri"
"uri-reference"
"iri"
"iri-reference"
"ipv4"
"ipv6"
"hostname"
"idn-hostname"
"email"
"idn-email"
"date-time":例如 2018-11-13T20:20:39+00:00
"time":例如 20:20:39+00:00
"date":例如 2018-11-13
Dates and times(日期和时间)
Email addresses(邮箱地址)
Hostnames(host)
IP Addresses(IP地址)
Resource identifiers(绝对或相对资源路径)
URI template
JSON Pointer(json schema 快捷链接)
Regular Expressions(正则)
number
multipleOf 将数字限定为该属性的倍数,可以为任何整数
Range(设置范围):
minimum
、exclusiveMinimum
、maximum
、exclusiveMaximum
x ≥ minimum
x > exclusiveMinimum
x ≤ maximum
x < exclusiveMaximum
例如:
{ "type": "number", "minimum": 0, "maximum": 100, "exclusiveMaximum": true }复制代码
integer (只能表示整数)
object(JSON映射类型)
properties(属性键值对)
key 属性名称
value 对象
patternProperties (如果属性名匹配模式,属性值必须通过特定schema的验证)
additionalProperties 默认为true,设置为false表示不允许额外的属性
required 定义必须的字段
propertyNames 验证属性名
minProperties 限制至少有几个属性
maxProperties 限制最多有几个属性
例如:
{ "type": "object", "properties": { "number": { "type": "number" }, "street_name": { "type": "string" }, "street_type": { "enum": ["Street", "Avenue", "Boulevard"] } } } { "type": "object", "patternProperties": { "^S_": { "type": "string" }, "^I_": { "type": "integer" } } } // 允许类型为string的额外属性 { "type": "object", "properties": { "number": { "type": "number" }, "street_name": { "type": "string" }, "street_type": { "enum": ["Street", "Avenue", "Boulevard"] } }, "additionalProperties": { "type": "string" } } { "type": "object", "propertyNames": { "pattern": "^[A-Za-z_][A-Za-z0-9_]*$" } } //ERR { "001 invalid": "value" }复制代码
array
items
列表:存放同种类型数据
元组:存放不同类型数据
additionalItems:默认为true,允许额外类型的项;如果不是元组,则忽略该属性
contains:该属性表示包含某种类型即可
minItems
maxItems
uniqueItems 用于保证item唯一
例如:
// 列表 { "type": "array", "items": { "type": "number" } } // 元组 { "type": "array", "items": [ { "type": "number" }, { "type": "string" }, { "enum": ["Street", "Avenue", "Boulevard"] }, { "enum": ["NW", "NE", "SW", "SE"] } ] }复制代码
boolean
布尔类型只匹配两个特殊值:true和false。请注意,架构不接受判定其余值为true或false,例如1和0的值。
null
当架构指定空缺类型时,它只有一个可接受的值:null
在json中,null不等同于不存在的东西
2. 通用关键字
JSON Schema包含一些关键字不用于验证,而是用于描述模式;编写JSON Schema的开发人员不一定需要这些“注释”关键字,但鼓励使用这些字段使架构能“自我记录”。
title 标题
description 描述
default 表示默认值
examples 示例JSON
readOnly 表示不应修改值
writeOnly 表示可以设置值
$comment 表示注释
enum 表示枚举
const 常量、限制为单个值
{ "title": "Match anything", "description": "This is a schema that matches anything.", "default": "Default value", "examples": [ "Anything", 4035 ], "readOnly": true, "writeOnly": false } { "enum": ["red", "amber", "green"] }复制代码
3. Schema 组合
allOf(AND):所有条件都对子模式有效、非空数组,每一项都是有效的JSON Schema
anyOf(OR):至少有一个条件对子模式有效、非空数组
oneOf(XOR):有且只有一个条件对子模式有效、非空数组
not(NOT):所有的都不匹配则表示成功
{ "allOf": [ { "type": "string" }, { "maxLength": 5 } ] } "short" TRUE "too long" FALSE { "anyOf": [ { "type": "string", "maxLength": 5 }, { "type": "number", "minimum": 0 } ] } "short" TRUE "too long" FALSE 12 TRUE -5 FALSE { "oneOf": [ { "type": "number", "multipleOf": 5 }, { "type": "number", "multipleOf": 3 } ] } 10 TRUE 9 TRUE 2 FALSE 15 FALSE { "not": { "type": "string" } } 42 TRUE { "key": "value" } TRUE "I am a string" FALSE复制代码
注:allOf不允许使用additionalProperties
分解模式:子模式的公共部分支持分解,以下的两个模式等效
{ "oneOf": [ { "type": "number", "multipleOf": 5 }, { "type": "number", "multipleOf": 3 } ] } { "type": "number", "oneOf": [ { "multipleOf": 5 }, { "multipleOf": 3 } ] }
作者:此间码农
链接:https://juejin.cn/post/7028757292552028167