反应验证不适用于套接字

React validations not working with socket

所以我通过套接字从后端接收数据,然后将数据(项目)推送到数组,但是如果变量为真(意味着它已暂停),我不想将项目推送到数组。

    const [sales, setSales] = useState([])
    const [paused, setPaused] = useState(false);
    const handlePush = (dt) => {
        if(paused) return;
            let data = dt.itemListed.data
            let obj = {
                name: dt.itemListed.data.item.metadata.name,
                data
            }
            if (sales.findIndex(i => i.name === dt.itemListed.data.item.metadata.name) > 0) return;
            if (sales.length >= 10) sales.pop();
            setSales(prevState => [obj, ...prevState])
    }
    useEffect(() => {
        socket.on("itemListed", (dt) => {
            handlePush(dt);
        })
    }, [socket])

变量 paused 设置为 true,我已经在调试它了,我还在屏幕上显示了一条文本,说明它是否暂停。另外,我检查数组大小是否为 10 的代码也不起作用。

代码工作正常,但后来我换成 socket.io-client lib,它停止工作了。

我认为正在发生的事情是 useEffect 只被“读取”一次,它忽略了未来的验证,它一直只是推送项目。

我能做什么?

这应该可以解决您的问题

useEffect(() => {
    socket.on("itemListed", (dt) => {
        handlePush(dt);
    })

    return () => {
        socket.off("itemListed") // cleanup
    };
}, [socket, handlePush])

您的 useEffect 正在侦听使用旧 pause 值的先前版本的 handlePush,因此它仍然能够推送。

如果您将函数 handlePush 添加为 useEffect 的依赖项,它会在每次 handlePush 更改时 re-run 这样您就会拥有最新的函数。

为了提高性能,您还应该在 handlePush() 函数上使用 useCallback() 挂钩。