Error interacting with upgradeable contract via web3 "Contract with hash not found."

Hello guys,

I am in a bit of a mix here, i am still trying to wrap my head around the upgradeable contract.

I have been able to deploy a smart contract here https://etherscan.io/address/0xfe3f733569896f14d3bb15da145f177950de3239

I can interact with the contract using OZ contract-loader with .fromArtifact() and the contract address. Which means i must always have the contract’s build file.

but anytime i try loading the contract using web3.js with ABI it keeps throwing this error
Contract with hash fe3F733569896F14D3BB15DA145f177950de3239 not found.

I understand the contract code in this address is a proxy contract, so my question is this, how do i interact with an upgradeable contract without using artifact? I just want to use the ABI and the contract address on the blockchain.

1 Like

Hi @1baga,

Sorry for the delay in getting back to you.

You should be able to interact with an upgradeable contract using the address of the proxy contract (in your case: 0xfe3f733569896f14d3bb15da145f177950de3239) and the ABI of the implementation contract (in your case: 0x6ebcd4b1d977e50687b29a8831d78e76818ba09a)

I used the following script to interact with your contract:

index.js

Load contract using address and ABI

// src/index.js
const Web3 = require('web3');

const { projectId, mnemonic } = require('../secrets.json');
const abi = require('./ERC20ABI.json');

const HDWalletProvider = require('@truffle/hdwallet-provider');

const provider = new HDWalletProvider(mnemonic, `https://mainnet.infura.io/v3/${projectId}`);

async function main() {
  // Set up web3 object
  const web3 = new Web3(provider);

  // Set up a web3 contract, representing a deployed ERC20, using the contract loader
  const address = '0xfe3f733569896f14d3bb15da145f177950de3239';
  const token = new web3.eth.Contract(abi, address);

  // Retrieve accounts
  const accounts = await web3.eth.getAccounts();

  console.log(`Account: ${accounts[0]}`);

  // Call the deployed token contract
  const name = await token.methods.name().call();
  const symbol = await token.methods.symbol().call();
  const decimals = await token.methods.decimals().call();
  const totalSupply = await token.methods.totalSupply().call();
  console.log(`${name} (${symbol}) - Decimals:${decimals} Total Supply:${totalSupply}`);

  // At termination, `provider.engine.stop()' should be called to finish the process elegantly.
  provider.engine.stop();
}

main();

ERC20ABI.json

[
	{
		"inputs": [
			{
				"internalType": "string",
				"name": "name",
				"type": "string"
			},
			{
				"internalType": "string",
				"name": "symbol",
				"type": "string"
			}
		],
		"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": "from",
				"type": "address"
			},
			{
				"indexed": true,
				"internalType": "address",
				"name": "to",
				"type": "address"
			},
			{
				"indexed": false,
				"internalType": "uint256",
				"name": "value",
				"type": "uint256"
			}
		],
		"name": "Transfer",
		"type": "event"
	},
	{
		"inputs": [
			{
				"internalType": "address",
				"name": "owner",
				"type": "address"
			},
			{
				"internalType": "address",
				"name": "spender",
				"type": "address"
			}
		],
		"name": "allowance",
		"outputs": [
			{
				"internalType": "uint256",
				"name": "",
				"type": "uint256"
			}
		],
		"stateMutability": "view",
		"type": "function"
	},
	{
		"inputs": [
			{
				"internalType": "address",
				"name": "spender",
				"type": "address"
			},
			{
				"internalType": "uint256",
				"name": "amount",
				"type": "uint256"
			}
		],
		"name": "approve",
		"outputs": [
			{
				"internalType": "bool",
				"name": "",
				"type": "bool"
			}
		],
		"stateMutability": "nonpayable",
		"type": "function"
	},
	{
		"inputs": [
			{
				"internalType": "address",
				"name": "account",
				"type": "address"
			}
		],
		"name": "balanceOf",
		"outputs": [
			{
				"internalType": "uint256",
				"name": "",
				"type": "uint256"
			}
		],
		"stateMutability": "view",
		"type": "function"
	},
	{
		"inputs": [],
		"name": "decimals",
		"outputs": [
			{
				"internalType": "uint8",
				"name": "",
				"type": "uint8"
			}
		],
		"stateMutability": "view",
		"type": "function"
	},
	{
		"inputs": [
			{
				"internalType": "address",
				"name": "spender",
				"type": "address"
			},
			{
				"internalType": "uint256",
				"name": "subtractedValue",
				"type": "uint256"
			}
		],
		"name": "decreaseAllowance",
		"outputs": [
			{
				"internalType": "bool",
				"name": "",
				"type": "bool"
			}
		],
		"stateMutability": "nonpayable",
		"type": "function"
	},
	{
		"inputs": [
			{
				"internalType": "address",
				"name": "spender",
				"type": "address"
			},
			{
				"internalType": "uint256",
				"name": "addedValue",
				"type": "uint256"
			}
		],
		"name": "increaseAllowance",
		"outputs": [
			{
				"internalType": "bool",
				"name": "",
				"type": "bool"
			}
		],
		"stateMutability": "nonpayable",
		"type": "function"
	},
	{
		"inputs": [],
		"name": "name",
		"outputs": [
			{
				"internalType": "string",
				"name": "",
				"type": "string"
			}
		],
		"stateMutability": "view",
		"type": "function"
	},
	{
		"inputs": [],
		"name": "symbol",
		"outputs": [
			{
				"internalType": "string",
				"name": "",
				"type": "string"
			}
		],
		"stateMutability": "view",
		"type": "function"
	},
	{
		"inputs": [],
		"name": "totalSupply",
		"outputs": [
			{
				"internalType": "uint256",
				"name": "",
				"type": "uint256"
			}
		],
		"stateMutability": "view",
		"type": "function"
	},
	{
		"inputs": [
			{
				"internalType": "address",
				"name": "recipient",
				"type": "address"
			},
			{
				"internalType": "uint256",
				"name": "amount",
				"type": "uint256"
			}
		],
		"name": "transfer",
		"outputs": [
			{
				"internalType": "bool",
				"name": "",
				"type": "bool"
			}
		],
		"stateMutability": "nonpayable",
		"type": "function"
	},
	{
		"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"
			}
		],
		"stateMutability": "nonpayable",
		"type": "function"
	}
]

Interact with the contract using the script:

$ node src/index.js
Account: 0x77737a65C296012C67F8c7f656d1Df81827c9541
Sanu Gold (SGLD) - Decimals:18 Total Supply:5000

Hi @1baga,

Checking that you were able to use the above solution?