useState 变量在事件回调中为空
Posted
技术标签:
【中文标题】useState 变量在事件回调中为空【英文标题】:useState variables are null in event callback 【发布时间】:2021-07-14 07:21:04 【问题描述】:我正在开发一个与solidity 智能合约交互的reactjs Web 应用程序。
这个智能合约发出事件,我想在我的网络应用程序中监听这个事件。
这是我的反应 js 文件:
import React, useState, useEffect from "react";
import getWeb3 from "./getWeb3";
import Contract1 from "./contracts/Contract1.json";
const App = () =>
// Hooked variables
const [web3, setWeb3] = useState(null);
const [account, setAccount] = useState(null);
const [contract, setContract] = useState(null);
function callback(event)
console.log(account); // Problem: Every hooked variables are null here
async function init()
const web3 = await getWeb3();
const accounts = await web3.eth.getAccounts();
const networkId = await web3.eth.net.getId();
setAccount(accounts[0]);
let deployedNetwork = Contract1.networks[networkId];
let _contract = new web3.eth.Contract(Contract1.abi, deployedNetwork && deployedNetwork.address);
_contract.events.MyEvent().on("data",(e) => callback(e));
setContract(_contract);
setWeb3(web3);
...
;
useEffect(() => init(); , []);
...
在我的应用程序中一切正常。
当我的智能合约发出 MyEvent 时调用回调函数。
但是有一点很奇怪:回调函数中每个挂钩的变量都是空的。 我想这是一个范围问题,因为此变量已设置并且在我的应用程序的其他地方可以正常工作。
有什么想法吗?
非常感谢
【问题讨论】:
callback
和后面使用的event_callback
一样吗? callback
在哪里使用?我同意,看来您在回调中有一个陈旧的 account
状态外壳。你能分享更多callback
对account
状态所做的事情吗?
非常抱歉,我犯了一个错误。你说得对:这与我编辑帖子的功能相同。谢谢
【参考方案1】:
你可以使用另外一个useEffect来查看账户和合约,然后你可以在账户变化时订阅和取消订阅
useEffect(() =>
if(account && _contract)
_contract.events.MyEvent().on("data",(e) =>
);
return () =>
//unscubscribe here
, [account, _contract])
【讨论】:
【参考方案2】:正如前面的答案所暗示的,问题是init
函数只执行一次,我们需要把它放在依赖数组中。为此,该函数和之前的所有函数都应包含在useCallback
中。然后 React 会知道什么时候重新运行东西并且钩子对象会被填充。
这就是它的样子:
import React, useState, useEffect, useCallback from "react";
...
const App = () =>
...
const callback = useCallback((event) =>
console.log(account); // Problem: Every hooked variables are null here
, [account])
const init = useCallback(async () =>
...
, [//The proper dependencies of this function]);
useEffect(() => init(); , [init]);
...
【讨论】:
我不明白初始化执行一次。但是 init 订阅了一个回调。调用此回调时,将设置帐户以上是关于useState 变量在事件回调中为空的主要内容,如果未能解决你的问题,请参考以下文章
useState 中的变量未在 useEffect 回调中更新