Reputation: 895
I'm having a hard time trying to satisfy Typescript when redefining the fetch function on @urql/core.
I found two SO answers that kind of nailed the problem, but somehow they doesn't work for me:
My code looks like this:
import { Client } from "@urql/core"
const client = new Client({
fetch: async (...args: Parameters<typeof fetch>) => {
const response = await fetch(...args);
// ...
And the Typescript complaint is:
error| Type '(input: RequestInfo, init?: RequestInit | undefined) => Promise' is not assignable to type '{ (input: RequestInfo | URL, init?: RequestInit | undefined): Promise; (input: RequestInfo, init?: RequestInit | undefined): Promise<...>; }'. Types of parameters 'input' and 'input' are incompatible. Type 'RequestInfo | URL' is not assignable to type 'RequestInfo'. Type 'Request' is not assignable to type 'RequestInfo'. Property 'duplex' is missing in type 'Request' but required in type 'import("./node_modules/undici-types/fetch").Request'.
(path slightly edited to hide personal information)
I tried a simplified fetch replacement just to seek how to satisfy Typescript, and found that this code works fine:
const fetcher = async (...args: Parameters<typeof fetch>) => {
const response = await fetch(...args)
// ...
return response
}
While this one gives me the exact same error as the initial snippet from above:
const originalFetch = global.fetch
global.fetch = async (...args: Parameters<typeof global.fetch>) => {
const response = await originalFetch(...args)
// ...
return response
}
My main question is how to solve this issue and satisfy Typescript.
I tried different things before reaching for Parameters<>
and every single attempt gave me a different Typescript error:
// The initial wasn't typed
global.fetch = async (...args) => {
const response = await originalFetch(...args)
// No overload matches this call
// Secondly used the very same parameters shown on previous attempt error message
global.fetch = async (...args: [RequestInfo | URL, RequestInit | undefined]) => {
const response = await originalFetch(...args)
// but then it complains about missing property 'referrer' from the `undici` type
// Thirdly I removed the `URL` option from the first parameter
global.fetch = async (...args: [RequestInfo, RequestInit | undefined]) => {
const response = await originalFetch(...args)
// but it seems is needed cause "Type 'RequestInfo | URL' is not assignable to type 'RequestInfo'"
It's really puzzling seeing it working fine when I assign to whatever name, but breaking when trying to overwrite the global function. Since I'm trying to tamper with response data from @urql/core
, I cannot use another method as I have to replace the fetch
member from Client
.
Upvotes: 1
Views: 157
Reputation: 950
import fetch from "cross-fetch";
import { gql, Client, fetchExchange } from '@urql/core';
const client = createClient({
url: process.env.GRAPHQL_URI || "",
exchanges: [fetchExchange],
fetch: fetch,
});
Using cross-fetch
solved above problem for me. To install cross-fetch
follow this
yarn add cross-fetch @urql/core
npm install cross-fetch @urql/core
Upvotes: 0