javascript - 反应反模式?
问题描述
以下是 React 中的反模式吗?我喜欢这种模式,因为当组件被实例化时,它为我提供了静态函数的上下文。然后稍后我可以导入该类并调用静态方法来修改状态。或者这可以以更好的方式完成吗?
// componentA.js
function bleedContext() {
ComponentA.staticMethod = ComponentA.staticMethod.bind(this)
}
export default class ComponentA {
static staticMethod() {
this.setState({foo: 'bar'})
}
constructor() {
this.state = {}
bleedContext.call(this)
}
render() {
return (
...
)
}
}
// componentB.js
import ComponentA from 'path/to/componentA'
export default class ComponentB {
handleClick() {
ComponentA.staticMethod()
}
render() {
return (
<button onClick={this.handleClick} />
)
}
}
解决方案
这显然是一种反模式,也可能是一个错误,具体取决于条件。静态类方法不应与类实例一起操作。staticMethod
绑定到特定的组件实例和用途setState
,这只能证明一个类是单例(尽管单例通常也是反模式)。如果期望有多个类实例,这将导致错误和内存泄漏,并且每个 React 组件都应该有多个实例,至少在测试时是这样。
在 React 中,两个独立组件相互交互的正确方法是拥有一个提供这种交互的公共父组件,例如:
class ModalContainer extends Component {
modalRef = React.createRef();
render() {
return <>
<Modal ref={this.modalRef} />
<SomeComponentThatUsesModal modalRef={this.modalRef} />
</>;
}
}
上面示例的问题是,如果是嵌套的,这将需要modalRef
深入传递 prop 。<SomeComponentThatUsesModal>
这个问题可以通过 React 上下文或其他第三方全局状态解决方案(如 Redux)来解决。
这可以使用 React 16.3 上下文 API 来完成,考虑到Modal
类实例具有open
方法:
const ModalContext = React.createContext();
function getModal(modalRef) {
return {
open: data => modalRef.current.open(data);
close: () => modalRef.current.close();
}
}
class ModalContainer extends Component {
modalRef = React.createRef();
render() {
return <>
<Modal ref={this.modalRef} />
<ModalContext.Provider value={getModal(this.modalRef)}>
{this.props.children}
</ModalContext.Provider>
</>;
}
}
然后对于任何深度嵌套的组件模态对象,使用open
和 close 方法将通过上下文可用:
const SomeComponentThatUsesModal = props => <div>
<ModalContext.Consumer>
{modal => <button onClick={() => modal.open('foo')} />}
</ModalContext.Consumer>
</div>;
<ModalContainer>
...deeply nested component
<SomeComponentThatUsesModal />
...
</ModalContainer>
这是一个演示。
推荐阅读
- javascript - 为什么它不更新我数据库中的日期?
- regex - 如何在文档中找到可能以不同形式编写的单词?(Python)
- python - 在 azure 数据块和 azure 数据工厂中执行 python 脚本
- java - 我的元素列表 xpath 计数为 0
- python - 如何简化具有多个包含变量的 .str.contains 代码?
- python-3.x - 如何通过python3调用远程服务器中的文件?
- html - Webpack 文件加载器不会构建 PDF 文件
- javascript - 贝宝订阅集成
- javascript - 对象操作:组合集合的两个条目
- operator-keyword - 如何将输入运算符 (+,-) 转换为 C 中的数学