prefresh-vite is not preserving the state of a component
SuperDisk opened this issue · 12 comments
I'm making my own prefresh integration for fun, and I decided to compare the behavior of mine to a known working implementation so I could verify how it works. My custom integration (done by basically following the blog post and reading a bit of the prefresh-vite
code) works, and when I update a component it preserves state unless I add or remove hooks.
I tried prefresh-vite
however and it's actually not working-- I created a sample application with npm init preact
and put this code in index.jsx
:
import { render } from 'preact';
import {useState} from 'preact/hooks';
export function App() {
const [ctr, setCtr] = useState(0);
return (
<div>
<p>The counter: {ctr}</p>
<button onClick={() => setCtr(ctr+1)}>Increment</button>
</div>
);
}
render(<App />, document.getElementById('app'));
When I modify something (like just changing some text inconsequentially) it instantly updates in the browser but also resets the counter to 0 every time. I'm not sure what's happening, I put a breakpoint in flushUpdates
and it doesn't throw an exception (I don't think).
Hey, it's been a while since I looked at this repo. I tried running the tests which fail on full browser reload as well as made a new vite app with Preact and it worked. Do you have a repro or do you want to work on a fix?
Hmm, so you couldn't reproduce it? The code above is pretty much it. Here's the behavior I'm seeing:
prefresh-.2.mp4
My vite.config.js
is the default:
import { defineConfig } from 'vite';
import preact from '@preact/preset-vite';
// https://vitejs.dev/config/
export default defineConfig({
plugins: [preact()],
});
I just tried creating a Preact app with preact-cli
(which I think uses webpack?) and the behavior there seems to work-- that is, updating the code doesn't reset the counter. So it's potentially an issue with the Vite integration?
npm init preact creates a vite one which seemed to work, your vite configuration should work unless you have to explicitly enable prefresh. Or it's a bug in a recent vite version
What does npx vite --version
show for you in your npm init preact
project?
Not at home atm but the tests use v5 https://github.com/preactjs/prefresh/blob/main/test/fixture/vite/package.json that being said, let's not make this issue a debugging session. I can either look at it in the next few weeks or as you have a working impl feel free to look into it
Just got back to this seems to work just fine on #544
FWIW this still doesn't work for me with a freshly generated npm init preact
project. I also changed vite to latest
in package.json
and it has the same problem.
Mind creating a reproduction then?
For me, when I modify anything in index.jsx, the whole state gets reset.
But that's the function that contains render
, that's expected because as mentioned in the memory leak issue, ESM HMR creates a new copy of the file. Also creating a repro in stackblitz etc makes it a lot easier to talk about.
i.e. if I move your Counter
to a new file, that does not contain render()
everything works just fine.
Yep you're right, sorry for the confusion. I guess looking back it should have been obvious that HMR is re-executing all that stuff. Thanks.