admin管理员组文章数量:1317898
Why am I getting this error?
Warning: Can't call setState (or forceUpdate) on an unmounted ponent. This is a no-op, but it indicates a memory leak in your application. To fix, cancel all subscriptions and asynchronous tasks in the ponentWillUnmount method.
postAction.js
export const getPosts = () => db.ref('posts').once('value');
ponents:
constructor(props) {
super(props);
this.state = { posts: null };
}
ponentDidMount() {
getPosts()
.then(snapshot => {
const result = snapshot.val();
this.setState(() => ({ posts: result }));
})
.catch(error => {
console.error(error);
});
}
ponentWillUnmount() {
this.setState({ posts: null });
}
render() {
return (
<div>
<PostList posts={this.state.posts} />
</div>
);
}
Why am I getting this error?
Warning: Can't call setState (or forceUpdate) on an unmounted ponent. This is a no-op, but it indicates a memory leak in your application. To fix, cancel all subscriptions and asynchronous tasks in the ponentWillUnmount method.
postAction.js
export const getPosts = () => db.ref('posts').once('value');
ponents:
constructor(props) {
super(props);
this.state = { posts: null };
}
ponentDidMount() {
getPosts()
.then(snapshot => {
const result = snapshot.val();
this.setState(() => ({ posts: result }));
})
.catch(error => {
console.error(error);
});
}
ponentWillUnmount() {
this.setState({ posts: null });
}
render() {
return (
<div>
<PostList posts={this.state.posts} />
</div>
);
}
Share
Improve this question
edited Jul 9, 2018 at 13:33
Tholle
113k22 gold badges208 silver badges197 bronze badges
asked Jul 9, 2018 at 13:30
Bayram AkbuzBayram Akbuz
751 silver badge7 bronze badges
4
-
1
unmounted ponent dont have state, no need to do that. React is already telling you this is a
no-op
– Rikin Commented Jul 9, 2018 at 13:34 -
You should not call
this.setState
inponentWillUnmount
. Does the warning disappear if you remove that? – Tholle Commented Jul 9, 2018 at 13:35 - Hey you can read react lifecycle hooks docs on official website. It says when ponent is unmounting, no sort of state updation is done because ultimately that ponent's UI is being destroyed – Meet Zaveri Commented Jul 9, 2018 at 13:35
- getPosts() is asynchronous method. That's the mistake. Thank you all. Thank you @nicolas-tower – Bayram Akbuz Commented Jul 9, 2018 at 14:03
4 Answers
Reset to default 7As others mentioned, the setState in ponentWillUnmount is unnecessary, but it should not be causing the error you're seeing. Instead, the likely culprit for that is this code:
ponentDidMount() {
getPosts()
.then(snapshot => {
const result = snapshot.val();
this.setState(() => ({ posts: result }));
})
.catch(error => {
console.error(error);
});
}
since getPosts() is asynchronous, it's possible that before it can resolve, the ponent has unmounted. You're not checking for this, and so the .then can end up running after the ponent has unmounted.
To handle that, you can set a flag in willUnmount, and check for that flag in the .then:
ponentDidMount() {
getPosts()
.then(snapshot => {
if (this.isUnmounted) {
return;
}
const result = snapshot.val();
this.setState(() => ({ posts: result }));
})
.catch(error => {
console.error(error);
});
}
ponentWillUnmount() {
this.isUnmounted = true;
}
React ponent's state is a local entity. Unmounted ponent dont have state, no need to do that. React is already telling you this is a no-op
which means no-operation in tech speak. It means that you telling ponent to do something when its already destroyed.
https://reactjs/docs/react-ponent.html#ponentwillunmount
You should not call setState() in ponentWillUnmount() because the ponent will never be re-rendered. Once a ponent instance is unmounted, it will never be mounted again.
Remove this
ponentWillUnmount() {
this.setState({ posts: null });
}
it's useless
From the doc:
You should not call setState() in ponentWillUnmount() because the ponent will never be re-rendered. Once a ponent instance is unmounted, it will never be mounted again.
https://reactjs/docs/react-ponent.html#ponentwillunmount
You can try this code:
constructor(props) {
super(props);
this.state = { posts: null };
}
_isMounted = false;
ponentDidMount() {
this._isMounted = true;
getPosts()
.then(snapshot => {
const result = snapshot.val();
if(this._isMounted) {
this.setState(() => ({ posts: result }))
}
})
.catch(error => {
console.error(error);
});
}
ponentWillUnmount() {
this._isMounted = false;
this.setState({ posts: null });
}
render() {
return (
<div>
<PostList posts={this.state.posts} />
</div>
);
}
By using _isMounted, setState is called only if the ponent is mounted. the answer simply does a check to see if the ponent is mounted before setting the state.
本文标签:
版权声明:本文标题:javascript - Can't call setState (or forceUpdate) on an unmounted component. This is a no-op, but it indicates a memory 内容由网友自发贡献,该文观点仅代表作者本人, 转载请联系作者并注明出处:http://www.betaflare.com/web/1742034920a2417164.html, 本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容,一经查实,本站将立刻删除。
发表评论