3

我有一个应用程序,它利用 Oauth2 “重定向流”来验证用户,即用户被重定向到另一个网站登录,然后被重定向回我的网站。

文档和其他来源似乎都声称业务逻辑应该放在动作创建者或减速器中。但是我有一个login()不会以任何方式改变状态的函数,它的作用是将应用程序的当前状态保存为 localStorage 中的普通对象,然后将用户重定向到授权服务器。当用户登录并被重定向回来时,状态被恢复(通过另一段代码)并作为初始状态提供给我的商店创建函数。

我的问题:函数的逻辑login只是检索状态,但不会以任何方式更改它,因此它不属于减速器。它也不返回作为动作创建者定义的动作。我应该把它放在我的应用程序结构的什么位置?

拥有一个实际上不创建动作的动作创建者是否“可以”?我现在正在使用 redux-thunk 执行此操作(因为我需要这样做getState())并且它可以正常工作,但感觉不对,因为它实际上不是“动作创建者”,另一方面我也有一个logout()确实返回的函数一个动作,所以感觉他们应该住在同一个地方。我想这是一种极端情况,但并不是因为我可以想到很多理由以这种方式保存状态并将访问者重定向到其他站点(或者甚至只是保存状态而不重定向)。

PS。我知道有一些库可以自动将我的 redux 存储与 localStorage 同步,但这并不是问题的重点。

编辑:一些澄清:

Redux 文档中关于将业务逻辑放在何处:对于 归约器或动作创建器中应该放置哪些逻辑,没有一个明确的答案。

继续阅读,很明显只有两个地方我应该放置业务逻辑,要么在 reducer 要么在 action creator 中。现在,由于我想做的事情不会影响状态,并且根据定义,reducer 会影响状态,所以我倾向于将此逻辑放入动作创建器中。

关于动作创建者的文档:动作创建者就是这样——创建动作的函数。将术语“动作”和“动作创建者”混为一谈很容易,因此请尽量使用正确的术语。[...] 在 Redux 中,动作创建者只需返回一个动作

动作文档:动作是纯 JavaScript 对象。

我的登录示例的伪代码:

function login() {
    // retrieving and serializing the state, then:
    localStorage.set('my_app_id_state', my_serialized_state);
    window.location = url_to_authorization_service;
}

这段代码显然在动作创建者中没有位置,因为我没有返回动作,这是动作创建者的目的。但是我仍然需要检索状态,所以我也不能让它完全独立。

再说一遍,问题是我应该将这段代码放在我的应用程序结构中的什么位置?

同样,代码可以正常工作,一切都很好,所以我想这更像是一个学术问题,但它让我很烦恼,因为我在这里显然违反了 Redux 的基本规则。也许这只是一个例外?

4

2 回答 2

0

Dan Abramov在推特上回复说,我将得出这样的结论,即这是文档中概述的规则的一个例外。

丹·阿布拉莫夫的回复

于 2016-06-16T14:56:48.567 回答
0

这是一个很好的问题,让我意识到我做错了什么。所以希望这个答案至少对双方都有帮助:)

以这个改编自Real World Redux 示例的示例为例

私有函数

function oauth(url) {
 return (dispatch) => {
   dispatch({
    type: types.OAUTH_LOGIN,
    url
   });
 };
}

由动作创建者调用(返回一个函数)

export function loginToApi(redirectUrl) {
  return (dispatch) => {
    return dispatch(oauth(redirectUrl))
  }
}

然后在组件中调用该操作,如下所示:

login() {
 return this.props.dispatch(loginToApi());
}

因此,回答您的问题的一种方法是将您的业务逻辑放在一个私有方法中,然后由操作创建者调用。

可能有一种更优雅的方式,但这就是我在上面提到的文档中的做法。

关于将状态存储在本地存储中的登录逻辑:我认为您不需要这个。Redux 商店正在为您管理状态。

于 2016-06-15T20:39:17.333 回答