You need to enable JavaScript to run this app.
最新活动
大模型
产品
解决方案
定价
生态与合作
支持与服务
开发者
了解我们

TypeScript是否错误收窄了ReadableStreamDefaultReader.read()返回值的类型?

TypeScript是否错误收窄了ReadableStreamDefaultReader.read()返回值的类型?

你这个观察真的很细致!没错,这确实是TypeScript类型定义里存在的一个和实际行为不符的问题。

先看你贴的这段测试代码:

async function test(stream: ReadableStream<Uint8Array>) {
  const reader = stream.getReader()
  const { value, done } = await reader.read()
  // typeof value == Uint8Array<ArrayBufferLike> | undefined
  if (done) return
  // TypeScript推断此时typeof value == Uint8Array<ArrayBufferLike>
}

按照TypeScript的类型收窄逻辑,当donefalse时,它会认定value一定是有效的Uint8Array<ArrayBufferLike>实例,但实际运行场景里完全不是这样。

问题出在ReadableStreamDefaultController.enqueue()方法上,这个方法的chunk参数是可选的——你可以直接不带任何参数调用它:

controller.enqueue() // 没有传入chunk

实际测试就能发现,这种情况下调用reader.read()会返回{ value: undefined, done: false },但TypeScript的类型定义并没有覆盖这种场景,它错误地收窄了返回值的类型,默认只有当donetrue时,value才可能是undefined

本质上这是TypeScript的类型定义没有完全对齐标准的实际行为:标准里允许enqueue接收undefined作为chunk,对应的read()自然也可能在流未结束时返回undefinedvalue,但TypeScript的类型定义漏掉了这个细节。

内容来源于stack exchange

火山引擎 最新活动