实现高阶缩减器(createReducer
)函数非常简单,但是编写类型定义(CreateReducer
)如下所示更为复杂
// HELPER TYPES
type SimpleAction<ActionType> = {
type: ActionType
}
interface PayloadAction<Payload, AT> extends SimpleAction<AT> {
payload: Payload
}
type Reducer<State, Action extends SimpleAction<Action['type']>> = (state: State, action: Action) => State
type PureReducer<State, Action extends SimpleAction<Action['type']>> = (state: State, action: Action) => State
// COUNT EXAMPLE TYPES
type Count = number
const increment = 'increment'
type IncrementAction = SimpleAction<typeof increment>
type ActionReducerMap<State, Action extends SimpleAction<Action['type']>> = { [ActionType in Action['type']]: PureReducer<State, SimpleAction<ActionType>> }
const countActionReducerMap: ActionReducerMap<Count, IncrementAction> = {
[increment]: (count, { type }) => count + 1,
}
type CreateReducer = <State>(initialState: State) => <Action extends SimpleAction<Action['type']>>(arm: ActionReducerMap<State, Action>) => Reducer<State, Action>
const createReducer: CreateReducer = initialState => arm => (state = initialState, action) => {
const actionTypes = Object.keys(arm)
if (actionTypes.includes(action.type)) {
return arm[action.type](state, action)
} else {
return state
}
}
// Count reducer using previously created count action reducer map
const countReducer = createReducer(0)(countActionReducerMap)
// Seemingly the same reducer except that the action reducer map is passed as an object literal inline
const countReducerInline = createReducer(0)({
// ERROR Parameter 'count' implicitly has an 'any' type
[increment]: (count, { type }: IncrementAction) => count + 1,
})
// Both reducers work as expected
console.log(countReducer(1, { type: increment })) // 2
console.log(countReducerInline(1, { type: increment })) // 2
您如何解决有关countReducerInline
函数的类型错误?
或您将如何实现CreateReducer
类型?