繁體中文

開發者工具 · JSON 格式化程式和驗證程序

整個 JSON 語法在一頁上:六個值類型,兩個容器

· 背景

json 標準 驗證

整個 JSON 語法在一頁上:六種值類型、兩個用 JSON 標記說明的容器和精確的驗證邊界
原始 ToolAcre 向量圖

JSON 的整個語法都在一頁上,並熟記它使得每個驗證器錯誤都顯而易見。這篇文章將介紹六種值類型、兩種容器以及一些令人困惑的規則。

您見過的每個錯誤都來自一個頁面

每個語法錯誤都是對緊湊語法的破壞。打開物件後,解析器需要帶有引號的成員名稱或右大括號;在名稱之後,需要一個冒號;在一個值之後,它需要一個逗號或容器的結尾。將錯誤視為失敗的轉換比將報告的字元視為神秘的字元更有用。

ToolAcre 接受標準 JSON 值和空格,然後套用兩個實際輸入限制。解析之前,長度超過 8,000,000 個字元的文字將被拒絕,超出 512 容器的掃描器巢狀將被拒絕,而不是無限期地遍歷。這些是產品邊界,而不是新的 JSON 類型。在其中,診斷識別出令牌流不再滿足語法的第一個點。

六個值 — 物件、陣列、字串、數字、true/false 和 null,事實上沒有其他值

JSON 值是物件、陣列、字串、數字、布林值或 null。物件和陣列可以包含這六個容器中的任何一個,包括更多容器。字面拼字完全是 `true`、`false` 和 `null`;大小寫不彈性。諸如 `True`、`None`、`undefined`、`NaN` 和 `Infinity` 之類的標記位於嚴格的 JSON 之外,即使另一種語言可以識別其中的某些標記。

這個簡短的清單使分類成為一種有用的調試技術。在 `{"reading": NaN}` 中,冒號正確引入了一個值,但 `N` 不能開始任何允許的值。僅在確定資料的含義後才替換它,可能是 `null` 或引用的狀態。語法工具可以拒絕該標記;它無法選擇應用程式的替代品或決定該欄位是否屬於那裡。

物件和陣列 - 逗號分隔的成員、冒號以及為什麼 RFC 8259 將排序和重複名稱留給實現

物件包含逗號分隔的名稱 /value 成員。每個名稱都是一個雙引號字串,後面跟著一個冒號和一個值。陣列包含逗號分隔的值,沒有名稱或冒號。空 `{}` 和 `[]` 容器有效,但逗號不能開頭、結尾或出現兩次。將每個分隔符號與其容器相符會很快暴露出許多明顯的「意外令牌」故障。

物件名稱應是唯一的,但此驗證器不會拒絕重複的拼字。 `{"port": 80, "port": 443}` 解析,`JSON.parse` 保留後面的值。然後,格式化僅發出倖存的成員,因此無法從結果中復原較早的文字。陣列位置的行為有所不同:每個元素仍然存在,並其順序是值的一部分。

精確的字串和數字

字串使用雙引號。反斜線可以引入引號、反斜線、斜線、`b`、`f`、`n`、`r`、`t` 或四位 Unicode 轉義;禁止使用原始控製字元。單引號是字串外部的普通無效標記。這些規則解釋了為什麼複製的 JavaScript 文字和貼上的多行文字看起來可讀,但未通過嚴格的 JSON 驗證。

數字可以有減號、整數部分、可選分數和可選指數。它不能以 `+` 開頭、使用十六進位表示法、在另一個數字之前帶有前導零或拼寫非有限值。 `-0.25e+2` 有效;`01`、`.5`、`2.` 和 `Infinity` 不是。解析檢查語法,而不檢查 JavaScript 是否可以準確保留每個數字。

空白和頂層

在字串之外,JSON 空白僅限於空格、水平製表符、換行符和回車符。從網頁複製的不間斷空格不能與普通空格互換。格式化可以在標記周圍自由選擇允許的空格,但它必須保留屬於帶引號的字串內的空格,因為這些字元是資料。

完整檔案可以是任何單一 JSON 值,而不僅僅是物件或陣列。 `42`、`false` 和 `"ready"` 是有效的頂層文字。禁止的是第一個值之後的第二個值: `42 43` 是兩個文件,而不是一個。這種差異解釋了為什麼換行符號分隔的 JSON 需要逐筆記錄處理,而不是對整個檔案進行普通解析。

工作範例:手動解析小文件

採用 `{"order": [17, null, {"paid": true}], "note": "ship soon"}`。根物件開始一個名為 `order` 的成員;它的值是一個包含數字、null 和另一個物件的陣列。然後逗號引入 `note`,其值是帶有轉義換行符的字串。每個冒號、逗號和結束定界符都有一個語法作用。

現在刪除 `paid` 之前的引號。在嵌套大括號之後,解析器需要一個右大括號或引號的名稱,因此它在 `p` 處失敗。或者,在 `true` 之後加上逗號;解析器接受逗號,然後在 `}` 處失敗,因為後面必須有另一個成員。手動預測這些位置可以將驗證轉變為確認,並阻止隨機標點符號編輯。

這不包括什麼

語法沒有日期、十進制貨幣、二進位、UUID 或持續時間類型。應用程式通常用字串或數字來表示這些概念,並分別施加約定。時間戳可以是完全有效的 JSON 字串,但包含不可能的日期。同樣,語法上有效的物件可以省略所需的屬性或使用錯誤的單位,而不會違反單一解析規則。

ToolAcre 不執行模式檢查、網域驗證或規範化。它也不會重新解釋 JSON5 或 JSONC 功能,例如註解和尾隨逗號。它的工作範圍更窄:接受產品限制內的一個嚴格的 JSON 文字,格式化解析的值,並識別語法錯誤。將有關形狀和含義的後續問題保留在消費應用程式的驗證層中。

重點:記住語法,相信位置

持久檢查表很短:六個值類別、帶引號的物件名稱、僅在項目之間使用逗號、僅在名稱和值之間使用冒號、嚴格的字串轉義、嚴格的數字拼字、四個空白字元以及一個頂級值。當檔案失敗時,確定報告位置之前允許的語法,並將該期望與實際存在的字元進行比較。

相信該位置是第一個不可能點,而不總是需要刪除的字元。右大括號可能會被突出顯示,因為前面的逗號承諾了另一個成員;一封無辜的信件可能會因為缺少開頭引文而被突出顯示。修復原因,重新執行驗證,然後重複。對於超大或極深的輸入,請先解決 8 百萬字元或 512 深度的產品邊界,然後語法診斷才能提供協助。