I have wrote a contract in solidity language and test it in remix.ethereum.org and all functionality was working, but when I tried to test it with nodejs and web3 library using ganache there was a scenario not working as it should. I modify an array in my contract then I call a function to return that array but what I get is an empty array, I don't know why and tried to search for similar problem but I didn't found.
contract code
pragma solidity ^0.4.17;
contract web2decentorage {
address public decentorage;
address public webUser;
address[] public storageNodes;
uint userValue; //this value in wei
uint storageNodeValue;
function web2decentorage(uint UV, uint SNV) public {
userValue = UV;
storageNodeValue = SNV;
decentorage = msg.sender; //decentorage ID that will manage this contract
}
function getPaidByUser() public payable {
require(msg.value > userValue); //here we should put the amount of money the user shoudl pay
webUser = msg.sender; //save the user ID
}
function addStorageNode(address A) public restricted {
storageNodes.push(A);
}
function payStorageNode(address A) public restricted {
for(uint i=0; i<storageNodes.length; i++){
if(storageNodes[i] == A){
storageNodes[i].transfer(storageNodeValue); //amount of money should be sent to a storage node
}
}
}
function getStorageNodes() public restricted returns(address[]) {
return storageNodes;
}
function getDecentorage() public restricted view returns(address) {
return decentorage;
}
function getwebUser() public restricted view returns(address) {
return webUser;
}
modifier restricted() {
require(msg.sender == decentorage);
_;
}
}
test code
beforeEach(async () => {
accounts = await web3.eth.getAccounts();
console.log(accounts);
//deploy to ganache network the contract
web2decentorage = await new web3.eth.Contract(JSON.parse(interface))
.deploy({ data:bytecode , arguments: [499,100]})
.send({from: accounts[0], gas: '1000000'});
});
describe('web2decentorage', ()=>{
it('a storage node will be part of this contract and be added as one of the storage nodes that stores the data', async() => {
await web2decentorage.methods.addStorageNode(accounts[1]).call({
from: accounts[0]
});
const returnVal = await web2decentorage.methods.getStorageNodes().call({
from: accounts[0]
});
console.log(returnVal);
//assert.equal(accounts[2],storageNodes[0]);
});
});
I add a node then check if the array has the added node I find it empty.
await web2decentorage.methods.addStorageNode(accounts[1]).call({
from: accounts[0]
});
You need to use the .send()
function (not .call()
) in order to make a transaction that will produce state changes (in your case, pushing the new item of storageNodes
to contract storage).
Call is for read-only actions, so you can safely use for interacting with getStorageNodes()
for example.