如何用客户端JS压缩数据并在服务端解码?支持哪些压缩格式?
浏览器端数据压缩与服务端JavaScript解码方案
一、浏览器端压缩各类数据并发送至服务端
1. 压缩文本/JSON数据
现代浏览器原生支持CompressionStream API,可直接对文本、JSON进行压缩,步骤如下:
// 压缩JSON数据(支持Gzip/Brotli/Deflate) async function compressJSON(data, format = 'gzip') { const jsonStr = JSON.stringify(data); const uint8Array = new TextEncoder().encode(jsonStr); // 创建压缩流,format可选'gzip'/'br'/'deflate' const compressionStream = new CompressionStream(format); const compressedStream = new Blob([uint8Array]).stream().pipeThrough(compressionStream); return await new Response(compressedStream).blob(); } // 发送压缩后的数据到服务端 async function sendCompressedData(data) { const compressedBlob = await compressJSON(data, 'br'); // 用Brotli压缩 const response = await fetch('/api/decompress', { method: 'POST', headers: { 'Content-Encoding': 'br', // 告知服务端压缩格式 'Content-Type': 'application/json' }, body: compressedBlob }); return await response.json(); }
2. 压缩二进制数据
直接处理Blob/ArrayBuffer类型的二进制数据:
async function compressBinaryData(blob, format = 'deflate') { const compressionStream = new CompressionStream(format); const compressedStream = blob.stream().pipeThrough(compressionStream); return await new Response(compressedStream).blob(); }
二、服务端(Node.js)解码压缩数据
Node.js内置zlib模块,可处理Gzip/Deflate/Brotli格式的解压:
const zlib = require('zlib'); const { pipeline } = require('stream/promises'); const express = require('express'); const app = express(); app.post('/api/decompress', async (req, res) => { try { const encoding = req.headers['content-encoding']; let decompressStream; // 根据请求头选择对应解压流 switch(encoding) { case 'gzip': decompressStream = zlib.createGunzip(); break; case 'deflate': decompressStream = zlib.createInflate(); break; case 'br': decompressStream = zlib.createBrotliDecompress(); break; default: return res.status(400).send('不支持的压缩格式'); } // 流式解压并解析数据 let rawContent = ''; await pipeline(req, decompressStream, async function* (source) { for await (const chunk of source) { rawContent += chunk.toString(); } }); const parsedData = JSON.parse(rawContent); res.json({ success: true, data: parsedData }); } catch (err) { res.status(500).send('解压失败'); } }); app.listen(3000, () => console.log('服务端运行在3000端口'));
三、可用的压缩格式
- Gzip:兼容性最广,所有现代浏览器/服务端均支持,基于Deflate算法,体积适中。
- Deflate:比Gzip少了文件头和校验信息,体积略小,兼容性接近Gzip。
- Brotli:Google推出的高效压缩算法,压缩比高于Gzip,现代浏览器(Chrome 59+/Firefox 55+)和Node.js 11.7+支持,适合对传输体积敏感的场景。
兼容旧浏览器方案:若需支持IE等旧环境,可使用第三方库pako(纯JS实现的Deflate/Gzip压缩),示例:
import pako from 'pako'; function compressWithPako(data) { const jsonStr = JSON.stringify(data); const uint8Array = new TextEncoder().encode(jsonStr); const compressed = pako.gzip(uint8Array); return new Blob([compressed]); }
内容的提问来源于stack exchange,提问作者Mikko Ohtamaa
相关产品推荐
相关产品推荐

