feat: sync and update with all changes from fork (#720)
* feat: sync and update with all changes from fork * refactor: extract clipboard copy logic into custom hook * fix: correct spelling of DEFAULT_REFRESH_FREQUENCY_MS in Stamps and WalletBalance providers * refactor(ui-tests): replace fixed sleeps with condition-based waits * fix: handle null values for size and granteeCount in infoGroups * fix(lint): add newline at end of file in useClipboardCopy hook * fix(ui-tests): page.goto URL * refactor: update import paths for useClipboardCopy --------- Co-authored-by: Ferenc Sárai <sarai.ferenc@gmail.com>
This commit is contained in:
+86
-37
@@ -1,27 +1,25 @@
|
||||
import { debounce } from '@material-ui/core'
|
||||
import { BZZ, DAI, EthAddress, PrivateKey } from '@ethersphere/bee-js'
|
||||
import { BigNumber as BN, Contract, providers, Wallet } from 'ethers'
|
||||
import { BZZ_TOKEN_ADDRESS, bzzABI } from './bzz-abi'
|
||||
import { debounce } from '@mui/material'
|
||||
import { Contract, JsonRpcProvider, TransactionReceipt, TransactionResponse, Wallet } from 'ethers'
|
||||
|
||||
const NETWORK_ID = 100
|
||||
import { BZZ_TOKEN_ADDRESS, bzzABI } from './bzzAbi'
|
||||
import { ethAddressString, newGnosisProvider } from './chain'
|
||||
|
||||
async function getNetworkChainId(url: string): Promise<number> {
|
||||
const provider = new providers.JsonRpcProvider(url, NETWORK_ID)
|
||||
await provider.ready
|
||||
async function getNetworkChainId(url: string): Promise<bigint> {
|
||||
const provider = newGnosisProvider(url)
|
||||
const network = await provider.getNetwork()
|
||||
|
||||
return network.chainId
|
||||
}
|
||||
|
||||
async function eth_getBalance(address: EthAddress | string, provider: providers.JsonRpcProvider): Promise<DAI> {
|
||||
address = new EthAddress(address)
|
||||
|
||||
const balance = await provider.getBalance(address.toHex())
|
||||
async function eth_getBalance(address: EthAddress | string, provider: JsonRpcProvider): Promise<DAI> {
|
||||
const addressString = ethAddressString(address)
|
||||
const balance = await provider.getBalance(addressString)
|
||||
|
||||
return DAI.fromWei(balance.toString())
|
||||
}
|
||||
|
||||
async function eth_getBlockByNumber(provider: providers.JsonRpcProvider): Promise<string> {
|
||||
async function eth_getBlockByNumber(provider: JsonRpcProvider): Promise<string> {
|
||||
const blockNumber = await provider.getBlockNumber()
|
||||
|
||||
return blockNumber.toString()
|
||||
@@ -29,56 +27,75 @@ async function eth_getBlockByNumber(provider: providers.JsonRpcProvider): Promis
|
||||
|
||||
async function eth_getBalanceERC20(
|
||||
address: EthAddress | string,
|
||||
provider: providers.JsonRpcProvider,
|
||||
provider: JsonRpcProvider,
|
||||
tokenAddress = BZZ_TOKEN_ADDRESS,
|
||||
): Promise<BZZ> {
|
||||
address = new EthAddress(address)
|
||||
|
||||
const addressString = ethAddressString(address)
|
||||
const contract = new Contract(tokenAddress, bzzABI, provider)
|
||||
const balance = await contract.balanceOf(address.toHex())
|
||||
// Use staticCall directly to bypass argument resolution
|
||||
const balance = await contract.balanceOf.staticCall(addressString)
|
||||
|
||||
return BZZ.fromPLUR(balance.toString())
|
||||
}
|
||||
|
||||
interface TransferResponse {
|
||||
transaction: providers.TransactionResponse
|
||||
receipt: providers.TransactionReceipt
|
||||
transaction: TransactionResponse
|
||||
receipt: TransactionReceipt
|
||||
}
|
||||
|
||||
export async function estimateNativeTransferTransactionCost(
|
||||
privateKey: PrivateKey | string,
|
||||
jsonRpcProvider: string,
|
||||
jsonRpcProviderUrl: string,
|
||||
): Promise<{ gasPrice: DAI; totalCost: DAI }> {
|
||||
privateKey = new PrivateKey(privateKey)
|
||||
|
||||
const signer = await makeReadySigner(privateKey, jsonRpcProvider)
|
||||
const gasLimit = '21000'
|
||||
const gasPrice = await signer.getGasPrice()
|
||||
const signer = await makeReadySigner(privateKey, jsonRpcProviderUrl)
|
||||
|
||||
return { gasPrice: DAI.fromWei(gasPrice.toString()), totalCost: DAI.fromWei(gasPrice.mul(gasLimit).toString()) }
|
||||
if (!signer.provider) {
|
||||
throw new Error('Signer provider is invalid!')
|
||||
}
|
||||
|
||||
const gasLimit = BigInt(21000)
|
||||
const feeData = await signer.provider.getFeeData()
|
||||
const gasPrice = feeData.gasPrice || BigInt(0)
|
||||
|
||||
return {
|
||||
gasPrice: DAI.fromWei(gasPrice.toString()),
|
||||
totalCost: DAI.fromWei((gasPrice * gasLimit).toString()),
|
||||
}
|
||||
}
|
||||
|
||||
export async function sendNativeTransaction(
|
||||
privateKey: PrivateKey | string,
|
||||
to: EthAddress | string,
|
||||
value: DAI,
|
||||
jsonRpcProvider: string,
|
||||
jsonRpcProviderUrl: string,
|
||||
externalGasPrice?: DAI,
|
||||
): Promise<TransferResponse> {
|
||||
privateKey = new PrivateKey(privateKey)
|
||||
to = new EthAddress(to)
|
||||
|
||||
const signer = await makeReadySigner(privateKey, jsonRpcProvider)
|
||||
const gasPrice = externalGasPrice ?? DAI.fromWei((await signer.getGasPrice()).toString())
|
||||
const signer = await makeReadySigner(privateKey, jsonRpcProviderUrl)
|
||||
|
||||
if (!signer.provider) {
|
||||
throw new Error('Signer provider is invalid!')
|
||||
}
|
||||
|
||||
const feedData = await signer.provider.getFeeData()
|
||||
const gasPrice = externalGasPrice ?? DAI.fromWei(feedData.gasPrice?.toString() || '0')
|
||||
const transaction = await signer.sendTransaction({
|
||||
to: to.toHex(),
|
||||
value: BN.from(value.toWeiString()),
|
||||
gasPrice: BN.from(gasPrice.toWeiString()),
|
||||
gasLimit: BN.from(21000),
|
||||
value: BigInt(value.toWeiString()),
|
||||
gasPrice: BigInt(gasPrice.toWeiString()),
|
||||
gasLimit: BigInt(21000),
|
||||
type: 0,
|
||||
})
|
||||
const receipt = await transaction.wait(1)
|
||||
|
||||
if (!receipt) {
|
||||
throw new Error('Invalid receipt!')
|
||||
}
|
||||
|
||||
return { transaction, receipt }
|
||||
}
|
||||
|
||||
@@ -86,29 +103,61 @@ export async function sendBzzTransaction(
|
||||
privateKey: PrivateKey | string,
|
||||
to: EthAddress | string,
|
||||
value: BZZ,
|
||||
jsonRpcProvider: string,
|
||||
jsonRpcProviderUrl: string,
|
||||
): Promise<TransferResponse> {
|
||||
privateKey = new PrivateKey(privateKey)
|
||||
to = new EthAddress(to)
|
||||
|
||||
const signer = await makeReadySigner(privateKey, jsonRpcProvider)
|
||||
const gasPrice = await signer.getGasPrice()
|
||||
const signer = await makeReadySigner(privateKey, jsonRpcProviderUrl)
|
||||
|
||||
if (!signer.provider) {
|
||||
throw new Error('Signer provider is invalid!')
|
||||
}
|
||||
|
||||
const feeData = await signer.provider.getFeeData()
|
||||
const gasPrice = feeData.gasPrice || BigInt(0)
|
||||
const bzz = new Contract(BZZ_TOKEN_ADDRESS, bzzABI, signer)
|
||||
const transaction = await bzz.transfer(to, value, { gasPrice })
|
||||
const receipt = await transaction.wait(1)
|
||||
|
||||
if (!receipt) {
|
||||
throw new Error('Invalid receipt!')
|
||||
}
|
||||
|
||||
return { transaction, receipt }
|
||||
}
|
||||
|
||||
async function makeReadySigner(privateKey: PrivateKey, jsonRpcProvider: string) {
|
||||
const provider = new providers.JsonRpcProvider(jsonRpcProvider, NETWORK_ID)
|
||||
await provider.ready
|
||||
const signer = new Wallet(privateKey.toUint8Array(), provider)
|
||||
async function makeReadySigner(privateKey: PrivateKey, jsonRpcProviderUrl: string) {
|
||||
const provider = newGnosisProvider(jsonRpcProviderUrl)
|
||||
await provider.getNetwork()
|
||||
const signer = new Wallet(privateKey.toString(), provider)
|
||||
|
||||
return signer
|
||||
}
|
||||
|
||||
export const Rpc = {
|
||||
export interface Rpc {
|
||||
getNetworkChainId: (url: string) => Promise<bigint>
|
||||
sendNativeTransaction: (
|
||||
privateKey: PrivateKey | string,
|
||||
to: EthAddress | string,
|
||||
value: DAI,
|
||||
jsonRpcProviderUrl: string,
|
||||
externalGasPrice?: DAI,
|
||||
) => Promise<TransferResponse>
|
||||
sendBzzTransaction: (
|
||||
privateKey: PrivateKey | string,
|
||||
to: EthAddress | string,
|
||||
value: BZZ,
|
||||
jsonRpcProviderUrl: string,
|
||||
) => Promise<TransferResponse>
|
||||
_eth_getBalance: (address: EthAddress | string, provider: JsonRpcProvider) => Promise<DAI>
|
||||
_eth_getBalanceERC20: (address: EthAddress | string, provider: JsonRpcProvider, tokenAddress?: string) => Promise<BZZ>
|
||||
eth_getBalance: (address: EthAddress | string, provider: JsonRpcProvider) => Promise<DAI>
|
||||
eth_getBalanceERC20: (address: EthAddress | string, provider: JsonRpcProvider, tokenAddress: string) => Promise<BZZ>
|
||||
eth_getBlockByNumber: (provider: JsonRpcProvider) => Promise<string>
|
||||
}
|
||||
|
||||
export const RPC: Rpc = {
|
||||
getNetworkChainId,
|
||||
sendNativeTransaction,
|
||||
sendBzzTransaction,
|
||||
|
||||
Reference in New Issue
Block a user