T
TanStack•2y ago
absent-sapphire

Type safe HistoryState in navigate

We're relying on HistoryState in our application and while params and search are both very well handled in the docs and the API, I find HistoryState far less easy to work with.. probably a skill issue 🙂 . I keep running in to the TS error using navigate
navigate({ to: "/foo", state: { bar }});
navigate({ to: "/foo", state: { bar }});
Object literal may only specify known properties, and 'bar' does not exist in type 'NonNullableUpdater<HistoryState>' The best workaround I found is when I want to use navigate is the following:
interface FooState extends HistoryState {
foo: string,
}
const newState = { foo: string } as FooState;
navigate({ to: "/foo", state: newState });
interface FooState extends HistoryState {
foo: string,
}
const newState = { foo: string } as FooState;
navigate({ to: "/foo", state: newState });
But this feels terrible and provides no type safety as I'm just casting it, would be nice to have something similar to validateSearch for State.. similarly when consuming state I have to do the same.
const Component = () => {
const { location } = useRouterState();
return location.state as FooState;
return (
<pre>{state.foo}</pre>
);
}
const Component = () => {
const { location } = useRouterState();
return location.state as FooState;
return (
<pre>{state.foo}</pre>
);
}
Any suggestions how to work with state in a type safe matter using the lib is greatly appreciated.
13 Replies
metropolitan-bronze
metropolitan-bronze•2y ago
This may have something to do with your set up. Could you give us a Stackblitz repro to poke around in? Here's a starter with the basics set up: https://stackblitz.com/github/tanstack/router/tree/main/examples/react/quickstart-file-based
StackBlitz
Router Quickstart File Based Example - StackBlitz
Run official live example code for Router Quickstart File Based, created by Tanstack on StackBlitz
absent-sapphire
absent-sapphireOP•2y ago
Thank you for showing interest @Sean Cassiere I'm actually using the Code Based Routing So I threw together a Stackblitz, based on the quickstart but more in line with how I structured it in my repo, to show how I avoid the TS error: https://stackblitz.com/edit/github-fy1g9w?file=src%2Fcomponents%2FHomePage.tsx
Peter Tellgren
StackBlitz
Code Based Router, History State - StackBlitz
Run official live example code for Router Quickstart, created by Tanstack on StackBlitz
metropolitan-bronze
metropolitan-bronze•2y ago
Oh... This is what you meant by HistoryState. Tanstack Router currently doesn't officially support passing data using the state property between routes since it cannot be made type-safe. HistoryState isn't persistent across Tabs and whilst I'm not well versed with the SSR stuff, I can't imagine it'll full to deal with over there either. Can I ask why the URL Query and Path parameters cannot be used here? Since none of the data actually being passed using state is actually private.
absent-sapphire
absent-sapphireOP•2y ago
so in one case we pass a File Object (that we want to carry with us through a wizzard like flow) and I'm not sure that can be passed in any other way (serialised in Search params?) until we have a server way of holding on to the file. We had this fully working with React Router so perhaps that is a better fit for us in the near term. Additionally we do work with sensitive data in this project and some clients (wrongfully IMO) oppose to putting some state in the URL wich I think would be a better place. ( but does also have some issues due to the length limitations, e.g. very long list of filters)
metropolitan-bronze
metropolitan-bronze•2y ago
Would React Context maybe fit this use case?
absent-sapphire
absent-sapphireOP•2y ago
the issue is that React Context is not persistent, where as state is persistent over page reloads
metropolitan-bronze
metropolitan-bronze•2y ago
Good point! Could you log an issue on github for this? I'll track put it down in the Maintainers channel. We'll see what Tanner and crew think about this.
absent-sapphire
absent-sapphireOP•2y ago
Yes, can and will do, but later today
metropolitan-bronze
metropolitan-bronze•2y ago
No probs, just drop the link here.
absent-sapphire
absent-sapphireOP•2y ago
oh, I had an intereting related issue that I'm not sure I fully understand, let me try to explain I have a route say /thing/$id that contains a button that takes me to /thing/$id/nested with some state.. on the nested page I have a component that uses history state, and a back button. but when I go back it still renders the nested component and throws error. I think this bug is also present on https://tanstack.com/router/latest/docs/framework/react/examples/basic 1. Go to Posts 2. click a post in the list 3. Click the last one ( Not found) 4. click a post in the list: - Not found still visible
React Router Basic Example | TanStack Router Docs
An example showing how to implement Basic in React Router
absent-sapphire
absent-sapphireOP•2y ago
However, in my scenario if I wrapped the state in useMemo and prevented them from being undefined the page did eventually render the correct component 🤔
harsh-harlequin
harsh-harlequin•2y ago
No description
wise-white
wise-white•4w ago
Hey guys, I have a scenario very similar to Peter's scenario. So, I was wondering if you have any updates on this.

Did you find this page helpful?