skipToken support for typescript-react-apollo
Moeface opened this issue · 4 comments
skip
as an option for suspense hooks is going to be deprecated in favour of a new skipToken
technique in an upcoming version of Apollo, as it provides more type safety.
Apollo docs on skip
:
This option is deprecated and only supported to ease the migration from useQuery. It will be removed in a future release. Please use skipToken instead of the skip option as it is more type-safe.
More reading:
- https://www.apollographql.com/docs/react/data/suspense/#skipping-suspense-hooks
- https://www.apollographql.com/docs/react/api/react/hooks/#skiptoken
You can work around this at the moment by using useSuspenseQuery
directly from @apollo/client
and using the document and types generated by graphql-code-generator
, eg:
import { useSuspenseQuery, skipToken } from '@apollo/client'
import { ExampleQueryResult, ExampleQueryDocument } from './generated'`
const { data } = useSuspenseQuery<ExampleQueryResult>(
ExampleQueryDocument,
id ? { variables: { id } } : skipToken
)
Describe the solution you'd like
It would great if the generated suspense hook had native support for this (which aligns with what their docs recommend), eg:
import { skipToken } from '@apollo/client'
import { useExampleSuspenseQuery } from './generated'`
const { data } = useExampleSuspenseQuery(id ? { variables: { id } } : skipToken)
The fix is pretty easy to do:
Before:
export function useFeedSuspenseQueryMySuffix(baseOptions?: Apollo.SuspenseQueryHookOptions<FeedQuery, FeedQueryVariables>) {
const options = {...defaultOptions, ...baseOptions}
return Apollo.useSuspenseQuery<FeedQuery, FeedQueryVariables>(FeedDocument, options);
}`);
After:
export function useFeedSuspenseQueryMySuffix(baseOptions?: Apollo.SkipToken | Apollo.SuspenseQueryHookOptions<FeedQuery, FeedQueryVariables>) {
const options = (baseOptions === Apollo.skipToken) ? baseOptions : { ...defaultOptions, ...baseOptions }
return Apollo.useSuspenseQuery<FeedQuery, FeedQueryVariables>(FeedDocument, options);
}`);
Just need to add Apollo.SkipToken the type on the baseOptions and change a little bit how options is defined.
I already do a commit on a fork:
vbornand@792f7ed
Do you want I create a PR?
@vbornand I attempted something similar but it gives incorrect types for when you don't supply skipToken
.
eg:
const { data } = useDataSuspenseQuery({ variables: { foo: bar }})
^--- this is now `Data | undefined` instead of just `Data`
@apollo/client
's native useSuspense
hook has a lot of overloads to support variations of this functionality so I think it may end up being more complicated:
The useSuspenseQuery
differs from the usual useQuery
and useLazyQuery
by having a number of overloaded functions. In order to fully support this in codegen, I set it up to generate a dedicated d.ts for useSuspenseQuery
and tested it. However, this approach results in the creation of more files in codegen, which is a concern.
To minimize the amount of generated code, I managed to make it function correctly by merely supporting the skipToken
. However, inferring types for deepPartial
due to options like returnPartialData
remains impossible.
I am still considering how to best integrate this feature. Just like useSuspenseQuery
, useBackgroundQuery
also has various overloaded functions, indicating the need for a separate file to comprehensively define these types.
I can submit a PR for this, but I need opinions on the creation of an additional file.
ps. At this point, it seems much better to just use TypedDocumentNode