diff --git a/packages/swr-openapi/src/__test__/types.test-d.ts b/packages/swr-openapi/src/__test__/types.test-d.ts index 1ea997c36..b3a16420b 100644 --- a/packages/swr-openapi/src/__test__/types.test-d.ts +++ b/packages/swr-openapi/src/__test__/types.test-d.ts @@ -336,6 +336,52 @@ describe("types", () => { }); }); }); + + describe("custom error types", () => { + const uniqueKey = "<unique-key>"; + type Key = typeof uniqueKey; + const useQuery = createQueryHook<paths, `${string}/${string}`, Key, Error>(client, uniqueKey); + const useImmutable = createImmutableHook<paths, `${string}/${string}`, Key, Error>(client, uniqueKey); + const useInfinite = createInfiniteHook<paths, `${string}/${string}`, Key, Error>(client, uniqueKey); + + describe("useQuery", () => { + it("returns correct error", () => { + const { error } = useQuery("/pet/{petId}", { + params: { + path: { + petId: 5, + }, + }, + }); + + expectTypeOf(error).toEqualTypeOf<PetInvalid | Error | undefined>(); + }); + }); + + describe("useImmutable", () => { + it("returns correct error", () => { + const { error } = useImmutable("/pet/{petId}", { + params: { + path: { + petId: 5, + }, + }, + }); + + expectTypeOf(error).toEqualTypeOf<PetInvalid | Error | undefined>(); + }); + }); + + describe("useInfinite", () => { + it("returns correct error", () => { + const { error } = useInfinite("/pet/findByStatus", (_index, _prev) => ({ + params: { query: { status: "available" } }, + })); + + expectTypeOf(error).toEqualTypeOf<PetStatusInvalid | Error | undefined>(); + }); + }); + }); }); describe("TypesForRequest", () => { diff --git a/packages/swr-openapi/src/infinite.ts b/packages/swr-openapi/src/infinite.ts index 4ad7fdb88..c17584c30 100644 --- a/packages/swr-openapi/src/infinite.ts +++ b/packages/swr-openapi/src/infinite.ts @@ -33,16 +33,18 @@ import { useCallback, useDebugValue } from "react"; * }); * ``` */ -export function createInfiniteHook<Paths extends {}, IMediaType extends MediaType, Prefix extends string>( - client: Client<Paths, IMediaType>, - prefix: Prefix, -) { +export function createInfiniteHook< + Paths extends {}, + IMediaType extends MediaType, + Prefix extends string, + FetcherError = never, +>(client: Client<Paths, IMediaType>, prefix: Prefix) { return function useInfinite< Path extends PathsWithMethod<Paths, "get">, R extends TypesForGetRequest<Paths, Path>, Init extends R["Init"], Data extends R["Data"], - Error extends R["Error"], + Error extends R["Error"] | FetcherError, Config extends SWRInfiniteConfiguration<Data, Error>, >(path: Path, getInit: SWRInfiniteKeyLoader<Data, Init | null>, config?: Config) { type Key = [Prefix, Path, Init | undefined] | null; diff --git a/packages/swr-openapi/src/query-base.ts b/packages/swr-openapi/src/query-base.ts index 234101842..bf6ff3d88 100644 --- a/packages/swr-openapi/src/query-base.ts +++ b/packages/swr-openapi/src/query-base.ts @@ -8,16 +8,18 @@ import { useCallback, useDebugValue, useMemo } from "react"; * @private */ export function configureBaseQueryHook(useHook: SWRHook) { - return function createQueryBaseHook<Paths extends {}, IMediaType extends MediaType, Prefix extends string>( - client: Client<Paths, IMediaType>, - prefix: Prefix, - ) { + return function createQueryBaseHook< + Paths extends {}, + IMediaType extends MediaType, + Prefix extends string, + FetcherError = never, + >(client: Client<Paths, IMediaType>, prefix: Prefix) { return function useQuery< Path extends PathsWithMethod<Paths, "get">, R extends TypesForGetRequest<Paths, Path>, Init extends R["Init"], Data extends R["Data"], - Error extends R["Error"], + Error extends R["Error"] | FetcherError, Config extends R["SWRConfig"], >( path: Path,