Window: btoa() 方法
Window 介面的 btoa() 方法從一個二進位制字串(即,字串中的每個字元都被視為二進位制資料的一個位元組)建立一個 Base64 編碼的 ASCII 字串。
你可以使用此方法編碼可能導致通訊問題的資料,傳輸資料,然後使用 Window.atob() 方法再次解碼資料。例如,你可以編碼控制字元,例如 ASCII 值 0 到 31。
如果你的資料在一個 Uint8Array 物件中,也請考慮使用 Uint8Array.prototype.toBase64() 方法,以避免建立包含原始位元組的字串。
語法
btoa(stringToEncode)
引數
stringToEncode-
要編碼的二進位制字串。JavaScript 中的字串編碼為 UTF-16,因此這意味著每個字元的程式碼點必須小於 256,表示一個位元組的資料。
返回值
一個包含 stringToEncode 的 Base64 表示的 ASCII 字串。
異常
InvalidCharacterErrorDOMException-
字串中包含的字元不適合單個位元組。有關更多詳細資訊,請參閱下面的“Unicode 字串”。
示例
const encodedData = window.btoa("Hello, world"); // encode a string
const decodedData = window.atob(encodedData); // decode the string
Unicode 字串
Base64,顧名思義,需要二進位制資料作為輸入。就 JavaScript 字串而言,這意味著字串中每個字元的程式碼點只佔用一個位元組。因此,如果你將一個包含佔用多個位元組的字元的字串傳遞給 btoa(),你將收到一個錯誤,因為這不被視為二進位制資料。
const ok = "a";
console.log(ok.codePointAt(0).toString(16)); // 61: occupies < 1 byte
const notOK = "✓";
console.log(notOK.codePointAt(0).toString(16)); // 2713: occupies > 1 byte
console.log(window.btoa(ok)); // YQ==
console.log(window.btoa(notOK)); // error
由於 btoa 將其輸入字串的程式碼點解釋為位元組值,因此如果字元的程式碼點超過 0xff,在字串上呼叫 btoa 將導致“字元超出範圍”異常。對於需要編碼任意 Unicode 文字的用例,需要先將字串轉換為其組成位元組的 UTF-8,然後編碼這些位元組。
最簡單的解決方案是使用 TextEncoder 和 TextDecoder 在 UTF-8 和字串的單位元組表示之間進行轉換。
function base64ToBytes(base64) {
const binString = atob(base64);
return Uint8Array.from(binString, (m) => m.codePointAt(0));
}
function bytesToBase64(bytes) {
const binString = Array.from(bytes, (byte) =>
String.fromCodePoint(byte),
).join("");
return btoa(binString);
}
// Usage
bytesToBase64(new TextEncoder().encode("a Ā 𐀀 文 🦄")); // "YSDEgCDwkICAIOaWhyDwn6aE"
new TextDecoder().decode(base64ToBytes("YSDEgCDwkICAIOaWhyDwn6aE")); // "a Ā 𐀀 文 🦄"
轉換任意二進位制資料
上一節中的 bytesToBase64 和 base64ToBytes 函式可以直接用於在 Base64 字串和 Uint8Array 之間進行轉換。
為了獲得更好的效能,透過 FileReader 和 fetch API,可以在 Web 平臺中本地實現 Base64 資料 URL 之間的非同步轉換。
async function bytesToBase64DataUrl(bytes, type = "application/octet-stream") {
return await new Promise((resolve, reject) => {
const reader = Object.assign(new FileReader(), {
onload: () => resolve(reader.result),
onerror: () => reject(reader.error),
});
reader.readAsDataURL(new File([bytes], "", { type }));
});
}
async function dataUrlToBytes(dataUrl) {
const res = await fetch(dataUrl);
return new Uint8Array(await res.arrayBuffer());
}
// Usage
await bytesToBase64DataUrl(new Uint8Array([0, 1, 2])); // "data:application/octet-stream;base64,AAEC"
await dataUrlToBytes("data:application/octet-stream;base64,AAEC"); // Uint8Array [0, 1, 2]
注意:對於支援環境,也請考慮原生的 Uint8Array.fromBase64()、Uint8Array.prototype.toBase64() 和 Uint8Array.prototype.setFromBase64() 方法。
規範
| 規範 |
|---|
| HTML # dom-btoa-dev |
瀏覽器相容性
載入中…
另見
btoa的 polyfill 在core-js中可用。dataURLWorkerGlobalScope.btoa():相同的方法,但在 Worker 作用域中。Window.atob()Uint8Array.prototype.toBase64()- Base64