JS 可否使用字符串传输文件?

作者站长头像
站长
· 阅读数 6

在一个场景中,数据只能通过字符串传输,需要传文件或二进制对象时就比较麻烦。目前使用将文件编码为base64传输,但是这种方式会时传输的数据增大(50K的文件编码后为80K)。测试使用浏览器的TextDecoder将文件编码为iso-8859-1,可以保持编码后字符串的大小和原文件一样,但是再转回文件时就转不回来了(TextEncoder只支持utf-8)编码:

new TextDecoder('iso8859-1').decode(file);

====更新=====现通过以下方式解码,但是zip压缩包会出现乱码

let buffer = new ArrayBuffer(textData.length);
let arr = new Uint8Array(buffer);
for(let i = 0; i < textData.length; i++){
    arr[i] = textData.charCodeAt(i);
}

JS 可否使用字符串传输文件?

请问是否还有其他方式可以实现?

回复
1个回答
avatar
test
2024-06-27

用Blob对象:

function stringToBlob(str, contentType) {
  return new Blob([new Uint8Array([...str].map(ch => ch.charCodeAt(0)))], { type: contentType });
}

const blob = stringToBlob(textData, 'application/zip');
const url = URL.createObjectURL(blob);

用ArrayBuffer和DataView来控制二进制数据的读写:

function stringToArrayBuffer(str) {
  const buffer = new ArrayBuffer(str.length);
  const view = new DataView(buffer);
  for (let i = 0; i < str.length; i++) {
    view.setUint8(i, str.charCodeAt(i));
  }
  return buffer;
}

const buffer = stringToArrayBuffer(textData);

修复ISO-8859-1编码:

function encodeIso8859_1(arrayBuffer) {
  const uint8Array = new Uint8Array(arrayBuffer);
  return String.fromCharCode(...uint8Array);
}

function decodeIso8859_1(str) {
  const uint8Array = new Uint8Array(str.length);
  for (let i = 0; i < str.length; i++) {
    uint8Array[i] = str.charCodeAt(i);
  }
  return uint8Array.buffer;
}
回复
likes
适合作为回答的
  • 经过验证的有效解决办法
  • 自己的经验指引,对解决问题有帮助
  • 遵循 Markdown 语法排版,代码语义正确
不该作为回答的
  • 询问内容细节或回复楼层
  • 与题目无关的内容
  • “赞”“顶”“同问”“看手册”“解决了没”等毫无意义的内容