** 已编辑/重新措辞 **
在对我的问题进行了一些很好的回答之后,我编辑了问题中的代码,以尽可能清楚地说明我不理解的内容。
我有一个 withErrorHandler 将用作许多单独组件的 hoc。
其中一个组件是 MyComponent。
withErrorHandler 的 componentWillMount 中的代码按预期工作,但由于它是一个废弃的方法,我必须将它移到某个地方。
位置 - ComponentDidMount 拦截器将无法拦截错误。
位置 - 构造函数 拦截器将拦截错误,但 withError 处理程序中的 Modal 不会显示给用户。
这里到底发生了什么?
import React from 'react';
import Modal from '../../components/UI/Modal/Modal';
import Aux from '../Aux/Aux';
const withErrorHandler = (WrappedComponent, axiosInstance) => {
return class extends React.Component {
constructor(props) {
super(props);
this.state= {
error: null
};
}
componentWillMount() {
let { request, response} = axiosInstance.interceptors;
this.requestInterceptor = request.use(req => {
this.setState({error: null});
return req;
})
this.responseInterceptor = response.use(resp => resp, error => {
console.log("axiosInstance Intercepted Error\t",error)
this.setState({error})
})
}
componentWillUnmount() {
let { request, response} = axiosInstance.interceptors;
request.eject(this.requestInterceptor);
response.eject(this.responseInterceptor);
}
errorConfirmedHandler = () => {
this.setState({error: null})
}
render() {
return <Aux>
<Modal show={this.state.error} modalClosed={this.errorConfirmedHandler}>
{this.state.error ? this.state.error.message : null}
</Modal>
<WrappedComponent {...this.props} />
</Aux>
}
}
}
export default withErrorHandler;
import React, { Component } from 'react';
import axiosInstance from '../../AxiosInstance';
import Spinner from '../../components/UI/Spinner/Spinner';
import withErrorHandler from '../../hoc/withErrorHandler/withErrorhandler';
class MyComponent extends Component {
constructor(props) {
super(props);
this.state = {
ingredients: null,
error: false
}
}
componentDidMount() {
// Deliberately placed Error in 'ingredients.json' by removing n
axiosInstance.get('ingredients.jso').then(response => {
this.setState({
ingredients: response.data
})
}).catch(error => {
console.log(`Unable to load Ingredients\nError:\t${JSON.stringify(error, null, 2)}`)
this.setState({ error: true})
})
}
render() {
return (
this.state.ingredients ?
<p>show ingredients</p> :
this.state.error ? <p>Ingredients Can't be loaded</p> : <Spinner />
);
}
}
export default withErrorHandler(MyComponent, axiosInstance);
最佳答案
你不应该在 constructor
中执行任何副作用,它应该主要用于初始化本地状态(和其他变量)或与内容绑定(bind)函数。
其次,在 react 中,您应该谨慎使用以下方法,因为它们在服务器和客户端上都被调用。
构造函数
componentwillmount
(已弃用)getderivedstatefromprops
更好的方法是在 componentDidMount
生命周期方法中更新状态。该方法会在组件的整个生命周期内触发一次。
class Component1 extends React.Component {
constructor(props) {
super(props);
this.state = {
result: null,
};
this.fetchResult = this.fetchResult.bind(this)
}
componentDidMount() {
this.fetchResult()
}
fetchResult () {
axiosInstance
.get(url)
.then((result) => {
console.log("result", result);
this.setState({ result });
})
.catch((error) => {});
}
render() {
return (
<>
<h1>SomeText</h1>
<p>{this.state.result ? "Hey, I got the result" : "Waiting..."}</p>
</>
);
}
}
关于javascript - 为什么在异步调用的构造函数中使用 setState 时此组件不更新 - ReactJS/ReactNative?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/63425476/