Lädt...


🔧 Mastering Infinite Scrolling with React Query v5


Nachrichtenbereich: 🔧 Programmierung
🔗 Quelle: dev.to

Introduction:

In the world of web development, building a todo list application is a rite of passage. In this tutorial, we'll take it a step further by integrating TypeScript for type safety and React Query for efficient data management. By the end, you'll have a fully functional todo list application with robust error handling, real-time updates, and type-safe code.

Step 1: Setting Up Your Project

To get started, let's set up a new React project with TypeScript and React Query. We'll use Vite for fast development and a modern build setup.

npm init vite@latest infinite-scroll-app --template react-ts

after that you have to select react as our option here
framework-reactand then we will select typescript + swc (Speedy Web Compiler ) you can discover more details about it through this link https://www.dhiwise.com/post/maximize-performance-how-swc-enhances-vite-and-react
typescriptAfter finishing this you have to change directory to the project created and install dependencies

# Change directory
cd infinite-scroll-app
# install dependencies
npm install
# Install React Query
npm install react-query@latest

Step 2: Configuring ReactQuery within our project

In order to make react query works ensure that you've wrapped your application with QueryClientProvider and provided a QueryClient instance.So your main.tsx file will look like this

import React from "react";
import ReactDOM from "react-dom/client";
import App from "./App.tsx";
import { QueryClient, QueryClientProvider } from "react-query";

const queryClient = new QueryClient();

ReactDOM.createRoot(document.getElementById("root")!).render(
  <React.StrictMode>
    <QueryClientProvider client={queryClient}>
      <App />
    </QueryClientProvider>
  </React.StrictMode>
);

To Get data we will be using Fake APi JSON Placeholder with the Todo endpoint.

Step 3: Fetching data

In this step we will be fetching our data from the API and then we set the limit to 10. The expected behavior for this is to render 10 values on the screen when the page is initially loaded and then continuously add more values when the user reaches the bottom screen.
So for this purpose and to make our project organized we are going to create a folder called services and add file called api.ts inside

project_architecture

Now let's create the function to fetch our data:

export const fetchData = async (page: number) => {
  const response = await fetch(
    `https://jsonplaceholder.typicode.com/todos?_pages=${page}&_limit=${10}`
  );
  const todos = await response.json();
  return todos;
};

Now let's go to our App.tsx file and implement the logic of implementing React infinite scrolling
Here, we will use the useInfiniteQuery hook from the React query library. Consider the block of code below:

  const { data, error, fetchNextPage, hasNextPage, isFetching, isLoading } = useInfiniteQuery({
    queryKey: ["todos"],
    queryFn: ({ pageParam }) => fetchData(pageParam),
    initialPageParam: 0,
    getNextPageParam: (lastPage, allPages) => {
      return lastPage.length > 0 ? allPages.length + 1 : undefined;
    },
  });

The options for useInfiniteQuery are identical to the useQuery hook with the addition of the following:

  • initialPageParam : Required : The default page param to use when fetching the first page.

  • getNextPageParam : Required : When new data is received for this query, this function receives both the last page of the infinite list of data and the full array of all pages, as well as pageParam information.

The useInfiniteQuery hook return those properties:

  • data, which contains the data from the API.

  • error, which handles any error from fetching the data from the API.

  • fetchNextpage, which fetches the next set of data to be displayed when the user reaches the bottom.

  • hasNextpage, which checks to see if there's any more data to be displayed.

  • isFetching, which shows when the data is currently being fetched.

  • isLoading, which shows when the first set of data is being loaded from the API.

Step 4: displaying data

In this step we display the list of data that will be renered on our initial page

The data properties for useInfiniteQuery will contain 2 attributes pages and pageParams

  • data.pages: TData[] Array containing all pages.
  • data.pageParams: unknown[] Array containing all page params. so we are going to format our returned data array before displaying them
  const flatData = useMemo(() => data?.pages.flat() ?? [], [data]);

  if (isLoading) return <h1>Loading...</h1>;

  if (error) return <h1>Error on fetch data...</h1>;

  return (
    <div>
      {flatData?.map((item) => (
        <div key={item.id}>
          <p>{item.title}</p>
        </div>
      ))}

      {isFetching && <div>Fetching more data...</div>}
    </div>
  );

Step 5: Implementing scrolling behavior

To make the infinte scroll works peerfectly we have first to detect if we have reached the ned of page to trigger a new request and get new data
You might have been wondering how the DOM knows when the user scrolls to the bottom of the page. Well, that's where the IntersectionObserver API comes in! The IntersectionObserver API provides a way to detect an element's position relative to the root element or viewport.

   const observer = useRef<IntersectionObserver>();
  const lastElementRef = useCallback(
    (node: HTMLDivElement) => {
      if (isLoading) return;

      if (observer.current) observer.current.disconnect();

      observer.current = new IntersectionObserver((entries) => {
        console.log(entries);
        if (entries[0].isIntersecting && hasNextPage && !isFetching) {
          fetchNextPage();
        }
      });

      if (node) observer.current.observe(node);
    },
    [fetchNextPage, hasNextPage, isFetching, isLoading]
  );

This piece of code observes the user's motion on the screen. If the user reaches the bottom of the screen, the IntersectionObserver is alerted and serves the next set of data. Technically, it takes note of the point where the last element in the data intersects and then if hasNextPage is true, it fetches the new set of data to display.

Step 6: Final Result

Full code for this component

import { useInfiniteQuery } from "react-query";
import { fetchData } from "./services/api";
import { useCallback, useMemo, useRef } from "react";

function App() {
  const observer = useRef<IntersectionObserver>();

  const { data, error, fetchNextPage, hasNextPage, isFetching, isLoading } = useInfiniteQuery({
    queryKey: ["todos"],
    queryFn: ({ pageParam }) => fetchData(pageParam),
    initialPageParam: 0,
    getNextPageParam: (lastPage, allPages) => {
      return lastPage.length > 0 ? allPages.length + 1 : undefined;
    },
  });
  const flatData = useMemo(() => data?.pages.flat() ?? [], [data]);

  const lastElementRef = useCallback(
    (node: HTMLDivElement) => {
      if (isLoading) return;

      if (observer.current) observer.current.disconnect();

      observer.current = new IntersectionObserver((entries) => {
        console.log(entries);
        if (entries[0].isIntersecting && hasNextPage && !isFetching) {
          fetchNextPage();
        }
      });

      if (node) observer.current.observe(node);
    },
    [fetchNextPage, hasNextPage, isFetching, isLoading]
  );
  if (isLoading) return <h1>Loading...</h1>;

  if (error) return <h1>Error on fetch data...</h1>;

  return (
    <div>
      {flatData?.map((item) => (
        <div key={item.id} ref={lastElementRef}>
          <p>{item.title}</p>
        </div>
      ))}

      {isFetching && <div>Fetching more data...</div>}
    </div>
  );
}

export default App;

and this will be our result

Recording-2024-05-16-at-01-15-49 hosted at ImgBB — ImgBB

Image Recording-2024-05-16-at-01-15-49 hosted in ImgBB

favicon ibb.co

So that's it guys , I hope you liked of this article and i helped you to learn somthing new :D.

To access the full code for this project and explore further, you can find the repository on my: GitHub

...

🔧 Mastering Infinite Scrolling with React Query v5


📈 54.58 Punkte
🔧 Programmierung

🔧 How to Implement React Infinite Scrolling with React Query v5


📈 51.92 Punkte
🔧 Programmierung

🔧 How to Implement React Infinite Scrolling with React Query v5


📈 51.92 Punkte
🔧 Programmierung

🔧 Infinite Scrolling: Mastering the Intersection Observer API By Making Seamless Infinite Scroll like a Pro


📈 47.03 Punkte
🔧 Programmierung

🔧 This Week In React #185: React Conf, React Query, refs, Next.js after, mini-react...


📈 38.99 Punkte
🔧 Programmierung

🔧 This Week In React #185: React Conf, React Query, refs, Next.js after, mini-react...


📈 38.99 Punkte
🔧 Programmierung

🔧 What is react-query? Why should we use react-query?


📈 35.68 Punkte
🔧 Programmierung

🔧 Mastering React Query. Simplifying Data Management in React with Separation Patterns


📈 34.59 Punkte
🔧 Programmierung

🔧 Infinite Scrolling Demo with Intersection Observer, React, and `useRef`


📈 34.08 Punkte
🔧 Programmierung

🔧 How to Create Infinite Scrolling in React Using the Intersection Observer API


📈 34.08 Punkte
🔧 Programmierung

🔧 2024 Guide to Infinite Scrolling in React/Next.js


📈 34.08 Punkte
🔧 Programmierung

🔧 How to implement Infinite Scrolling in React Native


📈 34.08 Punkte
🔧 Programmierung

🔧 How to implement Infinite Scrolling in React Native


📈 34.08 Punkte
🔧 Programmierung

🐧 What is your opinion on smooth scrolling vs traditional non smooth scrolling on your favorite apps?


📈 33.48 Punkte
🐧 Linux Tipps

🔧 CodeSOD: Query Query Query


📈 32.37 Punkte
🔧 Programmierung

🔧 How To AutoScroll In React?Creating Smooth Auto-Scrolling Functionality in React


📈 30.84 Punkte
🔧 Programmierung

🔧 Virtual Scrolling in React: Implementation from scratch and using react-window


📈 30.84 Punkte
🔧 Programmierung

🔧 Infinite list loading 🤔, with React Query - useInfiniteQuery hook !


📈 28.14 Punkte
🔧 Programmierung

🔧 Optimized Infinite Scroll with Next.js 14 Server Actions and React Query


📈 28.14 Punkte
🔧 Programmierung

🔧 #2 React Query: Infinite Scroll


📈 28.14 Punkte
🔧 Programmierung

🔧 Mastering TanStack Query: A Comprehensive Guide to Efficient Data Fetching in React


📈 27.54 Punkte
🔧 Programmierung

🔧 Mastering React Query. Structuring Your Code for Scalability and Reusability


📈 27.54 Punkte
🔧 Programmierung

🔧 Mastering React Query: A Comprehensive Guide


📈 27.54 Punkte
🔧 Programmierung

🔧 How to scrape infinite scrolling webpages with Python


📈 27.04 Punkte
🔧 Programmierung

🔧 How to scrape infinite scrolling webpages with Python


📈 27.04 Punkte
🔧 Programmierung

🔧 How to create infinite scrolling with Tailwind CSS and JavaScript


📈 27.04 Punkte
🔧 Programmierung

🔧 Effortless Infinite Scrolling: How to Implement Lazy Loading with Intersection Observer


📈 27.04 Punkte
🔧 Programmierung

🔧 Master Infinite Scrolling in 20 Easy Steps


📈 27.04 Punkte
🔧 Programmierung

matomo