我目前正在与“无法在未安装的组件错误上使用setState()或forceUpdate()”作斗争,并且很难跟踪错误来自哪个异步操作。我怀疑是因为我使用setInterval
添加秒来显示当前时间。这是我在componentDidMount
,componentWillUpdate
和componentWillUnmount
中负责管理时间显示的内容:
componentDidMount() {
this.mounted = true;
//listener to identify whether app is active/inactive
AppState.addEventListener('change', this.handleAppStateChange.bind(this));
//get user's intranet schedule
this.props.actionsMain.getSchedule(this.props.staff.staffID);
this.getLocation();
//After the first location received, re-check every 20 seconds
this.locationInterval = setInterval(() => {
this.getLocation();
}, 20000);
}
componentDidUpdate() {
//when we just received server time, parse and set the time to state, then set the interval timer
if (this.props.scheduleReceived && this.state.time[0] === null) {
let time = this.props.schedule['time_server'].split(':'),
hh = parseInt(time[0]) + this.props.location.zone,
mm = parseInt(time[1]),
ss = parseInt(time[2]);
if (this.mounted) {
this.setState({ time: [hh, mm, ss] });
this.serverTimeInterval = setInterval(() => {
let { time } = this.state, hh = time[0], mm = time[1], ss = time[2];
//add second and adjust time
ss += 1;
if (ss >= 60) {
ss -= 60;
mm += 1;
if (mm >= 60) {
mm -= 60;
hh += 1;
if (hh >= 24)
hh -= 24;
}
}
if (this.mounted)
this.setState({ time: [hh, mm, ss] })
}, 1000)
}
}
}
componentWillUnmount() {
//Remove all timer events
clearInterval(this.serverTimeInterval);
clearInterval(this.locationInterval);
//Remove listener
AppState.removeEventListener('change', this.handleAppStateChange.bind(this));
this.mounted = false;
}
任何人都可以指出我在这里做错了什么,即使我正在做的事情也是一种很好的做法吗?
同样,我的第二个怀疑来自提取位置承诺,该承诺是从setInterval()
执行并返回到未安装的组件的。如果有任何经验法则可以遵循,我将如何确保setInterval,setState和Promises和谐地工作,那真是太棒了!
谢谢!
答案 0 :(得分:0)
永远不要在componentDidUpdate中调用setState,否则会导致无限循环