Smart contract method is not a function in web3
Asked Answered
R

4

5

I am trying to follow an older tutorial on web3, but am getting errors that I believe are due Solidity being updated. I have the following code shown below

var express = require("express"),
    Web3 = require("web3"),
    web3;    
if (typeof web3 !== 'undefined') {
  web3 = new Web3(web3.currentProvider);
} else {
  // set the provider you want from Web3.providers
  web3 = new Web3(new Web3.providers.HttpProvider("http://localhost:8545"));
}

web3.eth.defaultAccount = web3.eth.accounts[0];

//define contract variable using ABI from compiled Remix tab.
var myContract = new web3.eth.Contract([abi_data]);

myContract.options.address = 'contract_address';

myContract.methods.totalSupply(function(err,res){
    if(!err){
        console.log(res);
    } else {
        console.log(err);
    }
})

where abi_data is my contract's abi data, contract_address is my contract's actual address in the Roptsen test network, and where totalSupply() is the method in my solidity smart contract on the Ropsten test network that returns the total supply of the token referenced in the contract. When testing this with node app.js to see if this logs properly, this error is returned...

/home/ubuntu/workspace/node_modules/web3-eth-contract/src/index.js:693
    throw errors.InvalidNumberOfParams(args.length, this.method.inputs.length, this.method.name);
    ^

Error: Invalid number of parameters for "totalSupply". Got 1 expected 0!
    at Object.InvalidNumberOfParams (/home/ubuntu/workspace/node_modules/web3-core-helpers/src/errors.js:32:16)
    at Object._createTxObject (/home/ubuntu/workspace/node_modules/web3-eth-contract/src/index.js:693:22)
    at Object.<anonymous> (/home/ubuntu/workspace/client/app.js:290:25)
    at Module._compile (module.js:570:32)
    at Object.Module._extensions..js (module.js:579:10)
    at Module.load (module.js:487:32)
    at tryModuleLoad (module.js:446:12)
    at Function.Module._load (module.js:438:3)
    at Module.runMain (module.js:604:10)
    at run (bootstrap_node.js:389:7)
    at startup (bootstrap_node.js:149:9)

And totalSupply is defined in Soldiity as follows...

function totalSupply() constant returns (uint256 totalSupply){
    return _totalSupply;
}

Using Adam's fix, I still get the following error...

Error: Invalid JSON RPC response: ""
at Object.InvalidResponse (/home/ubuntu/workspace/node_modules/web3-core-helpers/src/errors.js:42:16)
at XMLHttpRequest.request.onreadystatechange (/home/ubuntu/workspace/node_modules/web3-providers-http/src/index.js:73:32)
at XMLHttpRequestEventTarget.dispatchEvent (/home/ubuntu/workspace/node_modules/xhr2/lib/xhr2.js:64:18)
at XMLHttpRequest._setReadyState (/home/ubuntu/workspace/node_modules/xhr2/lib/xhr2.js:354:12)
at XMLHttpRequest._onHttpRequestError (/home/ubuntu/workspace/node_modules/xhr2/lib/xhr2.js:544:12)
at ClientRequest.<anonymous> (/home/ubuntu/workspace/node_modules/xhr2/lib/xhr2.js:414:24)
at emitOne (events.js:96:13)
at ClientRequest.emit (events.js:188:7)
at Socket.socketErrorListener (_http_client.js:310:9)
at emitOne (events.js:96:13)
at Socket.emit (events.js:188:7)
at emitErrorNT (net.js:1277:8)
at _combinedTickCallback (internal/process/next_tick.js:80:11)
at process._tickCallback (internal/process/next_tick.js:104:9)
Revest answered 31/1, 2018 at 16:47 Comment(3)
Try myContract.methods.totalSupply.Rasla
I made this adjustment. I now get the following error Error: Invalid number of parameters for "totalSupply". Got 1 expected 0! I updated the question to reflect this.Revest
This stuff is changing so fast each tutorial only has a shelf life of a few months before problems creep inRanie
R
6

Take a closer look at the web3 1.0 documentation for calling methods (it's very different from the 0.2x API). To call a contract method, you need to first create the method object using contractInstance.methods.methodName() replacing "methodName" with the method in the contract you want to call. You also need to pass in the parameters for the contract function to this method (the callback does not get passed in here). With the method object, you can then use either the call method (for constant functions) or send (for transactions). totalSupply should be a constant function, so your code should be:

myContract.methods.totalSupply().call(function(err,res){
    if(!err){
        console.log(res);
    } else {
        console.log(err);
    }
);

Or you can use the returned Promise instead of passing in the callback:

myContract.methods.totalSupply().call().then(function(res){
    console.log(res);
}).catch(function(err) {
    console.log(err);
});

Sending transactions is similar, but uses an event emitter for receiving the transaction hash, receipt, etc.

Rasla answered 31/1, 2018 at 18:33 Comment(2)
I ran into one more error with this, but it appears the issue is due to my attempt to use the test RPC without doing a couple extra steps.Revest
Hi @Revest And which are those extra steps to use the test RPC? I'm already connected to ganach-cli on my local environmentStroud
T
4

For anyone else struggling, try to check whether your ABI json actually includes the method you are trying to call. It could have been that you copied the ABI for the wrong contract as Remix would by default list the first contract in the default template rather than your newly created contract.

Territoriality answered 30/10, 2021 at 17:42 Comment(2)
this one worked for me. thanksHydroxyl
lmao, this worked for me too, had to pick the correct contract from the dropdown hahahaVolnay
A
2

This is a new language for me so my error came when I copied the abi into my variable and it pasted an extra set of "[]" so it looked something like:

const abi = [[...]];

If I'm correct, it should be:

const abi = [...];

with only single set of the most outer square brackets. This is probably only a mistake for someone like myself who is still learning the syntax of this language.

Albertoalberts answered 2/1, 2022 at 19:40 Comment(0)
E
0

There is actually a simple fix to this:

I was using express and web3 together but web3 1.0.0-beta was the issue. You just have to install a stable version such as 0.19.0 or 0.20.0

npm install web3@^0.19.0 --save

Then it will work.

Eugenie answered 19/4, 2018 at 11:6 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.