首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >解压缩Gzip数据格式的客户端JavaScript问题( webSocket )

解压缩Gzip数据格式的客户端JavaScript问题( webSocket )
EN

Stack Overflow用户
提问于 2020-12-27 22:55:42
回答 2查看 722关注 0票数 0

我有一个通过WebSocket发送数据的服务,但是数据是gzipped的。当我试图不压缩Blob数据时,我遇到了一个问题。我使用的包佛莱特gzip-js帕科zlib都有不同的错误,但是当我为节点js和Package节点-gzip编写代码时,有趣的是,它使用了zlib包,上面提到的一切都很好,而且数据将被删除。

Client.js (问题是unGzip数据)

代码语言:javascript
运行
复制
let ws = new WebSocket('wss://api.huobi.pro/ws');

var zlib = require('zlib');;

let zip = {
    gzip: function gzip(input, options) {
        return new Promise(function (resolve, reject) {
            zlib.gzip(input, options, function (error, result) {
                if (!error) resolve(result); else reject(Error(error));
            });
        });
    },
    ungzip: function ungzip(input, options) {
        return new Promise(function (resolve, reject) {
            zlib.gunzip(input, options, function (error, result) {
                if (!error) resolve(result); else reject(Error(error));
            });
        });
    }
};

ws.onopen = ( function () {
    ws.send(`{
                "sub": "market.ethbtc.kline.1min",
                "id": "id1"
            }`);
});

ws.onmessage = async function (event) {
    console.log(await zip.ungzip(event.data));
};

错误:默认错误: TypeError:无效的非字符串/缓冲区块

Node.js工作

代码语言:javascript
运行
复制
const {ungzip} = require('node-gzip');

ws = new WebSocket('wss://api.huobi.pro/ws');
    
    ws.on('open', function () {
            ws.send('{
                "sub": "market.ethbtc.kline.1min",
                "id": "id1"
            }');
        });
    
     ws.on('message', function (data) {
            ungzip(data).then((r) => {
                let data = JSON.parse(r.toString());
                console.log(data); 
            }).catch(console.error)
        }); 

在浏览器中,event.data是Blob数据,当我在它们上使用text方法时,有一些简单的代码,上面的大多数库和包都说数据头是未知的。

但是,为什么相同的数据点具有相同的结构,一个在node.js上工作,另一个在浏览器中不工作

请帮我解压缩数据

在上面的unGziped代码中使用Node.js后的响应数据示例,我希望在我的Client.js中使用相同的响应数据

代码语言:javascript
运行
复制
{
  "ch": "market.ethbtc.kline.1min",
  "ts": 1489474082831, //system update time
  "tick": {
    "id": 1489464480,
    "amount": 0.0,
    "count": 0,
    "open": 7962.62,
    "close": 7962.62,
    "low": 7962.62,
    "high": 7962.62,
    "vol": 0.0
  }
}
EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2020-12-28 04:41:39

如果您console.log event.data的值,您将看到它实际上是一个Blob。您不能直接使用它,而是必须转换为Uint8Array

我还注意到端点返回gzipped,所以我也将解析它。

我的解决方案:

代码语言:javascript
运行
复制
import { gunzip, strFromU8 } from 'fflate'; 
// If you can't use ES Modules:
// const { gunzip, strFromU8 } = require('fflate');
const ws = new WebSocket('wss://api.huobi.pro/ws');
ws.onopen = function() {
  ws.send(JSON.stringify({
    sub: 'market.ethbtc.kline.1min',
    id: 'id1'
  }));
}
ws.onmessage = function(event) {
  const fr = new FileReader();
  fr.onload = function() {
    gunzip(
      new Uint8Array(fr.result),
      function(err, raw) {
        if (err) {
          console.error(err);
          return;
        }
        const data = JSON.parse(strFromU8(raw));
        // Use the data variable however you wish
      }
    );
  }
  fr.readAsArrayBuffer(event.data);
}
票数 1
EN

Stack Overflow用户

发布于 2020-12-27 23:01:21

无论使用哪种模式,这两个例子之间都有明显的区别。

如果这样做不起作用(因为它试图立即访问,而无需等待承诺):

代码语言:javascript
运行
复制
ws.onmessage = function (event) {
    console.log(gzip.unzip(event.data));
}

只需以与工作版本相同的方式访问它:

代码语言:javascript
运行
复制
ws.onmessage = function (data) {
    gzip.unzip(data)
    .then((result) => {
        let data = JSON.parse(result.toString());
        console.log(data); 
    })
    .catch(console.error)
}

gzip.unzipungzip可能都会兑现承诺。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/65471252

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档