Part 83: Enhancing the Search Experience: From Test Data to Real-time Search in Next.Js
[App] Client-Side Data Fetching

The power of a search feature lies in its ability to quickly and accurately deliver relevant results to users. Our SearchBox component was initially built using test data, which limited its functionality. Now, it's time to elevate the user experience by enabling the search across all available reviews, ensuring users can find exactly what they're looking for. In this post, we'll explore how to achieve this by fetching real data and optimizing our component for a seamless search experience.
Transitioning from Test Data to Real Data
Understanding Client vs. Server Components
Our SearchBox is a Client Component, which means it cannot directly fetch data in the same way a Server Component can. Server Components can declare their functions as asynchronous and perform data fetching within them, but this isn't possible for Client Components. However, we can use a clever workaround: fetching data in a Server Component and passing it as a prop to the Client Component.
Fetching Data in the Server Component
We begin by updating our ReviewsPage component, which is a Server Component. Here, we can load the data we need and pass it down to the SearchBox.
Define a New Data Fetching Function: We create a new function
getSearchableReviewsthat fetches theslugandtitlefor all reviews://lib/reviews.js export async function getSearchableReviews() { const { data } = await fetchReviews({ fields: ['slug', 'title'], sort: ['publishedAt:desc'], pagination: { pageSize: 100 }, }); return data.map(({ attributes }) => ({ slug: attributes.slug, title: attributes.title, })); }Integrate Data Fetching in
ReviewsPage: We call this new function within theReviewsPagecomponent and pass the result to theSearchBox.import { getReviews, getSearchableReviews } from '@/lib/reviews'; export default async function ReviewsPage({ searchParams }) { const page = parsePageParam(searchParams.page); const { reviews, pageCount } = await getReviews(PAGE_SIZE, page); console.log('[ReviewsPage] rendering:', page); return ( <> <Heading>Reviews</Heading> <div className="flex justify-between pb-3"> <PaginationBar href="/reviews" page={page} pageCount={pageCount} /> </div> <ul className="flex flex-row flex-wrap gap-3"> {reviews.map((review, index) => (
Optimizing the Search Functionality
With real data now available to the SearchBox, we need to enhance its functionality to ensure a smooth user experience.
Implementing Case-Insensitive Search
To make the search case-insensitive, we convert both the review titles and the user's query to lowercase before performing the search.
//SearchBox.jsx
//remove const reviews = [
export default function SearchBox(reviews) {
const filtered = reviews.filter((review) =>
review.title.toLowerCase().includes(query.toLowerCase())
).slice(0, 5);
Limiting Search Results
To prevent overwhelming the user with too many results, we limit the number of displayed options to five. This is achieved using the slice method.
Understanding Data Flow
The SearchBox component receives the reviews prop from the ReviewsPage, which is a Server Component. This data is passed through JavaScript injected into the page by Next.js, ensuring it can be used by the Client Component to filter results dynamically.
Considerations for Data Passing
While this method effectively provides the SearchBox with the necessary data, it's important to be mindful of the potential increase in page size. The data is passed as a JavaScript object, increasing the page's weight. In scenarios where the data set might grow significantly, alternative strategies, such as client-side fetching, could be explored to maintain optimal performance.
Conclusion
By fetching real data and enhancing the search logic, we've transformed our SearchBox into a robust and efficient tool for navigating reviews. This approach demonstrates the power of integrating client-side interactivity with server-side data handling, a crucial technique for modern web applications. As we continue to refine this feature, exploring client-side data fetching will open new doors for further improvements in scalability and performance. Stay tuned for more updates as we continue to enhance our application's search capabilities!
Last updated