日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁(yè) > 编程资源 > 编程问答 >内容正文

编程问答

以太坊钱包开发系列4 - 发送Token(代币)

發(fā)布時(shí)間:2023/12/10 编程问答 38 豆豆
生活随笔 收集整理的這篇文章主要介紹了 以太坊钱包开发系列4 - 发送Token(代币) 小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

以太坊去中心化網(wǎng)頁(yè)錢包開發(fā)系列,將從零開始開發(fā)出一個(gè)可以實(shí)際使用的錢包,本系列文章是理論與實(shí)戰(zhàn)相結(jié)合,一共有四篇:創(chuàng)建錢包賬號(hào)、賬號(hào)Keystore文件導(dǎo)入導(dǎo)出、展示錢包信息及發(fā)起簽名交易、發(fā)送Token(代幣),本文是第四篇,Token(代幣、通證)是以太坊的一大特色,既然開發(fā)錢包,則發(fā)送Token 功能必不可少。

合約 ABI 信息

首先我們需要明白,進(jìn)行Token轉(zhuǎn)賬的時(shí)候,其實(shí)是在調(diào)用合約的轉(zhuǎn)賬函數(shù),而要調(diào)用一個(gè)合約的函數(shù),需要知道合約的 ABI 信息。

其次 通常我們所說的Token, 其實(shí)指的是符合 ERC20 標(biāo)準(zhǔn)接口的合約, ERC20 接口定義如下:

contract ERC20Interface {string public constant name = "Token Name";string public constant symbol = "SYM";uint8 public constant decimals = 0;function totalSupply() public constant returns (uint);function balanceOf(address tokenOwner) public constant returns (uint balance);function allowance(address tokenOwner, address spender) public constant returns (uint remaining);function approve(address spender, uint tokens) public returns (bool success);function transfer(address to, uint tokens) public returns (bool success);function transferFrom(address from, address to, uint tokens) public returns (bool success);event Transfer(address indexed from, address indexed to, uint tokens);event Approval(address indexed tokenOwner, address indexed spender, uint tokens); } 復(fù)制代碼

ABI 全稱是 Application Binary Interface,它就是合約接口的描述,因此有了合約的接口定義,就可以很容易通過編譯拿到ABI 信息,比如像下圖在Remix 的編譯選項(xiàng)卡就可以直接復(fù)制ABI。

生成的 ABI 描述大概長(zhǎng)這樣:

[ ...{"constant": true,"inputs": [],"name": "totalSupply","outputs": [{"name": "","type": "uint256"}],"payable": false,"stateMutability": "view","type": "function"},{"constant": true,"inputs": [{"name": "tokenOwner","type": "address"}],"name": "balanceOf","outputs": [{"name": "balance","type": "uint256"}],"payable": false,"stateMutability": "view","type": "function"},... ] 復(fù)制代碼

它是一個(gè)JSON形式的數(shù)組,數(shù)組里每一個(gè)元素,都是對(duì)函數(shù)接口的描述,在外部調(diào)用合約的時(shí)候就需要遵從這個(gè)接口,以上面的接口為例,通常一個(gè)接口描述包含下述幾個(gè)字段:

  • name: 函數(shù)會(huì)事件的名稱
  • type: 可取值有function,constructor,fallback,event
  • inputs: 函數(shù)的輸入?yún)?shù),每個(gè)參數(shù)對(duì)象包含下述屬性:
    • name: 參數(shù)名稱
    • type: 參數(shù)的規(guī)范型(Canonical Type)。
  • outputs: 一系列的類似inputs的對(duì)象,如果無返回值時(shí),可以省略。
  • constant: true表示函數(shù)聲明自己不會(huì)改變狀態(tài)變量的值。
  • payable: true表示函數(shù)可以接收ether,否則表示不能。

接下來在構(gòu)造合約對(duì)象就需要是使用ABI。

構(gòu)造合約對(duì)象

ethers.js 構(gòu)造合約對(duì)象很簡(jiǎn)單,僅需要提供三個(gè)參數(shù)給ethers.Contract構(gòu)造函數(shù),代碼如下:

var abi = [...];var addr = "0x...";var contract = new ethers.Contract(address, abi, provider);復(fù)制代碼

合約的地址在合約部署之后,可以獲得,關(guān)于Token合約部署及ERC20相關(guān)的概念,這里不展開講,不熟悉的同學(xué),可以參考我另一篇文章創(chuàng)建自己的數(shù)字貨幣。

只有就可以是使用 contract 對(duì)象來調(diào)用Token合約的函數(shù)。

獲取Token余額及轉(zhuǎn)移Token

獲取Token余額

結(jié)合UI來實(shí)現(xiàn)以下獲取Token余額,UI如下:

在HTML里,定義的標(biāo)簽如下:

<tr><th>TT Token:</th><td><input type="text" readonly="readonly" class="readonly" id="wallet-token-balance" value="0.0" /></div></td></tr> 復(fù)制代碼

對(duì)應(yīng)的邏輯代碼也很簡(jiǎn)單:

var tokenBalance = $('#wallet-token-balance');// 直接調(diào)用合約方法contract.balanceOf(activeWallet.address).then(function(balance){tokenBalance.val(balance);}); 復(fù)制代碼

轉(zhuǎn)移Token

轉(zhuǎn)移Token的UI效果如下:

界面的HTML代碼如下:

<h3>轉(zhuǎn)移代幣:</h3> <table><tr><th>發(fā)送至:</th><td><input type="text" placeholder="(target address)" id="wallet-token-send-target-address" /></td></tr><tr><th>金額:</th><td><input type="text" placeholder="(amount)" id="wallet-token-send-amount" /></td></tr><tr><td> </td><td><div id="wallet-token-submit-send" class="submit disable">發(fā)送</div></td></tr> </table> 復(fù)制代碼

上面定義了兩個(gè)文本輸入框及一個(gè)“發(fā)送“按鈕,在邏輯處理部分,轉(zhuǎn)移Token代幣盡管和獲取余額類似,同樣是調(diào)用合約的方法,不過轉(zhuǎn)移代幣需要發(fā)起一個(gè)交易,因此需要測(cè)量gas 消耗。 點(diǎn)擊發(fā)送時(shí)運(yùn)行一下(關(guān)鍵)代碼:

var inputTargetAddress = $('#wallet-token-send-target-address'); var inputAmount = $('#wallet-token-send-amount'); var submit = $('#wallet-token-submit-send');var targetAddress = ethers.utils.getAddress(inputTargetAddress.val()); var amount = inputAmount.val();submit.click(function() { // 先計(jì)算transfer 需要的gas 消耗量,這一步有默認(rèn)值,非必須。contract.estimate.transfer(targetAddress, amount).then(function(gas) {// 必須關(guān)聯(lián)一個(gè)有過簽名錢包對(duì)象let contractWithSigner = contract.connect(activeWallet);// 發(fā)起交易,前面2個(gè)參數(shù)是函數(shù)的參數(shù),第3個(gè)是交易參數(shù)contractWithSigner.transfer(targetAddress, amount, {gasLimit: gas,// 偷懶,直接是用 2gweigasPrice: ethers.utils.parseUnits("2", "gwei"),}).then(function(tx) {console.log(tx);// 介紹刷新上面的Token余額,重置輸入框}); }); } 復(fù)制代碼

上述有一個(gè)地方都要注意一下,在合約調(diào)用 transfer 之前, 需要連接一個(gè)signer,因?yàn)榘l(fā)起交易的時(shí)候需要用它來進(jìn)行簽名,在ethers.js API里 Wallet 是 signer(抽象類)的實(shí)現(xiàn)類。

所有會(huì)更改區(qū)塊鏈數(shù)據(jù)的函數(shù)都需要關(guān)聯(lián)簽名器,如果是視圖函數(shù)則只需要連接provider。

ethers.js 的 Contract 提供了一個(gè)非常方便方法:contract.estimate.functionName 來計(jì)算預(yù)測(cè)交易的gasLimit。

在發(fā)起交易的時(shí)候,可以提供一個(gè)可選的Overrides參數(shù),在這個(gè)參數(shù)里可以指定如交易的 gasLimit 、 gasPrice,如果我們不指定這個(gè)參數(shù)時(shí),會(huì)默認(rèn)使用 contract.estimate 獲得的值作為 gasLimit,以及 provider.getGasPrice() 的值來指定 gasPrice。

完整源碼請(qǐng)訂閱深入淺出區(qū)塊鏈技術(shù)小專欄查看, 哈哈,是不是有一點(diǎn)雞賊,創(chuàng)作不易呀。 戳鏈接收看詳細(xì)的視頻課程講解。

參考文檔: ethers.js

深入淺出區(qū)塊鏈 - 系統(tǒng)學(xué)習(xí)區(qū)塊鏈,打造最好的區(qū)塊鏈技術(shù)博客。

深入淺出區(qū)塊鏈知識(shí)星球最專業(yè)技術(shù)問答社區(qū),加入社區(qū)還可以在微信群里和300多位區(qū)塊鏈技術(shù)愛好者一起交流。

總結(jié)

以上是生活随笔為你收集整理的以太坊钱包开发系列4 - 发送Token(代币)的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。