diff --git a/contracts/controller/Avatar.sol b/contracts/controller/Avatar.sol index ec5ac7a8..3624bdc5 100644 --- a/contracts/controller/Avatar.sol +++ b/contracts/controller/Avatar.sol @@ -2,32 +2,12 @@ pragma solidity ^0.5.17; import "@daostack/infra-experimental/contracts/Reputation.sol"; import "./DAOToken.sol"; -import "@openzeppelin/contracts-ethereum-package/contracts/ownership/Ownable.sol"; +import "./Vault.sol"; import "@openzeppelin/contracts-ethereum-package/contracts/token/ERC20/IERC20.sol"; import "@openzeppelin/contracts-ethereum-package/contracts/token/ERC20/SafeERC20.sol"; import "@openzeppelin/upgrades/contracts/Initializable.sol"; -//Proxy contracts cannot recive eth via fallback function. -//For now , we will use this vault to overcome that -contract Vault is Ownable { - event ReceiveEther(address indexed _sender, uint256 _value); - - /** - * @dev enables this contract to receive ethers - */ - function() external payable { - emit ReceiveEther(msg.sender, msg.value); - } - - function sendEther(uint256 _amountInWei, address payable _to) external onlyOwner returns(bool) { - // solhint-disable-next-line avoid-call-value - (bool success, ) = _to.call.value(_amountInWei)(""); - require(success, "sendEther failed."); - } -} - - /** * @title An Avatar holds tokens, reputation and ether for a controller */ @@ -41,7 +21,6 @@ contract Avatar is Initializable, Ownable { mapping(string=>string) public db; event GenericCall(address indexed _contract, bytes _data, uint _value, bool _success); - event SendEther(uint256 _amountInWei, address indexed _to); event ExternalTokenTransfer(address indexed _externalToken, address indexed _to, uint256 _value); event ExternalTokenTransferFrom(address indexed _externalToken, address _from, address _to, uint256 _value); event ExternalTokenApproval(address indexed _externalToken, address _spender, uint256 _value); @@ -104,7 +83,6 @@ contract Avatar is Initializable, Ownable { */ function sendEther(uint256 _amountInWei, address payable _to) external onlyOwner returns(bool) { vault.sendEther(_amountInWei, _to); - emit SendEther(_amountInWei, _to); return true; } diff --git a/contracts/controller/Vault.sol b/contracts/controller/Vault.sol new file mode 100644 index 00000000..e83fdc30 --- /dev/null +++ b/contracts/controller/Vault.sol @@ -0,0 +1,25 @@ +pragma solidity ^0.5.17; + +import "@openzeppelin/contracts-ethereum-package/contracts/ownership/Ownable.sol"; + + +//Proxy contracts cannot recive eth via fallback function. +//For now , we will use this vault to overcome that +contract Vault is Ownable { + event ReceiveEther(address indexed _sender, uint256 _value); + event SendEther(address indexed _to, uint256 _value); + + /** + * @dev enables this contract to receive ethers + */ + function() external payable { + emit ReceiveEther(msg.sender, msg.value); + } + + function sendEther(uint256 _amountInWei, address payable _to) external onlyOwner returns(bool) { + // solhint-disable-next-line avoid-call-value + (bool success, ) = _to.call.value(_amountInWei)(""); + require(success, "sendEther failed."); + emit SendEther(_to, _amountInWei); + } +} diff --git a/package-lock.json b/package-lock.json index 516af186..0eda4529 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,6 +1,6 @@ { "name": "@daostack/arc-experimental", - "version": "0.1.1-rc.18", + "version": "0.1.1-rc.19", "lockfileVersion": 1, "requires": true, "dependencies": { diff --git a/package.json b/package.json index c0b8e9b3..31b847cc 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "@daostack/arc-experimental", - "version": "0.1.1-rc.18", + "version": "0.1.1-rc.19", "description": "A platform for building DAOs", "files": [ "contracts/", diff --git a/test/avatar.js b/test/avatar.js index d7e36331..ab17b3a6 100644 --- a/test/avatar.js +++ b/test/avatar.js @@ -1,5 +1,6 @@ const helpers = require('./helpers'); const Avatar = artifacts.require("./Avatar.sol"); +const Vault = artifacts.require("./Vault.sol"); const ERC20Mock = artifacts.require('./test/ERC20Mock.sol'); const ActionMock = artifacts.require('./test/ActionMock.sol'); const SchemeMock = artifacts.require('./test/SchemeMock.sol'); @@ -73,8 +74,15 @@ contract('Avatar', accounts => { var avatarBalance = await web3.eth.getBalance(vault)/web3.utils.toWei('1', "ether"); assert.equal(avatarBalance,1); var tx = await avatar.sendEther(web3.utils.toWei('1', "ether"),otherAvatar.address); - assert.equal(tx.logs.length, 1); - assert.equal(tx.logs[0].event, "SendEther"); + var vaultContract = await Vault.at(vault); + await vaultContract.getPastEvents('SendEther', { + filter: {_addr: avatar.address}, // Using an array means OR: e.g. 20 or 23 + fromBlock: tx.blockNumber, + toBlock: 'latest' + }) + .then(function(events){ + assert.equal(events[0].event,"SendEther"); + }); avatarBalance =await web3.eth.getBalance(vault)/web3.utils.toWei('1', "ether"); assert.equal(avatarBalance,0); var otherVault = await otherAvatar.vault(); diff --git a/test/controller.js b/test/controller.js index 7a1a50c1..2c814d20 100644 --- a/test/controller.js +++ b/test/controller.js @@ -2,6 +2,7 @@ const helpers = require('./helpers'); const Controller = artifacts.require("./Controller.sol"); const Reputation = artifacts.require("./Reputation.sol"); const Avatar = artifacts.require("./Avatar.sol"); +const Vault = artifacts.require("./Vault.sol"); const DAOToken = artifacts.require("./DAOToken.sol"); const GlobalConstraintMock = artifacts.require('./test/GlobalConstraintMock.sol'); const ActionMock = artifacts.require('./test/ActionMock.sol'); @@ -407,7 +408,8 @@ contract('Controller', accounts => { await web3.eth.sendTransaction({from:accounts[0],to:avatar.address, value: web3.utils.toWei('1', "ether")}); //send some ether from an organization's avatar to the otherAvatar var tx = await controller.sendEther(web3.utils.toWei('1', "ether"),otherAvatar.address); - await avatar.getPastEvents('SendEther', { + var vault = await Vault.at(await avatar.vault()); + await vault.getPastEvents('SendEther', { filter: {_addr: avatar.address}, // Using an array means OR: e.g. 20 or 23 fromBlock: tx.blockNumber, toBlock: 'latest' @@ -415,8 +417,7 @@ contract('Controller', accounts => { .then(function(events){ assert.equal(events[0].event,"SendEther"); }); - var vault = await avatar.vault(); - var avatarBalance = await web3.eth.getBalance(vault)/web3.utils.toWei('1', "ether"); + var avatarBalance = await web3.eth.getBalance(vault.address)/web3.utils.toWei('1', "ether"); assert.equal(avatarBalance, 0); var otherVault = await otherAvatar.vault(); var otherAvatarBalance = await web3.eth.getBalance(otherVault)/web3.utils.toWei('1', "ether"); @@ -585,16 +586,16 @@ contract('Controller', accounts => { var globalConstraintsCount =await controller.globalConstraintsCount(); assert.equal(globalConstraintsCount[0],0); var tx = await controller.sendEther(web3.utils.toWei('1', "ether"),otherAvatar.address); - await avatar.getPastEvents('SendEther', { - filter: {_addr: avatar.address}, // Using an array means OR: e.g. 20 or 23 - fromBlock: tx.blockNumber, - toBlock: 'latest' - }) - .then(function(events){ - assert.equal(events[0].event,"SendEther"); - }); - var vault = await avatar.vault(); - var avatarBalance = await web3.eth.getBalance(vault)/web3.utils.toWei('1', "ether"); + var vault = await Vault.at(await avatar.vault()); + await vault.getPastEvents('SendEther', { + filter: {_addr: avatar.address}, // Using an array means OR: e.g. 20 or 23 + fromBlock: tx.blockNumber, + toBlock: 'latest' + }) + .then(function(events){ + assert.equal(events[0].event,"SendEther"); + }); + var avatarBalance = await web3.eth.getBalance(vault.address)/web3.utils.toWei('1', "ether"); assert.equal(avatarBalance, 0); var otherVault = await otherAvatar.vault(); var otherAvatarBalance = await web3.eth.getBalance(otherVault)/web3.utils.toWei('1', "ether");