state 的值始终是默认值。反应 16.12.0

value of state is always default. React js 16.12.0

我有两个useEffect-s。一个用于从 api 获取数据并将其保存在状态中,第二个仅调用一次并开始侦听 websocket 事件。 在 websocket 事件处理程序中,我记录了获取的数据,但它始终具有默认值。 即使获取数据成功完成并且列表绘制在 UI 上,列表的值始终为空 - [].

const [list, setList] = useState([]);

useEffect(() => {
   axios.get("https://sample.api.com/get/list")
       .then(res => {
           setList(res.data);
       });
}, [window.location.pathname.split('/')[2]]);

useEffect(() => {
   webSocket.on('messageRecieved', (message) => {
        console.log(list);
    }); 
}, []);

尝试改变

.then(res => {

.then((res) => {

如果您向每个挂钩添加了控制台日志,或者是否在其中预设了值,请说明:

useEffect(() => {
   axios.get("https://sample.api.com/get/list")
       .then((res) => {
           console.log(res.data)
           setList(res.data);
       });
}, [window.location.pathname.split('/')[2]]);

useEffect(() => {
   webSocket.on('messageRecieved', (message) => {
        console.log(list);
        console.log(message);
    }); 
}, []);

您还可以添加错误捕获,以防万一:

.catch((error) => {
    console.log(error.response)
})

您的第二个效果是由于关闭而引用初始列表值(一个空数组)。这就是为什么 useEffect 应该在它的第二个参数中引用它的所有依赖项。

但在这种情况下,您不想在每次更新列表时都订阅 webSocket 事件,您可以在列表上使用 React 的 refs。

const listValue = useRef([]);
const [list, setList] = useState(listValue.current);

设置值时:

res => {
    listValue.current = res.data
    setList(listValue.current);
}

并且在一次性检索列表时触发 useEffect:

useEffect(() => {
    webSocket.on('messageRecieved', (message) => {
       console.log(listValue.current);
    }); 
}, []);