diff --git a/src/index.tsx b/src/index.tsx index 3418184..1f793db 100644 --- a/src/index.tsx +++ b/src/index.tsx @@ -181,63 +181,70 @@ export function useEffectReducer< effectsMap?: EffectsMap ): [TState, React.Dispatch] { const entitiesRef = useRef>>(new Set()); - const wrappedReducer = ( - [state, stateEffectTuples, entitiesToStop]: AggregatedEffectsState< - TState, - TEvent - >, - event: TEvent | FlushEvent - ): AggregatedEffectsState => { - const nextEffectEntities: Array> = []; - const nextEntitiesToStop: Array> = []; - - if (event.type === flushEffectsSymbol) { - // Record that effects have already been executed - return [state, stateEffectTuples.slice(event.count), nextEntitiesToStop]; - } - - const exec = ( - effect: TEffect | EffectFunction - ) => { - const effectObject = toEffectObject(effect, effectsMap); - const effectEntity = createEffectEntity( - effectObject - ); - nextEffectEntities.push(effectEntity); + const wrappedReducer = useMemo( + () => ( + [state, stateEffectTuples, entitiesToStop]: AggregatedEffectsState< + TState, + TEvent + >, + event: TEvent | FlushEvent + ): AggregatedEffectsState => { + const nextEffectEntities: Array> = []; + const nextEntitiesToStop: Array> = []; + + if (event.type === flushEffectsSymbol) { + // Record that effects have already been executed + return [ + state, + stateEffectTuples.slice(event.count), + nextEntitiesToStop, + ]; + } - return effectEntity; - }; + const exec = ( + effect: TEffect | EffectFunction + ) => { + const effectObject = toEffectObject(effect, effectsMap); + const effectEntity = createEffectEntity( + effectObject + ); + nextEffectEntities.push(effectEntity); - exec.stop = (entity: EffectEntity) => { - nextEntitiesToStop.push(entity); - }; + return effectEntity; + }; - exec.replace = ( - entity: EffectEntity, - effect: TEffect | EffectFunction - ) => { - if (entity) { + exec.stop = (entity: EffectEntity) => { nextEntitiesToStop.push(entity); - } - return exec(effect); - }; + }; + + exec.replace = ( + entity: EffectEntity, + effect: TEffect | EffectFunction + ) => { + if (entity) { + nextEntitiesToStop.push(entity); + } + return exec(effect); + }; - const nextState = effectReducer( - state, - event, - exec as EffectReducerExec - ); - - return [ - nextState, - nextEffectEntities.length - ? [...stateEffectTuples, [nextState, nextEffectEntities]] - : stateEffectTuples, - entitiesToStop.length - ? [...entitiesToStop, ...nextEntitiesToStop] - : nextEntitiesToStop, - ]; - }; + const nextState = effectReducer( + state, + event, + exec as EffectReducerExec + ); + + return [ + nextState, + nextEffectEntities.length + ? [...stateEffectTuples, [nextState, nextEffectEntities]] + : stateEffectTuples, + entitiesToStop.length + ? [...entitiesToStop, ...nextEntitiesToStop] + : nextEntitiesToStop, + ]; + }, + [effectReducer, effectsMap] + ); const initialStateAndEffects: AggregatedEffectsState< TState,