function return2d() public view returns(uint256[1][1]) {
uint256 x = 354;
return [[x]];
}
in js
await contractX.return2d();
Error: Error: [number-to-bn] while converting number ["354"] to BN.js instance, error: invalid number value. Value must be an integer, hex string, BN or BigNumber instance. Note, decimals are not supported. Given value: "354"
at Object.toBN (node_modules/truffle/build/webpack:/~/web3-utils/src/utils.js:64:1)
at _convertNumber (node_modules/truffle/build/webpack:/packages/truffle-contract/lib/reformat.js:18:1)
at arr.map.item (node_modules/truffle/build/webpack:/packages/truffle-contract/lib/reformat.js:31:1)
at Array.map (<anonymous>)
at _convertNumberArray (node_modules/truffle/build/webpack:/packages/truffle-contract/lib/reformat.js:31:1)
at abiSegment.forEach (node_modules/truffle/build/webpack:/packages/truffle-contract/lib/reformat.js:57:1)
at Array.forEach (<anonymous>)
at Function.numbers (node_modules/truffle/build/webpack:/packages/truffle-contract/lib/reformat.js:47:1)
at Promise (node_modules/truffle/build/webpack:/packages/truffle-contract/lib/execute.js:120:1)
at <anonymous>
at process._tickCallback (internal/process/next_tick.js:182:7)
I suppose the first piece of code is Solidity. This should work
function return2d() public constant returns(uint256[1][1] res) {
uint x = 10;
res[0][0] = x;
}
Tested with truffle.
@chmelva4, thanks for the answer! I checked your code, but unfortunately I got the same result.
Error: Error: [number-to-bn] while converting number ["10"] to BN.js instance, error: invalid number value. Value must be an integer, hex string, BN or BigNumber instance. Note, decimals are not supported. Given value: "10"
at Object.toBN (node_modules/truffle/build/webpack:/~/web3-utils/src/utils.js:64:1)
at _convertNumber (node_modules/truffle/build/webpack:/packages/truffle-contract/lib/reformat.js:18:1)
at arr.map.item (node_modules/truffle/build/webpack:/packages/truffle-contract/lib/reformat.js:31:1)
at Array.map (<anonymous>)
at _convertNumberArray (node_modules/truffle/build/webpack:/packages/truffle-contract/lib/reformat.js:31:1)
at abiSegment.forEach (node_modules/truffle/build/webpack:/packages/truffle-contract/lib/reformat.js:57:1)
at Array.forEach (<anonymous>)
at Function.numbers (node_modules/truffle/build/webpack:/packages/truffle-contract/lib/reformat.js:47:1)
at Promise (node_modules/truffle/build/webpack:/packages/truffle-contract/lib/execute.js:120:1)
at <anonymous>
at process._tickCallback (internal/process/next_tick.js:188:7)
Thats because you are most likely converting the number incorrectly after getting it from blockchain.
I did it like this and it works.
it('should return 10', async () => {
var test2d = await Test2d.deployed();
var x = await test2d.return2d()
console.log(x);
assert.isTrue(x[0][0].toNumber() == 10);
})
You should take a look in debugger at what you are passing as arguments to toBN function. I think it cannot handle arrays.
@chmelva4 I get the error but I don't make the console.log. The error is output after await contractX.return2d(). What version of truffle do you have installed?
v4.1.14
@chmelva4 exactly! it doesn't work on v5 truffle
Apparently the issue happens when using async/await. If you switch to promisses (which is cumbersome), it works.
@chmelva4 so, it's valid issue. It should work with async/await
Ye you're right, I posted that for info.
Using truffle v5 and also getting the same issue when using the truffle contract-abstraction to call a contract that returns a 2D array.
@chmelva4 Any way to not use async/await but promises with truffle contract abstractions?
Looks like it may be possible to wrap the Truffle Artifacts using own web3 in dependencies for testing and then call the contract functions via contract.methods.functions() and handle results case by case instead of relying on Truffle Contract Artifacts.
Uncaught Error: Error: [number-to-bn] while converting number ["5446375890709390460","0"] to BN.js instance, error: invalid number value. Value must be an integer, hex string, BN or BigNumber instance. Note, decimals are not supported. Given value: "5446375890709390460,0"
at Object.toBN (node_modules/web3-utils/src/utils.js:64:15)
at _convertNumber (node_modules/truffle-contract/lib/reformat.js:18:40)
at arr.map.item (node_modules/truffle-contract/lib/reformat.js:31:27)
at Array.map (<anonymous>)
at _convertNumberArray (node_modules/truffle-contract/lib/reformat.js:31:14)
at abiSegment.forEach (node_modules/truffle-contract/lib/reformat.js:57:20)
at Array.forEach (<anonymous>)
at Function.numbers (node_modules/truffle-contract/lib/reformat.js:47:14)
at Promise (node_modules/truffle-contract/lib/execute.js:120:37)
I'll check that with the truffle team asap :)
Running into the same issue when trying to return a 2d array from Solidity (using pragma experimental ABIEncoderV2;).
Any updates/way to fix it?
I've tested this with web3.js v1.2.2 and it can return a 2D array without a problem.
Contract:
pragma solidity ^0.5.8;
pragma experimental ABIEncoderV2;
contract Test {
function return2d() public view returns(uint256[1][1] memory) {
uint256 x = 354;
return [[x]];
}
}
JS:
var web3 = new Web3('http://localhost:7545');
const contract = new web3.eth.Contract([
{
"constant": true,
"inputs": [],
"name": "return2d",
"outputs": [
{
"name": "",
"type": "uint256[1][1]"
}
],
"payable": false,
"stateMutability": "view",
"type": "function"
}
], '0x4F063F7C86561137d10a08C13Bb228BF93B90B9B');
contract.methods.return2d().call().then(console.log);
> [ [ '354' ] ]