【问题标题】:Google App Engine - how to gzip requests correctlyGoogle App Engine - 如何正确压缩请求
【发布时间】:2018-01-19 15:06:39
【问题描述】:

在我的 Google App Engine 应用程序(标准环境,用 Java + Scala 编写)中,我希望对服务器的一些请求进行 gzip 压缩。经过一番试验,我得到了它的大部分工作,但有几点我不确定。我没有找到太多关于正确使用客户端 gzip 的文档,大多数文档和示例似乎都关心服务器对其响应的编码,因此我不确定我是否按照我应该做的一切。

我以这种方式发送请求(在客户端应用程序中使用 akka.http):

        val uploadReq = Http().singleRequest(
          HttpRequest(
            uri = "https://xxx.appspot.com/upload-a-file",
            method = HttpMethods.POST,
            headers = List(headers.`Content-Encoding`(HttpEncodings.gzip)) 
            entity = HttpEntity(ContentTypes.`text/plain(UTF-8)`,  Gzip.encode(ByteString(bytes)))
          )
        )

在生产 GAE 服务器上,我得到已解码的 gzip 请求正文,编码标头仍然存在。在开发服务器上这是不同的,标头也存在,但请求正文仍然是 gzip 压缩的。

解码请求输入流的代码不是问题,但我没有找到一个干净的方法来检查我的服务器代码是否应该解码请求正文。我目前的解决方法是,如果客户端知道它正在与开发服务器通信,它根本不使用 gzip 编码,而且我从不尝试解码请求正文,因为我依靠 Google App Engine 为我做这件事。

  • 我应该在客户端对请求正文进行不同的编码吗?
  • 是否有其他方法可以在服务器上识别传入的请求正文是否需要解码?
  • 我可以假设 Google App Engine 生产服务器会为我解码正文吗?

【问题讨论】:

  • Try on prod,当 dev server 和 prod 有区别的时候,相信 prod,这就是真相的来源。我记得有一次深入研究并注意到开发服务器的行为不同(确认这是谷歌支持的错误)
  • Google 文档 App Engine 的“问题”与从未弄乱内容一样,这也不是我们在实践中看到的。具体来说:cloud.google.com/appengine/docs/standard/go/…

标签: http google-app-engine http-post gzip


【解决方案1】:

记录一下:我最终得到的解决方案是检查请求正文,如果它看起来像 gzip 压缩,我将其解压缩,完全忽略标题。这适用于 prod(App Engine 进行解压缩并且代码不会造成伤害)和 dev(代码解压缩的地方)。 Scala 代码如下:

def decompressStream(input: InputStream): InputStream = {
  val pushbackInputStream = new PushbackInputStream(input, 2)
  val signature = new Array[Byte](2)
  pushbackInputStream.read(signature)
  pushbackInputStream.unread(signature)
  if (signature(0) == 0x1f.toByte && signature(1) == 0x8b.toByte) {
    new GZIPInputStream(pushbackInputStream)
  } else pushbackInputStream
}

理论上的缺点是有人可能会偶然发送包含 0x1f/0x8b 标头的请求。这在我的情况下不会发生,因此我可以接受。

【讨论】:

    猜你喜欢
    • 2023-03-10
    • 1970-01-01
    • 2011-07-02
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-06-12
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多