2
votes

I have a route page with a datatable fetch data when component mount. When I click on the same react-router-dom Link (to the route above) multiple times, it seems like component only unmount when the route change (with different component to be render).

I want the component to be forced remount when click on the same link again in order to fetch new data. Are there any options in react-router-dom Link or any other Link component or any trick to do this?

My sample code here: https://codesandbox.io/s/react-router-9wrkz

I want the About component will remount when click About link multiple times

4
I've updated my answer with your codesandbox - Mohamed Ramrami
Nice, thanks @Mohamed Ramrami, is this the best practice to achieve this - Quoc Van Tang
I don't know if it's the 'best', but probably the simplest way to force a re-mount. - Mohamed Ramrami

4 Answers

13
votes

One way to force a component to re-mount is to change the key prop (you can use Date.now() or props.location.key):

  <Route
    path="/about"
    render={props => <About key={props.location.key} {...props} />}
  />
2
votes

You can use this method for rendering

componentWillReceiveProps(recievedProps) {
    console.log("componentWillReceiveProps called");
    if (
      recievedProps &&
      this.props &&
      recievedProps.location &&
      this.props.location &&
      recievedProps.location.key &&
      this.props.location.key &&
      recievedProps.location.key !== this.props.location.key
    ) {
      this.setState({ loading: true });
      promise().then(result => {
        this.setState({ value: result, loading: false });
      });
    }
  }
0
votes

For future reference. In addition to the answers mentioned above I needed to tweak some things because none of them worked as desired for me. The comparing of props was mentioned before, but because the key is in an object (reference) it never saw the update (you're comparing the same object). So I keep track by saving it as a prop.

I like using the componentDidUpdate better because you aren't unmounting and mounting an entire component when probably all you need is to update certain elements,

For this example your component does need to be linked using withRouter(), so you can access the route props.

    // You cant use prevProps because object will be the same, so save it in component
    private currentRouteLocationKey: string| undefined; 

    public componentDidUpdate(): void {
    const currentRouteKey = this.props.history.location.key;

        // Compare keys so you only update when needed
        if (this.currentRouteLocationKey !== currentRouteKey) {
            // Add logic you want reset/ updated
            this.refreshPage();

            // Save the new key
            this.currentRouteLocationKey = currentRouteKey;
        }
    }
-2
votes

Why not just force reloading onClick by creating a function in your component:

remount(){
    location.reload(true);
}

And then assign onClick handler to the Link:

<Link to="/your route" onClick = {this.remount}>

Seems to work fine unless you have objections to reloading the page.