Improve React component organization #1436
Description
More React components! Moooore
Most of our React components are roughly organized into "views" and "controllers," but the divisions between them are sometimes blurred. The GitHub panel components also introduce "containers," which are mostly controllers wrapped by Relay. I'd like to bring more order and consistency to our divisions here (surprise surprise, I know).
Here are the categories I'd like to divide our components into:
- Items are intended to be used as top-level components within subtrees that are rendered into some Portal and passed to the Atom API, like pane items, dock items, or tooltips. They are mostly responsible for implementing the Atom "item" contract. These live within
lib/items/
, are tested withintest/items/
, and are named with anItem
suffix. Examples:IssueishPaneItem
,FilePatchPaneItem
. - Containers are responsible for statefully fetching asynchronous data and rendering their children appropriately. They handle the logic for how subtrees handle loading operations (displaying a loading spinner, passing null objects to their children) and how errors are reported. Containers should mostly be thin wrappers around things like
<ObserveModel>
,<QueryRenderer>
, or context providers. These live withinlib/containers
, are tested withintest/containers
, and are named with aContainer
suffix. Examples:PrInfoContainer
,GitTabContainer
. - Controllers are responsible for implementing action methods and maintaining state for some subtree of components. A Controller's
render()
method should only consist of passing props to a single child, usually a View. These live withinlib/controllers
, are tested withintest/controllers
, and are named with aController
suffix. Examples:GitTabController
,RecentCommitsController
,ConflictController
. - Views are responsible for accepting props and rendering a DOM tree. View components should contain very few non-render methods and little state. These live within
lib/views
, are tested withintest/views
, and are named with aView
suffix. Examples:GitTabView
,GithubLoginView
.
@atom/github-package: Would this classification make more sense to you? Can you think of any existing code that we couldn't fit into this schema?
Once we decide which way we're going, we'd need to convert existing components gradually through incremental, focused refactoring, like we did with the React port. It might be a good opportunity to improve our tests as we go, too.