带有打字稿的 Redux Thunk [英] Redux Thunk with Typescript

查看:41
本文介绍了带有打字稿的 Redux Thunk的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在学习 Typescript,并且正在尝试实现一个简单的 React/Redux 应用程序.当我使用同步操作时,它工作正常,但问题出在异步操作上.我正在关注官方的 redux 教程.

首先我声明会话的状态

导出接口 UserSessionState {登录:布尔值;}

然后我声明动作的接口

interface UpdateSessionAction {类型:'USER_LOGIN';有效载荷:布尔值;}

我用联合类型导出它们

导出类型 UserActionTypes = UpdateSessionAction;

然后我有实际的行动

<预><代码>导出函数 updateSession(loggedIn: UserSessionState) {返回 {类型:'USER_LOGIN',有效载荷:登录,};}

我有一个假的api调用

function api() {返回 Promise.resolve(true);}

最后是登录

export const userLogin = (): ThunkAction<空白,{},{},任何动作>=>异步(调度:ThunkDispatch<{}, {}, AnyAction>)=>{const res = 等待 api();dispatch(updateSession({ login: res }));};

在reducer中我只是简单地初始化状态

initialState: UserSessionState = {loggedIn: false}

然后我为减速器做普通的 redux 东西.

最后在我的商店中调用用于检查状态的初始操作

store.dispatch(userLogin());

我不断收到此错误:

'ThunkAction, {}, {}, AnyAction>' 类型的参数不可分配给AnyAction"类型的参数.类型ThunkAction, {}, {}, AnyAction>"中缺少属性type"但在AnyAction"类型中是必需的.

我缺少一个 type 但我不知道我做错了什么.

解决方案

简而言之:

您收到此错误是因为从您的 userLogin() 函数返回的是一个 ThunkAction,缺少 type

为什么会这样?

dispatch 应该接受 AnyAction 类型的参数.AnyAction 是一个 redux 类型,它扩展了 Action(有一个强制属性 type).

这是来自当前的 redux 类型文件

export interface Action{类型:T}/*** 接受任何其他属性的 Action 类型.* 这主要是针对`Reducer`类型的使用.* 这不是`Action` 本身的一部分,以防止用户扩展`Action.*/导出接口 AnyAction 扩展 Action {//允许在动作中定义任何额外的属性.[额外道具:字符串]:任何}

如何解决?使用 ThunkDispatch 类型代替 redux 的标准 Dispatch.以下示例以及更多示例可在 this Gist

上找到

const mapDispatchToProps = (dispatch: ThunkDispatch) =>{返回 {onRequestClick: (arg: any) =>调度(myAsyncAction(arg)),};}

另外,请参阅此文章,部分将调度映射到道具

I am learning Typescript and I am trying to implement a simple React/Redux app. When I use sync actions it works fine, but the problems are with the async action. I am following the official redux tutorial.

First I declare the state for the session

export interface UserSessionState {
  loggedIn: boolean;
}

Then I declare the interface for the action

interface UpdateSessionAction {
  type: 'USER_LOGIN';
  payload: boolean;
}

I export them with Union Types

export type UserActionTypes = UpdateSessionAction;

Then I have the actual Action


export function updateSession(loggedIn: UserSessionState) {
  return {
    type: 'USER_LOGIN',
    payload: loggedIn,
  };
}

I have a fake api call

function api() {
  return Promise.resolve(true);
}

And finally the login

export const userLogin = (): ThunkAction<
  void,
  {},
  {},
  AnyAction
> => async (dispatch: ThunkDispatch<{}, {}, AnyAction>) => {
  const res = await api();
  dispatch(updateSession({ loggedIn: res }));
};

In the reducer I simply initialize the state

initialState: UserSessionState = {loggedIn: false}

Then I do the normal redux stuff for the reducer.

Finally in my store I call the initial action for checking the state

store.dispatch(userLogin());

I keep getting this error:

Argument of type 'ThunkAction<Promise<void>, {}, {}, AnyAction>' is not assignable to parameter of type 'AnyAction'.
  Property 'type' is missing in type 'ThunkAction<Promise<void>, {}, {}, AnyAction>' but required in type 'AnyAction'.

I am missing a type but I have no idea what I do wrong.

解决方案

In short:

You get this error because what returned from your userLogin() function is a ThunkAction, which is missing type

Why this is happening?

dispatch should accept parameter of type AnyAction. AnyAction is a redux type, which extends Action (which have a mandatory property type).

This is from the current redux types file

export interface Action<T = any> {
  type: T
}

/**
 * An Action type which accepts any other properties.
 * This is mainly for the use of the `Reducer` type.
 * This is not part of `Action` itself to prevent users who are extending `Action.
 */
export interface AnyAction extends Action {
  // Allows any extra properties to be defined in an action.
  [extraProps: string]: any
}

How to fix it? Use ThunkDispatch type instead of redux's standard Dispatch. The following example and more can be found on this Gist

const mapDispatchToProps = (dispatch: ThunkDispatch<MyState, void, Action>) => {
  return {
    onRequestClick: (arg: any) => dispatch(myAsyncAction(arg)),
  };
}

Also, see this article, section Map Dispatch to Props

这篇关于带有打字稿的 Redux Thunk的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆