2

I need to update a contract by calling one of their function but I cant use web3.js so I need to send a raw transaction.

example of function to be call on the contract:

test(address buyer, uint256 amount)

my code in javascript:

var rawTx = {
   nonce: 'CX350',
   gasPrice: 'C350',
   gasLimit: '0x09184e72a000',
   to: 'myAddress',
   value: 'CX350',
   data:  .....
}

How I can encode this call and parameters:

test('0xc5622be5861b7200cbace14e28b98c4ab77bd9b4', 10000)

??

1
  • Why can't you use web3.js? You will end up rewriting significant chunks of it if you want to send transactions in javascript.
    – carver
    Commented Aug 25, 2017 at 16:18

2 Answers 2

2

Well the above approach works, but why not use the web3.js library which helps in doing the same. Just download web3.js using NPM (or anywhere else) and get the modules required for the task, by:

const_ = require('lodash');
const SolidityFunction = require('web3/lib/web3/function');

You can use the web3.js library along with your ABI to find the function definition, using the below code:

var ABI = JSON.parse(<your_ABI>);
var functionDef = new SolidityFunction('', _.find(ABI, { name: '<your_function_name>' }), '');

After this, you can call the method toPayload which will help you converting the values that you want to pass to your function into HEX Data.

var payloadData = functionDef.toPayload([<value_for_var_1>, <value_for_var_2>, <value_for_var_3>, <value_for_var_4>]).data;

payloadData can be used as Value for the DATA property. Example:

var rawTx = {
 to: <to_address>,
 data: payloadData,
 value: '0x0',
 from: <from_address>,
 nonce: nonce,
 gasLimit: gasLimit,
 gasPrice: gasPrice
}

You can use this approach and forget about how many zeros to pad with. As the toPayload function handles everything.

0
4

This is fairly straightforward as per the ABI spec

First you need the function selector for test(address,uint256) which is the first four bytes of the keccak-256 hash of that string, namely 0xba14d606.

Then you need the address as a 32-byte word: 0x000000000000000000000000c5622be5861b7200cbace14e28b98c4ab77bd9b4.

Finally you need 10000 as a 32-byte word: 0x0000000000000000000000000000000000000000000000000000000000002710

So the final data string you require is:

0xba14d606000000000000000000000000c5622be5861b7200cbace14e28b98c4ab77bd9b40000000000000000000000000000000000000000000000000000000000002710

And that's it!

5
  • thanks, it worked :) But now I face another problem: the raw tx works on the Ether Scan ropsten.etherscan.io/pushTx however on web3.js: Error: invalid argument 0: cannot unmarshal non-string as hex data Commented Aug 25, 2017 at 14:14
  • You probably just need to put the data in single quotation marks, but it's hard to tell exactly on this info. Commented Aug 25, 2017 at 14:18
  • My function test(uint256) data: '0xb3f4d2350000000000000000000000000000000000000000000000000000000000003039' ` const txParams = { nonce: nonce, gasPrice: '0x09184e72a000', gasLimit: web3.toHex(47189), to: contractAddress, value: '0x00', data: data, chainId: 3 } ` still getting the error :/ Commented Aug 25, 2017 at 14:30
  • I think the function signature of test(uint256) is 0x29e99f07, so try that instead of your first four bytes. I.e. 0x29e99f070000000000000000000000000000000000000000000000000‌​000000000003039 Commented Aug 25, 2017 at 14:38
  • Great! Good to know. Commented Aug 25, 2017 at 14:40

Not the answer you're looking for? Browse other questions tagged or ask your own question.