Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

React中的演示(UI)组件和容器组件 #16

Open
Hancoson opened this issue Jul 23, 2017 · 0 comments
Open

React中的演示(UI)组件和容器组件 #16

Hancoson opened this issue Jul 23, 2017 · 0 comments
Labels

Comments

@Hancoson
Copy link
Owner

React中的组件可以分为presentational components即UI(演示)组件和container components即容器组件。今天就来说说他们两个的区别以及这样的好处。

区别

我的演示组件:

  • 它只关心事物的样子。
  • 内部可以包含容器组件,通常有一些自己的DOM标记和样式。
  • 通常可以通过this.props.children进行控制。
  • 对应用程序的其余部分没有依赖关系,例如Fluxactionstores
  • 不需要指定数据的加载或变异。
  • 通过props接受和会掉数据。
  • 很少有自己的状态。
  • 被编写为功能组件,除非它们需要状态,生命周期或性能优化。
  • 示例:页面,边栏,故事,用户信息,列表。

我的容器组件:

  • 关心事情如何运作
  • 可能包含容器组件,但通常没有自己的任何DOM标记,除了一些包装div,并且没有任何样式。
  • 向演示组件或其他容器组件提供数据和行为。
  • 调用Flux/redux操作,并将其作为回调给演示组件。
  • 通常是有状态的,因为它们往往作为数据源。
  • 通常使用更高阶的组件(如来自Reat Reduxconnect()),来自RelaycreateContainer()或来自Flux UtilsContainer.create()生成的,而不是用手写。
  • 示例:UserPage,FollowersSidebar,StoryContainer,FollowedUserList。

好处

  • 更好的分离问题。通过以这种方式编写组件,您可以更好地理解您的应用程序和UI。
  • 更好的可重用性。您可以使用完全不同的状态源的相同的演示组件,并将其转换为可以进一步重复使用的单独的容器组件。
  • 演示组件本质上是您的应用程序的“调色板”。您可以将它们放在一个页面上,让设计师调整所有的变体,而不用触摸应用程序的逻辑。您可以在该页面上运行截图回归测试。
  • 这迫使您提取“布局组件”,例如Sidebar,Page,ContextMenu,并使用this.props.children,而不是在多个容器组件中复制相同的标记和布局。

记住,组件不必发出DOM。他们只需要在UI问题之间提供组合界限。

何时使用容器组件

我建议您开始构建您的应用程序的时候从UI组件开始。最终你会意识到,你正在把太多的props传给中间组件。当您注意到某些组件不使用他们收到的props,而只是转发它们,并且您必须在子组件需要更多数据时重新连接所有这些中间组件,这是引入一些容器组件的好时机。这样,您可以将数据和props到子组件,而不需要在不相关组件中负担。

这是一个持续的重构过程,所以不要开始就尝试。当您尝试使用此模式时,您将开始直观的了解何时抽出一些容器,就像您知道何时提取功能一样。

其他方法

重要的是,您明​​白UI组件和容器之间的区别不是一个技术性的。相反,它的目的是区别的。

相比之下,这里有一些相关(但不同的)技术区别:

  • 有状态和无状态的。一些组件使用React setState()方法,有些则不使用。虽然容器组件往往是有状态的,而且表示组件往往是无状态的,但这并不是一个难题。演示组件可以是有状态的,容器也可以是无状态的。
  • 类和函数。由于React 0.14,组件可以被声明为类和函数。功能组件更容易定义,但它们缺少当前仅适用于类组件的某些功能。其中一些限制可能会在将来消失,但今天存在。由于功能组件更易于理解,我建议您使用它们,除非您需要状态,生命周期或性能优化,这些类型组件此时才可用。
  • 纯净和不纯。人们说如果一个组件是纯粹的,如果它保证返回相同的结果给予相同的道具和状态。纯组件可以被定义为类和函数,并且可以是有状态的和无状态的。纯组件的另一个重要方面是它们不依赖于道具或状态中的深层突变,因此它们的渲染性能可以通过其shouldComponentUpdate()钩子中的浅层比较来优化。目前只有类可以定义shouldComponentUpdate(),但可能会在将来发生更改。

两个UI组件和容器都可以落入这些存储桶中。根据我的经验,UI组件往往是无状态的纯函数,容器往往是有状态的纯类。然而,这不是一个规则,而是一个观察,我已经看到与具体情况有关的恰恰相反的情况。

不要将UI和容器组件分离作为一个教条。有时候没有关系,也很难绘制线。如果您不确定特定组件是否应该是表示性的还是集装箱的,那么决定可能还为时过早。不要着急!

延伸阅读

Getting Started with Redux
Mixins are Dead, Long Live Composition
Container Components
Atomic Web Design
Building the Facebook News Feed with Relay

原文链接

@Hancoson Hancoson added the React label Apr 13, 2018
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

1 participant