URL 編碼與解碼

編碼單個值、編碼整條 URL,或反過來解碼。

查詢參數

這個工具能做什麼

URL 只能包含有限的一組 ASCII 字元。其它任何東西——空格、中文、&、=、?、# 和大部分標點——都必須先百分號編碼成 %XX 位元組,才能安全地放進連結、表單提交或 API 呼叫。本頁雙向完成這種編碼,而且不同於多數編碼器,它還會把結果拆開:貼上任意 URL 或查詢字串,參數就會以解碼後的鍵值表呈現,一眼讀懂一條追蹤連結或 OAuth 跳轉。

文字依 UTF-8 處理,所以「中文」會變成 %E4%B8%AD%E6%96%87,與瀏覽器和伺服器的預期完全一致。解碼是寬容的:不構成合法跳脫的孤立 % 會原樣保留而不是拋錯,解碼表單資料時 + 會當作空格。

編碼單一值 vs 編碼整條 URL

「編碼元件」就是 JavaScript 的 encodeURIComponent:除字母、數字和 -_.!~*'() 之外全部跳脫。用於放進查詢參數、路徑段或表單欄位的單一值。「編碼 URL」是 encodeURI:保留結構字元 :/?#[]@!$&'()*+,;= 不動,只跳脫空格和非 ASCII 文字,讓一條完整位址仍是合法位址。用錯是經典 bug——對整條 URL 用 encodeURIComponent 會把每個 / 變成 %2F 從而弄壞連結,而對含 & 的值用 encodeURI 會悄悄把它拆成兩個參數。

「空格用 +」選項在 %20(RFC 3986,URL 中使用)與 +(application/x-www-form-urlencoded,HTML 表單本體和許多舊式查詢串使用)之間切換。兩種在這裡都能正確解碼;編碼時依目標系統的預期選擇。

常見錯誤

重複編碼:對已編碼的值再編碼會把 %20 變成 %2520,伺服器看到的是字面的 %20。如果解碼結果裡還有 %XX 序列,就再解一次。忘記對值裡的 & 或 # 編碼會截斷參數。對整條 URL 用 encodeURIComponent 會破壞協定與斜線。用戶端與伺服器對 + 和 %20 的約定不一致,會讓使用者名稱裡出現加號。最後,百分號編碼不是加密也不是混淆——解碼後完全可讀,絕不要靠它隱藏權杖;需要不透明傳輸時通常用 Base64,但它同樣可以輕易還原。

背景:百分號編碼從哪裡來

百分號編碼隨第一份 URL 規範 RFC 1738(1994,Tim Berners-Lee 等人撰寫)一同定義,並在 RFC 3986(2005)中完善,後者是現行的 URI 語法標準。% 跳脫機制早於 UTF-8 的普及,所以舊系統有時依 Latin-1 或 Shift-JIS 編碼位元組,依 UTF-8 解碼時就會出現亂碼——HTML5 的 URL Standard(WHATWG)最終規定新編碼一律使用 UTF-8。「空格用 +」的約定來自獨立的 HTML 表單規範而非 URL 標準,這就是今天兩種空格編碼並存的歷史原因。

應用領域

手工拼接 API 請求(搜尋詞、篩選條件、回呼位址),除錯廣告平台的追蹤連結(utm_source、gclid、fbclid),閱讀 OAuth 與 SSO 跳轉(redirect_uri、state、scope),建構帶主旨和內文的 mailto: 與 tel: 連結,分享含中文或日文路徑的連結,以及檢查以表單格式傳送的 Webhook 負載。參數表特別適合把工單裡的長 URL 貼進來,看清到底請求了什麼。查詢串裡的值經常是 JSON 或 Base64——先在這裡解碼,再把值貼到對應的工具。

常見問題

encodeURI 和 encodeURIComponent 有什麼差別?

encodeURIComponent 除未保留字元外全部跳脫,用於單一值;encodeURI 保留 URL 結構字元(/ ? & = # :),用於完整位址。絕不要對整條 URL 用 encodeURIComponent。

空格應該是 %20 還是 +?

URL 中用 %20(RFC 3986);+ 只用於 application/x-www-form-urlencoded 表單本體和遵循 HTML 表單約定的查詢串。這裡兩種都解碼為空格。

為什麼解碼結果裡有 %2520?

這個值被編碼了兩次。再解碼一次即可得到原文。

支援中文和 emoji 嗎?

支援。文字依 UTF-8 位元組編碼,每個漢字變成三個 %XX,多數 emoji 變成四個。

會有資料傳送到伺服器嗎?

不會。編碼、解碼和參數解析全部在瀏覽器中完成。