diff --git a/packages/query-core/src/queryClient.ts b/packages/query-core/src/queryClient.ts index 6112abed94..b8c1833a55 100644 --- a/packages/query-core/src/queryClient.ts +++ b/packages/query-core/src/queryClient.ts @@ -247,25 +247,26 @@ export class QueryClient { filters: RefetchQueryFilters = {}, options?: RefetchOptions, ): Promise { + const fetchOptions = { + ...options, + cancelRefetch: options?.cancelRefetch ?? true, + } const promises = notifyManager.batch(() => this.#queryCache .findAll(filters) .filter((query) => !query.isDisabled()) - .map((query) => - query.fetch(undefined, { - ...options, - cancelRefetch: options?.cancelRefetch ?? true, - }), - ), + .map((query) => { + let promise = query.fetch(undefined, fetchOptions) + if (!fetchOptions.throwOnError) { + promise = promise.catch(noop) + } + return query.state.fetchStatus === 'paused' + ? Promise.resolve() + : promise + }), ) - let promise = Promise.all(promises).then(noop) - - if (!options?.throwOnError) { - promise = promise.catch(noop) - } - - return promise + return Promise.all(promises).then(noop) } fetchQuery< diff --git a/packages/query-core/src/tests/queryClient.test.tsx b/packages/query-core/src/tests/queryClient.test.tsx index 51a55a67b7..bde738afb8 100644 --- a/packages/query-core/src/tests/queryClient.test.tsx +++ b/packages/query-core/src/tests/queryClient.test.tsx @@ -1,7 +1,12 @@ import { waitFor } from '@testing-library/react' import '@testing-library/jest-dom' -import { sleep, queryKey, createQueryClient } from './utils' +import { + sleep, + queryKey, + createQueryClient, + mockNavigatorOnLine, +} from './utils' import type { QueryCache, QueryClient, @@ -1020,6 +1025,33 @@ describe('queryClient', () => { } expect(error).toEqual('error') }) + + test('should resolve Promise immediately if query is paused', async () => { + const key1 = queryKey() + const queryFn1 = vi.fn().mockReturnValue('data1') + await queryClient.fetchQuery({ queryKey: key1, queryFn: queryFn1 }) + const onlineMock = mockNavigatorOnLine(false) + + await queryClient.refetchQueries({ queryKey: key1 }) + + // if we reach this point, the test succeeds because the Promise was resolved immediately + expect(queryFn1).toHaveBeenCalledTimes(1) + onlineMock.mockRestore() + }) + + test('should refetch if query we are offline but query networkMode is always', async () => { + const key1 = queryKey() + queryClient.setQueryDefaults(key1, { networkMode: 'always' }) + const queryFn1 = vi.fn().mockReturnValue('data1') + await queryClient.fetchQuery({ queryKey: key1, queryFn: queryFn1 }) + const onlineMock = mockNavigatorOnLine(false) + + await queryClient.refetchQueries({ queryKey: key1 }) + + // initial fetch + refetch (even though we are offline) + expect(queryFn1).toHaveBeenCalledTimes(2) + onlineMock.mockRestore() + }) }) describe('invalidateQueries', () => {