Torc
Torc

Reputation: 1322

React-Query useQueries hook to run useInfiniteQuery hooks in parallel

I am new to React-Query, but I have not been able to find an example to the following question:

I can see from the parallel query documentation on GitHub, that it's fairly easy to set-up a map of normal queries.

The example provided:

function App({ users }) {
  const userQueries = useQueries({
    queries: users.map(user => {
      return {
        queryKey: ['user', user.id],
        queryFn: () => fetchUserById(user.id),
      }
    })
  })
}

If I have an infinite query like the following, how would I be able to provide the individual query options, specifically the page parameter?:

  const ids: string[] = ['a', 'b', 'c'];

  const useGetDetailsById = () => {
    return useInfiniteQuery<GetDetailsByIdResponse, AxiosError>(
      ['getDetailsById', id],
      async ({ pageParam = '' }) => {
        const { data } = await getDetailsById(
          id, // I want to run queries for `id` in _parallel_
          pageParam
        );
        return data;
      },
      {
        getNextPageParam: (lastPage: GetDetailsByIdResponse) =>
          lastPage.nextPageToken,
        retry: false,
      }
    );
  };

Upvotes: 4

Views: 1056

Answers (2)

Michael Ozeryansky
Michael Ozeryansky

Reputation: 8053

I've solved this for my use case by using one useInifiniteQuery to handle paging, and the fetch function uses queryClient to get the array of network requests.

// Use ReactQuery to fetch array with cache
function fetchPage(
  queryClient: QueryClient,
  urls: string[],
  pageParam: PageParams
) {
  const requests = urls.map(url => {
    return queryClient
      .fetchQuery({
        queryKey: ['/api/endpoint', url],
        queryFn: () => fetchURL(url),
      })
      .catch(error => {
        throw error
      })
  })
  return Promise.all(requests)
}

// Component handles paging with one useInfiniteQuery
export default function Page() {
  const [urls, setUrls] = useState<string[]>([
    ...
  ])

  const queryClient = useQueryClient()
  const {
    data: pagedData,
    fetchNextPage,
    hasNextPage,
    isFetchingNextPage,
  } = useInfiniteQuery({
    queryKey: ['page', urls],
    queryFn: ({ pageParam }) => fetchPage(queryClient, urls, pageParam),
    initialPageParam: { ... },
    getNextPageParam: (lastPage, allPages, lastPageParam) => { ... }
    retry: Infinity,
  })

  const data = useMemo(() => {
    return pagedData?.pages...
  }, [pagedData])

  ...

Upvotes: 0

TkDodo
TkDodo

Reputation: 28843

No, I'm afraid there is currently no such thing as useInfiniteQueries.

Upvotes: 1

Related Questions