了解 React 的新上下文 API

简介

在一个有很多不同前端框架的世界里,总是很难知道该选择哪一个。我想用曾经流行的棱角吗?或者,潜心研究VueJS对我的知识范围有好处吗?

然后我们有了ReactJS,一个由Facebook创建的框架,似乎正在席卷前端框架世界。使用组件、虚拟DOM和JSX(这是另一天的事了!),Reaction似乎涵盖了所有内容,使其成为一个强大的框架。

新的Context API最近在React 16.3中引入:

一种通过组件树传递数据的方法,而无需在每个级别手动传递道具

听上去不错!我们来挖坑吧。

Reaction上下文API documentation的屏幕截图

道具和状态

在REACTIVE中,您有proposs‘和state`。有两件非常重要的事情需要理解。

PROPS 是PROPERTIES的缩写,是从父组件传递到组件的数据。

状态 是组件内部管理的数据。那么,如果每个组件都有自己的状态,我们如何将该信息共享给另一个组件呢?您可以使用道具,但道具只能在父组件和子组件之间传递。

那么,如果我们有很多层组件来传递一位信息,我们该怎么办?也被称为,螺旋钻?

道具钻取(上下文接口解决的问题)

让我们来看一个道具钻取的例子,这样我们就可以理解上下文API解决了什么问题。在本例中,我们将看到如何将信息从一个组件传递给子组件,然后再传递给该组件的子组件。

 1const Lowest = (props) => (
 2  <div className="lowest">{props.name}</div>
 3)
 4
 5const Middle = (props) => (
 6  <div className="middle">
 7    <Lowest name={props.name} />
 8  </div>
 9)
10
11class Highest extends Component {
12  state = {
13    name: "Context API"
14  }
15
16  render() {
17    return  <div className="highest">
18      {this.state.name}
19      <Middle name={this.state.name} />
20    </div>
21  }
22}

我知道命名不是最真实的,但它有助于演示上下文向下传递到嵌套组件的能力。更真实的场景可能发生在基于卡片的用户界面中:CardGrid->CardContent->CardFooter->LikeButton

回到我们的例子,这是Highest -> Middle -> Lowest组件如何嵌套:

 1<Highest>
 2
 3    <Middle>
 4
 5    	<Lowest>
 6
 7    		{/* we want our content here but dont want to prop pass ALLLL the way down ! */}
 8
 9    	</Lowest>
10
11    </Middle>
12
13</Highest>

注意到为了让最高层和最低层对话,他们需要中间人充当信使吗?

好吧,你看,我们有可以为我们处理所有工作的反应上下文。

React的上下文接口

Reaction上下文允许我们拥有一种可以全局地看到整个应用程序 的状态。

我们必须从上下文提供者()开始,定义您想要发送的数据,并且您需要上下文消费者()获取该数据并在调用时使用它。

有了上下文,您现在可以声明一次状态,然后通过上下文使用者在应用程序的每个部分使用该数据。

听起来很不可思议,对吧?让我们看看如何在一个简单的React应用程序中设置它。

让我们开始建造吧!

使用上下文接口构建名称转移

今天,我们将设置一个基本的Reaction应用程序。让我们来做一个应用程序,它将一个名称从一个组件传递到另一个组件,而这个组件恰好不是子组件!太棒了!我们将有三个不同的级别,一个是名称存储在State中的最高组件,我们将有中间组件,然后是最低组件。

我们的应用程序将从最高到最低发送状态中的名称,而不必与中间对话。 打开您喜欢使用的任何代码编辑器,让我们开始编码!

首先,我们需要应用程序的`react‘依赖项。继续并将其添加到您的依赖项中,或者如果您使用的是文本编辑器,请执行以下步骤来安装它:

1.如果您尚未安装NPM,请在您的计算机上全局安装NPM。 2.npm安装-保存反应 3.检查您的Package.json中的react依赖项。

在我们的主.js文件中,这就是魔术发生的地方。每当我们构建一个Reaction应用程序时,你总是需要导入你的依赖项,否则该文件将不知道要使用它。因此,在index.js文件的顶部,让我们导入我们需要的内容:

1import React, { Component } from 'react';

我们已经完成了导入,现在让我们转到组件。为了提高可读性,我们希望在变量中声明上下文。在我们的导入项下,让我们执行以下操作:

1const AppContext = React.createContext()

我们的组件层次

我们的Highest组件将具有状态。我们的状态将有一个名称,我们希望将该名称传递给Lowest组件,而不必与Middle组件对话:

 1class Highest extends Component {
 2    state = {
 3    	name : React Context API,
 4    }
 5
 6    render() {
 7    	return ( 
 8    	<AppContext.Provider value={this.state}>
 9    	  {this.props.children}
10    	</AppContext.Provider>
11    	)
12    }
13}

我们将构建我们的子组件,称之为中间组件:

1const Middle = () => (
2  <div>
3    <p>Im the middle component</p>
4    <Lowest />
5  </div>
6)

其子组件将被称为Lowest

1const Lowest = () => (
2  <div>
3     <AppContext.Consumer>
4        {(context) => context.name}
5      </AppContext.Consumer>
6  </div>
7)

我们来复习一下这个。您将看到我们在Highest中有一个状态,我们希望将其传递给Lowest。我们有静态属性 ,它将允许我们声明我们想要的上下文是什么。在我们的例子中,名称为Reaction Context API

提供者持有这些数据,这样当它被另一个组件消费时,它就知道该给它什么。在我们的最低组件中,你会看到我们有消费者想要这些数据,而不必首先将其传递给中间组件。相反,该组件只是挂起,声明Lowest是它的孩子。

何时不使用上下文

对于一个简单的支柱钻孔解决方案,可以规模体面,给上下文去!对于具有多个(和更复杂)状态、还原器等的大型应用程序,Redux可能更适合。

没有必要在您的应用程序中到处使用上下文,这会让事情变得有点混乱。足智多谋地使用您的代码,而不是仅仅使用上下文跳过额外的输入。

结论

Reaction上下文API非常棒。但是不要使用它,除非您知道它对您和您的代码都是有益的。Redux可能会很好。远离道具钻探,要知道像背景这样的东西可以帮助你避免这种情况。这是一个很棒的选择!

如果你想查看所有的代码,你可以在codesandbox](https://codesandbox.io/s/ox8q7zk0ly).上获得所有代码

Published At
Categories with 技术
Tagged with
comments powered by Disqus