我是React的新手。我有2种不同的情况,我在使用React Hooks,但是我无法正确地从本地API接收数据。
情况1:
export const RegisterT = () => {
const [test, setTest] = useState()
const addrState = {}
axios.get('http://127.0.0.1:3333/states', { addrState })
.then(res => {
setTest(res.data)
console.log(test)
})
...
}
它可以与状态test
一起正常显示API的内容,但是我不知道Axios为什么/如何继续调用API无限-无止境。 (注:第一次调用返回未定义,然后下一次调用成功)我在做什么错了?
要解决此问题,我尝试使用useEffect
(情况2):
export const RegisterT = () => {
const [test, setTest] = useState()
const addrState = {}
useEffect(() => {
axios.get('http://127.0.0.1:3333/states', { addrState })
.then(res => {
setTest(res.data)
console.log(test);
})
}, [])
...
}
现在,Axios仅能运行一次,但API不会提供任何数据。也许我应该在这种情况下使用异步/等待,但是我无法使其工作。有谁知道如何解决此问题(案例1或案例2)?
谢谢。
答案 0 :(得分:2)
更新状态是异步操作。因此,state
直到下一次呈现该组件时才真正更新。如果要捕获正确的状态,则可以console.log(res.data)
或将其包装在useEffect
钩子中,并以test
作为依赖项。
export const RegisterT = () => {
const [test, setTest] = useState()
const addrState = {}
// effect only runs when component is mounted
useEffect(() => {
axios.get('http://127.0.0.1:3333/states', { addrState })
.then(res => {
setTest(res.data);
});
}, []);
// effect runs whenever value of test changes
useEffect(() => {
console.log(test);
}, [test]);
}
这样可以保证console.log
的值更新时test
可以运行。
此外,一次调用API请求的原因是您在依赖项数组中未提及任何内容。第一次安装组件时,[]
空依赖项数组会运行效果。
async/await
只是Promise
对象的包装。因此它们的行为类似。
答案 1 :(得分:1)
使用useEffect
的解决方案很好。如果您不使用它,则每个渲染器都会调用该请求。如果您在console.log
中输入任何信息,也是如此。之所以看不到useEffect
中的数据,是因为状态值不会在当前渲染中更新,而是在下一个由状态设置器调用的状态中更新。将console.log(test);
移动到useEffect
之后以查看数据。初始化时它将为undefined
,但在下一个渲染中,它应包含来自请求的数据。