Capeudinho
Capeudinho

Reputation: 33

How to re-render component on url change

In the GroupInfo component of my application, there is an useEffect that should trigger when the match from props change. But it does not. The code of the useEffect is as follows.

useEffect
(
    () =>
    {
        try
        {
            const runEffect = async () =>
            {
                const _id = match.params.id;
                const response = await api.get
                (
                    "/groupidindex",
                    {
                        params:
                        {
                            _id
                        }
                    }
                );
                setGroup (response.data);
            }
            runEffect();
        }
        catch (error)
        {
            throw new Error (error);
        }
    },
    [match]
)

And the piece of code where the link is set is the following.

<Link key = {index} to = {match.url.concat ("/"+group._id)}>

The declaration of the component in the App.js file is the following.

<Route path = "/groups/:id/:id" component = {GroupInfo}/>

The GroupInfo component does not render when the path meets the requirements, and does not re-render when the path changes. It renders/re-renders when I reload the page, however. I used an useEffect that changed on url change before, in another component of the same application, and it worked fine.

Upvotes: 2

Views: 1423

Answers (1)

Thomas
Thomas

Reputation: 12657

Are you sure that the match object changes, or just some of its properties?

Besides that, your try...catch block is useless. There can never be an error in this code that it would catch.

const runEffect = async () => {...} may throw an syntax error, but no runtime error that try..catch can handle. And runEffect() can return a rejected Promise, but your try..catch won't deal with that either. unless you await runEffect().

And I find it pointless to re-throw new Error(error); inside a Promise chain, all this will get you is a Uncaught (in promise) ... error entry in the console.

I tried, however, substitute "[match]" with "[match.url]" in the useEffect and nothing changed.

sry, I don't know about that; maybe it's a bit too late over here. But ultimately you only care about the id-param, don't you?

I'd write it like this:

// you can put these outside the component itself as 
// they don't rely on anything but the passed arguments:
const getGroup = async (_id) => {
  const response = await api.get("/groupidindex", {
    params: {
      _id
    }
  });

  return response.data;
}

const logError = error => {
  console.error(error) 
};

// in the component
useEffect(() => {
  getGroup(match.params.id).then(setGroup).catch(logError);
}, [match.params.id])

Now, concerning the try...catch, I used it there because of a warning message in the application's backend. The message was: "UnhandledPromiseRejectionWarning: Unhandled promise rejection.

If you don't care about the error and just don't want the error-message, you can .catch() the error with a function noop(){}.

Upvotes: 1

Related Questions