DEV Community

codeek
codeek

Posted on

🚀 Stop Filtering on the Frontend, Build Server-Side Search in React using React Query For Performance Optimization

Searching using React query

Every React Developer Has Done This at Least Once 😅

const filteredProducts = products.filter((product) =>
  product.title.toLowerCase().includes(search.toLowerCase())
);
Enter fullscreen mode Exit fullscreen mode

It works...

Until your API returns 10,000+ products.

Now you're downloading thousands of unnecessary records just to search for a single keyword.

  • ❌ Slower loading
  • ❌ Wasted bandwidth
  • ❌ High memory usage
  • ❌ Doesn't scale

So what's the better approach?

🚀 The Solution: Server-Side Search

Instead of downloading every product and filtering them inside React, let your backend search the database and return only the matching records.

When you combine this with TanStack React Query, you also get:

  • ✅ Automatic caching
  • ✅ Loading states
  • ✅ Background refetching
  • ✅ Request deduplication
  • ✅ Cleaner server-state management

In this guide, we'll build a production-ready server-side search using React Query.


Why Server-Side Search?

Imagine an ecommerce application with 100,000 products.

❌ Client-Side Search

Frontend
     ↓
GET /products
     ↓
100,000 products
     ↓
React filters data
Enter fullscreen mode Exit fullscreen mode

Problems

  • Huge API responses
  • Slow initial loading
  • High memory usage
  • Wasted network bandwidth
  • Poor scalability

✅ Server-Side Search

Frontend
     ↓
GET /products?search=iphone
     ↓
Backend searches database
     ↓
Returns only matching products
Enter fullscreen mode Exit fullscreen mode

Benefits

  • Faster responses
  • Smaller payloads
  • Better scalability
  • Lower memory usage
  • Better user experience

Project Structure

src
├── api
│     productApi.js
│
├── hooks
│     useProducts.js
│
├── pages
│     ProductPage.jsx
│
└── components
      SearchInput.jsx
Enter fullscreen mode Exit fullscreen mode

Keeping your API logic separate from your UI makes applications much easier to maintain as they grow.


Step 1 — Install React Query

npm install @tanstack/react-query axios
Enter fullscreen mode Exit fullscreen mode

Create your Query Client.

const queryClient = new QueryClient();

<QueryClientProvider client={queryClient}>
  <App />
</QueryClientProvider>;
Enter fullscreen mode Exit fullscreen mode

Step 2 — Create the API Function

Your backend should support query parameters like this:

GET /products?search=iphone
Enter fullscreen mode Exit fullscreen mode

Create the API function.

export const getProducts = async (search) => {
  const response = await axios.get("/products", {
    params: {
      search,
    },
  });

  return response.data;
};
Enter fullscreen mode Exit fullscreen mode

Instead of filtering on the frontend, we're sending the search value directly to the backend.


Step 3 — Create a React Query Hook

export const useProducts = (search) => {
  return useQuery({
    queryKey: ["products", search],
    queryFn: () => getProducts(search),
  });
};
Enter fullscreen mode Exit fullscreen mode

This is where React Query really shines.

Every unique search term gets its own cache automatically.

Searching for:

iphone
Enter fullscreen mode Exit fullscreen mode

and later:

samsung
Enter fullscreen mode Exit fullscreen mode

creates two independent cached queries without any extra code.


Step 4 — Create Search State

const [search, setSearch] = useState("");
Enter fullscreen mode Exit fullscreen mode
<input
  value={search}
  onChange={(e) => setSearch(e.target.value)}
  placeholder="Search products..."
/>
Enter fullscreen mode Exit fullscreen mode

Step 5 — Fetch Products

const { data, isLoading } = useProducts(search);
Enter fullscreen mode Exit fullscreen mode

Every time the search changes:

User Types
      ↓
React State Updates
      ↓
React Query
      ↓
Backend API
      ↓
Updated Products
Enter fullscreen mode Exit fullscreen mode

No client-side filtering required.


Step 6 — Render Products

{
  data?.products?.map((product) => (
    <ProductCard key={product.id} product={product} />
  ));
}
Enter fullscreen mode Exit fullscreen mode

That's it.

React Query automatically handles:

  • Caching
  • Loading states
  • Background refetching
  • Request deduplication
  • Server-state synchronization

⚡ Bonus Improvement: Debounce Search

Without debouncing:

i
ip
iph
ipho
iphon
iphone
Enter fullscreen mode Exit fullscreen mode

That's 6 API requests.

Instead, debounce the search input by 300–500ms so the request is only sent after the user pauses typing.

This significantly reduces unnecessary API calls while keeping the UI responsive.


Complete Flow

User Types
      ↓
Search State Updates
      ↓
React Query detects new queryKey
      ↓
Calls Backend API
      ↓
Database searches records
      ↓
Returns matching products
      ↓
React UI updates
Enter fullscreen mode Exit fullscreen mode

Simple.

Clean.

Scalable.


Why React Query Makes This Better

Without React Query, you'd have to manually manage:

  • Loading states
  • Error handling
  • Caching
  • Duplicate requests
  • Background refetching

React Query gives you all of these features out of the box, making it a perfect companion for server-side search.


Final Thoughts

Client-side searching is completely fine for small datasets.

However, once you're building applications like:

  • 🛒 Ecommerce
  • 📊 Admin Dashboards
  • 👥 CRM Systems
  • 📦 Inventory Management
  • 🏢 HR Platforms

server-side search becomes the professional solution.

Your frontend stays lightweight, your backend does the heavy lifting, and your users enjoy a much faster experience.


🎥 Watch the Full Video Tutorial

This article is part of my Modern Ecommerce in React & Modern Stacks (2026) series.

▶️ Full Playlist

https://www.youtube.com/watch?v=Jluy-W9eP-4&list=PL_02r0p8Ku_6tR8L-n-yj7MW8rrMtswwk&index=1

In Episode 11, I walk through the complete implementation of server-side search using React Query, Axios, and backend query parameters.

👉 Watch Episode 11

https://www.youtube.com/watch?v=QrA5_bvORZU&list=PL_02r0p8Ku_6tR8L-n-yj7MW8rrMtswwk&index=11

If you're following the full series, you'll learn how to build a production-ready ecommerce application from scratch using modern React technologies.


If this article helped you, consider following Codeek for more tutorials on React, TypeScript, Chakra UI, TanStack Query, Zustand, Stripe, Firebase, and full-stack development.

Happy coding! 🚀

Top comments (0)