Ether.js-读取合约信息

1.Contract类

在ethers中,Contract类是部署在以太坊网络上的合约(EVM字节码)的抽象。通过它,开发者可以非常容易的对合约进行读取call和交易transaction,并可以获得交易的结果和事件。以太坊强大的地方正是合约,所以对于合约的操作要熟练掌握。

2.创建Contract变量

1.只读和可读写Contract

Contract对象分为两类,只读和可读写。只读Contract只能读取链上合约信息,执行call操作,即调用合约中view和pure的函数,而不能执行交易transaction。创建这两种Contract变量的方法有所不同:

  1. 只读Contract:参数分别是合约地址,合约abi和provider变量(只读)
const contract = new ethers.Contract(`address`, `abi`, `provider`);
  1. 可读写Contract:参数分别是合约地址,合约abi和signer变量。Signer签名者是ethers中的另一个类,用于签名交易。
const contract = new ethers.Contract(`address`, `abi`, `signer`);

注意 ethers中的call指的是只读操作,与solidity中的call不同

2.读取合约信息

1.创建Provider

我们使用Alchemy节点的API Key创建Provider

// 利用Alchemy的rpc节点连接以太坊网络
// 填上你的Alchemy API Key,''处填写你所创建的API Key
const ALCHEMY_ID = '' 
//链接以太坊主网
const provider = new ethers.providers.JsonRpcProvider(`https://eth-mainnet.g.alchemy.com/v2/${ALCHEMY_ID}`)

2.创建只读Contract实例

创建只读Contract实例需要填入3个参数,分别是合约地址,合约abi和provider变量。

方法1.

直接输入合约abi。你可以从remix的编译页面中复制,在本地编译合约时生成的artifact文件夹的json文件中得到,或者从etherscan开源合约的代码页面得到。我们用这个方法创建WETH的合约实例:

// 第1种输入abi的方式: 复制abi全文
// WETH的abi可以在这里复制:https://etherscan.io/token/0xc02aaa39b223fe8d0a0e5c4f27ead9083c756cc2#code
const abiWETH = '[{"constant":true,"inputs":[],"name":"name","outputs":[{"name":"","type":"string"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"name":"guy","type":"address"},{"name":"wad","type":"uint256"}],"name":"approve","outputs":[{"name":"","type":"bool"}],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[],"name":"totalSupply","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"name":"src","type":"address"},{"name":"dst","type":"address"},{"name":"wad","type":"uint256"}],"name":"transferFrom","outputs":[{"name":"","type":"bool"}],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"name":"wad","type":"uint256"}],"name":"withdraw","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[],"name":"decimals","outputs":[{"name":"","type":"uint8"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[{"name":"","type":"address"}],"name":"balanceOf","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[],"name":"symbol","outputs":[{"name":"","type":"string"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"name":"dst","type":"address"},{"name":"wad","type":"uint256"}],"name":"transfer","outputs":[{"name":"","type":"bool"}],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[],"name":"deposit","outputs":[],"payable":true,"stateMutability":"payable","type":"function"},{"constant":true,"inputs":[{"name":"","type":"address"},{"name":"","type":"address"}],"name":"allowance","outputs":[{"name":"","type":"uint256"}],"payable":false,"stateMutability":"view","type":"function"},{"payable":true,"stateMutability":"payable","type":"fallback"},{"anonymous":false,"inputs":[{"indexed":true,"name":"src","type":"address"},{"indexed":true,"name":"guy","type":"address"},{"indexed":false,"name":"wad","type":"uint256"}],"name":"Approval","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"name":"src","type":"address"},{"indexed":true,"name":"dst","type":"address"},{"indexed":false,"name":"wad","type":"uint256"}],"name":"Transfer","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"name":"dst","type":"address"},{"indexed":false,"name":"wad","type":"uint256"}],"name":"Deposit","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"name":"src","type":"address"},{"indexed":false,"name":"wad","type":"uint256"}],"name":"Withdrawal","type":"event"}]';
const addressWETH = '0xc02aaa39b223fe8d0a0e5c4f27ead9083c756cc2' // WETH Contract
const contractWETH = new ethers.Contract(addressWETH, abiWETH, provider)
方法2.

由于abi可读性太差,ethers创新的引入了Human-Readable Abi(人类可读abi)。开发者可以通过function signature和event signature来写abi。我们用这个方法创建稳定币DAI的合约实例:

// 第2种输入abi的方式:输入程序需要用到的函数,逗号分隔,ethers会自动帮你转换成相应的abi
// 人类可读abi,以ERC20合约为例
const abiERC20 = [
  "function name() view returns (string)",
  "function symbol() view returns (string)",
  "function totalSupply() view returns (uint256)",
  "function balanceOf(address) view returns (uint)",
];
const addressDAI = '0x6B175474E89094C44Da98b954EedeAC495271d0F' // DAI Contract
const contractDAI = new ethers.Contract(addressDAI, abiERC20, provider)

3.读取WETH和DAI的链上信息

const main = async () => {
  // 1. 读取WETH合约的链上信息(WETH abi)
  const nameWETH = await contractWETH.name()
  const symbolWETH = await contractWETH.symbol()
  const totalSupplyWETH = await contractWETH.totalSupply()
  console.log("\n1. 读取WETH合约信息")
  console.log(`合约地址: ${addressWETH}`)
  console.log(`名称: ${nameWETH}`)
  console.log(`代号: ${symbolWETH}`)
  console.log(`总供给: ${ethers.utils.formatEther(totalSupplyWETH)}`)
  const balanceWETH = await contractWETH.balanceOf('vitalik.eth')
  console.log(`Vitalik持仓: ${ethers.utils.formatEther(balanceWETH)}\n`)

  // 2. 读取DAI合约的链上信息(IERC20接口合约)
  const nameDAI = await contractDAI.name()
  const symbolDAI = await contractDAI.symbol()
  const totalSupplDAI = await contractDAI.totalSupply()
  console.log("\n2. 读取DAI合约信息")
  console.log(`合约地址: ${addressDAI}`)
  console.log(`名称: ${nameDAI}`)
  console.log(`代号: ${symbolDAI}`)
  console.log(`总供给: ${ethers.utils.formatEther(totalSupplDAI)}`)
  const balanceDAI = await contractDAI.balanceOf('vitalik.eth')
  console.log(`Vitalik持仓: ${ethers.utils.formatEther(balanceDAI)}\n`)
}

main()

在这里插入图片描述
说明 我们可以通过etherscan验证Vitalik钱包里的WETH余额, 是否与通过Contract读取的一致。 通过ENS 查到Vitalik钱包地址是0xd8dA6BF26964aF9D7eEd9e03E53415D37aA96045,然后通过合约方法balanceOf得到余额正好是0 WETH
在这里插入图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值