Why does TContext in useMutation default to {} and not infer from onMutate return type? #9899
-
|
Hi, I’m experimenting with optimistic updates using useMutation in React Query (v5). Example: return useMutation<Result, Error, Variables>({
onMutate: async () => {
const snapshot = queryClient.getQueryData(["user"]);
return { snapshot };
},
onError: (err, variables, context) => {
// ❌ context is {} here unless I specify <..., ..., ..., { snapshot: User }>
},
});I expected the context type to be inferred from the return of onMutate, but it seems React Query does not infer this. Is there a recommended pattern for typing mutation context? Thanks! |
Beta Was this translation helpful? Give feedback.
Replies: 2 comments
-
|
You need to explicitly specify the 4th generic of useMutation (TContext). return useMutation<
onError: (err, variables, context) => { Why this happens UseMutationOptions has 4 generics: If you only provide 3, TContext falls back to its default: TContext = unknown // or treated as {} React Query currently does not infer TContext from onMutate, This is the recommended and type-safe way to use mutation context. |
Beta Was this translation helpful? Give feedback.
-
|
@rjsgud49 Thanks!Thanks! |
Beta Was this translation helpful? Give feedback.
You need to explicitly specify the 4th generic of useMutation (TContext).
React Query does not infer the return type of onMutate, so without providing TContext, the type defaults to {}, which is why context.snapshot gives a TS error.
return useMutation<
Result,
Error,
Variables,
{ snapshot: User | undefined }
onError: (err, variables, context) => {
if (context?.snapshot) {
queryClient.setQueryData(["user"], context.snapshot);
}
},
});
Why this happens
UseMutationOptions has 4 generics:
TData, TError, TVariables, TContext
If you only provide 3, TContext falls back to its default:
TCont…