首頁  >  文章  >  web前端  >  如何使用「atob」在 JavaScript 中解碼 UTF-8 base64 字串,同時避免編碼錯誤?

如何使用「atob」在 JavaScript 中解碼 UTF-8 base64 字串,同時避免編碼錯誤?

Mary-Kate Olsen
Mary-Kate Olsen原創
2024-10-31 21:08:291000瀏覽

How do you decode UTF-8 base64 strings in JavaScript using `atob` while avoiding encoding errors?

使用atob 從常見文字來源解碼base64

使用atob 解碼來自以UTF-8 產生輸出的服務的API 回應字串時,您可能會遇到錯誤或損壞的字串編碼。這是由於JavaScript 的base64 處理的限制:

<code class="js">const notOK = "✓"
console.log(btoa(notOK)); // error</code>

Unicode 問題

即使在ECMAScript 中解決了此錯誤,「Unicode 問題」仍然存在,因為base64 是二進位檔案假設每個編碼字元佔用一個位元組的格式。許多 Unicode 字元需要多個位元組進行編碼,這可能會導致編碼失敗。

來源:MDN (2021)

<code class="js">const ok = "a";
console.log(ok.codePointAt(0).toString(16)); // 0x61: occupies 1 byte

const notOK = "✓";
console.log(notOK.codePointAt(0).toString(16)); // 0x2713: occupies 2 bytes</code>

二元互通性的解決方案

如果您不確定選擇哪種解決方案,這可能就是您想要的。繼續捲動以查看 ASCII base64 解決方案以及此答案的歷史記錄。

考慮使用二進位方法,將 UTF-8 字串轉換為二進位表示形式,反之亦然。

編碼UTF-8 ⇢ 二進位

<code class="js">function toBinary(string) {
  const codeUnits = new Uint16Array(string.length);
  for (let i = 0; i < codeUnits.length; i++) {
    codeUnits[i] = string.charCodeAt(i);
  }
  return btoa(String.fromCharCode(...new Uint8Array(codeUnits.buffer)));
}
encoded = toBinary("✓ à la mode") // "EycgAOAAIABsAGEAIABtAG8AZABlAA=="</code>

解碼二進位⇢ UTF-8

<code class="js">function fromBinary(encoded) {
  const binary = atob(encoded);
  const bytes = new Uint8Array(binary.length);
  for (let i = 0; i < bytes.length; i++) {
    bytes[i] = binary.charCodeAt(i);
  }
  return String.fromCharCode(...new Uint16Array(bytes.buffer));
}
decoded = fromBinary(encoded) // "✓ à la mode"</code>

具有ASCII base64 互通性的解決方案要保留UTF-8 功能,另一種方法是透過建議使用ASCII base64 互通性,這可以修正“Unicode 問題”,同時保持與基於文字的base64 字串的兼容性。

編碼UTF-8 ⇢ ASCII base64

解碼ASCII base64 ⇢ UTF -8
<code class="js">function b64EncodeUnicode(str) {
    // Percent-encode Unicode, then convert to byte array
    return btoa(encodeURIComponent(str).replace(/%([0-9A-F]{2})/g,
        function(match, p1) {
            return String.fromCharCode('0x' + p1);
    }));
}
b64EncodeUnicode('✓ à la mode'); // "4pyTIMOgIGxhIG1vZGU="</code>

TypeScript 支援function b64DecodeUnicode(str) { // Convert byte array to percent-encoding, then decode return decodeURIComponent(atob(str).split('').map(function(c) { return '%' + ('00' + c.charCodeAt(0).toString(16)).slice(-2); }).join('')); } b64DecodeUnicode('4pyTIMOgIGxhIG1vZGU='); // "✓ à la mode"<h3></h3>從GitHub API 等來源解碼base64 字串可能需要刪除空格Safari。 <pre class="brush:php;toolbar:false">&lt;code class=&quot;ts&quot;&gt;function b64EncodeUnicode(str) { return btoa(encodeURIComponent(str).replace(/%([0-9A-F]{2})/g, function(match, p1) { return String.fromCharCode(parseInt(p1, 16)) })) } function b64DecodeUnicode(str) { return decodeURIComponent(Array.prototype.map.call(atob(str), function(c) { return '%' + ('00' + c.charCodeAt(0).toString(16)).slice(-2) }).join('')) }&lt;/code&gt;</pre> <h3>js-base64 和 base64-js 等函式庫也提供了可靠的解決方案。 </h3> <ul></ul>

以上是如何使用「atob」在 JavaScript 中解碼 UTF-8 base64 字串,同時避免編碼錯誤?的詳細內容。更多資訊請關注PHP中文網其他相關文章!

陳述:
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn