Type-specific keywords

特定类型的关键字

type 关键字是JSON模式的基础,它指定模式的数据类型,JSON Schema的核心定义以下基础类型

  • string
  • Numeric types
  • object
  • array
  • boolean
  • null

type关键字可以是字符串或者数组:

{ "type": "number" }
{ "type": [ "string", "number" ] }

string

string 类型用于文本字符串

length

minLengthmaxLength 关键字限制字符串长度。(必须是非负数)

{
    "type": "string",
    "minLength": 2,
    "maxLength": 3
}

正则表达式

pattern 关键字被用于限制一个字符串转换为特定的正则表达式

{
    "type": "string",
    "pattern": "^(\\([0-9]{3}\\))?[0-9]{3}-[0-9]{4}

quot;
}

Format

format 关键字允许对某些类型的字符串值通常用于基本的语义验证。这允许值受到约束,超出了JSON Schema中的其他工具(包括 正则表达式)所能提供的范围。

日期和时间

  • "date-time" :2018-11-13T20:20:39+00:00。
  • "time" :20:20:39+00:00
  • "date" :2018-11-13。

电子邮箱地址

  • "email" : 互联网电子邮箱
  • "idn-email" :Internet电子邮箱地址的国际化形式

主机名

  • "hostname":互联网主机名
  • "idn-hostname":国际化internet主机名

资源标识符

  • "uri"
  • "uri-reference"
  • "iri"
  • "iri-reference"

URI 模板

  • "uri-template"

JSON指针

  • "json-pointer"
  • "relative-json-pointer"

Numeric types

数值类型

integer

关键字 integer 类型用于整数

{
    "type": "integer"
}

在javascript中 `1.0` 也是被允许的,在python则否, 为避免这种情况,使用 `multipleOf` 关键字可在所有的模式上实现相同的行为

浮点数不允许

multipleOf 关键字

{
    "type": "number",
    "multipleOf": "1.0"
}

number

number 可用于任何数字类型,整数或者浮点数

{
    "type": "number"
}

multipleOf

multipleOf 关键字可以限制指定数字的倍数。

{
    "type": "number",
    "multipleOf": 10
}

不是10的倍数

范围

  • x >= minimum
  • x > exclusiveMinimum
  • x <= maximum
  • x < exclusiveMaximum
{
    "type": "number",
    "minimun": 0,
    "exclusiveMaximum": 100
}

小于 minimum 0

exclusiveMaximum 不包含 100

大于 exclusiveMaximum

草案4中 exclusiveMinimumexclusiveMaximum 都是布尔值

  • exclusiveMinimum 为true 不包含最小值
  • exclusiveMaximum 为true 不包含最大值
{
    "type": "number",
    "minimum": 0,
    "maximum": 100,
    "exclusiveMaximum": true
}
{
    "type": "number",
    "minimum": 0,
    "maximum": 100,
    "exclusiveMinimum": false
}

object

object key必须为字符串,仅表示从字符串到值得映射

{
    "type": "object"
}

properties

properties 关键字定义对象上的属性, properties 是个对象,每个键是属性的名称,值用于验证该属性的JSON模式

{
    "type": "object",
    "properties": {
        "age": {
            "type": "number"
        },
        "name": {
            "type": "string"
        }
    }
}

`age` 应为number

additionalProperties

additionalProperties 控制是否禁止 properties 列出的其他的属性, 默认为false。

{
    "type": "object",
    "properties": {
        "age": {
            "type": "number"
        },
        "name": {
            "type": "string"
        }
    },
    "additionalProperties": true
}

禁止添加其他字段

如果 additionalProperties 为对象,则验证未列出的其他属性都要满足 additionalProperties

{
    "type": "object",
    "properties": {
        "number": {
            "type": "number"
        },
        "name": {
            "type": "string"
        }
    },
    "additionalProperties": {
        "type": "string"
    }
}

新的属性应该为 `number`

Required Properties

required 关键字定义所需属性的列表,接手零到多个字符串的列表,且每个字符串唯一

{
    "type": "object",
    "properties": {
        "name": {
            "type": "string"
        },
        "age": {
            "type": "number"
        }
    },
    "required": ["name", "age"]
}

缺少必要属性 `age`

Property names

验证属性的名称

{
    "type": "object",
    "propertiesNames": {
        "pattern": "^[A-Za-z_][A-Za-z0-9_]*

quot;
}
}

Size

minPropertiesmaxProperties 限制属性值得数量,参数为非负整数

{
    "type": "Object",
    "minProperties": 2,
    "maxProperties": 3
}

没有属性,不在范围内

超出范围

### Dependencies

dependencies 关键字确定依赖关系

  • Property dependencies 属性依赖
  • Schema dependencies 模式依赖

Property dependencies

属性依赖,标识一个属性对另一个属性的依赖

{
    "type": "object",
    "properties": {
        "age": {
            "type": "number"
        },
        "name": {
            "type": "string"
        },
        "gender": "string"
    },
    "dependencies": {
        "name": ["gender"]
    }
}

缺少 gender

Schema dependencies

模式依赖

{
    "type": "object",
    "properties": {
        "age": {
            "type": "number"
        },
        "name": {
            "type": "string"
        }
    },
    "dependencies": {
        "name": {
            "properties": {
                "gender": {
                    "type": "string"
                }
            },
            "required": ["gender"]
        }
    }
}

Pattern Properties

模式属性:patternProperties 关键字用于正则验证属性

{
  "type": "object",
  "patternProperties": {
    "^S_": { "type": "string" },
    "^I_": { "type": "integer" }
  },
  "additionalProperties": false
}

属性值应该为string

array

数组用于有序元素,数组中每个元素都可以具有不同类型

{
    "type": "array"
}

Items

{
    "type": "array",
    "items": {
        "type": "number"
    }
}

Contains

contains 针对数组中的一个或者多个验证

{
    "type": "array",
    "contains": {
        "type": "number"
    }
}

Tuple validation

元组验证

{
    "type": "array",
    "items": [
        {
            "type": "number",
        },
        {
            "type": "string",
        },
        {
            "type": "number",
            "enum": [1, 2, 3]
        }
    ]
}

AdditionalItems

additionalItems 关键字是否允许超出所定义的项目,false则是不允许在数组中添加其他项

{
    "type": "array",
    "items": [
        {
            "type": "number",
        },
        {
            "type": "string",
        },
        {
            "type": "number",
            "enum": [1, 2, 3]
        }
    ],
    "additionalItems": false
}

additionalItems 为对象时

{
    "type": "array",
    "items": [
        {
            "type": "number",
        },
        {
            "type": "string",
        },
        {
            "type": "number",
            "enum": [1, 2, 3]
        }
    ],
    "additionalItems": {
        "type": "string"
    }
}

Length

minItemsmaxItems 限制数组长度,每个关键字必须为非负数

{
    "type": "array",
    "minItems": 2,
    "maxItems": 3
}

Uniqueness

uniqueItems 关键字确保数组中的每一项都是唯一的

{
    "type": "array",
    "uniqueItems": true
}

boolean

{
    "type": "number"
}

null

用于标志缺失值

{
    "type": "null"
}

Generic keywords

一般关键字

注释

不严格用于验证,但用来描述一个模式的一部分

  • title
  • description
  • default
  • example
{
  "title" : "Match anything",
  "description" : "This is a schema that matches anything.",
  "default" : "Default value",
  "examples" : [
    "Anything",
    4035
  ]
}

$comment

枚举值

enum 关键字用于限制值,以固定的一组值,至少包含一个元素的数组,每个元素都是唯一的。

{
    "type": "string",
    "enum": ["resd", "green"]
}

type 限定类型, enum 也会被限制

{
    "type": "string",
    "enum": ["red", "green", null]
}
const { validator } = require("@exodus/schemasafe")

const validate = validator({
    "type": "string",
    "enum": ["red", "green", null]
})

console.log(validate("red"))
console.log(validate(null))

const

const 关键字用于限定值,以一个单一的值

{
    "properties": {
        "country": {
            "const": "123"
        }
    }
}
const { validator } = require("@exodus/schemasafe")

const validate = validator({
    "properties": {
        "country": {
            "const": "123"
        }
    }
})

console.log(validate({country: '123'}))
console.log(validate({country: '456'}))

下面两个方法等价

{ "const": "United States of America" }

{ "enum": [ "United States of America" ] }

Media: string-encoding non-JSON data

contentMediaType

contentMediaType 关键字指定的MIME类型的字符串的内容

contentEncoding

contentEncoding 关键字指定的编码用于存储内容

{
    "type": "string",
    "contentMediaType": "text/html"
}
{
    "type": "string",
    "contentEncoding": "base64",
    "contentMediaType": "image/png"
}

Combining schemas

  • allOf 全部都要有效
  • anyOf 满足其中一个即可
  • oneOf [只能]满足其中一个
  • not 不能满足

allOf

{
    "allOf": [
        {
            "type": "string",
        },
        {
            "maxLength": 5
        }
    ]
}
const { validator } = require("@exodus/schemasafe")

const validate = validator({
    "allOf": [
        {
            "type": "string",
        },
        {
            "maxLength": 5
        }
    ]
})

console.log(validate('123'))
console.log(validate('123456'))

anyOf

{
    "anyOf": [
        {
            "type": "number"
        },
        {
            "type": "string"
        }
    ]
}
const { validator } = require("@exodus/schemasafe")

const validate = validator({
    "anyOf": [
        {
            "type": "number"
        },
        {
            "type": "string"
        }
    ]
})

console.log(validate(1))
console.log(validate({name: '1'}))
console.log(validate(null))

oneOf

{
    "oneOf": [
        {
            "type": "number",
            "multipleOf": 5
        },
        {
            "type": "number",
            "multipleOf": 5
        }
    ]
}
const { validator } = require("@exodus/schemasafe")

const validate = validator({
    "oneOf": [
        {
            "type": "number",
            "multipleOf": 5
        },
        {
            "type": "number",
            "multipleOf": 3
        }
    ]
})

console.log(validate(10))
console.log(validate(15))
console.log(validate(9))

not

{
    "not": {
        "type": "string"
    }
}
const { validator } = require("@exodus/schemasafe")

const validate = validator({
    "not": {
        "type": "string"
    }
})

console.log(validate(1))
console.log(validate('123'))
console.log(validate(null))

Applying subschemas conditionally

ifthenelse 关键字

{
  "type": "object",
  "properties": {
    "street_address": {
      "type": "string"
    },
    "country": {
      "enum": ["United States of America", "Canada"]
    }
  },
  "if": {
    "properties": { "country": { "const": "United States of America" } }
  },
  "then": {
    "properties": { "postal_code": { "pattern": "[0-9]{5}(-[0-9]{4})?" } }
  },
  "else": {
    "properties": { "postal_code": { "pattern": "[A-Z][0-9][A-Z] [0-9][A-Z][0-9]" } }
  }
}
const { validator } = require("@exodus/schemasafe")

const validate = validator({
    "type": "object",
  "properties": {
    "street_address": {
      "type": "string"
    },
    "country": {
      "enum": ["United States of America", "Canada"]
    }
  },
  "if": {
    "properties": { "country": { "const": "United States of America" } }
  },
  "then": {
    "properties": { "postal_code": { "pattern": "[0-9]{5}(-[0-9]{4})?" } }
  },
  "else": {
    "properties": { "postal_code": { "pattern": "[A-Z][0-9][A-Z] [0-9][A-Z][0-9]" } }
  }
})

console.log(validate({
  "street_address": "1600 Pennsylvania Avenue NW",
  "country": "United States of America",
  "postal_code": "20500"
}))

console.log(validate({
    "street_address": "24 Sussex Drive",
    "country": "Canada",
    "postal_code": "10000"
}))

console.log(validate({
    {
      "street_address": "24 Sussex Drive",
      "country": "Canada",
      "postal_code": "K1M 1M4"
    }
}))

The $schema keyword

$schema 关键字被用于声明一个JSON片段实际上是一块JSON架构的。它还声明了针对该架构编写的JSON Schema标准版本

"$schema": "http://json-schema.org/draft/2019-09/schema#"