跳至內容
結構定義轉換

JSON Schema ⇄ Zod 轉換器

可以從 JSON Schema 產生 Zod 結構定義,也可以反過來從 Zod 程式碼寫出 JSON Schema 的雙向轉換工具。required.optional()、enum、union、巢狀物件、字串 format 與長度限制都會雙向對應。無法轉換的部分會以警告顯示。所有處理都在瀏覽器內完成,您貼上的結構定義不會被傳送出去。

指南: 使用方式與特色

  • 選擇「JSON Schema → Zod」並貼上結構定義,就會產生 `z.object({ ... })` 形式的 Zod 結構定義與 `z.infer` 型別別名。
  • 選擇「Zod → JSON Schema」則是反向轉換。就算保留 `import` 行或 `export const user =` 也沒關係,剖析器會取出以 `z.` 開頭的運算式。
  • 不在 `required` 中的屬性會加上 `.optional()`;反向轉換時,沒有 `.optional()` 的屬性則會被收進 `required`。
  • 字串的細節也是雙向對應:`format: "email"` 會變成 `.email()`,`minLength` 會變成 `.min()`。
  • `$ref`、`allOf` 這類無法轉換的內容會以警告顯示在結果下方,不會默默產生壞掉的結果。

FAQ: 常見問題

  • 這和從 JSON 範例產生 Zod 的「JSON to Zod」有什麼不同?

    輸入不同。JSON to Zod 是從 API 回應之類的「值範例」推論型別,因此無法得知哪些欄位是必填、字串的 format 是什麼。本工具以 JSON Schema 本身為輸入,所以 required、enum、minLength、format:email 等限制會直接反映到 Zod 的鏈式呼叫(.optional() / .enum() / .min() / .email())。若您手上已經有 OpenAPI 或 JSON Schema 定義,這條路徑更精確。
  • required 與 .optional() 如何對應?

    兩者的預設值剛好相反。JSON Schema 是「列在 required 陣列中才是必填」,Zod 則是「沒有 .optional() 就是必填」。轉換器會吸收這個差異:轉成 Zod 時,不在 required 中的屬性會加上 .optional();反向轉換時,沒有 .optional() 的屬性會被收進 required 陣列。
  • 使用 $ref 的結構定義可以轉換嗎?

    參照不會被展開,$ref 會變成 z.any() 並顯示警告。如果您的結構把共用定義抽到 $defs,請在貼上前先展開,或在產生後手動修改該處。allOf 同樣會提出警告,因為這裡無法表達交集型別,只會轉換第一個子結構。
  • 產生的 Zod 可以直接用於正式環境的驗證嗎?

    可以當作骨架,但原本就不在 JSON Schema 裡的業務規則(允許的信箱網域、欄位之間的一致性等)不會被產生出來。另外 pattern 會轉成 z.string().regex(),若原本的正規表示式不相容於 ECMAScript,行為可能會不同。產生後請務必確認內容。

使用情境: 主要應用情境

  • 從 OpenAPI 定義產生前端型別與驗證

    OpenAPI 的 components.schemas 就是 JSON Schema,直接貼上即可同時取得 Zod 結構定義與 z.infer 型別,避免伺服器契約與前端驗證逐漸脫節。

  • 把既有的 Zod 結構定義輸出成 API 契約

    如果專案中是先寫 Zod 結構定義,可以用反向轉換產生 JSON Schema,貼進 OpenAPI 的 components 或文件中。

  • 把手寫的驗證改為結構定義驅動

    要取代大量 if 判斷時,只要有既有的 JSON Schema,就能一次產生完整的 Zod 起點,較不會漏掉必填欄位與 enum。

  • 讓 AI 產生的 JSON Schema 真的能用

    把 LLM 產出的 JSON Schema 直接貼上,轉換成能在 TypeScript 中運作的 Zod 結構定義,同時獲得靜態型別與執行期驗證。

注意: 注意事項與限制

  • $ref、allOf 與條件式不會展開

    $ref 不會解析參照,會變成 z.any();allOf 只轉換第一個子結構。if/then/else 與 not 不支援。以上都會在結果下方以警告顯示,請自行補上這些部分。

  • Zod → JSON Schema 是以文字方式剖析程式碼

    為了讓一切在瀏覽器內完成,工具不會執行程式碼,而是當作文字剖析。支援 z.object / z.array / z.union / z.enum / z.literal / z.record 與常見的鏈式方法,但透過變數參照的結構定義,或 .refine() 這類任意函式無法用 JSON Schema 表達,因此會被忽略。

  • pattern 的正規表示式會原樣搬移

    JSON Schema 的 pattern 會轉成 z.string().regex(),反向時其內容會回到 pattern。JSON Schema 也允許不相容於 ECMAScript 的正規表示式,直接搬移可能導致行為改變。

  • 請務必檢查產生的結果

    本工具用來產生移轉的起點。業務規則與欄位之間的一致性檢查,只要原始結構定義中沒有就不會被產生;用於正式環境驗證前請先確認內容。

這個工具的相關文章

Recent Articles

工具介紹
2026-08-06

JSON Schema 與 Zod 雙向轉換的原理|required 與 .optional() 的對應

解析雙向轉換器的實作:把 JSON Schema 轉成 Zod 結構定義,也把 Zod 程式碼轉回 JSON Schema。內容涵蓋 required 與 .optional() 預設值相反的陷阱、限制條件對照表,以及不執行程式碼就完成剖析的做法。

使用案例
2026-08-06

SQL 子句執行順序參考|為什麼 WHERE 看不到 SELECT 的別名

SQL 並不是照您撰寫的順序執行。以邏輯執行順序(FROM → WHERE → GROUP BY → HAVING → SELECT → ORDER BY → LIMIT)為主軸,說明別名為何在 WHERE 無法使用、WHERE 與 HAVING 的分工、ONLY_FULL_GROUP_BY、COUNT(*) 與 COUNT(欄位) 的差異,以及 LEFT JOIN 搭配 WHERE 的陷阱。

使用案例
2026-08-06

unified diff 格式閱讀指南|看懂 git diff 的 @@ 標頭

說明如何閱讀 git 產生的 unified diff 格式:@@ -12,7 +12,9 @@ 四個數字的意義、只改一個字元為何顯示成整行替換、空白與換行字元的陷阱、\ No newline at end of file、合併提交的 @@@ 組合式 diff,以及以 similarity index 推斷檔案更名。

使用案例
2026-08-06

UTC⇄JST 換算參考手冊|9小時時差對照表與時區踩雷指南

以對照表整理 UTC 與日本時間(JST)的換算,並說明與台灣時間(UTC+8)相差 1 小時的關係。內容涵蓋 ISO 8601 的 Z 與 +09:00、JavaScript 日期解析悄悄位移 9 小時的條件、MySQL/PostgreSQL 的時區行為,以及 GitHub Actions cron 一律以 UTC 執行的陷阱。

使用案例
2026-08-04

CREATE TABLE 參考手冊|MySQL、PostgreSQL、SQLite 的型別與約束差異

以跨資料庫對照表整理 CREATE TABLE(DDL)的寫法:型別對應表、自動編號(AUTO_INCREMENT / IDENTITY / rowid)的方言差異、外鍵的 ON DELETE 行為,以及 MySQL 會靜默忽略的 CHECK 約束。

工具介紹
2026-08-03

從資料表設計自動產生 CREATE TABLE 語句的原理|DDL 產生器

解析 DDL 產生器的實作:以視覺化方式設計資料表並產生 CREATE TABLE 語句與 ER 圖。內容涵蓋 MySQL/PostgreSQL/SQLite 的型別轉換規則,以及從 JSON 範例推論欄位的演算法。

廣告

廣告