API调用返回的Contract_ABI有JSON接口错误

Posted

技术标签:

【中文标题】API调用返回的Contract_ABI有JSON接口错误【英文标题】:Contract_ABI returned from API call has JSON interface error 【发布时间】:2021-06-30 10:48:56 【问题描述】:

我正在尝试通过从 BSCSCAN 测试网 API 获取合约 ABI 来设置智能合约。我已经成功地从 TESTNET API 获得了 USDT 的合约 ABI (https://testnet.bscscan.com/address/0x337610d27c682e347c9cd60bd4b3b107c9d34ddd) 但是当我尝试设置合约时,我收到了这个错误:

Error: You must provide the json interface of the contract when instantiating a contract object.
    at Contract (C:\Users\User\Documents\Coding Projects\trading-bot - modified\node_modules\web3-eth-contract\src\index.js:70:15)
    at new Contract (C:\Users\User\Documents\Coding Projects\trading-bot - modified\node_modules\web3-eth\src\index.js:149:22)

这是我在 main() 函数中运行以获取 ABI 的异步函数

// Funciton to get the token ABI that uses the BSCSCAN API to get the token you want (IN THIS CASE USDT)
async function getTokenWanted()
let tokenAddress = '0x337610d27c682e347c9cd60bd4b3b107c9d34ddd';
let tokenWantedAPI = "https://api-testnet.bscscan.com/api?module=contract&action=getabi&address="+tokenAddress+"&apikey=" +process.env.BSCSCAN_API;

        try 
          const res = await fetch(tokenWantedAPI);
          const headerDate = res.headers && res.headers.get('date') ? res.headers.get('date') : 'no response date';
          console.log('Status Code:', res.status);
          console.log('Date in Response header:', headerDate);
          let users = await res.json();
          contractABI =users.result;

          return contractABI
         catch (err) 
          console.log(err.message); //can be console.error
        


// Function to setup the token contract 
async function setupTokenWantedContract()
  let contract_ABI = await getTokenWanted();
  console.log(contract_ABI);
  let token_Address ='0x337610d27c682e347c9cd60bd4b3b107c9d34ddd';
  const tokenContract = new web3.eth.Contract(contract_ABI, token_Address);
  
  return tokenContract;

这些函数在主函数中运行,如下所示:

async function main()

let tokenWantedContract = awaitsetupTokenWantedContract()


登录到控制台时收集到的 ABI 合约是这样的(这与您在 bscscan 中转到合约 ABI 并将其复制并粘贴到代码中时完全相同,但是我想这样做动态地,因此我使用 API):

["inputs":[],"payable":false,"stateMutability":"nonpayable","type":"constructor","anonymous":false,"inputs":["indexed":true,"internalType":"address","name":"owner","type":"address","indexed":true,"internalType":"address","name":"spender","type":"address","indexed":false,"internalType":"uint256","name":"value","type":"uint256"],"name":"Approval","type":"event","anonymous":false,"inputs":["indexed":true,"internalType":"address","name":"previousOwner","type":"address","indexed":true,"internalType":"address","name":"newOwner","type":"address"],"name":"OwnershipTransferred","type":"event","anonymous":false,"inputs":["indexed":true,"internalType":"address","name":"from","type":"address","indexed":true,"internalType":"address","name":"to","type":"address","indexed":false,"internalType":"uint256","name":"value","type":"uint256"],"name":"Transfer","type":"event","constant":true,"inputs":[],"name":"_decimals","outputs":["internalType":"uint8","name":"","type":"uint8"],"payable":false,"stateMutability":"view","type":"function","constant":true,"inputs":[],"name":"_name","outputs":["internalType":"string","name":"","type":"string"],"payable":false,"stateMutability":"view","type":"function","constant":true,"inputs":[],"name":"_symbol","outputs":["internalType":"string","name":"","type":"string"],"payable":false,"stateMutability":"view","type":"function","constant":true,"inputs":["internalType":"address","name":"owner","type":"address","internalType":"address","name":"spender","type":"address"],"name":"allowance","outputs":["internalType":"uint256","name":"","type":"uint256"],"payable":false,"stateMutability":"view","type":"function","constant":false,"inputs":["internalType":"address","name":"spender","type":"address","internalType":"uint256","name":"amount","type":"uint256"],"name":"approve","outputs":["internalType":"bool","name":"","type":"bool"],"payable":false,"stateMutability":"nonpayable","type":"function","constant":true,"inputs":["internalType":"address","name":"account","type":"address"],"name":"balanceOf","outputs":["internalType":"uint256","name":"","type":"uint256"],"payable":false,"stateMutability":"view","type":"function","constant":true,"inputs":[],"name":"decimals","outputs":["internalType":"uint256","name":"","type":"uint256"],"payable":false,"stateMutability":"view","type":"function","constant":false,"inputs":["internalType":"address","name":"spender","type":"address","internalType":"uint256","name":"subtractedValue","type":"uint256"],"name":"decreaseAllowance","outputs":["internalType":"bool","name":"","type":"bool"],"payable":false,"stateMutability":"nonpayable","type":"function","constant":true,"inputs":[],"name":"getOwner","outputs":["internalType":"address","name":"","type":"address"],"payable":false,"stateMutability":"view","type":"function","constant":false,"inputs":["internalType":"address","name":"spender","type":"address","internalType":"uint256","name":"addedValue","type":"uint256"],"name":"increaseAllowance","outputs":["internalType":"bool","name":"","type":"bool"],"payable":false,"stateMutability":"nonpayable","type":"function","constant":false,"inputs":["internalType":"uint256","name":"amount","type":"uint256"],"name":"mint","outputs":["internalType":"bool","name":"","type":"bool"],"payable":false,"stateMutability":"nonpayable","type":"function","constant":true,"inputs":[],"name":"name","outputs":["internalType":"string","name":"","type":"string"],"payable":false,"stateMutability":"view","type":"function","constant":true,"inputs":[],"name":"owner","outputs":["internalType":"address","name":"","type":"address"],"payable":false,"stateMutability":"view","type":"function","constant":false,"inputs":[],"name":"renounceOwnership","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function","constant":true,"inputs":[],"name":"symbol","outputs":["internalType":"string","name":"","type":"string"],"payable":false,"stateMutability":"view","type":"function","constant":true,"inputs":[],"name":"totalSupply","outputs":["internalType":"uint256","name":"","type":"uint256"],"payable":false,"stateMutability":"view","type":"function","constant":false,"inputs":["internalType":"address","name":"recipient","type":"address","internalType":"uint256","name":"amount","type":"uint256"],"name":"transfer","outputs":["internalType":"bool","name":"","type":"bool"],"payable":false,"stateMutability":"nonpayable","type":"function","constant":false,"inputs":["internalType":"address","name":"sender","type":"address","internalType":"address","name":"recipient","type":"address","internalType":"uint256","name":"amount","type":"uint256"],"name":"transferFrom","outputs":["internalType":"bool","name":"","type":"bool"],"payable":false,"stateMutability":"nonpayable","type":"function","constant":false,"inputs":["internalType":"address","name":"newOwner","type":"address"],"name":"transferOwnership","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"] 

这是我目前尝试过的:

将api的结果包装到JSON.Parse()中,但是如果它被包装在JSON.Parse()中,错误是一样的。

感谢任何帮助,因为我是 web3 编码的新手,并认为这将是一个有趣的项目!谢谢!

【问题讨论】:

【参考方案1】:

显然,当我在这个代码块上使用 JSON.Parse 时,我不知何故让它工作了:

// Funciton to get the token ABI that uses the BSCSCAN API to get the token you want (IN THIS CASE USDT)
async function getTokenWanted()
let tokenAddress = '0x337610d27c682e347c9cd60bd4b3b107c9d34ddd';
let tokenWantedAPI = "https://api-testnet.bscscan.com/api?module=contract&action=getabi&address="+tokenAddress+"&apikey=" +process.env.BSCSCAN_API;

        try 
          const res = await fetch(tokenWantedAPI);
          const headerDate = res.headers && res.headers.get('date') ? res.headers.get('date') : 'no response date';
          console.log('Status Code:', res.status);
          console.log('Date in Response header:', headerDate);
          let users = await res.json();
          contractABI =JSON.parse(users.result);

          return contractABI
         catch (err) 
          console.log(err.message); //can be console.error
        

奇怪,我第一次尝试 JSON.Parse() 时一定有问题。

【讨论】:

以上是关于API调用返回的Contract_ABI有JSON接口错误的主要内容,如果未能解决你的问题,请参考以下文章

调用从 react-app 返回 JSON 的 REST API

Fetch -API 返回 HTML 而不是 JSON

API 调用返回 HTML 而不是 JSON

如何使用 Chainlink api 调用通过 api 从 json 返回中检索字符串值

如何将 JSON 返回反序列化为从 RestSharp 调用到 API 的对象数组?

如何使用从 API 调用返回的 JSON 数据使 jquery 自动建议