You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
This might be a duplicate of #268, but I think this weighs in favor of treating #268 as a real bug (instead of as-designed) and actually fixing it. The short version is as follows. I created a slice with createSlice from reduxjs/redux-toolkit with an incrementNextId action:
describe("plain increment",()=>{// this passesit("should increment next_id",()=>{varstate=slice.slice_reducer(undefined,slice.incrementNextId({}))expect(state.next_id).toEqual(2)})})
Using the wrapped reducer does not with a nearly identical test (the only difference is which reducer is used and how we inspect state):
describe("undoable increment",()=>{// this failsit("should increment next_id",()=>{varstate=slice.undoable_slice_reducer(undefined,slice.incrementNextId({}))expect(state.present.next_id).toEqual(2)// nope, the value is actually 1})})
If I modify the second test as follows, it passes, which doesn't seem right:
describe("undoable increment",()=>{// this works, but it shouldn'tit("should increment next_id",()=>{varstate=slice.undoable_slice_reducer(undefined,slice.incrementNextId({}))// ignored?state=slice.undoable_slice_reducer(state,slice.incrementNextId({}))// this time, with feeling!expect(state.present.next_id).toEqual(2)// works now?})})
Here's where things get totally off the rails. This fails both tests:
describe("undoable increment",()=>{// this failsit("should increment next_id",()=>{varstate=slice.undoable_slice_reducer(undefined,slice.incrementNextId({}))expect(state.present.next_id).toEqual(2)// nope, the value is actually 1})// this fails, tooit("should also increment next_id",()=>{varstate=slice.undoable_slice_reducer(undefined,slice.incrementNextId({}))expect(state.present.next_id).toEqual(2)// nope, the value is actually 1})})
If I make the above modification to the first test, both tests now pass:
describe("undoable increment",()=>{// this works, but it shouldn'tit("should increment next_id",()=>{varstate=slice.undoable_slice_reducer(undefined,slice.incrementNextId({}))// ignored?state=slice.undoable_slice_reducer(state,slice.incrementNextId({}))// this time, with feeling!expect(state.present.next_id).toEqual(2)// works now?})// this now…works?it("should also increment next_id",()=>{varstate=slice.undoable_slice_reducer(undefined,slice.incrementNextId({}))expect(state.present.next_id).toEqual(2)// now this passes; WTF?!})})
If I move that approach to the second test, only it passes:
describe("undoable increment",()=>{// this failsit("should increment next_id",()=>{varstate=slice.undoable_slice_reducer(undefined,slice.incrementNextId({}))expect(state.present.next_id).toEqual(2)// nope, the value is actually 1})// this now…works?it("should also increment next_id",()=>{varstate=slice.undoable_slice_reducer(undefined,slice.incrementNextId({}))// ignored?state=slice.undoable_slice_reducer(state,slice.incrementNextId({}))// this time, with feeling!expect(state.present.next_id).toEqual(2)// works now?})})
One can work around this by adding the following to one's test case, but that just helps illustrate how weird this behavior is:
beforeEach(()=>{varstate=slice.undoable_slice_reducer(undefined,{}asAnyAction)// first no-opslice.undoable_slice_reducer(state,{}asAnyAction)// second no-op})
Both lines are necessary. If you omit the second, you'll still get failures.
posita
changed the title
redux-undo does not play well with reducers created with redux-toolkit's createSlice
Does not play well with reducers created with redux-toolkit's createSlice
Jun 24, 2020
This might be a duplicate of #268, but I think this weighs in favor of treating #268 as a real bug (instead of as-designed) and actually fixing it. The short version is as follows. I created a slice with
createSlice
from reduxjs/redux-toolkit with anincrementNextId
action:Here's the rub. Using the plain reducer works just like it should according to Redux's instructions on how to test reducers:
Using the wrapped reducer does not with a nearly identical test (the only difference is which reducer is used and how we inspect state):
If I modify the second test as follows, it passes, which doesn't seem right:
Here's where things get totally off the rails. This fails both tests:
If I make the above modification to the first test, both tests now pass:
If I move that approach to the second test, only it passes:
Complete source code is available via posita/redux-toolkit-undo-clash.
The text was updated successfully, but these errors were encountered: