为什么Typescript期望fetch()的`body`属性是ReadableStream<Uint8Array>?

13
  const request: RequestInfo = {
    method,
    cache,
    redirect,
    headers: {} as Headers,
    body: null as string | null,
  };

  ...

  fetch(url, request);

使用以上方法,我得到了:

Type 'string | null' is not assignable to type 'ReadableStream<Uint8Array> | null'.
  Type 'string' is not assignable to type 'ReadableStream<Uint8Array> | null'.

在TS的类型声明中,有:

interface RequestInit {
    /**
     * A BodyInit object or null to set request's body.
     */
    body?: BodyInit | null;
}

type BodyInit = Blob | BufferSource | FormData | URLSearchParams | ReadableStream<Uint8Array> | string;

为什么它期望 ReadableStream<Uint8Array>

2个回答

6

不确定完全理解你的问题,但让我们回答两种可能性。

RequestInfo类型是用于请求(Request)实例的类型,例如:

const request: RequestInfo = new Request(url, requestInit);

你所创建的对象实际上是fetch方法的第二个参数requestInit,你需要使用RequestInit类型。
const requestInit: RequestInit = {
  method,
  cache,
  redirect,
  headers: {} as Headers,
  body: null as string | null,
};
...
fetch(url, requestInit);

现在,如果你想知道为什么RequestInitBodyInit成员可以是一个ReadablStream<Uint8Array>,那是因为规范允许它,尽管目前没有浏览器支持它,规范还不是特别完善

2
您展示的定义不太正确,您展示的是RequestInit,而不是RequestInfo。我所拥有的(以及我在微软页面上看到的TS定义)是这样的:
type RequestInfo = Request | string

interface Request extends Body {
  // No definition for `body` here
  // ...
}

interface Body {
  readonly body: ReadableStream<Uint8Array> | null
  // ...
}

所以很明显,编译器为什么会抱怨是清楚的。但我不明白为什么定义是这样的,因为我确定可以将 string 作为请求的 body。我认为你需要将其转换为可读流:

body: 'string' as unknown as ReadableStream<Uint8Array>

或者将其转换为any类型,因为这种类型转换比较长。我认为在这里转换为any不会导致任何混淆、错误或问题。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接