v0.8.0
This release contains a couple breaking changes, including one that will affect almost all existing users. The plan is for these to be the final breaking changes before 1.0 is released, and that 1.0 will hopefully be out within the next couple weeks.
Breaking Changes
createSlice
Now Requires a name
Field
So far, createSlice
has accepted an optional field called slice
, which is used as the prefix for action types generated by that slice:
const counterSlice1 = createSlice({
slice: "counter", // or could be left out entirely
initialState: 0,
reducers: {
increment: state => state + 1,
}
});
The slice
field has been changed to name
, and is now required to be a non-empty string.
const counterSlice1 = createSlice({
name: "counter", // required!
initialState: 0,
reducers: {
increment: state => state + 1,
}
});
This removes cases where multiple slices could have accidentally generated identical action types by leaving out the slice name while having similar reducer names. The field name change from slice
to name
was made to clarify what the field means.
Migration: change all uses of slice
to name
, and add name
to any createSlice()
calls that didn't specify it already.
createAction
Defaults to a void
Payload Type
Previously, createAction("someType")
would default to allowing a payload type of any
when used with TypeScript. This has been changed to default to void
instead. This means that you must specify the type of the payload, such as createAction<string>("someType")
.
Note that this is not necessary when using createSlice
, as it already infers the correct payload types based on your reducer functions.
Migration: ensure that any calls to createAction()
explicitly specify the payload type as a generic.
Other Changes
createSlice
Exports the Case Reducer Functions
createSlice
already returned an object containing the generated slice reducer function and the generated action creators. It now also includes all of the provided case reducers in a field called caseReducers
.
const todosSlice = createSlice({
name: "todos",
initialState: [],
reducers: {
addTodo(state, action) {
const {id, text} = action.payload;
state.push({id, text});
},
toggleTodo(state, action) {
const todo = state[action.payload.index];
todo.completed = !todo.completed
}
},
extraReducers: {
["app/logout"](state, action) {
return []
}
}
});
console.log(todosSlice)
/*
{
name: "todos",
reducer: Function,
actions: {
addTodo: Function,
toggleTodo: Function,
},
caseReducers: {
addTodo: Function,
toggleTodo: Function
}
}
*/
Notes
Special thanks to @phryneas for coaching me through finally starting to get a vague grasp on some very complicated TS types :)
Changelog
- Create slice changes (@phryneas - #197)
- Include case reducers in createSlice result (@markerikson - #209)
- Use
void
instead ofany
for undefined payloads (@Krisztiaan , @markerikson - #174) - Improve reducer warning (@markerikson - #207)
- change inference behaviour in old TS versions (@phryneas - #166)