Redux Thunk 和 Redux Saga 有啥区别?

Posted

技术标签:

【中文标题】Redux Thunk 和 Redux Saga 有啥区别?【英文标题】:What is the difference between Redux Thunk and Redux Saga?Redux Thunk 和 Redux Saga 有什么区别? 【发布时间】:2018-10-21 11:54:25 【问题描述】:

Redux Thunk 和 Redux Saga 都是 Redux 的中间件。两者有什么区别以及如何确定何时使用 Redux Thunk 或 Redux Saga?

【问题讨论】:

Pros/cons of using redux-saga with ES6 generators vs redux-thunk with ES2017 async/await的可能重复 【参考方案1】:

Redux Thunk 和 Redux Saga 都负责处理副作用。 简单来说,应用于最常见的场景(异步函数,特别是 AJAX 调用)Thunk 允许 Promises” 来处理它们,Saga 使用生成器。 Thunk 使用简单,许多开发人员都熟悉 Promises,Saga/Generators 更强大,但你需要学习它们。 当 Promise 足够好时,Thunk 也是如此,当您定期处理更复杂的情况时,Saga 为您提供更好的工具。

例如,当您在路由/视图中启动 AJAX 调用然后用户移动到另一个时会发生什么?无论如何,你能安全地让减速器改变状态吗? Saga 使取消效果变得微不足道,Thunk 需要您照顾它,解决方案不能很好地扩展。

实际上,选择一个或另一个确实取决于(同义反复)项目。

要记住的一点是,这两个中间件可以共存,因此您可以从 Thunks 开始,并在需要时/如果需要时引入 Sagas(然后根据实际经验选择重构的方式/内容...一种解决方案特别适合“学习项目”、MVP 等) 一般来说,Sagas 更强大且更易于测试,但它们引入了许多新概念,如果您还在学习其他技术(尤其是 Redux),这可能会让人有点不知所措。

具体来说,在处理简单有效的 Redux 哲学(将动作(文字对象)馈入 reducer(纯函数))时,您可以使用更有限但易于掌握的 Thunk 处理副作用(Promise.then( ).error()),或者 Saga 需要你面对(强大的)概念,即你可以用这些动作做更复杂的事情。

还值得一提的是 (redux-)observable 作为一种更复杂(甚至更强大)的范式来处理副作用,以防万一你熟悉它(如果你已经熟悉它,它可能更容易使用比学习 Saga)。

【讨论】:

【参考方案2】:

其实两者都是Redux处理异步动作的中间件。想知道then之间的区别,请注意下图:

中间件盒通常是指将现有软件中的不同功能粘合在一起的软件服务。对于 Redux,中间件在分派一个动作和将动作交给 reducer 之间提供了一个第三方扩展点。然后reducer创建新的状态。

Redux Thunk 是一个中间件,可让您调用返回函数而不是动作对象的动作创建者。该函数接收 store 的 dispatch 方法,然后在异步操作完成后用于在函数体内调度常规同步操作。 352B 体积,简单易学易用

Redux Saga 利用称为GeneratorsES6 功能,允许我们编写看起来是同步的并且非常容易测试的异步代码。在 saga 中,我们可以轻松地测试我们的异步流程,并且我们的操作保持纯净。 复杂,难以学习和理解,14kB 的体积,但很容易组织复杂的异步操作,并且非常易读,并且 saga 有许多有用的工具来处理异步操作

提示:如果您无法理解它们之间的区别或无法理解redux-saga 流程,但仍希望拥有可读的代码并避免回调地狱,请使用async/await 跟踪redux-thunk,我给offer举个例子:

// simple usage of redux-thunk:
export const asyncApiCall = values => 
  return dispatch => 
    return axios.get(url)
      .then(response =>
        dispatch(successHandle(response));
      )
      .catch(error => 
        dispatch(errorHandle(error));
      );
    ;
  ;



// async/await usage of redux-thunk:
export const asyncApiCall = values => 
  return async dispatch => 
    try 
      const response = await axios.get(url);
      dispatch(successHandle(response));
    
    catch(error) 
      dispatch(errorHandle(error));
    
  ;
;

【讨论】:

以上是关于Redux Thunk 和 Redux Saga 有啥区别?的主要内容,如果未能解决你的问题,请参考以下文章

何时使用 Redux-saga / Redux thunk 何时不使用? [关闭]

Redux Thunk 和 Redux Saga 有啥区别?

为啥使用 redux-thunk 或 redux-saga 进行 fetches?

redux中间件小结,结合redux-thunk和redux-saga

redux-saga

手写Redux-Saga源码