147 votes

Comment convertir un tableau uint8 en chaîne codée base64 ?

J'ai une communication webSocket, je reçois une chaîne encodée en base64, je la convertis en uint8 et je travaille dessus, mais maintenant j'ai besoin de la renvoyer, j'ai le tableau uint8, et j'ai besoin de le convertir en chaîne base64, pour pouvoir l'envoyer. Comment puis-je faire cette conversion ?

23voto

Rohit Sengar Points 198
function Uint8ToBase64(u8Arr){
  var CHUNK_SIZE = 0x8000; //arbitrary number
  var index = 0;
  var length = u8Arr.length;
  var result = '';
  var slice;
  while (index < length) {
    slice = u8Arr.subarray(index, Math.min(index + CHUNK_SIZE, length)); 
    result += String.fromCharCode.apply(null, slice);
    index += CHUNK_SIZE;
  }
  return btoa(result);
}

Vous pouvez utiliser cette fonction si vous avez un très grand Uint8Array. Ceci est pour Javascript, peut être utile dans le cas de FileReader readAsArrayBuffer.

7voto

Kamil Kiełczewski Points 6496

JS pur - sans corde middlestep (sans btoa)

Dans la solution ci-dessous, j'ai omis la conversion en chaîne. L'IDEA est le suivant :

  • joindre 3 octets (3 éléments du tableau) et vous obtenez 24 bits
  • diviser 24bits en quatre nombres de 6 bits (qui prennent des valeurs de 0 à 63)
  • utiliser ces chiffres comme index dans l'alphabet base64
  • cas particulier : lorsque le tableau d'octets d'entrée la longueur n'est pas divisée par 3, il faut ajouter = o == au résultat

La solution ci-dessous fonctionne sur des morceaux de 3 octets, elle est donc adaptée aux grands tableaux. Solution similaire pour convertir base64 en tableau binaire (sans atob ) est ICI

function bytesArrToBase64(arr) {
  const abc = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"; // base64 alphabet
  const bin = n => n.toString(2).padStart(8,0); // convert num to 8-bit binary string
  const l = arr.length
  let result = '';

  for(let i=0; i<=(l-1)/3; i++) {
    let c1 = i*3+1>=l; // case when "=" is on end
    let c2 = i*3+2>=l; // case when "=" is on end
    let chunk = bin(arr[3*i]) + bin(c1? 0:arr[3*i+1]) + bin(c2? 0:arr[3*i+2]);
    let r = chunk.match(/.{1,6}/g).map((x,j)=> j==3&&c2 ? '=' :(j==2&&c1 ? '=':abc[+('0b'+x)]));  
    result += r.join('');
  }

  return result;
}

// ----------
// TEST
// ----------

let test = "Alice's Adventure in Wondeland.";
let testBytes = [...test].map(c=> c.charCodeAt(0) );

console.log('test string:', test);
console.log('bytes:', JSON.stringify(testBytes));
console.log('btoa            ', btoa(test));
console.log('bytesArrToBase64', bytesArrToBase64(testBytes));

3voto

KARTHIKEYAN.A Points 4408

Utilisez ce qui suit pour convertir un tableau uint8 en chaîne codée en base64

function arrayBufferToBase64(buffer) {
            var binary = '';
            var bytes = [].slice.call(new Uint8Array(buffer));
            bytes.forEach((b) => binary += String.fromCharCode(b));
            return window.btoa(binary);
        };

1voto

Richie Bendall Points 1694

Depuis btoa ne fonctionne qu'avec les chaînes de caractères, nous pouvons transformer les Uint8Array en chaînes de caractères avec String.fromCharCode :

const toBase64 = uInt8Array => btoa(String.fromCharCode(...uInt8Array));

0voto

Tate Thurston Points 327

La documentation de MDN bien couvrir btoa.

Puisque vous disposez déjà de données binaires, vous pouvez convertir votre Uint8Array en chaîne de caractères ASCII et invoquer l'opération suivante btoa sur cette chaîne.

function encodeBase64Bytes(bytes: Uint8Array): string {
  return btoa(
    bytes.reduce((acc, current) => acc + String.fromCharCode(current), "")
  );
}

Complexité avec btoa se présente lorsque vous devez encoder des chaînes JS arbitraires, qui peuvent occuper plus d'un seul octet, telles que "

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X