effector / vite-react-template

Try effector with React in seconds!
https://stackblitz.com/edit/effector-react
21 stars 2 forks source link

HMR #3

Open iposokhin opened 2 years ago

iposokhin commented 2 years ago

There are two issues related with hot module replacement(HMR), these issues is following:

  1. keep states of stores between module replacements
  2. avoid duplicates of units and connection between units

For example we have two files a.ts and b.ts:

// a.ts

import { createEvent } from "effector";

export const reset = createEvent();
export const inc = createEvent();
export const dec = createEvent();
// b.ts

import { inc, dec, reset } from "./a";
import { attach, createStore, sample } from "effector";

export const $count = createStore(0)
  .on(inc, (count) => count + 1)
  .on(dec, (count) => count - 1)
  .reset(reset);

const logFx = attach({
  source: $count,
  effect(count) {
    console.log("COUNT: ", count);
  },
});

sample({
  clock: $count,
  target: logFx,
});
import { $count } from "./a";
import { inc, dec } from "./b";
import { useStore } from "effector-react";
import React from "react";

export function App() {
  const count = useStore($count);

  return (
    <>
      <div>Count: {count}</div>
      <button onClick={() => inc()}>+</button>
      <button onClick={() => dec()}>-</button>
    </>
  );
}

When we start project this files will be compiled and executed by compiler, so we will have one set of units and connections. But when we make a change, vite's hmr will replace changed module and the compiler compiles and executes the changed module again. After all we have two copies of units and connections. Thus, we get a copy for each replaced module.

How to reproduce:

  1. make change in the beginning of the b.ts file
  2. increase or decrease counter
  3. check console, when logger effect fired twice

What I think about possible solutions.:

  1. For the second issue: we could create domain for each module and wrap up all content of module in withRegion, and when hmr is fired we could clean replaced module
  2. For both issues: we need a more stable sids that is not related from position in file and can keep between hmr
sergeysova commented 1 year ago

At the moment I just disable fastRefresh