javascript - 即使“then”返回值响应,useEffect 也返回未定义
问题描述
我似乎无法弄清楚为什么 useEffect 会这样做...... Wait() 是一个睡眠异步函数, getData() 是一个 Axios 请求。
return wait().then(getData().then((resp) => {
console.log(resp)
}))
此代码记录了 resp 变量的有效值,但它在 return 语句中返回 undefined。发生了什么,我如何让它返回 resp 变量?
编辑***
const wait = React.useCallback( async() => {
if (loading === false) {
await sleep(4000);
} else if (loading === true){
await sleep(0);
} else {
await sleep(2000);
}
}, [loading])
const getData = React.useCallback(() => {
const value = Axios.post("http://localhost:3001/api/get-value",
{user: userProp}).then((response) => {
const recievedData = response.data;
const dataValue = recievedData.map((val) => {
return [val.value]
})
if (loading === true){
setLoading(false);
}
return parseInt(dataValue);
}).then((resp) => {
setMoisture(resp) // if I turn this off still no go.
return resp
})
return value
}, [userProp, loading])
const Data = React.useCallback(() => {
try {
return wait().then(getData)
} catch (error) {
setError(true);
return error;
}
}, [wait, getData])
React.useEffect(() => {
let isEffect = false
if (props.location.state !== undefined) {
Data().then((firstResponse) => {
if (!isEffect){
setMoisture(firstResponse)
}
})
}
return () => {
isEffect = true;
}
}, [props.location.state, Data, moisture]);
解决方案
提供给 useEffect 的回调必须返回一个函数或未定义(如果提供了一个函数,这被认为是一个清理函数。清理函数用于分离事件侦听器,取消任何正在进行的请求,并防止如果组件被卸载,任何更新)
为了访问您的 http 请求产生的响应,您应该将其存储在一个状态中(您可以使用 useState 或 useReducer)
const [rest, setResp] = React.useState();
React.useEffect(() => {
wait().then(_ => getData()).then(setResp);
}, [YOUR_DEPENDENCIES]);
// update jsx based on rest
根据您问题中的更新,您需要的是轮询
请查看下面的示例(请记住,这是说明可能解决方案的代码)
function usePolling(fetcher, interval) {
const [payload, setPayload] = React.useState(null);
React.useEffect(function () {
// you must implement the error handling
fetcher()
.then(function (resp) {
setPayload(resp)
})
}, [fetcher]);
React.useEffect(function () {
let timeoutId;
function poll() {
timeoutId = setTimeout(function () {
// you must implement the error handling
fetcher()
.then(function (resp) {
setPayload(resp)
poll();
})
}, interval);
}
poll()
return function () {
clearTimeout(timeoutId);
}
}, [fetcher, interval]);
return payload;
}
function App() {
const payload = usePolling(function () {
return Promise.resolve(Date.now())
}, 3000);
return (
<div>polling payload: {payload}</div>
)
}
ReactDOM.render(<App/>, document.getElementById('app'))
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width">
<title>JS Bin</title>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/17.0.1/umd/react.production.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/17.0.1/umd/react-dom.production.min.js"></script>
</head>
<body>
<div id="app"></div>
</body>
</html>
推荐阅读
- php - 如何阻止名为 filename.php.jpg 的文件上传
- excel - 描述性统计,百分位数
- matlab - 在 Matlab 上运行 Faster R-CNN 时的 CUDA_ERROR_ILLEGAL_ADDRESS
- r - 如何在R中的同一数据框中按组或类别(按组)与其他列(具有多个值)匹配列中的值
- javascript - 似乎无法在 Python 项目中使用 Js2Py 捕获异常
- javascript - 使用 PWA 服务工作者在离线模式下保存/提供 Web 服务
- swift - Firebase - 为什么不搜索在我的应用中工作的用户?(当用户输入两个字母时更新搜索控制器)
- r - 创建 beta 分布 QQ 图
- java - 在特定行的 txt 文件上写入问题
- vue.js - 如何使用 Vuejs 处理 url