網際網路工程任務組 A. Wright,編輯
網際網路草案
預定狀態:資訊性 H. Andrews,編輯
到期日:2020年3月20日
B. Hutton,編輯
Wellcome Sanger 研究所
2019年9月17日

JSON Schema 驗證:JSON 結構驗證詞彙
draft-handrews-json-schema-validation-02

摘要

JSON Schema (application/schema+json) 有多種用途,其中之一是 JSON 實例驗證。本文件指定 JSON Schema 的詞彙,以描述 JSON 文件含義、為處理 JSON 資料的使用者介面提供提示,並對有效文件外觀做出斷言。

讀者須知

此草案的問題列表可在 <https://github.com/json-schema-org/json-schema-spec/issues>找到。

如需其他資訊,請參閱 <https://json-schema.dev.org.tw/>

若要提供意見,請使用此問題追蹤器、首頁列出的通訊方式,或寄電子郵件給文件編輯者。

本備忘錄的狀態

此網際網路草案的提交完全符合 BCP 78 和 BCP 79 的規定。

網際網路草案是網際網路工程任務組 (IETF) 的工作文件。請注意,其他群組也可能將工作文件作為網際網路草案發布。目前的網際網路草案列表位於 https://datatracker.ietf.org/drafts/current/。

網際網路草案是有效期最長六個月的草案文件,隨時可能被其他文件更新、取代或廢棄。將網際網路草案用作參考資料或引用它們(「進行中的工作」除外)是不適當的。

此網際網路草案將於 2020 年 3 月 20 日到期。

版權聲明

版權所有 (c) 2019 IETF Trust 和被認定為文件作者的人員。保留所有權利。

本文件受 BCP 78 和 IETF Trust 關於 IETF 文件(https://trustee.ietf.org/license-info)的法律條款約束,該條款於本文件發布之日生效。請仔細審閱這些文件,因為它們描述您關於本文件的權利和限制。從本文件中提取的程式碼元件必須包含「簡化 BSD 授權」文字,如 Trust 法律條款第 4.e 節所述,並依「簡化 BSD 授權」所述,不提供擔保。


目錄

1. 簡介

JSON Schema 可用於要求指定的 JSON 文件(實例)滿足一定數量的條件。這些條件透過使用本規範中描述的關鍵字來聲明。此外,還定義了一組關鍵字,以協助產生互動式使用者介面實例。

本規範將使用 JSON Schema 核心規範定義的概念、語法和術語。

2. 慣例和術語

本文件中,「MUST」、「MUST NOT」、「REQUIRED」、「SHALL」、「SHALL NOT」、「SHOULD」、「SHOULD NOT」、「RECOMMENDED」、「MAY」和「OPTIONAL」等關鍵字應按照 RFC 2119 中的描述進行解釋。

本規範使用「容器實例」一詞來指代陣列和物件實例。它使用「子實例」一詞來指代陣列元素或物件成員值。

如果此陣列的任何兩個元素不相等,則表示陣列值中的元素是唯一的。

3. 概述

JSON Schema 驗證會對實例資料的結構聲明約束。滿足所有聲明約束的實例位置,將使用任何包含非斷言資訊的關鍵字進行註解,例如描述性中繼資料和使用提示。如果實例中的所有位置都滿足所有聲明約束,則表示該實例對於綱要有效。

每個綱要物件都針對它所適用的每個實例位置獨立評估。這透過確保驗證器不需要在整個文件的驗證過程中維護狀態,大大簡化了驗證器的實作要求。

本規範定義了一組斷言關鍵字,以及一個小型中繼資料關鍵字詞彙,可用於使用有用的資訊註解 JSON 實例。第 7 節關鍵字主要用作註解,但也可以選擇用作斷言。第 8 節關鍵字是用於處理嵌入為 JSON 字串的文件的註解。

4. 互通性考量

4.1. 字串實例驗證

應該注意的是,空字元 (\u0000) 在 JSON 字串中是有效的。要驗證的實例可能包含帶有此字元的字串值,而不管底層程式語言處理此類資料的能力如何。

4.2. 數值實例驗證

JSON 規範允許具有任意精度的數字,而 JSON Schema 沒有新增任何此類界限。這表示 JSON Schema 處理的數值實例可以是任意大和/或具有任意長的十進位部分,而不管底層程式語言處理此類資料的能力如何。

4.3. 正規表示式

使用正規表示式或將實例值限制為正規表示式的關鍵字,受制於 JSON Schema 核心規範中正規表示式的互通性考量。

5. 中繼綱要

預設 JSON Schema 中繼綱要的目前 URI 是 <https://json-schema.dev.org.tw/draft/2019-09/schema>。為了方便綱要作者,此中繼綱要描述了本規範和 JSON Schema 核心規範中定義的所有詞彙,以及兩個為過渡期保留的舊關鍵字。每個章節都提供了個別的詞彙和詞彙中繼綱要 URI。某些詞彙是選擇性支援的,這在相關章節中有詳細說明。

為了更正錯誤,可能會在規範草案之間發佈更新的詞彙和中繼綱要 URI。實作應考慮在本規範草案之後和下一個草案之前發佈的 URI,以表示與此處列出的語法和語意相同。

6. 結構驗證詞彙

綱要中的驗證關鍵字會對實例的成功驗證施加要求。這些關鍵字都是斷言,不帶任何註解行為。

未使用 "$vocabulary" 的元綱要應被視為要求此詞彙表,如同其 URI 以 true 值存在一樣。

此詞彙表(稱為驗證詞彙表)的目前 URI 為:<https://json-schema.dev.org.tw/draft/2019-09/vocab/validation>

對應的元綱要的目前 URI 為:<https://json-schema.dev.org.tw/draft/2019-09/meta/validation>

6.1. 任何實例類型的驗證關鍵字

6.1.1. type

此關鍵字的值必須是字串或陣列。如果它是陣列,則陣列的元素必須是字串,且必須是唯一的。

字串值必須是六個原始類型之一("null"、"boolean"、"object"、"array"、"number" 或 "string"),或是 "integer",它會匹配任何小數部分為零的數字。

當且僅當實例屬於此關鍵字所列出的任何集合時,該實例才會驗證通過。

6.1.2. enum

此關鍵字的值必須是陣列。此陣列應至少包含一個元素。陣列中的元素應是唯一的。

如果實例的值等於此關鍵字陣列值中的其中一個元素,則該實例會針對此關鍵字成功驗證通過。

陣列中的元素可以是任何類型,包括 null。

6.1.3. const

此關鍵字的值可以是任何類型,包括 null。

使用此關鍵字的功能等同於使用具有單一值的 "enum"

如果實例的值等於此關鍵字的值,則該實例會針對此關鍵字成功驗證通過。

6.2. 數值實例(number 和 integer)的驗證關鍵字

6.2.1. multipleOf

"multipleOf" 的值必須是嚴格大於 0 的數字。

只有當數值實例除以此關鍵字的值的結果為整數時,該數值實例才有效。

6.2.2. maximum

"maximum" 的值必須是數字,表示數值實例的包含性上限。

如果實例是數字,則只有當實例小於或完全等於 "maximum" 時,此關鍵字才會驗證通過。

6.2.3. exclusiveMaximum

"exclusiveMaximum" 的值必須是數字,表示數值實例的排除性上限。

如果實例是數字,則只有當實例的值嚴格小於(不等於)"exclusiveMaximum" 時,該實例才有效。

6.2.4. minimum

"minimum" 的值必須是數字,表示數值實例的包含性下限。

如果實例是數字,則只有當實例大於或完全等於 "minimum" 時,此關鍵字才會驗證通過。

6.2.5. exclusiveMinimum

"exclusiveMinimum" 的值必須是數字,表示數值實例的排除性下限。

如果實例是數字,則只有當實例的值嚴格大於(不等於)"exclusiveMinimum" 時,該實例才有效。

6.3. 字串的驗證關鍵字

6.3.1. maxLength

此關鍵字的值必須是非負整數。

如果字串實例的長度小於或等於此關鍵字的值,則該實例會針對此關鍵字有效。

字串實例的長度定義為 RFC 8259 中定義的字元數。

6.3.2. minLength

此關鍵字的值必須是非負整數。

如果字串實例的長度大於或等於此關鍵字的值,則該實例會針對此關鍵字有效。

字串實例的長度定義為 RFC 8259 中定義的字元數。

省略此關鍵字的行為與值為 0 的行為相同。

6.3.3. pattern

此關鍵字的值必須是字串。根據 ECMA 262 正則表達式方言,此字串應為有效的正則表達式。

如果正則表達式成功匹配實例,則認為字串實例有效。請注意:正則表達式並非隱式錨定。

6.4. 陣列的驗證關鍵字

6.4.1. maxItems

此關鍵字的值必須是非負整數。

如果陣列實例的大小小於或等於此關鍵字的值,則該實例會針對 "maxItems" 有效。

6.4.2. minItems

此關鍵字的值必須是非負整數。

如果陣列實例的大小大於或等於此關鍵字的值,則該實例會針對 "minItems" 有效。

省略此關鍵字的行為與值為 0 的行為相同。

6.4.3. uniqueItems

此關鍵字的值必須是布林值。

如果此關鍵字的布林值為 false,則實例會成功驗證。如果此關鍵字的布林值為 true,則當其實例的所有元素都是唯一的時,該實例會成功驗證。

省略此關鍵字的行為與值為 false 的行為相同。

6.4.4. maxContains

此關鍵字的值必須是非負整數。

如果針對 "contains" 的綱要有效的元素數量小於或等於此關鍵字的值,則陣列實例會針對 "maxContains" 有效。

如果相同的綱要物件中沒有 "contains",則此關鍵字無效。

6.4.5. minContains

此關鍵字的值必須是非負整數。

如果針對 "contains" 的綱要有效的元素數量大於或等於此關鍵字的值,則陣列實例會針對 "minContains" 有效。

允許值為 0,但僅適用於將出現次數範圍設定為從 0 到 "maxContains" 的值。如果 "maxContains" 不存在且值為 0,則 "contains" 將始終通過驗證。

如果相同的綱要物件中沒有 "contains",則此關鍵字無效。

省略此關鍵字的行為與值為 1 的行為相同。

6.5. 物件的驗證關鍵字

6.5.1. maxProperties

此關鍵字的值必須是非負整數。

如果物件實例的屬性數量小於或等於此關鍵字的值,則該實例會針對 "maxProperties" 有效。

6.5.2. minProperties

此關鍵字的值必須是非負整數。

如果物件實例的屬性數量大於或等於此關鍵字的值,則該實例會針對 "minProperties" 有效。

省略此關鍵字的行為與值為 0 的行為相同。

6.5.3. required

此關鍵字的值必須是陣列。此陣列中的元素(如果有的話)必須是字串,且必須是唯一的。

如果陣列中的每個項目都是實例中屬性的名稱,則物件實例會針對此關鍵字有效。

省略此關鍵字的行為與空陣列的行為相同。

6.5.4. dependentRequired

此關鍵字的值必須是物件。此物件中的屬性(如果有的話)必須是陣列。每個陣列中的元素(如果有的話)必須是字串,且必須是唯一的。

此關鍵字會指定當存在特定其他屬性時,必須存在的屬性。它們的要求取決於其他屬性的存在。

如果實例和此關鍵字的值中都出現的每個名稱,其對應陣列中的每個項目也都是實例中屬性的名稱,則驗證會成功。

省略此關鍵字的行為與空物件的行為相同。

7. 使用 "format" 的語意內容詞彙表

7.1. 前言

單獨的結構驗證可能不足以讓應用程式正確使用某些值。"format" 註解關鍵字的定義旨在允許綱要作者傳達一組固定值的語意資訊,這些值可由權威資源(例如 RFC 或其他外部規範)準確描述。

實作可以將 "format" 視為註解和斷言,並嘗試驗證該值是否符合指定的語意。如需詳細資訊,請參閱下方的實作要求。

此關鍵字的值稱為格式屬性。它必須是字串。格式屬性通常只能驗證一組給定的實例類型。如果要驗證的實例類型不在這個集合中,則此格式屬性和實例的驗證應成功。本節中定義的所有格式屬性都適用於字串,但可以指定格式屬性以套用至 核心 JSON 綱要中定義的資料模型中定義的任何實例類型。[CREF1]請注意,本規範中的 "type" 關鍵字定義了不屬於資料模型的 "integer" 類型。因此,格式屬性可以限制為數字,但不能明確限制為整數。但是,數值格式可以與值為 "integer" 的 "type" 關鍵字一起使用,或可以明確定義為當數字不是整數時始終通過,這會產生與僅套用於整數基本相同的行為。

未使用 "$vocabulary" 的元綱要應被視為使用此詞彙表,如同其 URI 以 false 值存在一樣。如需詳細資訊,請參閱下方的實作要求。

此詞彙表(稱為格式詞彙表)的目前 URI 為:<https://json-schema.dev.org.tw/draft/2019-09/vocab/format>

對應的元綱要的目前 URI 為:<https://json-schema.dev.org.tw/draft/2019-09/meta/format>

7.2. 實作要求

"format" 關鍵字的作用是註解,以及選擇性的斷言。[CREF2]這是由於該關鍵字的歷史原因,並且與目前的關鍵字設計原則不符。為了管理這種模糊性,"format" 關鍵字是在其自身單獨的詞彙表中定義的,如上所述。詞彙表宣告的 true 或 false 值會決定處理使用 "format" 的綱要所需的實作要求,以及綱要作者可以依賴的行為。

7.2.1. 作為註解

如果實作支援註解收集,則必須將 format 的值收集為註解。這可以在綱要驗證不可用或不夠充分時啟用應用程式層級的驗證。

此要求不受詞彙表宣告的布林值影響,也不受下一節中描述的 "format" 斷言行為的組態影響。[CREF3]即使以 false 值宣告詞彙表時也要求收集註解是不典型的,但即使未實作斷言評估,仍必須確保可以執行應用程式層級驗證的最佳實務。由於 "format" 一直是本規範的一部分,因此即使使用 false 詞彙表宣告也要求實作知道它,並不認為是一種負擔。

7.2.2. 作為斷言

無論詞彙表宣告的布林值為何,可以將 "format" 評估為斷言的實作都必須提供選項來啟用和停用此類評估。當選項未明確指定時,斷言評估行為取決於詞彙表宣告的布林值。

在實作此完整規範時,此詞彙**必須**支援值為 false (但請參閱以下詳細資訊),且**可能**支援值為 true。

當此詞彙宣告值為 false 時,實作應: [CREF4]這符合目前實作的現況,它們針對某些或所有格式屬性提供各種不同程度的驗證,包括完全不驗證。其目的也是為了鼓勵僅依賴註解行為,並在應用程式中執行語意驗證,這是建議的最佳實務。

當此詞彙宣告值為 true 時,支援此形式詞彙的實作: [CREF5]預期對於簡單的格式 (例如日期時間),語法驗證將會徹底。對於複雜的格式 (例如電子郵件地址,它們是各種標準的合併,並且隨著時間推移有許多調整,其中包含模糊和/或過時的規則,可能會或可能不會受到使用該值的其他應用程式的限制),最少限度的驗證就足夠了。例如,不包含 "@" 的實例字串顯然不是有效的電子郵件地址,而包含 7 位元 ASCII 之外字元的 "email" 或 "hostname" 也顯然是無效的。

由於許多屬性所涉及的複雜性,對格式屬性進行最少限度驗證的要求是有意模糊和寬容的。請特別注意,要求僅限於語法檢查;不應期望實作會傳送電子郵件、嘗試連線至 URL,或以其他方式檢查由格式實例識別的實體是否存在。

建議實作針對每個格式使用通用的剖析程式庫或知名的正規表示式。實作**應**清楚記錄如何以及在何種程度上驗證每個格式屬性。

標準核心和驗證元綱要在其 "$vocabulary" 關鍵字中包含此詞彙,值為 false,因為預設情況下,不要求實作支援此關鍵字作為斷言。理解到以 true 值支援格式詞彙會大幅增加程式碼大小,並且在某些情況下會增加執行時間,因此並非適用於所有實作。

7.2.3. 自訂格式屬性

實作**可能**支援自訂格式屬性。除了各方之間的協議之外,綱要作者**不應**期望對等實作支援此類自訂格式屬性。實作**不得**因未知的格式屬性而導致驗證失敗或停止處理。當將 "format" 視為註解時,實作**應**收集已知和未知的格式屬性值。

詞彙不支援明確宣告關鍵字的不同值集。由於此限制以及此關鍵字歷史上不均勻的實作,如果需要互通性,建議在自訂詞彙中定義其他關鍵字,而不是其他格式屬性。

7.3. 定義的格式

7.3.1. 日期、時間和持續時間

這些屬性適用於字串實例。

日期和時間格式名稱衍生自 RFC 3339,第 5.6 節。持續時間格式來自 RFC 3339 附錄 A 中給出的 ISO 8601 ABNF。

支援格式的實作**應**實作對以下屬性的支援

date-time
如果字串實例符合「date-time」產生式的有效表示法,則此字串實例對此屬性有效。
date
如果字串實例符合「full-date」產生式的有效表示法,則此字串實例對此屬性有效。
time
如果字串實例符合「full-time」產生式的有效表示法,則此字串實例對此屬性有效。
duration
如果字串實例符合「duration」產生式的有效表示法,則此字串實例對此屬性有效。

實作**可能**使用該章節中定義的其他產生式名稱來支援其他屬性。如果實作了「full-date」或「full-time」,則必須實作對應的簡短形式(分別為「date」或「time」),並且必須具有相同的行為。實作**不應**定義任何名稱與 RFC 3339 產生式相符的擴充屬性,除非它根據該產生式的規則進行驗證。[CREF6]目前對於需要支援所有 RFC 3339 格式沒有共識,因此這種保留命名空間的方法將鼓勵實驗,而不會承諾支援整個集合。格式實作要求通常會變得更靈活,或者它們可能會被提升為完全指定的屬性或被刪除。

7.3.2. 電子郵件地址

這些屬性適用於字串實例。

如果字串實例是有效的網際網路電子郵件地址,則此字串實例對這些屬性有效,如下所示

email
RFC 5322,第 3.4.1 節所定義。
idn-email
RFC 6531 所定義

請注意,對於 "email" 屬性有效的所有字串,對於 "idn-email" 屬性也有效。

7.3.3. 主機名稱

這些屬性適用於字串實例。

如果字串實例是網際網路主機名稱的有效表示法,則此字串實例對這些屬性有效,如下所示

hostname
RFC 1123,第 2.1 節所定義,包括使用 RFC 5891,第 4.4 節中指定的 Punycode 演算法產生之主機名稱。
idn-hostname
如 RFC 1123 中針對 hostname 所定義,或如 RFC 5890,第 2.3.2.3 節所定義的國際化主機名稱。

請注意,對於 "hostname" 屬性有效的所有字串,對於 "idn-hostname" 屬性也有效。

7.3.4. IP 位址

這些屬性適用於字串實例。

如果字串實例是 IP 位址的有效表示法,則此字串實例對這些屬性有效,如下所示

ipv4
根據 RFC 2673,第 3.2 節中定義的「點分四組」ABNF 語法的 IPv4 位址。
ipv6
RFC 4291,第 2.2 節中定義的 IPv6 位址。

7.3.5. 資源識別碼

這些屬性適用於字串實例。

uri
如果字串實例是有效的 URI,則此字串實例對此屬性有效,根據 [RFC3986]
uri-reference
如果字串實例是有效的 URI 參考 (URI 或相對參考),則此字串實例對此屬性有效,根據 [RFC3986]
iri
如果字串實例是有效的 IRI,則此字串實例對此屬性有效,根據 [RFC3987]
iri-reference
如果字串實例是有效的 IRI 參考 (IRI 或相對參考),則此字串實例對此屬性有效,根據 [RFC3987]
uuid
如果字串實例是 UUID 的有效字串表示法,則此字串實例對此屬性有效,根據 [RFC4122]

請注意,所有有效的 URI 都是有效的 IRI,而且所有有效的 URI 參考也是有效的 IRI 參考。

另請注意,「uuid」格式適用於純 UUID,而不是 URN 中的 UUID。例如 "f81d4fae-7dec-11d0-a765-00a0c91e6bf6"。對於 URN 形式的 UUID,請使用 "uri" 格式,並使用 "^urn:uuid:" 的「模式」正規表示式來指示 URI 結構和 URN 命名空間。

7.3.6. uri-template

此屬性適用於字串實例。

如果字串實例是有效的 URI 範本 (任何層級),則此字串實例對此屬性有效,根據 [RFC6570]

請注意,URI 範本可用於 IRI;沒有單獨的 IRI 範本規範。

7.3.7. JSON 指標

這些屬性適用於字串實例。

json-pointer
如果字串實例是有效的 JSON 字串表示法,表示 JSON 指標,則此字串實例對此屬性有效,根據 RFC 6901,第 5 節
relative-json-pointer
如果字串實例是有效的相對 JSON 指標,則此字串實例對此屬性有效。

若要允許絕對和相對 JSON 指標,請使用 "anyOf" 或 "oneOf" 來指示對任一格式的支援。

7.3.8. regex

此屬性適用於字串實例。

正規表示式,其**應**根據 ECMA 262 正規表示式方言有效。

驗證格式的實作**必須**接受此規範的正規表示式章節中定義的 ECMA 262 子集,並且**應**接受所有有效的 ECMA 262 表示式。

8. 字串編碼資料內容的詞彙

8.1. 前言

本節中定義的註解表示實例包含以 JSON 字串編碼的非 JSON 資料。

這些屬性提供將 JSON 資料解譯為豐富多媒體文件所需的額外資訊。它們描述內容的類型、編碼方式和/或如何驗證。它們不作為驗證斷言;格式錯誤的字串編碼文件**不得**導致包含的實例被視為無效。

未使用 "$vocabulary" 的元綱要應被視為要求此詞彙表,如同其 URI 以 true 值存在一樣。

此詞彙的目前 URI (稱為內容詞彙) 為:<https://json-schema.dev.org.tw/draft/2019-09/vocab/content>

對應元綱要的目前 URI 為:<https://json-schema.dev.org.tw/draft/2019-09/meta/content>

8.2. 實作要求

由於安全性和效能問題,以及可能內容類型的開放式性質,實作**不得**預設自動解碼、剖析和/或驗證字串內容。這也支援由與處理包含文件不同的消費者處理的內嵌文件之使用案例。

本節中的所有關鍵字僅適用於字串,對其他資料類型沒有影響。

實作可以選擇提供自動解碼、剖析和/或驗證字串內容的功能。然而,預設情況下**不得**執行這些操作,並且**必須**將每個字串編碼文件的驗證結果與封閉文件分開提供。此過程**應該**等同於針對原始綱要完整評估實例,然後使用註解來解碼、剖析和/或驗證每個字串編碼文件。[CREF7]目前,執行並從這種自動解碼、剖析和驗證功能返回剖析資料和/或驗證結果的確切機制尚未指定。如果此功能證明受歡迎,則可能會在未來的草案中更詳細地指定。

另請參閱安全性考量章節,了解根據這些關鍵字自動處理實例字串可能引入的漏洞。

8.3. contentEncoding

如果實例值是字串,則此屬性定義字串**應該**被解釋為二進位資料,並使用此屬性命名的編碼進行解碼。

此屬性的可能值列於RFC 2045,第 6.1 節RFC 4648。對於在兩個 RFC 中都有定義的「base64」,**應該**使用 RFC 4648 中的定義,該定義取消了行長度的限制,因為其他各種規範都強制規定了不同的長度。請注意,可以使用「pattern」關鍵字來約束字串中的行長度。

如果此關鍵字不存在,但存在「contentMediaType」,則表示該媒體類型可以像任何其他 JSON 字串值一樣編碼為 UTF-8,而無需額外解碼。

此屬性的值**必須**是字串。

8.4. contentMediaType

如果實例是字串,則此屬性表示字串內容的媒體類型。如果存在「contentEncoding」,則此屬性描述解碼後的字串。

此屬性的值**必須**是字串,而該字串**必須**是RFC 2046所定義的媒體類型。

8.5. contentSchema

如果實例是字串,且存在「contentMediaType」,則此屬性包含一個描述字串結構的綱要。

此關鍵字**可以**與任何可以對應到 JSON 綱要資料模型的媒體類型一起使用。

如果不存在「contentMediaType」,則**應該**忽略此屬性的值。

8.6. 範例

以下是一個範例綱要,說明「contentEncoding」和「contentMediaType」的用法

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

                    

此綱要描述的實例預期為字串,並且其值應可解釋為 base64 編碼的 PNG 影像。

另一個範例

{
    "type": "string",
    "contentMediaType": "text/html"
}

                    

此綱要描述的實例預期為包含 HTML 的字串,並使用 JSON 字串解碼成的任何字元集。根據RFC 8259的第 8.1 節,在完全封閉的系統之外,這**必須**是 UTF-8。

此範例描述一個使用 HMAC SHA-256 演算法進行 MAC 的 JWT,並且在其宣告集中需要「iss」和「exp」欄位。

{
    "type": "string",
    "contentMediaType": "application/jwt",
    "contentSchema": {
        "type": "array",
        "minItems": 2,
        "items": [
            {
                "const": {
                    "typ": "JWT",
                    "alg": "HS256"
                }
            },
            {
                "type": "object",
                "required": ["iss", "exp"],
                "properties": {
                    "iss": {"type": "string"},
                    "exp": {"type": "integer"}
                }
            }
        ]
    }
}
                    

請注意,不會出現「contentEncoding」。雖然「application/jwt」媒體類型使用 base64url 編碼,但該編碼是由媒體類型定義的,它決定了如何將 JWT 字串解碼為兩個 JSON 資料結構的清單:第一個是標頭,然後是有效載荷。由於 JWT 媒體類型確保 JWT 可以用 JSON 字串表示,因此無需進一步編碼或解碼。

9. 基本元資料註解的詞彙表

這些通用註解關鍵字為文件和使用者介面顯示目的提供常用的資訊。它們無意形成一套全面的功能。相反地,可以為更複雜的基於註解的應用程式定義其他詞彙表。

未使用 "$vocabulary" 的元綱要應被視為要求此詞彙表,如同其 URI 以 true 值存在一樣。

此詞彙表(稱為元資料詞彙表)的目前 URI 為:<https://json-schema.dev.org.tw/draft/2019-09/vocab/meta-data>

對應的中繼綱要的目前 URI 為:<https://json-schema.dev.org.tw/draft/2019-09/meta/meta-data>

9.1. 「title」和「description」

這兩個關鍵字的值**必須**是字串。

這兩個關鍵字都可用於使用有關此使用者介面產生的資料的資訊來裝飾使用者介面。標題最好簡短,而描述則提供有關此綱要描述的實例的用途的說明。

9.2. 「default」

此關鍵字的值沒有限制。當此關鍵字的多次出現適用於單個子實例時,實作**應該**移除重複項。

此關鍵字可用於提供與特定綱要相關聯的預設 JSON 值。建議預設值針對相關綱要有效。

9.3. 「deprecated」

此關鍵字的值**必須**是布林值。當此關鍵字的多次出現適用於單個子實例時,如果任何出現指定為 true 值,應用程式**應該**將該實例位置視為已棄用。

如果「deprecated」的值為布林值 true,則表示應用程式**應該**避免使用宣告的屬性。這可能表示該屬性將在未來被移除。

包含值為 true 的「deprecated」的根綱要表示可能在未來移除所描述的整個資源。

當藉由「items」將「deprecated」關鍵字應用於陣列中的項目時,如果「items」是單一綱要,則棄用與整個陣列相關,而如果「items」是綱要陣列,則棄用與根據子綱要位置的相應項目相關。

省略此關鍵字的行為與值為 false 的行為相同。

9.4. 「readOnly」和「writeOnly」

這些關鍵字的值**必須**是布林值。當這些關鍵字的多次出現適用於單個子實例時,如果任何出現指定為 true 值,則結果行為**應該**與 true 值相同,否則**應該**與 false 值相同。

如果「readOnly」的值為布林值 true,則表示實例的值由擁有機構獨佔管理,並且預期擁有機構會忽略或拒絕應用程式修改此屬性值的嘗試。

如果整個文件都標記為「readOnly」,則發送到擁有機構的實例文檔**可以**被忽略,或者**可以**導致錯誤,具體取決於該機構的判斷。

如果「writeOnly」的值為布林值 true,則表示當從擁有機構檢索實例時,該值永遠不會存在。它可以在發送到擁有機構以更新或建立文件(或它代表的資源)時存在,但它不會包含在實例的任何更新或新建立的版本中。

如果整個文件都標記為「writeOnly」,則實例文檔**可以**以某種形式的空白文件傳回,或者**可以**在檢索時產生錯誤,或讓檢索請求被忽略,具體取決於該機構的判斷。

例如,「readOnly」將用於將資料庫產生的序號標記為唯讀,而「writeOnly」將用於將密碼輸入欄位標記為僅寫入。

這些關鍵字可用於協助使用者介面實例的產生。特別是,應用程式**可以**選擇使用一個小工具,在輸入僅寫入欄位時隱藏輸入值。

省略這些關鍵字的行為與 false 值相同。

9.5. 「examples」

此關鍵字的值**必須**是陣列。陣列中的值沒有限制。當此關鍵字的多次出現適用於單個子實例時,實作**必須**提供所有值的扁平陣列,而不是陣列的陣列。

此關鍵字可用於提供與特定綱要相關聯的範例 JSON 值,以說明用法。建議這些值針對相關綱要有效。

實作**可以**使用「default」(如果存在)的值作為額外範例。如果不存在「examples」,則仍然**可以**以這種方式使用「default」。

10. 安全性考量

JSON 綱要驗證為 JSON 綱要核心定義了一個詞彙表,並涉及此處列出的所有安全性考量。

JSON 綱要驗證允許使用正規表示式,正規表示式有許多不同的(通常不相容的)實作。某些實作允許嵌入任意程式碼,這不在 JSON 綱要的範圍內,且**不得**允許。正規表示式通常也可以被精心設計為計算成本極高(使用所謂的「災難性回溯」),從而導致阻斷服務攻擊。

支援根據「contentEncoding」和/或「contentMediaType」驗證或以其他方式評估實例字串資料的實作存在根據誤導性資訊以不安全的方式評估資料的風險。應用程式可以透過僅在綱要和實例之間建立關係時(例如,它們共享相同的授權)執行此類處理來降低此風險。

處理媒體類型或編碼應受該媒體類型或編碼的安全性考量約束。例如,當處理 JSON 字串中編碼的 JavaScript 或 ECMAScript 時,RFC 4329 指令碼媒體類型的安全性考量適用。

11. 參考文獻

11.1. 規範性參考文獻

[ecma262] ECMA 262 規範
[json-schema] Wright, A.H. Andrews, 「JSON 綱要:用於描述 JSON 文件的一種媒體類型」,Internet-Draft draft-handrews-json-schema-02,2017 年 11 月。
[relative-json-pointer] Luff, G.H. Andrews, 「相對 JSON 指標」,Internet-Draft draft-handrews-relative-json-pointer-01,2017 年 11 月。
[RFC1123] Braden, R., 「網際網路主機的要求 - 應用程式和支援」,STD 3, RFC 1123, DOI 10.17487/RFC1123, 1989 年 10 月。
[RFC2045] Freed, N.N. Borenstein, 「多用途網際網路郵件延伸 (MIME) 第一部分:網際網路訊息主體格式」,RFC 2045, DOI 10.17487/RFC2045, 1996 年 11 月。
[RFC2046] Freed, N.N. Borenstein, 「多用途網際網路郵件延伸 (MIME) 第二部分:媒體類型」,RFC 2046, DOI 10.17487/RFC2046, 1996 年 11 月。
[RFC2119] Bradner, S., 「在 RFC 中用於指示要求層級的關鍵字」,BCP 14, RFC 2119, DOI 10.17487/RFC2119, 1997 年 3 月。
[RFC2673] Crawford, M., 「網域名稱系統中的二進位標籤」,RFC 2673, DOI 10.17487/RFC2673, 1999 年 8 月。
[RFC3339] Klyne, G.C. Newman, 「網際網路上的日期和時間:時間戳記」,RFC 3339, DOI 10.17487/RFC3339, 2002 年 7 月。
[RFC3986] Berners-Lee, T.Fielding, R.L. Masinter, 「統一資源識別碼 (URI):一般語法」,STD 66, RFC 3986, DOI 10.17487/RFC3986, 2005 年 1 月。
[RFC3987] Duerst, M.M. Suignard, 「國際化資源識別碼 (IRI)」,RFC 3987, DOI 10.17487/RFC3987, 2005 年 1 月。
[RFC4122] Leach, P.Mealling, M.R. Salz, 「通用唯一識別碼 (UUID) URN 命名空間」,RFC 4122, DOI 10.17487/RFC4122, 2005 年 7 月。
[RFC4291] Hinden, R.S. Deering, 「IP 第 6 版定址架構」,RFC 4291, DOI 10.17487/RFC4291, 2006 年 2 月。
[RFC4648] Josefsson, S., "The Base16, Base32, and Base64 Data Encodings", RFC 4648, DOI 10.17487/RFC4648, 2006年10月。
[RFC5322] Resnick, P., "Internet Message Format", RFC 5322, DOI 10.17487/RFC5322, 2008年10月。
[RFC5890] Klensin, J., "Internationalized Domain Names for Applications (IDNA): Definitions and Document Framework", RFC 5890, DOI 10.17487/RFC5890, 2010年8月。
[RFC5891] Klensin, J., "Internationalized Domain Names in Applications (IDNA): Protocol", RFC 5891, DOI 10.17487/RFC5891, 2010年8月。
[RFC6531] Yao, J.W. Mao, "SMTP Extension for Internationalized Email", RFC 6531, DOI 10.17487/RFC6531, 2012年2月。
[RFC6570] Gregorio, J., Fielding, R., Hadley, M., Nottingham, M.D. Orchard, "URI Template", RFC 6570, DOI 10.17487/RFC6570, 2012年3月。
[RFC6901] Bryan, P., Zyp, K.M. Nottingham, "JavaScript Object Notation (JSON) Pointer", RFC 6901, DOI 10.17487/RFC6901, 2013年4月。
[RFC8259] Bray, T., "The JavaScript Object Notation (JSON) Data Interchange Format", STD 90, RFC 8259, DOI 10.17487/RFC8259, 2017年12月。

11.2. 參考文獻

[RFC4329] Hoehrmann, B., "Scripting Media Types", RFC 4329, DOI 10.17487/RFC4329, 2006年4月。

附錄 A. 從驗證移至核心的關鍵字

從本文件到本草案發佈時,有幾個關鍵字已移至 核心規範 中,某些情況下會重新命名或其他變更。這會影響到以下先前的驗證關鍵字:

"definitions"
重新命名為 "$defs",以符合 "$ref" 並縮短輸入長度。為了避免使仍然使用舊名稱的模式失效,模式詞彙作者**不應**定義具有不同行為的 "definitions" 關鍵字。雖然此文件中引用的單一詞彙元模式中沒有 "definitions",但它仍存在於預設元模式中,而且當使用該元模式時,實作**應**假設 "$defs" 和 "definitions" 具有相同的行為。
"allOf"、"anyOf"、"oneOf"、"not"、"if"、"then"、"else"、"items"、"additionalItems"、"contains"、"propertyNames"、"properties"、"patternProperties"、"additionalProperties"
所有這些關鍵字都會將子模式應用於實例並組合它們的結果,而不會斷言任何自身的條件。如果沒有斷言關鍵字,這些應用程式只能透過使用 false 布林值模式或反轉 true 布林值模式(或等效模式物件)的結果來造成斷言失敗。基於這個原因,它們最好被定義為一種通用機制,驗證、超模式和擴充詞彙都可以基於此機制。
"dependencies"
這個關鍵字有兩種不同的行為模式,這使得實作和推理相對具有挑戰性。模式形式已移至核心並重新命名為 "dependentSchemas",作為應用程式詞彙的一部分。它類似於 "properties",只是它不是將其子模式應用於屬性值,而是將其應用於包含該屬性的物件。"dependencies" 的屬性名稱陣列形式保留在此處並重新命名為 "dependentRequired",因為它是一種斷言,是條件使用 "required" 斷言關鍵字的快捷方式。

附錄 B. 致謝

感謝 Gary Court、Francis Galiegue、Kris Zyp 和 Geraint Luff 為 JSON Schema 的初始草案所做的工作。

感謝 Jason Desrosiers、Daniel Perrett、Erik Wilde、Ben Hutton、Evgeny Poberezkin、Brad Bowman、Gowry Sankar、Donald Pipowitch、Dave Finlay 和 Denis Laxalde 對文件的提交和修補程式。

附錄 C. 變更記錄

[CREF8]本節將在離開 Internet-Draft 狀態之前移除。

draft-handrews-json-schema-validation-02

draft-handrews-json-schema-validation-01

draft-handrews-json-schema-validation-00

draft-wright-json-schema-validation-01

draft-wright-json-schema-validation-00

draft-fge-json-schema-validation-00

作者地址

Austin Wright (編輯) 電子郵件:[email protected]
Henry Andrews (編輯) 電子郵件:[email protected]
Ben Hutton (編輯) Wellcome Sanger Institute 電子郵件:[email protected] URI:https://jsonschema.dev