TypeScript报错:参数类型无法赋值给never类型(mapDispatchToProps)
TypeScript报错:Argument of type is not assignable to parameter of type 'never'
问题表现
使用typesafe-actions做Redux类型推导时,通过ActionType<typeof actions>得到的Action类型被识别为never,dispatch调用时触发类型不匹配错误。
问题相关代码
Reducer侧Action定义:
export const setInfoGDPRAction = createAction(InfoActionTypes.SET_GDPR, (resolve) => (acceptedgdpr: boolean) => resolve(acceptedgdpr));
组件connect相关代码:
type Action = ActionType<typeof actions>; // 悬浮提示Action = never const mapStateToProps = (state: ApplicationState): RootProps => ({ data: state.data, } as RootProps); const mapDispatchToProps = (dispatch: React.Dispatch<Action>, props: RootProps): RootProps => ({ setGDPRData: (accepted: boolean) => dispatch(actions.setInfoGDPRAction(accepted)), } as RootProps); export default connect(mapStateToProps, mapDispatchToProps)(Root);
错误原因
ActionType推导为never的核心原因是传入的actions集合中没有可识别的合法action creator,常见触发场景有两个:
createAction写法错误:如果使用builder回调模式定义action,漏写末尾的执行括号(),会导致导出的是高阶函数而非标准action creator,类型工具无法识别其产生的action结构actions对象组装错误:导入action时路径不对、没有把定义好的action creator正确合并到actions对象中,会导致typeof actions对应的对象为空/无合法action creator,空联合类型的推导结果就是never
修复方案
- 修正action定义,根据你的使用场景二选一即可:
- 普通同步action场景,不需要套resolve回调层,直接传入payload构造函数:
export const setInfoGDPRAction = createAction( InfoActionTypes.SET_GDPR, (acceptedgdpr: boolean) => acceptedgdpr );- 如果是配合redux-promise等中间件使用的回调式builder写法,必须在
createAction调用末尾加()执行builder,返回真正的action creator:
export const setInfoGDPRAction = createAction(InfoActionTypes.SET_GDPR, (resolve) => (acceptedgdpr: boolean) => resolve(acceptedgdpr) )(); // 这里的括号不能漏 - 检查
actions对象的组装逻辑,确保所有定义的action creator都被正确合并到对象中,示例:// 导入所有模块的action import * as infoActions from './info-reducer'; import * as userActions from './user-reducer'; // 合并为统一actions对象 const actions = { ...infoActions, ...userActions }; // 此时再推导Action类型即可得到正确的action联合类型 type Action = ActionType<typeof actions>;
额外提示:
mapStateToProps和mapDispatchToProps中不建议用as RootProps做硬类型断言,断言会掩盖属性漏传、类型不匹配等潜在问题,去掉断言后TypeScript会自动做结构校验。
内容的提问来源于stack exchange,提问作者OJs
相关产品推荐
相关产品推荐

