ionicons-v5-a Back
Advanced techniques for managing Query Parameters in React apps
react

4 min read

Advanced techniques for managing Query Parameters in React apps

Managing query parameters can be a challenging task, especially in complex reactive web applications with shareable URLs. Let's explore the approach I've developed after overcoming some initial challenges.


The problem

Managing query parameters can be a challenging task in large applications. Complexity arises when there are numerous instances where query parameters need modification, especially as the number of query parameters increases.

Handling various types of user interactions and integrating them with the app state becomes challenging, particularly in extensive and intricate reactive applications.

The case

Let’s outline the aspects that will be covered in this article:

  1. Reading from URL: The app should read query params on page load.
  2. Changing URL: URL should be changed on user’s events.
  3. Browser arrows: The app should react on back/forward browser buttons.
  4. The app should recover URL from state after you returned back from other routes.

All the examples will be given assuming developing single page React app with react-router.

The idea

The idea is as follows:

  1. The source of truth is always the app state, except 2 cases.
  2. The URL is the source of truth only in two cases:
    • when the back/forward button is pressed
    • when the page is loading.
  3. Whenever the app state changes, the URL changes accordingly.

Reading from URL

Reading from URL has 2 steps:

  const readQueryParams = () => {
    // 1. Converting URL from string to object
    const queryParams = (qs.parse(window.location.search.slice(1)) as unknown) as AppQueryParams;
    // 2. Filling app state with values
    fillStoreWithValues(queryParams);
  }

Changing URL

Changing URL has 2 steps:

  const setQueryStringUrl = () => {
    const params: AppQueryParams = {
      search: search || undefined
    };
 
    // 1. Stringifying params from app state
    const queryParams = qs.stringify(params);
 
    // 2. push only in case url changed
    if (
      `${window.location.origin}/?${queryParams}` !==
        window.location.href
    ) {            
      navigate(`?${queryParams}`);
    }
    return queryParams;
  };

Back/forward browser buttons

Using the readQueryParams method let’s setup back/forward buttons interactions:

  // reading query params after browser back button pressed
  useUpdateEffect(() => {
    if (navigationType === 'POP') {
      readQueryParams();
    }
    // eslint-disable-next-line react-hooks/exhaustive-deps
  }, [location.key]);

Change URL when app state is changed

Using the setQueryStringUrl method let’s setup changing URL after state is changed:

  useEffect(() => {
    // updating url query params after state is changed
    setQueryStringUrl();
    // eslint-disable-next-line react-hooks/exhaustive-deps
  }, [search]);

Conclusion

To witness this approach in action, please take a look at the demo. It’s important to note that the demo provides a simple example, but this approach becomes essential when you have complex interactions between your app’s state and URL. In such scenarios, you can effectively manage URL persistence and selectively merge specific portions of your store.

Demo


Dzmitry Kozhukh

Written by Dzmitry Kozhukh

Frontend developer


Next