4

我有一个 Windows 8 应用程序连接到用 Node.js 编写的 Web 服务。在 Windows 8 端,我将请求正文压缩为 gzip。但在 Node.js 方面,我发现我的 req.body 类型是Object.

我不能zlib用来解压身体,因为它不是stream.

我可以zlib用来解压缩请求,但我不知道如何req.body从解压缩的流中检索内容并以 JSON 格式解析正文。

顺便说一句,我通过 Fiddler 查看了我的请求,它告诉我请求正文已压缩,解压缩后我可以通过 Fiddler 看到我的原始正文,因此请求应该是正确的。

更新 如下是我的 Node.js 应用程序

(功能 () {
    var express = require("express");
    var zlib = 要求(“zlib”);

    var app = express();
    变量端口 = 12345;

    应用程序配置(功能(){
        app.use(express.compress());
        app.use(express.bodyParser());
    });

    app.post("/test", function (req, res) {
        var request = req.body;
        req.pipe(zlib.createGunzip());

        变量响应 = {
            状态:0,
            值:“确定”
        };
        res.send(200, 响应);
    });

    console.log("从端口 %d 开始", port);
    app.listen(端口);
})();

以下是我的 Windows 商店应用程序代码(部分)

        私有异步无效按钮1_Click_1(对象发送者,RoutedEventArgs e)
        {
            var 消息 = 新
            {
                名称=“肖恩”,
                值 = "12345678901234567890123456789012345678901234567890"
            };
            var json = 等待 JsonConvert.SerializeObjectAsync(消息, Formatting.Indented);
            var bytes = Encoding.UTF8.GetBytes(json);

            var client = new HttpClient();
            client.BaseAddress = new Uri("http://192.168.56.1:12345/");
            client.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));
            client.DefaultRequestHeaders.ExpectContinue = false;
            var jsonContent = new JsonContent(message);
            var gzipContent = new GZipContent3(jsonContent);
            var res = await client.PostAsync("test", gzipContent);

            var dialog = new Windows.UI.Popups.MessageDialog(":)", "完成");
            等待对话框.ShowAsync();
        }


        内部类 GZipContent3 : ByteArrayContent
        {
            公共 GZipContent3(HttpContent 内容)
                :基础(加载GZipBytes(内容))
            {
                //base.Headers.ContentType = content.Headers.ContentType;
                base.Headers.ContentType = new MediaTypeHeaderValue("x-application/x-gzip");
                base.Headers.ContentEncoding.Add("gzip");
            }

            私有静态字节[] LoadGZipBytes(HttpContent 内容)
            {
                var source = content.ReadAsByteArrayAsync().Result;
                字节[] 缓冲区;
                使用 (var outStream = new MemoryStream())
                {
                    使用 (var gzip = new GZipStream(outStream, CompressionMode.Compress, true))
                    {
                        gzip.Write(source, 0, source.Length);
                    }
                    缓冲区 = outStream.ToArray();
                }
                返回缓冲区;
            }
        }


        内部类 JsonContent : StringContent
        {
            私有常量字符串 defaultMediaType = "application/json";

            公共 JsonContent(字符串 json)
                :基础(json)
            {
                var mediaTypeHeaderValue = new MediaTypeHeaderValue(defaultMediaType);
                mediaTypeHeaderValue.CharSet = Encoding.UTF8.WebName;
                base.Headers.ContentType = mediaTypeHeaderValue;
            }

            公共 JsonContent(对象内容)
                :这个(GetJson(内容))
            {
            }

            私有静态字符串 GetJson(对象内容)
            {
                如果(内容 == 空)
                {
                    抛出新的 ArgumentNullException(“内容”);
                }
                var json = JsonConvert.SerializeObject(内容, Formatting.Indented);
                返回 json;
            }
        }
4

2 回答 2

1

http://www.senchalabs.org/connect/json.html。基本上,您需要基于connect.json()该管道通过解压缩流编写自己的中间件,connect.compress()但方向相反:http ://www.senchalabs.org/connect/compress.html

此外,请确保您Content-Encoding在请求中发送正确的标头。

如果你告诉我你到目前为止有什么,我可以进一步帮助你。

于 2013-01-16T07:43:27.517 回答
1

我正在做类似的事情并最终登陆

function getGZipped(req, callback) {
    var gunzip = zlib.createGunzip();
    req.pipe(gunzip);

    var buffer  = [];
    gunzip.on('data', function (data) {
        // decompression chunk ready, add it to the buffer
        buffer.push(data);
    }).on('end', function () {
        //response and decompression complete, join the buffer and return
        callback(null, JSON.parse(buffer));
    }).on('error', function (e) {
        callback(e);
    });
}
于 2015-09-15T20:04:18.410 回答