如何使类型安全操作与 redux 逻辑转换一起工作?

How to make typesafe-actions work with redux-logic transform?

Redux-logic 提供了一种称为 transform 的方法,它允许在 action 到达 reducer 之前对其进行转换。这对各种情况都有帮助。通常我想分派一个只有我的用户输入的操作,有时我的 reducer 需要支持数据才能执行状态更新。

因此,我可以在 redux-logic 转换过程中执行此操作,但这似乎与类型安全操作(我也在使用)冲突。我怎样才能告诉 typescript 我的动作在到达 reducer 之前已经被转换了?

想象一下,我使用 { userName: string } 这样的有效负载进行调度,但我的转换过程添加了 属性,所以我得到 { userName: 'John Doe', recordId: 9 }.

我是打字稿的新手,但意识到我知道如何解决这个问题。

在reducer中我们通常导入action类型,它是这样的:

// actions.ts
import { action } from 'typesafe-actions';
import actionTypes from './actionTypes';

export const someAction = (data) = action(
  actionTypes.SOME_ACTION_TYPE,
  { data },
);

// reducer.ts
import { ActionType } from 'typesafe-actions';
import { StateSlice } from './types';
import * as actions from './actions';

const initialState: StateSlice = { ... };

const reducer = (state = initialState, action: ActionType<typeof actions>): StateSlice => {
  ...
};

因此,要更新它以接受已被 redux-logic 中间件修改的操作,我们必须告诉 typescript 该类型已被扩展。它是这样的:

// actions.ts
import { action } from 'typesafe-actions';
import actionTypes from './actionTypes';

export const someAction = (data) = action(
  actionTypes.SOME_ACTION_TYPE,
  { data },
);

// reducer.ts
import { ActionType } from 'typesafe-actions';
import { StateSlice, SOME_TYPE } from './types';
import * as actions from './actions';

type OriginalAction = ActionType<typeof actions.someAction>;
interface MutatedAction1 extends OriginalAction {
  payload: OriginalAction['payload'] & {
    thingWeAddedInReduxLogic: SOME_TYPE;
  };
}

// repeat for other actions, then use a union type like this

type MutatedActionType = MutatedAction1 | MutatedAction2 | ... ;

const initialState: StateSlice = { ... };

const reducer = (state = initialState, action: MutatedActionType): StateSlice => {
  ...
};

这是我能够使用的真实代码的缩写版本。希望这对某人有所帮助。

有一个关于标准动作类型的包 https://github.com/redux-utilities/flux-standard-action

和redux-logic提供https://github.com/jeffbski/redux-logic/blob/master/definitions/action.d.ts这是我们需要使用的动作接口