Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Access React Router history stack

I have an application where you arrive at a photo album listing via various means (searching, drill down by category, etc). From the album, you click open individual photos and iterate through them using left/right arrows, as well as various editing tools. Each of the iterate/tool actions does a history.push() to add the route to the router history. I am trying to implement a button that will go back to the exact place in the history before you started viewing individual photos. To do that, I'd like to walk the history stack backwards to the point where the the history matches 1 of several patterns then do a history.go(-14) (or whatever) to jump back to the route that started the whole chain.

I've been searching the React router code as well as the HTML5 History object and I don't see any way of accessing the history stack directly so I can walk it back. I'd rather not depend on making each individual photo action push their path to a separate place since that makes it fragile (each photo action is built by a different developer and adding new actions in the future will require previous knowledge to remember to do that).

I can't go to a hard coded path because that would be pushed to the top of the history stack and hitting back arrow would just return you to the last individual photo page instead of the search page that generated the album list in the first place.

Any suggestions on accessing the history stack?

like image 957
John P Avatar asked May 29 '18 01:05

John P


People also ask

How do I access history stack in react router?

History / useHistory is no longer available in React router v6. You can use useNavigate and location state property to figure out from where to the current location is navigated from. Like explained in here.

How do I see previous route history in react?

To detect previous path in React Router, we can set the state property to an object with the location. pathname as the value. <Link to={{ pathname: "/nextpath", state: { prevPath: location.

How do I access stack history?

history object allows you to access the history stack of the browser. To navigate to a URL in the history, you use the back() , forward() , and go() methods. The history. length returns the number of URLs in the history stack.


1 Answers

I do not know if this would be relevant to your case anymore since this is an old question, but I will put this answer here since I had to solve a similar problem myself.

In my own research, I was not able to find a "history.stack" object, but there is a workaround that is also listed here. Basically, you set up a goBack counter that gets passed to the next route as location state. You can then go back the in the stack however many times the counter says to.

let goBack
if (history.location.state) {
    goBack = history.location.state.goBack
} else {
    goBack = -1
}

You can pass location state in React Links by replacing the to= prop with an object.

<Link to={
    { pathname: "/next/path", state: { goBack: goBack - 1 } }
}> Click Here! </Link>

You then just call history.go(history.location.state.goBack) whenever you need to go to the entry route.

If you have the possibility of entering one of the changed routes without hitting the entry one (like a user copies and pastes a URL pointing to a single image), then you can add default behaviour.

if (history.location.state) {
    history.go(history.location.state.goBack)
} else {
    // You can add a default action if a user lands on route from an external link
    history.push('/base/url')
}

This solution could also work if you need more complex behaviours like having 'checkpoint' routes that skip any routes in between as you go back. Just change goBack to be a list of numbers (representing the gaps in between each go-back jump) that you can pop each time you revert back to a checkpoint.

Another solution that might tickle your fancy is to just replace the route instead of pushing it to the stack, but this requires writing a custom component that wraps Link. You can find how to do that here

like image 198
Noah May Avatar answered Oct 06 '22 10:10

Noah May