关于javascript:使用XHR和分块传输编码的HTTP POST

HTTP POST using XHR with Chunked Transfer Encoding

我有一个REST API,可以通过HTTP Post接受音频文件。该API支持Transfer-Encoding:分块的请求标头,以便在从客户端上运行的记录器创建文件时可以分段上传文件。这样服务器可以在到达文件时开始处理文件,以提高性能。例如:

HTTP 1.1 POST .../v1/processAudio

Transfer-Encoding: chunked

[Chunk 1 256 Bytes] (server starts processing when arrives)

[Chunk 2 256 Bytes]

[Chunk 3 256 Bytes]

...

音频文件通常很短,大小约为10K至100K。我有正在运行的C#和Java代码,所以我知道API可以工作。但是,我似乎无法使用javascript在浏览器中进行录制和上传。

这是我的测试代码,该代码使用Transfer-Encoding对localhost进行POST:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
<html>
<script type="text/javascript">
  function streamUpload() {
    var blob = new Blob(['GmnQPBU+nyRGER4JPAW4DjDQC19D']);
    var xhr = new XMLHttpRequest();
    // Add any event handlers here...
    xhr.open('POST', '/', true);
    xhr.setRequestHeader("Transfer-Encoding","chunked");
    xhr.send(blob);
  }


<body>
  Test Chunked Upload using XHR
  <button onclick="streamUpload()">Start Upload</button>
</body>

</html>

问题是我在Chrome中收到以下错误

拒绝设置不安全的标头" Transfer-Encoding"

streamUpload @ uploadTest.html:14
onclick @ uploadTest.html:24

看完XHR文档后,我仍然感到困惑,因为它没有谈论不安全的请求标头。我想知道XHR是否可能不允许或实现Transfer-Encoding:为HTTP POST分块?

我已经研究了使用多个XHR.send()请求和WebSocket的变通方法,但是两者都不可取,因为这将需要对已经到位,简单,稳定且可运行的服务器API进行重大更改。唯一的问题是,我们似乎无法通过Transfer-Encoding:分块的请求标头通过psedo流从浏览器进行POST。

任何想法或建议都将非常有帮助。


正如评论中提到的那样,您不允许设置该标头,因为它是由用户代理控制的。

有关完整的标头集,请参见4.6.2 W3C XMLHttpRequest级别1中的setRequestHeader()方法,并注意Transfer-Encoding是由用户代理控制以使其控制传输的那些方面的标头之一。

  • 接受字符集
  • 接受编码
  • 访问控制请求标头
  • 访问控制请求方法
  • 连接
  • 内容长度
  • 曲奇饼
  • Cookie2
  • 日期
  • DNT
  • 期望
  • 主办
  • 活着
  • 起源
  • 推荐人
  • TE
  • 预告片
  • 传输编码
  • 升级
  • 用户代理
  • 通过

WhatWG Fetch API生活标准中也有类似的列表。
https://fetch.spec.whatwg.org/#terminology-headers