openapi-typescript icon indicating copy to clipboard operation
openapi-typescript copied to clipboard

Type for `useQuery` error dosen't cover unexpected errors

Open ludwighogstrom opened this issue 1 year ago • 1 comments

openapi-react-query version

0.3.0

Description

The type of the error returned by useQuery and queryOptions is determined by the "paths" specification. For example:

const {data, error} = useQuery(queryClient.queryOptions("get", "/my-path"));

In this case, error is typed as:

{ error_code: number } | null

That object matches the API response when an expected error occurs.

However, if something unexpected goes wrong—such as fetch throwing TypeError: Failed to fetch—the typing no longer aligns. In this case, the error is not an object with an error_code property but a FetchError instead.

An unexpected response can also occur if the API is temporarily down and fails to return a response in the expected format.

Reproduction

Block the request in Chrome DevTools and log the error. You'll see that the error is a TypeError: Failed to fetch, rather than the expected format defined by the API specification.

Instruction how to block request https://developer.chrome.com/docs/devtools/network-request-blocking

Expected result

The typing of error should be something else. Maybe unknown?

ludwighogstrom avatar Feb 12 '25 14:02 ludwighogstrom

It seems that TanStack Query recommends keeping the error type as an Error (default behavior). https://tanstack.com/query/v5/docs/framework/react/typescript#typing-the-error-field

However, this has the drawback that type inference for all other generics of useQuery will not work anymore. It is generally not considered a good practice to throw something that isn't an Error...

ludwighogstrom avatar Feb 12 '25 15:02 ludwighogstrom

There are also cases where a proxy returns a 502 Bad Gateway or 503 Service Unavailable with a response not looking anything like the types provided from the schema.

I also have some additional headers (Request/Correlation id) that can be used in the frontend to correlate the request with the backend logs. There seems to be no way to access these with the current state of the error object.

Maybe a combination of the response (optional) and the original error would be good to actually be able to determine what went wrong. Something like:

{
  response?: Response;
  error: unknown;
}

cbodin avatar Mar 25 '25 19:03 cbodin