diff --git a/.changeset/tidy-lions-cache.md b/.changeset/tidy-lions-cache.md new file mode 100644 index 00000000000..a882954da0b --- /dev/null +++ b/.changeset/tidy-lions-cache.md @@ -0,0 +1,5 @@ +--- +'@tanstack/query-core': patch +--- + +Memoize falsy `combine` results when the function and query results are unchanged. diff --git a/packages/query-core/src/__tests__/queriesObserver.test.tsx b/packages/query-core/src/__tests__/queriesObserver.test.tsx index 171d1493c7e..9b34d323bda 100644 --- a/packages/query-core/src/__tests__/queriesObserver.test.tsx +++ b/packages/query-core/src/__tests__/queriesObserver.test.tsx @@ -735,6 +735,41 @@ describe('queriesObserver', () => { expect(combined1).toBe(combined2) }) + it.each([ + ['zero', 0], + ['negative zero', -0], + ['NaN', Number.NaN], + ['false', false], + ['empty string', ''], + ['null', null], + ['undefined', undefined], + ['zero bigint', 0n], + ])( + 'should cache the falsy combined result %s when nothing has changed', + (_name, value) => { + const combine = vi.fn(() => value) + const key = queryKey() + const queries = [{ queryKey: key, queryFn: () => 1 }] + const observer = new QueriesObserver(queryClient, queries, { + combine, + }) + + const [raw1, getCombined1] = observer.getOptimisticResult( + queries, + combine, + ) + getCombined1(raw1) + + const [raw2, getCombined2] = observer.getOptimisticResult( + queries, + combine, + ) + getCombined2(raw2) + + expect(combine).toHaveBeenCalledTimes(1) + }, + ) + it('should track properties on all observers when trackResult is called', () => { const key1 = queryKey() const key2 = queryKey() diff --git a/packages/query-core/src/queriesObserver.ts b/packages/query-core/src/queriesObserver.ts index 4fcf8e5d41e..5395cbfbea2 100644 --- a/packages/query-core/src/queriesObserver.ts +++ b/packages/query-core/src/queriesObserver.ts @@ -40,7 +40,7 @@ export class QueriesObserver< #queries: Array #options?: QueriesObserverOptions #observers: Array - #combinedResult?: TCombinedResult + #combinedResult!: TCombinedResult #lastCombine?: CombineFn #lastResult?: Array #lastQueryHashes?: Array @@ -227,7 +227,6 @@ export class QueriesObserver< queryHashes.some((hash, i) => hash !== lastHashes[i])) if ( - !this.#combinedResult || this.#result !== this.#lastResult || queryHashesChanged || combine !== this.#lastCombine