在反应中更改高阶组件中的道具
Posted
技术标签:
【中文标题】在反应中更改高阶组件中的道具【英文标题】:Change props in Higher-Order-Component in react 【发布时间】:2019-03-26 16:49:04 【问题描述】:我正在尝试理解高阶组件(以下简称 HOC):
因此,我创建了一个示例 HOC 来为我的组件执行 GET 请求:
import React from 'react';
import Text from 'react-native';
import axios from 'axios';
export default (Elem, props = ) =>
// mock props for testing
props =
apiRequests:
"todoList":
url: "https://jsonplaceholder.typicode.com/todos"
return class extends React.Component
componentWillMount()
let apis = Object.keys(props.apiRequests);
for(let i = 0; i < apis.length; i++)
props.apiRequests[apis[i]].done = false
axios.get(props.apiRequests[apis[i]].url).then((resp) =>
console.warn("done")
props.apiRequests[apis[i]].done = true
props.apiRequests[apis[i]].data = resp.data
)
render()
return (<Elem ...props />)
现在,当我用上面的 HOC 包装我的组件时,我得到 done
为 false
的道具。
但是,很快,当我收到我的 API 响应时,HOC 会在我的控制台中记录 done
,但我的组件中的数据没有更新。我做错了什么?
【问题讨论】:
【参考方案1】:道具是不可变的。这个
props.apiRequests[apis[i]].done = true
是一个错误,不会导致子组件被重新渲染。
从异步请求接收到的状态应该存储在组件状态中,setState
触发重新渲染。 componentWillMount
已被弃用,因为它被滥用于异步例程。应该是:
return class extends React.Component
this.state = ;
componentDidMount()
let apis = Object.keys(props.apiRequests);
for(let i = 0; i < apis.length; i++)
axios.get(props.apiRequests[apis[i]].url).then((resp) =>
this.setState( apis[i]]: resp.data );
)
render()
return (<Elem data=this.state />)
根据预期接收数据的方式,可以使用Promise.all
批量执行状态更新。
【讨论】:
+1 指出不推荐使用componentWillMount
。许多人不关心那些与问题没有直接关系的不良做法,只是不加注释。
嗯,我明白了,谢谢你的回答。另一个愚蠢的问题,因为我是新手,所以这种 HOC 有意义吗?是否有任何性能/可维护性警告?
@AyushGupta 不客气。您可以通过将其设为React.PureComponent
并批量执行请求来提高性能。可能有道理,取决于你的情况。通常,您不仅需要提出请求,还需要以某种方式处理它。如果 HOC 接受 Promise 并使用已解析的值作为 props 呈现包装的组件,那么它会更加灵活。以上是关于在反应中更改高阶组件中的道具的主要内容,如果未能解决你的问题,请参考以下文章
通过 React 高阶组件传递子道具的正确 TypeScript 类型