-
-
Notifications
You must be signed in to change notification settings - Fork 3k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
test(react-query): refactor test file structure 1 file by 1 api
- Loading branch information
Showing
4 changed files
with
226 additions
and
218 deletions.
There are no files selected for viewing
36 changes: 1 addition & 35 deletions
36
...t-query/src/__tests__/prefetch.test-d.tsx → ...sts__/usePrefetchInfiniteQuery.test-d.tsx
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
188 changes: 188 additions & 0 deletions
188
packages/react-query/src/__tests__/usePrefetchInfiniteQuery.test.tsx
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,188 @@ | ||
import { describe, expect, it, vi } from 'vitest' | ||
import React from 'react' | ||
import { fireEvent, waitFor } from '@testing-library/react' | ||
|
||
import { | ||
QueryCache, | ||
usePrefetchInfiniteQuery, | ||
useSuspenseInfiniteQuery, | ||
} from '..' | ||
import { createQueryClient, queryKey, renderWithClient, sleep } from './utils' | ||
|
||
import type { InfiniteData, UseSuspenseInfiniteQueryOptions } from '..' | ||
import type { Mock } from 'vitest' | ||
|
||
const generateInfiniteQueryOptions = ( | ||
data: Array<{ data: string; currentPage: number; totalPages: number }>, | ||
) => { | ||
let currentPage = 0 | ||
|
||
return { | ||
queryFn: vi | ||
.fn<(...args: Array<any>) => Promise<(typeof data)[number]>>() | ||
.mockImplementation(async () => { | ||
const currentPageData = data[currentPage] | ||
if (!currentPageData) { | ||
throw new Error('No data defined for page ' + currentPage) | ||
} | ||
|
||
await sleep(10) | ||
currentPage++ | ||
|
||
return currentPageData | ||
}), | ||
initialPageParam: 1, | ||
getNextPageParam: (lastPage: (typeof data)[number]) => | ||
lastPage.currentPage === lastPage.totalPages | ||
? undefined | ||
: lastPage.currentPage + 1, | ||
} | ||
} | ||
|
||
describe('usePrefetchInfiniteQuery', () => { | ||
const queryCache = new QueryCache() | ||
const queryClient = createQueryClient({ queryCache }) | ||
|
||
const Fallback = vi.fn().mockImplementation(() => <div>Loading...</div>) | ||
|
||
function Suspended<T = unknown>(props: { | ||
queryOpts: UseSuspenseInfiniteQueryOptions< | ||
T, | ||
Error, | ||
InfiniteData<T>, | ||
any, | ||
Array<string>, | ||
any | ||
> | ||
renderPage: (page: T) => React.JSX.Element | ||
}) { | ||
const state = useSuspenseInfiniteQuery(props.queryOpts) | ||
|
||
return ( | ||
<div> | ||
{state.data.pages.map((page, index) => ( | ||
<div key={index}>{props.renderPage(page)}</div> | ||
))} | ||
<button onClick={() => state.fetchNextPage()}>Next Page</button> | ||
</div> | ||
) | ||
} | ||
|
||
it('should prefetch an infinite query if query state does not exist', async () => { | ||
const data = [ | ||
{ data: 'Do you fetch on render?', currentPage: 1, totalPages: 3 }, | ||
{ data: 'Or do you render as you fetch?', currentPage: 2, totalPages: 3 }, | ||
{ | ||
data: 'Either way, Tanstack Query helps you!', | ||
currentPage: 3, | ||
totalPages: 3, | ||
}, | ||
] | ||
|
||
const queryOpts = { | ||
queryKey: queryKey(), | ||
...generateInfiniteQueryOptions(data), | ||
} | ||
|
||
function App() { | ||
usePrefetchInfiniteQuery({ ...queryOpts, pages: data.length }) | ||
|
||
return ( | ||
<React.Suspense fallback={<Fallback />}> | ||
<Suspended | ||
queryOpts={queryOpts} | ||
renderPage={(page) => <div>data: {page.data}</div>} | ||
/> | ||
</React.Suspense> | ||
) | ||
} | ||
|
||
const rendered = renderWithClient(queryClient, <App />) | ||
|
||
await waitFor(() => rendered.getByText('data: Do you fetch on render?')) | ||
fireEvent.click(rendered.getByText('Next Page')) | ||
await waitFor(() => | ||
rendered.getByText('data: Or do you render as you fetch?'), | ||
) | ||
fireEvent.click(rendered.getByText('Next Page')) | ||
await waitFor(() => | ||
rendered.getByText('data: Either way, Tanstack Query helps you!'), | ||
) | ||
expect(Fallback).toHaveBeenCalledTimes(1) | ||
expect(queryOpts.queryFn).toHaveBeenCalledTimes(3) | ||
}) | ||
|
||
it('should not display fallback if the query cache is already populated', async () => { | ||
const queryOpts = { | ||
queryKey: queryKey(), | ||
...generateInfiniteQueryOptions([ | ||
{ data: 'Prefetch rocks!', currentPage: 1, totalPages: 3 }, | ||
{ data: 'No waterfalls, boy!', currentPage: 2, totalPages: 3 }, | ||
{ data: 'Tanstack Query #ftw', currentPage: 3, totalPages: 3 }, | ||
]), | ||
} | ||
|
||
await queryClient.prefetchInfiniteQuery({ ...queryOpts, pages: 3 }) | ||
;(queryOpts.queryFn as Mock).mockClear() | ||
|
||
function App() { | ||
usePrefetchInfiniteQuery(queryOpts) | ||
|
||
return ( | ||
<React.Suspense fallback={<Fallback />}> | ||
<Suspended | ||
queryOpts={queryOpts} | ||
renderPage={(page) => <div>data: {page.data}</div>} | ||
/> | ||
</React.Suspense> | ||
) | ||
} | ||
|
||
const rendered = renderWithClient(queryClient, <App />) | ||
|
||
await waitFor(() => rendered.getByText('data: Prefetch rocks!')) | ||
fireEvent.click(rendered.getByText('Next Page')) | ||
await waitFor(() => rendered.getByText('data: No waterfalls, boy!')) | ||
fireEvent.click(rendered.getByText('Next Page')) | ||
await waitFor(() => rendered.getByText('data: Tanstack Query #ftw')) | ||
expect(queryOpts.queryFn).not.toHaveBeenCalled() | ||
expect(Fallback).not.toHaveBeenCalled() | ||
}) | ||
|
||
it('should not create an endless loop when using inside a suspense boundary', async () => { | ||
const queryOpts = { | ||
queryKey: queryKey(), | ||
...generateInfiniteQueryOptions([ | ||
{ data: 'Infinite Page 1', currentPage: 1, totalPages: 3 }, | ||
{ data: 'Infinite Page 2', currentPage: 1, totalPages: 3 }, | ||
{ data: 'Infinite Page 3', currentPage: 1, totalPages: 3 }, | ||
]), | ||
} | ||
|
||
function Prefetch({ children }: { children: React.ReactNode }) { | ||
usePrefetchInfiniteQuery(queryOpts) | ||
return <>{children}</> | ||
} | ||
|
||
function App() { | ||
return ( | ||
<React.Suspense> | ||
<Prefetch> | ||
<Suspended | ||
queryOpts={queryOpts} | ||
renderPage={(page) => <div>data: {page.data}</div>} | ||
/> | ||
</Prefetch> | ||
</React.Suspense> | ||
) | ||
} | ||
|
||
const rendered = renderWithClient(queryClient, <App />) | ||
await waitFor(() => rendered.getByText('data: Infinite Page 1')) | ||
fireEvent.click(rendered.getByText('Next Page')) | ||
await waitFor(() => rendered.getByText('data: Infinite Page 2')) | ||
fireEvent.click(rendered.getByText('Next Page')) | ||
await waitFor(() => rendered.getByText('data: Infinite Page 3')) | ||
expect(queryOpts.queryFn).toHaveBeenCalledTimes(3) | ||
}) | ||
}) |
36 changes: 36 additions & 0 deletions
36
packages/react-query/src/__tests__/usePrefetchQuery.test-d.tsx
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,36 @@ | ||
import { describe, expectTypeOf, it } from 'vitest' | ||
import { usePrefetchQuery } from '..' | ||
|
||
describe('usePrefetchQuery', () => { | ||
it('should return nothing', () => { | ||
const result = usePrefetchQuery({ | ||
queryKey: ['key'], | ||
queryFn: () => Promise.resolve(5), | ||
}) | ||
|
||
expectTypeOf(result).toEqualTypeOf<void>() | ||
}) | ||
|
||
it('should not allow refetchInterval, enabled or throwOnError options', () => { | ||
usePrefetchQuery({ | ||
queryKey: ['key'], | ||
queryFn: () => Promise.resolve(5), | ||
// @ts-expect-error TS2345 | ||
refetchInterval: 1000, | ||
}) | ||
|
||
usePrefetchQuery({ | ||
queryKey: ['key'], | ||
queryFn: () => Promise.resolve(5), | ||
// @ts-expect-error TS2345 | ||
enabled: true, | ||
}) | ||
|
||
usePrefetchQuery({ | ||
queryKey: ['key'], | ||
queryFn: () => Promise.resolve(5), | ||
// @ts-expect-error TS2345 | ||
throwOnError: true, | ||
}) | ||
}) | ||
}) |
Oops, something went wrong.