web3 API has method getBalance
. How does it work? geth just calculates and cache balances of all addresses, i.e. it works as block explorer? Or there is some magic?
How fast is getBalance
? Can I make 100 requests per second to one geth instance?
Ethereum Stack Exchange is a question and answer site for users of Ethereum, the decentralized application platform and smart contract enabled blockchain. It only takes a minute to sign up.
Sign up to join this communityweb3 API has method getBalance
. How does it work? geth just calculates and cache balances of all addresses, i.e. it works as block explorer? Or there is some magic?
How fast is getBalance
? Can I make 100 requests per second to one geth instance?
I'm writing code that uses the RPC to query the node using C++. The goal of my code is to get the data as quickly as I can, so I've done some basic performance testing.
In general, I'm finding that the RPC is quite slow in itself relative to say caching the data (obviously), but I'm finding that certain functions are clearly faster than others. I initially thought that getBalance would be one of the slower functions, but I'm not finding it to be slow at all.
Of course, the only way for you to figure it out for your particular case is to write a simple test case and time it directly.
Concerning how it works, I'm not sure I understand your question exactly, but I am certain the node is querying a block explorer. Given its speed, I would guess the node holds balances for every account at every block (storing only changed values, of course). I doubt that the node recalculates balances each time it's requested, otherwise it would be much slower, I would think.
https://twitter.com/rstormsf/status/1110250992111476737
Stop using web3.eth.getBalance
or token.balanceOf
if you need to get balance for more than 5 ethereum addresses.
Use the power of solidity to get any necessary data from ethereum blockchain.
Checkout this video tutorial: https://youtu.be/pL1dZhodxvI
Example:
Query eth balances and erc20 token balances in batches.
We need solidity contract:
pragma solidity >=0.4.22 <0.6.0;
interface ERC20 {
function balanceOf(address owner) external view returns (uint256);
}
contract BalanceOracle {
function exploreBalances(address[] calldata users) external view returns(uint256[] memory balances) {
balances = new uint256[](users.length);
for(uint i = 0; i < users.length; i++) {
balances[i] = users[i].balance;
}
}
function erc20Balances(address _token, address[] calldata users) external view returns(uint256[] memory balances) {
ERC20 erc20 = ERC20(_token);
balances = new uint256[](users.length);
for(uint i = 0; i < users.length; i++) {
balances[i] = erc20.balanceOf(users[i]);
}
}
}
Javascript example:
const ethers = require('ethers')
const {formatEther} = ethers.utils
const fs = require('fs')
let provider = new ethers.providers.InfuraProvider('mainnet')
const abi = [
"function exploreBalances(address[] users) external view returns (uint256[] balances)"
]
const BALANCE_ORACLE_ADDRESS = "0x292c4fc2198998d2dc38ac1f302fddf843abbaa3"
const contract = new ethers.Contract(BALANCE_ORACLE_ADDRESS, abi, provider)
async function main() {
let addresses = fs.readFileSync('./addresses.csv', {encoding: 'utf8'})
addresses = addresses.split('\n')
let balances = await contract.exploreBalances(addresses)
let addressesWithBalances = []
balances.forEach((balance, index) =>
{
return addressesWithBalances.push({
address: addresses[index], balance: formatEther(balance)
})
}
)
console.log(addressesWithBalances)
}
main()
Profit!
Sponsored by https://peppersec.com