# JSON 格式化 — 排好它、壓扁它，或者轉換它

JSON、XML、HTML、CSS 和 YAML，格式化或轉換。沒有一個字被貼進別人的伺服器。

> 格式化和壓縮 JSON、XML、HTML、CSS 和 YAML，把 JSON 轉成 YAML 或 XML 再轉回來。解析器在你的瀏覽器裡跑，什麼都不上傳——token 和配置檔案從不離開你的機器。

本頁是一個完全在你的瀏覽器裡執行的互動式工具，地址是 https://abox.tools/zh-TW/json-formatter/。你交給它的任何內容都不會被上傳。下面是這個頁面用文字對該工具的全部說明；要使用它，請開啟這個地址。

## 你的文字和程式碼**不會上傳**。這裡根本沒有伺服器。

格式化和轉換都是對一串字元做算術，就在這個頁面裡做完。解析器是手寫的，都在 `src/` 裡：`shared/parse-json.js`、`shared/parse-xml.js`、`css.js`、`shared/parse-yaml.js`；此外別無他物。這個工具沒有任何形式的網路功能，沒有什麼可取，也沒有什麼可發。這一點在本站幾乎別處都不如在這裡要緊：人們往格式化器裡貼的，是訪問令牌、會話 cookie、客戶記錄，還有尚未釋出的程式碼。

- ✗ 不上傳
- ✗ 不註冊
- ✗ 無大小限制
- ✓ 斷網可用
- ✓ 開源

## 怎樣在不上傳的前提下格式化或轉換 JSON

1. **選好要做的事。** 兩個分頁，一個輸入框：「格式化」把 JSON、XML、HTML、CSS 和 YAML 排好或壓扁；「轉換」把 JSON 變成 YAML 或 XML，再變回來。你剛格式化完的文字就是你要轉換的文字，不用貼第二遍。
2. **貼進來，或者把檔案拖進來。** 凡是你能選中並複製的都行。拖到選擇框上的檔案由你自己的瀏覽器讀進輸入框：這裡根本沒有可省略的上傳步驟。
3. **讓它自己判斷語言，或者直接告訴它。** 選單裡寫著它把這段文字當成了什麼，改正只要一次點選。判斷只是個起點，所以它被擺出來，而不是悄悄套用。
4. **選好縮排，或者乾脆壓平。** 兩個空格、四個空格，或者一個製表符。壓平就是同一份文件，只是把純粹為了閱讀才存在的空白都去掉，結果裡會寫明這樣省下了多少位元組。
5. **在出錯的地方讀錯誤。** 這裡的解析器失敗時，會說它看到了什麼，以及在第幾行第幾列，而不是「位置 4193 處有意外的 token」。通常這就足夠把一份配置檔案改對，不用再開啟別的東西。
6. **把結果帶走。** 複製它，或者下載成檔案，檔名跟著輸出語言走。

## 說得更細的版本

[怎麼不把 JSON 交給任何人也能格式化](https://abox.tools/zh-TW/guides/format-json-without-uploading-it/): 在自己的瀏覽器裡排版、檢查和壓縮 JSON：一個格式化工具絕不該改動你檔案的哪些地方、錯誤資訊該怎麼讀，以及你把東西貼進哪個框裡為什麼要緊。

## 工具箱裡還有

- [YAML 轉 JSON](https://abox.tools/zh-TW/yaml-to-json/): 兩個方向都有，而且會告訴你各自的代價。這些都不會貼進別人的伺服器。
- [XML 格式化](https://abox.tools/zh-TW/xml-formatter/): 排開了好讀的 XML，壓平了好發的 XML，還有兩個方向的 JSON 轉換。這些都不會貼進別人的伺服器。
- [文字比對](https://abox.tools/zh-TW/text-diff/): 兩段文字進來，每處差異都被標出來，逐行、逐詞。沒有一個字被貼進別人的伺服器。
- [Base64 編碼解碼](https://abox.tools/zh-TW/base64/): Base64、百分號編碼、HTML 實體、十六進位和反斜槓轉義，雙向都行。沒有一個字被貼進別人的伺服器。

## 常見問題

### 我的文字會被傳到哪裡去嗎？

不會。這個頁面上的每個解析器和寫出器，都是在你自己的瀏覽器裡、你自己的硬體上執行的函式。這個工具沒有任何形式的網路功能：它從不去取什麼，也從不發出什麼；頁面的 `Content-Security-Policy` 裡寫著它允許聯絡的每一個地址，沒有一個屬於本站。這正是拿它來處理訪問令牌、會話 cookie 或客戶記錄的理由：把這類東西貼進別人的格式化器，等於把它交給了對方。

### 格式化 JSON 除了排版之外還會改動什麼嗎？

不會，而這比聽起來難。鍵會保持你寫的順序：建在 `JSON.parse` 上的格式化器會悄悄把像整數的鍵挪到前面，於是 `{"10":a,"2":b}` 回來就成了 `{"2":b,"10":a}`。數字會保留你敲的那些位，所以二十位的 id 不會把最後三位丟給雙精度，`1e999` 也不會變成 `null`。重複的鍵兩個都留著，因為標準並沒說哪個勝出，丟掉一個就是替你做決定。

### 它能格式化哪些語言？

JSON、XML、HTML、CSS 和 YAML。JSON、XML、HTML 和 CSS 還能壓平；YAML 不行，因為它的短寫法是流式風格，那是讀不下去的，而讀不下去恰恰是把檔案留在 YAML 的理由的反面。JavaScript 是有意不在名單上的，見下面那條問題。

### 為什麼它不格式化 JavaScript、Python 或 SQL？

因為要排開一門程式語言，就得把它真正解析明白，而一個差不多對的格式化器比沒有還糟：它產出的程式碼看起來沒問題，做的卻是另一回事。JSON、XML、CSS 和 YAML 的文法小到可以手讀，也能用你自己跑得動的測試查清楚。JavaScript 的格式化器叫 Prettier，那是整整 1 MB 的解析器，它該待在你的編輯器裡，而不是一個網頁上。

### 我的 YAML 寫的是 no，轉成 JSON 卻成了字串。為什麼？

因為它本來就是字串，而這裡讀的是 YAML 1.2，不是 1.1。在 YAML 1.1 裡，`yes`、`no`、`on` 和 `off` 是布林值，這就是那個把挪威的國家程式碼變成 `false` 的著名毛病。YAML 1.2 把它去掉了，這個工具也一樣：只有 `true`、`false`、`null` 和 `~` 會被讀成文字之外的東西。反過來寫出去時，這些詞會*加上引號*，儘管這裡不加引號也照樣讀成文字——因為下一個開啟這個檔案的東西未必如此。PyYAML 至今預設還是 1.1。讀得嚴、寫得穩，是唯一在兩個方向上都不出錯的組合。

### 把 YAML 轉成 JSON 會丟什麼？

註釋，因為 JSON 沒地方放。錨點、別名和標籤會被直接拒絕，而不是替你猜：它們每一個說的都是 JSON 說不出來的事，而一個悄悄挑了個解釋的轉換器，交給你的將是一份並非原文所說的文件。反方向不丟任何東西：每一份 JSON 文件本來就已經是一份 YAML 文件。

### 把 JSON 轉成 XML 會丟什麼？

空物件、空陣列和空字串之間的區別，它們都會變成一個空元素；還有每個值的類型，因為 XML 沒有類型——這也是為什麼反向轉換會把一切都留成字串，而不是斷定 `8080` 是個數字。陣列會變成重複出現的元素，因為只有這種形狀讀得回來；而元素名承載不了的鍵，會把不便的字元替換掉，而不是吐出一份沒有解析器讀得動的文件。

### 重新縮排 HTML 會改變頁面的樣子嗎？

可能會，這一點這裡說得很老實。兩個行內元素之間的空白，就是兩個詞之間的一個空格，挪動它並不免費。有兩件事把這個風險摁住：`<pre>` 和 `<textarea>` 原樣照抄，而一個只裝著文字的元素會留在一行上。其餘的才會被排開。

### 它能處理多大的檔案？

這裡沒有設上限，因為沒有哪臺伺服器在為上限掏錢。真正的天花板是你自己的機器：幾 MB 的 JSON 沒問題；文件特別長的時候，頁面會等你敲字停一下再重新排版，而不是跟你搶鍵盤。

### 它免費嗎，需要註冊嗎？

免費，沒有帳號，不用登入，沒有試用期，貼多少也沒有上限。本站帶廣告，經費就是從那裡來的，廣告拿不到任何關於你文字的資訊。

### 斷網能用嗎？

能。頁面載入一次之後斷開網路，它照樣運作。這也是證明「什麼都沒上傳」最省事的辦法，真要把你的文字送出去格式化，拔線那一刻就停了。

## 這條隱私承諾怎麼核實

- **你貼進來的東西沒有出去的路。** Content-Security-Policy 裡寫著這個頁面允許聯絡的每一個地址，沒有一個屬於本站。這裡沒有任何可以收走一個貼進來的 token 的接收端，就算有，程式碼裡也沒有把它送過去的東西。
- **這裡不會去取任何東西。** 整個 `src/` 裡沒有 `fetch`，沒有 `XMLHttpRequest`，也沒有 `sendBeacon`。每個解析器和每個寫出器，都是這個頁面裡接收一串字元、返回一串字元的函式。
- **格式化器會原樣保留交給它的東西。** 一個 JSON 物件回來時，鍵還是你寫的順序，數字還是你寫的那些位，因為 `src/shared/parse-json.js` 是一個解析器，而不是對 `JSON.parse` 的呼叫——後者會把像整數的鍵挪到前面，還會把二十位的 id 變成最接近的雙精度。`tests/js/text-format.test.js` 裡的測試查的正是這些。
- **Google 載入了什麼，又拿不到什麼。** 廣告指令碼和統計指令碼來自 Google，捐助按鈕來自 Buy Me a Coffee。你的文字，一個字元也沒有交給它們。讀取、解析、寫出文字的每一行程式碼都由這個源提供，也都擺在儲存庫裡。
- **斷網也照樣能用。** 斷開網路，這個工具跟原來一模一樣，因為它裡面從來就沒有聯網這一步。這是最省事的一條證明。

**你可以自己核對。**上面這些不用你信。這個頁面是儲存庫裡的模板和配置產生出來的，構建指令碼你能讀，也能自己跑一遍，跑出來的結果就提交在 `dist` 分支上。拿實際發給你的內容，跟你自己從原始碼構建出來的結果對一遍就知道了： https://github.com/A-Box-of-Tools/website

最值得先讀的幾個檔案：`config/site.toml` 裡是 Content-Security-Policy，`src/shared/parse-json.js` 是那個會按你寫的順序保留鍵的解析器；至於為什麼一次轉換就是一個解析器加一個寫出器、中間沒有任何同時懂兩種格式的東西，看 `src/convert.js`。
