ReadableStreamBYOBRequest
注意:此功能在 Web Workers 中可用。
ReadableStreamBYOBRequest 接口是 Streams API 的一部分,它表示一个“拉取请求”,用于从底层源获取数据,并将以零拷贝(zero-copy)的方式传输给消费者(绕过流的内部队列)。
当消费者请求数据且流的内部队列为空时,会创建 ReadableStreamBYOBRequest 对象并进入“BYOB 模式”。(如果流已缓冲数据,则会直接解析消费者的请求)。底层字节源可以通过其控制器的 ReadableByteStreamController.byobRequest 属性访问活动的 BYOB 请求,如果没有待处理的请求,该属性将设置为 null。
支持“BYOB 模式”的底层源应检查 ReadableByteStreamController.byobRequest,如果存在,则必须使用它来传输数据。如果底层源在 ReadableByteStreamController.byobRequest 为 null 时收到数据,则可以使用 ReadableByteStreamController.enqueue() 将其入队。当底层推送源在流的内部缓冲区不为空时收到新数据,可能会发生这种情况。
底层源通过向 BYOB 请求的 view 写入数据,然后调用 respond() 来使用该请求,或者通过调用 respondWithNewView() 并将新视图作为参数传递来使用。请注意,“新视图”实际上必须是相同缓冲区的一个视图,从相同的偏移量开始。这可能用于在底层源无法填充整个原始视图时返回一个较短的缓冲区。
请注意,只有在 ReadableStream() 构造函数中为源指定了 type="bytes" 时,才会为底层源创建 ReadableByteStreamController。“BYOB 模式”在 ReadableController() 构造函数中指定了 autoAllocateChunkSize 时,或者在使用 ReadableStreamBYOBReader 时(通常是通过调用带有参数 { mode: 'byob' } 的 ReadableStream.getReader() 来构造)启用。
构造函数
无。ReadableStreamBYOBRequest 实例由 ReadableByteStreamController 根据需要自动创建。
实例属性
ReadableStreamBYOBRequest.view只读-
返回当前视图。这是一个将在调用
ReadableStreamBYOBRequest.respond()时传输给消费者的缓冲区视图。
实例方法
ReadableStreamBYOBRequest.respond()-
通知相关的可读字节流,指定数量的字节已写入当前
view,这会导致消费者的挂起请求被解析。请注意,调用此方法后,view将被传输且不再可修改。 ReadableStreamBYOBRequest.respondWithNewView()-
通知相关的可读字节流,应将作为参数传递的视图传输给可读字节流的消费者。此新视图必须使用与原始
view相同的缓冲区,从相同的偏移量开始,并且长度相同或更短。请注意,调用此方法后,view将被传输且不再可修改。
示例
以下代码摘自 使用可读字节流 > 创建可读套接字推送字节流 中的实时示例。
具有待传输数据的推送底层字节源应首先检查 controller.byobRequest 是否非 null。如果未启用自动块分配且与默认读取器一起使用,则拉取底层字节源才需要此检查。
if (controller.byobRequest) {
/* code to transfer data */
}
有两种方法可以将数据读取到 ReadableStreamBYOBRequest 然后进行传输。第一种是将数据写入 ReadableStreamBYOBRequest.view 属性,然后调用 ReadableStreamBYOBRequest.respond() 来指示要传输的数据量。操作完成后,byobRequest.view 将被分离,并且该请求应被丢弃。
下面的代码使用一个假定的 readInto() 方法将数据复制到视图中,以展示这种情况
const v = controller.byobRequest.view;
bytesRead = socket.readInto(v.buffer, v.byteOffset, v.byteLength);
controller.byobRequest.respond(bytesRead);
另一种方法是调用 ReadableStreamBYOBRequest.respondWithNewView(),并将您自己的对同一底层后备数据的视图传递进去。请注意,这只是指定实际传输的底层缓冲区/内存后备的范围的另一种方式。上面的代码等效于 respondWithNewView 的代码将是
const v = controller.byobRequest.view;
bytesRead = socket.readInto(v.buffer, v.byteOffset, v.byteLength);
const newView = new Uint8Array(v.buffer, v.byteOffset, bytesRead);
controller.byobRequest.respondWithNewView(newView);
规范
| 规范 |
|---|
| Streams # rs-byob-request-class |
浏览器兼容性
加载中…