reactjs - 如何避免我的应用程序出现“无法对未安装的组件执行 React 状态更新”错误?
问题描述
我正在尝试制作上传文件的一部分,但我遇到了一个问题,比如当我上传 csv 文件并且第一个组件出现错误时,当我在另一个组件上上传文件时它没有出现错误
错误是这样的:
index.js:1 Warning: Can't perform a React state update on an unmounted component. This is a no-op, but it indicates a memory leak in your application. To fix, cancel all subscriptions and asynchronous tasks in the componentWillUnmount method.
我的网站运行良好,但我担心这个错误会使它变得糟糕
info
state 用于上传文件。
我需要上传每个组件的文件,Parent component
但我在子组件中使用它,它工作正常,除了那个错误
我认为info
国家正在制造问题。
我想知道如何避免该错误
先感谢您
我的代码是这样的:
父组件:
const eachComponent = (index, id) => (
<DataSide id={id} key={index} onClick={chartItself}>
<SettingMenu
panelNum={index + 1}
show={show[index]}
chart={chart[index]}
changeLayout={changeLayout}
/>
{ChangeableType(index + 1).map(
(id, idx) =>
chart[index].key === id.key && ChangeableType(index + 1)[idx]
)}
{BarTypes(index).map(
(id, idx) => chart[index].key === id.key && BarTypes(index)[idx]
)}
{/* {LineTypes(index).map(
(id, idx) => chart[index].key === id.key && LineTypes(index)[idx]
)}
{GridTypes(index).map(
(id, idx) => chart[index].key === id.key && GridTypes(index)[idx]
)} */}
</DataSide>
);
const layout = [
eachComponent(0, "first"),
eachComponent(1, "second"),
eachComponent(2, "third"),
eachComponent(3, "fourth"),
和子组件:
const CsvFile = ({ match, location }) => {
const { panelNum, changeLayout } = location.state;
const chart = location.data;
const { Plugins, DataContextUseState } = useContext(DataContextApi);
const [plugins, setPlugins] = Plugins;
const [DataContext, setDataContext] = DataContextUseState;
const [info, setInfo] = useState([]);
///this info is the cause as i guess
const history = useHistory();
const [y, setY] = useState();
const [x, setX] = useState();
const [title, setTitle] = useState("");
这是我正在使用info
state 的第二个子组件:
const CsvFileReader = ({ setInfo }) => {
const handleOnDrop = data => {
const infos = data.map(item => item.data);
setTimeout(() => setInfo([...infos]), 1000);
};
const handleOnError = (err, file, inputElem, reason) => {
console.log(err);
};
const handleOnRemoveFile = data => {
console.log(data);
};
return (
<>
<MainReader>
<CSVReader
onDrop={handleOnDrop}
onError={handleOnError}
config={
(({ fastMode: true }, { chunk: "LocalChunkSize" }),
{ header: false })
}
addRemoveButton
onRemoveFile={handleOnRemoveFile}
>
解决方案
您正在使用超时来更新状态,可能是在组件卸载之后。使用 react ref 存储对当前超时的引用,并在组件卸载时清除它。
const CsvFileReader = ({ setInfo }) => {
const timerRef = React.useRef();
useEffect(() => {
return () => clearTimeout(timerRef.current); // clear any running timeouts
}, []);
const handleOnDrop = data => {
const infos = data.map(item => item.data);
timerRef.current = setTimeout(() => setInfo([...infos]), 1000); // save timeout ref
};
推荐阅读
- javascript - 通过函数使用 Splice() 方法推送号码
- python-3.x - raise HTTPError(req.full_url, code, msg, hdrs, fp) urllib.error.HTTPError: HTTP Error 429: Too Many Requests
- c++ - SDL_mixer 质量差,带有 WAVE 音频格式
- sql - 从子查询到主查询选择最小日期值
- python - 如何在curses中合并两个不同的边界
- javascript - Multer 不上传文件
- javascript - JavaScript 以最佳方式缩短长线
- kotlin - jdbi3 withHandle在kotlin中抛出错误
- javascript - 如何使用电报 API 发送本地存储的照片?
- sas - 仅显示在一列中按组更改的连续观察值