使用 Redux Hooks 而不是 connect() 好的设计吗?

Posted

技术标签:

【中文标题】使用 Redux Hooks 而不是 connect() 好的设计吗?【英文标题】:Is using Redux Hooks instead of connect() good design? 【发布时间】:2020-05-09 16:57:17 【问题描述】:

目前有两个概念如何将 React 组件连接到 redux 存储:connect() 和 Redux Hooks。我想知道使用钩子是否被认为是好的软件设计。

它损害了单一职责原则,因为组件不仅负责呈现数据,还负责连接到商店。 组件和 Redux 之间存在紧密耦合。重用组件或从 Redux 切换到另一个状态管理解决方案将很困难。

在软件质量方面,hook 与connect() 相比有什么优势吗?

【问题讨论】:

您在软件质量方面遵循哪些参数? 您始终可以遵循 Container-Presentation 方法,在 Container 中使用钩子,将数据传递给展示组件。 Hooks 的优势在于它们是 React 的未来,使用 HoC 可能会在未来消失。 【参考方案1】:

就个人而言,我强烈赞成使用钩子而不是 connect()(),原因如下:

可以轻松嵌套在其他自定义钩子中以创建复杂的行为,这是 connect()() 无法做到的 在编码和重构过程中更容易在组件中添加/删除 - 语义的破坏性更小(您仍在导出相同的内容) 关注点分离 - 如果您的组件使用多个不同的 redux 状态位,它们都通过一个 mapStateToProps 函数进入,而您可以为不同的 redux 状态位创建多个挂钩 简化了 React 树 - connect()() 有效地渲染了两个 React 元素:“哑”元素和连接的元素。这会使您的树嵌套两倍! 更直观的语法 - 我发现自己经常使用 connect()() 访问文档,尽管我已经使用了数百次。

同意钩子比connect()() 更耦合——如果你担心这个问题,你可以添加一个抽象层:

import  useBadgers  from '../reducers/badgers';

function MyBadgerList() 
    const badgers = useBadgers();

// ../reducers/badgers.js
export const useBadgers = () => useSelector(state => state.badgers);

【讨论】:

我真的可以了解 HOC 的嵌套如何影响应用程序的性能吗?工作中的平均组件就像无数个连接的 HOC connect(mapStateToProps, mapDispatchToProps)(WithErrorBoundary(withStyles(styles)(withRouter(Component)))) 我知道除了错误边界之外的所有组件都有钩子替换,但我需要某种统计/分析措施让它们给我们时间重构。【参考方案2】:

connectuseSelector/useDispatch 都是从 React 组件与 Redux 存储交互的有效方式。但是,它们有不同的权衡。我在 Thoughts on React Hooks, Redux, and Separation of Concerns 的帖子中谈到了这些权衡,在 Hooks, HOCs, and Tradeoffs 上发表了我的 ReactBoston 2019 演讲。

总结:是的,钩子通常会导致组件在内部做更多的事情,而不是做不同事情的单独组件。这两种方法都是有效的 - 这是您特别想构建您的系统的问题。

就“优势”而言:React-Redux 的钩子需要编写的总代码比 connect 少,不添加间接,并且更易于与 TypeScript 一起使用。

【讨论】:

以上是关于使用 Redux Hooks 而不是 connect() 好的设计吗?的主要内容,如果未能解决你的问题,请参考以下文章

上下文 + Hooks 或 Redux

大道理小聪明系列 - Redux + Hooks 工程实践一则

React - Redux Hooks的使用细节详解

auto-redux,跟普通hooks一样使用redux。

一库让你快速搭建redux。auto-redux,跟普通hooks一样使用redux。

如何使用 Redux-Saga 和 Hooks 调用 API