React:无法在未安装的组件上执行React状态更新

时间:2020-08-01 00:37:08

标签: javascript reactjs async-await fetch use-effect

我正在尝试将一些json数据加载到我的React应用程序中,并对数据进行一些修改,然后再使用它(向数据集的每一行添加一列,并向其添加其他数据)以创建D3.js可视化效果。我设法使其正常运行并显示在console.log中,但是,每当我开始对应用程序进行任何更改时,都会弹出以下错误窗口: enter image description here

我不确定为什么会这样。我试图通过向fetchUrl()函数(类似于await addQuarterStringsToArr(data))添加一个'await'或在主要组件中使用访存API来应用此修改帮助程序函数,但是在所有这些情况下,我都没有这样做”无法获得带有附加列的所需数据集。

这是我的codesandbox

您能告诉我我在做什么错吗?我一般对React和编程都不熟悉,因此对如何解决这个问题感到困惑。

提前谢谢!

3 个答案:

答案 0 :(得分:3)

如果要使用setState,则需要确保已安装该组件。您可以使用componentDidMount函数并在该函数内执行提取请求。 https://en.reactjs.org/docs/react-component.html#componentdidmount

请记住,在使用componentWillUnmount函数卸载组件时也要中止请求。 https://en.reactjs.org/docs/react-component.html#componentwillunmount

正在发生的事情是,您正在执行获取请求,并且在装入组件之前调用了setState,或者您在获取请求完成之前(或者同时发生了这两种情况)执行了获取请求并卸下了组件,< / p>

答案 1 :(得分:1)

您需要执行与此类似的操作。

import { useEffect, useState } from 'react';


const useFetch = (url) => {
    const [response, setResponse] = useState(null);
    const [loading, setLoading] = useState(false);
    const [hasError, setHasError] = useState(false);

    useEffect(() => {
        setLoading(true);
        fetch(
            url,{
            method: 'GET',
        }).then(res => {
            setResponse(res);
            setLoading(false);
        })
        .catch(() => {
            setHasError(true);
            setLoading(false);
        });
    }, [url]);
    return [response, loading, hasError];
};
export default useFetch;


利用它。

import { useEffect, useState } from 'react';
const component = () => {
     const [response, loading, hasError] = useFetch('http://myurl.com/api/post');

useEffect(() => {
    if(response !== null){ 
      console.log(response);
    }
});

   return <>
     {loading && <span>loading</span> }
     {hasError && <span>Some error!!!</span>} 
     <div> {JSON.stringify(response)} </div>
   </>;
}


我宁愿使用useReducer,但在这种情况下,因为您正在请求Hooks。这是我到目前为止所做的更好的方法。

答案 2 :(得分:1)

您不是要从addQuarterStringsToArr函数返回数据,这就是为什么setData(addQuarterStringsToArr(data))在这里将无法定义的原因。

仅在addQuarterStringsToArr函数中返回数据集,如下所示:

// helper function to add corresponding text for the quarter and year as a string
export default function addQuarterStringsToArr(dataset) {
  for (let i = 0; i < dataset.length; i++) {
    switch (dataset[i][0].substring(5, 7)) {
      case "01":
      case "02":
      case "03":
        dataset[i].push(dataset[i][0].substring(0, 4) + " Q1");
        break;
      case "04":
      case "05":
      case "06":
        dataset[i].push(dataset[i][0].substring(0, 4) + " Q2");
        break;
      case "07":
      case "08":
      case "09":
        dataset[i].push(dataset[i][0].substring(0, 4) + " Q3");
        break;
      case "10":
      case "11":
      case "12":
        dataset[i].push(dataset[i][0].substring(0, 4) + " Q4");
        break;
      default:
        break;
    }
  }
  return dataset;
}

希望这样做。