Solidity
如何通過 uint32, uint8web3.js 中智能合約的參數
我正在做估算氣體。這是我的程式碼。
var sdate = new Date('2021-07-01 00:00:00'); var edate = new Date('2021-07-31 00:00:00'); var arrDate = []; arrDate.push(sdate/1000); arrDate.push(edate/1000); var arrCategory = [1,12,14]; var param1 = web3.eth.abi.encodeParameter('uint32[]',arrDate); var param2 = web3.eth.abi.encodeParameter('uint8[]',arrCategory); let Contract = new web3.eth.Contract(myPack.abi, myPack.ca); Contract.methods.createTicket(param1, param2).estimateGas({from: accounts[0]}) .then(console.log);
我遇到了錯誤
Uncaught TypeError: t.map is not a function at h.formatParam (index.js:218) at index.js:100 at Array.map (<anonymous>) at h.encodeParameters (index.js:94) at index.js:439 at Array.map (<anonymous>) at Object.d._encodeMethodABI (index.js:438) at Object.d._processExecuteArguments (index.js:701) at Object.d._executeMethod (index.js:720) at estimateGas (issuecfm:257)
我在 encodeParameter 之前嘗試了一些東西
大數
var BN = web3.utils.BN; arrDate = arrDate.map(item => {return new BN(item)}); arrCategory = arrCategory.map(item => {return new BN(item)});
和字元串
arrDate = arrDate.map(item => {return item.toString()}); arrCategory = arrCategory.map(item => {return item.toString()});
經過大量搜尋,我盡我所能。但我仍然得到同樣的錯誤。如果您能教我如何修改我的程式碼,我將不勝感激。
添加
我像這樣修改了我的程式碼。
var parameters = web3.eth.abi.encodeParameters(['uint32[]', 'uint8[]'],[arrDate, arrCategory]); console.log(parameters); console.log(web3.eth.abi.decodeParameters(['uint32[]', 'uint8[]'],parameters)); let Contract = new web3.eth.Contract(myPack.abi, myPack.ca); Contract.methods.createTicket(parameters).estimateGas({from: accounts[0]}) .then(console.log); 0x000000000000000000000000000000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000e000000000000000000000000000000000000000000000000000000000000000040000000000000000000000000000000000000000000000000000000060e31e7000000000000000000000000000000000000000000000000000000000615b16ef0000000000000000000000000000000000000000000000000000000060e31e7000000000000000000000000000000000000000000000000000000000615b16ef000000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000090000000000000000000000000000000000000000000000000000000000000011 c {0: Array(4), 1: Array(3), __length__: 2}
我在控制台中檢查了參數的值是否正確編碼和解碼。&-一世
並遇到下一個錯誤
errors.js:33 Uncaught Error: Invalid number of parameters for "createTicket". Got 1 expected 2! at Object.InvalidNumberOfParams (errors.js:33) at Object.d._createTxObject (index.js:670) at estimateGas (issuecfm:261) at HTMLDocument.<anonymous> (issuecfm:130) at j (jquery-latest.min.js:2) at Object.fireWith [as resolveWith] (jquery-latest.min.js:2) at Function.ready (jquery-latest.min.js:2) at HTMLDocument.J (jquery-latest.min.js:2)
web.eth.abi.encodeParameters()
我相信您必須使用以下函式在數組中編碼兩個參數:您傳入一個類型數組和一個帶有參數值的數組,如下所示:
web3.eth.abi.encodeParameters(['uint32[]','uint8[]'], [arrDate, arrCategory]);
在你的solidity合約中,你像這樣解碼數據:
function createTicket(bytes calldata params) external ... { (uint32[] arrDate, uint8[] arrCategory) = abi.decode(params, (uint32[], uint8[]));
我從堆棧溢出中得到了一個簡單的解決方案。
使用 web3 合約助手函式,您需要傳遞“原始”JS 參數,而不是 ABI 編碼的數據。
所以我修改了我的程式碼
let contract = new web3.eth.Contract(myPack.abi, myPack.ca); // mind the `arrDate` and `arrCategory` instead of `param1` and `param2` contract.methods.createTicket(arrDate, arrCategory) .estimateGas({from: accounts[0]}) .then(console.log);
有用!!