The param title seems to be ignored by most browsers, so I think we should not pass it down to the browser as it may lead to confusion. But we can store it.
User Stories
As a Frontity developer
I want to use the replace method (instead of push)
so that update the most recent entry on the history stack
As a Frontity developer
I want to populate the state and title of each history entry
so that I can recover that state in Frontity when the user moves around
Possible solution
Initial proposed solution (click to open)
Add a second parameter to actions.router.set for these options.
actions.router.set("/a-url");
actions.router.set("/new-url", {
method: "push",
title: "Some title",
state: {
someState: "that I want to save",
},
});
actions.router.set("/other-url", {
method: "replace",
title: "Some other title",
state: {
otherState: "that I want to save",
},
});
Maybe we can use state.router.historyState instead of state.router.state? Does it make sense? It would provide more info than just calling it state, which besides being repetitive might also be confusing.
Iām a bit confused now, so I guess other users might be as well if they come to use this api. Is browserHistory editable or a read-only object? I mean, that as a user I might think that updating that part of the state is going to update the window.history.
EDIT:
It is more confusing to me that the browserHistory doesnāt exactly map to window.history.
One more thing: Iād avoid exposing the title field in the frontity api. As itās not used, Iād just internally set title to empty string in order to prevent any future bugs, but thatās it.
So my final API would look something like:
actions.router.set("/some-url", {
method: "push",
state: {
someState: "useful data to save",
},
});
state.router.link = "/current-url";
state.router.browserHistoryState = {
someState: "useful data to save",
};
// or
state.router.windowHistoryState = {
someState: "useful data to save",
};
I had doubts on what the state object stored in window.history should look like, because it was used to store the initial state.router.link and that link was used to update the state when popstate event was fired, i.e. when the user navigated back or forward though the history.
I decided to implement it in a way that what you get from window.history.state is exactly the same object you get from state.router.state, therefore removing the link field, and using window.location instead to update the app state when a popstate event fires.
In addition to this, I wasnāt sure to what value state.router.method should store after a popstate event. The options where to store the original method in window.store.state and restore that value, or actually store pop and making it clear this way that we arrived to the current state because the user moved through history.
I decided that the most useful info would be to store pop, because knowing the original method used to create that state didnāt seem to provide any useful information. So the values that can be found in state.router.method would be 'push' | 'replace' | 'pop'.
I might be wrong, so please go through the PR and let me know what you think and if I should make any changes.
state: An object that is saved in window.history. It will be recovered when the user navigates between different URLs with the Back and Forward button of the browser. The default is an empty object {}.
The state object passed in the options is saved in state.router.state.
The new method: "replace" option is useful to replace the current URL of the app, without creating a new entry in the history. It is particularly useful when you want to update the URL (or state object) of the current history entry in response to some user action that has changed the current URL but itās not perceived that way, like an infinite scroll or a swipe.
@orballo feel free to add more things if I missed something.