Apollo useLazyQuery加载Modal数据出现旧数据延迟问题求助
问题原因
核心问题是useLazyQuery的异步特性:调用getBand()后,Apollo需要时间完成查询并更新response状态,但你在handleOpen里同步调用setInfo(response?.userName),此时拿到的还是查询触发前的旧值——第一次点击时是空,后续点击时是上一次的查询结果。
解决方案
以下是三种可行修复方式,按需选择:
方案1:用useEffect监听查询结果变化
移除handleOpen里的setInfo,改用useEffect监听response的更新,自动同步最新数据到info状态:
// BAND INFO MODAL const [getBand, { error: err, loading: load, data: response }] = useLazyQuery(QUERY_NAME); const [info, setInfo] = useState(""); const [open, setOpen] = useState(false); // 监听response变化,同步最新数据 useEffect(() => { if (response?.userName) { setInfo(response.userName); } }, [response]); function handleOpen(params) { getBand({ variables: { name: params } }); setOpen(true); } function handleClose() { setOpen(false); setInfo(""); }
方案2:直接使用Apollo查询的response,移除额外状态
Apollo已经帮你管理了查询数据的状态,没必要额外维护info,直接在Modal渲染时用response?.userName即可,减少状态冗余:
// BAND INFO MODAL const [getBand, { error: err, loading: load, data: response }] = useLazyQuery(QUERY_NAME); const [open, setOpen] = useState(false); function handleOpen(params) { getBand({ variables: { name: params } }); setOpen(true); } function handleClose() { setOpen(false); } // 渲染Modal时直接使用response // 示例:<Modal open={open} onClose={handleClose}>{load ? '加载中...' : response?.userName}</Modal>
方案3:利用useLazyQuery的onCompleted回调
调用getBand时传入onCompleted回调,查询完成后再设置数据并打开Modal,确保拿到最新结果:
// BAND INFO MODAL const [getBand, { error: err, loading: load }] = useLazyQuery(QUERY_NAME); const [info, setInfo] = useState(""); const [open, setOpen] = useState(false); function handleOpen(params) { getBand({ variables: { name: params }, onCompleted: (data) => { setInfo(data?.userName); setOpen(true); } }); } function handleClose() { setOpen(false); setInfo(""); }
额外提示
- 可在Modal中展示
load状态的加载提示(如加载动画),提升用户体验; - 记得处理
err状态,查询失败时给用户明确反馈。
内容的提问来源于stack exchange,提问作者Matt L
相关产品推荐
相关产品推荐

