From 87b7a780eb21c870c729561b56e44b708c4248f9 Mon Sep 17 00:00:00 2001 From: Vadim Arasev Date: Wed, 26 Dec 2018 14:34:08 +0300 Subject: [PATCH 001/187] Add `mintReward()`, `stake()`, `withdraw()` into ERC677BridgeToken --- contracts/ERC677BridgeToken.sol | 50 +++++++++++++++++++++++++++++++++ 1 file changed, 50 insertions(+) diff --git a/contracts/ERC677BridgeToken.sol b/contracts/ERC677BridgeToken.sol index 74cd52909..0e444a04e 100644 --- a/contracts/ERC677BridgeToken.sol +++ b/contracts/ERC677BridgeToken.sol @@ -14,6 +14,8 @@ contract ERC677BridgeToken is MintableToken { address public bridgeContract; + address public blockRewardContract; + address public validatorSetContract; event ContractFallbackCallFailed(address from, address to, uint value); @@ -28,11 +30,31 @@ contract ERC677BridgeToken is bridgeContract = _bridgeContract; } + function setBlockRewardContract(address _blockRewardContract) onlyOwner public { + require(_blockRewardContract != address(0) && isContract(_blockRewardContract)); + blockRewardContract = _blockRewardContract; + } + + function setValidatorSetContract(address _validatorSetContract) onlyOwner public { + require(_validatorSetContract != address(0) && isContract(_validatorSetContract)); + validatorSetContract = _validatorSetContract; + } + modifier validRecipient(address _recipient) { require(_recipient != address(0) && _recipient != address(this)); _; } + modifier onlyBlockRewardContract() { + require(msg.sender == blockRewardContract); + _; + } + + modifier onlyValidatorSetContract() { + require(msg.sender == validatorSetContract); + _; + } + function transferAndCall(address _to, uint _value, bytes _data) external validRecipient(_to) returns (bool) { @@ -104,5 +126,33 @@ contract ERC677BridgeToken is require(token.transfer(_to, balance)); } + function mintReward(address[] _receivers, uint256[] _rewards) external onlyBlockRewardContract { + for (uint256 i = 0; i < _receivers.length; i++) { + address to = _receivers[i]; + uint256 amount = _rewards[i]; + + // Mint `amount` for `to` + totalSupply_ = totalSupply_.add(amount); + balances[to] = balances[to].add(amount); + emit Mint(to, amount); + emit Transfer(address(0), to, amount); + } + } + + function stake(address _staker, uint256 _amount) external onlyValidatorSetContract { + // Transfer `_amount` from `_staker` to `validatorSetContract` + require(_amount <= balances[_staker]); + balances[_staker] = balances[_staker].sub(_amount); + balances[validatorSetContract] = balances[validatorSetContract].add(_amount); + emit Transfer(_staker, validatorSetContract, _amount); + } + + function withdraw(address _staker, uint256 _amount) external onlyValidatorSetContract { + // Transfer `_amount` from `validatorSetContract` to `_staker` + require(_amount <= balances[validatorSetContract]); + balances[validatorSetContract] = balances[validatorSetContract].sub(_amount); + balances[_staker] = balances[_staker].add(_amount); + emit Transfer(validatorSetContract, _staker, _amount); + } } From 60644ade3f378d00e12b8167ca6ee5c7e6f685c4 Mon Sep 17 00:00:00 2001 From: Vadim Arasev Date: Wed, 26 Dec 2018 18:10:37 +0300 Subject: [PATCH 002/187] Add `ERC677BridgeTokenRewardable` contract --- contracts/ERC677BridgeToken.sol | 52 +----------------- contracts/ERC677BridgeTokenRewardable.sol | 66 +++++++++++++++++++++++ 2 files changed, 67 insertions(+), 51 deletions(-) create mode 100644 contracts/ERC677BridgeTokenRewardable.sol diff --git a/contracts/ERC677BridgeToken.sol b/contracts/ERC677BridgeToken.sol index 0e444a04e..e335f2622 100644 --- a/contracts/ERC677BridgeToken.sol +++ b/contracts/ERC677BridgeToken.sol @@ -14,8 +14,6 @@ contract ERC677BridgeToken is MintableToken { address public bridgeContract; - address public blockRewardContract; - address public validatorSetContract; event ContractFallbackCallFailed(address from, address to, uint value); @@ -30,31 +28,11 @@ contract ERC677BridgeToken is bridgeContract = _bridgeContract; } - function setBlockRewardContract(address _blockRewardContract) onlyOwner public { - require(_blockRewardContract != address(0) && isContract(_blockRewardContract)); - blockRewardContract = _blockRewardContract; - } - - function setValidatorSetContract(address _validatorSetContract) onlyOwner public { - require(_validatorSetContract != address(0) && isContract(_validatorSetContract)); - validatorSetContract = _validatorSetContract; - } - modifier validRecipient(address _recipient) { require(_recipient != address(0) && _recipient != address(this)); _; } - modifier onlyBlockRewardContract() { - require(msg.sender == blockRewardContract); - _; - } - - modifier onlyValidatorSetContract() { - require(msg.sender == validatorSetContract); - _; - } - function transferAndCall(address _to, uint _value, bytes _data) external validRecipient(_to) returns (bool) { @@ -97,7 +75,7 @@ contract ERC677BridgeToken is } function isContract(address _addr) - private + internal view returns (bool) { @@ -126,33 +104,5 @@ contract ERC677BridgeToken is require(token.transfer(_to, balance)); } - function mintReward(address[] _receivers, uint256[] _rewards) external onlyBlockRewardContract { - for (uint256 i = 0; i < _receivers.length; i++) { - address to = _receivers[i]; - uint256 amount = _rewards[i]; - - // Mint `amount` for `to` - totalSupply_ = totalSupply_.add(amount); - balances[to] = balances[to].add(amount); - emit Mint(to, amount); - emit Transfer(address(0), to, amount); - } - } - - function stake(address _staker, uint256 _amount) external onlyValidatorSetContract { - // Transfer `_amount` from `_staker` to `validatorSetContract` - require(_amount <= balances[_staker]); - balances[_staker] = balances[_staker].sub(_amount); - balances[validatorSetContract] = balances[validatorSetContract].add(_amount); - emit Transfer(_staker, validatorSetContract, _amount); - } - - function withdraw(address _staker, uint256 _amount) external onlyValidatorSetContract { - // Transfer `_amount` from `validatorSetContract` to `_staker` - require(_amount <= balances[validatorSetContract]); - balances[validatorSetContract] = balances[validatorSetContract].sub(_amount); - balances[_staker] = balances[_staker].add(_amount); - emit Transfer(validatorSetContract, _staker, _amount); - } } diff --git a/contracts/ERC677BridgeTokenRewardable.sol b/contracts/ERC677BridgeTokenRewardable.sol new file mode 100644 index 000000000..41b95947d --- /dev/null +++ b/contracts/ERC677BridgeTokenRewardable.sol @@ -0,0 +1,66 @@ +pragma solidity 0.4.24; + +import "./ERC677BridgeToken.sol"; + + +contract ERC677BridgeTokenRewardable is ERC677BridgeToken { + + address public blockRewardContract; + address public validatorSetContract; + + constructor( + string _name, + string _symbol, + uint8 _decimals + ) public ERC677BridgeToken(_name, _symbol, _decimals) {} + + function setBlockRewardContract(address _blockRewardContract) onlyOwner public { + require(_blockRewardContract != address(0) && isContract(_blockRewardContract)); + blockRewardContract = _blockRewardContract; + } + + function setValidatorSetContract(address _validatorSetContract) onlyOwner public { + require(_validatorSetContract != address(0) && isContract(_validatorSetContract)); + validatorSetContract = _validatorSetContract; + } + + modifier onlyBlockRewardContract() { + require(msg.sender == blockRewardContract); + _; + } + + modifier onlyValidatorSetContract() { + require(msg.sender == validatorSetContract); + _; + } + + function mintReward(address[] _receivers, uint256[] _rewards) external onlyBlockRewardContract { + for (uint256 i = 0; i < _receivers.length; i++) { + address to = _receivers[i]; + uint256 amount = _rewards[i]; + + // Mint `amount` for `to` + totalSupply_ = totalSupply_.add(amount); + balances[to] = balances[to].add(amount); + emit Mint(to, amount); + emit Transfer(address(0), to, amount); + } + } + + function stake(address _staker, uint256 _amount) external onlyValidatorSetContract { + // Transfer `_amount` from `_staker` to `validatorSetContract` + require(_amount <= balances[_staker]); + balances[_staker] = balances[_staker].sub(_amount); + balances[validatorSetContract] = balances[validatorSetContract].add(_amount); + emit Transfer(_staker, validatorSetContract, _amount); + } + + function withdraw(address _staker, uint256 _amount) external onlyValidatorSetContract { + // Transfer `_amount` from `validatorSetContract` to `_staker` + require(_amount <= balances[validatorSetContract]); + balances[validatorSetContract] = balances[validatorSetContract].sub(_amount); + balances[_staker] = balances[_staker].add(_amount); + emit Transfer(validatorSetContract, _staker, _amount); + } + +} From 94947ebc3d34d1db4185ab9fa05d2edc3ecbb7ad Mon Sep 17 00:00:00 2001 From: fernandomg Date: Wed, 26 Dec 2018 08:59:14 -0300 Subject: [PATCH 003/187] Update BridgeValidator to support linked-list - Store validators as a linked-list - Store reward address as a map [validator] -> rewardAddr --- .../BridgeValidators.sol | 103 ++++++++++++++---- 1 file changed, 82 insertions(+), 21 deletions(-) diff --git a/contracts/upgradeable_contracts/BridgeValidators.sol b/contracts/upgradeable_contracts/BridgeValidators.sol index d3ee1edba..d741cf4f1 100644 --- a/contracts/upgradeable_contracts/BridgeValidators.sol +++ b/contracts/upgradeable_contracts/BridgeValidators.sol @@ -9,89 +9,150 @@ import "../upgradeability/EternalStorage.sol"; contract BridgeValidators is IBridgeValidators, EternalStorage, Ownable { using SafeMath for uint256; + address constant F_ADDR = 0xFFfFfFffFFfffFFfFFfFFFFFffFFFffffFfFFFfF; + event ValidatorAdded (address indexed validator); event ValidatorRemoved (address indexed validator); event RequiredSignaturesChanged (uint256 requiredSignatures); - function initialize(uint256 _requiredSignatures, address[] _initialValidators, address _owner) - public returns(bool) + function initialize( + uint256 _requiredSignatures, + address[] _initialValidators, + address[] _initialRewards, + address _owner + ) + public + returns (bool) { require(!isInitialized()); require(_owner != address(0)); setOwner(_owner); require(_requiredSignatures != 0); require(_initialValidators.length >= _requiredSignatures); + require(_initialValidators.length == _initialRewards.length); + for (uint256 i = 0; i < _initialValidators.length; i++) { - require(_initialValidators[i] != address(0)); - assert(validators(_initialValidators[i]) != true); + require(_initialValidators[i] != address(0) || _initialValidators[i] != F_ADDR); + require(!isValidator(_initialValidators[i])); + + if (i == 0) { + setValidator(F_ADDR, _initialValidators[i]); + if (_initialValidators.length == 1) { + setValidator(_initialValidators[i], F_ADDR); + } + } else if (i == _initialValidators.length - 1) { + setValidator(_initialValidators[i - 1], _initialValidators[i]); + setValidator(_initialValidators[i], F_ADDR); + } else { + setValidator(_initialValidators[i - 1], _initialValidators[i]); + } + setValidatorCount(validatorCount().add(1)); - setValidator(_initialValidators[i], true); + setValidatorRewardAddress(_initialValidators[i], _initialRewards[i]); emit ValidatorAdded(_initialValidators[i]); } + uintStorage[keccak256(abi.encodePacked("requiredSignatures"))] = _requiredSignatures; uintStorage[keccak256("deployedAtBlock")] = block.number; setInitialize(true); emit RequiredSignaturesChanged(_requiredSignatures); + return isInitialized(); } function addValidator(address _validator) external onlyOwner { require(_validator != address(0)); require(!isValidator(_validator)); + + address firstValidator = getNextValidator(F_ADDR); + setValidator(_validator, firstValidator); + setValidator(F_ADDR, _validator); + setValidatorCount(validatorCount().add(1)); - setValidator(_validator, true); emit ValidatorAdded(_validator); } function removeValidator(address _validator) external onlyOwner { require(validatorCount() > requiredSignatures()); require(isValidator(_validator)); - setValidator(_validator, false); + address validatorsNext = getNextValidator(_validator); + address index = F_ADDR; + address next = getNextValidator(index); + + // find the element in the list pointing to _validator + while (next != _validator) { + index = next; + next = getNextValidator(index); + } + + setValidator(index, validatorsNext); + deleteItemFromAddressStorage("validatorsList", _validator); + deleteItemFromAddressStorage("validatorsRewards", _validator); setValidatorCount(validatorCount().sub(1)); + emit ValidatorRemoved(_validator); } - function setRequiredSignatures(uint256 _requiredSignatures) external onlyOwner { + function setRequiredSignatures(uint256 _requiredSignatures) + external + onlyOwner + { require(validatorCount() >= _requiredSignatures); require(_requiredSignatures != 0); uintStorage[keccak256(abi.encodePacked("requiredSignatures"))] = _requiredSignatures; emit RequiredSignaturesChanged(_requiredSignatures); } - function getBridgeValidatorsInterfacesVersion() public pure returns(uint64 major, uint64 minor, uint64 patch) { + function getBridgeValidatorsInterfacesVersion() + public + pure + returns (uint64 major, uint64 minor, uint64 patch) + { return (2, 0, 0); } - function requiredSignatures() public view returns(uint256) { + function requiredSignatures() public view returns (uint256) { return uintStorage[keccak256(abi.encodePacked("requiredSignatures"))]; } - function validatorCount() public view returns(uint256) { + function validatorCount() public view returns (uint256) { return uintStorage[keccak256(abi.encodePacked("validatorCount"))]; } - function validators(address _validator) public view returns(bool) { - return boolStorage[keccak256(abi.encodePacked("validators", _validator))]; - } - - function isValidator(address _validator) public view returns(bool) { - return validators(_validator) == true; + function isValidator(address _validator) public view returns (bool) { + return _validator != F_ADDR && getNextValidator(_validator) != address(0); } - function isInitialized() public view returns(bool) { + function isInitialized() public view returns (bool) { return boolStorage[keccak256(abi.encodePacked("isInitialized"))]; } - function deployedAtBlock() public view returns(uint256) { + function deployedAtBlock() public view returns (uint256) { return uintStorage[keccak256("deployedAtBlock")]; } + function getValidatorRewardAddress(address _validator) public view returns (address) { + return addressStorage[keccak256(abi.encodePacked("validatorsRewards", _validator))]; + } + + function getNextValidator(address _address) internal view returns (address) { + return addressStorage[keccak256(abi.encodePacked("validatorsList", _address))]; + } + + function setValidatorRewardAddress(address _validator, address _reward) internal { + addressStorage[keccak256(abi.encodePacked("validatorsRewards", _validator))] = _reward; + } + + function deleteItemFromAddressStorage(string _mapName, address _address) private { + delete addressStorage[keccak256(abi.encodePacked(_mapName, _address))]; + } + function setValidatorCount(uint256 _validatorCount) private { uintStorage[keccak256(abi.encodePacked("validatorCount"))] = _validatorCount; } - function setValidator(address _validator, bool _status) private { - boolStorage[keccak256(abi.encodePacked("validators", _validator))] = _status; + function setValidator(address _prevValidator, address _validator) private { + addressStorage[keccak256(abi.encodePacked("validatorsList", _prevValidator))] = _validator; } function setInitialize(bool _status) private { From 9f8b18c9886db2e8d2f84ed1c4361d446832830d Mon Sep 17 00:00:00 2001 From: fernandomg Date: Wed, 26 Dec 2018 08:59:34 -0300 Subject: [PATCH 004/187] Add/Update tests for BridgeValidator --- test/validators_test.js | 91 +++++++++++++++++++++++++++++++++++------ 1 file changed, 79 insertions(+), 12 deletions(-) diff --git a/test/validators_test.js b/test/validators_test.js index d5070f1de..496fa116e 100644 --- a/test/validators_test.js +++ b/test/validators_test.js @@ -1,17 +1,17 @@ const BridgeValidators = artifacts.require("BridgeValidators.sol"); const EternalStorageProxy = artifacts.require("EternalStorageProxy.sol"); -const {ERROR_MSG, ERROR_MSG_OPCODE, ZERO_ADDRESS} = require('./setup'); +const {ERROR_MSG, ZERO_ADDRESS} = require('./setup'); contract('BridgeValidators', async (accounts) => { - let token + let bridgeValidators let owner = accounts[0] - const user = accounts[1]; + beforeEach(async () => { bridgeValidators = await BridgeValidators.new(); }) + describe('#initialize', async () => { it('sets values', async () => { - // function initialize(uint256 _requiredSignatures, address[] _initialValidators, address _owner) public { '0x0000000000000000000000000000000000000000'.should.be.equal(await bridgeValidators.owner()) '0'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) false.should.be.equal(await bridgeValidators.isValidator(accounts[0])) @@ -19,9 +19,9 @@ contract('BridgeValidators', async (accounts) => { false.should.be.equal(await bridgeValidators.isInitialized()) '0'.should.be.bignumber.equal(await bridgeValidators.requiredSignatures()) '0'.should.be.bignumber.equal(await bridgeValidators.deployedAtBlock()) - await bridgeValidators.initialize(3, [accounts[0], accounts[1]], accounts[2], {from: accounts[2]}).should.be.rejectedWith(ERROR_MSG) - await bridgeValidators.initialize(2, [accounts[0], accounts[1]], accounts[2], {from: accounts[2]}).should.be.fulfilled; - await bridgeValidators.initialize(2, [accounts[0], accounts[1]], accounts[2], {from: accounts[2]}).should.be.rejectedWith(ERROR_MSG); + await bridgeValidators.initialize(3, accounts.slice(0, 3), accounts.slice(3, 5), accounts[2], {from: accounts[2]}).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.initialize(2, accounts.slice(0, 2), accounts.slice(2, 4), accounts[2], {from: accounts[2]}).should.be.fulfilled; + await bridgeValidators.initialize(2, accounts.slice(0, 2), accounts.slice(2, 4), accounts[2], {from: accounts[2]}).should.be.rejectedWith(ERROR_MSG); true.should.be.equal(await bridgeValidators.isInitialized()) '2'.should.be.bignumber.equal(await bridgeValidators.requiredSignatures()) true.should.be.equal(await bridgeValidators.isValidator(accounts[0])) @@ -39,13 +39,14 @@ contract('BridgeValidators', async (accounts) => { describe('#addValidator', async () => { let owner = accounts[2]; let validators = [accounts[0], accounts[1]]; + let rewards = accounts.slice(2, 4) let requiredSignatures = 2; beforeEach(async () => { - await bridgeValidators.initialize(requiredSignatures, validators, owner, {from: owner}).should.be.fulfilled + await bridgeValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled '2'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) }) it('adds validator', async () => { - let newValidator = accounts[3]; + let newValidator = accounts[4]; false.should.be.equal(await bridgeValidators.isValidator(newValidator)) await bridgeValidators.addValidator(newValidator, {from: validators[0]}).should.be.rejectedWith(ERROR_MSG) @@ -67,9 +68,10 @@ contract('BridgeValidators', async (accounts) => { describe('#removeValidator', async () => { let owner = accounts[2]; let validators = [accounts[0], accounts[1], accounts[3]]; + let rewards = accounts.slice(4, 7); let requiredSignatures = 2; beforeEach(async () => { - await bridgeValidators.initialize(requiredSignatures, validators, owner, {from: owner}).should.be.fulfilled + await bridgeValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled '3'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) }) @@ -107,9 +109,10 @@ contract('BridgeValidators', async (accounts) => { describe('#setRequiredSignatures', async () => { let owner = accounts[2]; let validators = [accounts[0], accounts[1], accounts[3]]; + let rewards = accounts.slice(4, 7) let requiredSignatures = 2; beforeEach(async () => { - await bridgeValidators.initialize(requiredSignatures, validators, owner, {from: owner}).should.be.fulfilled + await bridgeValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled '3'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) }) @@ -127,13 +130,15 @@ contract('BridgeValidators', async (accounts) => { requiredSignatures.should.be.bignumber.equal(await bridgeValidators.requiredSignatures()); }) }) + describe('#upgradable', async () => { it('can be upgraded via upgradeToAndCall', async () => { let storageProxy = await EternalStorageProxy.new().should.be.fulfilled; let required_signatures = 2; let validators = [accounts[0], accounts[1]]; + let rewards = accounts.slice(3, 5); let owner = accounts[2] - let data = bridgeValidators.initialize.request(required_signatures, validators, owner).params[0].data + let data = bridgeValidators.initialize.request(required_signatures, validators, rewards, owner).params[0].data await storageProxy.upgradeToAndCall('1', bridgeValidators.address, data).should.be.fulfilled; let finalContract = await BridgeValidators.at(storageProxy.address); true.should.be.equal(await finalContract.isInitialized()); @@ -145,4 +150,66 @@ contract('BridgeValidators', async (accounts) => { validators.length.should.be.bignumber.equal(await finalContract.validatorCount()) }) }) + + describe('#single list remove', () => { + it(`should remove ${accounts[0]} - without Proxy`, async () => { + // Given + const { initialize, isInitialized, removeValidator } = bridgeValidators + await initialize(1, accounts.slice(0, 2), accounts.slice(2, 4), owner, { from: owner }).should.be.fulfilled + true.should.be.equal(await isInitialized()) + + // When + const { logs } = await removeValidator(accounts[0], { from: owner }).should.be.fulfilled + + // Then + logs[0].event.should.be.equal('ValidatorRemoved') + logs[0].args.should.be.deep.equal({ validator: accounts[0] }) + }) + + accounts.slice(0, 5).forEach(validator => { + it(`should remove ${validator} - with Proxy`, async () => { + // Given + const proxy = await EternalStorageProxy.new() + const bridgeValidatorsImpl = await BridgeValidators.new() + await proxy.upgradeTo('1', bridgeValidatorsImpl.address) + bridgeValidators = BridgeValidators.at(proxy.address) + const { initialize, isInitialized, removeValidator } = bridgeValidators + await initialize( + 1, + accounts.slice(0, 5), + accounts.slice(5), + owner, + { from: owner } + ).should.be.fulfilled + true.should.be.equal(await isInitialized()) + + // When + const { logs } = await removeValidator( + validator, + { from: owner } + ).should.be.fulfilled + + // Then + logs[0].event.should.be.equal('ValidatorRemoved') + logs[0].args.should.be.deep.equal({ validator }) + }) + }) + }) + + describe('#reward address', () => { + it(`reward address is properly assigned`, async () => { + // Given + const { initialize, isInitialized, getValidatorRewardAddress } = bridgeValidators + await initialize(1, accounts.slice(0, 5), accounts.slice(5), owner, { from: owner }).should.be.fulfilled + + // When + true.should.be.equal(await isInitialized()) + + // Then + for (let i = 0; i < accounts.slice(0, 5).length; i++) { + const validator = accounts[i] + accounts[i + 5].should.be.equal(await getValidatorRewardAddress(validator)) + } + }) + }) }) From eb9e9bf276e884a9e4b593fec375ee5e16465d54 Mon Sep 17 00:00:00 2001 From: fernandomg Date: Wed, 26 Dec 2018 17:25:06 -0300 Subject: [PATCH 005/187] Fix tests that initialize `BridgeValidator` --- test/erc_to_erc/foreign_bridge.test.js | 17 ++-- test/erc_to_erc/home_bridge.test.js | 92 +++++++++++----------- test/erc_to_native/foreign_bridge.test.js | 16 ++-- test/erc_to_native/home_bridge.test.js | 77 ++++++++++--------- test/native_to_erc/foreign_bridge_test.js | 18 +++-- test/native_to_erc/home_bridge_test.js | 94 ++++++++++++----------- test/poa20_test.js | 6 +- 7 files changed, 177 insertions(+), 143 deletions(-) diff --git a/test/erc_to_erc/foreign_bridge.test.js b/test/erc_to_erc/foreign_bridge.test.js index c121f5ead..f47ff509b 100644 --- a/test/erc_to_erc/foreign_bridge.test.js +++ b/test/erc_to_erc/foreign_bridge.test.js @@ -11,12 +11,13 @@ const requireBlockConfirmations = 8; const gasPrice = web3.toWei('1', 'gwei') contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { - let validatorContract, authorities, owner, token; + let validatorContract, authorities, rewards, owner, token; before(async () => { validatorContract = await BridgeValidators.new() authorities = [accounts[1], accounts[2]]; + rewards = [accounts[3], accounts[4]]; owner = accounts[0] - await validatorContract.initialize(1, authorities, owner) + await validatorContract.initialize(1, authorities, rewards, owner) }) describe('#initialize', async () => { @@ -58,6 +59,7 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { patch.should.be.bignumber.gte(0) }) }) + describe('#executeSignatures', async () => { var value = web3.toBigNumber(web3.toWei(0.25, "ether")); beforeEach(async () => { @@ -136,15 +138,16 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { }) describe('#withdraw with 2 minimum signatures', async () => { - let multisigValidatorContract, twoAuthorities, ownerOfValidatorContract, foreignBridgeWithMultiSignatures + let multisigValidatorContract, twoAuthorities, twoRewards, ownerOfValidatorContract, foreignBridgeWithMultiSignatures var value = web3.toBigNumber(web3.toWei(0.5, "ether")); beforeEach(async () => { multisigValidatorContract = await BridgeValidators.new() token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); twoAuthorities = [accounts[0], accounts[1]]; + twoRewards = [accounts[2], accounts[3]]; ownerOfValidatorContract = accounts[3] const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")); - await multisigValidatorContract.initialize(2, twoAuthorities, ownerOfValidatorContract, {from: ownerOfValidatorContract}) + await multisigValidatorContract.initialize(2, twoAuthorities, twoRewards, ownerOfValidatorContract, {from: ownerOfValidatorContract}) foreignBridgeWithMultiSignatures = await ForeignBridge.new() const oneEther = web3.toBigNumber(web3.toWei(1, "ether")); await foreignBridgeWithMultiSignatures.initialize(multisigValidatorContract.address, token.address, requireBlockConfirmations, gasPrice, {from: ownerOfValidatorContract}); @@ -184,9 +187,10 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { it('works with 5 validators and 3 required signatures', async () => { const recipient = accounts[8] const authoritiesFiveAccs = [accounts[1], accounts[2], accounts[3], accounts[4], accounts[5]] + const rewardsFiveAccs = [accounts[6], accounts[7], accounts[8], accounts[9], accounts[0]] const ownerOfValidators = accounts[0] const validatorContractWith3Signatures = await BridgeValidators.new() - await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) + await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, rewardsFiveAccs, ownerOfValidators) const erc20Token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); const value = web3.toBigNumber(web3.toWei(0.5, "ether")); const foreignBridgeWithThreeSigs = await ForeignBridge.new() @@ -222,6 +226,7 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { it('can be upgraded', async () => { const REQUIRED_NUMBER_OF_VALIDATORS = 1 const VALIDATORS = [accounts[1]] + const REWARDS = [accounts[2]] const PROXY_OWNER = accounts[0] // Validators Contract let validatorsProxy = await EternalStorageProxy.new().should.be.fulfilled; @@ -230,7 +235,7 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { validatorsContractImpl.address.should.be.equal(await validatorsProxy.implementation()) validatorsProxy = await BridgeValidators.at(validatorsProxy.address); - await validatorsProxy.initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, PROXY_OWNER).should.be.fulfilled; + await validatorsProxy.initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, REWARDS, PROXY_OWNER).should.be.fulfilled; let token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); // ForeignBridge V1 Contract diff --git a/test/erc_to_erc/home_bridge.test.js b/test/erc_to_erc/home_bridge.test.js index 512fab1ca..92e8d673b 100644 --- a/test/erc_to_erc/home_bridge.test.js +++ b/test/erc_to_erc/home_bridge.test.js @@ -13,12 +13,13 @@ const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")); contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { - let homeContract, validatorContract, authorities, owner, token; + let homeContract, validatorContract, authorities, rewards, owner, token; before(async () => { validatorContract = await BridgeValidators.new() authorities = [accounts[1]]; + rewards = [accounts[2]]; owner = accounts[0] - await validatorContract.initialize(1, authorities, owner) + await validatorContract.initialize(1, authorities, rewards, owner) }) describe('#initialize', async() => { beforeEach(async () => { @@ -155,9 +156,10 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { it('test with 2 signatures required', async () => { let token2sig = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); let validatorContractWith2Signatures = await BridgeValidators.new() - let authoritiesTwoAccs = [accounts[1], accounts[2], accounts[3]]; + let authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]]; + let rewardsThreeAccs = [accounts[4], accounts[5], accounts[6]]; let ownerOfValidators = accounts[0] - await validatorContractWith2Signatures.initialize(2, authoritiesTwoAccs, ownerOfValidators) + await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, rewardsThreeAccs, ownerOfValidators) let homeBridgeWithTwoSigs = await HomeBridge.new(); await homeBridgeWithTwoSigs.initialize(validatorContractWith2Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token2sig.address); await token2sig.transferOwnership(homeBridgeWithTwoSigs.address); @@ -167,7 +169,7 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const balanceBefore = await token2sig.balanceOf(recipient) const msgHash = Web3Utils.soliditySha3(recipient, value, transactionHash); - const {logs} = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesTwoAccs[0]}).should.be.fulfilled; + const {logs} = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; logs[0].event.should.be.equal("SignedForAffirmation"); logs[0].args.should.be.deep.equal({ signer: authorities[0], @@ -177,8 +179,8 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const notProcessed = await homeBridgeWithTwoSigs.numAffirmationsSigned(msgHash); notProcessed.should.be.bignumber.equal(1); - await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesTwoAccs[0]}).should.be.rejectedWith(ERROR_MSG); - const secondSignature = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesTwoAccs[1]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[0]}).should.be.rejectedWith(ERROR_MSG); + const secondSignature = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; const balanceAfter = await token2sig.balanceOf(recipient) balanceAfter.should.be.bignumber.equal(balanceBefore.add(value)) @@ -190,10 +192,10 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { transactionHash }) - const senderHash = Web3Utils.soliditySha3(authoritiesTwoAccs[0], msgHash) + const senderHash = Web3Utils.soliditySha3(authoritiesThreeAccs[0], msgHash) true.should.be.equal(await homeBridgeWithTwoSigs.affirmationsSigned(senderHash)) - const senderHash2 = Web3Utils.soliditySha3(authoritiesTwoAccs[1], msgHash); + const senderHash2 = Web3Utils.soliditySha3(authoritiesThreeAccs[1], msgHash); true.should.be.equal(await homeBridgeWithTwoSigs.affirmationsSigned(senderHash2)) const markedAsProcessed = await homeBridgeWithTwoSigs.numAffirmationsSigned(msgHash); @@ -218,9 +220,10 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { it('doesnt allow to deposit if requiredSignatures has changed', async () => { let token2sig = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); let validatorContractWith2Signatures = await BridgeValidators.new() - let authoritiesTwoAccs = [accounts[1], accounts[2], accounts[3]]; + let authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]]; + let rewardsThreeAccs = [accounts[4], accounts[5], accounts[6]]; let ownerOfValidators = accounts[0] - await validatorContractWith2Signatures.initialize(2, authoritiesTwoAccs, ownerOfValidators) + await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, rewardsThreeAccs, ownerOfValidators) let homeBridgeWithTwoSigs = await HomeBridge.new(); await homeBridgeWithTwoSigs.initialize(validatorContractWith2Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token2sig.address); await token2sig.transferOwnership(homeBridgeWithTwoSigs.address); @@ -230,22 +233,23 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const balanceBefore = await token.balanceOf(recipient) const msgHash = Web3Utils.soliditySha3(recipient, value, transactionHash); - await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesTwoAccs[0]}).should.be.fulfilled; - await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesTwoAccs[1]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; balanceBefore.add(value).should.be.bignumber.equal(await token2sig.balanceOf(recipient)) await validatorContractWith2Signatures.setRequiredSignatures(3).should.be.fulfilled; - await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesTwoAccs[2]}).should.be.rejectedWith(ERROR_MSG); + await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[2]}).should.be.rejectedWith(ERROR_MSG); await validatorContractWith2Signatures.setRequiredSignatures(1).should.be.fulfilled; - await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesTwoAccs[2]}).should.be.rejectedWith(ERROR_MSG); + await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[2]}).should.be.rejectedWith(ERROR_MSG); balanceBefore.add(value).should.be.bignumber.equal(await token2sig.balanceOf(recipient)) }) it('works with 5 validators and 3 required signatures', async () => { const recipient = accounts[8] const authoritiesFiveAccs = [accounts[1], accounts[2], accounts[3], accounts[4], accounts[5]] + const rewardsFiveAccs = [accounts[6], accounts[7], accounts[8], accounts[9], accounts[0]] let ownerOfValidators = accounts[0] const validatorContractWith3Signatures = await BridgeValidators.new() - await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) + await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, rewardsFiveAccs, ownerOfValidators) const token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); const homeBridgeWithThreeSigs = await HomeBridge.new(); @@ -285,13 +289,14 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { }) describe('#submitSignature', async () => { - let validatorContractWith2Signatures,authoritiesTwoAccs,ownerOfValidators,tokenPOA20,homeBridgeWithTwoSigs + let validatorContractWith2Signatures,authoritiesThreeAccs,rewardsThreeAccs,ownerOfValidators,tokenPOA20,homeBridgeWithTwoSigs beforeEach(async () => { let token2sig = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); validatorContractWith2Signatures = await BridgeValidators.new() - authoritiesTwoAccs = [accounts[1], accounts[2], accounts[3]]; + authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]]; + rewardsThreeAccs = [accounts[4], accounts[5], accounts[6]]; ownerOfValidators = accounts[0] - await validatorContractWith2Signatures.initialize(2, authoritiesTwoAccs, ownerOfValidators) + await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, rewardsThreeAccs, ownerOfValidators) homeBridgeWithTwoSigs = await HomeBridge.new(); await homeBridgeWithTwoSigs.initialize(validatorContractWith2Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token2sig.address); await token2sig.transferOwnership(homeBridgeWithTwoSigs.address); @@ -301,7 +306,7 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { var value = web3.toBigNumber(web3.toWei(0.5, "ether")); var transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; var message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); - var signature = await sign(authoritiesTwoAccs[0], message) + var signature = await sign(authoritiesThreeAccs[0], message) const {logs} = await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authorities[0]}).should.be.fulfilled; logs[0].event.should.be.equal('SignedForUserRequest') const msgHashFromLog = logs[0].args.messageHash @@ -322,24 +327,25 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { var transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; var message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); const hashMsg = Web3Utils.soliditySha3(message); - var signature = await sign(authoritiesTwoAccs[0], message) - var signature2 = await sign(authoritiesTwoAccs[1], message) + var signature = await sign(authoritiesThreeAccs[0], message) + var signature2 = await sign(authoritiesThreeAccs[1], message) '2'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesTwoAccs[0]}).should.be.fulfilled; - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesTwoAccs[0]}).should.be.rejectedWith(ERROR_MSG); - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesTwoAccs[1]}).should.be.rejectedWith(ERROR_MSG); - const {logs} = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesTwoAccs[1]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.rejectedWith(ERROR_MSG); + await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[1]}).should.be.rejectedWith(ERROR_MSG); + const {logs} = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; logs.length.should.be.equal(2) logs[1].event.should.be.equal('CollectedSignatures') - logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesTwoAccs[1]) + logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesThreeAccs[1]) const markedAsProcessed = new web3.BigNumber(2).pow(255).add(2); markedAsProcessed.should.be.bignumber.equal(await homeBridgeWithTwoSigs.numMessagesSigned(hashMsg)) }) it('works with 5 validators and 3 required signatures', async () => { const recipientAccount = accounts[8] const authoritiesFiveAccs = [accounts[1], accounts[2], accounts[3], accounts[4], accounts[5]] + const rewardsFiveAccs = [accounts[6], accounts[7], accounts[8], accounts[9], accounts[0]] const validatorContractWith3Signatures = await BridgeValidators.new() - await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) + await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, rewardsFiveAccs, ownerOfValidators) const token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); const homeBridgeWithThreeSigs = await HomeBridge.new(); @@ -366,20 +372,20 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { var homeGasPrice = web3.toBigNumber(0); var transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; var message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); - var signature = await sign(authoritiesTwoAccs[0], message) - var signature2 = await sign(authoritiesTwoAccs[1], message) - var signature3 = await sign(authoritiesTwoAccs[2], message) + var signature = await sign(authoritiesThreeAccs[0], message) + var signature2 = await sign(authoritiesThreeAccs[1], message) + var signature3 = await sign(authoritiesThreeAccs[2], message) '2'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesTwoAccs[0]}).should.be.fulfilled; - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesTwoAccs[0]}).should.be.rejectedWith(ERROR_MSG); - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesTwoAccs[1]}).should.be.rejectedWith(ERROR_MSG); - const {logs} = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesTwoAccs[1]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.rejectedWith(ERROR_MSG); + await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[1]}).should.be.rejectedWith(ERROR_MSG); + const {logs} = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; logs.length.should.be.equal(2) logs[1].event.should.be.equal('CollectedSignatures') - logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesTwoAccs[1]) + logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesThreeAccs[1]) await validatorContractWith2Signatures.setRequiredSignatures(3).should.be.fulfilled; '3'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); - const attackerTx = await homeBridgeWithTwoSigs.submitSignature(signature3, message, {from: authoritiesTwoAccs[2]}).should.be.rejectedWith(ERROR_MSG); + const attackerTx = await homeBridgeWithTwoSigs.submitSignature(signature3, message, {from: authoritiesThreeAccs[2]}).should.be.rejectedWith(ERROR_MSG); }) it('attack when decreasing requiredSignatures', async () => { var recipientAccount = accounts[8] @@ -387,17 +393,17 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { var homeGasPrice = web3.toBigNumber(0); var transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; var message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); - var signature = await sign(authoritiesTwoAccs[0], message) - var signature2 = await sign(authoritiesTwoAccs[1], message) - var signature3 = await sign(authoritiesTwoAccs[2], message) + var signature = await sign(authoritiesThreeAccs[0], message) + var signature2 = await sign(authoritiesThreeAccs[1], message) + var signature3 = await sign(authoritiesThreeAccs[2], message) '2'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesTwoAccs[0]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; await validatorContractWith2Signatures.setRequiredSignatures(1).should.be.fulfilled; '1'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); - const {logs} = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesTwoAccs[1]}).should.be.fulfilled; + const {logs} = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; logs.length.should.be.equal(2) logs[1].event.should.be.equal('CollectedSignatures') - logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesTwoAccs[1]) + logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesThreeAccs[1]) }) }) diff --git a/test/erc_to_native/foreign_bridge.test.js b/test/erc_to_native/foreign_bridge.test.js index fa49de156..c1be28577 100644 --- a/test/erc_to_native/foreign_bridge.test.js +++ b/test/erc_to_native/foreign_bridge.test.js @@ -11,12 +11,13 @@ const requireBlockConfirmations = 8; const gasPrice = web3.toWei('1', 'gwei'); contract('ForeignBridge_ERC20_to_Native', async (accounts) => { - let validatorContract, authorities, owner, token; + let validatorContract, authorities, rewards, owner, token; before(async () => { validatorContract = await BridgeValidators.new() authorities = [accounts[1], accounts[2]]; + rewards = [accounts[3], accounts[4]]; owner = accounts[0] - await validatorContract.initialize(1, authorities, owner) + await validatorContract.initialize(1, authorities, rewards, owner) }) describe('#initialize', async () => { @@ -146,14 +147,15 @@ contract('ForeignBridge_ERC20_to_Native', async (accounts) => { }) describe('#withdraw with 2 minimum signatures', async () => { - let multisigValidatorContract, twoAuthorities, ownerOfValidatorContract, foreignBridgeWithMultiSignatures + let multisigValidatorContract, twoAuthorities, twoRewards, ownerOfValidatorContract, foreignBridgeWithMultiSignatures const value = web3.toBigNumber(web3.toWei(0.5, "ether")); beforeEach(async () => { multisigValidatorContract = await BridgeValidators.new() token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); twoAuthorities = [accounts[0], accounts[1]]; + twoRewards = [accounts[8], accounts[9]]; ownerOfValidatorContract = accounts[3] - await multisigValidatorContract.initialize(2, twoAuthorities, ownerOfValidatorContract, {from: ownerOfValidatorContract}) + await multisigValidatorContract.initialize(2, twoAuthorities, twoRewards, ownerOfValidatorContract, {from: ownerOfValidatorContract}) foreignBridgeWithMultiSignatures = await ForeignBridge.new() await foreignBridgeWithMultiSignatures.initialize(multisigValidatorContract.address, token.address, requireBlockConfirmations, gasPrice, {from: ownerOfValidatorContract}); await token.mint(foreignBridgeWithMultiSignatures.address,value); @@ -196,9 +198,10 @@ contract('ForeignBridge_ERC20_to_Native', async (accounts) => { it('works with 5 validators and 3 required signatures', async () => { const recipient = accounts[8] const authoritiesFiveAccs = [accounts[1], accounts[2], accounts[3], accounts[4], accounts[5]] + const rewardsFiveAccs = [accounts[6], accounts[7], accounts[8], accounts[9], accounts[0]] const ownerOfValidators = accounts[0] const validatorContractWith3Signatures = await BridgeValidators.new() - await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) + await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, rewardsFiveAccs, ownerOfValidators) const erc20Token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); const value = web3.toBigNumber(web3.toWei(0.5, "ether")); const foreignBridgeWithThreeSigs = await ForeignBridge.new() @@ -234,6 +237,7 @@ contract('ForeignBridge_ERC20_to_Native', async (accounts) => { it('can be upgraded', async () => { const REQUIRED_NUMBER_OF_VALIDATORS = 1 const VALIDATORS = [accounts[1]] + const REWARDS = [accounts[2]] const PROXY_OWNER = accounts[0] // Validators Contract let validatorsProxy = await EternalStorageProxy.new().should.be.fulfilled; @@ -242,7 +246,7 @@ contract('ForeignBridge_ERC20_to_Native', async (accounts) => { validatorsContractImpl.address.should.be.equal(await validatorsProxy.implementation()) validatorsProxy = await BridgeValidators.at(validatorsProxy.address); - await validatorsProxy.initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, PROXY_OWNER).should.be.fulfilled; + await validatorsProxy.initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, REWARDS, PROXY_OWNER).should.be.fulfilled; let token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); // ForeignBridge V1 Contract diff --git a/test/erc_to_native/home_bridge.test.js b/test/erc_to_native/home_bridge.test.js index a78e33062..89588b691 100644 --- a/test/erc_to_native/home_bridge.test.js +++ b/test/erc_to_native/home_bridge.test.js @@ -12,13 +12,14 @@ const oneEther = web3.toBigNumber(web3.toWei(1, "ether")); const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")); contract('HomeBridge_ERC20_to_Native', async (accounts) => { - let homeContract, validatorContract, blockRewardContract, authorities, owner; + let homeContract, validatorContract, blockRewardContract, authorities, rewards, owner; before(async () => { validatorContract = await BridgeValidators.new() blockRewardContract = await BlockReward.new() authorities = [accounts[1]] + rewards = [accounts[2]] owner = accounts[0] - await validatorContract.initialize(1, authorities, owner) + await validatorContract.initialize(1, authorities, rewards, owner) }) describe('#initialize', async() => { @@ -300,9 +301,10 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { it('test with 2 signatures required', async () => { const validatorContractWith2Signatures = await BridgeValidators.new() - const authoritiesTwoAccs = [accounts[1], accounts[2], accounts[3]]; + const authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]]; + const rewardsThreeAccs = [accounts[4], accounts[5], accounts[6]]; const ownerOfValidators = accounts[0] - await validatorContractWith2Signatures.initialize(2, authoritiesTwoAccs, ownerOfValidators) + await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, rewardsThreeAccs, ownerOfValidators) const homeBridgeWithTwoSigs = await HomeBridge.new(); await homeBridgeWithTwoSigs.initialize(validatorContractWith2Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address); const recipient = accounts[5]; @@ -311,14 +313,14 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const balanceBefore = await web3.eth.getBalance(recipient) const msgHash = Web3Utils.soliditySha3(recipient, value, transactionHash); - const { logs } = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesTwoAccs[0]}).should.be.fulfilled; + const { logs } = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; logs[0].event.should.be.equal("SignedForAffirmation"); logs[0].args.should.be.deep.equal({ signer: authorities[0], transactionHash }); const notProcessed = await homeBridgeWithTwoSigs.numAffirmationsSigned(msgHash); notProcessed.should.be.bignumber.equal(1); - await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesTwoAccs[0]}).should.be.rejectedWith(ERROR_MSG); - const secondSignature = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesTwoAccs[1]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[0]}).should.be.rejectedWith(ERROR_MSG); + const secondSignature = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; const balanceAfter = await web3.eth.getBalance(recipient) balanceAfter.should.be.bignumber.equal(balanceBefore.add(value)) @@ -326,10 +328,10 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { secondSignature.logs[1].event.should.be.equal("AffirmationCompleted"); secondSignature.logs[1].args.should.be.deep.equal({ recipient, value, transactionHash }) - const senderHash = Web3Utils.soliditySha3(authoritiesTwoAccs[0], msgHash) + const senderHash = Web3Utils.soliditySha3(authoritiesThreeAccs[0], msgHash) true.should.be.equal(await homeBridgeWithTwoSigs.affirmationsSigned(senderHash)) - const senderHash2 = Web3Utils.soliditySha3(authoritiesTwoAccs[1], msgHash); + const senderHash2 = Web3Utils.soliditySha3(authoritiesThreeAccs[1], msgHash); true.should.be.equal(await homeBridgeWithTwoSigs.affirmationsSigned(senderHash2)) const markedAsProcessed = await homeBridgeWithTwoSigs.numAffirmationsSigned(msgHash); @@ -356,9 +358,10 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { it('works with 5 validators and 3 required signatures', async () => { const recipient = accounts[8] const authoritiesFiveAccs = [accounts[1], accounts[2], accounts[3], accounts[4], accounts[5]] + const rewardsFiveAccs = [accounts[6], accounts[7], accounts[8], accounts[9], accounts[0]] let ownerOfValidators = accounts[0] const validatorContractWith3Signatures = await BridgeValidators.new() - await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) + await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, rewardsFiveAccs, ownerOfValidators) const homeBridgeWithThreeSigs = await HomeBridge.new(); await homeBridgeWithThreeSigs.initialize(validatorContractWith3Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address); @@ -386,12 +389,13 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { }) describe('#submitSignature', async () => { - let validatorContractWith2Signatures,authoritiesTwoAccs,ownerOfValidators,homeBridgeWithTwoSigs + let validatorContractWith2Signatures,authoritiesThreeAccs,rewardsThreeAccs,ownerOfValidators,homeBridgeWithTwoSigs beforeEach(async () => { validatorContractWith2Signatures = await BridgeValidators.new() - authoritiesTwoAccs = [accounts[1], accounts[2], accounts[3]]; + authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]]; + rewardsThreeAccs = [accounts[4], accounts[5], accounts[6]]; ownerOfValidators = accounts[0] - await validatorContractWith2Signatures.initialize(2, authoritiesTwoAccs, ownerOfValidators) + await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, rewardsThreeAccs, ownerOfValidators) homeBridgeWithTwoSigs = await HomeBridge.new(); await homeBridgeWithTwoSigs.initialize(validatorContractWith2Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address); }) @@ -402,7 +406,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); - const signature = await sign(authoritiesTwoAccs[0], message) + const signature = await sign(authoritiesThreeAccs[0], message) const { logs } = await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authorities[0]}).should.be.fulfilled; logs[0].event.should.be.equal('SignedForUserRequest') @@ -422,24 +426,25 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); - const signature = await sign(authoritiesTwoAccs[0], message) - const signature2 = await sign(authoritiesTwoAccs[1], message) + const signature = await sign(authoritiesThreeAccs[0], message) + const signature2 = await sign(authoritiesThreeAccs[1], message) '2'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesTwoAccs[0]}).should.be.fulfilled; - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesTwoAccs[0]}).should.be.rejectedWith(ERROR_MSG); - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesTwoAccs[1]}).should.be.rejectedWith(ERROR_MSG); - const { logs } = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesTwoAccs[1]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.rejectedWith(ERROR_MSG); + await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[1]}).should.be.rejectedWith(ERROR_MSG); + const { logs } = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; logs.length.should.be.equal(2) logs[1].event.should.be.equal('CollectedSignatures') - logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesTwoAccs[1]) + logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesThreeAccs[1]) }) it('works with 5 validators and 3 required signatures', async () => { const recipientAccount = accounts[8] const authoritiesFiveAccs = [accounts[1], accounts[2], accounts[3], accounts[4], accounts[5]] + const rewardsFiveAccs = [accounts[6], accounts[7], accounts[8], accounts[9], accounts[0]] const validatorContractWith3Signatures = await BridgeValidators.new() - await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) + await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, rewardsFiveAccs, ownerOfValidators) const homeBridgeWithThreeSigs = await HomeBridge.new(); await homeBridgeWithThreeSigs.initialize(validatorContractWith3Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address); @@ -464,23 +469,23 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const value = web3.toBigNumber(web3.toWei(0.5, "ether")); const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); - const signature = await sign(authoritiesTwoAccs[0], message) - const signature2 = await sign(authoritiesTwoAccs[1], message) - const signature3 = await sign(authoritiesTwoAccs[2], message) + const signature = await sign(authoritiesThreeAccs[0], message) + const signature2 = await sign(authoritiesThreeAccs[1], message) + const signature3 = await sign(authoritiesThreeAccs[2], message) '2'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesTwoAccs[0]}).should.be.fulfilled; - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesTwoAccs[0]}).should.be.rejectedWith(ERROR_MSG); - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesTwoAccs[1]}).should.be.rejectedWith(ERROR_MSG); - const { logs } = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesTwoAccs[1]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.rejectedWith(ERROR_MSG); + await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[1]}).should.be.rejectedWith(ERROR_MSG); + const { logs } = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; logs.length.should.be.equal(2) logs[1].event.should.be.equal('CollectedSignatures') - logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesTwoAccs[1]) + logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesThreeAccs[1]) await validatorContractWith2Signatures.setRequiredSignatures(3).should.be.fulfilled; '3'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); - await homeBridgeWithTwoSigs.submitSignature(signature3, message, {from: authoritiesTwoAccs[2]}).should.be.rejectedWith(ERROR_MSG); + await homeBridgeWithTwoSigs.submitSignature(signature3, message, {from: authoritiesThreeAccs[2]}).should.be.rejectedWith(ERROR_MSG); }) it('attack when decreasing requiredSignatures', async () => { @@ -488,18 +493,18 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const value = web3.toBigNumber(web3.toWei(0.5, "ether")); const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); - const signature = await sign(authoritiesTwoAccs[0], message) - const signature2 = await sign(authoritiesTwoAccs[1], message) + const signature = await sign(authoritiesThreeAccs[0], message) + const signature2 = await sign(authoritiesThreeAccs[1], message) '2'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesTwoAccs[0]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; await validatorContractWith2Signatures.setRequiredSignatures(1).should.be.fulfilled; '1'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); - const { logs } = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesTwoAccs[1]}).should.be.fulfilled; + const { logs } = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; logs.length.should.be.equal(2) logs[1].event.should.be.equal('CollectedSignatures') - logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesTwoAccs[1]) + logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesThreeAccs[1]) }) }) diff --git a/test/native_to_erc/foreign_bridge_test.js b/test/native_to_erc/foreign_bridge_test.js index 42b115cb1..7cc796632 100644 --- a/test/native_to_erc/foreign_bridge_test.js +++ b/test/native_to_erc/foreign_bridge_test.js @@ -28,12 +28,13 @@ const getEvents = function(contract, filter) { }); } contract('ForeignBridge', async (accounts) => { - let validatorContract, authorities, owner, token; + let validatorContract, authorities, rewards, owner, token; before(async () => { validatorContract = await BridgeValidators.new() authorities = [accounts[1], accounts[2]]; + rewards = [accounts[3], accounts[4]]; owner = accounts[0] - await validatorContract.initialize(1, authorities, owner) + await validatorContract.initialize(1, authorities, rewards, owner) }) describe('#initialize', async () => { @@ -69,6 +70,7 @@ contract('ForeignBridge', async (accounts) => { patch.should.be.bignumber.gte(0) }) }) + describe('#executeSignatures', async () => { beforeEach(async () => { foreignBridge = await ForeignBridge.new() @@ -168,14 +170,15 @@ contract('ForeignBridge', async (accounts) => { }) describe('#executeSignatures with 2 minimum signatures', async () => { - let multisigValidatorContract, twoAuthorities, ownerOfValidatorContract, foreignBridgeWithMultiSignatures + let multisigValidatorContract, twoAuthorities, twoRewards, ownerOfValidatorContract, foreignBridgeWithMultiSignatures beforeEach(async () => { multisigValidatorContract = await BridgeValidators.new() token = await POA20.new("POA ERC20 Foundation", "POA20", 18); twoAuthorities = [accounts[0], accounts[1]]; + twoRewards = [accounts[2], accounts[3]]; ownerOfValidatorContract = accounts[3] const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")); - await multisigValidatorContract.initialize(2, twoAuthorities, ownerOfValidatorContract, {from: ownerOfValidatorContract}) + await multisigValidatorContract.initialize(2, twoAuthorities, twoRewards, ownerOfValidatorContract, {from: ownerOfValidatorContract}) foreignBridgeWithMultiSignatures = await ForeignBridge.new() const oneEther = web3.toBigNumber(web3.toWei(1, "ether")); await foreignBridgeWithMultiSignatures.initialize(multisigValidatorContract.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, {from: ownerOfValidatorContract}); @@ -225,9 +228,10 @@ contract('ForeignBridge', async (accounts) => { it('works with 5 validators and 3 required signatures', async () => { const recipient = accounts[8] const authoritiesFiveAccs = [accounts[1], accounts[2], accounts[3], accounts[4], accounts[5]] + const rewardsFiveAccs = [accounts[6], accounts[7], accounts[8], accounts[9], accounts[0]] const ownerOfValidators = accounts[0] const validatorContractWith3Signatures = await BridgeValidators.new() - await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) + await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, rewardsFiveAccs, ownerOfValidators) const erc20Token = await POA20.new("Some ERC20", "RSZT", 18); const value = web3.toBigNumber(web3.toWei(0.5, "ether")); const foreignBridgeWithThreeSigs = await ForeignBridge.new() @@ -259,7 +263,6 @@ contract('ForeignBridge', async (accounts) => { }) }) - describe('#onTokenTransfer', async () => { it('can only be called from token contract', async ()=> { const owner = accounts[3] @@ -361,6 +364,7 @@ contract('ForeignBridge', async (accounts) => { it('can be upgraded', async () => { const REQUIRED_NUMBER_OF_VALIDATORS = 1 const VALIDATORS = [accounts[1]] + const REWARDS = [accounts[2]] const PROXY_OWNER = accounts[0] const FOREIGN_DAILY_LIMIT = oneEther; const FOREIGN_MAX_AMOUNT_PER_TX = halfEther; @@ -372,7 +376,7 @@ contract('ForeignBridge', async (accounts) => { validatorsContractImpl.address.should.be.equal(await validatorsProxy.implementation()) validatorsProxy = await BridgeValidators.at(validatorsProxy.address); - await validatorsProxy.initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, PROXY_OWNER).should.be.fulfilled; + await validatorsProxy.initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, REWARDS, PROXY_OWNER).should.be.fulfilled; // POA20 let token = await POA20.new("POA ERC20 Foundation", "POA20", 18); diff --git a/test/native_to_erc/home_bridge_test.js b/test/native_to_erc/home_bridge_test.js index 94cddca3e..72c000a3a 100644 --- a/test/native_to_erc/home_bridge_test.js +++ b/test/native_to_erc/home_bridge_test.js @@ -12,13 +12,15 @@ const oneEther = web3.toBigNumber(web3.toWei(1, "ether")); const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")); contract('HomeBridge', async (accounts) => { - let homeContract, validatorContract, authorities, owner; + let homeContract, validatorContract, authorities, rewards, owner; before(async () => { validatorContract = await BridgeValidators.new() authorities = [accounts[1]]; + rewards = [accounts[2]]; owner = accounts[0] - await validatorContract.initialize(1, authorities, owner) + await validatorContract.initialize(1, authorities, rewards, owner) }) + describe('#initialize', async() => { beforeEach(async () => { homeContract = await HomeBridge.new() @@ -212,9 +214,10 @@ contract('HomeBridge', async (accounts) => { it('test with 2 signatures required', async () => { let validatorContractWith2Signatures = await BridgeValidators.new() - let authoritiesTwoAccs = [accounts[1], accounts[2], accounts[3]]; + let authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]]; + let rewardsThreeAccs = [accounts[4], accounts[5], accounts[6]]; let ownerOfValidators = accounts[0] - await validatorContractWith2Signatures.initialize(2, authoritiesTwoAccs, ownerOfValidators) + await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, rewardsThreeAccs, ownerOfValidators) let homeBridgeWithTwoSigs = await HomeBridge.new(); await homeBridgeWithTwoSigs.initialize(validatorContractWith2Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations); @@ -231,7 +234,7 @@ contract('HomeBridge', async (accounts) => { const balanceBefore = await web3.eth.getBalance(recipient) const msgHash = Web3Utils.soliditySha3(recipient, value, transactionHash); - const {logs} = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesTwoAccs[0]}).should.be.fulfilled; + const {logs} = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; logs[0].event.should.be.equal("SignedForAffirmation"); logs[0].args.should.be.deep.equal({ signer: authorities[0], @@ -241,8 +244,8 @@ contract('HomeBridge', async (accounts) => { const notProcessed = await homeBridgeWithTwoSigs.numAffirmationsSigned(msgHash); notProcessed.should.be.bignumber.equal(1); - await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesTwoAccs[0]}).should.be.rejectedWith(ERROR_MSG); - const secondSignature = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesTwoAccs[1]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[0]}).should.be.rejectedWith(ERROR_MSG); + const secondSignature = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; const balanceAfter = await web3.eth.getBalance(recipient) balanceAfter.should.be.bignumber.equal(balanceBefore.add(value)) @@ -255,10 +258,10 @@ contract('HomeBridge', async (accounts) => { transactionHash }) - const senderHash = Web3Utils.soliditySha3(authoritiesTwoAccs[0], msgHash) + const senderHash = Web3Utils.soliditySha3(authoritiesThreeAccs[0], msgHash) true.should.be.equal(await homeBridgeWithTwoSigs.affirmationsSigned(senderHash)) - const senderHash2 = Web3Utils.soliditySha3(authoritiesTwoAccs[1], msgHash); + const senderHash2 = Web3Utils.soliditySha3(authoritiesThreeAccs[1], msgHash); true.should.be.equal(await homeBridgeWithTwoSigs.affirmationsSigned(senderHash2)) const markedAsProcessed = await homeBridgeWithTwoSigs.numAffirmationsSigned(msgHash); @@ -282,9 +285,10 @@ contract('HomeBridge', async (accounts) => { it('doesnt allow to withdraw if requiredSignatures has changed', async () => { let validatorContractWith2Signatures = await BridgeValidators.new() - let authoritiesTwoAccs = [accounts[1], accounts[2], accounts[3]]; + let authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]]; + let rewardsThreeAccs = [accounts[4], accounts[5], accounts[6]]; let ownerOfValidators = accounts[0] - await validatorContractWith2Signatures.initialize(2, authoritiesTwoAccs, ownerOfValidators) + await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, rewardsThreeAccs, ownerOfValidators) let homeBridgeWithTwoSigs = await HomeBridge.new(); await homeBridgeWithTwoSigs.initialize(validatorContractWith2Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations); @@ -301,13 +305,13 @@ contract('HomeBridge', async (accounts) => { const balanceBefore = await web3.eth.getBalance(recipient) const msgHash = Web3Utils.soliditySha3(recipient, value, transactionHash); - await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesTwoAccs[0]}).should.be.fulfilled; - await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesTwoAccs[1]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; balanceBefore.add(value).should.be.bignumber.equal(await web3.eth.getBalance(recipient)) await validatorContractWith2Signatures.setRequiredSignatures(3).should.be.fulfilled; - await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesTwoAccs[2]}).should.be.rejectedWith(ERROR_MSG); + await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[2]}).should.be.rejectedWith(ERROR_MSG); await validatorContractWith2Signatures.setRequiredSignatures(1).should.be.fulfilled; - await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesTwoAccs[2]}).should.be.rejectedWith(ERROR_MSG); + await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[2]}).should.be.rejectedWith(ERROR_MSG); balanceBefore.add(value).should.be.bignumber.equal(await web3.eth.getBalance(recipient)) }) @@ -339,9 +343,10 @@ contract('HomeBridge', async (accounts) => { it('works with 5 validators and 3 required signatures', async () => { const recipient = accounts[8] const authoritiesFiveAccs = [accounts[1], accounts[2], accounts[3], accounts[4], accounts[5]] + const rewardsFiveAccs = [accounts[6], accounts[7], accounts[8], accounts[9], accounts[0]] let ownerOfValidators = accounts[0] const validatorContractWith3Signatures = await BridgeValidators.new() - await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) + await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, rewardsFiveAccs, ownerOfValidators) const homeBridgeWithThreeSigs = await HomeBridge.new(); await homeBridgeWithThreeSigs.initialize(validatorContractWith3Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations); @@ -372,6 +377,7 @@ contract('HomeBridge', async (accounts) => { }) }) }) + describe('#isAlreadyProcessed', async () => { it('returns ', async () => { homeBridge = await HomeBridge.new(); @@ -384,12 +390,13 @@ contract('HomeBridge', async (accounts) => { }) describe('#submitSignature', async () => { - let validatorContractWith2Signatures,authoritiesTwoAccs,ownerOfValidators,tokenPOA20,homeBridgeWithTwoSigs + let validatorContractWith2Signatures,authoritiesThreeAccs,rewardsThreeAccs,ownerOfValidators,tokenPOA20,homeBridgeWithTwoSigs beforeEach(async () => { validatorContractWith2Signatures = await BridgeValidators.new() - authoritiesTwoAccs = [accounts[1], accounts[2], accounts[3]]; + authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]]; + rewardsThreeAccs = [accounts[4], accounts[5], accounts[6]]; ownerOfValidators = accounts[0] - await validatorContractWith2Signatures.initialize(2, authoritiesTwoAccs, ownerOfValidators) + await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, rewardsThreeAccs, ownerOfValidators) homeBridgeWithTwoSigs = await HomeBridge.new(); await homeBridgeWithTwoSigs.initialize(validatorContractWith2Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations); }) @@ -398,7 +405,7 @@ contract('HomeBridge', async (accounts) => { var value = web3.toBigNumber(web3.toWei(0.5, "ether")); var transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; var message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); - var signature = await sign(authoritiesTwoAccs[0], message) + var signature = await sign(authoritiesThreeAccs[0], message) const {logs} = await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authorities[0]}).should.be.fulfilled; logs[0].event.should.be.equal('SignedForUserRequest') const msgHashFromLog = logs[0].args.messageHash @@ -416,22 +423,23 @@ contract('HomeBridge', async (accounts) => { var homeGasPrice = web3.toBigNumber(0); var transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; var message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); - var signature = await sign(authoritiesTwoAccs[0], message) - var signature2 = await sign(authoritiesTwoAccs[1], message) + var signature = await sign(authoritiesThreeAccs[0], message) + var signature2 = await sign(authoritiesThreeAccs[1], message) '2'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesTwoAccs[0]}).should.be.fulfilled; - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesTwoAccs[0]}).should.be.rejectedWith(ERROR_MSG); - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesTwoAccs[1]}).should.be.rejectedWith(ERROR_MSG); - const {logs} = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesTwoAccs[1]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.rejectedWith(ERROR_MSG); + await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[1]}).should.be.rejectedWith(ERROR_MSG); + const {logs} = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; logs.length.should.be.equal(2) logs[1].event.should.be.equal('CollectedSignatures') - logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesTwoAccs[1]) + logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesThreeAccs[1]) }) it('works with 5 validators and 3 required signatures', async () => { const recipientAccount = accounts[8] const authoritiesFiveAccs = [accounts[1], accounts[2], accounts[3], accounts[4], accounts[5]] + const rewardsFiveAccs = [accounts[6], accounts[7], accounts[8], accounts[9], accounts[0]] const validatorContractWith3Signatures = await BridgeValidators.new() - await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) + await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, rewardsFiveAccs, ownerOfValidators) const homeBridgeWithThreeSigs = await HomeBridge.new(); await homeBridgeWithThreeSigs.initialize(validatorContractWith3Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations); @@ -457,20 +465,20 @@ contract('HomeBridge', async (accounts) => { var homeGasPrice = web3.toBigNumber(0); var transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; var message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); - var signature = await sign(authoritiesTwoAccs[0], message) - var signature2 = await sign(authoritiesTwoAccs[1], message) - var signature3 = await sign(authoritiesTwoAccs[2], message) + var signature = await sign(authoritiesThreeAccs[0], message) + var signature2 = await sign(authoritiesThreeAccs[1], message) + var signature3 = await sign(authoritiesThreeAccs[2], message) '2'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesTwoAccs[0]}).should.be.fulfilled; - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesTwoAccs[0]}).should.be.rejectedWith(ERROR_MSG); - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesTwoAccs[1]}).should.be.rejectedWith(ERROR_MSG); - const {logs} = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesTwoAccs[1]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.rejectedWith(ERROR_MSG); + await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[1]}).should.be.rejectedWith(ERROR_MSG); + const {logs} = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; logs.length.should.be.equal(2) logs[1].event.should.be.equal('CollectedSignatures') - logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesTwoAccs[1]) + logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesThreeAccs[1]) await validatorContractWith2Signatures.setRequiredSignatures(3).should.be.fulfilled; '3'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); - const attackerTx = await homeBridgeWithTwoSigs.submitSignature(signature3, message, {from: authoritiesTwoAccs[2]}).should.be.rejectedWith(ERROR_MSG); + const attackerTx = await homeBridgeWithTwoSigs.submitSignature(signature3, message, {from: authoritiesThreeAccs[2]}).should.be.rejectedWith(ERROR_MSG); }) it('attack when decreasing requiredSignatures', async () => { var recipientAccount = accounts[8] @@ -478,17 +486,17 @@ contract('HomeBridge', async (accounts) => { var homeGasPrice = web3.toBigNumber(0); var transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; var message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); - var signature = await sign(authoritiesTwoAccs[0], message) - var signature2 = await sign(authoritiesTwoAccs[1], message) - var signature3 = await sign(authoritiesTwoAccs[2], message) + var signature = await sign(authoritiesThreeAccs[0], message) + var signature2 = await sign(authoritiesThreeAccs[1], message) + var signature3 = await sign(authoritiesThreeAccs[2], message) '2'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesTwoAccs[0]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; await validatorContractWith2Signatures.setRequiredSignatures(1).should.be.fulfilled; '1'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); - const {logs} = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesTwoAccs[1]}).should.be.fulfilled; + const {logs} = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; logs.length.should.be.equal(2) logs[1].event.should.be.equal('CollectedSignatures') - logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesTwoAccs[1]) + logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesThreeAccs[1]) }) }) diff --git a/test/poa20_test.js b/test/poa20_test.js index f4d1d4c82..c15191916 100644 --- a/test/poa20_test.js +++ b/test/poa20_test.js @@ -99,7 +99,8 @@ contract('ERC677BridgeToken', async (accounts) => { beforeEach(async () => { validatorContract = await BridgeValidators.new() const authorities = [accounts[2]]; - await validatorContract.initialize(1, authorities, owner) + const rewards = [accounts[3]]; + await validatorContract.initialize(1, authorities, rewards, owner) homeErcToErcContract = await HomeErcToErcBridge.new() await homeErcToErcContract.initialize(validatorContract.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address) foreignNativeToErcBridge = await ForeignNativeToErcBridge.new() @@ -187,7 +188,8 @@ contract('ERC677BridgeToken', async (accounts) => { beforeEach(async () => { validatorContract = await BridgeValidators.new() const authorities = [accounts[2]]; - await validatorContract.initialize(1, authorities, owner) + const rewards = [accounts[3]]; + await validatorContract.initialize(1, authorities, rewards, owner) homeErcToErcContract = await HomeErcToErcBridge.new() await homeErcToErcContract.initialize(validatorContract.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address) foreignNativeToErcBridge = await ForeignNativeToErcBridge.new() From bc289bd2dbc074e8106a303043c96d1f015e44f1 Mon Sep 17 00:00:00 2001 From: Vadim Arasev Date: Thu, 27 Dec 2018 10:12:29 +0300 Subject: [PATCH 006/187] Add `DEPLOY_REWARDABLE_TOKEN` and `VALIDATOR_SET_ADDRESS` config options --- deploy/.env.example | 6 +++-- deploy/README.md | 10 ++++++++ deploy/src/native_to_erc/foreign.js | 38 +++++++++++++++++++++++++++-- 3 files changed, 50 insertions(+), 4 deletions(-) diff --git a/deploy/.env.example b/deploy/.env.example index 954064a0f..5c7a320da 100644 --- a/deploy/.env.example +++ b/deploy/.env.example @@ -20,7 +20,7 @@ HOME_MIN_AMOUNT_PER_TX=500000000000000000 HOME_REQUIRED_BLOCK_CONFIRMATIONS=1 HOME_GAS_PRICE=1000000000 -#for bridge erc to native mode +#for bridge erc_to_native and native_to_erc mode BLOCK_REWARD_ADDRESS= FOREIGN_RPC_URL=https://sokol.poa.network @@ -38,4 +38,6 @@ ERC20_TOKEN_ADDRESS= REQUIRED_NUMBER_OF_VALIDATORS=1 VALIDATORS="0x 0x 0x" - +#for bridge native_to_erc mode +DEPLOY_REWARDABLE_TOKEN=false +VALIDATOR_SET_ADDRESS= diff --git a/deploy/README.md b/deploy/README.md index 77c9051d0..7f532eea4 100644 --- a/deploy/README.md +++ b/deploy/README.md @@ -125,6 +125,16 @@ REQUIRED_NUMBER_OF_VALIDATORS=1 # the Foreign network to confirm that the finalized agreement was transferred # correctly to the Foreign network. VALIDATORS="0x 0x 0x" + +# The flag defining whether to use ERC677BridgeTokenRewardable contract instead of +# ERC677BridgeToken. +DEPLOY_REWARDABLE_TOKEN=false +# The address of ValidatorSet contract used by ERC677BridgeTokenRewardable contract. +# Makes sense only when DEPLOY_REWARDABLE_TOKEN=true +VALIDATOR_SET_ADDRESS=0x +# The address of BlockReward contract used by ERC677BridgeTokenRewardable contract. +# Makes sense only when DEPLOY_REWARDABLE_TOKEN=true +BLOCK_REWARD_ADDRESS=0x ``` diff --git a/deploy/src/native_to_erc/foreign.js b/deploy/src/native_to_erc/foreign.js index dfd1877d0..74d8ec544 100644 --- a/deploy/src/native_to_erc/foreign.js +++ b/deploy/src/native_to_erc/foreign.js @@ -6,6 +6,7 @@ const { deployContract, privateKeyToAddress, sendRawTxForeign } = require('../de const { web3Foreign, deploymentPrivateKey, FOREIGN_RPC_URL } = require('../web3') const ERC677BridgeToken = require('../../../build/contracts/ERC677BridgeToken.json') +const ERC677BridgeTokenRewardable = require('../../../build/contracts/ERC677BridgeTokenRewardable.json') const EternalStorageProxy = require('../../../build/contracts/EternalStorageProxy.json') const BridgeValidators = require('../../../build/contracts/BridgeValidators.json') const ForeignBridge = require('../../../build/contracts/ForeignBridgeNativeToErc.json') @@ -25,7 +26,10 @@ const { FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS, BRIDGEABLE_TOKEN_NAME, BRIDGEABLE_TOKEN_SYMBOL, - BRIDGEABLE_TOKEN_DECIMALS + BRIDGEABLE_TOKEN_DECIMALS, + DEPLOY_REWARDABLE_TOKEN, + BLOCK_REWARD_ADDRESS, + VALIDATOR_SET_ADDRESS } = env const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVATE_KEY) @@ -38,7 +42,7 @@ async function deployForeign() { console.log('\n[Foreign] deploying BRIDGEABLE_TOKEN_SYMBOL token') const erc677bridgeToken = await deployContract( - ERC677BridgeToken, + DEPLOY_REWARDABLE_TOKEN ? ERC677BridgeTokenRewardable : ERC677BridgeToken, [BRIDGEABLE_TOKEN_NAME, BRIDGEABLE_TOKEN_SYMBOL, BRIDGEABLE_TOKEN_DECIMALS], { from: DEPLOYMENT_ACCOUNT_ADDRESS, network: 'foreign', nonce: foreignNonce } ) @@ -195,6 +199,36 @@ async function deployForeign() { assert.equal(Web3Utils.hexToNumber(setBridgeContract.status), 1, 'Transaction Failed') foreignNonce++ + if (DEPLOY_REWARDABLE_TOKEN) { + console.log('\nset BlockReward contract on ERC677BridgeTokenRewardable') + const setBlockRewardContractData = await erc677bridgeToken.methods + .setBlockRewardContract(BLOCK_REWARD_ADDRESS) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + const setBlockRewardContract = await sendRawTxForeign({ + data: setBlockRewardContractData, + nonce: foreignNonce, + to: erc677bridgeToken.options.address, + privateKey: deploymentPrivateKey, + url: FOREIGN_RPC_URL + }) + assert.equal(Web3Utils.hexToNumber(setBlockRewardContract.status), 1, 'Transaction Failed') + foreignNonce++ + + console.log('\nset ValidatorSet contract on ERC677BridgeTokenRewardable') + const setValidatorSetContractData = await erc677bridgeToken.methods + .setValidatorSetContract(VALIDATOR_SET_ADDRESS) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + const setValidatorSetContract = await sendRawTxForeign({ + data: setValidatorSetContractData, + nonce: foreignNonce, + to: erc677bridgeToken.options.address, + privateKey: deploymentPrivateKey, + url: FOREIGN_RPC_URL + }) + assert.equal(Web3Utils.hexToNumber(setValidatorSetContract.status), 1, 'Transaction Failed') + foreignNonce++ + } + console.log('transferring ownership of ERC677BridgeToken token to foreignBridge contract') const txOwnershipData = await erc677bridgeToken.methods .transferOwnership(foreignBridgeStorage.options.address) From 47f766b6c90759281abffee38e0c0834417ed727 Mon Sep 17 00:00:00 2001 From: Vadim Arasev Date: Thu, 27 Dec 2018 18:49:33 +0300 Subject: [PATCH 007/187] Validate new config variables --- deploy/.env.example | 2 +- deploy/README.md | 2 +- deploy/src/loadEnv.js | 5 ++++- deploy/src/native_to_erc/foreign.js | 4 ++-- 4 files changed, 8 insertions(+), 5 deletions(-) diff --git a/deploy/.env.example b/deploy/.env.example index 5c7a320da..0dc009b6a 100644 --- a/deploy/.env.example +++ b/deploy/.env.example @@ -40,4 +40,4 @@ VALIDATORS="0x 0x 0x" #for bridge native_to_erc mode DEPLOY_REWARDABLE_TOKEN=false -VALIDATOR_SET_ADDRESS= +DPOS_VALIDATOR_SET_ADDRESS= diff --git a/deploy/README.md b/deploy/README.md index 7f532eea4..ee888bb0d 100644 --- a/deploy/README.md +++ b/deploy/README.md @@ -131,7 +131,7 @@ VALIDATORS="0x 0x 0x" DEPLOY_REWARDABLE_TOKEN=false # The address of ValidatorSet contract used by ERC677BridgeTokenRewardable contract. # Makes sense only when DEPLOY_REWARDABLE_TOKEN=true -VALIDATOR_SET_ADDRESS=0x +DPOS_VALIDATOR_SET_ADDRESS=0x # The address of BlockReward contract used by ERC677BridgeTokenRewardable contract. # Makes sense only when DEPLOY_REWARDABLE_TOKEN=true BLOCK_REWARD_ADDRESS=0x diff --git a/deploy/src/loadEnv.js b/deploy/src/loadEnv.js index 2645a0568..dbfa7ec37 100644 --- a/deploy/src/loadEnv.js +++ b/deploy/src/loadEnv.js @@ -61,7 +61,10 @@ if (BRIDGE_MODE === 'NATIVE_TO_ERC') { BRIDGEABLE_TOKEN_DECIMALS: envalid.num(), FOREIGN_DAILY_LIMIT: bigNumValidator(), FOREIGN_MAX_AMOUNT_PER_TX: bigNumValidator(), - FOREIGN_MIN_AMOUNT_PER_TX: bigNumValidator() + FOREIGN_MIN_AMOUNT_PER_TX: bigNumValidator(), + DEPLOY_REWARDABLE_TOKEN: envalid.bool(), + DPOS_VALIDATOR_SET_ADDRESS: addressValidator(), + BLOCK_REWARD_ADDRESS: addressValidator() } } if (BRIDGE_MODE === 'ERC_TO_ERC') { diff --git a/deploy/src/native_to_erc/foreign.js b/deploy/src/native_to_erc/foreign.js index 74d8ec544..7c4ec5cd5 100644 --- a/deploy/src/native_to_erc/foreign.js +++ b/deploy/src/native_to_erc/foreign.js @@ -29,7 +29,7 @@ const { BRIDGEABLE_TOKEN_DECIMALS, DEPLOY_REWARDABLE_TOKEN, BLOCK_REWARD_ADDRESS, - VALIDATOR_SET_ADDRESS + DPOS_VALIDATOR_SET_ADDRESS } = env const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVATE_KEY) @@ -216,7 +216,7 @@ async function deployForeign() { console.log('\nset ValidatorSet contract on ERC677BridgeTokenRewardable') const setValidatorSetContractData = await erc677bridgeToken.methods - .setValidatorSetContract(VALIDATOR_SET_ADDRESS) + .setValidatorSetContract(DPOS_VALIDATOR_SET_ADDRESS) .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) const setValidatorSetContract = await sendRawTxForeign({ data: setValidatorSetContractData, From 058335f54cb0570e0ab5b19f2b024e3446a5f74a Mon Sep 17 00:00:00 2001 From: fernandomg Date: Thu, 27 Dec 2018 15:09:23 -0300 Subject: [PATCH 008/187] Add `_reward` param to `addValidator` method --- contracts/upgradeable_contracts/BridgeValidators.sol | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/contracts/upgradeable_contracts/BridgeValidators.sol b/contracts/upgradeable_contracts/BridgeValidators.sol index d741cf4f1..09cd94bcc 100644 --- a/contracts/upgradeable_contracts/BridgeValidators.sol +++ b/contracts/upgradeable_contracts/BridgeValidators.sol @@ -60,12 +60,13 @@ contract BridgeValidators is IBridgeValidators, EternalStorage, Ownable { return isInitialized(); } - function addValidator(address _validator) external onlyOwner { + function addValidator(address _validator, address _reward) external onlyOwner { require(_validator != address(0)); require(!isValidator(_validator)); address firstValidator = getNextValidator(F_ADDR); setValidator(_validator, firstValidator); + setValidatorRewardAddress(_validator, _reward); setValidator(F_ADDR, _validator); setValidatorCount(validatorCount().add(1)); From 9d219727c6888afd31042bdb8a0dc20b85f6fb01 Mon Sep 17 00:00:00 2001 From: fernandomg Date: Thu, 27 Dec 2018 15:11:05 -0300 Subject: [PATCH 009/187] Fix/Add `require`s for `validator` and `reward` addresses --- contracts/upgradeable_contracts/BridgeValidators.sol | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/contracts/upgradeable_contracts/BridgeValidators.sol b/contracts/upgradeable_contracts/BridgeValidators.sol index 09cd94bcc..6eb5f7e0d 100644 --- a/contracts/upgradeable_contracts/BridgeValidators.sol +++ b/contracts/upgradeable_contracts/BridgeValidators.sol @@ -32,7 +32,8 @@ contract BridgeValidators is IBridgeValidators, EternalStorage, Ownable { require(_initialValidators.length == _initialRewards.length); for (uint256 i = 0; i < _initialValidators.length; i++) { - require(_initialValidators[i] != address(0) || _initialValidators[i] != F_ADDR); + require(_initialValidators[i] != address(0) && _initialValidators[i] != F_ADDR); + require(_initialRewards[i] != address(0)); require(!isValidator(_initialValidators[i])); if (i == 0) { @@ -61,7 +62,8 @@ contract BridgeValidators is IBridgeValidators, EternalStorage, Ownable { } function addValidator(address _validator, address _reward) external onlyOwner { - require(_validator != address(0)); + require(_validator != address(0) && _validator != F_ADDR); + require(_reward != address(0)); require(!isValidator(_validator)); address firstValidator = getNextValidator(F_ADDR); From e25f0ffc2e37887626ca2d2b1e75d9d8aa40d278 Mon Sep 17 00:00:00 2001 From: fernandomg Date: Thu, 27 Dec 2018 15:12:42 -0300 Subject: [PATCH 010/187] Extend BridgeValidators interface and make F_ADDR public --- contracts/IBridgeValidators.sol | 2 ++ contracts/upgradeable_contracts/BridgeValidators.sol | 4 ++-- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/contracts/IBridgeValidators.sol b/contracts/IBridgeValidators.sol index 2732ae41e..18098cd13 100644 --- a/contracts/IBridgeValidators.sol +++ b/contracts/IBridgeValidators.sol @@ -5,4 +5,6 @@ interface IBridgeValidators { function isValidator(address _validator) public view returns(bool); function requiredSignatures() public view returns(uint256); function owner() public view returns(address); + function getNextValidator(address _validator) public view returns(address); + function getValidatorRewardAddress(address _validator) public view returns(address); } diff --git a/contracts/upgradeable_contracts/BridgeValidators.sol b/contracts/upgradeable_contracts/BridgeValidators.sol index 6eb5f7e0d..f88b43e41 100644 --- a/contracts/upgradeable_contracts/BridgeValidators.sol +++ b/contracts/upgradeable_contracts/BridgeValidators.sol @@ -9,7 +9,7 @@ import "../upgradeability/EternalStorage.sol"; contract BridgeValidators is IBridgeValidators, EternalStorage, Ownable { using SafeMath for uint256; - address constant F_ADDR = 0xFFfFfFffFFfffFFfFFfFFFFFffFFFffffFfFFFfF; + address public constant F_ADDR = 0xFFfFfFffFFfffFFfFFfFFFFFffFFFffffFfFFFfF; event ValidatorAdded (address indexed validator); event ValidatorRemoved (address indexed validator); @@ -138,7 +138,7 @@ contract BridgeValidators is IBridgeValidators, EternalStorage, Ownable { return addressStorage[keccak256(abi.encodePacked("validatorsRewards", _validator))]; } - function getNextValidator(address _address) internal view returns (address) { + function getNextValidator(address _address) public view returns (address) { return addressStorage[keccak256(abi.encodePacked("validatorsList", _address))]; } From c43f117fbea63b7f6b9f0f74bae96d701eb3b4be Mon Sep 17 00:00:00 2001 From: fernandomg Date: Thu, 27 Dec 2018 15:41:58 -0300 Subject: [PATCH 011/187] Add/Extend BridgeValidators tests --- test/setup.js | 1 + test/validators_test.js | 26 +++++++++++++++++++++----- 2 files changed, 22 insertions(+), 5 deletions(-) diff --git a/test/setup.js b/test/setup.js index c8f0382ab..2e713af02 100644 --- a/test/setup.js +++ b/test/setup.js @@ -8,4 +8,5 @@ require('chai') exports.ERROR_MSG = 'VM Exception while processing transaction: revert'; exports.ERROR_MSG_OPCODE = 'VM Exception while processing transaction: invalid opcode'; exports.ZERO_ADDRESS = '0x0000000000000000000000000000000000000000' +exports.F_ADDRESS = '0xFFfFfFffFFfffFFfFFfFFFFFffFFFffffFfFFFfF' exports.INVALID_ARGUMENTS = 'Invalid number of arguments to Solidity function' diff --git a/test/validators_test.js b/test/validators_test.js index 496fa116e..68e9173b0 100644 --- a/test/validators_test.js +++ b/test/validators_test.js @@ -1,6 +1,6 @@ const BridgeValidators = artifacts.require("BridgeValidators.sol"); const EternalStorageProxy = artifacts.require("EternalStorageProxy.sol"); -const {ERROR_MSG, ZERO_ADDRESS} = require('./setup'); +const { ERROR_MSG, ZERO_ADDRESS, F_ADDRESS } = require('./setup'); contract('BridgeValidators', async (accounts) => { let bridgeValidators @@ -22,6 +22,9 @@ contract('BridgeValidators', async (accounts) => { await bridgeValidators.initialize(3, accounts.slice(0, 3), accounts.slice(3, 5), accounts[2], {from: accounts[2]}).should.be.rejectedWith(ERROR_MSG) await bridgeValidators.initialize(2, accounts.slice(0, 2), accounts.slice(2, 4), accounts[2], {from: accounts[2]}).should.be.fulfilled; await bridgeValidators.initialize(2, accounts.slice(0, 2), accounts.slice(2, 4), accounts[2], {from: accounts[2]}).should.be.rejectedWith(ERROR_MSG); + await bridgeValidators.initialize(1, [accounts[0]], [ZERO_ADDRESS], [accounts[1]], { from: accounts[1] }).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.initialize(1, [ZERO_ADDRESS], [accounts[0]], [accounts[1]], { from: accounts[1] }).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.initialize(1, [F_ADDRESS], [accounts[0]], [accounts[1]], { from: accounts[1] }).should.be.rejectedWith(ERROR_MSG) true.should.be.equal(await bridgeValidators.isInitialized()) '2'.should.be.bignumber.equal(await bridgeValidators.requiredSignatures()) true.should.be.equal(await bridgeValidators.isValidator(accounts[0])) @@ -47,10 +50,11 @@ contract('BridgeValidators', async (accounts) => { }) it('adds validator', async () => { let newValidator = accounts[4]; + let newReward = accounts[5]; false.should.be.equal(await bridgeValidators.isValidator(newValidator)) - await bridgeValidators.addValidator(newValidator, {from: validators[0]}).should.be.rejectedWith(ERROR_MSG) - const {logs} = await bridgeValidators.addValidator(newValidator, {from: owner}).should.be.fulfilled + await bridgeValidators.addValidator(newValidator, newReward, {from: validators[0]}).should.be.rejectedWith(ERROR_MSG) + const {logs} = await bridgeValidators.addValidator(newValidator, newReward, {from: owner}).should.be.fulfilled true.should.be.equal(await bridgeValidators.isValidator(newValidator)) '3'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) logs[0].event.should.be.equal('ValidatorAdded') @@ -59,10 +63,22 @@ contract('BridgeValidators', async (accounts) => { it('cannot add already existing validator', async () => { true.should.be.equal(await bridgeValidators.isValidator(validators[0])) - await bridgeValidators.addValidator(validators[0], {from: owner}).should.be.rejectedWith(ERROR_MSG) - await bridgeValidators.addValidator(ZERO_ADDRESS, {from: owner}).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.addValidator(validators[0], rewards[0], {from: owner}).should.be.rejectedWith(ERROR_MSG) '2'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) }) + + it(`cannot add 0xf as validator address`, async () => { + // Given + await bridgeValidators.addValidator(F_ADDRESS, rewards[0], { from: owner }).should.be.rejectedWith(ERROR_MSG) + }) + + it(`cannot add 0x0 as validator address`, async () => { + await bridgeValidators.addValidator(ZERO_ADDRESS, rewards[0], {from: owner}).should.be.rejectedWith(ERROR_MSG) + }) + + it(`cannot add 0x0 as reward address`, async () => { + await bridgeValidators.addValidator(accounts[4], ZERO_ADDRESS, { from: owner }).should.be.rejectedWith(ERROR_MSG) + }) }) describe('#removeValidator', async () => { From 45a094f5dd48a81186315ffd857394ec603f8cf5 Mon Sep 17 00:00:00 2001 From: Vadim Arasev Date: Fri, 28 Dec 2018 16:36:54 +0300 Subject: [PATCH 012/187] Extend poa20 tests --- contracts/test/ValidatorSet.sol | 6 + .../ERC677BridgeTokenRewardableMock.sol | 22 +++ test/poa20_test.js | 176 +++++++++++++++++- 3 files changed, 198 insertions(+), 6 deletions(-) create mode 100644 contracts/test/ValidatorSet.sol create mode 100644 test/mockContracts/ERC677BridgeTokenRewardableMock.sol diff --git a/contracts/test/ValidatorSet.sol b/contracts/test/ValidatorSet.sol new file mode 100644 index 000000000..d715ffaa8 --- /dev/null +++ b/contracts/test/ValidatorSet.sol @@ -0,0 +1,6 @@ +pragma solidity 0.4.24; + + +contract ValidatorSet { + constructor() {} +} diff --git a/test/mockContracts/ERC677BridgeTokenRewardableMock.sol b/test/mockContracts/ERC677BridgeTokenRewardableMock.sol new file mode 100644 index 000000000..7edad2fc3 --- /dev/null +++ b/test/mockContracts/ERC677BridgeTokenRewardableMock.sol @@ -0,0 +1,22 @@ +pragma solidity 0.4.24; + +import '../../contracts/ERC677BridgeTokenRewardable.sol'; + + +contract ERC677BridgeTokenRewardableMock is ERC677BridgeTokenRewardable { + + constructor( + string _name, + string _symbol, + uint8 _decimals + ) public ERC677BridgeTokenRewardable(_name, _symbol, _decimals) {} + + function setBlockRewardContractMock(address _blockRewardContract) public { + blockRewardContract = _blockRewardContract; + } + + function setValidatorSetContractMock(address _validatorSetContract) public { + validatorSetContract = _validatorSetContract; + } + +} diff --git a/test/poa20_test.js b/test/poa20_test.js index f4d1d4c82..c5c2ba663 100644 --- a/test/poa20_test.js +++ b/test/poa20_test.js @@ -1,5 +1,8 @@ const POA20 = artifacts.require("ERC677BridgeToken.sol"); +const POA20RewardableMock = artifacts.require("./mockContracts/ERC677BridgeTokenRewardableMock"); const ERC677ReceiverTest = artifacts.require("ERC677ReceiverTest.sol") +const BlockRewardTest = artifacts.require("BlockReward.sol") +const ValidatorSetTest = artifacts.require("ValidatorSet.sol") const { ERROR_MSG, ZERO_ADDRESS} = require('./setup'); const Web3Utils = require('web3-utils'); const HomeErcToErcBridge = artifacts.require("HomeBridgeErcToErc.sol"); @@ -11,12 +14,13 @@ const gasPrice = Web3Utils.toWei('1', 'gwei'); const oneEther = web3.toBigNumber(web3.toWei(1, "ether")); const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")); -contract('ERC677BridgeToken', async (accounts) => { +async function testERC677BridgeToken(accounts, rewardable) { let token let owner = accounts[0] const user = accounts[1]; + const tokenContract = rewardable ? POA20RewardableMock : POA20; beforeEach(async () => { - token = await POA20.new("POA ERC20 Foundation", "POA20", 18); + token = await tokenContract.new("POA ERC20 Foundation", "POA20", 18); }) it('default values', async () => { @@ -74,6 +78,160 @@ contract('ERC677BridgeToken', async (accounts) => { }) }) + if (rewardable) { + describe('#blockRewardContract', async() => { + it('can set BlockReward contract', async () => { + const blockRewardContract = await BlockRewardTest.new(); + (await token.blockRewardContract()).should.be.equal(ZERO_ADDRESS); + + await token.setBlockRewardContract(blockRewardContract.address).should.be.fulfilled; + + (await token.blockRewardContract()).should.be.equal(blockRewardContract.address); + }) + + it('only owner can set BlockReward contract', async () => { + const blockRewardContract = await BlockRewardTest.new(); + (await token.blockRewardContract()).should.be.equal(ZERO_ADDRESS); + + await token.setBlockRewardContract(blockRewardContract.address, {from: user }).should.be.rejectedWith(ERROR_MSG); + (await token.blockRewardContract()).should.be.equal(ZERO_ADDRESS); + + await token.setBlockRewardContract(blockRewardContract.address, {from: owner }).should.be.fulfilled; + (await token.blockRewardContract()).should.be.equal(blockRewardContract.address); + }) + + it('fail to set invalid BlockReward contract address', async () => { + const invalidContractAddress = '0xaaB52d66283F7A1D5978bcFcB55721ACB467384b'; + (await token.blockRewardContract()).should.be.equal(ZERO_ADDRESS); + + await token.setBlockRewardContract(invalidContractAddress).should.be.rejectedWith(ERROR_MSG); + (await token.blockRewardContract()).should.be.equal(ZERO_ADDRESS); + + await token.setBlockRewardContract(ZERO_ADDRESS).should.be.rejectedWith(ERROR_MSG); + (await token.blockRewardContract()).should.be.equal(ZERO_ADDRESS); + }) + }) + + describe('#validatorSetContract', async() => { + it('can set ValidatorSet contract', async () => { + const validatorSetContract = await ValidatorSetTest.new(); + (await token.validatorSetContract()).should.be.equal(ZERO_ADDRESS); + + await token.setValidatorSetContract(validatorSetContract.address).should.be.fulfilled; + + (await token.validatorSetContract()).should.be.equal(validatorSetContract.address); + }) + + it('only owner can set ValidatorSet contract', async () => { + const validatorSetContract = await ValidatorSetTest.new(); + (await token.validatorSetContract()).should.be.equal(ZERO_ADDRESS); + + await token.setValidatorSetContract(validatorSetContract.address, {from: user }).should.be.rejectedWith(ERROR_MSG); + (await token.validatorSetContract()).should.be.equal(ZERO_ADDRESS); + + await token.setValidatorSetContract(validatorSetContract.address, {from: owner }).should.be.fulfilled; + (await token.validatorSetContract()).should.be.equal(validatorSetContract.address); + }) + + it('fail to set invalid ValidatorSet contract address', async () => { + const invalidContractAddress = '0xaaB52d66283F7A1D5978bcFcB55721ACB467384b'; + (await token.validatorSetContract()).should.be.equal(ZERO_ADDRESS); + + await token.setValidatorSetContract(invalidContractAddress).should.be.rejectedWith(ERROR_MSG); + (await token.validatorSetContract()).should.be.equal(ZERO_ADDRESS); + + await token.setValidatorSetContract(ZERO_ADDRESS).should.be.rejectedWith(ERROR_MSG); + (await token.validatorSetContract()).should.be.equal(ZERO_ADDRESS); + }) + }) + + describe('#mintReward', async() => { + it('can only be called by BlockReward contract', async () => { + await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled; + await token.mintReward([], [], {from: user }).should.be.rejectedWith(ERROR_MSG); + await token.mintReward([], [], {from: accounts[2] }).should.be.fulfilled; + }) + it('should increase totalSupply and balances', async () => { + const user1 = accounts[1]; + const user2 = accounts[2]; + const user3 = accounts[3]; + + assert.equal(await token.totalSupply(), 0); + (await token.balanceOf(user1)).should.be.bignumber.equal(0); + (await token.balanceOf(user2)).should.be.bignumber.equal(0); + (await token.balanceOf(user3)).should.be.bignumber.equal(0); + + await token.setBlockRewardContractMock(accounts[4]).should.be.fulfilled; + await token.mintReward([user1, user2, user3], [100, 200, 300], {from: accounts[4] }).should.be.fulfilled; + + assert.equal(await token.totalSupply(), 600); + (await token.balanceOf(user1)).should.be.bignumber.equal(100); + (await token.balanceOf(user2)).should.be.bignumber.equal(200); + (await token.balanceOf(user3)).should.be.bignumber.equal(300); + }) + }) + + describe('#stake', async() => { + it('can only be called by ValidatorSet contract', async () => { + await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled; + await token.mintReward([user], [100], {from: accounts[2] }).should.be.fulfilled; + await token.setValidatorSetContractMock(accounts[3]).should.be.fulfilled; + await token.stake(user, 100, {from: accounts[4] }).should.be.rejectedWith(ERROR_MSG); + await token.stake(user, 100, {from: accounts[3] }).should.be.fulfilled; + }) + it('should revert if user doesn\'t have enough balance', async () => { + await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled; + await token.mintReward([user], [99], {from: accounts[2] }).should.be.fulfilled; + (await token.balanceOf(user)).should.be.bignumber.equal(99); + await token.setValidatorSetContractMock(accounts[3]).should.be.fulfilled; + await token.stake(user, 100, {from: accounts[3] }).should.be.rejectedWith(ERROR_MSG); + }) + it('should decrease user\'s balance and increase ValidatorSet\'s balance', async () => { + await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled; + await token.mintReward([user], [100], {from: accounts[2] }).should.be.fulfilled; + (await token.balanceOf(user)).should.be.bignumber.equal(100); + (await token.balanceOf(accounts[3])).should.be.bignumber.equal(0); + await token.setValidatorSetContractMock(accounts[3]).should.be.fulfilled; + await token.stake(user, 100, {from: accounts[3] }).should.be.fulfilled; + (await token.balanceOf(user)).should.be.bignumber.equal(0); + (await token.balanceOf(accounts[3])).should.be.bignumber.equal(100); + }) + }) + + describe('#withdraw', async() => { + it('can only be called by ValidatorSet contract', async () => { + await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled; + await token.mintReward([user], [100], {from: accounts[2] }).should.be.fulfilled; + await token.setValidatorSetContractMock(accounts[3]).should.be.fulfilled; + await token.stake(user, 100, {from: accounts[3] }).should.be.fulfilled; + await token.withdraw(user, 100, {from: accounts[4] }).should.be.rejectedWith(ERROR_MSG); + await token.withdraw(user, 100, {from: accounts[3] }).should.be.fulfilled; + }) + it('should revert if ValidatorSet doesn\'t have enough balance', async () => { + await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled; + await token.mintReward([user], [100], {from: accounts[2] }).should.be.fulfilled; + (await token.balanceOf(user)).should.be.bignumber.equal(100); + await token.setValidatorSetContractMock(accounts[3]).should.be.fulfilled; + await token.stake(user, 100, {from: accounts[3] }).should.be.fulfilled; + await token.withdraw(user, 101, {from: accounts[3] }).should.be.rejectedWith(ERROR_MSG); + await token.withdraw(user, 100, {from: accounts[3] }).should.be.fulfilled; + }) + it('should decrease ValidatorSet\'s balance and increase user\'s balance', async () => { + await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled; + await token.mintReward([user], [100], {from: accounts[2] }).should.be.fulfilled; + (await token.balanceOf(user)).should.be.bignumber.equal(100); + (await token.balanceOf(accounts[3])).should.be.bignumber.equal(0); + await token.setValidatorSetContractMock(accounts[3]).should.be.fulfilled; + await token.stake(user, 100, {from: accounts[3] }).should.be.fulfilled; + (await token.balanceOf(user)).should.be.bignumber.equal(0); + (await token.balanceOf(accounts[3])).should.be.bignumber.equal(100); + await token.withdraw(user, 60, {from: accounts[3] }).should.be.fulfilled; + (await token.balanceOf(user)).should.be.bignumber.equal(60); + (await token.balanceOf(accounts[3])).should.be.bignumber.equal(40); + }) + }) + } + describe('#mint', async() => { it('can mint by owner', async () => { (await token.totalSupply()).should.be.bignumber.equal(0); @@ -260,7 +418,7 @@ contract('ERC677BridgeToken', async (accounts) => { it('can take send ERC20 tokens', async ()=> { const owner = accounts[0]; const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")); - let tokenSecond = await POA20.new("Roman Token", "RST", 18); + let tokenSecond = await tokenContract.new("Roman Token", "RST", 18); await tokenSecond.mint(accounts[0], halfEther).should.be.fulfilled; halfEther.should.be.bignumber.equal(await tokenSecond.balanceOf(accounts[0])) @@ -271,7 +429,6 @@ contract('ERC677BridgeToken', async (accounts) => { await token.claimTokens(tokenSecond.address, accounts[3], {from: owner}); '0'.should.be.bignumber.equal(await tokenSecond.balanceOf(token.address)) halfEther.should.be.bignumber.equal(await tokenSecond.balanceOf(accounts[3])) - }) }) describe('#transfer', async () => { @@ -293,7 +450,7 @@ contract('ERC677BridgeToken', async (accounts) => { logs[0].event.should.be.equal("Transfer") }) it('if transfer called on contract, still works even if onTokenTransfer doesnot exist', async () => { - const someContract = await POA20.new("Some", "Token", 18); + const someContract = await tokenContract.new("Some", "Token", 18); await token.mint(user, 2, {from: owner }).should.be.fulfilled; const tokenTransfer = await token.transfer(someContract.address, 1, {from: user}).should.be.fulfilled; const tokenTransfer2 = await token.transfer(accounts[0], 1, {from: user}).should.be.fulfilled; @@ -301,7 +458,14 @@ contract('ERC677BridgeToken', async (accounts) => { (await token.balanceOf(user)).should.be.bignumber.equal(0); tokenTransfer.logs[0].event.should.be.equal("Transfer") tokenTransfer2.logs[0].event.should.be.equal("Transfer") - }) }) +} + +contract('ERC677BridgeToken', async (accounts) => { + await testERC677BridgeToken(accounts, false); +}) + +contract('ERC677BridgeTokenRewardable', async (accounts) => { + await testERC677BridgeToken(accounts, true); }) From 76d45e2861d8dfd91ce99beaa41736a408dd427d Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Thu, 3 Jan 2019 13:07:21 -0300 Subject: [PATCH 013/187] Add validatorList method --- contracts/IBridgeValidators.sol | 2 +- .../upgradeable_contracts/BridgeValidators.sol | 14 ++++++++++++++ test/validators_test.js | 14 ++++++++++++++ 3 files changed, 29 insertions(+), 1 deletion(-) diff --git a/contracts/IBridgeValidators.sol b/contracts/IBridgeValidators.sol index 18098cd13..0c9f877c6 100644 --- a/contracts/IBridgeValidators.sol +++ b/contracts/IBridgeValidators.sol @@ -5,6 +5,6 @@ interface IBridgeValidators { function isValidator(address _validator) public view returns(bool); function requiredSignatures() public view returns(uint256); function owner() public view returns(address); - function getNextValidator(address _validator) public view returns(address); function getValidatorRewardAddress(address _validator) public view returns(address); + function validatorList() public view returns (address[]); } diff --git a/contracts/upgradeable_contracts/BridgeValidators.sol b/contracts/upgradeable_contracts/BridgeValidators.sol index f88b43e41..b03728e99 100644 --- a/contracts/upgradeable_contracts/BridgeValidators.sol +++ b/contracts/upgradeable_contracts/BridgeValidators.sol @@ -142,6 +142,20 @@ contract BridgeValidators is IBridgeValidators, EternalStorage, Ownable { return addressStorage[keccak256(abi.encodePacked("validatorsList", _address))]; } + function validatorList() public view returns (address[]) { + address [] memory list = new address[](validatorCount()); + uint256 counter = 0; + address nextValidator = getNextValidator(F_ADDR); + + while (nextValidator != F_ADDR) { + list[counter] = nextValidator; + nextValidator = getNextValidator(nextValidator); + counter++; + } + + return list; + } + function setValidatorRewardAddress(address _validator, address _reward) internal { addressStorage[keccak256(abi.encodePacked("validatorsRewards", _validator))] = _reward; } diff --git a/test/validators_test.js b/test/validators_test.js index 68e9173b0..137fee13c 100644 --- a/test/validators_test.js +++ b/test/validators_test.js @@ -228,4 +228,18 @@ contract('BridgeValidators', async (accounts) => { } }) }) + describe('#Validators list', () => { + it('should return validators list', async () => { + // Given + const validators = accounts.slice(0, 5) + const { initialize, validatorList } = bridgeValidators + await initialize(1, validators, accounts.slice(5), owner, { from: owner }).should.be.fulfilled + + // When + const returnedList = await validatorList() + + // Then + returnedList.should.be.eql(validators) + }) + }) }) From 349bbbb355d9ee155eefc53886780a4e6f3f7f4c Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 7 Jan 2019 11:03:49 -0300 Subject: [PATCH 014/187] Update BridgeValidators version --- contracts/upgradeable_contracts/BridgeValidators.sol | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/contracts/upgradeable_contracts/BridgeValidators.sol b/contracts/upgradeable_contracts/BridgeValidators.sol index b03728e99..3772c43da 100644 --- a/contracts/upgradeable_contracts/BridgeValidators.sol +++ b/contracts/upgradeable_contracts/BridgeValidators.sol @@ -111,7 +111,7 @@ contract BridgeValidators is IBridgeValidators, EternalStorage, Ownable { pure returns (uint64 major, uint64 minor, uint64 patch) { - return (2, 0, 0); + return (2, 1, 0); } function requiredSignatures() public view returns (uint256) { From 363a304ef91e153b0769ee3d989780a0b9be35bc Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 7 Jan 2019 11:46:04 -0300 Subject: [PATCH 015/187] Add removed nextValidator test --- test/validators_test.js | 20 ++++++++++++++++++++ 1 file changed, 20 insertions(+) diff --git a/test/validators_test.js b/test/validators_test.js index 137fee13c..1ce4214a3 100644 --- a/test/validators_test.js +++ b/test/validators_test.js @@ -182,6 +182,26 @@ contract('BridgeValidators', async (accounts) => { logs[0].args.should.be.deep.equal({ validator: accounts[0] }) }) + it(`Removed validator should return zero address on nextValidator`, async () => { + // Given + const { initialize, isInitialized, removeValidator, getNextValidator } = bridgeValidators + await initialize(1, accounts.slice(0, 2), accounts.slice(2, 4), owner, { from: owner }).should.be.fulfilled + true.should.be.equal(await isInitialized()) + const initialNextValidator = await getNextValidator(accounts[0]) + + // When + const { logs } = await removeValidator(accounts[0], { from: owner }).should.be.fulfilled + + // Then + logs[0].event.should.be.equal('ValidatorRemoved') + logs[0].args.should.be.deep.equal({ validator: accounts[0] }) + + const updatedNextValidator = await getNextValidator(accounts[0]) + + initialNextValidator.should.be.equals(accounts[1]) + updatedNextValidator.should.be.equals(ZERO_ADDRESS) + }) + accounts.slice(0, 5).forEach(validator => { it(`should remove ${validator} - with Proxy`, async () => { // Given From 4e9db7b626ef73a847b019247865d9f0ae1d53d4 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 7 Jan 2019 15:25:26 -0300 Subject: [PATCH 016/187] Refactor BridgeValidators --- contracts/IBridgeValidators.sol | 1 - contracts/IRewardableValidators.sol | 10 + .../BaseBridgeValidators.sol | 86 ++++++ .../BridgeValidators.sol | 100 +------ .../RewardableValidators.sol | 99 +++++++ test/erc_to_erc/foreign_bridge.test.js | 16 +- test/erc_to_erc/home_bridge.test.js | 22 +- test/erc_to_native/foreign_bridge.test.js | 16 +- test/erc_to_native/home_bridge.test.js | 19 +- test/native_to_erc/foreign_bridge_test.js | 14 +- test/native_to_erc/home_bridge_test.js | 22 +- test/poa20_test.js | 6 +- test/rewardable_validators_test.js | 265 ++++++++++++++++++ test/validators_test.js | 60 ++-- 14 files changed, 521 insertions(+), 215 deletions(-) create mode 100644 contracts/IRewardableValidators.sol create mode 100644 contracts/upgradeable_contracts/BaseBridgeValidators.sol create mode 100644 contracts/upgradeable_contracts/RewardableValidators.sol create mode 100644 test/rewardable_validators_test.js diff --git a/contracts/IBridgeValidators.sol b/contracts/IBridgeValidators.sol index 0c9f877c6..51fd06bf2 100644 --- a/contracts/IBridgeValidators.sol +++ b/contracts/IBridgeValidators.sol @@ -5,6 +5,5 @@ interface IBridgeValidators { function isValidator(address _validator) public view returns(bool); function requiredSignatures() public view returns(uint256); function owner() public view returns(address); - function getValidatorRewardAddress(address _validator) public view returns(address); function validatorList() public view returns (address[]); } diff --git a/contracts/IRewardableValidators.sol b/contracts/IRewardableValidators.sol new file mode 100644 index 000000000..5240c5d0a --- /dev/null +++ b/contracts/IRewardableValidators.sol @@ -0,0 +1,10 @@ +pragma solidity 0.4.24; + + +interface IRewardableValidators { + function isValidator(address _validator) public view returns(bool); + function requiredSignatures() public view returns(uint256); + function owner() public view returns(address); + function validatorList() public view returns (address[]); + function getValidatorRewardAddress(address _validator) public view returns(address); +} diff --git a/contracts/upgradeable_contracts/BaseBridgeValidators.sol b/contracts/upgradeable_contracts/BaseBridgeValidators.sol new file mode 100644 index 000000000..bd752d2c9 --- /dev/null +++ b/contracts/upgradeable_contracts/BaseBridgeValidators.sol @@ -0,0 +1,86 @@ +pragma solidity 0.4.24; + +import "./Ownable.sol"; +import "../libraries/SafeMath.sol"; +import "../upgradeability/EternalStorage.sol"; + + +contract BaseBridgeValidators is EternalStorage, Ownable { + using SafeMath for uint256; + + address public constant F_ADDR = 0xFFfFfFffFFfffFFfFFfFFFFFffFFFffffFfFFFfF; + + event RequiredSignaturesChanged (uint256 requiredSignatures); + + function setRequiredSignatures(uint256 _requiredSignatures) + external + onlyOwner + { + require(validatorCount() >= _requiredSignatures); + require(_requiredSignatures != 0); + uintStorage[keccak256(abi.encodePacked("requiredSignatures"))] = _requiredSignatures; + emit RequiredSignaturesChanged(_requiredSignatures); + } + + function getBridgeValidatorsInterfacesVersion() + public + pure + returns (uint64 major, uint64 minor, uint64 patch) + { + return (2, 1, 0); + } + + function requiredSignatures() public view returns (uint256) { + return uintStorage[keccak256(abi.encodePacked("requiredSignatures"))]; + } + + function validatorCount() public view returns (uint256) { + return uintStorage[keccak256(abi.encodePacked("validatorCount"))]; + } + + function isValidator(address _validator) public view returns (bool) { + return _validator != F_ADDR && getNextValidator(_validator) != address(0); + } + + function isInitialized() public view returns (bool) { + return boolStorage[keccak256(abi.encodePacked("isInitialized"))]; + } + + function deployedAtBlock() public view returns (uint256) { + return uintStorage[keccak256("deployedAtBlock")]; + } + + function getNextValidator(address _address) public view returns (address) { + return addressStorage[keccak256(abi.encodePacked("validatorsList", _address))]; + } + + function validatorList() public view returns (address[]) { + address [] memory list = new address[](validatorCount()); + uint256 counter = 0; + address nextValidator = getNextValidator(F_ADDR); + + while (nextValidator != F_ADDR) { + list[counter] = nextValidator; + nextValidator = getNextValidator(nextValidator); + counter++; + } + + return list; + } + + function deleteItemFromAddressStorage(string _mapName, address _address) internal { + delete addressStorage[keccak256(abi.encodePacked(_mapName, _address))]; + } + + function setValidatorCount(uint256 _validatorCount) internal { + uintStorage[keccak256(abi.encodePacked("validatorCount"))] = _validatorCount; + } + + function setValidator(address _prevValidator, address _validator) internal { + addressStorage[keccak256(abi.encodePacked("validatorsList", _prevValidator))] = _validator; + } + + function setInitialize(bool _status) internal { + boolStorage[keccak256(abi.encodePacked("isInitialized"))] = _status; + } +} diff --git a/contracts/upgradeable_contracts/BridgeValidators.sol b/contracts/upgradeable_contracts/BridgeValidators.sol index 3772c43da..f1278440c 100644 --- a/contracts/upgradeable_contracts/BridgeValidators.sol +++ b/contracts/upgradeable_contracts/BridgeValidators.sol @@ -1,24 +1,16 @@ pragma solidity 0.4.24; -import "./Ownable.sol"; -import "../IBridgeValidators.sol"; -import "../libraries/SafeMath.sol"; -import "../upgradeability/EternalStorage.sol"; +import "./BaseBridgeValidators.sol"; -contract BridgeValidators is IBridgeValidators, EternalStorage, Ownable { - using SafeMath for uint256; - - address public constant F_ADDR = 0xFFfFfFffFFfffFFfFFfFFFFFffFFFffffFfFFFfF; +contract BridgeValidators is BaseBridgeValidators { event ValidatorAdded (address indexed validator); event ValidatorRemoved (address indexed validator); - event RequiredSignaturesChanged (uint256 requiredSignatures); function initialize( uint256 _requiredSignatures, address[] _initialValidators, - address[] _initialRewards, address _owner ) public @@ -29,11 +21,9 @@ contract BridgeValidators is IBridgeValidators, EternalStorage, Ownable { setOwner(_owner); require(_requiredSignatures != 0); require(_initialValidators.length >= _requiredSignatures); - require(_initialValidators.length == _initialRewards.length); for (uint256 i = 0; i < _initialValidators.length; i++) { require(_initialValidators[i] != address(0) && _initialValidators[i] != F_ADDR); - require(_initialRewards[i] != address(0)); require(!isValidator(_initialValidators[i])); if (i == 0) { @@ -49,7 +39,6 @@ contract BridgeValidators is IBridgeValidators, EternalStorage, Ownable { } setValidatorCount(validatorCount().add(1)); - setValidatorRewardAddress(_initialValidators[i], _initialRewards[i]); emit ValidatorAdded(_initialValidators[i]); } @@ -61,14 +50,12 @@ contract BridgeValidators is IBridgeValidators, EternalStorage, Ownable { return isInitialized(); } - function addValidator(address _validator, address _reward) external onlyOwner { + function addValidator(address _validator) external onlyOwner { require(_validator != address(0) && _validator != F_ADDR); - require(_reward != address(0)); require(!isValidator(_validator)); address firstValidator = getNextValidator(F_ADDR); setValidator(_validator, firstValidator); - setValidatorRewardAddress(_validator, _reward); setValidator(F_ADDR, _validator); setValidatorCount(validatorCount().add(1)); @@ -90,89 +77,8 @@ contract BridgeValidators is IBridgeValidators, EternalStorage, Ownable { setValidator(index, validatorsNext); deleteItemFromAddressStorage("validatorsList", _validator); - deleteItemFromAddressStorage("validatorsRewards", _validator); setValidatorCount(validatorCount().sub(1)); emit ValidatorRemoved(_validator); } - - function setRequiredSignatures(uint256 _requiredSignatures) - external - onlyOwner - { - require(validatorCount() >= _requiredSignatures); - require(_requiredSignatures != 0); - uintStorage[keccak256(abi.encodePacked("requiredSignatures"))] = _requiredSignatures; - emit RequiredSignaturesChanged(_requiredSignatures); - } - - function getBridgeValidatorsInterfacesVersion() - public - pure - returns (uint64 major, uint64 minor, uint64 patch) - { - return (2, 1, 0); - } - - function requiredSignatures() public view returns (uint256) { - return uintStorage[keccak256(abi.encodePacked("requiredSignatures"))]; - } - - function validatorCount() public view returns (uint256) { - return uintStorage[keccak256(abi.encodePacked("validatorCount"))]; - } - - function isValidator(address _validator) public view returns (bool) { - return _validator != F_ADDR && getNextValidator(_validator) != address(0); - } - - function isInitialized() public view returns (bool) { - return boolStorage[keccak256(abi.encodePacked("isInitialized"))]; - } - - function deployedAtBlock() public view returns (uint256) { - return uintStorage[keccak256("deployedAtBlock")]; - } - - function getValidatorRewardAddress(address _validator) public view returns (address) { - return addressStorage[keccak256(abi.encodePacked("validatorsRewards", _validator))]; - } - - function getNextValidator(address _address) public view returns (address) { - return addressStorage[keccak256(abi.encodePacked("validatorsList", _address))]; - } - - function validatorList() public view returns (address[]) { - address [] memory list = new address[](validatorCount()); - uint256 counter = 0; - address nextValidator = getNextValidator(F_ADDR); - - while (nextValidator != F_ADDR) { - list[counter] = nextValidator; - nextValidator = getNextValidator(nextValidator); - counter++; - } - - return list; - } - - function setValidatorRewardAddress(address _validator, address _reward) internal { - addressStorage[keccak256(abi.encodePacked("validatorsRewards", _validator))] = _reward; - } - - function deleteItemFromAddressStorage(string _mapName, address _address) private { - delete addressStorage[keccak256(abi.encodePacked(_mapName, _address))]; - } - - function setValidatorCount(uint256 _validatorCount) private { - uintStorage[keccak256(abi.encodePacked("validatorCount"))] = _validatorCount; - } - - function setValidator(address _prevValidator, address _validator) private { - addressStorage[keccak256(abi.encodePacked("validatorsList", _prevValidator))] = _validator; - } - - function setInitialize(bool _status) private { - boolStorage[keccak256(abi.encodePacked("isInitialized"))] = _status; - } } diff --git a/contracts/upgradeable_contracts/RewardableValidators.sol b/contracts/upgradeable_contracts/RewardableValidators.sol new file mode 100644 index 000000000..2f04ca90e --- /dev/null +++ b/contracts/upgradeable_contracts/RewardableValidators.sol @@ -0,0 +1,99 @@ +pragma solidity 0.4.24; + +import "./BaseBridgeValidators.sol"; + + +contract RewardableValidators is BaseBridgeValidators { + + event ValidatorAdded (address indexed validator); + event ValidatorRemoved (address indexed validator); + + function initialize( + uint256 _requiredSignatures, + address[] _initialValidators, + address[] _initialRewards, + address _owner + ) + public + returns (bool) + { + require(!isInitialized()); + require(_owner != address(0)); + setOwner(_owner); + require(_requiredSignatures != 0); + require(_initialValidators.length >= _requiredSignatures); + require(_initialValidators.length == _initialRewards.length); + + for (uint256 i = 0; i < _initialValidators.length; i++) { + require(_initialValidators[i] != address(0) && _initialValidators[i] != F_ADDR); + require(_initialRewards[i] != address(0)); + require(!isValidator(_initialValidators[i])); + + if (i == 0) { + setValidator(F_ADDR, _initialValidators[i]); + if (_initialValidators.length == 1) { + setValidator(_initialValidators[i], F_ADDR); + } + } else if (i == _initialValidators.length - 1) { + setValidator(_initialValidators[i - 1], _initialValidators[i]); + setValidator(_initialValidators[i], F_ADDR); + } else { + setValidator(_initialValidators[i - 1], _initialValidators[i]); + } + + setValidatorCount(validatorCount().add(1)); + setValidatorRewardAddress(_initialValidators[i], _initialRewards[i]); + emit ValidatorAdded(_initialValidators[i]); + } + + uintStorage[keccak256(abi.encodePacked("requiredSignatures"))] = _requiredSignatures; + uintStorage[keccak256("deployedAtBlock")] = block.number; + setInitialize(true); + emit RequiredSignaturesChanged(_requiredSignatures); + + return isInitialized(); + } + + function addValidator(address _validator, address _reward) external onlyOwner { + require(_validator != address(0) && _validator != F_ADDR); + require(_reward != address(0)); + require(!isValidator(_validator)); + + address firstValidator = getNextValidator(F_ADDR); + setValidator(_validator, firstValidator); + setValidatorRewardAddress(_validator, _reward); + setValidator(F_ADDR, _validator); + + setValidatorCount(validatorCount().add(1)); + emit ValidatorAdded(_validator); + } + + function removeValidator(address _validator) external onlyOwner { + require(validatorCount() > requiredSignatures()); + require(isValidator(_validator)); + address validatorsNext = getNextValidator(_validator); + address index = F_ADDR; + address next = getNextValidator(index); + + // find the element in the list pointing to _validator + while (next != _validator) { + index = next; + next = getNextValidator(index); + } + + setValidator(index, validatorsNext); + deleteItemFromAddressStorage("validatorsList", _validator); + deleteItemFromAddressStorage("validatorsRewards", _validator); + setValidatorCount(validatorCount().sub(1)); + + emit ValidatorRemoved(_validator); + } + + function getValidatorRewardAddress(address _validator) public view returns (address) { + return addressStorage[keccak256(abi.encodePacked("validatorsRewards", _validator))]; + } + + function setValidatorRewardAddress(address _validator, address _reward) internal { + addressStorage[keccak256(abi.encodePacked("validatorsRewards", _validator))] = _reward; + } +} diff --git a/test/erc_to_erc/foreign_bridge.test.js b/test/erc_to_erc/foreign_bridge.test.js index f47ff509b..0a24d9614 100644 --- a/test/erc_to_erc/foreign_bridge.test.js +++ b/test/erc_to_erc/foreign_bridge.test.js @@ -11,13 +11,12 @@ const requireBlockConfirmations = 8; const gasPrice = web3.toWei('1', 'gwei') contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { - let validatorContract, authorities, rewards, owner, token; + let validatorContract, authorities, owner, token; before(async () => { validatorContract = await BridgeValidators.new() authorities = [accounts[1], accounts[2]]; - rewards = [accounts[3], accounts[4]]; owner = accounts[0] - await validatorContract.initialize(1, authorities, rewards, owner) + await validatorContract.initialize(1, authorities, owner) }) describe('#initialize', async () => { @@ -138,16 +137,15 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { }) describe('#withdraw with 2 minimum signatures', async () => { - let multisigValidatorContract, twoAuthorities, twoRewards, ownerOfValidatorContract, foreignBridgeWithMultiSignatures + let multisigValidatorContract, twoAuthorities, ownerOfValidatorContract, foreignBridgeWithMultiSignatures var value = web3.toBigNumber(web3.toWei(0.5, "ether")); beforeEach(async () => { multisigValidatorContract = await BridgeValidators.new() token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); twoAuthorities = [accounts[0], accounts[1]]; - twoRewards = [accounts[2], accounts[3]]; ownerOfValidatorContract = accounts[3] const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")); - await multisigValidatorContract.initialize(2, twoAuthorities, twoRewards, ownerOfValidatorContract, {from: ownerOfValidatorContract}) + await multisigValidatorContract.initialize(2, twoAuthorities, ownerOfValidatorContract, {from: ownerOfValidatorContract}) foreignBridgeWithMultiSignatures = await ForeignBridge.new() const oneEther = web3.toBigNumber(web3.toWei(1, "ether")); await foreignBridgeWithMultiSignatures.initialize(multisigValidatorContract.address, token.address, requireBlockConfirmations, gasPrice, {from: ownerOfValidatorContract}); @@ -187,10 +185,9 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { it('works with 5 validators and 3 required signatures', async () => { const recipient = accounts[8] const authoritiesFiveAccs = [accounts[1], accounts[2], accounts[3], accounts[4], accounts[5]] - const rewardsFiveAccs = [accounts[6], accounts[7], accounts[8], accounts[9], accounts[0]] const ownerOfValidators = accounts[0] const validatorContractWith3Signatures = await BridgeValidators.new() - await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, rewardsFiveAccs, ownerOfValidators) + await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) const erc20Token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); const value = web3.toBigNumber(web3.toWei(0.5, "ether")); const foreignBridgeWithThreeSigs = await ForeignBridge.new() @@ -226,7 +223,6 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { it('can be upgraded', async () => { const REQUIRED_NUMBER_OF_VALIDATORS = 1 const VALIDATORS = [accounts[1]] - const REWARDS = [accounts[2]] const PROXY_OWNER = accounts[0] // Validators Contract let validatorsProxy = await EternalStorageProxy.new().should.be.fulfilled; @@ -235,7 +231,7 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { validatorsContractImpl.address.should.be.equal(await validatorsProxy.implementation()) validatorsProxy = await BridgeValidators.at(validatorsProxy.address); - await validatorsProxy.initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, REWARDS, PROXY_OWNER).should.be.fulfilled; + await validatorsProxy.initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, PROXY_OWNER).should.be.fulfilled; let token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); // ForeignBridge V1 Contract diff --git a/test/erc_to_erc/home_bridge.test.js b/test/erc_to_erc/home_bridge.test.js index 92e8d673b..781df6a98 100644 --- a/test/erc_to_erc/home_bridge.test.js +++ b/test/erc_to_erc/home_bridge.test.js @@ -13,13 +13,12 @@ const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")); contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { - let homeContract, validatorContract, authorities, rewards, owner, token; + let homeContract, validatorContract, authorities, owner, token; before(async () => { validatorContract = await BridgeValidators.new() authorities = [accounts[1]]; - rewards = [accounts[2]]; owner = accounts[0] - await validatorContract.initialize(1, authorities, rewards, owner) + await validatorContract.initialize(1, authorities, owner) }) describe('#initialize', async() => { beforeEach(async () => { @@ -157,9 +156,8 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { let token2sig = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); let validatorContractWith2Signatures = await BridgeValidators.new() let authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]]; - let rewardsThreeAccs = [accounts[4], accounts[5], accounts[6]]; let ownerOfValidators = accounts[0] - await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, rewardsThreeAccs, ownerOfValidators) + await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, ownerOfValidators) let homeBridgeWithTwoSigs = await HomeBridge.new(); await homeBridgeWithTwoSigs.initialize(validatorContractWith2Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token2sig.address); await token2sig.transferOwnership(homeBridgeWithTwoSigs.address); @@ -221,9 +219,8 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { let token2sig = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); let validatorContractWith2Signatures = await BridgeValidators.new() let authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]]; - let rewardsThreeAccs = [accounts[4], accounts[5], accounts[6]]; let ownerOfValidators = accounts[0] - await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, rewardsThreeAccs, ownerOfValidators) + await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, ownerOfValidators) let homeBridgeWithTwoSigs = await HomeBridge.new(); await homeBridgeWithTwoSigs.initialize(validatorContractWith2Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token2sig.address); await token2sig.transferOwnership(homeBridgeWithTwoSigs.address); @@ -246,10 +243,9 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { it('works with 5 validators and 3 required signatures', async () => { const recipient = accounts[8] const authoritiesFiveAccs = [accounts[1], accounts[2], accounts[3], accounts[4], accounts[5]] - const rewardsFiveAccs = [accounts[6], accounts[7], accounts[8], accounts[9], accounts[0]] let ownerOfValidators = accounts[0] const validatorContractWith3Signatures = await BridgeValidators.new() - await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, rewardsFiveAccs, ownerOfValidators) + await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) const token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); const homeBridgeWithThreeSigs = await HomeBridge.new(); @@ -289,14 +285,13 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { }) describe('#submitSignature', async () => { - let validatorContractWith2Signatures,authoritiesThreeAccs,rewardsThreeAccs,ownerOfValidators,tokenPOA20,homeBridgeWithTwoSigs + let validatorContractWith2Signatures,authoritiesThreeAccs,ownerOfValidators,tokenPOA20,homeBridgeWithTwoSigs beforeEach(async () => { let token2sig = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); validatorContractWith2Signatures = await BridgeValidators.new() authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]]; - rewardsThreeAccs = [accounts[4], accounts[5], accounts[6]]; ownerOfValidators = accounts[0] - await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, rewardsThreeAccs, ownerOfValidators) + await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, ownerOfValidators) homeBridgeWithTwoSigs = await HomeBridge.new(); await homeBridgeWithTwoSigs.initialize(validatorContractWith2Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token2sig.address); await token2sig.transferOwnership(homeBridgeWithTwoSigs.address); @@ -343,9 +338,8 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { it('works with 5 validators and 3 required signatures', async () => { const recipientAccount = accounts[8] const authoritiesFiveAccs = [accounts[1], accounts[2], accounts[3], accounts[4], accounts[5]] - const rewardsFiveAccs = [accounts[6], accounts[7], accounts[8], accounts[9], accounts[0]] const validatorContractWith3Signatures = await BridgeValidators.new() - await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, rewardsFiveAccs, ownerOfValidators) + await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) const token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); const homeBridgeWithThreeSigs = await HomeBridge.new(); diff --git a/test/erc_to_native/foreign_bridge.test.js b/test/erc_to_native/foreign_bridge.test.js index c1be28577..fa49de156 100644 --- a/test/erc_to_native/foreign_bridge.test.js +++ b/test/erc_to_native/foreign_bridge.test.js @@ -11,13 +11,12 @@ const requireBlockConfirmations = 8; const gasPrice = web3.toWei('1', 'gwei'); contract('ForeignBridge_ERC20_to_Native', async (accounts) => { - let validatorContract, authorities, rewards, owner, token; + let validatorContract, authorities, owner, token; before(async () => { validatorContract = await BridgeValidators.new() authorities = [accounts[1], accounts[2]]; - rewards = [accounts[3], accounts[4]]; owner = accounts[0] - await validatorContract.initialize(1, authorities, rewards, owner) + await validatorContract.initialize(1, authorities, owner) }) describe('#initialize', async () => { @@ -147,15 +146,14 @@ contract('ForeignBridge_ERC20_to_Native', async (accounts) => { }) describe('#withdraw with 2 minimum signatures', async () => { - let multisigValidatorContract, twoAuthorities, twoRewards, ownerOfValidatorContract, foreignBridgeWithMultiSignatures + let multisigValidatorContract, twoAuthorities, ownerOfValidatorContract, foreignBridgeWithMultiSignatures const value = web3.toBigNumber(web3.toWei(0.5, "ether")); beforeEach(async () => { multisigValidatorContract = await BridgeValidators.new() token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); twoAuthorities = [accounts[0], accounts[1]]; - twoRewards = [accounts[8], accounts[9]]; ownerOfValidatorContract = accounts[3] - await multisigValidatorContract.initialize(2, twoAuthorities, twoRewards, ownerOfValidatorContract, {from: ownerOfValidatorContract}) + await multisigValidatorContract.initialize(2, twoAuthorities, ownerOfValidatorContract, {from: ownerOfValidatorContract}) foreignBridgeWithMultiSignatures = await ForeignBridge.new() await foreignBridgeWithMultiSignatures.initialize(multisigValidatorContract.address, token.address, requireBlockConfirmations, gasPrice, {from: ownerOfValidatorContract}); await token.mint(foreignBridgeWithMultiSignatures.address,value); @@ -198,10 +196,9 @@ contract('ForeignBridge_ERC20_to_Native', async (accounts) => { it('works with 5 validators and 3 required signatures', async () => { const recipient = accounts[8] const authoritiesFiveAccs = [accounts[1], accounts[2], accounts[3], accounts[4], accounts[5]] - const rewardsFiveAccs = [accounts[6], accounts[7], accounts[8], accounts[9], accounts[0]] const ownerOfValidators = accounts[0] const validatorContractWith3Signatures = await BridgeValidators.new() - await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, rewardsFiveAccs, ownerOfValidators) + await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) const erc20Token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); const value = web3.toBigNumber(web3.toWei(0.5, "ether")); const foreignBridgeWithThreeSigs = await ForeignBridge.new() @@ -237,7 +234,6 @@ contract('ForeignBridge_ERC20_to_Native', async (accounts) => { it('can be upgraded', async () => { const REQUIRED_NUMBER_OF_VALIDATORS = 1 const VALIDATORS = [accounts[1]] - const REWARDS = [accounts[2]] const PROXY_OWNER = accounts[0] // Validators Contract let validatorsProxy = await EternalStorageProxy.new().should.be.fulfilled; @@ -246,7 +242,7 @@ contract('ForeignBridge_ERC20_to_Native', async (accounts) => { validatorsContractImpl.address.should.be.equal(await validatorsProxy.implementation()) validatorsProxy = await BridgeValidators.at(validatorsProxy.address); - await validatorsProxy.initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, REWARDS, PROXY_OWNER).should.be.fulfilled; + await validatorsProxy.initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, PROXY_OWNER).should.be.fulfilled; let token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); // ForeignBridge V1 Contract diff --git a/test/erc_to_native/home_bridge.test.js b/test/erc_to_native/home_bridge.test.js index 89588b691..2168f1f18 100644 --- a/test/erc_to_native/home_bridge.test.js +++ b/test/erc_to_native/home_bridge.test.js @@ -12,14 +12,13 @@ const oneEther = web3.toBigNumber(web3.toWei(1, "ether")); const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")); contract('HomeBridge_ERC20_to_Native', async (accounts) => { - let homeContract, validatorContract, blockRewardContract, authorities, rewards, owner; + let homeContract, validatorContract, blockRewardContract, authorities, owner; before(async () => { validatorContract = await BridgeValidators.new() blockRewardContract = await BlockReward.new() authorities = [accounts[1]] - rewards = [accounts[2]] owner = accounts[0] - await validatorContract.initialize(1, authorities, rewards, owner) + await validatorContract.initialize(1, authorities, owner) }) describe('#initialize', async() => { @@ -302,9 +301,8 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { it('test with 2 signatures required', async () => { const validatorContractWith2Signatures = await BridgeValidators.new() const authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]]; - const rewardsThreeAccs = [accounts[4], accounts[5], accounts[6]]; const ownerOfValidators = accounts[0] - await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, rewardsThreeAccs, ownerOfValidators) + await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, ownerOfValidators) const homeBridgeWithTwoSigs = await HomeBridge.new(); await homeBridgeWithTwoSigs.initialize(validatorContractWith2Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address); const recipient = accounts[5]; @@ -358,10 +356,9 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { it('works with 5 validators and 3 required signatures', async () => { const recipient = accounts[8] const authoritiesFiveAccs = [accounts[1], accounts[2], accounts[3], accounts[4], accounts[5]] - const rewardsFiveAccs = [accounts[6], accounts[7], accounts[8], accounts[9], accounts[0]] let ownerOfValidators = accounts[0] const validatorContractWith3Signatures = await BridgeValidators.new() - await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, rewardsFiveAccs, ownerOfValidators) + await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) const homeBridgeWithThreeSigs = await HomeBridge.new(); await homeBridgeWithThreeSigs.initialize(validatorContractWith3Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address); @@ -389,13 +386,12 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { }) describe('#submitSignature', async () => { - let validatorContractWith2Signatures,authoritiesThreeAccs,rewardsThreeAccs,ownerOfValidators,homeBridgeWithTwoSigs + let validatorContractWith2Signatures,authoritiesThreeAccs,ownerOfValidators,homeBridgeWithTwoSigs beforeEach(async () => { validatorContractWith2Signatures = await BridgeValidators.new() authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]]; - rewardsThreeAccs = [accounts[4], accounts[5], accounts[6]]; ownerOfValidators = accounts[0] - await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, rewardsThreeAccs, ownerOfValidators) + await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, ownerOfValidators) homeBridgeWithTwoSigs = await HomeBridge.new(); await homeBridgeWithTwoSigs.initialize(validatorContractWith2Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address); }) @@ -442,9 +438,8 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { it('works with 5 validators and 3 required signatures', async () => { const recipientAccount = accounts[8] const authoritiesFiveAccs = [accounts[1], accounts[2], accounts[3], accounts[4], accounts[5]] - const rewardsFiveAccs = [accounts[6], accounts[7], accounts[8], accounts[9], accounts[0]] const validatorContractWith3Signatures = await BridgeValidators.new() - await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, rewardsFiveAccs, ownerOfValidators) + await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) const homeBridgeWithThreeSigs = await HomeBridge.new(); await homeBridgeWithThreeSigs.initialize(validatorContractWith3Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address); diff --git a/test/native_to_erc/foreign_bridge_test.js b/test/native_to_erc/foreign_bridge_test.js index 7cc796632..35d316c3c 100644 --- a/test/native_to_erc/foreign_bridge_test.js +++ b/test/native_to_erc/foreign_bridge_test.js @@ -32,9 +32,8 @@ contract('ForeignBridge', async (accounts) => { before(async () => { validatorContract = await BridgeValidators.new() authorities = [accounts[1], accounts[2]]; - rewards = [accounts[3], accounts[4]]; owner = accounts[0] - await validatorContract.initialize(1, authorities, rewards, owner) + await validatorContract.initialize(1, authorities, owner) }) describe('#initialize', async () => { @@ -170,15 +169,14 @@ contract('ForeignBridge', async (accounts) => { }) describe('#executeSignatures with 2 minimum signatures', async () => { - let multisigValidatorContract, twoAuthorities, twoRewards, ownerOfValidatorContract, foreignBridgeWithMultiSignatures + let multisigValidatorContract, twoAuthorities, ownerOfValidatorContract, foreignBridgeWithMultiSignatures beforeEach(async () => { multisigValidatorContract = await BridgeValidators.new() token = await POA20.new("POA ERC20 Foundation", "POA20", 18); twoAuthorities = [accounts[0], accounts[1]]; - twoRewards = [accounts[2], accounts[3]]; ownerOfValidatorContract = accounts[3] const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")); - await multisigValidatorContract.initialize(2, twoAuthorities, twoRewards, ownerOfValidatorContract, {from: ownerOfValidatorContract}) + await multisigValidatorContract.initialize(2, twoAuthorities, ownerOfValidatorContract, {from: ownerOfValidatorContract}) foreignBridgeWithMultiSignatures = await ForeignBridge.new() const oneEther = web3.toBigNumber(web3.toWei(1, "ether")); await foreignBridgeWithMultiSignatures.initialize(multisigValidatorContract.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, {from: ownerOfValidatorContract}); @@ -228,10 +226,9 @@ contract('ForeignBridge', async (accounts) => { it('works with 5 validators and 3 required signatures', async () => { const recipient = accounts[8] const authoritiesFiveAccs = [accounts[1], accounts[2], accounts[3], accounts[4], accounts[5]] - const rewardsFiveAccs = [accounts[6], accounts[7], accounts[8], accounts[9], accounts[0]] const ownerOfValidators = accounts[0] const validatorContractWith3Signatures = await BridgeValidators.new() - await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, rewardsFiveAccs, ownerOfValidators) + await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) const erc20Token = await POA20.new("Some ERC20", "RSZT", 18); const value = web3.toBigNumber(web3.toWei(0.5, "ether")); const foreignBridgeWithThreeSigs = await ForeignBridge.new() @@ -364,7 +361,6 @@ contract('ForeignBridge', async (accounts) => { it('can be upgraded', async () => { const REQUIRED_NUMBER_OF_VALIDATORS = 1 const VALIDATORS = [accounts[1]] - const REWARDS = [accounts[2]] const PROXY_OWNER = accounts[0] const FOREIGN_DAILY_LIMIT = oneEther; const FOREIGN_MAX_AMOUNT_PER_TX = halfEther; @@ -376,7 +372,7 @@ contract('ForeignBridge', async (accounts) => { validatorsContractImpl.address.should.be.equal(await validatorsProxy.implementation()) validatorsProxy = await BridgeValidators.at(validatorsProxy.address); - await validatorsProxy.initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, REWARDS, PROXY_OWNER).should.be.fulfilled; + await validatorsProxy.initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, PROXY_OWNER).should.be.fulfilled; // POA20 let token = await POA20.new("POA ERC20 Foundation", "POA20", 18); diff --git a/test/native_to_erc/home_bridge_test.js b/test/native_to_erc/home_bridge_test.js index 72c000a3a..f3f6d93e9 100644 --- a/test/native_to_erc/home_bridge_test.js +++ b/test/native_to_erc/home_bridge_test.js @@ -12,13 +12,12 @@ const oneEther = web3.toBigNumber(web3.toWei(1, "ether")); const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")); contract('HomeBridge', async (accounts) => { - let homeContract, validatorContract, authorities, rewards, owner; + let homeContract, validatorContract, authorities, owner; before(async () => { validatorContract = await BridgeValidators.new() authorities = [accounts[1]]; - rewards = [accounts[2]]; owner = accounts[0] - await validatorContract.initialize(1, authorities, rewards, owner) + await validatorContract.initialize(1, authorities, owner) }) describe('#initialize', async() => { @@ -215,9 +214,8 @@ contract('HomeBridge', async (accounts) => { it('test with 2 signatures required', async () => { let validatorContractWith2Signatures = await BridgeValidators.new() let authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]]; - let rewardsThreeAccs = [accounts[4], accounts[5], accounts[6]]; let ownerOfValidators = accounts[0] - await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, rewardsThreeAccs, ownerOfValidators) + await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, ownerOfValidators) let homeBridgeWithTwoSigs = await HomeBridge.new(); await homeBridgeWithTwoSigs.initialize(validatorContractWith2Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations); @@ -286,9 +284,8 @@ contract('HomeBridge', async (accounts) => { it('doesnt allow to withdraw if requiredSignatures has changed', async () => { let validatorContractWith2Signatures = await BridgeValidators.new() let authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]]; - let rewardsThreeAccs = [accounts[4], accounts[5], accounts[6]]; let ownerOfValidators = accounts[0] - await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, rewardsThreeAccs, ownerOfValidators) + await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, ownerOfValidators) let homeBridgeWithTwoSigs = await HomeBridge.new(); await homeBridgeWithTwoSigs.initialize(validatorContractWith2Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations); @@ -343,10 +340,9 @@ contract('HomeBridge', async (accounts) => { it('works with 5 validators and 3 required signatures', async () => { const recipient = accounts[8] const authoritiesFiveAccs = [accounts[1], accounts[2], accounts[3], accounts[4], accounts[5]] - const rewardsFiveAccs = [accounts[6], accounts[7], accounts[8], accounts[9], accounts[0]] let ownerOfValidators = accounts[0] const validatorContractWith3Signatures = await BridgeValidators.new() - await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, rewardsFiveAccs, ownerOfValidators) + await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) const homeBridgeWithThreeSigs = await HomeBridge.new(); await homeBridgeWithThreeSigs.initialize(validatorContractWith3Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations); @@ -390,13 +386,12 @@ contract('HomeBridge', async (accounts) => { }) describe('#submitSignature', async () => { - let validatorContractWith2Signatures,authoritiesThreeAccs,rewardsThreeAccs,ownerOfValidators,tokenPOA20,homeBridgeWithTwoSigs + let validatorContractWith2Signatures,authoritiesThreeAccs,ownerOfValidators,tokenPOA20,homeBridgeWithTwoSigs beforeEach(async () => { validatorContractWith2Signatures = await BridgeValidators.new() authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]]; - rewardsThreeAccs = [accounts[4], accounts[5], accounts[6]]; ownerOfValidators = accounts[0] - await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, rewardsThreeAccs, ownerOfValidators) + await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, ownerOfValidators) homeBridgeWithTwoSigs = await HomeBridge.new(); await homeBridgeWithTwoSigs.initialize(validatorContractWith2Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations); }) @@ -437,9 +432,8 @@ contract('HomeBridge', async (accounts) => { it('works with 5 validators and 3 required signatures', async () => { const recipientAccount = accounts[8] const authoritiesFiveAccs = [accounts[1], accounts[2], accounts[3], accounts[4], accounts[5]] - const rewardsFiveAccs = [accounts[6], accounts[7], accounts[8], accounts[9], accounts[0]] const validatorContractWith3Signatures = await BridgeValidators.new() - await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, rewardsFiveAccs, ownerOfValidators) + await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) const homeBridgeWithThreeSigs = await HomeBridge.new(); await homeBridgeWithThreeSigs.initialize(validatorContractWith3Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations); diff --git a/test/poa20_test.js b/test/poa20_test.js index c15191916..f4d1d4c82 100644 --- a/test/poa20_test.js +++ b/test/poa20_test.js @@ -99,8 +99,7 @@ contract('ERC677BridgeToken', async (accounts) => { beforeEach(async () => { validatorContract = await BridgeValidators.new() const authorities = [accounts[2]]; - const rewards = [accounts[3]]; - await validatorContract.initialize(1, authorities, rewards, owner) + await validatorContract.initialize(1, authorities, owner) homeErcToErcContract = await HomeErcToErcBridge.new() await homeErcToErcContract.initialize(validatorContract.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address) foreignNativeToErcBridge = await ForeignNativeToErcBridge.new() @@ -188,8 +187,7 @@ contract('ERC677BridgeToken', async (accounts) => { beforeEach(async () => { validatorContract = await BridgeValidators.new() const authorities = [accounts[2]]; - const rewards = [accounts[3]]; - await validatorContract.initialize(1, authorities, rewards, owner) + await validatorContract.initialize(1, authorities, owner) homeErcToErcContract = await HomeErcToErcBridge.new() await homeErcToErcContract.initialize(validatorContract.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address) foreignNativeToErcBridge = await ForeignNativeToErcBridge.new() diff --git a/test/rewardable_validators_test.js b/test/rewardable_validators_test.js new file mode 100644 index 000000000..fd8ddc81c --- /dev/null +++ b/test/rewardable_validators_test.js @@ -0,0 +1,265 @@ +const BridgeValidators = artifacts.require("RewardableValidators.sol"); +const EternalStorageProxy = artifacts.require("EternalStorageProxy.sol"); +const { ERROR_MSG, ZERO_ADDRESS, F_ADDRESS } = require('./setup'); + +contract('RewardableValidators', async (accounts) => { + let bridgeValidators + let owner = accounts[0] + + beforeEach(async () => { + bridgeValidators = await BridgeValidators.new(); + }) + + describe('#initialize', async () => { + it('sets values', async () => { + '0x0000000000000000000000000000000000000000'.should.be.equal(await bridgeValidators.owner()) + '0'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) + false.should.be.equal(await bridgeValidators.isValidator(accounts[0])) + false.should.be.equal(await bridgeValidators.isValidator(accounts[1])) + false.should.be.equal(await bridgeValidators.isInitialized()) + '0'.should.be.bignumber.equal(await bridgeValidators.requiredSignatures()) + '0'.should.be.bignumber.equal(await bridgeValidators.deployedAtBlock()) + await bridgeValidators.initialize(3, accounts.slice(0, 3), accounts.slice(3, 5), accounts[2], {from: accounts[2]}).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.initialize(2, accounts.slice(0, 2), accounts.slice(2, 4), accounts[2], {from: accounts[2]}).should.be.fulfilled; + await bridgeValidators.initialize(2, accounts.slice(0, 2), accounts.slice(2, 4), accounts[2], {from: accounts[2]}).should.be.rejectedWith(ERROR_MSG); + await bridgeValidators.initialize(1, [accounts[0]], [ZERO_ADDRESS], [accounts[1]], { from: accounts[1] }).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.initialize(1, [ZERO_ADDRESS], [accounts[0]], [accounts[1]], { from: accounts[1] }).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.initialize(1, [F_ADDRESS], [accounts[0]], [accounts[1]], { from: accounts[1] }).should.be.rejectedWith(ERROR_MSG) + true.should.be.equal(await bridgeValidators.isInitialized()) + '2'.should.be.bignumber.equal(await bridgeValidators.requiredSignatures()) + true.should.be.equal(await bridgeValidators.isValidator(accounts[0])) + true.should.be.equal(await bridgeValidators.isValidator(accounts[1])) + accounts[2].should.be.equal(await bridgeValidators.owner()) + '2'.should.be.bignumber.equal(await bridgeValidators.validatorCount()); + (await bridgeValidators.deployedAtBlock()).should.be.bignumber.above(0) + const [major, minor, patch] = await bridgeValidators.getBridgeValidatorsInterfacesVersion() + major.should.be.bignumber.gte(0) + minor.should.be.bignumber.gte(0) + patch.should.be.bignumber.gte(0) + }) + }) + + describe('#addValidator', async () => { + let owner = accounts[2]; + let validators = [accounts[0], accounts[1]]; + let rewards = accounts.slice(2, 4) + let requiredSignatures = 2; + beforeEach(async () => { + await bridgeValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + '2'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) + }) + it('adds validator', async () => { + let newValidator = accounts[4]; + let newReward = accounts[5]; + + false.should.be.equal(await bridgeValidators.isValidator(newValidator)) + await bridgeValidators.addValidator(newValidator, newReward, {from: validators[0]}).should.be.rejectedWith(ERROR_MSG) + const {logs} = await bridgeValidators.addValidator(newValidator, newReward, {from: owner}).should.be.fulfilled + true.should.be.equal(await bridgeValidators.isValidator(newValidator)) + '3'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) + logs[0].event.should.be.equal('ValidatorAdded') + logs[0].args.should.be.deep.equal({validator: newValidator}) + }) + + it('cannot add already existing validator', async () => { + true.should.be.equal(await bridgeValidators.isValidator(validators[0])) + await bridgeValidators.addValidator(validators[0], rewards[0], {from: owner}).should.be.rejectedWith(ERROR_MSG) + '2'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) + }) + + it(`cannot add 0xf as validator address`, async () => { + // Given + await bridgeValidators.addValidator(F_ADDRESS, rewards[0], { from: owner }).should.be.rejectedWith(ERROR_MSG) + }) + + it(`cannot add 0x0 as validator address`, async () => { + await bridgeValidators.addValidator(ZERO_ADDRESS, rewards[0], {from: owner}).should.be.rejectedWith(ERROR_MSG) + }) + + it(`cannot add 0x0 as reward address`, async () => { + await bridgeValidators.addValidator(accounts[4], ZERO_ADDRESS, { from: owner }).should.be.rejectedWith(ERROR_MSG) + }) + }) + + describe('#removeValidator', async () => { + let owner = accounts[2]; + let validators = [accounts[0], accounts[1], accounts[3]]; + let rewards = accounts.slice(4, 7); + let requiredSignatures = 2; + beforeEach(async () => { + await bridgeValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + '3'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) + }) + + it('removes validator', async () => { + let toRemove = validators[0]; + true.should.be.equal(await bridgeValidators.isValidator(toRemove)) + await bridgeValidators.removeValidator(toRemove, {from: validators[0]}).should.be.rejectedWith(ERROR_MSG) + const {logs} = await bridgeValidators.removeValidator(toRemove, {from: owner}).should.be.fulfilled + false.should.be.equal(await bridgeValidators.isValidator(toRemove)) + '2'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) + logs[0].event.should.be.equal('ValidatorRemoved') + logs[0].args.should.be.deep.equal({validator: toRemove}) + }) + + it('cannot remove if it will break requiredSignatures', async () => { + let toRemove = validators[0]; + let toRemove2 = validators[1]; + true.should.be.equal(await bridgeValidators.isValidator(toRemove)) + true.should.be.equal(await bridgeValidators.isValidator(toRemove)) + await bridgeValidators.removeValidator(toRemove, {from: owner}).should.be.fulfilled + await bridgeValidators.removeValidator(toRemove2, {from: owner}).should.be.rejectedWith(ERROR_MSG) + false.should.be.equal(await bridgeValidators.isValidator(toRemove)) + true.should.be.equal(await bridgeValidators.isValidator(toRemove2)) + '2'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) + }) + + it('cannot remove non-existent validator', async () => { + false.should.be.equal(await bridgeValidators.isValidator(accounts[4])) + await bridgeValidators.removeValidator(accounts[4], {from: owner}).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.removeValidator(ZERO_ADDRESS, {from: owner}).should.be.rejectedWith(ERROR_MSG) + '3'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) + }) + }) + + describe('#setRequiredSignatures', async () => { + let owner = accounts[2]; + let validators = [accounts[0], accounts[1], accounts[3]]; + let rewards = accounts.slice(4, 7) + let requiredSignatures = 2; + beforeEach(async () => { + await bridgeValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + '3'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) + }) + + it('sets req signatures', async () => { + let newReqSig = 3; + requiredSignatures.should.be.bignumber.equal(await bridgeValidators.requiredSignatures()); + await bridgeValidators.setRequiredSignatures(newReqSig, {from: validators[0]}).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.setRequiredSignatures(newReqSig, {from: owner}).should.be.fulfilled + newReqSig.should.be.bignumber.equal(await bridgeValidators.requiredSignatures()); + }) + it('cannot set more than validators count', async () => { + let newReqSig = 4; + requiredSignatures.should.be.bignumber.equal(await bridgeValidators.requiredSignatures()); + await bridgeValidators.setRequiredSignatures(newReqSig, {from: owner}).should.be.rejectedWith(ERROR_MSG) + requiredSignatures.should.be.bignumber.equal(await bridgeValidators.requiredSignatures()); + }) + }) + + describe('#upgradable', async () => { + it('can be upgraded via upgradeToAndCall', async () => { + let storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + let required_signatures = 2; + let validators = [accounts[0], accounts[1]]; + let rewards = accounts.slice(3, 5); + let owner = accounts[2] + let data = bridgeValidators.initialize.request(required_signatures, validators, rewards, owner).params[0].data + await storageProxy.upgradeToAndCall('1', bridgeValidators.address, data).should.be.fulfilled; + let finalContract = await BridgeValidators.at(storageProxy.address); + true.should.be.equal(await finalContract.isInitialized()); + required_signatures.should.be.bignumber.equal(await finalContract.requiredSignatures()) + + true.should.be.equal(await finalContract.isValidator(validators[0])) + true.should.be.equal(await finalContract.isValidator(validators[1])) + owner.should.be.equal(await finalContract.owner()) + validators.length.should.be.bignumber.equal(await finalContract.validatorCount()) + }) + }) + + describe('#single list remove', () => { + it(`should remove ${accounts[0]} - without Proxy`, async () => { + // Given + const { initialize, isInitialized, removeValidator } = bridgeValidators + await initialize(1, accounts.slice(0, 2), accounts.slice(2, 4), owner, { from: owner }).should.be.fulfilled + true.should.be.equal(await isInitialized()) + + // When + const { logs } = await removeValidator(accounts[0], { from: owner }).should.be.fulfilled + + // Then + logs[0].event.should.be.equal('ValidatorRemoved') + logs[0].args.should.be.deep.equal({ validator: accounts[0] }) + }) + + it(`Removed validator should return zero address on nextValidator`, async () => { + // Given + const { initialize, isInitialized, removeValidator, getNextValidator } = bridgeValidators + await initialize(1, accounts.slice(0, 2), accounts.slice(2, 4), owner, { from: owner }).should.be.fulfilled + true.should.be.equal(await isInitialized()) + const initialNextValidator = await getNextValidator(accounts[0]) + + // When + const { logs } = await removeValidator(accounts[0], { from: owner }).should.be.fulfilled + + // Then + logs[0].event.should.be.equal('ValidatorRemoved') + logs[0].args.should.be.deep.equal({ validator: accounts[0] }) + + const updatedNextValidator = await getNextValidator(accounts[0]) + + initialNextValidator.should.be.equals(accounts[1]) + updatedNextValidator.should.be.equals(ZERO_ADDRESS) + }) + + accounts.slice(0, 5).forEach(validator => { + it(`should remove ${validator} - with Proxy`, async () => { + // Given + const proxy = await EternalStorageProxy.new() + const bridgeValidatorsImpl = await BridgeValidators.new() + await proxy.upgradeTo('1', bridgeValidatorsImpl.address) + bridgeValidators = BridgeValidators.at(proxy.address) + const { initialize, isInitialized, removeValidator } = bridgeValidators + await initialize( + 1, + accounts.slice(0, 5), + accounts.slice(5), + owner, + { from: owner } + ).should.be.fulfilled + true.should.be.equal(await isInitialized()) + + // When + const { logs } = await removeValidator( + validator, + { from: owner } + ).should.be.fulfilled + + // Then + logs[0].event.should.be.equal('ValidatorRemoved') + logs[0].args.should.be.deep.equal({ validator }) + }) + }) + }) + + describe('#reward address', () => { + it(`reward address is properly assigned`, async () => { + // Given + const { initialize, isInitialized, getValidatorRewardAddress } = bridgeValidators + await initialize(1, accounts.slice(0, 5), accounts.slice(5), owner, { from: owner }).should.be.fulfilled + + // When + true.should.be.equal(await isInitialized()) + + // Then + for (let i = 0; i < accounts.slice(0, 5).length; i++) { + const validator = accounts[i] + accounts[i + 5].should.be.equal(await getValidatorRewardAddress(validator)) + } + }) + }) + describe('#Validators list', () => { + it('should return validators list', async () => { + // Given + const validators = accounts.slice(0, 5) + const { initialize, validatorList } = bridgeValidators + await initialize(1, validators, accounts.slice(5), owner, { from: owner }).should.be.fulfilled + + // When + const returnedList = await validatorList() + + // Then + returnedList.should.be.eql(validators) + }) + }) +}) diff --git a/test/validators_test.js b/test/validators_test.js index 1ce4214a3..e2d7517eb 100644 --- a/test/validators_test.js +++ b/test/validators_test.js @@ -19,12 +19,10 @@ contract('BridgeValidators', async (accounts) => { false.should.be.equal(await bridgeValidators.isInitialized()) '0'.should.be.bignumber.equal(await bridgeValidators.requiredSignatures()) '0'.should.be.bignumber.equal(await bridgeValidators.deployedAtBlock()) - await bridgeValidators.initialize(3, accounts.slice(0, 3), accounts.slice(3, 5), accounts[2], {from: accounts[2]}).should.be.rejectedWith(ERROR_MSG) - await bridgeValidators.initialize(2, accounts.slice(0, 2), accounts.slice(2, 4), accounts[2], {from: accounts[2]}).should.be.fulfilled; - await bridgeValidators.initialize(2, accounts.slice(0, 2), accounts.slice(2, 4), accounts[2], {from: accounts[2]}).should.be.rejectedWith(ERROR_MSG); - await bridgeValidators.initialize(1, [accounts[0]], [ZERO_ADDRESS], [accounts[1]], { from: accounts[1] }).should.be.rejectedWith(ERROR_MSG) - await bridgeValidators.initialize(1, [ZERO_ADDRESS], [accounts[0]], [accounts[1]], { from: accounts[1] }).should.be.rejectedWith(ERROR_MSG) - await bridgeValidators.initialize(1, [F_ADDRESS], [accounts[0]], [accounts[1]], { from: accounts[1] }).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.initialize(1, [ZERO_ADDRESS], [accounts[1]], { from: accounts[1] }).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.initialize(1, [F_ADDRESS], [accounts[1]], { from: accounts[1] }).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.initialize(2, accounts.slice(0, 2), accounts[2], {from: accounts[2]}).should.be.fulfilled; + await bridgeValidators.initialize(2, accounts.slice(0, 2), accounts[2], {from: accounts[2]}).should.be.rejectedWith(ERROR_MSG); true.should.be.equal(await bridgeValidators.isInitialized()) '2'.should.be.bignumber.equal(await bridgeValidators.requiredSignatures()) true.should.be.equal(await bridgeValidators.isValidator(accounts[0])) @@ -42,19 +40,17 @@ contract('BridgeValidators', async (accounts) => { describe('#addValidator', async () => { let owner = accounts[2]; let validators = [accounts[0], accounts[1]]; - let rewards = accounts.slice(2, 4) let requiredSignatures = 2; beforeEach(async () => { - await bridgeValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + await bridgeValidators.initialize(requiredSignatures, validators, owner, {from: owner}).should.be.fulfilled '2'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) }) it('adds validator', async () => { let newValidator = accounts[4]; - let newReward = accounts[5]; false.should.be.equal(await bridgeValidators.isValidator(newValidator)) - await bridgeValidators.addValidator(newValidator, newReward, {from: validators[0]}).should.be.rejectedWith(ERROR_MSG) - const {logs} = await bridgeValidators.addValidator(newValidator, newReward, {from: owner}).should.be.fulfilled + await bridgeValidators.addValidator(newValidator, {from: validators[0]}).should.be.rejectedWith(ERROR_MSG) + const {logs} = await bridgeValidators.addValidator(newValidator, {from: owner}).should.be.fulfilled true.should.be.equal(await bridgeValidators.isValidator(newValidator)) '3'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) logs[0].event.should.be.equal('ValidatorAdded') @@ -63,31 +59,26 @@ contract('BridgeValidators', async (accounts) => { it('cannot add already existing validator', async () => { true.should.be.equal(await bridgeValidators.isValidator(validators[0])) - await bridgeValidators.addValidator(validators[0], rewards[0], {from: owner}).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.addValidator(validators[0], {from: owner}).should.be.rejectedWith(ERROR_MSG) '2'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) }) it(`cannot add 0xf as validator address`, async () => { // Given - await bridgeValidators.addValidator(F_ADDRESS, rewards[0], { from: owner }).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.addValidator(F_ADDRESS, { from: owner }).should.be.rejectedWith(ERROR_MSG) }) it(`cannot add 0x0 as validator address`, async () => { - await bridgeValidators.addValidator(ZERO_ADDRESS, rewards[0], {from: owner}).should.be.rejectedWith(ERROR_MSG) - }) - - it(`cannot add 0x0 as reward address`, async () => { - await bridgeValidators.addValidator(accounts[4], ZERO_ADDRESS, { from: owner }).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.addValidator(ZERO_ADDRESS, {from: owner}).should.be.rejectedWith(ERROR_MSG) }) }) describe('#removeValidator', async () => { let owner = accounts[2]; let validators = [accounts[0], accounts[1], accounts[3]]; - let rewards = accounts.slice(4, 7); let requiredSignatures = 2; beforeEach(async () => { - await bridgeValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + await bridgeValidators.initialize(requiredSignatures, validators, owner, {from: owner}).should.be.fulfilled '3'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) }) @@ -125,10 +116,9 @@ contract('BridgeValidators', async (accounts) => { describe('#setRequiredSignatures', async () => { let owner = accounts[2]; let validators = [accounts[0], accounts[1], accounts[3]]; - let rewards = accounts.slice(4, 7) let requiredSignatures = 2; beforeEach(async () => { - await bridgeValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + await bridgeValidators.initialize(requiredSignatures, validators, owner, {from: owner}).should.be.fulfilled '3'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) }) @@ -152,9 +142,8 @@ contract('BridgeValidators', async (accounts) => { let storageProxy = await EternalStorageProxy.new().should.be.fulfilled; let required_signatures = 2; let validators = [accounts[0], accounts[1]]; - let rewards = accounts.slice(3, 5); let owner = accounts[2] - let data = bridgeValidators.initialize.request(required_signatures, validators, rewards, owner).params[0].data + let data = bridgeValidators.initialize.request(required_signatures, validators, owner).params[0].data await storageProxy.upgradeToAndCall('1', bridgeValidators.address, data).should.be.fulfilled; let finalContract = await BridgeValidators.at(storageProxy.address); true.should.be.equal(await finalContract.isInitialized()); @@ -171,7 +160,7 @@ contract('BridgeValidators', async (accounts) => { it(`should remove ${accounts[0]} - without Proxy`, async () => { // Given const { initialize, isInitialized, removeValidator } = bridgeValidators - await initialize(1, accounts.slice(0, 2), accounts.slice(2, 4), owner, { from: owner }).should.be.fulfilled + await initialize(1, accounts.slice(0, 2), owner, { from: owner }).should.be.fulfilled true.should.be.equal(await isInitialized()) // When @@ -185,7 +174,7 @@ contract('BridgeValidators', async (accounts) => { it(`Removed validator should return zero address on nextValidator`, async () => { // Given const { initialize, isInitialized, removeValidator, getNextValidator } = bridgeValidators - await initialize(1, accounts.slice(0, 2), accounts.slice(2, 4), owner, { from: owner }).should.be.fulfilled + await initialize(1, accounts.slice(0, 2), owner, { from: owner }).should.be.fulfilled true.should.be.equal(await isInitialized()) const initialNextValidator = await getNextValidator(accounts[0]) @@ -213,7 +202,6 @@ contract('BridgeValidators', async (accounts) => { await initialize( 1, accounts.slice(0, 5), - accounts.slice(5), owner, { from: owner } ).should.be.fulfilled @@ -232,28 +220,12 @@ contract('BridgeValidators', async (accounts) => { }) }) - describe('#reward address', () => { - it(`reward address is properly assigned`, async () => { - // Given - const { initialize, isInitialized, getValidatorRewardAddress } = bridgeValidators - await initialize(1, accounts.slice(0, 5), accounts.slice(5), owner, { from: owner }).should.be.fulfilled - - // When - true.should.be.equal(await isInitialized()) - - // Then - for (let i = 0; i < accounts.slice(0, 5).length; i++) { - const validator = accounts[i] - accounts[i + 5].should.be.equal(await getValidatorRewardAddress(validator)) - } - }) - }) describe('#Validators list', () => { it('should return validators list', async () => { // Given const validators = accounts.slice(0, 5) const { initialize, validatorList } = bridgeValidators - await initialize(1, validators, accounts.slice(5), owner, { from: owner }).should.be.fulfilled + await initialize(1, validators, owner, { from: owner }).should.be.fulfilled // When const returnedList = await validatorList() From 5c553e06eb323e77c3628549c38f04bf224e07a0 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 7 Jan 2019 15:42:38 -0300 Subject: [PATCH 017/187] Update ValidatorAdded event on RewardableValidators --- contracts/upgradeable_contracts/RewardableValidators.sol | 6 +++--- test/rewardable_validators_test.js | 2 +- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/contracts/upgradeable_contracts/RewardableValidators.sol b/contracts/upgradeable_contracts/RewardableValidators.sol index 2f04ca90e..95d32df10 100644 --- a/contracts/upgradeable_contracts/RewardableValidators.sol +++ b/contracts/upgradeable_contracts/RewardableValidators.sol @@ -5,7 +5,7 @@ import "./BaseBridgeValidators.sol"; contract RewardableValidators is BaseBridgeValidators { - event ValidatorAdded (address indexed validator); + event ValidatorAdded (address indexed validator, address reward); event ValidatorRemoved (address indexed validator); function initialize( @@ -43,7 +43,7 @@ contract RewardableValidators is BaseBridgeValidators { setValidatorCount(validatorCount().add(1)); setValidatorRewardAddress(_initialValidators[i], _initialRewards[i]); - emit ValidatorAdded(_initialValidators[i]); + emit ValidatorAdded(_initialValidators[i], _initialRewards[i]); } uintStorage[keccak256(abi.encodePacked("requiredSignatures"))] = _requiredSignatures; @@ -65,7 +65,7 @@ contract RewardableValidators is BaseBridgeValidators { setValidator(F_ADDR, _validator); setValidatorCount(validatorCount().add(1)); - emit ValidatorAdded(_validator); + emit ValidatorAdded(_validator, _reward); } function removeValidator(address _validator) external onlyOwner { diff --git a/test/rewardable_validators_test.js b/test/rewardable_validators_test.js index fd8ddc81c..c595b7adc 100644 --- a/test/rewardable_validators_test.js +++ b/test/rewardable_validators_test.js @@ -58,7 +58,7 @@ contract('RewardableValidators', async (accounts) => { true.should.be.equal(await bridgeValidators.isValidator(newValidator)) '3'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) logs[0].event.should.be.equal('ValidatorAdded') - logs[0].args.should.be.deep.equal({validator: newValidator}) + logs[0].args.should.be.deep.equal({ validator: newValidator, reward: newReward }) }) it('cannot add already existing validator', async () => { From 1d7456cf778b36653b9569602b15a9ee552bb2c3 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 8 Jan 2019 12:25:20 -0300 Subject: [PATCH 018/187] Add end of list check on removeValidator --- contracts/upgradeable_contracts/BridgeValidators.sol | 4 ++++ contracts/upgradeable_contracts/RewardableValidators.sol | 4 ++++ 2 files changed, 8 insertions(+) diff --git a/contracts/upgradeable_contracts/BridgeValidators.sol b/contracts/upgradeable_contracts/BridgeValidators.sol index f1278440c..7c4483dec 100644 --- a/contracts/upgradeable_contracts/BridgeValidators.sol +++ b/contracts/upgradeable_contracts/BridgeValidators.sol @@ -73,6 +73,10 @@ contract BridgeValidators is BaseBridgeValidators { while (next != _validator) { index = next; next = getNextValidator(index); + + if (next == F_ADDR) { + revert(); + } } setValidator(index, validatorsNext); diff --git a/contracts/upgradeable_contracts/RewardableValidators.sol b/contracts/upgradeable_contracts/RewardableValidators.sol index 95d32df10..37e5539b0 100644 --- a/contracts/upgradeable_contracts/RewardableValidators.sol +++ b/contracts/upgradeable_contracts/RewardableValidators.sol @@ -79,6 +79,10 @@ contract RewardableValidators is BaseBridgeValidators { while (next != _validator) { index = next; next = getNextValidator(index); + + if (next == F_ADDR) { + revert(); + } } setValidator(index, validatorsNext); From b74360256415b3fe2f5aca4a9e0a486655643caf Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 8 Jan 2019 13:59:16 -0300 Subject: [PATCH 019/187] Refactor addValidator and RemoveValidator methods --- .../BaseBridgeValidators.sol | 31 +++++++++++++++++++ .../BridgeValidators.sol | 30 ++---------------- .../RewardableValidators.sol | 30 ++---------------- 3 files changed, 35 insertions(+), 56 deletions(-) diff --git a/contracts/upgradeable_contracts/BaseBridgeValidators.sol b/contracts/upgradeable_contracts/BaseBridgeValidators.sol index bd752d2c9..49e340c58 100644 --- a/contracts/upgradeable_contracts/BaseBridgeValidators.sol +++ b/contracts/upgradeable_contracts/BaseBridgeValidators.sol @@ -30,6 +30,37 @@ contract BaseBridgeValidators is EternalStorage, Ownable { return (2, 1, 0); } + function _addValidator(address _validator) internal onlyOwner { + require(_validator != address(0) && _validator != F_ADDR); + require(!isValidator(_validator)); + + address firstValidator = getNextValidator(F_ADDR); + setValidator(_validator, firstValidator); + setValidator(F_ADDR, _validator); + setValidatorCount(validatorCount().add(1)); + } + + function _removeValidator(address _validator) internal onlyOwner { + require(validatorCount() > requiredSignatures()); + require(isValidator(_validator)); + address validatorsNext = getNextValidator(_validator); + address index = F_ADDR; + address next = getNextValidator(index); + + while (next != _validator) { + index = next; + next = getNextValidator(index); + + if (next == F_ADDR) { + revert(); + } + } + + setValidator(index, validatorsNext); + deleteItemFromAddressStorage("validatorsList", _validator); + setValidatorCount(validatorCount().sub(1)); + } + function requiredSignatures() public view returns (uint256) { return uintStorage[keccak256(abi.encodePacked("requiredSignatures"))]; } diff --git a/contracts/upgradeable_contracts/BridgeValidators.sol b/contracts/upgradeable_contracts/BridgeValidators.sol index 7c4483dec..578657a6d 100644 --- a/contracts/upgradeable_contracts/BridgeValidators.sol +++ b/contracts/upgradeable_contracts/BridgeValidators.sol @@ -51,38 +51,12 @@ contract BridgeValidators is BaseBridgeValidators { } function addValidator(address _validator) external onlyOwner { - require(_validator != address(0) && _validator != F_ADDR); - require(!isValidator(_validator)); - - address firstValidator = getNextValidator(F_ADDR); - setValidator(_validator, firstValidator); - setValidator(F_ADDR, _validator); - - setValidatorCount(validatorCount().add(1)); + _addValidator(_validator); emit ValidatorAdded(_validator); } function removeValidator(address _validator) external onlyOwner { - require(validatorCount() > requiredSignatures()); - require(isValidator(_validator)); - address validatorsNext = getNextValidator(_validator); - address index = F_ADDR; - address next = getNextValidator(index); - - // find the element in the list pointing to _validator - while (next != _validator) { - index = next; - next = getNextValidator(index); - - if (next == F_ADDR) { - revert(); - } - } - - setValidator(index, validatorsNext); - deleteItemFromAddressStorage("validatorsList", _validator); - setValidatorCount(validatorCount().sub(1)); - + _removeValidator(_validator); emit ValidatorRemoved(_validator); } } diff --git a/contracts/upgradeable_contracts/RewardableValidators.sol b/contracts/upgradeable_contracts/RewardableValidators.sol index 37e5539b0..f8061baf5 100644 --- a/contracts/upgradeable_contracts/RewardableValidators.sol +++ b/contracts/upgradeable_contracts/RewardableValidators.sol @@ -55,41 +55,15 @@ contract RewardableValidators is BaseBridgeValidators { } function addValidator(address _validator, address _reward) external onlyOwner { - require(_validator != address(0) && _validator != F_ADDR); require(_reward != address(0)); - require(!isValidator(_validator)); - - address firstValidator = getNextValidator(F_ADDR); - setValidator(_validator, firstValidator); + _addValidator(_validator); setValidatorRewardAddress(_validator, _reward); - setValidator(F_ADDR, _validator); - - setValidatorCount(validatorCount().add(1)); emit ValidatorAdded(_validator, _reward); } function removeValidator(address _validator) external onlyOwner { - require(validatorCount() > requiredSignatures()); - require(isValidator(_validator)); - address validatorsNext = getNextValidator(_validator); - address index = F_ADDR; - address next = getNextValidator(index); - - // find the element in the list pointing to _validator - while (next != _validator) { - index = next; - next = getNextValidator(index); - - if (next == F_ADDR) { - revert(); - } - } - - setValidator(index, validatorsNext); - deleteItemFromAddressStorage("validatorsList", _validator); + _removeValidator(_validator); deleteItemFromAddressStorage("validatorsRewards", _validator); - setValidatorCount(validatorCount().sub(1)); - emit ValidatorRemoved(_validator); } From 6912fdcad9b8a1c669edd3d0867245984d824e17 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 8 Jan 2019 14:08:31 -0300 Subject: [PATCH 020/187] Rename setValidator to setNextValidator --- .../upgradeable_contracts/BaseBridgeValidators.sol | 8 ++++---- contracts/upgradeable_contracts/BridgeValidators.sol | 10 +++++----- .../upgradeable_contracts/RewardableValidators.sol | 10 +++++----- 3 files changed, 14 insertions(+), 14 deletions(-) diff --git a/contracts/upgradeable_contracts/BaseBridgeValidators.sol b/contracts/upgradeable_contracts/BaseBridgeValidators.sol index 49e340c58..f60da8750 100644 --- a/contracts/upgradeable_contracts/BaseBridgeValidators.sol +++ b/contracts/upgradeable_contracts/BaseBridgeValidators.sol @@ -35,8 +35,8 @@ contract BaseBridgeValidators is EternalStorage, Ownable { require(!isValidator(_validator)); address firstValidator = getNextValidator(F_ADDR); - setValidator(_validator, firstValidator); - setValidator(F_ADDR, _validator); + setNextValidator(_validator, firstValidator); + setNextValidator(F_ADDR, _validator); setValidatorCount(validatorCount().add(1)); } @@ -56,7 +56,7 @@ contract BaseBridgeValidators is EternalStorage, Ownable { } } - setValidator(index, validatorsNext); + setNextValidator(index, validatorsNext); deleteItemFromAddressStorage("validatorsList", _validator); setValidatorCount(validatorCount().sub(1)); } @@ -107,7 +107,7 @@ contract BaseBridgeValidators is EternalStorage, Ownable { uintStorage[keccak256(abi.encodePacked("validatorCount"))] = _validatorCount; } - function setValidator(address _prevValidator, address _validator) internal { + function setNextValidator(address _prevValidator, address _validator) internal { addressStorage[keccak256(abi.encodePacked("validatorsList", _prevValidator))] = _validator; } diff --git a/contracts/upgradeable_contracts/BridgeValidators.sol b/contracts/upgradeable_contracts/BridgeValidators.sol index 578657a6d..371bdc332 100644 --- a/contracts/upgradeable_contracts/BridgeValidators.sol +++ b/contracts/upgradeable_contracts/BridgeValidators.sol @@ -27,15 +27,15 @@ contract BridgeValidators is BaseBridgeValidators { require(!isValidator(_initialValidators[i])); if (i == 0) { - setValidator(F_ADDR, _initialValidators[i]); + setNextValidator(F_ADDR, _initialValidators[i]); if (_initialValidators.length == 1) { - setValidator(_initialValidators[i], F_ADDR); + setNextValidator(_initialValidators[i], F_ADDR); } } else if (i == _initialValidators.length - 1) { - setValidator(_initialValidators[i - 1], _initialValidators[i]); - setValidator(_initialValidators[i], F_ADDR); + setNextValidator(_initialValidators[i - 1], _initialValidators[i]); + setNextValidator(_initialValidators[i], F_ADDR); } else { - setValidator(_initialValidators[i - 1], _initialValidators[i]); + setNextValidator(_initialValidators[i - 1], _initialValidators[i]); } setValidatorCount(validatorCount().add(1)); diff --git a/contracts/upgradeable_contracts/RewardableValidators.sol b/contracts/upgradeable_contracts/RewardableValidators.sol index f8061baf5..c0aedcd81 100644 --- a/contracts/upgradeable_contracts/RewardableValidators.sol +++ b/contracts/upgradeable_contracts/RewardableValidators.sol @@ -30,15 +30,15 @@ contract RewardableValidators is BaseBridgeValidators { require(!isValidator(_initialValidators[i])); if (i == 0) { - setValidator(F_ADDR, _initialValidators[i]); + setNextValidator(F_ADDR, _initialValidators[i]); if (_initialValidators.length == 1) { - setValidator(_initialValidators[i], F_ADDR); + setNextValidator(_initialValidators[i], F_ADDR); } } else if (i == _initialValidators.length - 1) { - setValidator(_initialValidators[i - 1], _initialValidators[i]); - setValidator(_initialValidators[i], F_ADDR); + setNextValidator(_initialValidators[i - 1], _initialValidators[i]); + setNextValidator(_initialValidators[i], F_ADDR); } else { - setValidator(_initialValidators[i - 1], _initialValidators[i]); + setNextValidator(_initialValidators[i - 1], _initialValidators[i]); } setValidatorCount(validatorCount().add(1)); From 212d7964122cd26838dfeb74f4dc584bb89796b8 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 8 Jan 2019 14:36:52 -0300 Subject: [PATCH 021/187] Add zero address check on getNextValidator usage --- contracts/upgradeable_contracts/BaseBridgeValidators.sol | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/contracts/upgradeable_contracts/BaseBridgeValidators.sol b/contracts/upgradeable_contracts/BaseBridgeValidators.sol index f60da8750..5dda8436e 100644 --- a/contracts/upgradeable_contracts/BaseBridgeValidators.sol +++ b/contracts/upgradeable_contracts/BaseBridgeValidators.sol @@ -51,7 +51,7 @@ contract BaseBridgeValidators is EternalStorage, Ownable { index = next; next = getNextValidator(index); - if (next == F_ADDR) { + if (next == F_ADDR || next == address(0) ) { revert(); } } @@ -94,6 +94,10 @@ contract BaseBridgeValidators is EternalStorage, Ownable { list[counter] = nextValidator; nextValidator = getNextValidator(nextValidator); counter++; + + if (nextValidator == address(0) ) { + revert(); + } } return list; From fa36918944cebee13421cd2d803938e9409946fa Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 8 Jan 2019 17:24:08 -0300 Subject: [PATCH 022/187] Move validatorList method to RewardableValidators --- contracts/IBridgeValidators.sol | 1 - .../BaseBridgeValidators.sol | 18 ------------------ .../RewardableValidators.sol | 18 ++++++++++++++++++ test/validators_test.js | 15 --------------- 4 files changed, 18 insertions(+), 34 deletions(-) diff --git a/contracts/IBridgeValidators.sol b/contracts/IBridgeValidators.sol index 51fd06bf2..2732ae41e 100644 --- a/contracts/IBridgeValidators.sol +++ b/contracts/IBridgeValidators.sol @@ -5,5 +5,4 @@ interface IBridgeValidators { function isValidator(address _validator) public view returns(bool); function requiredSignatures() public view returns(uint256); function owner() public view returns(address); - function validatorList() public view returns (address[]); } diff --git a/contracts/upgradeable_contracts/BaseBridgeValidators.sol b/contracts/upgradeable_contracts/BaseBridgeValidators.sol index 5dda8436e..c275edca8 100644 --- a/contracts/upgradeable_contracts/BaseBridgeValidators.sol +++ b/contracts/upgradeable_contracts/BaseBridgeValidators.sol @@ -85,24 +85,6 @@ contract BaseBridgeValidators is EternalStorage, Ownable { return addressStorage[keccak256(abi.encodePacked("validatorsList", _address))]; } - function validatorList() public view returns (address[]) { - address [] memory list = new address[](validatorCount()); - uint256 counter = 0; - address nextValidator = getNextValidator(F_ADDR); - - while (nextValidator != F_ADDR) { - list[counter] = nextValidator; - nextValidator = getNextValidator(nextValidator); - counter++; - - if (nextValidator == address(0) ) { - revert(); - } - } - - return list; - } - function deleteItemFromAddressStorage(string _mapName, address _address) internal { delete addressStorage[keccak256(abi.encodePacked(_mapName, _address))]; } diff --git a/contracts/upgradeable_contracts/RewardableValidators.sol b/contracts/upgradeable_contracts/RewardableValidators.sol index c0aedcd81..660d3e606 100644 --- a/contracts/upgradeable_contracts/RewardableValidators.sol +++ b/contracts/upgradeable_contracts/RewardableValidators.sol @@ -67,6 +67,24 @@ contract RewardableValidators is BaseBridgeValidators { emit ValidatorRemoved(_validator); } + function validatorList() public view returns (address[]) { + address [] memory list = new address[](validatorCount()); + uint256 counter = 0; + address nextValidator = getNextValidator(F_ADDR); + + while (nextValidator != F_ADDR) { + list[counter] = nextValidator; + nextValidator = getNextValidator(nextValidator); + counter++; + + if (nextValidator == address(0) ) { + revert(); + } + } + + return list; + } + function getValidatorRewardAddress(address _validator) public view returns (address) { return addressStorage[keccak256(abi.encodePacked("validatorsRewards", _validator))]; } diff --git a/test/validators_test.js b/test/validators_test.js index e2d7517eb..a98ae5145 100644 --- a/test/validators_test.js +++ b/test/validators_test.js @@ -219,19 +219,4 @@ contract('BridgeValidators', async (accounts) => { }) }) }) - - describe('#Validators list', () => { - it('should return validators list', async () => { - // Given - const validators = accounts.slice(0, 5) - const { initialize, validatorList } = bridgeValidators - await initialize(1, validators, owner, { from: owner }).should.be.fulfilled - - // When - const returnedList = await validatorList() - - // Then - returnedList.should.be.eql(validators) - }) - }) }) From a3b947a50721accd4cf7844992ca1b444a6f08c8 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 9 Jan 2019 08:17:55 -0300 Subject: [PATCH 023/187] Remove onlyOwner modifier on BaseBridgeValidators methods --- contracts/upgradeable_contracts/BaseBridgeValidators.sol | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/contracts/upgradeable_contracts/BaseBridgeValidators.sol b/contracts/upgradeable_contracts/BaseBridgeValidators.sol index c275edca8..0ea2661dd 100644 --- a/contracts/upgradeable_contracts/BaseBridgeValidators.sol +++ b/contracts/upgradeable_contracts/BaseBridgeValidators.sol @@ -30,7 +30,7 @@ contract BaseBridgeValidators is EternalStorage, Ownable { return (2, 1, 0); } - function _addValidator(address _validator) internal onlyOwner { + function _addValidator(address _validator) internal { require(_validator != address(0) && _validator != F_ADDR); require(!isValidator(_validator)); @@ -40,7 +40,7 @@ contract BaseBridgeValidators is EternalStorage, Ownable { setValidatorCount(validatorCount().add(1)); } - function _removeValidator(address _validator) internal onlyOwner { + function _removeValidator(address _validator) internal { require(validatorCount() > requiredSignatures()); require(isValidator(_validator)); address validatorsNext = getNextValidator(_validator); From 5bf54405c98eba14c525e42d7627595f170189fe Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 9 Jan 2019 08:38:08 -0300 Subject: [PATCH 024/187] Add zero address check for getNextValidator --- contracts/upgradeable_contracts/BaseBridgeValidators.sol | 2 ++ contracts/upgradeable_contracts/RewardableValidators.sol | 1 + 2 files changed, 3 insertions(+) diff --git a/contracts/upgradeable_contracts/BaseBridgeValidators.sol b/contracts/upgradeable_contracts/BaseBridgeValidators.sol index 0ea2661dd..4405c0e9e 100644 --- a/contracts/upgradeable_contracts/BaseBridgeValidators.sol +++ b/contracts/upgradeable_contracts/BaseBridgeValidators.sol @@ -35,6 +35,7 @@ contract BaseBridgeValidators is EternalStorage, Ownable { require(!isValidator(_validator)); address firstValidator = getNextValidator(F_ADDR); + require(firstValidator != address(0)); setNextValidator(_validator, firstValidator); setNextValidator(F_ADDR, _validator); setValidatorCount(validatorCount().add(1)); @@ -46,6 +47,7 @@ contract BaseBridgeValidators is EternalStorage, Ownable { address validatorsNext = getNextValidator(_validator); address index = F_ADDR; address next = getNextValidator(index); + require(next != address(0)); while (next != _validator) { index = next; diff --git a/contracts/upgradeable_contracts/RewardableValidators.sol b/contracts/upgradeable_contracts/RewardableValidators.sol index 660d3e606..989df6b78 100644 --- a/contracts/upgradeable_contracts/RewardableValidators.sol +++ b/contracts/upgradeable_contracts/RewardableValidators.sol @@ -71,6 +71,7 @@ contract RewardableValidators is BaseBridgeValidators { address [] memory list = new address[](validatorCount()); uint256 counter = 0; address nextValidator = getNextValidator(F_ADDR); + require(nextValidator != address(0)); while (nextValidator != F_ADDR) { list[counter] = nextValidator; From e008b244fa9dcdcf0f5cfde5d73d9d801de80547 Mon Sep 17 00:00:00 2001 From: fernandomg Date: Thu, 27 Dec 2018 17:25:11 -0300 Subject: [PATCH 025/187] Create FeeManager related contracts --- contracts/IFeeManager.sol | 10 ++++++ .../upgradeable_contracts/BaseFeeManager.sol | 36 +++++++++++++++++++ .../FeeManagerHelpers.sol | 10 ++++++ 3 files changed, 56 insertions(+) create mode 100644 contracts/IFeeManager.sol create mode 100644 contracts/upgradeable_contracts/BaseFeeManager.sol create mode 100644 contracts/upgradeable_contracts/FeeManagerHelpers.sol diff --git a/contracts/IFeeManager.sol b/contracts/IFeeManager.sol new file mode 100644 index 000000000..57a4a9340 --- /dev/null +++ b/contracts/IFeeManager.sol @@ -0,0 +1,10 @@ +pragma solidity 0.4.24; + + +interface IFeeManager { + function calculateFee(uint256 _value, bool _recover) external view returns(uint256 fee); + function distributeFeeFromSignatures(uint256 _fee) external; + function distributeFeeFromAffirmation(uint256 _fee) external; + function setFee(uint256 _fee) external; + function getFee() external view returns(uint256 fee); +} diff --git a/contracts/upgradeable_contracts/BaseFeeManager.sol b/contracts/upgradeable_contracts/BaseFeeManager.sol new file mode 100644 index 000000000..813c220a7 --- /dev/null +++ b/contracts/upgradeable_contracts/BaseFeeManager.sol @@ -0,0 +1,36 @@ +pragma solidity 0.4.24; + +import "../upgradeability/EternalStorage.sol"; +import "../IFeeManager.sol"; +import "../libraries/SafeMath.sol"; + +contract BaseFeeManager is EternalStorage { + using SafeMath for uint256; + + event FeeUpdated(uint256 fee, uint256 fee); + + function calculateFee(uint256 _value, bool _recover) external view returns(uint256) { + uint256 fee = getFee(); + uint256 eth = 1 ether; + if (!_recover) { + return _value.mul(fee).div(eth); + } + return _value.mul(fee).div(eth.sub(fee)); // value * fee / (1 ether - fee) + } + + function distributeFeeFromSignatures(uint256 _fee) external { + } + + function distributeFeeFromAffirmation(uint256 _fee) external { + } + + function setFee(uint256 _fee) external { + uint256 fee = _fee.mul(1 ether); + uintStorage[keccak256(abi.encodePacked("fee"))] = fee; + emit FeeUpdated(_fee, fee); + } + + function getFee() public view returns(uint256) { + return uintStorage[keccak256(abi.encodePacked("fee"))]; + } +} diff --git a/contracts/upgradeable_contracts/FeeManagerHelpers.sol b/contracts/upgradeable_contracts/FeeManagerHelpers.sol new file mode 100644 index 000000000..4193d2ca2 --- /dev/null +++ b/contracts/upgradeable_contracts/FeeManagerHelpers.sol @@ -0,0 +1,10 @@ +pragma solidity 0.4.24; + +import "../upgradeability/EternalStorage.sol"; +import "../IFeeManager.sol"; + +contract FeeManagerHelpers is EternalStorage { + function feeManagerContract() public view returns(IFeeManager) { + return IFeeManager(addressStorage[keccak256(abi.encodePacked("feeManagerContract"))]); + } +} From ceb847852838d29026910d966122869db8340032 Mon Sep 17 00:00:00 2001 From: fernandomg Date: Thu, 27 Dec 2018 17:25:43 -0300 Subject: [PATCH 026/187] Implement Fee Distribution for ERC20 to Native mode --- .../upgradeable_contracts/BasicHomeBridge.sol | 12 ++++ .../erc20_to_native/FeeManagerErcToNative.sol | 71 +++++++++++++++++++ .../erc20_to_native/HomeBridgeErcToNative.sol | 24 +++++-- 3 files changed, 103 insertions(+), 4 deletions(-) create mode 100644 contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol diff --git a/contracts/upgradeable_contracts/BasicHomeBridge.sol b/contracts/upgradeable_contracts/BasicHomeBridge.sol index 6b5229c9c..6ae15724f 100644 --- a/contracts/upgradeable_contracts/BasicHomeBridge.sol +++ b/contracts/upgradeable_contracts/BasicHomeBridge.sol @@ -5,6 +5,7 @@ import "../libraries/SafeMath.sol"; import "openzeppelin-solidity/contracts/token/ERC20/ERC20Basic.sol"; import "./Validatable.sol"; import "../libraries/Message.sol"; +import "../IFeeManager.sol"; contract BasicHomeBridge is EternalStorage, Validatable { using SafeMath for uint256; @@ -70,6 +71,17 @@ contract BasicHomeBridge is EternalStorage, Validatable { if (signed >= reqSigs) { setNumMessagesSigned(hashMsg, markAsProcessed(signed)); emit CollectedSignatures(msg.sender, hashMsg, reqSigs); + + IFeeManager feeManager = feeManagerContract(); + if (feeManager != address(0)) { + address receipt; + uint256 amount; + bytes32 txHash; + address contractAddress; + (recipient, amount, txHash, contractAddress) = Message.parseMessage(message); + uint256 fee = feeManager.delegatecall(abi.encodeWithSignatures("calculateFee(uint256,bool)", amount, true)); + feeManager.delegatecall(abi.encodeWithSignature("distributeFeeFromSignatures(uint256)", fee)); + } } } diff --git a/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol new file mode 100644 index 000000000..2f16826f9 --- /dev/null +++ b/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol @@ -0,0 +1,71 @@ +pragma solidity 0.4.24; + +import "../BaseFeeManager.sol"; +import "../Validatable.sol"; +import "../../libraries/SafeMath.sol"; +import "../../IBridgeValidators.sol"; +import "../../IBlockReward.sol"; + +contract FeeManagerErcToNative is BaseFeeManager, Validatable { + using SafeMath for uint256; + + function distributeFeeFromAffirmation(uint256 _fee) external { + // TODO: decide whether distribute by stake or proportionally + distributeFeeFromAffirmationProportionally(_fee); + } + + function distributeFeeFromSignatures(uint256 _fee) external { + // TODO: decide whether distribute by stake or proportionally + distributeFeeFromSignatureProportionally(_fee); + } + + // + // Distribute Proportionally + // + function distributeFeeFromAffirmationProportionally(uint _fee) private { + uint256 feePerValidator = proportionalFee(); + address nextValidator = validators.getNextValidator(validators.F_ADDR()); + + while (nextValidator != validators.F_ADDR()) { + address rewardAddress = validators.getValidatorRewardAddress(nextValidator); + require(rewardAddress != address(0)); + blockReward.addExtraReceiver(feePerValidator, rewardAddress); + nextValidator = validators.getNextValidator(nextValidator); + } + } + + function distributeFeeFromSignatureProportionally(uint _fee) private { + uint256 feePerValidator = proportionalFee(); + address nextValidator = validators.getNextValidator(validators.F_ADDR()); + + while (nextValidator != validators.F_ADDR()) { + address rewardAddress = validators.getValidatorRewardAddress(nextValidator); + require(rewardAddress != address(0)); + rewardAddress.send(feePerValidator); + nextValidator = validators.getNextValidator(nextValidator); + } + } + + function proportionalFee() private returns(uint256) { + IBridgeValidators validators = validatorContract(); + IBlockReward blockReward = blockRewardContract(); + uint256 validatorsCount = validators.validatorCount(); + uint256 feePerValidator = _fee.div(validatorsCount); + return feePerValidator; + } + + // + // Distribute By Stake + // + function distributeFeeFromSignatureByStake(uint _fee) private { + // TODO: implement fee distribution from signature by stake + } + + function distributeFeeFromAffirmationByStake(uint _fee) private { + // TODO: implement fee distribution from affirmation by stake + } + + function stakeBasedFee(address _validator) private returns(uint256) { + // TODO: calculate fee for _validator based on its stake + } +} diff --git a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol index db98fae61..7d51fb528 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol @@ -7,6 +7,7 @@ import "../../IBlockReward.sol"; import "../../ERC677Receiver.sol"; import "../BasicHomeBridge.sol"; import "../ERC677Bridge.sol"; +import "../../IFeeManager.sol"; contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge { @@ -19,9 +20,15 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge { uint256 totalMinted = blockReward.mintedTotallyByBridge(address(this)); require(msg.value <= totalMinted.sub(totalBurntCoins())); setTotalSpentPerDay(getCurrentDay(), totalSpentPerDay(getCurrentDay()).add(msg.value)); - setTotalBurntCoins(totalBurntCoins().add(msg.value)); - address(0).transfer(msg.value); - emit UserRequestForSignature(msg.sender, msg.value); + uint256 valueToTransfer = msg.value; + IFeeManager feeManager = feeManagerContract(); + if (feeManager != address(0)) { + uint256 fee = feeManager.delegateCall(abi.encodeWithSignature("calculateFee(uint256,bool)", valueToTransfer, false)); + valueToTransfer = valueToTransfer - fee; + } + setTotalBurntCoins(totalBurntCoins().add(valueToTransfer)); + address(0).transfer(valueToTransfer); + emit UserRequestForSignature(msg.sender, valueToTransfer); } function initialize ( @@ -73,7 +80,16 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge { function onExecuteAffirmation(address _recipient, uint256 _value) internal returns(bool) { IBlockReward blockReward = blockRewardContract(); require(blockReward != address(0)); - blockReward.addExtraReceiver(_value, _recipient); + uint256 valueToMint = msg.value; + + IFeeManager feeManager = feeManagerContract(); + if (feeManager != address(0)) { + uint256 fee = feeManager.delegatecall(abi.encodeWithSignature("calculateFee(uint256,bool)", valueToMint, false)); + feeManager.delegatecall(abi.encodeWithSignature("distributeFeeFromAffirmation(uint256)", fee)); + valueToMint = valueToMint - fee; + } + + blockReward.addExtraReceiver(valueToMint, _recipient); return true; } From 5991ef31ebbe570a87100fa80bac54705a281507 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Fri, 4 Jan 2019 16:27:02 -0300 Subject: [PATCH 027/187] Update fee contract implementation --- .../upgradeable_contracts/BaseFeeManager.sol | 47 +++++++++++--- .../upgradeable_contracts/BasicHomeBridge.sol | 56 ++++++++++++++--- .../erc20_to_native/FeeManagerErcToNative.sol | 62 ++----------------- .../erc20_to_native/HomeBridgeErcToNative.sol | 16 +++-- 4 files changed, 104 insertions(+), 77 deletions(-) diff --git a/contracts/upgradeable_contracts/BaseFeeManager.sol b/contracts/upgradeable_contracts/BaseFeeManager.sol index 813c220a7..98114d0cd 100644 --- a/contracts/upgradeable_contracts/BaseFeeManager.sol +++ b/contracts/upgradeable_contracts/BaseFeeManager.sol @@ -3,11 +3,12 @@ pragma solidity 0.4.24; import "../upgradeability/EternalStorage.sol"; import "../IFeeManager.sol"; import "../libraries/SafeMath.sol"; +import "../IBridgeValidators.sol"; contract BaseFeeManager is EternalStorage { using SafeMath for uint256; - event FeeUpdated(uint256 fee, uint256 fee); + event FeeUpdated(uint256 fee); function calculateFee(uint256 _value, bool _recover) external view returns(uint256) { uint256 fee = getFee(); @@ -15,22 +16,50 @@ contract BaseFeeManager is EternalStorage { if (!_recover) { return _value.mul(fee).div(eth); } - return _value.mul(fee).div(eth.sub(fee)); // value * fee / (1 ether - fee) + return _value.mul(fee).div(eth.sub(fee)); } - function distributeFeeFromSignatures(uint256 _fee) external { + function setFee(uint256 _fee) external { + uintStorage[keccak256(abi.encodePacked("fee"))] = _fee; + emit FeeUpdated(_fee); + } + + function getFee() public view returns(uint256) { + return uintStorage[keccak256(abi.encodePacked("fee"))]; } function distributeFeeFromAffirmation(uint256 _fee) external { + distributeFeeProportionally(_fee, true); } - function setFee(uint256 _fee) external { - uint256 fee = _fee.mul(1 ether); - uintStorage[keccak256(abi.encodePacked("fee"))] = fee; - emit FeeUpdated(_fee, fee); + function distributeFeeFromSignatures(uint256 _fee) external { + distributeFeeProportionally(_fee, false); } - function getFee() public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("fee"))]; + function distributeFeeProportionally(uint256 _fee, bool _isAffirmation) internal { + IBridgeValidators validators = validatorContract(); + address [] memory validatorList = validators.validatorList(); + uint256 feePerValidator = _fee.div(validatorList.length); + + for (uint256 i = 0; i < validatorList.length; i++) { + address rewardAddress = validators.getValidatorRewardAddress(validatorList[i]); + onFeeDistribution(rewardAddress, feePerValidator, _isAffirmation); + } + } + + function onFeeDistribution(address _rewardAddress, uint256 _fee, bool _isAffirmation) internal { + if (_isAffirmation) { + onAffirmationFeeDistribution(_rewardAddress, _fee); + } else { + onSignatureFeeDistribution(_rewardAddress, _fee); + } + } + + function onAffirmationFeeDistribution(address _rewardAddress, uint256 _fee) internal; + + function onSignatureFeeDistribution(address _rewardAddress, uint256 _fee) internal; + + function validatorContract() public view returns(IBridgeValidators) { + return IBridgeValidators(addressStorage[keccak256(abi.encodePacked("validatorContract"))]); } } diff --git a/contracts/upgradeable_contracts/BasicHomeBridge.sol b/contracts/upgradeable_contracts/BasicHomeBridge.sol index 6ae15724f..9012c13e2 100644 --- a/contracts/upgradeable_contracts/BasicHomeBridge.sol +++ b/contracts/upgradeable_contracts/BasicHomeBridge.sol @@ -72,19 +72,23 @@ contract BasicHomeBridge is EternalStorage, Validatable { setNumMessagesSigned(hashMsg, markAsProcessed(signed)); emit CollectedSignatures(msg.sender, hashMsg, reqSigs); - IFeeManager feeManager = feeManagerContract(); + address feeManager = feeManagerContract(); if (feeManager != address(0)) { - address receipt; - uint256 amount; - bytes32 txHash; - address contractAddress; - (recipient, amount, txHash, contractAddress) = Message.parseMessage(message); - uint256 fee = feeManager.delegatecall(abi.encodeWithSignatures("calculateFee(uint256,bool)", amount, true)); - feeManager.delegatecall(abi.encodeWithSignature("distributeFeeFromSignatures(uint256)", fee)); + handleSignatureFeeDistribution(feeManager, message); } } } + function handleSignatureFeeDistribution(address feeManager, bytes message) internal { + address recipient; + uint256 amount; + bytes32 txHash; + address contractAddress; + (recipient, amount, txHash, contractAddress) = Message.parseMessage(message); + uint256 fee = calculateFee(amount, true, feeManager); + feeManager.delegatecall(abi.encodeWithSignature("distributeFeeFromSignatures(uint256)", fee)); + } + function setMessagesSigned(bytes32 _hash, bool _status) internal { boolStorage[keccak256(abi.encodePacked("messagesSigned", _hash))] = _status; } @@ -156,4 +160,40 @@ contract BasicHomeBridge is EternalStorage, Validatable { function requiredMessageLength() public pure returns(uint256) { return Message.requiredMessageLength(); } + + function feeManagerContract() public view returns(address) { + return addressStorage[keccak256(abi.encodePacked("feeManagerContract"))]; + } + + function setFeeManagerContract(address _feeManager) public onlyOwner { + require(_feeManager == address(0) || isContract(_feeManager)); + addressStorage[keccak256(abi.encodePacked("feeManagerContract"))] = _feeManager; + } + + function isContract(address _addr) internal view returns (bool) + { + uint length; + assembly { length := extcodesize(_addr) } + return length > 0; + } + + function calculateFee(uint256 _value, bool _recover, address _impl) internal view returns(uint256) { + uint256 fee; + assembly { + let ptr := mload(0x40) + + calldatacopy(ptr, 0, calldatasize) + + let result := delegatecall(gas, _impl, ptr, calldatasize, 0, 0) + + mstore(0x40, add(ptr, returndatasize)) + returndatacopy(ptr, 0, returndatasize) + + switch result + case 0 { revert(ptr, returndatasize) } + default { fee := ptr } + } + + return fee; + } } diff --git a/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol index 2f16826f9..3aa59dfdc 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol @@ -2,70 +2,20 @@ pragma solidity 0.4.24; import "../BaseFeeManager.sol"; import "../Validatable.sol"; -import "../../libraries/SafeMath.sol"; -import "../../IBridgeValidators.sol"; import "../../IBlockReward.sol"; contract FeeManagerErcToNative is BaseFeeManager, Validatable { - using SafeMath for uint256; - function distributeFeeFromAffirmation(uint256 _fee) external { - // TODO: decide whether distribute by stake or proportionally - distributeFeeFromAffirmationProportionally(_fee); + function blockRewardContract() internal view returns(IBlockReward) { + return IBlockReward(addressStorage[keccak256(abi.encodePacked("blockRewardContract"))]); } - function distributeFeeFromSignatures(uint256 _fee) external { - // TODO: decide whether distribute by stake or proportionally - distributeFeeFromSignatureProportionally(_fee); - } - - // - // Distribute Proportionally - // - function distributeFeeFromAffirmationProportionally(uint _fee) private { - uint256 feePerValidator = proportionalFee(); - address nextValidator = validators.getNextValidator(validators.F_ADDR()); - - while (nextValidator != validators.F_ADDR()) { - address rewardAddress = validators.getValidatorRewardAddress(nextValidator); - require(rewardAddress != address(0)); - blockReward.addExtraReceiver(feePerValidator, rewardAddress); - nextValidator = validators.getNextValidator(nextValidator); - } - } - - function distributeFeeFromSignatureProportionally(uint _fee) private { - uint256 feePerValidator = proportionalFee(); - address nextValidator = validators.getNextValidator(validators.F_ADDR()); - - while (nextValidator != validators.F_ADDR()) { - address rewardAddress = validators.getValidatorRewardAddress(nextValidator); - require(rewardAddress != address(0)); - rewardAddress.send(feePerValidator); - nextValidator = validators.getNextValidator(nextValidator); - } - } - - function proportionalFee() private returns(uint256) { - IBridgeValidators validators = validatorContract(); + function onAffirmationFeeDistribution(address _rewardAddress, uint256 _fee) internal { IBlockReward blockReward = blockRewardContract(); - uint256 validatorsCount = validators.validatorCount(); - uint256 feePerValidator = _fee.div(validatorsCount); - return feePerValidator; - } - - // - // Distribute By Stake - // - function distributeFeeFromSignatureByStake(uint _fee) private { - // TODO: implement fee distribution from signature by stake - } - - function distributeFeeFromAffirmationByStake(uint _fee) private { - // TODO: implement fee distribution from affirmation by stake + blockReward.addExtraReceiver(_fee, _rewardAddress); } - function stakeBasedFee(address _validator) private returns(uint256) { - // TODO: calculate fee for _validator based on its stake + function onSignatureFeeDistribution(address _rewardAddress, uint256 _fee) internal { + _rewardAddress.send(_fee); } } diff --git a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol index 7d51fb528..910b42ec0 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol @@ -21,9 +21,9 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge { require(msg.value <= totalMinted.sub(totalBurntCoins())); setTotalSpentPerDay(getCurrentDay(), totalSpentPerDay(getCurrentDay()).add(msg.value)); uint256 valueToTransfer = msg.value; - IFeeManager feeManager = feeManagerContract(); + address feeManager = feeManagerContract(); if (feeManager != address(0)) { - uint256 fee = feeManager.delegateCall(abi.encodeWithSignature("calculateFee(uint256,bool)", valueToTransfer, false)); + uint256 fee = calculateFee(valueToTransfer, false, feeManager); valueToTransfer = valueToTransfer - fee; } setTotalBurntCoins(totalBurntCoins().add(valueToTransfer)); @@ -82,9 +82,9 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge { require(blockReward != address(0)); uint256 valueToMint = msg.value; - IFeeManager feeManager = feeManagerContract(); + address feeManager = feeManagerContract(); if (feeManager != address(0)) { - uint256 fee = feeManager.delegatecall(abi.encodeWithSignature("calculateFee(uint256,bool)", valueToMint, false)); + uint256 fee = calculateFee(valueToMint, false, feeManager); feeManager.delegatecall(abi.encodeWithSignature("distributeFeeFromAffirmation(uint256)", fee)); valueToMint = valueToMint - fee; } @@ -100,4 +100,12 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge { function setTotalBurntCoins(uint256 _amount) internal { uintStorage[keccak256(abi.encodePacked("totalBurntCoins"))] = _amount; } + + function setFee(uint256 _fee) external onlyOwner { + require(feeManagerContract().delegatecall(abi.encodeWithSignature("setFee(uint256)", _fee))); + } + + function getFee() public view returns(uint256) { + return uintStorage[keccak256(abi.encodePacked("fee"))]; + } } From 9a349739fb11a67b620eb241a857e8704c86f7c0 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 8 Jan 2019 10:37:23 -0300 Subject: [PATCH 028/187] Fix onExecuteAffirmation --- .../erc20_to_native/HomeBridgeErcToNative.sol | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol index 910b42ec0..c7cd169de 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol @@ -80,7 +80,7 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge { function onExecuteAffirmation(address _recipient, uint256 _value) internal returns(bool) { IBlockReward blockReward = blockRewardContract(); require(blockReward != address(0)); - uint256 valueToMint = msg.value; + uint256 valueToMint = _value; address feeManager = feeManagerContract(); if (feeManager != address(0)) { From 515f23ac7481ea8937743b45e7bc3aa59d6f8bc5 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 8 Jan 2019 11:48:50 -0300 Subject: [PATCH 029/187] Update delegateCall usage on calculateFee method --- .../upgradeable_contracts/BasicHomeBridge.sol | 17 ++++------------- 1 file changed, 4 insertions(+), 13 deletions(-) diff --git a/contracts/upgradeable_contracts/BasicHomeBridge.sol b/contracts/upgradeable_contracts/BasicHomeBridge.sol index 9012c13e2..da259e22c 100644 --- a/contracts/upgradeable_contracts/BasicHomeBridge.sol +++ b/contracts/upgradeable_contracts/BasicHomeBridge.sol @@ -178,22 +178,13 @@ contract BasicHomeBridge is EternalStorage, Validatable { } function calculateFee(uint256 _value, bool _recover, address _impl) internal view returns(uint256) { - uint256 fee; + bytes memory callData = abi.encodeWithSignature("calculateFee(uint256,bool)", _value, _recover); assembly { - let ptr := mload(0x40) - - calldatacopy(ptr, 0, calldatasize) - - let result := delegatecall(gas, _impl, ptr, calldatasize, 0, 0) - - mstore(0x40, add(ptr, returndatasize)) - returndatacopy(ptr, 0, returndatasize) + let result := delegatecall(gas, _impl, add(callData, 0x20), mload(callData), 0, 32) switch result - case 0 { revert(ptr, returndatasize) } - default { fee := ptr } + case 0 { revert(0, 0) } + default { return(0, 32) } } - - return fee; } } From 9bbaf56aa5e25da1c5b0f43d630b7d30842224c9 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 9 Jan 2019 09:11:23 -0300 Subject: [PATCH 030/187] Fix rewardableValidatorContract method on BaseFeeManager --- contracts/upgradeable_contracts/BaseFeeManager.sol | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/contracts/upgradeable_contracts/BaseFeeManager.sol b/contracts/upgradeable_contracts/BaseFeeManager.sol index 98114d0cd..8c652c2e0 100644 --- a/contracts/upgradeable_contracts/BaseFeeManager.sol +++ b/contracts/upgradeable_contracts/BaseFeeManager.sol @@ -3,7 +3,7 @@ pragma solidity 0.4.24; import "../upgradeability/EternalStorage.sol"; import "../IFeeManager.sol"; import "../libraries/SafeMath.sol"; -import "../IBridgeValidators.sol"; +import "../IRewardableValidators.sol"; contract BaseFeeManager is EternalStorage { using SafeMath for uint256; @@ -37,7 +37,7 @@ contract BaseFeeManager is EternalStorage { } function distributeFeeProportionally(uint256 _fee, bool _isAffirmation) internal { - IBridgeValidators validators = validatorContract(); + IRewardableValidators validators = rewardableValidatorContract(); address [] memory validatorList = validators.validatorList(); uint256 feePerValidator = _fee.div(validatorList.length); @@ -59,7 +59,7 @@ contract BaseFeeManager is EternalStorage { function onSignatureFeeDistribution(address _rewardAddress, uint256 _fee) internal; - function validatorContract() public view returns(IBridgeValidators) { - return IBridgeValidators(addressStorage[keccak256(abi.encodePacked("validatorContract"))]); + function rewardableValidatorContract() public view returns(IRewardableValidators) { + return IRewardableValidators(addressStorage[keccak256(abi.encodePacked("validatorContract"))]); } } From 97d3759dc5bfefbfab793334b1816386df392ba4 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 9 Jan 2019 09:23:35 -0300 Subject: [PATCH 031/187] Remove unused files --- contracts/IFeeManager.sol | 10 ---------- contracts/upgradeable_contracts/BaseFeeManager.sol | 2 +- contracts/upgradeable_contracts/BasicHomeBridge.sol | 2 +- contracts/upgradeable_contracts/FeeManagerHelpers.sol | 10 ---------- .../erc20_to_native/HomeBridgeErcToNative.sol | 1 - 5 files changed, 2 insertions(+), 23 deletions(-) delete mode 100644 contracts/IFeeManager.sol delete mode 100644 contracts/upgradeable_contracts/FeeManagerHelpers.sol diff --git a/contracts/IFeeManager.sol b/contracts/IFeeManager.sol deleted file mode 100644 index 57a4a9340..000000000 --- a/contracts/IFeeManager.sol +++ /dev/null @@ -1,10 +0,0 @@ -pragma solidity 0.4.24; - - -interface IFeeManager { - function calculateFee(uint256 _value, bool _recover) external view returns(uint256 fee); - function distributeFeeFromSignatures(uint256 _fee) external; - function distributeFeeFromAffirmation(uint256 _fee) external; - function setFee(uint256 _fee) external; - function getFee() external view returns(uint256 fee); -} diff --git a/contracts/upgradeable_contracts/BaseFeeManager.sol b/contracts/upgradeable_contracts/BaseFeeManager.sol index 8c652c2e0..af8781e07 100644 --- a/contracts/upgradeable_contracts/BaseFeeManager.sol +++ b/contracts/upgradeable_contracts/BaseFeeManager.sol @@ -1,10 +1,10 @@ pragma solidity 0.4.24; import "../upgradeability/EternalStorage.sol"; -import "../IFeeManager.sol"; import "../libraries/SafeMath.sol"; import "../IRewardableValidators.sol"; + contract BaseFeeManager is EternalStorage { using SafeMath for uint256; diff --git a/contracts/upgradeable_contracts/BasicHomeBridge.sol b/contracts/upgradeable_contracts/BasicHomeBridge.sol index da259e22c..e4e35f35c 100644 --- a/contracts/upgradeable_contracts/BasicHomeBridge.sol +++ b/contracts/upgradeable_contracts/BasicHomeBridge.sol @@ -5,7 +5,7 @@ import "../libraries/SafeMath.sol"; import "openzeppelin-solidity/contracts/token/ERC20/ERC20Basic.sol"; import "./Validatable.sol"; import "../libraries/Message.sol"; -import "../IFeeManager.sol"; + contract BasicHomeBridge is EternalStorage, Validatable { using SafeMath for uint256; diff --git a/contracts/upgradeable_contracts/FeeManagerHelpers.sol b/contracts/upgradeable_contracts/FeeManagerHelpers.sol deleted file mode 100644 index 4193d2ca2..000000000 --- a/contracts/upgradeable_contracts/FeeManagerHelpers.sol +++ /dev/null @@ -1,10 +0,0 @@ -pragma solidity 0.4.24; - -import "../upgradeability/EternalStorage.sol"; -import "../IFeeManager.sol"; - -contract FeeManagerHelpers is EternalStorage { - function feeManagerContract() public view returns(IFeeManager) { - return IFeeManager(addressStorage[keccak256(abi.encodePacked("feeManagerContract"))]); - } -} diff --git a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol index c7cd169de..75d3d5c3a 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol @@ -7,7 +7,6 @@ import "../../IBlockReward.sol"; import "../../ERC677Receiver.sol"; import "../BasicHomeBridge.sol"; import "../ERC677Bridge.sol"; -import "../../IFeeManager.sol"; contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge { From 8eb4809735ad18ac970f1aadd786104d87139142 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 9 Jan 2019 09:31:36 -0300 Subject: [PATCH 032/187] Remove unused import --- .../erc20_to_native/FeeManagerErcToNative.sol | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol index 3aa59dfdc..4a2d2ca35 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol @@ -1,10 +1,9 @@ pragma solidity 0.4.24; import "../BaseFeeManager.sol"; -import "../Validatable.sol"; import "../../IBlockReward.sol"; -contract FeeManagerErcToNative is BaseFeeManager, Validatable { +contract FeeManagerErcToNative is BaseFeeManager { function blockRewardContract() internal view returns(IBlockReward) { return IBlockReward(addressStorage[keccak256(abi.encodePacked("blockRewardContract"))]); From fbf81a83b948c46d02893e50c8f006d797c9fba6 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Thu, 10 Jan 2019 08:44:40 -0300 Subject: [PATCH 033/187] Fixes on Fee related methods --- contracts/upgradeable_contracts/BasicHomeBridge.sol | 12 +++++++++++- .../erc20_to_native/HomeBridgeErcToNative.sol | 13 ++----------- 2 files changed, 13 insertions(+), 12 deletions(-) diff --git a/contracts/upgradeable_contracts/BasicHomeBridge.sol b/contracts/upgradeable_contracts/BasicHomeBridge.sol index e4e35f35c..9490d55f8 100644 --- a/contracts/upgradeable_contracts/BasicHomeBridge.sol +++ b/contracts/upgradeable_contracts/BasicHomeBridge.sol @@ -170,6 +170,14 @@ contract BasicHomeBridge is EternalStorage, Validatable { addressStorage[keccak256(abi.encodePacked("feeManagerContract"))] = _feeManager; } + function setFee(uint256 _fee) external onlyOwner { + require(feeManagerContract().delegatecall(abi.encodeWithSignature("setFee(uint256)", _fee))); + } + + function getFee() public view returns(uint256) { + return uintStorage[keccak256(abi.encodePacked("fee"))]; + } + function isContract(address _addr) internal view returns (bool) { uint length; @@ -178,13 +186,15 @@ contract BasicHomeBridge is EternalStorage, Validatable { } function calculateFee(uint256 _value, bool _recover, address _impl) internal view returns(uint256) { + uint256 fee; bytes memory callData = abi.encodeWithSignature("calculateFee(uint256,bool)", _value, _recover); assembly { let result := delegatecall(gas, _impl, add(callData, 0x20), mload(callData), 0, 32) + fee := mload(0) switch result case 0 { revert(0, 0) } - default { return(0, 32) } } + return fee; } } diff --git a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol index 75d3d5c3a..154fd6512 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol @@ -23,7 +23,7 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge { address feeManager = feeManagerContract(); if (feeManager != address(0)) { uint256 fee = calculateFee(valueToTransfer, false, feeManager); - valueToTransfer = valueToTransfer - fee; + valueToTransfer = valueToTransfer.sub(fee); } setTotalBurntCoins(totalBurntCoins().add(valueToTransfer)); address(0).transfer(valueToTransfer); @@ -85,9 +85,8 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge { if (feeManager != address(0)) { uint256 fee = calculateFee(valueToMint, false, feeManager); feeManager.delegatecall(abi.encodeWithSignature("distributeFeeFromAffirmation(uint256)", fee)); - valueToMint = valueToMint - fee; + valueToMint = valueToMint.sub(fee); } - blockReward.addExtraReceiver(valueToMint, _recipient); return true; } @@ -99,12 +98,4 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge { function setTotalBurntCoins(uint256 _amount) internal { uintStorage[keccak256(abi.encodePacked("totalBurntCoins"))] = _amount; } - - function setFee(uint256 _fee) external onlyOwner { - require(feeManagerContract().delegatecall(abi.encodeWithSignature("setFee(uint256)", _fee))); - } - - function getFee() public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("fee"))]; - } } From 16b39597e418d0ad8de3823bf16e4c54ba48ed8c Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Thu, 10 Jan 2019 08:59:23 -0300 Subject: [PATCH 034/187] Add ERC-to-Native feeManager basic tests --- test/erc_to_native/home_bridge.test.js | 159 +++++++++++++++++++++++++ 1 file changed, 159 insertions(+) diff --git a/test/erc_to_native/home_bridge.test.js b/test/erc_to_native/home_bridge.test.js index 2168f1f18..690ce051c 100644 --- a/test/erc_to_native/home_bridge.test.js +++ b/test/erc_to_native/home_bridge.test.js @@ -3,6 +3,8 @@ const HomeBridge = artifacts.require('HomeBridgeErcToNative.sol') const EternalStorageProxy = artifacts.require('EternalStorageProxy.sol') const BridgeValidators = artifacts.require('BridgeValidators.sol') const BlockReward = artifacts.require('BlockReward') +const RewardableValidators = artifacts.require("RewardableValidators.sol"); +const FeeManagerErcToNative = artifacts.require("FeeManagerErcToNative.sol"); const {ERROR_MSG, ZERO_ADDRESS} = require('../setup'); const {createMessage, sign } = require('../helpers/helpers'); const minPerTx = web3.toBigNumber(web3.toWei(0.01, "ether")); @@ -513,4 +515,161 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { '104'.should.be.bignumber.equal(requiredMessageLength) }) }) + + describe('#feeManager', async () => { + let homeBridge, rewardableValidators + let owner = accounts[0] + let validators = [accounts[1]] + let rewards = [accounts[2]] + let requiredSignatures = 1 + beforeEach(async () => { + rewardableValidators = await RewardableValidators.new() + homeBridge = await HomeBridge.new() + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, {from: owner}).should.be.fulfilled + await blockRewardContract.sendTransaction({ + from: accounts[2], + value: oneEther + }).should.be.fulfilled + }) + it('should be able to set and get fee manager contract', async () => { + // Given + const feeManager = await FeeManagerErcToNative.new() + + // When + await homeBridge.setFeeManagerContract(feeManager.address).should.be.fulfilled + + // Then + const feeManagerContract = await homeBridge.feeManagerContract() + feeManagerContract.should.be.equals(feeManager.address) + }) + it('should be able to set and get fee', async () => { + // Given + // 10% fee + const fee = web3.toBigNumber(web3.toWei(0.1, "ether")) + const feeManager = await FeeManagerErcToNative.new() + await homeBridge.setFeeManagerContract(feeManager.address).should.be.fulfilled + + // When + await homeBridge.setFee(fee).should.be.fulfilled + + // Then + const bridgeFee = await homeBridge.getFee() + bridgeFee.should.be.bignumber.equal(fee) + }) + }) + describe('#feeManager_ExecuteAffirmation', async () => { + it('should distribute fee to validator', async () => { + // Initialize + const owner = accounts[0] + const validators = [accounts[1]] + const rewards = [accounts[2]] + const requiredSignatures = 1 + const rewardableValidators = await RewardableValidators.new() + const homeBridge = await HomeBridge.new() + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, {from: owner}).should.be.fulfilled + await blockRewardContract.sendTransaction({ + from: accounts[2], + value: oneEther + }).should.be.fulfilled + + // Given + // 0.1% fee + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeManager = await FeeManagerErcToNative.new() + await homeBridge.setFeeManagerContract(feeManager.address).should.be.fulfilled + await homeBridge.setFee(feeInWei).should.be.fulfilled + + const recipient = accounts[5]; + const value = halfEther; + const balanceBefore = await web3.eth.getBalance(recipient) + const rewardAddressBalanceBefore = await web3.eth.getBalance(rewards[0]) + const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + + // When + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled + + // Then + logs[0].event.should.be.equal("SignedForAffirmation"); + logs[0].args.should.be.deep.equal({ + signer: validators[0], + transactionHash + }); + logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].args.should.be.deep.equal({ + recipient, + value, + transactionHash + }) + const balanceAfter = await web3.eth.getBalance(recipient) + const rewardAddressBalanceAfter = await web3.eth.getBalance(rewards[0]) + + rewardAddressBalanceAfter.should.be.bignumber.equal(rewardAddressBalanceBefore.add(value.mul(web3.toBigNumber(fee)))) + balanceAfter.should.be.bignumber.equal(balanceBefore.add(value.mul(web3.toBigNumber(1 - fee)))) + }) + it('should distribute fee to 3 validators', async () => { + // Initialize + const owner = accounts[0] + const validators = [accounts[1], accounts[2], accounts[3]] + const rewards = [accounts[4], accounts[5], accounts[6]] + const requiredSignatures = 1 + const rewardableValidators = await RewardableValidators.new() + const homeBridge = await HomeBridge.new() + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, {from: owner}).should.be.fulfilled + await blockRewardContract.sendTransaction({ + from: accounts[0], + value: oneEther + }).should.be.fulfilled + + // Given + const value = halfEther; + // 0.1% fee + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + // totalFee / 3 + const feePerValidator = web3.toBigNumber(166666666666666) + const feeManager = await FeeManagerErcToNative.new() + await homeBridge.setFeeManagerContract(feeManager.address).should.be.fulfilled + await homeBridge.setFee(feeInWei).should.be.fulfilled + + const recipient = accounts[8]; + const balanceBefore = await web3.eth.getBalance(recipient) + + const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const initialBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const initialBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + + + const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + + // When + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled + + // Then + logs[0].event.should.be.equal("SignedForAffirmation"); + logs[0].args.should.be.deep.equal({ + signer: validators[0], + transactionHash + }); + logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].args.should.be.deep.equal({ + recipient, + value, + transactionHash + }) + const balanceAfter = await web3.eth.getBalance(recipient) + balanceAfter.should.be.bignumber.equal(balanceBefore.add(value.mul(web3.toBigNumber(1 - fee)))) + + const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + + updatedBalanceRewardAddress1.should.be.bignumber.equal(initialBalanceRewardAddress1.add(feePerValidator)) + updatedBalanceRewardAddress2.should.be.bignumber.equal(initialBalanceRewardAddress2.add(feePerValidator)) + updatedBalanceRewardAddress3.should.be.bignumber.equal(initialBalanceRewardAddress3.add(feePerValidator)) + }) + }) }) From 9ee9ce4a6104cb3d98dfdd1c13c2cb8f62125ff8 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Thu, 10 Jan 2019 09:37:36 -0300 Subject: [PATCH 035/187] Fixes after merge --- .../upgradeable_contracts/BasicHomeBridge.sol | 6 +- test/erc_to_native/home_bridge.test.js | 55 ++++++++++++------- 2 files changed, 39 insertions(+), 22 deletions(-) diff --git a/contracts/upgradeable_contracts/BasicHomeBridge.sol b/contracts/upgradeable_contracts/BasicHomeBridge.sol index b82b30b12..14ee2e648 100644 --- a/contracts/upgradeable_contracts/BasicHomeBridge.sol +++ b/contracts/upgradeable_contracts/BasicHomeBridge.sol @@ -5,9 +5,11 @@ import "../libraries/SafeMath.sol"; import "openzeppelin-solidity/contracts/token/ERC20/ERC20Basic.sol"; import "./Validatable.sol"; import "../libraries/Message.sol"; +import "./OwnedUpgradeability.sol"; +import "./Ownable.sol"; -contract BasicHomeBridge is EternalStorage, Validatable { +contract BasicHomeBridge is EternalStorage, Validatable, Ownable, OwnedUpgradeability { using SafeMath for uint256; event UserRequestForSignature(address recipient, uint256 value); @@ -181,7 +183,7 @@ contract BasicHomeBridge is EternalStorage, Validatable { addressStorage[keccak256(abi.encodePacked("feeManagerContract"))] = _feeManager; } - function setFee(uint256 _fee) external onlyOwner { + function setFee(uint256 _fee) external onlyIfOwnerOfProxy { require(feeManagerContract().delegatecall(abi.encodeWithSignature("setFee(uint256)", _fee))); } diff --git a/test/erc_to_native/home_bridge.test.js b/test/erc_to_native/home_bridge.test.js index 3fcc74708..48c87799a 100644 --- a/test/erc_to_native/home_bridge.test.js +++ b/test/erc_to_native/home_bridge.test.js @@ -794,15 +794,19 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { describe('#feeManager', async () => { let homeBridge, rewardableValidators - let owner = accounts[0] + let owner = accounts[9] + let proxyOwner = accounts[0] let validators = [accounts[1]] let rewards = [accounts[2]] let requiredSignatures = 1 beforeEach(async () => { rewardableValidators = await RewardableValidators.new() - homeBridge = await HomeBridge.new() - await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled - await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, {from: owner}).should.be.fulfilled + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled + const homeBridgeImpl = await HomeBridge.new(); + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled + homeBridge = await HomeBridge.at(storageProxy.address); + await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled await blockRewardContract.sendTransaction({ from: accounts[2], value: oneEther @@ -813,7 +817,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const feeManager = await FeeManagerErcToNative.new() // When - await homeBridge.setFeeManagerContract(feeManager.address).should.be.fulfilled + await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled // Then const feeManagerContract = await homeBridge.feeManagerContract() @@ -824,10 +828,10 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { // 10% fee const fee = web3.toBigNumber(web3.toWei(0.1, "ether")) const feeManager = await FeeManagerErcToNative.new() - await homeBridge.setFeeManagerContract(feeManager.address).should.be.fulfilled + await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled // When - await homeBridge.setFee(fee).should.be.fulfilled + await homeBridge.setFee(fee, { from: proxyOwner }).should.be.fulfilled // Then const bridgeFee = await homeBridge.getFee() @@ -837,14 +841,18 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { describe('#feeManager_ExecuteAffirmation', async () => { it('should distribute fee to validator', async () => { // Initialize - const owner = accounts[0] + const owner = accounts[9] + const proxyOwner = accounts[0] const validators = [accounts[1]] const rewards = [accounts[2]] const requiredSignatures = 1 const rewardableValidators = await RewardableValidators.new() - const homeBridge = await HomeBridge.new() + const homeBridgeImpl = await HomeBridge.new(); + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled + const homeBridge = await HomeBridge.at(storageProxy.address); await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled - await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, {from: owner}).should.be.fulfilled + await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled await blockRewardContract.sendTransaction({ from: accounts[2], value: oneEther @@ -855,8 +863,8 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const fee = 0.001 const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) const feeManager = await FeeManagerErcToNative.new() - await homeBridge.setFeeManagerContract(feeManager.address).should.be.fulfilled - await homeBridge.setFee(feeInWei).should.be.fulfilled + await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled + await homeBridge.setFee(feeInWei, { from: proxyOwner }).should.be.fulfilled const recipient = accounts[5]; const value = halfEther; @@ -887,14 +895,18 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { }) it('should distribute fee to 3 validators', async () => { // Initialize - const owner = accounts[0] + const owner = accounts[9] + const proxyOwner = accounts[0] const validators = [accounts[1], accounts[2], accounts[3]] const rewards = [accounts[4], accounts[5], accounts[6]] - const requiredSignatures = 1 + const requiredSignatures = 2 const rewardableValidators = await RewardableValidators.new() - const homeBridge = await HomeBridge.new() + const homeBridgeImpl = await HomeBridge.new(); + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled + const homeBridge = await HomeBridge.at(storageProxy.address); await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled - await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, {from: owner}).should.be.fulfilled + await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled await blockRewardContract.sendTransaction({ from: accounts[0], value: oneEther @@ -908,8 +920,8 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { // totalFee / 3 const feePerValidator = web3.toBigNumber(166666666666666) const feeManager = await FeeManagerErcToNative.new() - await homeBridge.setFeeManagerContract(feeManager.address).should.be.fulfilled - await homeBridge.setFee(feeInWei).should.be.fulfilled + await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled + await homeBridge.setFee(feeInWei, { from: proxyOwner }).should.be.fulfilled const recipient = accounts[8]; const balanceBefore = await web3.eth.getBalance(recipient) @@ -922,12 +934,15 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; // When - const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled + const { logs: logsValidator1 } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[1]}).should.be.fulfilled // Then + logsValidator1.length.should.be.equals(1) + logs[0].event.should.be.equal("SignedForAffirmation"); logs[0].args.should.be.deep.equal({ - signer: validators[0], + signer: validators[1], transactionHash }); logs[1].event.should.be.equal("AffirmationCompleted"); From e752e94ec1a73162fac7f525ce7c1180280fcfbc Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Thu, 10 Jan 2019 15:59:24 -0300 Subject: [PATCH 036/187] Fix fee related methods --- contracts/upgradeable_contracts/BaseFeeManager.sol | 2 +- contracts/upgradeable_contracts/BasicHomeBridge.sol | 2 +- .../erc20_to_native/HomeBridgeErcToNative.sol | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/contracts/upgradeable_contracts/BaseFeeManager.sol b/contracts/upgradeable_contracts/BaseFeeManager.sol index af8781e07..4cb2efce9 100644 --- a/contracts/upgradeable_contracts/BaseFeeManager.sol +++ b/contracts/upgradeable_contracts/BaseFeeManager.sol @@ -10,7 +10,7 @@ contract BaseFeeManager is EternalStorage { event FeeUpdated(uint256 fee); - function calculateFee(uint256 _value, bool _recover) external view returns(uint256) { + function calculateFee(uint256 _value, bool _recover) external payable returns(uint256) { uint256 fee = getFee(); uint256 eth = 1 ether; if (!_recover) { diff --git a/contracts/upgradeable_contracts/BasicHomeBridge.sol b/contracts/upgradeable_contracts/BasicHomeBridge.sol index 14ee2e648..225a7fb56 100644 --- a/contracts/upgradeable_contracts/BasicHomeBridge.sol +++ b/contracts/upgradeable_contracts/BasicHomeBridge.sol @@ -92,7 +92,7 @@ contract BasicHomeBridge is EternalStorage, Validatable, Ownable, OwnedUpgradeab address contractAddress; (recipient, amount, txHash, contractAddress) = Message.parseMessage(message); uint256 fee = calculateFee(amount, true, feeManager); - feeManager.delegatecall(abi.encodeWithSignature("distributeFeeFromSignatures(uint256)", fee)); + require(feeManager.delegatecall(abi.encodeWithSignature("distributeFeeFromSignatures(uint256)", fee))); } function setMessagesSigned(bytes32 _hash, bool _status) internal { diff --git a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol index a25f59ef2..d9916f5d6 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol @@ -95,7 +95,7 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, address feeManager = feeManagerContract(); if (feeManager != address(0)) { uint256 fee = calculateFee(valueToMint, false, feeManager); - feeManager.delegatecall(abi.encodeWithSignature("distributeFeeFromAffirmation(uint256)", fee)); + require(feeManager.delegatecall(abi.encodeWithSignature("distributeFeeFromAffirmation(uint256)", fee))); valueToMint = valueToMint.sub(fee); } blockReward.addExtraReceiver(valueToMint, _recipient); From c7d62b43e1097a2211c808a5e1430c436756813c Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Thu, 10 Jan 2019 16:00:04 -0300 Subject: [PATCH 037/187] Add fallback and submitSignature fee basic tests --- test/erc_to_native/home_bridge.test.js | 102 +++++++++++++++++++++++++ 1 file changed, 102 insertions(+) diff --git a/test/erc_to_native/home_bridge.test.js b/test/erc_to_native/home_bridge.test.js index 48c87799a..81ad287fd 100644 --- a/test/erc_to_native/home_bridge.test.js +++ b/test/erc_to_native/home_bridge.test.js @@ -963,4 +963,106 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { updatedBalanceRewardAddress3.should.be.bignumber.equal(initialBalanceRewardAddress3.add(feePerValidator)) }) }) + describe('#feeManager_fallback', function () { + let homeBridge, rewardableValidators + let owner = accounts[9] + let proxyOwner = accounts[0] + let validators = [accounts[1]] + let rewards = [accounts[2]] + let requiredSignatures = 1 + beforeEach(async () => { + rewardableValidators = await RewardableValidators.new() + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled + const homeBridgeImpl = await HomeBridge.new(); + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled + homeBridge = await HomeBridge.at(storageProxy.address); + await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + await blockRewardContract.addMintedTotallyByBridge(oneEther, homeBridge.address) + }) + + it('should subtract fee from value', async () => { + // Given + // 0.1% fee + const value = halfEther + const recipient = accounts[8]; + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeManager = await FeeManagerErcToNative.new() + await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled + await homeBridge.setFee(feeInWei, { from: proxyOwner }).should.be.fulfilled + + // When + const { logs } = await homeBridge.sendTransaction({ from: recipient, value }).should.be.fulfilled + + // Then + const finalValue = value.mul(web3.toBigNumber(1 - fee)) + logs[0].event.should.be.equal('UserRequestForSignature') + logs[0].args.should.be.deep.equal({ recipient: recipient, value: finalValue }) + const currentDay = await homeBridge.getCurrentDay() + value.should.be.bignumber.equal(await homeBridge.totalSpentPerDay(currentDay)) + finalValue.should.be.bignumber.equal(await homeBridge.totalBurntCoins()) + const homeBridgeBalance = await web3.eth.getBalance(homeBridge.address) + homeBridgeBalance.should.be.bignumber.equal(value.sub(finalValue)) + }) + }) + describe('#feeManager_submitSignature', async () => { + it('should distribute fee to validator', async () => { + // Initialize + const owner = accounts[9] + const proxyOwner = accounts[0] + const validators = [accounts[1]] + const rewards = [accounts[2]] + const requiredSignatures = 1 + const rewardableValidators = await RewardableValidators.new() + const homeBridgeImpl = await HomeBridge.new(); + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled + const homeBridge = await HomeBridge.at(storageProxy.address); + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + await blockRewardContract.addMintedTotallyByBridge(oneEther, homeBridge.address) + + // Given + // 0.1% fee + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeManager = await FeeManagerErcToNative.new() + await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled + await homeBridge.setFee(feeInWei, { from: proxyOwner }).should.be.fulfilled + + const recipient = accounts[5]; + const initialValue = halfEther + const value = halfEther.mul(web3.toBigNumber(1-fee)); + const feeAmount = initialValue.mul(web3.toBigNumber(fee)) + const rewardAddressBalanceBefore = await web3.eth.getBalance(rewards[0]) + const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + + const initialBridgeBalance = await web3.eth.getBalance(homeBridge.address) + initialBridgeBalance.should.be.bignumber.equal('0') + + // When + await homeBridge.sendTransaction({ from: recipient, value: initialValue }).should.be.fulfilled + + const afterTransferBridgeBalance = await web3.eth.getBalance(homeBridge.address) + afterTransferBridgeBalance.should.be.bignumber.equal(feeAmount) + + const message = createMessage(recipient, value, transactionHash, homeBridge.address); + + const signature = await sign(validators[0], message) + + const { logs } = await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled; + + // Then + logs.length.should.be.equal(2) + logs[1].event.should.be.equal('CollectedSignatures') + + const finalBridgeBalance = await web3.eth.getBalance(homeBridge.address) + finalBridgeBalance.should.be.bignumber.equal('0') + + const rewardAddressBalanceAfter = await web3.eth.getBalance(rewards[0]) + console.log("rewardAddressBalanceAfter", rewardAddressBalanceAfter, "rewardAddressBalanceBefore", rewardAddressBalanceBefore) + rewardAddressBalanceAfter.should.be.bignumber.equal(rewardAddressBalanceBefore.add(feeAmount)) + }) + }) }) From 8876e15fffecea4a5dcb6fc62d20c6057512a6cf Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Fri, 11 Jan 2019 10:19:22 -0300 Subject: [PATCH 038/187] Refactor getFee --- contracts/upgradeable_contracts/BasicHomeBridge.sol | 12 +++++++++++- 1 file changed, 11 insertions(+), 1 deletion(-) diff --git a/contracts/upgradeable_contracts/BasicHomeBridge.sol b/contracts/upgradeable_contracts/BasicHomeBridge.sol index 225a7fb56..370076772 100644 --- a/contracts/upgradeable_contracts/BasicHomeBridge.sol +++ b/contracts/upgradeable_contracts/BasicHomeBridge.sol @@ -188,7 +188,17 @@ contract BasicHomeBridge is EternalStorage, Validatable, Ownable, OwnedUpgradeab } function getFee() public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("fee"))]; + uint256 fee; + bytes memory callData = abi.encodeWithSignature("getFee()"); + address feeManager = feeManagerContract(); + assembly { + let result := delegatecall(gas, feeManager, add(callData, 0x20), mload(callData), 0, 32) + fee := mload(0) + + switch result + case 0 { revert(0, 0) } + } + return fee; } function isContract(address _addr) internal view returns (bool) From 1993efcf4c6831fd5cafbfe15c8788a426da9d6b Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Fri, 11 Jan 2019 10:43:52 -0300 Subject: [PATCH 039/187] Add onSignaturesCollected --- contracts/upgradeable_contracts/BasicHomeBridge.sol | 8 ++++---- .../erc20_to_native/HomeBridgeErcToNative.sol | 7 +++++++ 2 files changed, 11 insertions(+), 4 deletions(-) diff --git a/contracts/upgradeable_contracts/BasicHomeBridge.sol b/contracts/upgradeable_contracts/BasicHomeBridge.sol index 370076772..778e6d2f2 100644 --- a/contracts/upgradeable_contracts/BasicHomeBridge.sol +++ b/contracts/upgradeable_contracts/BasicHomeBridge.sol @@ -78,10 +78,7 @@ contract BasicHomeBridge is EternalStorage, Validatable, Ownable, OwnedUpgradeab setNumMessagesSigned(hashMsg, markAsProcessed(signed)); emit CollectedSignatures(msg.sender, hashMsg, reqSigs); - address feeManager = feeManagerContract(); - if (feeManager != address(0)) { - handleSignatureFeeDistribution(feeManager, message); - } + onSignaturesCollected(message); } } @@ -102,6 +99,9 @@ contract BasicHomeBridge is EternalStorage, Validatable, Ownable, OwnedUpgradeab function onExecuteAffirmation(address, uint256) internal returns(bool) { } + function onSignaturesCollected(bytes) internal { + } + function numAffirmationsSigned(bytes32 _withdrawal) public view returns(uint256) { return uintStorage[keccak256(abi.encodePacked("numAffirmationsSigned", _withdrawal))]; } diff --git a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol index d9916f5d6..5432962fe 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol @@ -102,6 +102,13 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, return true; } + function onSignaturesCollected(bytes _message) internal { + address feeManager = feeManagerContract(); + if (feeManager != address(0)) { + handleSignatureFeeDistribution(feeManager, _message); + } + } + function fireEventOnTokenTransfer(address _from, uint256 _value) internal { emit UserRequestForSignature(_from, _value); } From faf9712db27d7f3a22eda384f2131368791dbfe1 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Fri, 11 Jan 2019 11:27:36 -0300 Subject: [PATCH 040/187] move reward logic to RewardableBridge --- .../upgradeable_contracts/BasicHomeBridge.sol | 61 +----------------- .../RewardableBridge.sol | 63 +++++++++++++++++++ .../erc20_to_native/HomeBridgeErcToNative.sol | 13 +++- 3 files changed, 74 insertions(+), 63 deletions(-) create mode 100644 contracts/upgradeable_contracts/RewardableBridge.sol diff --git a/contracts/upgradeable_contracts/BasicHomeBridge.sol b/contracts/upgradeable_contracts/BasicHomeBridge.sol index 778e6d2f2..d068a08cf 100644 --- a/contracts/upgradeable_contracts/BasicHomeBridge.sol +++ b/contracts/upgradeable_contracts/BasicHomeBridge.sol @@ -5,11 +5,9 @@ import "../libraries/SafeMath.sol"; import "openzeppelin-solidity/contracts/token/ERC20/ERC20Basic.sol"; import "./Validatable.sol"; import "../libraries/Message.sol"; -import "./OwnedUpgradeability.sol"; -import "./Ownable.sol"; -contract BasicHomeBridge is EternalStorage, Validatable, Ownable, OwnedUpgradeability { +contract BasicHomeBridge is EternalStorage, Validatable { using SafeMath for uint256; event UserRequestForSignature(address recipient, uint256 value); @@ -82,16 +80,6 @@ contract BasicHomeBridge is EternalStorage, Validatable, Ownable, OwnedUpgradeab } } - function handleSignatureFeeDistribution(address feeManager, bytes message) internal { - address recipient; - uint256 amount; - bytes32 txHash; - address contractAddress; - (recipient, amount, txHash, contractAddress) = Message.parseMessage(message); - uint256 fee = calculateFee(amount, true, feeManager); - require(feeManager.delegatecall(abi.encodeWithSignature("distributeFeeFromSignatures(uint256)", fee))); - } - function setMessagesSigned(bytes32 _hash, bool _status) internal { boolStorage[keccak256(abi.encodePacked("messagesSigned", _hash))] = _status; } @@ -173,51 +161,4 @@ contract BasicHomeBridge is EternalStorage, Validatable, Ownable, OwnedUpgradeab function onFailedAffirmation(address, uint256, bytes32) internal { } - - function feeManagerContract() public view returns(address) { - return addressStorage[keccak256(abi.encodePacked("feeManagerContract"))]; - } - - function setFeeManagerContract(address _feeManager) public onlyOwner { - require(_feeManager == address(0) || isContract(_feeManager)); - addressStorage[keccak256(abi.encodePacked("feeManagerContract"))] = _feeManager; - } - - function setFee(uint256 _fee) external onlyIfOwnerOfProxy { - require(feeManagerContract().delegatecall(abi.encodeWithSignature("setFee(uint256)", _fee))); - } - - function getFee() public view returns(uint256) { - uint256 fee; - bytes memory callData = abi.encodeWithSignature("getFee()"); - address feeManager = feeManagerContract(); - assembly { - let result := delegatecall(gas, feeManager, add(callData, 0x20), mload(callData), 0, 32) - fee := mload(0) - - switch result - case 0 { revert(0, 0) } - } - return fee; - } - - function isContract(address _addr) internal view returns (bool) - { - uint length; - assembly { length := extcodesize(_addr) } - return length > 0; - } - - function calculateFee(uint256 _value, bool _recover, address _impl) internal view returns(uint256) { - uint256 fee; - bytes memory callData = abi.encodeWithSignature("calculateFee(uint256,bool)", _value, _recover); - assembly { - let result := delegatecall(gas, _impl, add(callData, 0x20), mload(callData), 0, 32) - fee := mload(0) - - switch result - case 0 { revert(0, 0) } - } - return fee; - } } diff --git a/contracts/upgradeable_contracts/RewardableBridge.sol b/contracts/upgradeable_contracts/RewardableBridge.sol new file mode 100644 index 000000000..30d44cfac --- /dev/null +++ b/contracts/upgradeable_contracts/RewardableBridge.sol @@ -0,0 +1,63 @@ +pragma solidity 0.4.24; + +import "./OwnedUpgradeability.sol"; +import "./Ownable.sol"; + + +contract RewardableBridge is Ownable, OwnedUpgradeability { + + function setFee(uint256 _fee) external onlyIfOwnerOfProxy { + require(feeManagerContract().delegatecall(abi.encodeWithSignature("setFee(uint256)", _fee))); + } + + function getFee() public view returns(uint256) { + uint256 fee; + bytes memory callData = abi.encodeWithSignature("getFee()"); + address feeManager = feeManagerContract(); + assembly { + let result := delegatecall(gas, feeManager, add(callData, 0x20), mload(callData), 0, 32) + fee := mload(0) + + switch result + case 0 { revert(0, 0) } + } + return fee; + } + + function feeManagerContract() public view returns(address) { + return addressStorage[keccak256(abi.encodePacked("feeManagerContract"))]; + } + + function setFeeManagerContract(address _feeManager) public onlyOwner { + require(_feeManager == address(0) || isContract(_feeManager)); + addressStorage[keccak256(abi.encodePacked("feeManagerContract"))] = _feeManager; + } + + function isContract(address _addr) internal view returns (bool) + { + uint length; + assembly { length := extcodesize(_addr) } + return length > 0; + } + + function calculateFee(uint256 _value, bool _recover, address _impl) internal view returns(uint256) { + uint256 fee; + bytes memory callData = abi.encodeWithSignature("calculateFee(uint256,bool)", _value, _recover); + assembly { + let result := delegatecall(gas, _impl, add(callData, 0x20), mload(callData), 0, 32) + fee := mload(0) + + switch result + case 0 { revert(0, 0) } + } + return fee; + } + + function distributeFeeFromSignatures(uint256 _fee, address _feeManager) internal { + require(_feeManager.delegatecall(abi.encodeWithSignature("distributeFeeFromSignatures(uint256)", _fee))); + } + + function distributeFeeFromAffirmation(uint256 _fee, address _feeManager) internal { + require(_feeManager.delegatecall(abi.encodeWithSignature("distributeFeeFromAffirmation(uint256)", _fee))); + } +} diff --git a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol index 5432962fe..897a8a874 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol @@ -8,9 +8,10 @@ import "../../ERC677Receiver.sol"; import "../BasicHomeBridge.sol"; import "../ERC677Bridge.sol"; import "../OverdrawManagement.sol"; +import "../RewardableBridge.sol"; -contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, OverdrawManagement { +contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, OverdrawManagement, RewardableBridge { event AmountLimitExceeded(address recipient, uint256 value, bytes32 transactionHash); @@ -95,7 +96,7 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, address feeManager = feeManagerContract(); if (feeManager != address(0)) { uint256 fee = calculateFee(valueToMint, false, feeManager); - require(feeManager.delegatecall(abi.encodeWithSignature("distributeFeeFromAffirmation(uint256)", fee))); + distributeFeeFromAffirmation(fee, feeManager); valueToMint = valueToMint.sub(fee); } blockReward.addExtraReceiver(valueToMint, _recipient); @@ -105,7 +106,13 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, function onSignaturesCollected(bytes _message) internal { address feeManager = feeManagerContract(); if (feeManager != address(0)) { - handleSignatureFeeDistribution(feeManager, _message); + address recipient; + uint256 amount; + bytes32 txHash; + address contractAddress; + (recipient, amount, txHash, contractAddress) = Message.parseMessage(_message); + uint256 fee = calculateFee(amount, true, feeManager); + distributeFeeFromSignatures(fee, feeManager); } } From 51708637ac1a46d1657f5fd588a1814685c60e89 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Fri, 11 Jan 2019 11:46:25 -0300 Subject: [PATCH 041/187] Update send usage on onSignatureFeeDistribution --- contracts/upgradeable_contracts/Sacrifice.sol | 8 ++++++++ .../erc20_to_native/FeeManagerErcToNative.sol | 6 +++++- 2 files changed, 13 insertions(+), 1 deletion(-) create mode 100644 contracts/upgradeable_contracts/Sacrifice.sol diff --git a/contracts/upgradeable_contracts/Sacrifice.sol b/contracts/upgradeable_contracts/Sacrifice.sol new file mode 100644 index 000000000..d82b35e91 --- /dev/null +++ b/contracts/upgradeable_contracts/Sacrifice.sol @@ -0,0 +1,8 @@ +pragma solidity 0.4.24; + + +contract Sacrifice { + constructor(address _recipient) public payable { + selfdestruct(_recipient); + } +} diff --git a/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol index 4a2d2ca35..645241a33 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol @@ -2,6 +2,8 @@ pragma solidity 0.4.24; import "../BaseFeeManager.sol"; import "../../IBlockReward.sol"; +import "../Sacrifice.sol"; + contract FeeManagerErcToNative is BaseFeeManager { @@ -15,6 +17,8 @@ contract FeeManagerErcToNative is BaseFeeManager { } function onSignatureFeeDistribution(address _rewardAddress, uint256 _fee) internal { - _rewardAddress.send(_fee); + if (!_rewardAddress.send(_fee)) { + (new Sacrifice).value(_fee)(_rewardAddress); + } } } From 98dfc8becfaf7aa4fbd2ae2b9440c0032cc3293c Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Fri, 11 Jan 2019 12:31:24 -0300 Subject: [PATCH 042/187] Replace delegatecall with callcode on calculateFee --- contracts/upgradeable_contracts/BaseFeeManager.sol | 2 +- contracts/upgradeable_contracts/RewardableBridge.sol | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/contracts/upgradeable_contracts/BaseFeeManager.sol b/contracts/upgradeable_contracts/BaseFeeManager.sol index 4cb2efce9..af8781e07 100644 --- a/contracts/upgradeable_contracts/BaseFeeManager.sol +++ b/contracts/upgradeable_contracts/BaseFeeManager.sol @@ -10,7 +10,7 @@ contract BaseFeeManager is EternalStorage { event FeeUpdated(uint256 fee); - function calculateFee(uint256 _value, bool _recover) external payable returns(uint256) { + function calculateFee(uint256 _value, bool _recover) external view returns(uint256) { uint256 fee = getFee(); uint256 eth = 1 ether; if (!_recover) { diff --git a/contracts/upgradeable_contracts/RewardableBridge.sol b/contracts/upgradeable_contracts/RewardableBridge.sol index 30d44cfac..b3a0610f3 100644 --- a/contracts/upgradeable_contracts/RewardableBridge.sol +++ b/contracts/upgradeable_contracts/RewardableBridge.sol @@ -44,7 +44,7 @@ contract RewardableBridge is Ownable, OwnedUpgradeability { uint256 fee; bytes memory callData = abi.encodeWithSignature("calculateFee(uint256,bool)", _value, _recover); assembly { - let result := delegatecall(gas, _impl, add(callData, 0x20), mload(callData), 0, 32) + let result := callcode(gas, _impl, 0x0, add(callData, 0x20), mload(callData), 0, 32) fee := mload(0) switch result From d5b9bb5dcae9b793e31f5a1ad16d82a56cdcd63c Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Fri, 11 Jan 2019 17:21:55 -0300 Subject: [PATCH 043/187] Add fee tests for 5 validators --- test/erc_to_native/home_bridge.test.js | 221 ++++++++++++++++++++++++- 1 file changed, 220 insertions(+), 1 deletion(-) diff --git a/test/erc_to_native/home_bridge.test.js b/test/erc_to_native/home_bridge.test.js index 81ad287fd..74b486fbb 100644 --- a/test/erc_to_native/home_bridge.test.js +++ b/test/erc_to_native/home_bridge.test.js @@ -962,6 +962,84 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { updatedBalanceRewardAddress2.should.be.bignumber.equal(initialBalanceRewardAddress2.add(feePerValidator)) updatedBalanceRewardAddress3.should.be.bignumber.equal(initialBalanceRewardAddress3.add(feePerValidator)) }) + it('should distribute fee to 5 validators', async () => { + // Initialize + const owner = accounts[0] + const proxyOwner = accounts[0] + const validators = [accounts[0], accounts[1], accounts[2], accounts[3], accounts[4]] + const rewards = [accounts[5], accounts[6], accounts[7], accounts[8], accounts[9]] + const requiredSignatures = 5 + const rewardableValidators = await RewardableValidators.new() + const homeBridgeImpl = await HomeBridge.new(); + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled + const homeBridge = await HomeBridge.at(storageProxy.address); + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + await blockRewardContract.sendTransaction({ + from: accounts[0], + value: oneEther + }).should.be.fulfilled + + // Given + const value = halfEther; + // 0.1% fee + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeAmount = value.mul(web3.toBigNumber(fee)) + const feePerValidator = feeAmount.div(web3.toBigNumber(5)) + const feeManager = await FeeManagerErcToNative.new() + await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled + await homeBridge.setFee(feeInWei, { from: proxyOwner }).should.be.fulfilled + + const recipient = "0xf4bef13f9f4f2b203faf0c3cbbaabe1afe056955"; + const balanceBefore = await web3.eth.getBalance(recipient) + + const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const initialBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const initialBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + const initialBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) + const initialBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) + + + const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + + // When + const { logs: logsValidator1 } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[1]}).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[2]}).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[3]}).should.be.fulfilled + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[4]}).should.be.fulfilled + + // Then + logsValidator1.length.should.be.equals(1) + + logs[0].event.should.be.equal("SignedForAffirmation"); + logs[0].args.should.be.deep.equal({ + signer: validators[4], + transactionHash + }); + logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].args.should.be.deep.equal({ + recipient, + value, + transactionHash + }) + const balanceAfter = await web3.eth.getBalance(recipient) + balanceAfter.should.be.bignumber.equal(balanceBefore.add(value.sub(feeAmount))) + + const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + const updatedBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) + const updatedBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) + + updatedBalanceRewardAddress1.should.be.bignumber.equal(initialBalanceRewardAddress1.add(feePerValidator)) + updatedBalanceRewardAddress2.should.be.bignumber.equal(initialBalanceRewardAddress2.add(feePerValidator)) + updatedBalanceRewardAddress3.should.be.bignumber.equal(initialBalanceRewardAddress3.add(feePerValidator)) + updatedBalanceRewardAddress4.should.be.bignumber.equal(initialBalanceRewardAddress4.add(feePerValidator)) + updatedBalanceRewardAddress5.should.be.bignumber.equal(initialBalanceRewardAddress5.add(feePerValidator)) + }) }) describe('#feeManager_fallback', function () { let homeBridge, rewardableValidators @@ -1061,8 +1139,149 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { finalBridgeBalance.should.be.bignumber.equal('0') const rewardAddressBalanceAfter = await web3.eth.getBalance(rewards[0]) - console.log("rewardAddressBalanceAfter", rewardAddressBalanceAfter, "rewardAddressBalanceBefore", rewardAddressBalanceBefore) rewardAddressBalanceAfter.should.be.bignumber.equal(rewardAddressBalanceBefore.add(feeAmount)) }) + it('should distribute fee to 3 validators', async () => { + // Initialize + const owner = accounts[9] + const proxyOwner = accounts[0] + const validators = [accounts[1], accounts[2], accounts[3]] + const rewards = [accounts[4], accounts[5], accounts[6]] + const requiredSignatures = 3 + const rewardableValidators = await RewardableValidators.new() + const homeBridgeImpl = await HomeBridge.new(); + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled + const homeBridge = await HomeBridge.at(storageProxy.address); + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + await blockRewardContract.addMintedTotallyByBridge(oneEther, homeBridge.address) + + // Given + // 0.1% fee + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeManager = await FeeManagerErcToNative.new() + const feePerValidator = web3.toBigNumber(166666666666666) + await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled + await homeBridge.setFee(feeInWei, { from: proxyOwner }).should.be.fulfilled + + const recipient = accounts[7]; + const initialValue = halfEther + const value = halfEther.mul(web3.toBigNumber(1-fee)); + const feeAmount = initialValue.mul(web3.toBigNumber(fee)) + const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + + const initialBridgeBalance = await web3.eth.getBalance(homeBridge.address) + initialBridgeBalance.should.be.bignumber.equal('0') + + const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const initialBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const initialBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + + // When + await homeBridge.sendTransaction({ from: recipient, value: initialValue }).should.be.fulfilled + + const afterTransferBridgeBalance = await web3.eth.getBalance(homeBridge.address) + afterTransferBridgeBalance.should.be.bignumber.equal(feeAmount) + + const message = createMessage(recipient, value, transactionHash, homeBridge.address); + + const signature = await sign(validators[0], message) + const signature2 = await sign(validators[1], message) + const signature3 = await sign(validators[2], message) + + await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled; + await homeBridge.submitSignature(signature2, message, {from: validators[1]}).should.be.fulfilled; + const { logs } = await homeBridge.submitSignature(signature3, message, {from: validators[2]}).should.be.fulfilled; + + // Then + logs.length.should.be.equal(2) + logs[1].event.should.be.equal('CollectedSignatures') + + const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + + updatedBalanceRewardAddress1.should.be.bignumber.equal(initialBalanceRewardAddress1.add(feePerValidator)) + updatedBalanceRewardAddress2.should.be.bignumber.equal(initialBalanceRewardAddress2.add(feePerValidator)) + updatedBalanceRewardAddress3.should.be.bignumber.equal(initialBalanceRewardAddress3.add(feePerValidator)) + }) + it('should distribute fee to 5 validators', async () => { + // Initialize + const owner = accounts[0] + const proxyOwner = accounts[0] + const validators = [accounts[0], accounts[1], accounts[2], accounts[3], accounts[4]] + const rewards = [accounts[5], accounts[6], accounts[7], accounts[8], accounts[9]] + const requiredSignatures = 5 + const rewardableValidators = await RewardableValidators.new() + const homeBridgeImpl = await HomeBridge.new(); + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled + const homeBridge = await HomeBridge.at(storageProxy.address); + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + await blockRewardContract.addMintedTotallyByBridge(oneEther, homeBridge.address) + + // Given + // 0.1% fee + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeManager = await FeeManagerErcToNative.new() + await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled + await homeBridge.setFee(feeInWei, { from: proxyOwner }).should.be.fulfilled + + const recipient = accounts[0]; + const initialValue = halfEther + const value = halfEther.mul(web3.toBigNumber(1-fee)); + const feeAmount = initialValue.mul(web3.toBigNumber(fee)) + const feePerValidator = feeAmount.div(web3.toBigNumber(5)) + const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + + const initialBridgeBalance = await web3.eth.getBalance(homeBridge.address) + initialBridgeBalance.should.be.bignumber.equal('0') + + const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const initialBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const initialBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + const initialBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) + const initialBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) + + // When + await homeBridge.sendTransaction({ from: recipient, value: initialValue }).should.be.fulfilled + + const afterTransferBridgeBalance = await web3.eth.getBalance(homeBridge.address) + afterTransferBridgeBalance.should.be.bignumber.equal(feeAmount) + + const message = createMessage(recipient, value, transactionHash, homeBridge.address); + + const signature = await sign(validators[0], message) + const signature2 = await sign(validators[1], message) + const signature3 = await sign(validators[2], message) + const signature4 = await sign(validators[3], message) + const signature5 = await sign(validators[4], message) + + await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled; + await homeBridge.submitSignature(signature2, message, {from: validators[1]}).should.be.fulfilled; + await homeBridge.submitSignature(signature3, message, {from: validators[2]}).should.be.fulfilled; + await homeBridge.submitSignature(signature4, message, {from: validators[3]}).should.be.fulfilled; + const { logs } = await homeBridge.submitSignature(signature5, message, {from: validators[4]}).should.be.fulfilled; + + // Then + logs.length.should.be.equal(2) + logs[1].event.should.be.equal('CollectedSignatures') + + const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + const updatedBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) + const updatedBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) + + updatedBalanceRewardAddress1.should.be.bignumber.equal(initialBalanceRewardAddress1.add(feePerValidator)) + updatedBalanceRewardAddress2.should.be.bignumber.equal(initialBalanceRewardAddress2.add(feePerValidator)) + updatedBalanceRewardAddress3.should.be.bignumber.equal(initialBalanceRewardAddress3.add(feePerValidator)) + updatedBalanceRewardAddress4.should.be.bignumber.equal(initialBalanceRewardAddress4.add(feePerValidator)) + updatedBalanceRewardAddress5.should.be.bignumber.equal(initialBalanceRewardAddress5.add(feePerValidator)) + }) }) }) From 86de261ebd97633b4e55787301c0710e55b8d2d6 Mon Sep 17 00:00:00 2001 From: Tal Beja Date: Mon, 14 Jan 2019 10:58:43 +0200 Subject: [PATCH 044/187] first version of BridgeMapper conract --- .gitignore | 1 + .../upgradeable_contracts/BridgeMapper.sol | 69 + deploy/package-lock.json | 1401 +++-- package-lock.json | 5291 +++++++++++------ package.json | 2 +- 5 files changed, 4265 insertions(+), 2499 deletions(-) create mode 100644 contracts/upgradeable_contracts/BridgeMapper.sol diff --git a/.gitignore b/.gitignore index de8a6acc7..1bef161d2 100644 --- a/.gitignore +++ b/.gitignore @@ -2,3 +2,4 @@ node_modules build flats .node* +deploy/bridgeDeploymentOutput.txt diff --git a/contracts/upgradeable_contracts/BridgeMapper.sol b/contracts/upgradeable_contracts/BridgeMapper.sol new file mode 100644 index 000000000..03d3cb440 --- /dev/null +++ b/contracts/upgradeable_contracts/BridgeMapper.sol @@ -0,0 +1,69 @@ +pragma solidity 0.4.24; + +import "./Ownable.sol"; +import "../upgradeability/EternalStorage.sol"; + +contract BridgeMapper is EternalStorage, Ownable { + + event NewBridgeDeployed(address indexed homeBridge, address indexed foreignBridge, address indexed homeToken, address indexed foreignToken, uint256 homeStratBlock, uint256 foreignStartBlock); + + function homeBridgeByForeignToken(address _foreignToken) public view returns(address) { + return addressStorage[keccak256(abi.encodePacked("homeBridgeByForeignToken", _foreignToken))]; + } + + function setHomeBridgeByForeignToken(address _foreignToken, address _homeBridge) internal onlyOwner { + require(_foreignToken != address(0)); + require(_homeBridge != address(0)); + addressStorage[keccak256(abi.encodePacked("homeBridgeByForeignToken", _foreignToken))] = _homeBridge; + } + + function foreignBridgeByForeignToken(address _foreignToken) public view returns(address) { + return addressStorage[keccak256(abi.encodePacked("foreignBridgeByForeignToken", _foreignToken))]; + } + + function setForeignBridgeByForeignToken(address _foreignToken, address _foreignBridge) internal onlyOwner { + require(_foreignToken != address(0)); + require(_foreignBridge != address(0)); + addressStorage[keccak256(abi.encodePacked("foreignBridgeByForeignToken", _foreignToken))] = _foreignBridge; + } + + function homeTokenByForeignToken(address _foreignToken) public view returns(address) { + return addressStorage[keccak256(abi.encodePacked("homeTokenByForeignToken", _foreignToken))]; + } + + function setHomeTokenByForeignToken(address _foreignToken, address _homeToken) internal onlyOwner { + require(_foreignToken != address(0)); + require(_homeToken != address(0)); + addressStorage[keccak256(abi.encodePacked("homeTokenByForeignToken", _foreignToken))] = _homeToken; + } + + function homeStratBlockByForeignToken(address _foreignToken) public view returns(uint256) { + return uintStorage[keccak256(abi.encodePacked("homeStratBlockByForeignToken", _foreignToken))]; + } + + function setHomeStratBlockByForeignToken(address _foreignToken, uint256 _homeStratBlock) internal onlyOwner { + require(_foreignToken != address(0)); + require(_homeStratBlock != 0); + uintStorage[keccak256(abi.encodePacked("homeStratBlockByForeignToken", _foreignToken))] = _homeStratBlock; + } + + function foreignStartBlockByForeignToken(address _foreignToken) public view returns(uint256) { + return uintStorage[keccak256(abi.encodePacked("foreignStartBlockByForeignToken", _foreignToken))]; + } + + function setForeignStartBlockByForeignToken(address _foreignToken, uint256 _foreignStartBlock) internal onlyOwner { + require(_foreignToken != address(0)); + require(_foreignStartBlock != 0); + uintStorage[keccak256(abi.encodePacked("foreignStartBlockByForeignToken", _foreignToken))] = _foreignStartBlock; + } + + function addBridgeMapping(address _homeBridge, address _foreignBridge, address _homeToken, address _foreignToken, uint256 _homeStratBlock, uint256 _foreignStartBlock) public onlyOwner { + setHomeBridgeByForeignToken(_foreignToken, _homeBridge); + setForeignBridgeByForeignToken(_foreignToken, _foreignBridge); + setHomeTokenByForeignToken(_foreignToken, _homeToken); + setHomeStratBlockByForeignToken(_foreignToken, _homeStratBlock); + setForeignStartBlockByForeignToken(_foreignToken, _foreignStartBlock); + emit NewBridgeDeployed(_homeBridge, _foreignBridge, _homeToken, _foreignToken, _homeStratBlock, _foreignStartBlock); + } + +} \ No newline at end of file diff --git a/deploy/package-lock.json b/deploy/package-lock.json index a63423650..a73229982 100644 --- a/deploy/package-lock.json +++ b/deploy/package-lock.json @@ -10,7 +10,7 @@ "integrity": "sha512-OfC2uemaknXr87bdLUkWog7nYuliM9Ij5HUcajsVcMCpQrcLmtxRbVFTIqmcSkSeYRBFBRxs2FiUqFJDLdiebA==", "dev": true, "requires": { - "@babel/highlight": "^7.0.0" + "@babel/highlight": "7.0.0" } }, "@babel/highlight": { @@ -19,9 +19,9 @@ "integrity": "sha512-UFMC4ZeFC48Tpvj7C8UgLvtkaUuovQX+5xNWrsIoMG8o2z+XFKjKaN9iVmS84dPwVN00W4wPmqvYoZF3EGAsfw==", "dev": true, "requires": { - "chalk": "^2.0.0", - "esutils": "^2.0.2", - "js-tokens": "^4.0.0" + "chalk": "2.1.0", + "esutils": "2.0.2", + "js-tokens": "4.0.0" } }, "accepts": { @@ -29,7 +29,7 @@ "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.5.tgz", "integrity": "sha1-63d99gEXI6OxTopywIBcjoZ0a9I=", "requires": { - "mime-types": "~2.1.18", + "mime-types": "2.1.18", "negotiator": "0.6.1" } }, @@ -44,7 +44,7 @@ "integrity": "sha512-JY+iV6r+cO21KtntVvFkD+iqjtdpRUpGqKWgfkCdZq1R+kbreEl8EcdcJR4SmiIgsIQT33s6QzheQ9a275Q8xw==", "dev": true, "requires": { - "acorn": "^5.0.3" + "acorn": "5.5.3" } }, "acorn-object-rest-spread": { @@ -52,7 +52,7 @@ "resolved": "https://registry.npmjs.org/acorn-object-rest-spread/-/acorn-object-rest-spread-1.1.0.tgz", "integrity": "sha1-eGma790Y7DGCyq2t9S4ml8BI9HY=", "requires": { - "acorn": "^5.0.3" + "acorn": "5.5.3" } }, "ajv": { @@ -60,10 +60,10 @@ "resolved": "https://registry.npmjs.org/ajv/-/ajv-5.5.2.tgz", "integrity": "sha1-c7Xuyj+rZT49P5Qis0GtQiBdyWU=", "requires": { - "co": "^4.6.0", - "fast-deep-equal": "^1.0.0", - "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.3.0" + "co": "4.6.0", + "fast-deep-equal": "1.1.0", + "fast-json-stable-stringify": "2.0.0", + "json-schema-traverse": "0.3.1" } }, "ajv-keywords": { @@ -95,7 +95,7 @@ "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz", "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==", "requires": { - "color-convert": "^1.9.0" + "color-convert": "1.9.1" } }, "any-promise": { @@ -109,7 +109,7 @@ "integrity": "sha512-o5Roy6tNG4SL/FOkCAN6RzjiakZS25RLYFrcMttJqbdd8BWrnA+fGz57iN5Pb06pvBGvl5gQ0B48dJlslXvoTg==", "dev": true, "requires": { - "sprintf-js": "~1.0.2" + "sprintf-js": "1.0.3" } }, "array-flatten": { @@ -122,7 +122,7 @@ "resolved": "https://registry.npmjs.org/array-union/-/array-union-1.0.2.tgz", "integrity": "sha1-mjRBDk9OPaI96jdb5b5w8kd47Dk=", "requires": { - "array-uniq": "^1.0.1" + "array-uniq": "1.0.3" } }, "array-uniq": { @@ -146,9 +146,9 @@ "resolved": "https://registry.npmjs.org/asn1.js/-/asn1.js-4.10.1.tgz", "integrity": "sha512-p32cOF5q0Zqs9uBiONKYLm6BClCoBCM5O9JfeUSlnQLBTxYdTK+pW+nXflm8UkKd2UYlEbYz5qEi0JuZR9ckSw==", "requires": { - "bn.js": "^4.0.0", - "inherits": "^2.0.1", - "minimalistic-assert": "^1.0.0" + "bn.js": "4.11.8", + "inherits": "2.0.3", + "minimalistic-assert": "1.0.0" } }, "assert-plus": { @@ -181,8 +181,8 @@ "resolved": "https://registry.npmjs.org/babel-runtime/-/babel-runtime-6.25.0.tgz", "integrity": "sha1-M7mOql1IK7AajRqmtDetKwGuxBw=", "requires": { - "core-js": "^2.4.0", - "regenerator-runtime": "^0.10.0" + "core-js": "2.5.4", + "regenerator-runtime": "0.10.5" } }, "balanced-match": { @@ -201,7 +201,7 @@ "integrity": "sha1-Y7xdy2EzG5K8Bf1SiVPDNGKgb40=", "optional": true, "requires": { - "tweetnacl": "^0.14.3" + "tweetnacl": "0.14.5" } }, "bindings": { @@ -214,7 +214,7 @@ "resolved": "https://registry.npmjs.org/bip66/-/bip66-1.1.5.tgz", "integrity": "sha1-AfqHSHhcpwlV1QESF9GzE5lpyiI=", "requires": { - "safe-buffer": "^5.0.1" + "safe-buffer": "5.1.1" } }, "bl": { @@ -222,8 +222,8 @@ "resolved": "https://registry.npmjs.org/bl/-/bl-1.2.2.tgz", "integrity": "sha512-e8tQYnZodmebYDWGH7KMRvtzKXaJHx3BbilrgZCfvyLUYdKpK1t5PSPmpkny/SgiTSCnjfLW7v5rlONXVFkQEA==", "requires": { - "readable-stream": "^2.3.5", - "safe-buffer": "^5.1.1" + "readable-stream": "2.3.5", + "safe-buffer": "5.1.1" } }, "block-stream": { @@ -231,7 +231,7 @@ "resolved": "https://registry.npmjs.org/block-stream/-/block-stream-0.0.9.tgz", "integrity": "sha1-E+v+d4oDIFz+A3UUgeu0szAMEmo=", "requires": { - "inherits": "~2.0.0" + "inherits": "2.0.3" } }, "bluebird": { @@ -250,15 +250,15 @@ "integrity": "sha1-h2eKGdhLR9hZuDGZvVm84iKxBFQ=", "requires": { "bytes": "3.0.0", - "content-type": "~1.0.4", + "content-type": "1.0.4", "debug": "2.6.9", - "depd": "~1.1.1", - "http-errors": "~1.6.2", + "depd": "1.1.2", + "http-errors": "1.6.2", "iconv-lite": "0.4.19", - "on-finished": "~2.3.0", + "on-finished": "2.3.0", "qs": "6.5.1", "raw-body": "2.3.2", - "type-is": "~1.6.15" + "type-is": "1.6.16" } }, "boom": { @@ -266,7 +266,7 @@ "resolved": "https://registry.npmjs.org/boom/-/boom-4.3.1.tgz", "integrity": "sha1-T4owBctKfjiJ90kDD9JbluAdLjE=", "requires": { - "hoek": "4.x.x" + "hoek": "4.2.1" } }, "brace-expansion": { @@ -274,7 +274,7 @@ "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", "requires": { - "balanced-match": "^1.0.0", + "balanced-match": "1.0.0", "concat-map": "0.0.1" } }, @@ -288,12 +288,12 @@ "resolved": "https://registry.npmjs.org/browserify-aes/-/browserify-aes-1.1.1.tgz", "integrity": "sha512-UGnTYAnB2a3YuYKIRy1/4FB2HdM866E0qC46JXvVTYKlBlZlnvfpSfY6OKfXZAkv70eJ2a1SqzpAo5CRhZGDFg==", "requires": { - "buffer-xor": "^1.0.3", - "cipher-base": "^1.0.0", - "create-hash": "^1.1.0", - "evp_bytestokey": "^1.0.3", - "inherits": "^2.0.1", - "safe-buffer": "^5.0.1" + "buffer-xor": "1.0.3", + "cipher-base": "1.0.4", + "create-hash": "1.1.3", + "evp_bytestokey": "1.0.3", + "inherits": "2.0.3", + "safe-buffer": "5.1.1" } }, "browserify-cipher": { @@ -301,9 +301,9 @@ "resolved": "https://registry.npmjs.org/browserify-cipher/-/browserify-cipher-1.0.0.tgz", "integrity": "sha1-mYgkSHS/XtTijalWZtzWasj8Njo=", "requires": { - "browserify-aes": "^1.0.4", - "browserify-des": "^1.0.0", - "evp_bytestokey": "^1.0.0" + "browserify-aes": "1.1.1", + "browserify-des": "1.0.0", + "evp_bytestokey": "1.0.3" } }, "browserify-des": { @@ -311,9 +311,9 @@ "resolved": "https://registry.npmjs.org/browserify-des/-/browserify-des-1.0.0.tgz", "integrity": "sha1-2qJ3cXRwki7S/hhZQRihdUOXId0=", "requires": { - "cipher-base": "^1.0.1", - "des.js": "^1.0.0", - "inherits": "^2.0.1" + "cipher-base": "1.0.4", + "des.js": "1.0.0", + "inherits": "2.0.3" } }, "browserify-rsa": { @@ -321,8 +321,8 @@ "resolved": "https://registry.npmjs.org/browserify-rsa/-/browserify-rsa-4.0.1.tgz", "integrity": "sha1-IeCr+vbyApzy+vsTNWenAdQTVSQ=", "requires": { - "bn.js": "^4.1.0", - "randombytes": "^2.0.1" + "bn.js": "4.11.8", + "randombytes": "2.0.6" } }, "browserify-sha3": { @@ -330,7 +330,7 @@ "resolved": "https://registry.npmjs.org/browserify-sha3/-/browserify-sha3-0.0.1.tgz", "integrity": "sha1-P/NKMAbvFcD7NWflQbkaI0ASPRE=", "requires": { - "js-sha3": "^0.3.1" + "js-sha3": "0.3.1" } }, "browserify-sign": { @@ -338,13 +338,13 @@ "resolved": "https://registry.npmjs.org/browserify-sign/-/browserify-sign-4.0.4.tgz", "integrity": "sha1-qk62jl17ZYuqa/alfmMMvXqT0pg=", "requires": { - "bn.js": "^4.1.1", - "browserify-rsa": "^4.0.0", - "create-hash": "^1.1.0", - "create-hmac": "^1.1.2", - "elliptic": "^6.0.0", - "inherits": "^2.0.1", - "parse-asn1": "^5.0.0" + "bn.js": "4.11.8", + "browserify-rsa": "4.0.1", + "create-hash": "1.1.3", + "create-hmac": "1.1.6", + "elliptic": "6.4.0", + "inherits": "2.0.3", + "parse-asn1": "5.1.0" } }, "buffer": { @@ -352,8 +352,8 @@ "resolved": "https://registry.npmjs.org/buffer/-/buffer-5.1.0.tgz", "integrity": "sha512-YkIRgwsZwJWTnyQrsBTWefizHh+8GYj3kbL1BTiAQ/9pwpino0G7B2gp5tx/FUBqUlvtxV85KNR3mwfAtv15Yw==", "requires": { - "base64-js": "^1.0.2", - "ieee754": "^1.1.4" + "base64-js": "1.2.3", + "ieee754": "1.1.11" } }, "buffer-crc32": { @@ -393,7 +393,7 @@ "integrity": "sha1-lAhe9jWB7NPaqSREqP6U6CV3dR8=", "dev": true, "requires": { - "callsites": "^0.2.0" + "callsites": "0.2.0" } }, "callsites": { @@ -412,9 +412,9 @@ "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.1.0.tgz", "integrity": "sha512-LUHGS/dge4ujbXMJrnihYMcL4AoOweGnw9Tp3kQuqy1Kx5c1qKjqvMJZ6nVJPMWJtKCTN72ZogH3oeSO9g9rXQ==", "requires": { - "ansi-styles": "^3.1.0", - "escape-string-regexp": "^1.0.5", - "supports-color": "^4.0.0" + "ansi-styles": "3.2.1", + "escape-string-regexp": "1.0.5", + "supports-color": "4.5.0" } }, "chardet": { @@ -428,8 +428,8 @@ "resolved": "https://registry.npmjs.org/cipher-base/-/cipher-base-1.0.4.tgz", "integrity": "sha512-Kkht5ye6ZGmwv40uUDZztayT2ThLQGfnj/T71N/XzeZeo3nf8foyW7zGTsPYkEya3m5f3cAypH+qe7YOrM1U2Q==", "requires": { - "inherits": "^2.0.1", - "safe-buffer": "^5.0.1" + "inherits": "2.0.3", + "safe-buffer": "5.1.1" } }, "circular-json": { @@ -444,7 +444,7 @@ "integrity": "sha1-s12sN2R5+sw+lHR9QdDQ9SOP/LU=", "dev": true, "requires": { - "restore-cursor": "^2.0.0" + "restore-cursor": "2.0.0" } }, "cli-width": { @@ -463,7 +463,7 @@ "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.1.tgz", "integrity": "sha512-mjGanIiwQJskCC18rPR6OmrZ6fm2Lc7PeGFYwCmy5J34wC6F1PzdGL6xeMfmgicfYcNLGuVFA3WzXtIDCQSZxQ==", "requires": { - "color-name": "^1.1.1" + "color-name": "1.1.3" } }, "color-name": { @@ -476,7 +476,7 @@ "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.6.tgz", "integrity": "sha1-cj599ugBrFYTETp+RFqbactjKBg=", "requires": { - "delayed-stream": "~1.0.0" + "delayed-stream": "1.0.0" } }, "commander": { @@ -484,7 +484,7 @@ "resolved": "https://registry.npmjs.org/commander/-/commander-2.8.1.tgz", "integrity": "sha1-Br42f+v9oMMwqh4qBy09yXYkJdQ=", "requires": { - "graceful-readlink": ">= 1.0.0" + "graceful-readlink": "1.0.1" } }, "concat-map": { @@ -533,8 +533,8 @@ "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.4.tgz", "integrity": "sha1-K9OB8usgECAQXNUOpZ2mMJBpRoY=", "requires": { - "object-assign": "^4", - "vary": "^1" + "object-assign": "4.1.1", + "vary": "1.1.2" } }, "create-ecdh": { @@ -542,8 +542,8 @@ "resolved": "https://registry.npmjs.org/create-ecdh/-/create-ecdh-4.0.0.tgz", "integrity": "sha1-iIxyNZbN92EvZJgjPuvXo1MBc30=", "requires": { - "bn.js": "^4.1.0", - "elliptic": "^6.0.0" + "bn.js": "4.11.8", + "elliptic": "6.4.0" } }, "create-hash": { @@ -551,10 +551,10 @@ "resolved": "https://registry.npmjs.org/create-hash/-/create-hash-1.1.3.tgz", "integrity": "sha1-YGBCrIuSYnUPSDyt2rD1gZFy2P0=", "requires": { - "cipher-base": "^1.0.1", - "inherits": "^2.0.1", - "ripemd160": "^2.0.0", - "sha.js": "^2.4.0" + "cipher-base": "1.0.4", + "inherits": "2.0.3", + "ripemd160": "2.0.1", + "sha.js": "2.4.11" } }, "create-hmac": { @@ -562,12 +562,12 @@ "resolved": "https://registry.npmjs.org/create-hmac/-/create-hmac-1.1.6.tgz", "integrity": "sha1-rLniIaThe9sHbpBlfEK5PjcmzwY=", "requires": { - "cipher-base": "^1.0.3", - "create-hash": "^1.1.0", - "inherits": "^2.0.1", - "ripemd160": "^2.0.0", - "safe-buffer": "^5.0.1", - "sha.js": "^2.4.8" + "cipher-base": "1.0.4", + "create-hash": "1.1.3", + "inherits": "2.0.3", + "ripemd160": "2.0.1", + "safe-buffer": "5.1.1", + "sha.js": "2.4.11" } }, "cross-spawn": { @@ -576,11 +576,11 @@ "integrity": "sha512-eTVLrBSt7fjbDygz805pMnstIs2VTBNkRm0qxZd+M7A5XDdxVRWO5MxGBXZhjY4cqLYLdtrGqRf8mBPmzwSpWQ==", "dev": true, "requires": { - "nice-try": "^1.0.4", - "path-key": "^2.0.1", - "semver": "^5.5.0", - "shebang-command": "^1.2.0", - "which": "^1.2.9" + "nice-try": "1.0.5", + "path-key": "2.0.1", + "semver": "5.5.1", + "shebang-command": "1.2.0", + "which": "1.3.1" }, "dependencies": { "semver": { @@ -596,7 +596,7 @@ "resolved": "https://registry.npmjs.org/cryptiles/-/cryptiles-3.1.2.tgz", "integrity": "sha1-qJ+7Ig9c4l7FboxKqKT9e1sNKf4=", "requires": { - "boom": "5.x.x" + "boom": "5.2.0" }, "dependencies": { "boom": { @@ -604,7 +604,7 @@ "resolved": "https://registry.npmjs.org/boom/-/boom-5.2.0.tgz", "integrity": "sha512-Z5BTk6ZRe4tXXQlkqftmsAUANpXmuwlsF5Oov8ThoMbQRzdGTA1ngYRW160GexgOgjsFOKJz0LYhoNi+2AMBUw==", "requires": { - "hoek": "4.x.x" + "hoek": "4.2.1" } } } @@ -614,17 +614,17 @@ "resolved": "https://registry.npmjs.org/crypto-browserify/-/crypto-browserify-3.12.0.tgz", "integrity": "sha512-fz4spIh+znjO2VjL+IdhEpRJ3YN6sMzITSBijk6FK2UvTqruSQW+/cCZTSNsMiZNvUeq0CqurF+dAbyiGOY6Wg==", "requires": { - "browserify-cipher": "^1.0.0", - "browserify-sign": "^4.0.0", - "create-ecdh": "^4.0.0", - "create-hash": "^1.1.0", - "create-hmac": "^1.1.0", - "diffie-hellman": "^5.0.0", - "inherits": "^2.0.1", - "pbkdf2": "^3.0.3", - "public-encrypt": "^4.0.0", - "randombytes": "^2.0.0", - "randomfill": "^1.0.3" + "browserify-cipher": "1.0.0", + "browserify-sign": "4.0.4", + "create-ecdh": "4.0.0", + "create-hash": "1.1.3", + "create-hmac": "1.1.6", + "diffie-hellman": "5.0.2", + "inherits": "2.0.3", + "pbkdf2": "3.0.14", + "public-encrypt": "4.0.0", + "randombytes": "2.0.6", + "randomfill": "1.0.4" } }, "dashdash": { @@ -632,7 +632,7 @@ "resolved": "https://registry.npmjs.org/dashdash/-/dashdash-1.14.1.tgz", "integrity": "sha1-hTz6D3y+L+1d4gMmuN1YEDX24vA=", "requires": { - "assert-plus": "^1.0.0" + "assert-plus": "1.0.0" } }, "debug": { @@ -653,14 +653,14 @@ "resolved": "https://registry.npmjs.org/decompress/-/decompress-4.2.0.tgz", "integrity": "sha1-eu3YVCflqS2s/lVnSnxQXpbQH50=", "requires": { - "decompress-tar": "^4.0.0", - "decompress-tarbz2": "^4.0.0", - "decompress-targz": "^4.0.0", - "decompress-unzip": "^4.0.1", - "graceful-fs": "^4.1.10", - "make-dir": "^1.0.0", - "pify": "^2.3.0", - "strip-dirs": "^2.0.0" + "decompress-tar": "4.1.1", + "decompress-tarbz2": "4.1.1", + "decompress-targz": "4.1.1", + "decompress-unzip": "4.0.1", + "graceful-fs": "4.1.11", + "make-dir": "1.2.0", + "pify": "2.3.0", + "strip-dirs": "2.1.0" } }, "decompress-response": { @@ -668,7 +668,7 @@ "resolved": "https://registry.npmjs.org/decompress-response/-/decompress-response-3.3.0.tgz", "integrity": "sha1-gKTdMjdIOEv6JICDYirt7Jgq3/M=", "requires": { - "mimic-response": "^1.0.0" + "mimic-response": "1.0.0" } }, "decompress-tar": { @@ -676,9 +676,9 @@ "resolved": "https://registry.npmjs.org/decompress-tar/-/decompress-tar-4.1.1.tgz", "integrity": "sha512-JdJMaCrGpB5fESVyxwpCx4Jdj2AagLmv3y58Qy4GE6HMVjWz1FeVQk1Ct4Kye7PftcdOo/7U7UKzYBJgqnGeUQ==", "requires": { - "file-type": "^5.2.0", - "is-stream": "^1.1.0", - "tar-stream": "^1.5.2" + "file-type": "5.2.0", + "is-stream": "1.1.0", + "tar-stream": "1.5.5" } }, "decompress-tarbz2": { @@ -686,11 +686,11 @@ "resolved": "https://registry.npmjs.org/decompress-tarbz2/-/decompress-tarbz2-4.1.1.tgz", "integrity": "sha512-s88xLzf1r81ICXLAVQVzaN6ZmX4A6U4z2nMbOwobxkLoIIfjVMBg7TeguTUXkKeXni795B6y5rnvDw7rxhAq9A==", "requires": { - "decompress-tar": "^4.1.0", - "file-type": "^6.1.0", - "is-stream": "^1.1.0", - "seek-bzip": "^1.0.5", - "unbzip2-stream": "^1.0.9" + "decompress-tar": "4.1.1", + "file-type": "6.2.0", + "is-stream": "1.1.0", + "seek-bzip": "1.0.5", + "unbzip2-stream": "1.2.5" }, "dependencies": { "file-type": { @@ -705,9 +705,9 @@ "resolved": "https://registry.npmjs.org/decompress-targz/-/decompress-targz-4.1.1.tgz", "integrity": "sha512-4z81Znfr6chWnRDNfFNqLwPvm4db3WuZkqV+UgXQzSngG3CEKdBkw5jrv3axjjL96glyiiKjsxJG3X6WBZwX3w==", "requires": { - "decompress-tar": "^4.1.1", - "file-type": "^5.2.0", - "is-stream": "^1.1.0" + "decompress-tar": "4.1.1", + "file-type": "5.2.0", + "is-stream": "1.1.0" } }, "decompress-unzip": { @@ -715,10 +715,10 @@ "resolved": "https://registry.npmjs.org/decompress-unzip/-/decompress-unzip-4.0.1.tgz", "integrity": "sha1-3qrM39FK6vhVePczroIQ+bSEj2k=", "requires": { - "file-type": "^3.8.0", - "get-stream": "^2.2.0", - "pify": "^2.3.0", - "yauzl": "^2.4.2" + "file-type": "3.9.0", + "get-stream": "2.3.1", + "pify": "2.3.0", + "yauzl": "2.9.1" }, "dependencies": { "file-type": { @@ -731,8 +731,8 @@ "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-2.3.1.tgz", "integrity": "sha1-Xzj5PzRgCWZu4BUKBUFn+Rvdld4=", "requires": { - "object-assign": "^4.0.1", - "pinkie-promise": "^2.0.0" + "object-assign": "4.1.1", + "pinkie-promise": "2.0.1" } } } @@ -748,7 +748,7 @@ "integrity": "sha512-3MqfYKj2lLzdMSf8ZIZE/V+Zuy+BgD6f164e8K2w7dgnpKArBDerGYpM46IYYcjnkdPNMjPk9A6VFB8+3SKlXQ==", "dev": true, "requires": { - "object-keys": "^1.0.12" + "object-keys": "1.0.12" } }, "del": { @@ -757,13 +757,13 @@ "integrity": "sha1-wSyYHQZ4RshLyvhiz/kw2Qf/0ag=", "dev": true, "requires": { - "globby": "^5.0.0", - "is-path-cwd": "^1.0.0", - "is-path-in-cwd": "^1.0.0", - "object-assign": "^4.0.1", - "pify": "^2.0.0", - "pinkie-promise": "^2.0.0", - "rimraf": "^2.2.8" + "globby": "5.0.0", + "is-path-cwd": "1.0.0", + "is-path-in-cwd": "1.0.1", + "object-assign": "4.1.1", + "pify": "2.3.0", + "pinkie-promise": "2.0.1", + "rimraf": "2.6.2" }, "dependencies": { "globby": { @@ -772,12 +772,12 @@ "integrity": "sha1-69hGZ8oNuzMLmbz8aOrCvFQ3Dg0=", "dev": true, "requires": { - "array-union": "^1.0.1", - "arrify": "^1.0.0", - "glob": "^7.0.3", - "object-assign": "^4.0.1", - "pify": "^2.0.0", - "pinkie-promise": "^2.0.0" + "array-union": "1.0.2", + "arrify": "1.0.1", + "glob": "7.1.2", + "object-assign": "4.1.1", + "pify": "2.3.0", + "pinkie-promise": "2.0.1" } } } @@ -797,8 +797,8 @@ "resolved": "https://registry.npmjs.org/des.js/-/des.js-1.0.0.tgz", "integrity": "sha1-wHTS4qpqipoH29YfmhXCzYPsjsw=", "requires": { - "inherits": "^2.0.1", - "minimalistic-assert": "^1.0.0" + "inherits": "2.0.3", + "minimalistic-assert": "1.0.0" } }, "destroy": { @@ -811,9 +811,9 @@ "resolved": "https://registry.npmjs.org/diffie-hellman/-/diffie-hellman-5.0.2.tgz", "integrity": "sha1-tYNXOScM/ias9jIJn97SoH8gnl4=", "requires": { - "bn.js": "^4.1.0", - "miller-rabin": "^4.0.0", - "randombytes": "^2.0.0" + "bn.js": "4.11.8", + "miller-rabin": "4.0.1", + "randombytes": "2.0.6" } }, "doctrine": { @@ -822,7 +822,7 @@ "integrity": "sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==", "dev": true, "requires": { - "esutils": "^2.0.2" + "esutils": "2.0.2" } }, "dom-walk": { @@ -840,9 +840,9 @@ "resolved": "https://registry.npmjs.org/drbg.js/-/drbg.js-1.0.1.tgz", "integrity": "sha1-Pja2xCs3BDgjzbwzLVjzHiRFSAs=", "requires": { - "browserify-aes": "^1.0.6", - "create-hash": "^1.1.2", - "create-hmac": "^1.1.4" + "browserify-aes": "1.1.1", + "create-hash": "1.1.3", + "create-hmac": "1.1.6" } }, "duplexer3": { @@ -856,7 +856,7 @@ "integrity": "sha1-D8c6ntXw1Tw4GTOYUj735UN3dQU=", "optional": true, "requires": { - "jsbn": "~0.1.0" + "jsbn": "0.1.1" } }, "ee-first": { @@ -869,13 +869,13 @@ "resolved": "https://registry.npmjs.org/elliptic/-/elliptic-6.4.0.tgz", "integrity": "sha1-ysmvh2LIWDYYcAPI3+GT5eLq5d8=", "requires": { - "bn.js": "^4.4.0", - "brorand": "^1.0.1", - "hash.js": "^1.0.0", - "hmac-drbg": "^1.0.0", - "inherits": "^2.0.1", - "minimalistic-assert": "^1.0.0", - "minimalistic-crypto-utils": "^1.0.0" + "bn.js": "4.11.8", + "brorand": "1.1.0", + "hash.js": "1.1.3", + "hmac-drbg": "1.0.1", + "inherits": "2.0.3", + "minimalistic-assert": "1.0.0", + "minimalistic-crypto-utils": "1.0.1" } }, "encodeurl": { @@ -888,7 +888,7 @@ "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.1.tgz", "integrity": "sha512-1MkrZNvWTKCaigbn+W15elq2BB/L22nqrSY5DKlo3X6+vclJm8Bb5djXJBmEX6fS3+zCh/F4VBK5Z2KxJt4s2Q==", "requires": { - "once": "^1.4.0" + "once": "1.4.0" } }, "envalid": { @@ -915,7 +915,7 @@ "integrity": "sha512-7dFHNmqeFSEt2ZBsCriorKnn3Z2pj+fd9kmI6QoWw4//DL+icEBfc0U7qJCisqrTsKTjw4fNFy2pW9OqStD84g==", "dev": true, "requires": { - "is-arrayish": "^0.2.1" + "is-arrayish": "0.2.1" } }, "es-abstract": { @@ -924,11 +924,11 @@ "integrity": "sha512-C8Fx/0jFmV5IPoMOFPA9P9G5NtqW+4cOPit3MIuvR2t7Ag2K15EJTpxnHAYTzL+aYQJIESYeXZmDBfOBE1HcpA==", "dev": true, "requires": { - "es-to-primitive": "^1.1.1", - "function-bind": "^1.1.1", - "has": "^1.0.1", - "is-callable": "^1.1.3", - "is-regex": "^1.0.4" + "es-to-primitive": "1.1.1", + "function-bind": "1.1.1", + "has": "1.0.3", + "is-callable": "1.1.4", + "is-regex": "1.0.4" } }, "es-to-primitive": { @@ -937,9 +937,9 @@ "integrity": "sha1-RTVSSKiJeQNLZ5Lhm7gfK3l13Q0=", "dev": true, "requires": { - "is-callable": "^1.1.1", - "is-date-object": "^1.0.1", - "is-symbol": "^1.0.1" + "is-callable": "1.1.4", + "is-date-object": "1.0.1", + "is-symbol": "1.0.1" } }, "escape-html": { @@ -957,11 +957,11 @@ "resolved": "https://registry.npmjs.org/escodegen/-/escodegen-1.8.1.tgz", "integrity": "sha1-WltTr0aTEQvrsIZ6o0MN07cKEBg=", "requires": { - "esprima": "^2.7.1", - "estraverse": "^1.9.1", - "esutils": "^2.0.2", - "optionator": "^0.8.1", - "source-map": "~0.2.0" + "esprima": "2.7.3", + "estraverse": "1.9.3", + "esutils": "2.0.2", + "optionator": "0.8.2", + "source-map": "0.2.0" } }, "eslint": { @@ -970,44 +970,44 @@ "integrity": "sha512-/eVYs9VVVboX286mBK7bbKnO1yamUy2UCRjiY6MryhQL2PaaXCExsCQ2aO83OeYRhU2eCU/FMFP+tVMoOrzNrA==", "dev": true, "requires": { - "@babel/code-frame": "^7.0.0", - "ajv": "^6.5.3", - "chalk": "^2.1.0", - "cross-spawn": "^6.0.5", - "debug": "^3.1.0", - "doctrine": "^2.1.0", - "eslint-scope": "^4.0.0", - "eslint-utils": "^1.3.1", - "eslint-visitor-keys": "^1.0.0", - "espree": "^4.0.0", - "esquery": "^1.0.1", - "esutils": "^2.0.2", - "file-entry-cache": "^2.0.0", - "functional-red-black-tree": "^1.0.1", - "glob": "^7.1.2", - "globals": "^11.7.0", - "ignore": "^4.0.6", - "imurmurhash": "^0.1.4", - "inquirer": "^6.1.0", - "is-resolvable": "^1.1.0", - "js-yaml": "^3.12.0", - "json-stable-stringify-without-jsonify": "^1.0.1", - "levn": "^0.3.0", - "lodash": "^4.17.5", - "minimatch": "^3.0.4", - "mkdirp": "^0.5.1", - "natural-compare": "^1.4.0", - "optionator": "^0.8.2", - "path-is-inside": "^1.0.2", - "pluralize": "^7.0.0", - "progress": "^2.0.0", - "regexpp": "^2.0.0", - "require-uncached": "^1.0.3", - "semver": "^5.5.1", - "strip-ansi": "^4.0.0", - "strip-json-comments": "^2.0.1", - "table": "^4.0.3", - "text-table": "^0.2.0" + "@babel/code-frame": "7.0.0", + "ajv": "6.5.3", + "chalk": "2.1.0", + "cross-spawn": "6.0.5", + "debug": "3.2.5", + "doctrine": "2.1.0", + "eslint-scope": "4.0.0", + "eslint-utils": "1.3.1", + "eslint-visitor-keys": "1.0.0", + "espree": "4.0.0", + "esquery": "1.0.1", + "esutils": "2.0.2", + "file-entry-cache": "2.0.0", + "functional-red-black-tree": "1.0.1", + "glob": "7.1.2", + "globals": "11.7.0", + "ignore": "4.0.6", + "imurmurhash": "0.1.4", + "inquirer": "6.2.0", + "is-resolvable": "1.1.0", + "js-yaml": "3.12.0", + "json-stable-stringify-without-jsonify": "1.0.1", + "levn": "0.3.0", + "lodash": "4.17.11", + "minimatch": "3.0.4", + "mkdirp": "0.5.1", + "natural-compare": "1.4.0", + "optionator": "0.8.2", + "path-is-inside": "1.0.2", + "pluralize": "7.0.0", + "progress": "2.0.0", + "regexpp": "2.0.0", + "require-uncached": "1.0.3", + "semver": "5.5.1", + "strip-ansi": "4.0.0", + "strip-json-comments": "2.0.1", + "table": "4.0.3", + "text-table": "0.2.0" }, "dependencies": { "ajv": { @@ -1016,10 +1016,10 @@ "integrity": "sha512-LqZ9wY+fx3UMiiPd741yB2pj3hhil+hQc8taf4o2QGRFpWgZ2V5C8HA165DY9sS3fJwsk7uT7ZlFEyC3Ig3lLg==", "dev": true, "requires": { - "fast-deep-equal": "^2.0.1", - "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.4.1", - "uri-js": "^4.2.2" + "fast-deep-equal": "2.0.1", + "fast-json-stable-stringify": "2.0.0", + "json-schema-traverse": "0.4.1", + "uri-js": "4.2.2" } }, "debug": { @@ -1028,7 +1028,7 @@ "integrity": "sha512-D61LaDQPQkxJ5AUM2mbSJRbPkNs/TmdmOeLAi1hgDkpDfIfetSrjmWhccwtuResSwMbACjx/xXQofvM9CE/aeg==", "dev": true, "requires": { - "ms": "^2.1.1" + "ms": "2.1.1" } }, "fast-deep-equal": { @@ -1063,9 +1063,9 @@ "integrity": "sha512-XWwQtf3U3zIoKO1BbHh6aUhJZQweOwSt4c2JrPDg9FP3Ltv3+YfEv7jIDB8275tVnO/qOHbfuYg3kzw6Je7uWw==", "dev": true, "requires": { - "eslint-restricted-globals": "^0.1.1", - "object.assign": "^4.1.0", - "object.entries": "^1.0.4" + "eslint-restricted-globals": "0.1.1", + "object.assign": "4.1.0", + "object.entries": "1.0.4" } }, "eslint-config-prettier": { @@ -1074,7 +1074,7 @@ "integrity": "sha512-vA0TB8HCx/idHXfKHYcg9J98p0Q8nkfNwNAoP7e+ywUidn6ScaFS5iqncZAHPz+/a0A/tp657ulFHFx/2JDP4Q==", "dev": true, "requires": { - "get-stdin": "^6.0.0" + "get-stdin": "6.0.0" } }, "eslint-import-resolver-node": { @@ -1083,8 +1083,8 @@ "integrity": "sha512-sfmTqJfPSizWu4aymbPr4Iidp5yKm8yDkHp+Ir3YiTHiiDfxh69mOUsmiqW6RZ9zRXFaF64GtYmN7e+8GHBv6Q==", "dev": true, "requires": { - "debug": "^2.6.9", - "resolve": "^1.5.0" + "debug": "2.6.9", + "resolve": "1.8.1" }, "dependencies": { "resolve": { @@ -1093,7 +1093,7 @@ "integrity": "sha512-AicPrAC7Qu1JxPCZ9ZgCZlY35QgFnNqc+0LtbRNxnVw4TXvjQ72wnuL9JQcEBgXkI9JM8MsT9kaQoHcpCRJOYA==", "dev": true, "requires": { - "path-parse": "^1.0.5" + "path-parse": "1.0.5" } } } @@ -1104,8 +1104,8 @@ "integrity": "sha1-snA2LNiLGkitMIl2zn+lTphBF0Y=", "dev": true, "requires": { - "debug": "^2.6.8", - "pkg-dir": "^1.0.0" + "debug": "2.6.9", + "pkg-dir": "1.0.0" } }, "eslint-plugin-es": { @@ -1114,8 +1114,8 @@ "integrity": "sha512-9XcVyZiQRVeFjqHw8qHNDAZcQLqaHlOGGpeYqzYh8S4JYCWTCO3yzyen8yVmA5PratfzTRWDwCOFphtDEG+w/w==", "dev": true, "requires": { - "eslint-utils": "^1.3.0", - "regexpp": "^2.0.0" + "eslint-utils": "1.3.1", + "regexpp": "2.0.0" } }, "eslint-plugin-import": { @@ -1124,16 +1124,16 @@ "integrity": "sha512-FpuRtniD/AY6sXByma2Wr0TXvXJ4nA/2/04VPlfpmUDPOpOY264x+ILiwnrk/k4RINgDAyFZByxqPUbSQ5YE7g==", "dev": true, "requires": { - "contains-path": "^0.1.0", - "debug": "^2.6.8", + "contains-path": "0.1.0", + "debug": "2.6.9", "doctrine": "1.5.0", - "eslint-import-resolver-node": "^0.3.1", - "eslint-module-utils": "^2.2.0", - "has": "^1.0.1", - "lodash": "^4.17.4", - "minimatch": "^3.0.3", - "read-pkg-up": "^2.0.0", - "resolve": "^1.6.0" + "eslint-import-resolver-node": "0.3.2", + "eslint-module-utils": "2.2.0", + "has": "1.0.3", + "lodash": "4.17.11", + "minimatch": "3.0.4", + "read-pkg-up": "2.0.0", + "resolve": "1.8.1" }, "dependencies": { "doctrine": { @@ -1142,8 +1142,8 @@ "integrity": "sha1-N53Ocw9hZvds76TmcHoVmwLFpvo=", "dev": true, "requires": { - "esutils": "^2.0.2", - "isarray": "^1.0.0" + "esutils": "2.0.2", + "isarray": "1.0.0" } }, "resolve": { @@ -1152,7 +1152,7 @@ "integrity": "sha512-AicPrAC7Qu1JxPCZ9ZgCZlY35QgFnNqc+0LtbRNxnVw4TXvjQ72wnuL9JQcEBgXkI9JM8MsT9kaQoHcpCRJOYA==", "dev": true, "requires": { - "path-parse": "^1.0.5" + "path-parse": "1.0.5" } } } @@ -1163,12 +1163,12 @@ "integrity": "sha512-lfVw3TEqThwq0j2Ba/Ckn2ABdwmL5dkOgAux1rvOk6CO7A6yGyPI2+zIxN6FyNkp1X1X/BSvKOceD6mBWSj4Yw==", "dev": true, "requires": { - "eslint-plugin-es": "^1.3.1", - "eslint-utils": "^1.3.1", - "ignore": "^4.0.2", - "minimatch": "^3.0.4", - "resolve": "^1.8.1", - "semver": "^5.5.0" + "eslint-plugin-es": "1.3.1", + "eslint-utils": "1.3.1", + "ignore": "4.0.6", + "minimatch": "3.0.4", + "resolve": "1.8.1", + "semver": "5.5.1" }, "dependencies": { "resolve": { @@ -1177,7 +1177,7 @@ "integrity": "sha512-AicPrAC7Qu1JxPCZ9ZgCZlY35QgFnNqc+0LtbRNxnVw4TXvjQ72wnuL9JQcEBgXkI9JM8MsT9kaQoHcpCRJOYA==", "dev": true, "requires": { - "path-parse": "^1.0.5" + "path-parse": "1.0.5" } }, "semver": { @@ -1194,8 +1194,8 @@ "integrity": "sha512-tGek5clmW5swrAx1mdPYM8oThrBE83ePh7LeseZHBWfHVGrHPhKn7Y5zgRMbU/9D5Td9K4CEmUPjGxA7iw98Og==", "dev": true, "requires": { - "fast-diff": "^1.1.1", - "jest-docblock": "^21.0.0" + "fast-diff": "1.1.2", + "jest-docblock": "21.2.0" } }, "eslint-restricted-globals": { @@ -1210,8 +1210,8 @@ "integrity": "sha512-1G6UTDi7Jc1ELFwnR58HV4fK9OQK4S6N985f166xqXxpjU6plxFISJa2Ba9KCQuFa8RCnj/lSFJbHo7UFDBnUA==", "dev": true, "requires": { - "esrecurse": "^4.1.0", - "estraverse": "^4.1.1" + "esrecurse": "4.2.1", + "estraverse": "4.2.0" }, "dependencies": { "estraverse": { @@ -1240,8 +1240,8 @@ "integrity": "sha512-kapdTCt1bjmspxStVKX6huolXVV5ZfyZguY1lcfhVVZstce3bqxH9mcLzNn3/mlgW6wQ732+0fuG9v7h0ZQoKg==", "dev": true, "requires": { - "acorn": "^5.6.0", - "acorn-jsx": "^4.1.1" + "acorn": "5.7.3", + "acorn-jsx": "4.1.1" }, "dependencies": { "acorn": { @@ -1263,7 +1263,7 @@ "integrity": "sha512-SmiyZ5zIWH9VM+SRUReLS5Q8a7GxtRdxEBVZpm98rJM7Sb+A9DVCndXfkeFUd3byderg+EbDkfnevfCwynWaNA==", "dev": true, "requires": { - "estraverse": "^4.0.0" + "estraverse": "4.2.0" }, "dependencies": { "estraverse": { @@ -1280,7 +1280,7 @@ "integrity": "sha512-64RBB++fIOAXPw3P9cy89qfMlvZEXZkqqJkjqqXIvzP5ezRZjW+lPWjw35UX/3EhUPFYbg5ER4JYgDw4007/DQ==", "dev": true, "requires": { - "estraverse": "^4.1.0" + "estraverse": "4.2.0" }, "dependencies": { "estraverse": { @@ -1311,13 +1311,13 @@ "resolved": "https://registry.npmjs.org/eth-lib/-/eth-lib-0.1.27.tgz", "integrity": "sha512-B8czsfkJYzn2UIEMwjc7Mbj+Cy72V+/OXH/tb44LV8jhrjizQJJ325xMOMyk3+ETa6r6oi0jsUY14+om8mQMWA==", "requires": { - "bn.js": "^4.11.6", - "elliptic": "^6.4.0", - "keccakjs": "^0.2.1", - "nano-json-stream-parser": "^0.1.2", - "servify": "^0.1.12", - "ws": "^3.0.0", - "xhr-request-promise": "^0.1.2" + "bn.js": "4.11.8", + "elliptic": "6.4.0", + "keccakjs": "0.2.1", + "nano-json-stream-parser": "0.1.2", + "servify": "0.1.12", + "ws": "3.3.3", + "xhr-request-promise": "0.1.2" } }, "ethereum-common": { @@ -1330,8 +1330,8 @@ "resolved": "https://registry.npmjs.org/ethereumjs-tx/-/ethereumjs-tx-1.3.4.tgz", "integrity": "sha512-kOgUd5jC+0tgV7t52UDECMMz9Uf+Lro+6fSpCvzWemtXfMEcwI3EOxf5mVPMRbTFkMMhuERokNNVF3jItAjidg==", "requires": { - "ethereum-common": "^0.0.18", - "ethereumjs-util": "^5.0.0" + "ethereum-common": "0.0.18", + "ethereumjs-util": "5.1.5" } }, "ethereumjs-util": { @@ -1339,13 +1339,13 @@ "resolved": "https://registry.npmjs.org/ethereumjs-util/-/ethereumjs-util-5.1.5.tgz", "integrity": "sha512-xPaSEATYJpMTCGowIt0oMZwFP4R1bxd6QsWgkcDvFL0JtXsr39p32WEcD14RscCjfP41YXZPCVWA4yAg0nrJmw==", "requires": { - "bn.js": "^4.11.0", - "create-hash": "^1.1.2", - "ethjs-util": "^0.1.3", - "keccak": "^1.0.2", - "rlp": "^2.0.0", - "safe-buffer": "^5.1.1", - "secp256k1": "^3.0.1" + "bn.js": "4.11.8", + "create-hash": "1.1.3", + "ethjs-util": "0.1.4", + "keccak": "1.4.0", + "rlp": "2.0.0", + "safe-buffer": "5.1.1", + "secp256k1": "3.5.0" } }, "ethjs-unit": { @@ -1383,8 +1383,8 @@ "resolved": "https://registry.npmjs.org/evp_bytestokey/-/evp_bytestokey-1.0.3.tgz", "integrity": "sha512-/f2Go4TognH/KvCISP7OUsHn85hT9nUkxxA9BEWxFn+Oj9o8ZNLm/40hdlgSLyuOimsrTKLUMEorQexp/aPQeA==", "requires": { - "md5.js": "^1.3.4", - "safe-buffer": "^5.1.1" + "md5.js": "1.3.4", + "safe-buffer": "5.1.1" } }, "expand-template": { @@ -1397,36 +1397,36 @@ "resolved": "https://registry.npmjs.org/express/-/express-4.16.3.tgz", "integrity": "sha1-avilAjUNsyRuzEvs9rWjTSL37VM=", "requires": { - "accepts": "~1.3.5", + "accepts": "1.3.5", "array-flatten": "1.1.1", "body-parser": "1.18.2", "content-disposition": "0.5.2", - "content-type": "~1.0.4", + "content-type": "1.0.4", "cookie": "0.3.1", "cookie-signature": "1.0.6", "debug": "2.6.9", - "depd": "~1.1.2", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "etag": "~1.8.1", + "depd": "1.1.2", + "encodeurl": "1.0.2", + "escape-html": "1.0.3", + "etag": "1.8.1", "finalhandler": "1.1.1", "fresh": "0.5.2", "merge-descriptors": "1.0.1", - "methods": "~1.1.2", - "on-finished": "~2.3.0", - "parseurl": "~1.3.2", + "methods": "1.1.2", + "on-finished": "2.3.0", + "parseurl": "1.3.2", "path-to-regexp": "0.1.7", - "proxy-addr": "~2.0.3", + "proxy-addr": "2.0.3", "qs": "6.5.1", - "range-parser": "~1.2.0", + "range-parser": "1.2.0", "safe-buffer": "5.1.1", "send": "0.16.2", "serve-static": "1.13.2", "setprototypeof": "1.1.0", - "statuses": "~1.4.0", - "type-is": "~1.6.16", + "statuses": "1.4.0", + "type-is": "1.6.16", "utils-merge": "1.0.1", - "vary": "~1.1.2" + "vary": "1.1.2" }, "dependencies": { "setprototypeof": { @@ -1452,9 +1452,9 @@ "integrity": "sha512-bn71H9+qWoOQKyZDo25mOMVpSmXROAsTJVVVYzrrtol3d4y+AsKjf4Iwl2Q+IuT0kFSQ1qo166UuIwqYq7mGnA==", "dev": true, "requires": { - "chardet": "^0.7.0", - "iconv-lite": "^0.4.24", - "tmp": "^0.0.33" + "chardet": "0.7.0", + "iconv-lite": "0.4.24", + "tmp": "0.0.33" }, "dependencies": { "iconv-lite": { @@ -1463,7 +1463,7 @@ "integrity": "sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==", "dev": true, "requires": { - "safer-buffer": ">= 2.1.2 < 3" + "safer-buffer": "2.1.2" } } } @@ -1499,7 +1499,7 @@ "resolved": "https://registry.npmjs.org/fd-slicer/-/fd-slicer-1.0.1.tgz", "integrity": "sha1-i1vL2ewyfFBBv5qwI/1nUPEXfmU=", "requires": { - "pend": "~1.2.0" + "pend": "1.2.0" } }, "figures": { @@ -1508,7 +1508,7 @@ "integrity": "sha1-OrGi0qYsi/tDGgyUy3l6L84nyWI=", "dev": true, "requires": { - "escape-string-regexp": "^1.0.5" + "escape-string-regexp": "1.0.5" } }, "file-entry-cache": { @@ -1517,8 +1517,8 @@ "integrity": "sha1-w5KZDD5oR4PYOLjISkXYoEhFg2E=", "dev": true, "requires": { - "flat-cache": "^1.2.1", - "object-assign": "^4.0.1" + "flat-cache": "1.3.0", + "object-assign": "4.1.1" } }, "file-type": { @@ -1532,12 +1532,12 @@ "integrity": "sha512-Y1GUDo39ez4aHAw7MysnUD5JzYX+WaIj8I57kO3aEPT1fFRL4sr7mjei97FgnwhAyyzRYmQZaTHb2+9uZ1dPtg==", "requires": { "debug": "2.6.9", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "on-finished": "~2.3.0", - "parseurl": "~1.3.2", - "statuses": "~1.4.0", - "unpipe": "~1.0.0" + "encodeurl": "1.0.2", + "escape-html": "1.0.3", + "on-finished": "2.3.0", + "parseurl": "1.3.2", + "statuses": "1.4.0", + "unpipe": "1.0.0" }, "dependencies": { "statuses": { @@ -1553,8 +1553,8 @@ "integrity": "sha1-ay6YIrGizgpgq2TWEOzK1TyyTQ8=", "dev": true, "requires": { - "path-exists": "^2.0.0", - "pinkie-promise": "^2.0.0" + "path-exists": "2.1.0", + "pinkie-promise": "2.0.1" } }, "flat-cache": { @@ -1563,10 +1563,10 @@ "integrity": "sha1-0wMLMrOBVPTjt+nHCfSQ9++XxIE=", "dev": true, "requires": { - "circular-json": "^0.3.1", - "del": "^2.0.2", - "graceful-fs": "^4.1.2", - "write": "^0.2.1" + "circular-json": "0.3.3", + "del": "2.2.2", + "graceful-fs": "4.1.11", + "write": "0.2.1" } }, "for-each": { @@ -1574,7 +1574,7 @@ "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.2.tgz", "integrity": "sha1-LEBFC5NI6X8oEyJZO6lnBLmr1NQ=", "requires": { - "is-function": "~1.0.0" + "is-function": "1.0.1" } }, "forever-agent": { @@ -1587,9 +1587,9 @@ "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.3.2.tgz", "integrity": "sha1-SXBJi+YEwgwAXU9cI67NIda0kJk=", "requires": { - "asynckit": "^0.4.0", + "asynckit": "0.4.0", "combined-stream": "1.0.6", - "mime-types": "^2.1.12" + "mime-types": "2.1.18" } }, "forwarded": { @@ -1607,8 +1607,8 @@ "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-2.1.2.tgz", "integrity": "sha1-BGxwFjzvmq1GsOSn+kZ/si1x3jU=", "requires": { - "graceful-fs": "^4.1.2", - "jsonfile": "^2.1.0" + "graceful-fs": "4.1.11", + "jsonfile": "2.4.0" } }, "fs-promise": { @@ -1616,10 +1616,10 @@ "resolved": "https://registry.npmjs.org/fs-promise/-/fs-promise-2.0.3.tgz", "integrity": "sha1-9k5PhUvPaJqovdy6JokW2z20aFQ=", "requires": { - "any-promise": "^1.3.0", - "fs-extra": "^2.0.0", - "mz": "^2.6.0", - "thenify-all": "^1.6.0" + "any-promise": "1.3.0", + "fs-extra": "2.1.2", + "mz": "2.7.0", + "thenify-all": "1.6.0" } }, "fs.realpath": { @@ -1632,10 +1632,10 @@ "resolved": "https://registry.npmjs.org/fstream/-/fstream-1.0.11.tgz", "integrity": "sha1-XB+x8RdHcRTwYyoOtLcbPLD9MXE=", "requires": { - "graceful-fs": "^4.1.2", - "inherits": "~2.0.0", - "mkdirp": ">=0.5 0", - "rimraf": "2" + "graceful-fs": "4.1.11", + "inherits": "2.0.3", + "mkdirp": "0.5.1", + "rimraf": "2.6.2" } }, "function-bind": { @@ -1666,7 +1666,7 @@ "resolved": "https://registry.npmjs.org/getpass/-/getpass-0.1.7.tgz", "integrity": "sha1-Xv+OPmhNVprkyysSgmBOi6YhSfo=", "requires": { - "assert-plus": "^1.0.0" + "assert-plus": "1.0.0" } }, "glob": { @@ -1674,12 +1674,12 @@ "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz", "integrity": "sha512-MJTUg1kjuLeQCJ+ccE4Vpa6kKVXkPYJ2mOCQyUuKLcLQsdrMCpBPUi8qVE6+YuaJkozeA9NusTAw3hLr8Xe5EQ==", "requires": { - "fs.realpath": "^1.0.0", - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "^3.0.4", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" + "fs.realpath": "1.0.0", + "inflight": "1.0.6", + "inherits": "2.0.3", + "minimatch": "3.0.4", + "once": "1.4.0", + "path-is-absolute": "1.0.1" } }, "global": { @@ -1687,8 +1687,8 @@ "resolved": "https://registry.npmjs.org/global/-/global-4.3.2.tgz", "integrity": "sha1-52mJJopsdMOJCLEwWxD8DjlOnQ8=", "requires": { - "min-document": "^2.19.0", - "process": "~0.5.1" + "min-document": "2.19.0", + "process": "0.5.2" } }, "globals": { @@ -1702,11 +1702,11 @@ "resolved": "https://registry.npmjs.org/globby/-/globby-6.1.0.tgz", "integrity": "sha1-9abXDoOV4hyFj7BInWTfAkJNUGw=", "requires": { - "array-union": "^1.0.1", - "glob": "^7.0.3", - "object-assign": "^4.0.1", - "pify": "^2.0.0", - "pinkie-promise": "^2.0.0" + "array-union": "1.0.2", + "glob": "7.1.2", + "object-assign": "4.1.1", + "pify": "2.3.0", + "pinkie-promise": "2.0.1" } }, "got": { @@ -1714,20 +1714,20 @@ "resolved": "https://registry.npmjs.org/got/-/got-7.1.0.tgz", "integrity": "sha512-Y5WMo7xKKq1muPsxD+KmrR8DH5auG7fBdDVueZwETwV6VytKyU9OX/ddpq2/1hp1vIPvVb4T81dKQz3BivkNLw==", "requires": { - "decompress-response": "^3.2.0", - "duplexer3": "^0.1.4", - "get-stream": "^3.0.0", - "is-plain-obj": "^1.1.0", - "is-retry-allowed": "^1.0.0", - "is-stream": "^1.0.0", - "isurl": "^1.0.0-alpha5", - "lowercase-keys": "^1.0.0", - "p-cancelable": "^0.3.0", - "p-timeout": "^1.1.1", - "safe-buffer": "^5.0.1", - "timed-out": "^4.0.0", - "url-parse-lax": "^1.0.0", - "url-to-options": "^1.0.1" + "decompress-response": "3.3.0", + "duplexer3": "0.1.4", + "get-stream": "3.0.0", + "is-plain-obj": "1.1.0", + "is-retry-allowed": "1.1.0", + "is-stream": "1.1.0", + "isurl": "1.0.0", + "lowercase-keys": "1.0.1", + "p-cancelable": "0.3.0", + "p-timeout": "1.2.1", + "safe-buffer": "5.1.1", + "timed-out": "4.0.1", + "url-parse-lax": "1.0.0", + "url-to-options": "1.0.1" } }, "graceful-fs": { @@ -1750,8 +1750,8 @@ "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-5.0.3.tgz", "integrity": "sha1-ukAsJmGU8VlW7xXg/PJCmT9qff0=", "requires": { - "ajv": "^5.1.0", - "har-schema": "^2.0.0" + "ajv": "5.5.2", + "har-schema": "2.0.0" } }, "has": { @@ -1760,7 +1760,7 @@ "integrity": "sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw==", "dev": true, "requires": { - "function-bind": "^1.1.1" + "function-bind": "1.1.1" } }, "has-flag": { @@ -1784,7 +1784,7 @@ "resolved": "https://registry.npmjs.org/has-to-string-tag-x/-/has-to-string-tag-x-1.4.1.tgz", "integrity": "sha512-vdbKfmw+3LoOYVr+mtxHaX5a96+0f3DljYd8JOqvOLsf5mw2Otda2qCDT9qRqLAhrjyQ0h7ual5nOiASpsGNFw==", "requires": { - "has-symbol-support-x": "^1.4.1" + "has-symbol-support-x": "1.4.2" } }, "hash-base": { @@ -1792,7 +1792,7 @@ "resolved": "https://registry.npmjs.org/hash-base/-/hash-base-2.0.2.tgz", "integrity": "sha1-ZuodhW206KVHDK32/OI65SRO8uE=", "requires": { - "inherits": "^2.0.1" + "inherits": "2.0.3" } }, "hash.js": { @@ -1800,8 +1800,8 @@ "resolved": "https://registry.npmjs.org/hash.js/-/hash.js-1.1.3.tgz", "integrity": "sha512-/UETyP0W22QILqS+6HowevwhEFJ3MBJnwTf75Qob9Wz9t0DPuisL8kW8YZMK62dHAKE1c1p+gY1TtOLY+USEHA==", "requires": { - "inherits": "^2.0.3", - "minimalistic-assert": "^1.0.0" + "inherits": "2.0.3", + "minimalistic-assert": "1.0.0" } }, "hawk": { @@ -1809,10 +1809,10 @@ "resolved": "https://registry.npmjs.org/hawk/-/hawk-6.0.2.tgz", "integrity": "sha512-miowhl2+U7Qle4vdLqDdPt9m09K6yZhkLDTWGoUiUzrQCn+mHHSmfJgAyGaLRZbPmTqfFFjRV1QWCW0VWUJBbQ==", "requires": { - "boom": "4.x.x", - "cryptiles": "3.x.x", - "hoek": "4.x.x", - "sntp": "2.x.x" + "boom": "4.3.1", + "cryptiles": "3.1.2", + "hoek": "4.2.1", + "sntp": "2.1.0" } }, "hmac-drbg": { @@ -1820,9 +1820,9 @@ "resolved": "https://registry.npmjs.org/hmac-drbg/-/hmac-drbg-1.0.1.tgz", "integrity": "sha1-0nRXAQJabHdabFRXk+1QL8DGSaE=", "requires": { - "hash.js": "^1.0.3", - "minimalistic-assert": "^1.0.0", - "minimalistic-crypto-utils": "^1.0.1" + "hash.js": "1.1.3", + "minimalistic-assert": "1.0.0", + "minimalistic-crypto-utils": "1.0.1" } }, "hoek": { @@ -1844,7 +1844,7 @@ "depd": "1.1.1", "inherits": "2.0.3", "setprototypeof": "1.0.3", - "statuses": ">= 1.3.1 < 2" + "statuses": "1.5.0" }, "dependencies": { "depd": { @@ -1864,9 +1864,9 @@ "resolved": "https://registry.npmjs.org/http-signature/-/http-signature-1.2.0.tgz", "integrity": "sha1-muzZJRFHcvPZW2WmCruPfBj7rOE=", "requires": { - "assert-plus": "^1.0.0", - "jsprim": "^1.2.2", - "sshpk": "^1.7.0" + "assert-plus": "1.0.0", + "jsprim": "1.4.1", + "sshpk": "1.14.1" } }, "iconv-lite": { @@ -1901,8 +1901,8 @@ "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=", "requires": { - "once": "^1.3.0", - "wrappy": "1" + "once": "1.4.0", + "wrappy": "1.0.2" } }, "inherits": { @@ -1916,19 +1916,19 @@ "integrity": "sha512-QIEQG4YyQ2UYZGDC4srMZ7BjHOmNk1lR2JQj5UknBapklm6WHA+VVH7N+sUdX3A7NeCfGF8o4X1S3Ao7nAcIeg==", "dev": true, "requires": { - "ansi-escapes": "^3.0.0", - "chalk": "^2.0.0", - "cli-cursor": "^2.1.0", - "cli-width": "^2.0.0", - "external-editor": "^3.0.0", - "figures": "^2.0.0", - "lodash": "^4.17.10", + "ansi-escapes": "3.1.0", + "chalk": "2.1.0", + "cli-cursor": "2.1.0", + "cli-width": "2.2.0", + "external-editor": "3.0.3", + "figures": "2.0.0", + "lodash": "4.17.11", "mute-stream": "0.0.7", - "run-async": "^2.2.0", - "rxjs": "^6.1.0", - "string-width": "^2.1.0", - "strip-ansi": "^4.0.0", - "through": "^2.3.6" + "run-async": "2.3.0", + "rxjs": "6.3.2", + "string-width": "2.1.1", + "strip-ansi": "4.0.0", + "through": "2.3.8" } }, "ipaddr.js": { @@ -1948,7 +1948,7 @@ "integrity": "sha1-VAVy0096wxGfj3bDDLwbHgN6/74=", "dev": true, "requires": { - "builtin-modules": "^1.0.0" + "builtin-modules": "1.1.1" } }, "is-callable": { @@ -2001,7 +2001,7 @@ "integrity": "sha512-FjV1RTW48E7CWM7eE/J2NJvAEEVektecDBVBE5Hh3nM1Jd0kvhHtX68Pr3xsDf857xt3Y4AkwVULK1Vku62aaQ==", "dev": true, "requires": { - "is-path-inside": "^1.0.0" + "is-path-inside": "1.0.1" } }, "is-path-inside": { @@ -2010,7 +2010,7 @@ "integrity": "sha1-jvW33lBDej/cprToZe96pVy0gDY=", "dev": true, "requires": { - "path-is-inside": "^1.0.1" + "path-is-inside": "1.0.2" } }, "is-plain-obj": { @@ -2030,7 +2030,7 @@ "integrity": "sha1-VRdIm1RwkbCTDglWVM7SXul+lJE=", "dev": true, "requires": { - "has": "^1.0.1" + "has": "1.0.3" } }, "is-resolvable": { @@ -2081,8 +2081,8 @@ "resolved": "https://registry.npmjs.org/isurl/-/isurl-1.0.0.tgz", "integrity": "sha512-1P/yWsxPlDtn7QeRD+ULKQPaIaN6yF368GZ2vDfv0AL0NwpStafjWCDDdn0k8wgFMWpVAqG7oJhxHnlud42i9w==", "requires": { - "has-to-string-tag-x": "^1.2.0", - "is-object": "^1.0.1" + "has-to-string-tag-x": "1.4.1", + "is-object": "1.0.1" } }, "jest-docblock": { @@ -2108,8 +2108,8 @@ "integrity": "sha512-PIt2cnwmPfL4hKNwqeiuz4bKfnzHTBv6HyVgjahA6mPLwPDzjDWrplJBMjHUFxku/N3FlmrbyPclad+I+4mJ3A==", "dev": true, "requires": { - "argparse": "^1.0.7", - "esprima": "^4.0.0" + "argparse": "1.0.10", + "esprima": "4.0.1" }, "dependencies": { "esprima": { @@ -2141,7 +2141,7 @@ "resolved": "https://registry.npmjs.org/json-stable-stringify/-/json-stable-stringify-1.0.1.tgz", "integrity": "sha1-mnWdOcXy/1A/1TAGRu1EX4jE+a8=", "requires": { - "jsonify": "~0.0.0" + "jsonify": "0.0.0" } }, "json-stable-stringify-without-jsonify": { @@ -2160,7 +2160,7 @@ "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-2.4.0.tgz", "integrity": "sha1-NzaitCi4e72gzIO1P6PWM6NcKug=", "requires": { - "graceful-fs": "^4.1.6" + "graceful-fs": "4.1.11" } }, "jsonify": { @@ -2184,10 +2184,10 @@ "resolved": "https://registry.npmjs.org/keccak/-/keccak-1.4.0.tgz", "integrity": "sha512-eZVaCpblK5formjPjeTBik7TAg+pqnDrMHIffSvi9Lh7PQgM1+hSzakUeZFCk9DVVG0dacZJuaz2ntwlzZUIBw==", "requires": { - "bindings": "^1.2.1", - "inherits": "^2.0.3", - "nan": "^2.2.1", - "safe-buffer": "^5.1.0" + "bindings": "1.3.0", + "inherits": "2.0.3", + "nan": "2.10.0", + "safe-buffer": "5.1.1" } }, "keccakjs": { @@ -2195,8 +2195,8 @@ "resolved": "https://registry.npmjs.org/keccakjs/-/keccakjs-0.2.1.tgz", "integrity": "sha1-HWM6+QfvMFu/ny+mFtVsRFYd+k0=", "requires": { - "browserify-sha3": "^0.0.1", - "sha3": "^1.1.0" + "browserify-sha3": "0.0.1", + "sha3": "1.2.0" } }, "levn": { @@ -2204,8 +2204,8 @@ "resolved": "https://registry.npmjs.org/levn/-/levn-0.3.0.tgz", "integrity": "sha1-OwmSTt+fCDwEkP3UwLxEIeBHZO4=", "requires": { - "prelude-ls": "~1.1.2", - "type-check": "~0.3.2" + "prelude-ls": "1.1.2", + "type-check": "0.3.2" } }, "load-json-file": { @@ -2214,10 +2214,10 @@ "integrity": "sha1-eUfkIUmvgNaWy/eXvKq8/h/inKg=", "dev": true, "requires": { - "graceful-fs": "^4.1.2", - "parse-json": "^2.2.0", - "pify": "^2.0.0", - "strip-bom": "^3.0.0" + "graceful-fs": "4.1.11", + "parse-json": "2.2.0", + "pify": "2.3.0", + "strip-bom": "3.0.0" } }, "locate-path": { @@ -2226,8 +2226,8 @@ "integrity": "sha1-K1aLJl7slExtnA3pw9u7ygNUzY4=", "dev": true, "requires": { - "p-locate": "^2.0.0", - "path-exists": "^3.0.0" + "p-locate": "2.0.0", + "path-exists": "3.0.0" }, "dependencies": { "path-exists": { @@ -2254,7 +2254,7 @@ "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-1.2.0.tgz", "integrity": "sha512-aNUAa4UMg/UougV25bbrU4ZaaKNjJ/3/xnvg/twpmKROPdKZPZ9wGgI0opdZzO8q/zUFawoUuixuOv33eZ61Iw==", "requires": { - "pify": "^3.0.0" + "pify": "3.0.0" }, "dependencies": { "pify": { @@ -2269,8 +2269,8 @@ "resolved": "https://registry.npmjs.org/md5.js/-/md5.js-1.3.4.tgz", "integrity": "sha1-6b296UogpawYsENA/Fdk1bCdkB0=", "requires": { - "hash-base": "^3.0.0", - "inherits": "^2.0.1" + "hash-base": "3.0.4", + "inherits": "2.0.3" }, "dependencies": { "hash-base": { @@ -2278,8 +2278,8 @@ "resolved": "https://registry.npmjs.org/hash-base/-/hash-base-3.0.4.tgz", "integrity": "sha1-X8hoaEfs1zSZQDMZprCj8/auSRg=", "requires": { - "inherits": "^2.0.1", - "safe-buffer": "^5.0.1" + "inherits": "2.0.3", + "safe-buffer": "5.1.1" } } } @@ -2309,8 +2309,8 @@ "resolved": "https://registry.npmjs.org/miller-rabin/-/miller-rabin-4.0.1.tgz", "integrity": "sha512-115fLhvZVqWwHPbClyntxEVfVDfl9DLLTuJvq3g2O/Oxi8AiNouAHvDSzHS0viUJc+V5vm3eq91Xwqn9dp4jRA==", "requires": { - "bn.js": "^4.0.0", - "brorand": "^1.0.1" + "bn.js": "4.11.8", + "brorand": "1.1.0" } }, "mime": { @@ -2328,7 +2328,7 @@ "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.18.tgz", "integrity": "sha512-lc/aahn+t4/SWV/qcmumYjymLsWfN3ELhpmVuUFjgsORruuZPVSwAQryq+HHGvO/SI2KVX26bx+En+zhM8g8hQ==", "requires": { - "mime-db": "~1.33.0" + "mime-db": "1.33.0" } }, "mimic-fn": { @@ -2347,7 +2347,7 @@ "resolved": "https://registry.npmjs.org/min-document/-/min-document-2.19.0.tgz", "integrity": "sha1-e9KC4/WELtKVu3SM3Z8f+iyCRoU=", "requires": { - "dom-walk": "^0.1.0" + "dom-walk": "0.1.1" } }, "minimalistic-assert": { @@ -2365,7 +2365,7 @@ "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", "requires": { - "brace-expansion": "^1.1.7" + "brace-expansion": "1.1.11" } }, "minimist": { @@ -2386,7 +2386,7 @@ "resolved": "https://registry.npmjs.org/mkdirp-promise/-/mkdirp-promise-5.0.1.tgz", "integrity": "sha1-6bj2jlUsaKnBcTuEiD96HdA5uKE=", "requires": { - "mkdirp": "*" + "mkdirp": "0.5.1" } }, "mock-fs": { @@ -2409,8 +2409,8 @@ "resolved": "https://registry.npmjs.org/multistream/-/multistream-2.1.0.tgz", "integrity": "sha1-YlwmfVxEQkrWKUeItbtNo9yzLx0=", "requires": { - "inherits": "^2.0.1", - "readable-stream": "^2.0.5" + "inherits": "2.0.3", + "readable-stream": "2.3.5" } }, "mute-stream": { @@ -2424,9 +2424,9 @@ "resolved": "https://registry.npmjs.org/mz/-/mz-2.7.0.tgz", "integrity": "sha512-z81GNO7nnYMEhrGh9LeymoE4+Yr0Wn5McHIZMK5cfQCl+NDX08sCZgUc9/6MHni9IWuFLm1Z3HTCXu2z9fN62Q==", "requires": { - "any-promise": "^1.0.0", - "object-assign": "^4.0.1", - "thenify-all": "^1.0.0" + "any-promise": "1.3.0", + "object-assign": "4.1.1", + "thenify-all": "1.6.0" } }, "nan": { @@ -2467,10 +2467,10 @@ "integrity": "sha512-9jjUFbTPfEy3R/ad/2oNbKtW9Hgovl5O1FvFWKkKblNXoN/Oou6+9+KKohPK13Yc3/TyunyWhJp6gvRNR/PPAw==", "dev": true, "requires": { - "hosted-git-info": "^2.1.4", - "is-builtin-module": "^1.0.0", - "semver": "2 || 3 || 4 || 5", - "validate-npm-package-license": "^3.0.1" + "hosted-git-info": "2.7.1", + "is-builtin-module": "1.0.0", + "semver": "5.4.1", + "validate-npm-package-license": "3.0.4" } }, "number-to-bn": { @@ -2511,10 +2511,10 @@ "integrity": "sha512-exHJeq6kBKj58mqGyTQ9DFvrZC/eR6OwxzoM9YRoGBqrXYonaFyGiFMuc9VZrXf7DarreEwMpurG3dd+CNyW5w==", "dev": true, "requires": { - "define-properties": "^1.1.2", - "function-bind": "^1.1.1", - "has-symbols": "^1.0.0", - "object-keys": "^1.0.11" + "define-properties": "1.1.3", + "function-bind": "1.1.1", + "has-symbols": "1.0.0", + "object-keys": "1.0.12" } }, "object.entries": { @@ -2523,10 +2523,10 @@ "integrity": "sha1-G/mk3SKI9bM/Opk9JXZh8F0WGl8=", "dev": true, "requires": { - "define-properties": "^1.1.2", - "es-abstract": "^1.6.1", - "function-bind": "^1.1.0", - "has": "^1.0.1" + "define-properties": "1.1.3", + "es-abstract": "1.12.0", + "function-bind": "1.1.1", + "has": "1.0.3" } }, "oboe": { @@ -2534,7 +2534,7 @@ "resolved": "https://registry.npmjs.org/oboe/-/oboe-2.1.3.tgz", "integrity": "sha1-K0hl29Rr6BIlcT9Om/5Lz09oCk8=", "requires": { - "http-https": "^1.0.0" + "http-https": "1.0.0" } }, "on-finished": { @@ -2550,7 +2550,7 @@ "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", "requires": { - "wrappy": "1" + "wrappy": "1.0.2" } }, "onetime": { @@ -2559,7 +2559,7 @@ "integrity": "sha1-BnQoIw/WdEOyeUsiu6UotoZ5YtQ=", "dev": true, "requires": { - "mimic-fn": "^1.0.0" + "mimic-fn": "1.2.0" } }, "optionator": { @@ -2567,12 +2567,12 @@ "resolved": "https://registry.npmjs.org/optionator/-/optionator-0.8.2.tgz", "integrity": "sha1-NkxeQJ0/TWMB1sC0wFu6UBgK62Q=", "requires": { - "deep-is": "~0.1.3", - "fast-levenshtein": "~2.0.4", - "levn": "~0.3.0", - "prelude-ls": "~1.1.2", - "type-check": "~0.3.2", - "wordwrap": "~1.0.0" + "deep-is": "0.1.3", + "fast-levenshtein": "2.0.6", + "levn": "0.3.0", + "prelude-ls": "1.1.2", + "type-check": "0.3.2", + "wordwrap": "1.0.0" } }, "os-tmpdir": { @@ -2596,7 +2596,7 @@ "integrity": "sha512-vvcXsLAJ9Dr5rQOPk7toZQZJApBl2K4J6dANSsEuh6QI41JYcsS/qhTGa9ErIUUgK3WNQoJYvylxvjqmiqEA9Q==", "dev": true, "requires": { - "p-try": "^1.0.0" + "p-try": "1.0.0" } }, "p-locate": { @@ -2605,7 +2605,7 @@ "integrity": "sha1-IKAQOyIqcMj9OcwuWAaA893l7EM=", "dev": true, "requires": { - "p-limit": "^1.1.0" + "p-limit": "1.3.0" } }, "p-timeout": { @@ -2613,7 +2613,7 @@ "resolved": "https://registry.npmjs.org/p-timeout/-/p-timeout-1.2.1.tgz", "integrity": "sha1-XrOzU7f86Z8QGhA4iAuwVOu+o4Y=", "requires": { - "p-finally": "^1.0.0" + "p-finally": "1.0.0" } }, "p-try": { @@ -2627,11 +2627,11 @@ "resolved": "https://registry.npmjs.org/parse-asn1/-/parse-asn1-5.1.0.tgz", "integrity": "sha1-N8T5t+06tlx0gXtfJICTf7+XxxI=", "requires": { - "asn1.js": "^4.0.0", - "browserify-aes": "^1.0.0", - "create-hash": "^1.1.0", - "evp_bytestokey": "^1.0.0", - "pbkdf2": "^3.0.3" + "asn1.js": "4.10.1", + "browserify-aes": "1.1.1", + "create-hash": "1.1.3", + "evp_bytestokey": "1.0.3", + "pbkdf2": "3.0.14" } }, "parse-headers": { @@ -2639,7 +2639,7 @@ "resolved": "https://registry.npmjs.org/parse-headers/-/parse-headers-2.0.1.tgz", "integrity": "sha1-aug6eqJanZtwCswoaYzR8e1+lTY=", "requires": { - "for-each": "^0.3.2", + "for-each": "0.3.2", "trim": "0.0.1" } }, @@ -2649,7 +2649,7 @@ "integrity": "sha1-9ID0BDTvgHQfhGkJn43qGPVaTck=", "dev": true, "requires": { - "error-ex": "^1.2.0" + "error-ex": "1.3.2" } }, "parseurl": { @@ -2663,7 +2663,7 @@ "integrity": "sha1-D+tsZPD8UY2adU3V77YscCJ2H0s=", "dev": true, "requires": { - "pinkie-promise": "^2.0.0" + "pinkie-promise": "2.0.1" } }, "path-is-absolute": { @@ -2699,7 +2699,7 @@ "integrity": "sha1-8BLMuEFbcJb8LaoQVMPXI4lZTHM=", "dev": true, "requires": { - "pify": "^2.0.0" + "pify": "2.3.0" } }, "pbkdf2": { @@ -2707,11 +2707,11 @@ "resolved": "https://registry.npmjs.org/pbkdf2/-/pbkdf2-3.0.14.tgz", "integrity": "sha512-gjsZW9O34fm0R7PaLHRJmLLVfSoesxztjPjE9o6R+qtVJij90ltg1joIovN9GKrRW3t1PzhDDG3UMEMFfZ+1wA==", "requires": { - "create-hash": "^1.1.2", - "create-hmac": "^1.1.4", - "ripemd160": "^2.0.1", - "safe-buffer": "^5.0.1", - "sha.js": "^2.4.8" + "create-hash": "1.1.3", + "create-hmac": "1.1.6", + "ripemd160": "2.0.1", + "safe-buffer": "5.1.1", + "sha.js": "2.4.11" } }, "pend": { @@ -2739,7 +2739,7 @@ "resolved": "https://registry.npmjs.org/pinkie-promise/-/pinkie-promise-2.0.1.tgz", "integrity": "sha1-ITXW36ejWMBprJsXh3YogihFD/o=", "requires": { - "pinkie": "^2.0.0" + "pinkie": "2.0.4" } }, "pkg": { @@ -2768,9 +2768,9 @@ "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-4.0.1.tgz", "integrity": "sha1-f8DGyJV/mD9X8waiTlud3Y0N2IA=", "requires": { - "graceful-fs": "^4.1.2", - "jsonfile": "^3.0.0", - "universalify": "^0.1.0" + "graceful-fs": "4.1.11", + "jsonfile": "3.0.1", + "universalify": "0.1.1" } }, "jsonfile": { @@ -2778,7 +2778,7 @@ "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-3.0.1.tgz", "integrity": "sha1-pezG9l9T9mLEQVx2daAzHQmS7GY=", "requires": { - "graceful-fs": "^4.1.6" + "graceful-fs": "4.1.11" } }, "minimist": { @@ -2794,7 +2794,7 @@ "integrity": "sha1-ektQio1bstYp1EcFb/TpyTFM89Q=", "dev": true, "requires": { - "find-up": "^1.0.0" + "find-up": "1.1.2" } }, "pkg-fetch": { @@ -2821,8 +2821,8 @@ "resolved": "https://registry.npmjs.org/ajv/-/ajv-4.11.8.tgz", "integrity": "sha1-gv+wKynmYq5TvcIK8VlHcGc5xTY=", "requires": { - "co": "^4.6.0", - "json-stable-stringify": "^1.0.1" + "co": "4.6.0", + "json-stable-stringify": "1.0.1" } }, "assert-plus": { @@ -2840,7 +2840,7 @@ "resolved": "https://registry.npmjs.org/boom/-/boom-2.10.1.tgz", "integrity": "sha1-OciRjO/1eZ+D+UkqhI9iWt0Mdm8=", "requires": { - "hoek": "2.x.x" + "hoek": "2.16.3" } }, "cryptiles": { @@ -2848,7 +2848,7 @@ "resolved": "https://registry.npmjs.org/cryptiles/-/cryptiles-2.0.5.tgz", "integrity": "sha1-O9/s3GCBR8HGcgL6KR59ylnqo7g=", "requires": { - "boom": "2.x.x" + "boom": "2.10.1" } }, "form-data": { @@ -2856,9 +2856,9 @@ "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.1.4.tgz", "integrity": "sha1-M8GDrPGTJ27KqYFDpp6Uv+4XUNE=", "requires": { - "asynckit": "^0.4.0", - "combined-stream": "^1.0.5", - "mime-types": "^2.1.12" + "asynckit": "0.4.0", + "combined-stream": "1.0.6", + "mime-types": "2.1.18" } }, "fs-extra": { @@ -2866,9 +2866,9 @@ "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-4.0.1.tgz", "integrity": "sha1-f8DGyJV/mD9X8waiTlud3Y0N2IA=", "requires": { - "graceful-fs": "^4.1.2", - "jsonfile": "^3.0.0", - "universalify": "^0.1.0" + "graceful-fs": "4.1.11", + "jsonfile": "3.0.1", + "universalify": "0.1.1" } }, "har-schema": { @@ -2881,8 +2881,8 @@ "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-4.2.1.tgz", "integrity": "sha1-M0gdDxu/9gDdID11gSpqX7oALio=", "requires": { - "ajv": "^4.9.1", - "har-schema": "^1.0.5" + "ajv": "4.11.8", + "har-schema": "1.0.5" } }, "hawk": { @@ -2890,10 +2890,10 @@ "resolved": "https://registry.npmjs.org/hawk/-/hawk-3.1.3.tgz", "integrity": "sha1-B4REvXwWQLD+VA0sm3PVlnjo4cQ=", "requires": { - "boom": "2.x.x", - "cryptiles": "2.x.x", - "hoek": "2.x.x", - "sntp": "1.x.x" + "boom": "2.10.1", + "cryptiles": "2.0.5", + "hoek": "2.16.3", + "sntp": "1.0.9" } }, "hoek": { @@ -2906,9 +2906,9 @@ "resolved": "https://registry.npmjs.org/http-signature/-/http-signature-1.1.1.tgz", "integrity": "sha1-33LiZwZs0Kxn+3at+OE0qPvPkb8=", "requires": { - "assert-plus": "^0.2.0", - "jsprim": "^1.2.2", - "sshpk": "^1.7.0" + "assert-plus": "0.2.0", + "jsprim": "1.4.1", + "sshpk": "1.14.1" } }, "jsonfile": { @@ -2916,7 +2916,7 @@ "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-3.0.1.tgz", "integrity": "sha1-pezG9l9T9mLEQVx2daAzHQmS7GY=", "requires": { - "graceful-fs": "^4.1.6" + "graceful-fs": "4.1.11" } }, "minimist": { @@ -2939,28 +2939,28 @@ "resolved": "https://registry.npmjs.org/request/-/request-2.81.0.tgz", "integrity": "sha1-xpKJRqDgbF+Nb4qTM0af/aRimKA=", "requires": { - "aws-sign2": "~0.6.0", - "aws4": "^1.2.1", - "caseless": "~0.12.0", - "combined-stream": "~1.0.5", - "extend": "~3.0.0", - "forever-agent": "~0.6.1", - "form-data": "~2.1.1", - "har-validator": "~4.2.1", - "hawk": "~3.1.3", - "http-signature": "~1.1.0", - "is-typedarray": "~1.0.0", - "isstream": "~0.1.2", - "json-stringify-safe": "~5.0.1", - "mime-types": "~2.1.7", - "oauth-sign": "~0.8.1", - "performance-now": "^0.2.0", - "qs": "~6.4.0", - "safe-buffer": "^5.0.1", - "stringstream": "~0.0.4", - "tough-cookie": "~2.3.0", - "tunnel-agent": "^0.6.0", - "uuid": "^3.0.0" + "aws-sign2": "0.6.0", + "aws4": "1.6.0", + "caseless": "0.12.0", + "combined-stream": "1.0.6", + "extend": "3.0.1", + "forever-agent": "0.6.1", + "form-data": "2.1.4", + "har-validator": "4.2.1", + "hawk": "3.1.3", + "http-signature": "1.1.1", + "is-typedarray": "1.0.0", + "isstream": "0.1.2", + "json-stringify-safe": "5.0.1", + "mime-types": "2.1.18", + "oauth-sign": "0.8.2", + "performance-now": "0.2.0", + "qs": "6.4.0", + "safe-buffer": "5.1.1", + "stringstream": "0.0.5", + "tough-cookie": "2.3.4", + "tunnel-agent": "0.6.0", + "uuid": "3.2.1" } }, "sntp": { @@ -2968,7 +2968,7 @@ "resolved": "https://registry.npmjs.org/sntp/-/sntp-1.0.9.tgz", "integrity": "sha1-ZUEYTMkK7qbG57NeJlkIJEPGYZg=", "requires": { - "hoek": "2.x.x" + "hoek": "2.16.3" } } } @@ -3015,7 +3015,7 @@ "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.3.tgz", "integrity": "sha512-jQTChiCJteusULxjBp8+jftSQE5Obdl3k4cnmLA6WXtK6XFuWRnvVL7aCiBqaLPM8c4ph0S4tKna8XvmIwEnXQ==", "requires": { - "forwarded": "~0.1.2", + "forwarded": "0.1.2", "ipaddr.js": "1.6.0" } }, @@ -3024,11 +3024,11 @@ "resolved": "https://registry.npmjs.org/public-encrypt/-/public-encrypt-4.0.0.tgz", "integrity": "sha1-OfaZ86RlYN1eusvKaTyvfGXBjMY=", "requires": { - "bn.js": "^4.1.0", - "browserify-rsa": "^4.0.0", - "create-hash": "^1.1.0", - "parse-asn1": "^5.0.0", - "randombytes": "^2.0.1" + "bn.js": "4.11.8", + "browserify-rsa": "4.0.1", + "create-hash": "1.1.3", + "parse-asn1": "5.1.0", + "randombytes": "2.0.6" } }, "punycode": { @@ -3046,9 +3046,9 @@ "resolved": "https://registry.npmjs.org/query-string/-/query-string-5.1.1.tgz", "integrity": "sha512-gjWOsm2SoGlgLEdAGt7a6slVOk9mGiXmPFMqrEhLQ68rhQuBnpfs3+EmlvqKyxnCo9/PPlF+9MtY02S1aFg+Jw==", "requires": { - "decode-uri-component": "^0.2.0", - "object-assign": "^4.1.0", - "strict-uri-encode": "^1.0.0" + "decode-uri-component": "0.2.0", + "object-assign": "4.1.1", + "strict-uri-encode": "1.1.0" } }, "randombytes": { @@ -3056,7 +3056,7 @@ "resolved": "https://registry.npmjs.org/randombytes/-/randombytes-2.0.6.tgz", "integrity": "sha512-CIQ5OFxf4Jou6uOKe9t1AOgqpeU5fd70A8NPdHSGeYXqXsPe6peOwI0cUl88RWZ6sP1vPMV3avd/R6cZ5/sP1A==", "requires": { - "safe-buffer": "^5.1.0" + "safe-buffer": "5.1.1" } }, "randomfill": { @@ -3064,8 +3064,8 @@ "resolved": "https://registry.npmjs.org/randomfill/-/randomfill-1.0.4.tgz", "integrity": "sha512-87lcbR8+MhcWcUiQ+9e+Rwx8MyR2P7qnt15ynUlbm3TU/fjbgz4GsvfSUDTemtCCtVCqb4ZcEFlyPNTh9bBTLw==", "requires": { - "randombytes": "^2.0.5", - "safe-buffer": "^5.1.0" + "randombytes": "2.0.6", + "safe-buffer": "5.1.1" } }, "randomhex": { @@ -3095,9 +3095,9 @@ "integrity": "sha1-jvHAYjxqbbDcZxPEv6xGMysjaPg=", "dev": true, "requires": { - "load-json-file": "^2.0.0", - "normalize-package-data": "^2.3.2", - "path-type": "^2.0.0" + "load-json-file": "2.0.0", + "normalize-package-data": "2.4.0", + "path-type": "2.0.0" } }, "read-pkg-up": { @@ -3106,8 +3106,8 @@ "integrity": "sha1-a3KoBImE4MQeeVEP1en6mbO1Sb4=", "dev": true, "requires": { - "find-up": "^2.0.0", - "read-pkg": "^2.0.0" + "find-up": "2.1.0", + "read-pkg": "2.0.0" }, "dependencies": { "find-up": { @@ -3116,7 +3116,7 @@ "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", "dev": true, "requires": { - "locate-path": "^2.0.0" + "locate-path": "2.0.0" } } } @@ -3126,13 +3126,13 @@ "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.5.tgz", "integrity": "sha512-tK0yDhrkygt/knjowCUiWP9YdV7c5R+8cR0r/kt9ZhBU906Fs6RpQJCEilamRJj1Nx2rWI6LkW9gKqjTkshhEw==", "requires": { - "core-util-is": "~1.0.0", - "inherits": "~2.0.3", - "isarray": "~1.0.0", - "process-nextick-args": "~2.0.0", - "safe-buffer": "~5.1.1", - "string_decoder": "~1.0.3", - "util-deprecate": "~1.0.1" + "core-util-is": "1.0.2", + "inherits": "2.0.3", + "isarray": "1.0.0", + "process-nextick-args": "2.0.0", + "safe-buffer": "5.1.1", + "string_decoder": "1.0.3", + "util-deprecate": "1.0.2" } }, "regenerator-runtime": { @@ -3151,28 +3151,28 @@ "resolved": "https://registry.npmjs.org/request/-/request-2.85.0.tgz", "integrity": "sha512-8H7Ehijd4js+s6wuVPLjwORxD4zeuyjYugprdOXlPSqaApmL/QOy+EB/beICHVCHkGMKNh5rvihb5ov+IDw4mg==", "requires": { - "aws-sign2": "~0.7.0", - "aws4": "^1.6.0", - "caseless": "~0.12.0", - "combined-stream": "~1.0.5", - "extend": "~3.0.1", - "forever-agent": "~0.6.1", - "form-data": "~2.3.1", - "har-validator": "~5.0.3", - "hawk": "~6.0.2", - "http-signature": "~1.2.0", - "is-typedarray": "~1.0.0", - "isstream": "~0.1.2", - "json-stringify-safe": "~5.0.1", - "mime-types": "~2.1.17", - "oauth-sign": "~0.8.2", - "performance-now": "^2.1.0", - "qs": "~6.5.1", - "safe-buffer": "^5.1.1", - "stringstream": "~0.0.5", - "tough-cookie": "~2.3.3", - "tunnel-agent": "^0.6.0", - "uuid": "^3.1.0" + "aws-sign2": "0.7.0", + "aws4": "1.6.0", + "caseless": "0.12.0", + "combined-stream": "1.0.6", + "extend": "3.0.1", + "forever-agent": "0.6.1", + "form-data": "2.3.2", + "har-validator": "5.0.3", + "hawk": "6.0.2", + "http-signature": "1.2.0", + "is-typedarray": "1.0.0", + "isstream": "0.1.2", + "json-stringify-safe": "5.0.1", + "mime-types": "2.1.18", + "oauth-sign": "0.8.2", + "performance-now": "2.1.0", + "qs": "6.5.1", + "safe-buffer": "5.1.1", + "stringstream": "0.0.5", + "tough-cookie": "2.3.4", + "tunnel-agent": "0.6.0", + "uuid": "3.2.1" } }, "request-progress": { @@ -3180,7 +3180,7 @@ "resolved": "https://registry.npmjs.org/request-progress/-/request-progress-3.0.0.tgz", "integrity": "sha1-TKdUCBx/7GP1BeT6qCWqBs1mnb4=", "requires": { - "throttleit": "^1.0.0" + "throttleit": "1.0.0" } }, "require-uncached": { @@ -3189,8 +3189,8 @@ "integrity": "sha1-Tg1W1slmL9MeQwEcS5WqSZVUIdM=", "dev": true, "requires": { - "caller-path": "^0.1.0", - "resolve-from": "^1.0.0" + "caller-path": "0.1.0", + "resolve-from": "1.0.1" } }, "resolve": { @@ -3198,7 +3198,7 @@ "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.4.0.tgz", "integrity": "sha512-aW7sVKPufyHqOmyyLzg/J+8606v5nevBgaliIlV7nUpVMsDnoBGV/cbSLNjZAg9q0Cfd/+easKVKQ8vOu8fn1Q==", "requires": { - "path-parse": "^1.0.5" + "path-parse": "1.0.5" } }, "resolve-from": { @@ -3213,8 +3213,8 @@ "integrity": "sha1-n37ih/gv0ybU/RYpI9YhKe7g368=", "dev": true, "requires": { - "onetime": "^2.0.0", - "signal-exit": "^3.0.2" + "onetime": "2.0.1", + "signal-exit": "3.0.2" } }, "rimraf": { @@ -3222,7 +3222,7 @@ "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.6.2.tgz", "integrity": "sha512-lreewLK/BlghmxtfH36YYVg1i8IAce4TI7oao75I1g245+6BctqTVQiBP3YUJ9C6DQOXJmkYR9X9fCLtCOJc5w==", "requires": { - "glob": "^7.0.5" + "glob": "7.1.2" } }, "ripemd160": { @@ -3230,8 +3230,8 @@ "resolved": "https://registry.npmjs.org/ripemd160/-/ripemd160-2.0.1.tgz", "integrity": "sha1-D0WEKVxTo2KK9+bXmsohzlfRxuc=", "requires": { - "hash-base": "^2.0.0", - "inherits": "^2.0.1" + "hash-base": "2.0.2", + "inherits": "2.0.3" } }, "rlp": { @@ -3245,7 +3245,7 @@ "integrity": "sha1-A3GrSuC91yDUFm19/aZP96RFpsA=", "dev": true, "requires": { - "is-promise": "^2.1.0" + "is-promise": "2.1.0" } }, "rxjs": { @@ -3254,7 +3254,7 @@ "integrity": "sha512-hV7criqbR0pe7EeL3O66UYVg92IR0XsA97+9y+BWTePK9SKmEI5Qd3Zj6uPnGkNzXsBywBQWTvujPl+1Kn9Zjw==", "dev": true, "requires": { - "tslib": "^1.9.0" + "tslib": "1.9.3" } }, "safe-buffer": { @@ -3273,7 +3273,7 @@ "resolved": "https://registry.npmjs.org/scrypt/-/scrypt-6.0.3.tgz", "integrity": "sha1-BOAUpWgrU/pQwtXM4WfXGcBthw0=", "requires": { - "nan": "^2.0.8" + "nan": "2.10.0" } }, "scrypt.js": { @@ -3281,8 +3281,8 @@ "resolved": "https://registry.npmjs.org/scrypt.js/-/scrypt.js-0.2.0.tgz", "integrity": "sha1-r40UZbcemZARC+38WTuUeeA6ito=", "requires": { - "scrypt": "^6.0.2", - "scryptsy": "^1.2.1" + "scrypt": "6.0.3", + "scryptsy": "1.2.1" } }, "scryptsy": { @@ -3290,7 +3290,7 @@ "resolved": "https://registry.npmjs.org/scryptsy/-/scryptsy-1.2.1.tgz", "integrity": "sha1-oyJfpLJST4AnAHYeKFW987LZIWM=", "requires": { - "pbkdf2": "^3.0.3" + "pbkdf2": "3.0.14" } }, "secp256k1": { @@ -3298,14 +3298,14 @@ "resolved": "https://registry.npmjs.org/secp256k1/-/secp256k1-3.5.0.tgz", "integrity": "sha512-e5QIJl8W7Y4tT6LHffVcZAxJjvpgE5Owawv6/XCYPQljE9aP2NFFddQ8OYMKhdLshNu88FfL3qCN3/xYkXGRsA==", "requires": { - "bindings": "^1.2.1", - "bip66": "^1.1.3", - "bn.js": "^4.11.3", - "create-hash": "^1.1.2", - "drbg.js": "^1.0.1", - "elliptic": "^6.2.3", - "nan": "^2.2.1", - "safe-buffer": "^5.1.0" + "bindings": "1.3.0", + "bip66": "1.1.5", + "bn.js": "4.11.8", + "create-hash": "1.1.3", + "drbg.js": "1.0.1", + "elliptic": "6.4.0", + "nan": "2.10.0", + "safe-buffer": "5.1.1" } }, "seek-bzip": { @@ -3313,7 +3313,7 @@ "resolved": "https://registry.npmjs.org/seek-bzip/-/seek-bzip-1.0.5.tgz", "integrity": "sha1-z+kXyz0nS8/6x5J1ivUxc+sfq9w=", "requires": { - "commander": "~2.8.1" + "commander": "2.8.1" } }, "semver": { @@ -3327,18 +3327,18 @@ "integrity": "sha512-E64YFPUssFHEFBvpbbjr44NCLtI1AohxQ8ZSiJjQLskAdKuriYEP6VyGEsRDH8ScozGpkaX1BGvhanqCwkcEZw==", "requires": { "debug": "2.6.9", - "depd": "~1.1.2", - "destroy": "~1.0.4", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "etag": "~1.8.1", + "depd": "1.1.2", + "destroy": "1.0.4", + "encodeurl": "1.0.2", + "escape-html": "1.0.3", + "etag": "1.8.1", "fresh": "0.5.2", - "http-errors": "~1.6.2", + "http-errors": "1.6.2", "mime": "1.4.1", "ms": "2.0.0", - "on-finished": "~2.3.0", - "range-parser": "~1.2.0", - "statuses": "~1.4.0" + "on-finished": "2.3.0", + "range-parser": "1.2.0", + "statuses": "1.4.0" }, "dependencies": { "statuses": { @@ -3353,9 +3353,9 @@ "resolved": "https://registry.npmjs.org/serve-static/-/serve-static-1.13.2.tgz", "integrity": "sha512-p/tdJrO4U387R9oMjb1oj7qSMaMfmOyd4j9hOFoxZe2baQszgHcSWjuya/CiT5kgZZKRudHNOA0pYXOl8rQ5nw==", "requires": { - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "parseurl": "~1.3.2", + "encodeurl": "1.0.2", + "escape-html": "1.0.3", + "parseurl": "1.3.2", "send": "0.16.2" } }, @@ -3364,11 +3364,11 @@ "resolved": "https://registry.npmjs.org/servify/-/servify-0.1.12.tgz", "integrity": "sha512-/xE6GvsKKqyo1BAY+KxOWXcLpPsUUyji7Qg3bVD7hh1eRze5bR1uYiuDA/k3Gof1s9BTzQZEJK8sNcNGFIzeWw==", "requires": { - "body-parser": "^1.16.0", - "cors": "^2.8.1", - "express": "^4.14.0", - "request": "^2.79.0", - "xhr": "^2.3.3" + "body-parser": "1.18.2", + "cors": "2.8.4", + "express": "4.16.3", + "request": "2.85.0", + "xhr": "2.4.1" } }, "setimmediate": { @@ -3386,8 +3386,8 @@ "resolved": "https://registry.npmjs.org/sha.js/-/sha.js-2.4.11.tgz", "integrity": "sha512-QMEp5B7cftE7APOjk5Y6xgrbWu+WkLVQwk8JNjZ8nKRciZaByEW6MubieAiToS7+dwvrjGhH8jRXz3MVd0AYqQ==", "requires": { - "inherits": "^2.0.1", - "safe-buffer": "^5.0.1" + "inherits": "2.0.3", + "safe-buffer": "5.1.1" } }, "sha3": { @@ -3395,7 +3395,7 @@ "resolved": "https://registry.npmjs.org/sha3/-/sha3-1.2.0.tgz", "integrity": "sha1-aYnxtwpJhwWHajc+LGKs6WqpOZo=", "requires": { - "nan": "^2.0.5" + "nan": "2.10.0" } }, "shebang-command": { @@ -3404,7 +3404,7 @@ "integrity": "sha1-RKrGW2lbAzmJaMOfNj/uXer98eo=", "dev": true, "requires": { - "shebang-regex": "^1.0.0" + "shebang-regex": "1.0.0" } }, "shebang-regex": { @@ -3434,9 +3434,9 @@ "resolved": "https://registry.npmjs.org/simple-get/-/simple-get-2.7.0.tgz", "integrity": "sha512-RkE9rGPHcxYZ/baYmgJtOSM63vH0Vyq+ma5TijBcLla41SWlh8t6XYIGMR/oeZcmr+/G8k+zrClkkVrtnQ0esg==", "requires": { - "decompress-response": "^3.3.0", - "once": "^1.3.1", - "simple-concat": "^1.0.0" + "decompress-response": "3.3.0", + "once": "1.4.0", + "simple-concat": "1.0.0" } }, "slice-ansi": { @@ -3445,7 +3445,7 @@ "integrity": "sha512-POqxBK6Lb3q6s047D/XsDVNPnF9Dl8JSaqe9h9lURl0OdNqy/ujDrOiIHtsqXMGbWWTIomRzAMaTyawAU//Reg==", "dev": true, "requires": { - "is-fullwidth-code-point": "^2.0.0" + "is-fullwidth-code-point": "2.0.0" } }, "sntp": { @@ -3453,7 +3453,7 @@ "resolved": "https://registry.npmjs.org/sntp/-/sntp-2.1.0.tgz", "integrity": "sha512-FL1b58BDrqS3A11lJ0zEdnJ3UOKqVxawAkF3k7F0CVN7VQ34aZrV+G8BZ1WC9ZL7NyrwsW0oviwsWDgRuVYtJg==", "requires": { - "hoek": "4.x.x" + "hoek": "4.2.1" } }, "source-map": { @@ -3462,7 +3462,7 @@ "integrity": "sha1-2rc/vPwrqBm03gO9b26qSBZLP50=", "optional": true, "requires": { - "amdefine": ">=0.0.4" + "amdefine": "1.0.1" } }, "spdx-correct": { @@ -3471,8 +3471,8 @@ "integrity": "sha512-N19o9z5cEyc8yQQPukRCZ9EUmb4HUpnrmaL/fxS2pBo2jbfcFRVuFZ/oFC+vZz0MNNk0h80iMn5/S6qGZOL5+g==", "dev": true, "requires": { - "spdx-expression-parse": "^3.0.0", - "spdx-license-ids": "^3.0.0" + "spdx-expression-parse": "3.0.0", + "spdx-license-ids": "3.0.1" } }, "spdx-exceptions": { @@ -3487,8 +3487,8 @@ "integrity": "sha512-Yg6D3XpRD4kkOmTpdgbUiEJFKghJH03fiC1OPll5h/0sO6neh2jqRDVHOQ4o/LMea0tgCkbMgea5ip/e+MkWyg==", "dev": true, "requires": { - "spdx-exceptions": "^2.1.0", - "spdx-license-ids": "^3.0.0" + "spdx-exceptions": "2.1.0", + "spdx-license-ids": "3.0.1" } }, "spdx-license-ids": { @@ -3508,14 +3508,14 @@ "resolved": "https://registry.npmjs.org/sshpk/-/sshpk-1.14.1.tgz", "integrity": "sha1-Ew9Zde3a2WPx1W+SuaxsUfqfg+s=", "requires": { - "asn1": "~0.2.3", - "assert-plus": "^1.0.0", - "bcrypt-pbkdf": "^1.0.0", - "dashdash": "^1.12.0", - "ecc-jsbn": "~0.1.1", - "getpass": "^0.1.1", - "jsbn": "~0.1.0", - "tweetnacl": "~0.14.0" + "asn1": "0.2.3", + "assert-plus": "1.0.0", + "bcrypt-pbkdf": "1.0.1", + "dashdash": "1.14.1", + "ecc-jsbn": "0.1.1", + "getpass": "0.1.7", + "jsbn": "0.1.1", + "tweetnacl": "0.14.5" } }, "statuses": { @@ -3528,7 +3528,7 @@ "resolved": "https://registry.npmjs.org/stream-meter/-/stream-meter-1.0.4.tgz", "integrity": "sha1-Uq+Vql6nYKJJFxZwTb/5D3Ov3R0=", "requires": { - "readable-stream": "^2.1.4" + "readable-stream": "2.3.5" } }, "strict-uri-encode": { @@ -3542,8 +3542,8 @@ "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", "dev": true, "requires": { - "is-fullwidth-code-point": "^2.0.0", - "strip-ansi": "^4.0.0" + "is-fullwidth-code-point": "2.0.0", + "strip-ansi": "4.0.0" } }, "string_decoder": { @@ -3551,7 +3551,7 @@ "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", "integrity": "sha512-4AH6Z5fzNNBcH+6XDMfA/BTt87skxqJlO0lAh3Dker5zThcAxG6mKz+iGu308UKoPPQ8Dcqx/4JhujzltRa+hQ==", "requires": { - "safe-buffer": "~5.1.0" + "safe-buffer": "5.1.1" } }, "stringstream": { @@ -3565,7 +3565,7 @@ "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", "dev": true, "requires": { - "ansi-regex": "^3.0.0" + "ansi-regex": "3.0.0" } }, "strip-bom": { @@ -3579,7 +3579,7 @@ "resolved": "https://registry.npmjs.org/strip-dirs/-/strip-dirs-2.1.0.tgz", "integrity": "sha512-JOCxOeKLm2CAS73y/U4ZeZPTkE+gNVCzKt7Eox84Iej1LT/2pTWYpZKJuxwQpvX1LiZb1xokNR7RLfuBAa7T3g==", "requires": { - "is-natural-number": "^4.0.1" + "is-natural-number": "4.0.1" } }, "strip-hex-prefix": { @@ -3601,7 +3601,7 @@ "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-4.5.0.tgz", "integrity": "sha1-vnoN5ITexcXN34s9WRJQRJEvY1s=", "requires": { - "has-flag": "^2.0.0" + "has-flag": "2.0.0" } }, "swarm-js": { @@ -3609,19 +3609,19 @@ "resolved": "https://registry.npmjs.org/swarm-js/-/swarm-js-0.1.37.tgz", "integrity": "sha512-G8gi5fcXP/2upwiuOShJ258sIufBVztekgobr3cVgYXObZwJ5AXLqZn52AI+/ffft29pJexF9WNdUxjlkVehoQ==", "requires": { - "bluebird": "^3.5.0", - "buffer": "^5.0.5", - "decompress": "^4.0.0", - "eth-lib": "^0.1.26", - "fs-extra": "^2.1.2", - "fs-promise": "^2.0.0", - "got": "^7.1.0", - "mime-types": "^2.1.16", - "mkdirp-promise": "^5.0.1", - "mock-fs": "^4.1.0", - "setimmediate": "^1.0.5", - "tar.gz": "^1.0.5", - "xhr-request-promise": "^0.1.2" + "bluebird": "3.5.1", + "buffer": "5.1.0", + "decompress": "4.2.0", + "eth-lib": "0.1.27", + "fs-extra": "2.1.2", + "fs-promise": "2.0.3", + "got": "7.1.0", + "mime-types": "2.1.18", + "mkdirp-promise": "5.0.1", + "mock-fs": "4.4.2", + "setimmediate": "1.0.5", + "tar.gz": "1.0.7", + "xhr-request-promise": "0.1.2" } }, "table": { @@ -3630,12 +3630,12 @@ "integrity": "sha512-S7rnFITmBH1EnyKcvxBh1LjYeQMmnZtCXSEbHcH6S0NoKit24ZuFO/T1vDcLdYsLQkM188PVVhQmzKIuThNkKg==", "dev": true, "requires": { - "ajv": "^6.0.1", - "ajv-keywords": "^3.0.0", - "chalk": "^2.1.0", - "lodash": "^4.17.4", + "ajv": "6.5.3", + "ajv-keywords": "3.2.0", + "chalk": "2.1.0", + "lodash": "4.17.11", "slice-ansi": "1.0.0", - "string-width": "^2.1.1" + "string-width": "2.1.1" }, "dependencies": { "ajv": { @@ -3644,10 +3644,10 @@ "integrity": "sha512-LqZ9wY+fx3UMiiPd741yB2pj3hhil+hQc8taf4o2QGRFpWgZ2V5C8HA165DY9sS3fJwsk7uT7ZlFEyC3Ig3lLg==", "dev": true, "requires": { - "fast-deep-equal": "^2.0.1", - "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.4.1", - "uri-js": "^4.2.2" + "fast-deep-equal": "2.0.1", + "fast-json-stable-stringify": "2.0.0", + "json-schema-traverse": "0.4.1", + "uri-js": "4.2.2" } }, "fast-deep-equal": { @@ -3669,9 +3669,9 @@ "resolved": "https://registry.npmjs.org/tar/-/tar-2.2.1.tgz", "integrity": "sha1-jk0qJWwOIYXGsYrWlK7JaLg8sdE=", "requires": { - "block-stream": "*", - "fstream": "^1.0.2", - "inherits": "2" + "block-stream": "0.0.9", + "fstream": "1.0.11", + "inherits": "2.0.3" } }, "tar-stream": { @@ -3679,10 +3679,10 @@ "resolved": "https://registry.npmjs.org/tar-stream/-/tar-stream-1.5.5.tgz", "integrity": "sha512-mQdgLPc/Vjfr3VWqWbfxW8yQNiJCbAZ+Gf6GDu1Cy0bdb33ofyiNGBtAY96jHFhDuivCwgW1H9DgTON+INiXgg==", "requires": { - "bl": "^1.0.0", - "end-of-stream": "^1.0.0", - "readable-stream": "^2.0.0", - "xtend": "^4.0.0" + "bl": "1.2.2", + "end-of-stream": "1.4.1", + "readable-stream": "2.3.5", + "xtend": "4.0.1" } }, "tar.gz": { @@ -3690,11 +3690,11 @@ "resolved": "https://registry.npmjs.org/tar.gz/-/tar.gz-1.0.7.tgz", "integrity": "sha512-uhGatJvds/3diZrETqMj4RxBR779LKlIE74SsMcn5JProZsfs9j0QBwWO1RW+IWNJxS2x8Zzra1+AW6OQHWphg==", "requires": { - "bluebird": "^2.9.34", - "commander": "^2.8.1", - "fstream": "^1.0.8", - "mout": "^0.11.0", - "tar": "^2.1.1" + "bluebird": "2.11.0", + "commander": "2.8.1", + "fstream": "1.0.11", + "mout": "0.11.1", + "tar": "2.2.1" }, "dependencies": { "bluebird": { @@ -3715,7 +3715,7 @@ "resolved": "https://registry.npmjs.org/thenify/-/thenify-3.3.0.tgz", "integrity": "sha1-5p44obq+lpsBCCB5eLn2K4hgSDk=", "requires": { - "any-promise": "^1.0.0" + "any-promise": "1.3.0" } }, "thenify-all": { @@ -3723,7 +3723,7 @@ "resolved": "https://registry.npmjs.org/thenify-all/-/thenify-all-1.6.0.tgz", "integrity": "sha1-GhkY1ALY/D+Y+/I02wvMjMEOlyY=", "requires": { - "thenify": ">= 3.1.0 < 4" + "thenify": "3.3.0" } }, "throttleit": { @@ -3747,7 +3747,7 @@ "integrity": "sha512-jRCJlojKnZ3addtTOjdIqoRuPEKBvNXcGYqzO6zWZX8KfKEpnGY5jfggJQ3EjKuu8D4bJRr0y+cYJFmYbImXGw==", "dev": true, "requires": { - "os-tmpdir": "~1.0.2" + "os-tmpdir": "1.0.2" } }, "tough-cookie": { @@ -3755,7 +3755,7 @@ "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.3.4.tgz", "integrity": "sha512-TZ6TTfI5NtZnuyy/Kecv+CnoROnyXn2DN97LontgQpCwsX2XyLYCC0ENhYkehSOwAp8rTQKc/NUIF7BkQ5rKLA==", "requires": { - "punycode": "^1.4.1" + "punycode": "1.4.1" } }, "trim": { @@ -3774,7 +3774,7 @@ "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.6.0.tgz", "integrity": "sha1-J6XeoGs2sEoKmWZ3SykIaPD8QP0=", "requires": { - "safe-buffer": "^5.0.1" + "safe-buffer": "5.1.1" } }, "tweetnacl": { @@ -3788,7 +3788,7 @@ "resolved": "https://registry.npmjs.org/type-check/-/type-check-0.3.2.tgz", "integrity": "sha1-WITKtRLPHTVeP7eE8wgEsrUg23I=", "requires": { - "prelude-ls": "~1.1.2" + "prelude-ls": "1.1.2" } }, "type-is": { @@ -3797,7 +3797,7 @@ "integrity": "sha512-HRkVv/5qY2G6I8iab9cI7v1bOIdhm94dVjQCPFElW9W+3GeDOSHmy2EBYe4VTApuzolPcmgFTN3ftVJRKR2J9Q==", "requires": { "media-typer": "0.3.0", - "mime-types": "~2.1.18" + "mime-types": "2.1.18" } }, "typedarray-to-buffer": { @@ -3805,7 +3805,7 @@ "resolved": "https://registry.npmjs.org/typedarray-to-buffer/-/typedarray-to-buffer-3.1.5.tgz", "integrity": "sha512-zdu8XMNEDepKKR+XYOXAVPtWui0ly0NtohUscw+UmaHiAWT8hrV1rr//H6V+0DvJ3OQ19S979M0laLfX8rm82Q==", "requires": { - "is-typedarray": "^1.0.0" + "is-typedarray": "1.0.0" } }, "uid2": { @@ -3823,8 +3823,8 @@ "resolved": "https://registry.npmjs.org/unbzip2-stream/-/unbzip2-stream-1.2.5.tgz", "integrity": "sha512-izD3jxT8xkzwtXRUZjtmRwKnZoeECrfZ8ra/ketwOcusbZEp4mjULMnJOCfTDZBgGQAAY1AJ/IgxcwkavcX9Og==", "requires": { - "buffer": "^3.0.1", - "through": "^2.3.6" + "buffer": "3.6.0", + "through": "2.3.8" }, "dependencies": { "base64-js": { @@ -3838,8 +3838,8 @@ "integrity": "sha1-pyyTb3e5a/UvX357RnGAYoVR3vs=", "requires": { "base64-js": "0.0.8", - "ieee754": "^1.1.4", - "isarray": "^1.0.0" + "ieee754": "1.1.11", + "isarray": "1.0.0" } } } @@ -3854,8 +3854,8 @@ "resolved": "https://registry.npmjs.org/unique-temp-dir/-/unique-temp-dir-1.0.0.tgz", "integrity": "sha1-bc6VsmgcoAPuv7MEpBX5y6vMU4U=", "requires": { - "mkdirp": "^0.5.1", - "os-tmpdir": "^1.0.1", + "mkdirp": "0.5.1", + "os-tmpdir": "1.0.2", "uid2": "0.0.3" } }, @@ -3875,7 +3875,7 @@ "integrity": "sha512-KY9Frmirql91X2Qgjry0Wd4Y+YTdrdZheS8TFwvkbLWf/G5KNJDCh6pKL5OZctEW4+0Baa5idK2ZQuELRwPznQ==", "dev": true, "requires": { - "punycode": "^2.1.0" + "punycode": "2.1.1" }, "dependencies": { "punycode": { @@ -3891,7 +3891,7 @@ "resolved": "https://registry.npmjs.org/url-parse-lax/-/url-parse-lax-1.0.0.tgz", "integrity": "sha1-evjzA2Rem9eaJy56FKxovAYJ2nM=", "requires": { - "prepend-http": "^1.0.1" + "prepend-http": "1.0.4" } }, "url-set-query": { @@ -3930,8 +3930,8 @@ "integrity": "sha512-DpKm2Ui/xN7/HQKCtpZxoRWBhZ9Z0kqtygG8XCgNQ8ZlDnxuQmWhj566j8fN4Cu3/JmbhsDo7fcAJq4s9h27Ew==", "dev": true, "requires": { - "spdx-correct": "^3.0.0", - "spdx-expression-parse": "^3.0.0" + "spdx-correct": "3.0.0", + "spdx-expression-parse": "3.0.0" } }, "validator": { @@ -3949,9 +3949,9 @@ "resolved": "https://registry.npmjs.org/verror/-/verror-1.10.0.tgz", "integrity": "sha1-OhBcoXBTr1XW4nDB+CiGguGNpAA=", "requires": { - "assert-plus": "^1.0.0", + "assert-plus": "1.0.0", "core-util-is": "1.0.2", - "extsprintf": "^1.2.0" + "extsprintf": "1.3.0" } }, "web3": { @@ -4101,9 +4101,9 @@ "resolved": "https://registry.npmjs.org/eth-lib/-/eth-lib-0.2.7.tgz", "integrity": "sha1-L5Pxex4jrsN1nNSj/iDBKGo/wco=", "requires": { - "bn.js": "^4.11.6", - "elliptic": "^6.4.0", - "xhr-request-promise": "^0.1.2" + "bn.js": "4.11.8", + "elliptic": "6.4.0", + "xhr-request-promise": "0.1.2" } }, "uuid": { @@ -4229,12 +4229,11 @@ }, "websocket": { "version": "git://github.com/frozeman/WebSocket-Node.git#7004c39c42ac98875ab61126e5b4a925430f592c", - "from": "websocket@git://github.com/frozeman/WebSocket-Node.git#7004c39c42ac98875ab61126e5b4a925430f592c", "requires": { - "debug": "^2.2.0", - "nan": "^2.3.3", - "typedarray-to-buffer": "^3.1.2", - "yaeti": "^0.0.6" + "debug": "2.6.9", + "nan": "2.10.0", + "typedarray-to-buffer": "3.1.5", + "yaeti": "0.0.6" } }, "which": { @@ -4243,7 +4242,7 @@ "integrity": "sha512-HxJdYWq1MTIQbJ3nw0cqssHoTNU267KlrDuGZ1WYlxDStUtKUhOaJmh112/TZmHxxUfuJqPXSOm7tDyas0OSIQ==", "dev": true, "requires": { - "isexe": "^2.0.0" + "isexe": "2.0.0" } }, "wordwrap": { @@ -4262,7 +4261,7 @@ "integrity": "sha1-X8A4KOJkzqP+kUVUdvejxWbLB1c=", "dev": true, "requires": { - "mkdirp": "^0.5.1" + "mkdirp": "0.5.1" } }, "ws": { @@ -4270,9 +4269,9 @@ "resolved": "https://registry.npmjs.org/ws/-/ws-3.3.3.tgz", "integrity": "sha512-nnWLa/NwZSt4KQJu51MYlCcSQ5g7INpOrOMt4XV8j4dqTXdmlUmSHQ8/oLC069ckre0fRsgfvsKwbTdtKLCDkA==", "requires": { - "async-limiter": "~1.0.0", - "safe-buffer": "~5.1.0", - "ultron": "~1.1.0" + "async-limiter": "1.0.0", + "safe-buffer": "5.1.1", + "ultron": "1.1.1" } }, "xhr": { @@ -4280,10 +4279,10 @@ "resolved": "https://registry.npmjs.org/xhr/-/xhr-2.4.1.tgz", "integrity": "sha512-pAIU5vBr9Hiy5cpFIbPnwf0C18ZF86DBsZKrlsf87N5De/JbA6RJ83UP/cv+aljl4S40iRVMqP4pr4sF9Dnj0A==", "requires": { - "global": "~4.3.0", - "is-function": "^1.0.1", - "parse-headers": "^2.0.0", - "xtend": "^4.0.0" + "global": "4.3.2", + "is-function": "1.0.1", + "parse-headers": "2.0.1", + "xtend": "4.0.1" } }, "xhr-request": { @@ -4291,13 +4290,13 @@ "resolved": "https://registry.npmjs.org/xhr-request/-/xhr-request-1.1.0.tgz", "integrity": "sha512-Y7qzEaR3FDtL3fP30k9wO/e+FBnBByZeybKOhASsGP30NIkRAAkKD/sCnLvgEfAIEC1rcmK7YG8f4oEnIrrWzA==", "requires": { - "buffer-to-arraybuffer": "^0.0.5", - "object-assign": "^4.1.1", - "query-string": "^5.0.1", - "simple-get": "^2.7.0", - "timed-out": "^4.0.1", - "url-set-query": "^1.0.0", - "xhr": "^2.0.4" + "buffer-to-arraybuffer": "0.0.5", + "object-assign": "4.1.1", + "query-string": "5.1.1", + "simple-get": "2.7.0", + "timed-out": "4.0.1", + "url-set-query": "1.0.0", + "xhr": "2.4.1" } }, "xhr-request-promise": { @@ -4305,7 +4304,7 @@ "resolved": "https://registry.npmjs.org/xhr-request-promise/-/xhr-request-promise-0.1.2.tgz", "integrity": "sha1-NDxE0e53JrhkgGloLQ+EDIO0Jh0=", "requires": { - "xhr-request": "^1.0.1" + "xhr-request": "1.1.0" } }, "xhr2": { @@ -4328,8 +4327,8 @@ "resolved": "https://registry.npmjs.org/yauzl/-/yauzl-2.9.1.tgz", "integrity": "sha1-qBmB6nCleUYTOIPwKcWCGok1mn8=", "requires": { - "buffer-crc32": "~0.2.3", - "fd-slicer": "~1.0.1" + "buffer-crc32": "0.2.13", + "fd-slicer": "1.0.1" } } } diff --git a/package-lock.json b/package-lock.json index 37f350ac1..8a88464da 100644 --- a/package-lock.json +++ b/package-lock.json @@ -15,7 +15,7 @@ "integrity": "sha1-OU2+C7X+5Gs42JZzXoto7yOQ0A0=", "dev": true, "requires": { - "@types/node": "*" + "@types/node": "9.6.35" } }, "@types/form-data": { @@ -24,7 +24,7 @@ "integrity": "sha1-yayFsqX9GENbjIXZ7LUObWyJP/g=", "dev": true, "requires": { - "@types/node": "*" + "@types/node": "9.6.35" } }, "@types/node": { @@ -51,12 +51,11 @@ "integrity": "sha512-y2OKSEW4gf2838Eavc56vQY9V46zaXkf3Jl1WpTfUBbzAVrXSr4JRZAAWv55Tv9s5WNz1rVgBgz5d2aJIL1QCg==", "dev": true, "requires": { - "web3": "^0.18.4" + "web3": "0.18.4" }, "dependencies": { "bignumber.js": { "version": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", - "from": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", "dev": true }, "web3": { @@ -66,10 +65,10 @@ "dev": true, "requires": { "bignumber.js": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", - "crypto-js": "^3.1.4", - "utf8": "^2.1.1", - "xhr2": "*", - "xmlhttprequest": "*" + "crypto-js": "3.1.8", + "utf8": "2.1.2", + "xhr2": "0.1.4", + "xmlhttprequest": "1.8.0" } } } @@ -79,19 +78,25 @@ "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.5.tgz", "integrity": "sha1-63d99gEXI6OxTopywIBcjoZ0a9I=", "requires": { - "mime-types": "~2.1.18", + "mime-types": "2.1.18", "negotiator": "0.6.1" } }, + "aes-js": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/aes-js/-/aes-js-3.0.0.tgz", + "integrity": "sha1-4h3xCtbCBTKVvLuNq0Cwnb6ofk0=", + "dev": true + }, "ajv": { "version": "5.5.2", "resolved": "https://registry.npmjs.org/ajv/-/ajv-5.5.2.tgz", "integrity": "sha1-c7Xuyj+rZT49P5Qis0GtQiBdyWU=", "requires": { - "co": "^4.6.0", - "fast-deep-equal": "^1.0.0", - "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.3.0" + "co": "4.6.0", + "fast-deep-equal": "1.1.0", + "fast-json-stable-stringify": "2.0.0", + "json-schema-traverse": "0.3.1" } }, "align-text": { @@ -100,9 +105,9 @@ "integrity": "sha1-DNkKVhCT810KmSVsIrcGlDP60Rc=", "dev": true, "requires": { - "kind-of": "^3.0.2", - "longest": "^1.0.1", - "repeat-string": "^1.5.2" + "kind-of": "3.2.2", + "longest": "1.0.1", + "repeat-string": "1.6.1" }, "dependencies": { "kind-of": { @@ -111,7 +116,7 @@ "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", "dev": true, "requires": { - "is-buffer": "^1.1.5" + "is-buffer": "1.1.6" } } } @@ -128,7 +133,7 @@ "integrity": "sha1-w2rsy6VjuJzrVW82kPCx2eNUf38=", "dev": true, "requires": { - "string-width": "^2.0.0" + "string-width": "2.1.1" }, "dependencies": { "ansi-regex": { @@ -149,8 +154,8 @@ "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", "dev": true, "requires": { - "is-fullwidth-code-point": "^2.0.0", - "strip-ansi": "^4.0.0" + "is-fullwidth-code-point": "2.0.0", + "strip-ansi": "4.0.0" } }, "strip-ansi": { @@ -159,7 +164,7 @@ "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", "dev": true, "requires": { - "ansi-regex": "^3.0.0" + "ansi-regex": "3.0.0" } } } @@ -179,7 +184,7 @@ "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz", "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==", "requires": { - "color-convert": "^1.9.0" + "color-convert": "1.9.1" } }, "any-observable": { @@ -187,14 +192,20 @@ "resolved": "https://registry.npmjs.org/any-observable/-/any-observable-0.2.0.tgz", "integrity": "sha1-xnhwBYADV5AJCD9UrAq6+1wz0kI=" }, + "any-promise": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/any-promise/-/any-promise-1.3.0.tgz", + "integrity": "sha1-q8av7tzqUugJzcA3au0845Y10X8=", + "dev": true + }, "anymatch": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/anymatch/-/anymatch-2.0.0.tgz", "integrity": "sha512-5teOsQWABXHHBFP9y3skS5P3d/WfWXpv3FUpy+LorMrNYaT9pI4oLMQX7jzQ2KklNpGpWHzdCXTDT2Y3XGlZBw==", "dev": true, "requires": { - "micromatch": "^3.1.4", - "normalize-path": "^2.1.1" + "micromatch": "3.1.10", + "normalize-path": "2.1.1" } }, "argparse": { @@ -203,7 +214,7 @@ "integrity": "sha512-o5Roy6tNG4SL/FOkCAN6RzjiakZS25RLYFrcMttJqbdd8BWrnA+fGz57iN5Pb06pvBGvl5gQ0B48dJlslXvoTg==", "dev": true, "requires": { - "sprintf-js": "~1.0.2" + "sprintf-js": "1.0.3" } }, "arr-diff": { @@ -238,7 +249,7 @@ "resolved": "https://registry.npmjs.org/array-union/-/array-union-1.0.2.tgz", "integrity": "sha1-mjRBDk9OPaI96jdb5b5w8kd47Dk=", "requires": { - "array-uniq": "^1.0.1" + "array-uniq": "1.0.3" } }, "array-uniq": { @@ -268,6 +279,17 @@ "resolved": "https://registry.npmjs.org/asn1/-/asn1-0.2.3.tgz", "integrity": "sha1-2sh4dxPJlmhJ/IGAd36+nB3fO4Y=" }, + "asn1.js": { + "version": "4.10.1", + "resolved": "https://registry.npmjs.org/asn1.js/-/asn1.js-4.10.1.tgz", + "integrity": "sha512-p32cOF5q0Zqs9uBiONKYLm6BClCoBCM5O9JfeUSlnQLBTxYdTK+pW+nXflm8UkKd2UYlEbYz5qEi0JuZR9ckSw==", + "dev": true, + "requires": { + "bn.js": "4.11.6", + "inherits": "2.0.3", + "minimalistic-assert": "1.0.1" + } + }, "assert-plus": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", @@ -295,7 +317,7 @@ "resolved": "https://registry.npmjs.org/async/-/async-2.6.0.tgz", "integrity": "sha512-xAfGg1/NTLBBKlHFmnd7PlmUW9KhVQIUuSrYem9xzFUZy13ScvtyGGejaae9iAVRiRq9+Cx7DPFaAAhCpyxyPw==", "requires": { - "lodash": "^4.14.0" + "lodash": "4.17.5" } }, "async-each": { @@ -335,9 +357,9 @@ "resolved": "https://registry.npmjs.org/babel-code-frame/-/babel-code-frame-6.26.0.tgz", "integrity": "sha1-Y/1D99weO7fONZR9uP42mj9Yx0s=", "requires": { - "chalk": "^1.1.3", - "esutils": "^2.0.2", - "js-tokens": "^3.0.2" + "chalk": "1.1.3", + "esutils": "2.0.2", + "js-tokens": "3.0.2" }, "dependencies": { "ansi-styles": { @@ -350,11 +372,11 @@ "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz", "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=", "requires": { - "ansi-styles": "^2.2.1", - "escape-string-regexp": "^1.0.2", - "has-ansi": "^2.0.0", - "strip-ansi": "^3.0.0", - "supports-color": "^2.0.0" + "ansi-styles": "2.2.1", + "escape-string-regexp": "1.0.5", + "has-ansi": "2.0.0", + "strip-ansi": "3.0.1", + "supports-color": "2.0.0" } }, "supports-color": { @@ -369,25 +391,25 @@ "resolved": "https://registry.npmjs.org/babel-core/-/babel-core-6.26.0.tgz", "integrity": "sha1-rzL3izGm/O8RnIew/Y2XU/A6C7g=", "requires": { - "babel-code-frame": "^6.26.0", - "babel-generator": "^6.26.0", - "babel-helpers": "^6.24.1", - "babel-messages": "^6.23.0", - "babel-register": "^6.26.0", - "babel-runtime": "^6.26.0", - "babel-template": "^6.26.0", - "babel-traverse": "^6.26.0", - "babel-types": "^6.26.0", - "babylon": "^6.18.0", - "convert-source-map": "^1.5.0", - "debug": "^2.6.8", - "json5": "^0.5.1", - "lodash": "^4.17.4", - "minimatch": "^3.0.4", - "path-is-absolute": "^1.0.1", - "private": "^0.1.7", - "slash": "^1.0.0", - "source-map": "^0.5.6" + "babel-code-frame": "6.26.0", + "babel-generator": "6.26.1", + "babel-helpers": "6.24.1", + "babel-messages": "6.23.0", + "babel-register": "6.26.0", + "babel-runtime": "6.26.0", + "babel-template": "6.26.0", + "babel-traverse": "6.26.0", + "babel-types": "6.26.0", + "babylon": "6.18.0", + "convert-source-map": "1.5.1", + "debug": "2.6.8", + "json5": "0.5.1", + "lodash": "4.17.5", + "minimatch": "3.0.4", + "path-is-absolute": "1.0.1", + "private": "0.1.8", + "slash": "1.0.0", + "source-map": "0.5.7" }, "dependencies": { "babylon": { @@ -402,14 +424,14 @@ "resolved": "https://registry.npmjs.org/babel-generator/-/babel-generator-6.26.1.tgz", "integrity": "sha512-HyfwY6ApZj7BYTcJURpM5tznulaBvyio7/0d4zFOeMPUmfxkCjHocCuoLa2SAGzBI8AREcH3eP3758F672DppA==", "requires": { - "babel-messages": "^6.23.0", - "babel-runtime": "^6.26.0", - "babel-types": "^6.26.0", - "detect-indent": "^4.0.0", - "jsesc": "^1.3.0", - "lodash": "^4.17.4", - "source-map": "^0.5.7", - "trim-right": "^1.0.1" + "babel-messages": "6.23.0", + "babel-runtime": "6.26.0", + "babel-types": "6.26.0", + "detect-indent": "4.0.0", + "jsesc": "1.3.0", + "lodash": "4.17.5", + "source-map": "0.5.7", + "trim-right": "1.0.1" }, "dependencies": { "jsesc": { @@ -424,9 +446,9 @@ "resolved": "https://registry.npmjs.org/babel-helper-bindify-decorators/-/babel-helper-bindify-decorators-6.24.1.tgz", "integrity": "sha1-FMGeXxQte0fxmlJDHlKxzLxAozA=", "requires": { - "babel-runtime": "^6.22.0", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" + "babel-runtime": "6.26.0", + "babel-traverse": "6.26.0", + "babel-types": "6.26.0" } }, "babel-helper-builder-binary-assignment-operator-visitor": { @@ -434,9 +456,9 @@ "resolved": "https://registry.npmjs.org/babel-helper-builder-binary-assignment-operator-visitor/-/babel-helper-builder-binary-assignment-operator-visitor-6.24.1.tgz", "integrity": "sha1-zORReto1b0IgvK6KAsKzRvmlZmQ=", "requires": { - "babel-helper-explode-assignable-expression": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" + "babel-helper-explode-assignable-expression": "6.24.1", + "babel-runtime": "6.26.0", + "babel-types": "6.26.0" } }, "babel-helper-call-delegate": { @@ -444,10 +466,10 @@ "resolved": "https://registry.npmjs.org/babel-helper-call-delegate/-/babel-helper-call-delegate-6.24.1.tgz", "integrity": "sha1-7Oaqzdx25Bw0YfiL/Fdb0Nqi340=", "requires": { - "babel-helper-hoist-variables": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" + "babel-helper-hoist-variables": "6.24.1", + "babel-runtime": "6.26.0", + "babel-traverse": "6.26.0", + "babel-types": "6.26.0" } }, "babel-helper-define-map": { @@ -455,10 +477,10 @@ "resolved": "https://registry.npmjs.org/babel-helper-define-map/-/babel-helper-define-map-6.26.0.tgz", "integrity": "sha1-pfVtq0GiX5fstJjH66ypgZ+Vvl8=", "requires": { - "babel-helper-function-name": "^6.24.1", - "babel-runtime": "^6.26.0", - "babel-types": "^6.26.0", - "lodash": "^4.17.4" + "babel-helper-function-name": "6.24.1", + "babel-runtime": "6.26.0", + "babel-types": "6.26.0", + "lodash": "4.17.5" } }, "babel-helper-explode-assignable-expression": { @@ -466,9 +488,9 @@ "resolved": "https://registry.npmjs.org/babel-helper-explode-assignable-expression/-/babel-helper-explode-assignable-expression-6.24.1.tgz", "integrity": "sha1-8luCz33BBDPFX3BZLVdGQArCLKo=", "requires": { - "babel-runtime": "^6.22.0", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" + "babel-runtime": "6.26.0", + "babel-traverse": "6.26.0", + "babel-types": "6.26.0" } }, "babel-helper-explode-class": { @@ -476,10 +498,10 @@ "resolved": "https://registry.npmjs.org/babel-helper-explode-class/-/babel-helper-explode-class-6.24.1.tgz", "integrity": "sha1-fcKjkQ3uAHBW4eMdZAztPVTqqes=", "requires": { - "babel-helper-bindify-decorators": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" + "babel-helper-bindify-decorators": "6.24.1", + "babel-runtime": "6.26.0", + "babel-traverse": "6.26.0", + "babel-types": "6.26.0" } }, "babel-helper-function-name": { @@ -487,11 +509,11 @@ "resolved": "https://registry.npmjs.org/babel-helper-function-name/-/babel-helper-function-name-6.24.1.tgz", "integrity": "sha1-00dbjAPtmCQqJbSDUasYOZ01gKk=", "requires": { - "babel-helper-get-function-arity": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" + "babel-helper-get-function-arity": "6.24.1", + "babel-runtime": "6.26.0", + "babel-template": "6.26.0", + "babel-traverse": "6.26.0", + "babel-types": "6.26.0" } }, "babel-helper-get-function-arity": { @@ -499,8 +521,8 @@ "resolved": "https://registry.npmjs.org/babel-helper-get-function-arity/-/babel-helper-get-function-arity-6.24.1.tgz", "integrity": "sha1-j3eCqpNAfEHTqlCQj4mwMbG2hT0=", "requires": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" + "babel-runtime": "6.26.0", + "babel-types": "6.26.0" } }, "babel-helper-hoist-variables": { @@ -508,8 +530,8 @@ "resolved": "https://registry.npmjs.org/babel-helper-hoist-variables/-/babel-helper-hoist-variables-6.24.1.tgz", "integrity": "sha1-HssnaJydJVE+rbyZFKc/VAi+enY=", "requires": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" + "babel-runtime": "6.26.0", + "babel-types": "6.26.0" } }, "babel-helper-optimise-call-expression": { @@ -517,8 +539,8 @@ "resolved": "https://registry.npmjs.org/babel-helper-optimise-call-expression/-/babel-helper-optimise-call-expression-6.24.1.tgz", "integrity": "sha1-96E0J7qfc/j0+pk8VKl4gtEkQlc=", "requires": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" + "babel-runtime": "6.26.0", + "babel-types": "6.26.0" } }, "babel-helper-regex": { @@ -526,9 +548,9 @@ "resolved": "https://registry.npmjs.org/babel-helper-regex/-/babel-helper-regex-6.26.0.tgz", "integrity": "sha1-MlxZ+QL4LyS3T6zu0DY5VPZJXnI=", "requires": { - "babel-runtime": "^6.26.0", - "babel-types": "^6.26.0", - "lodash": "^4.17.4" + "babel-runtime": "6.26.0", + "babel-types": "6.26.0", + "lodash": "4.17.5" } }, "babel-helper-remap-async-to-generator": { @@ -536,11 +558,11 @@ "resolved": "https://registry.npmjs.org/babel-helper-remap-async-to-generator/-/babel-helper-remap-async-to-generator-6.24.1.tgz", "integrity": "sha1-XsWBgnrXI/7N04HxySg5BnbkVRs=", "requires": { - "babel-helper-function-name": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" + "babel-helper-function-name": "6.24.1", + "babel-runtime": "6.26.0", + "babel-template": "6.26.0", + "babel-traverse": "6.26.0", + "babel-types": "6.26.0" } }, "babel-helper-replace-supers": { @@ -548,12 +570,12 @@ "resolved": "https://registry.npmjs.org/babel-helper-replace-supers/-/babel-helper-replace-supers-6.24.1.tgz", "integrity": "sha1-v22/5Dk40XNpohPKiov3S2qQqxo=", "requires": { - "babel-helper-optimise-call-expression": "^6.24.1", - "babel-messages": "^6.23.0", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" + "babel-helper-optimise-call-expression": "6.24.1", + "babel-messages": "6.23.0", + "babel-runtime": "6.26.0", + "babel-template": "6.26.0", + "babel-traverse": "6.26.0", + "babel-types": "6.26.0" } }, "babel-helpers": { @@ -561,8 +583,8 @@ "resolved": "https://registry.npmjs.org/babel-helpers/-/babel-helpers-6.24.1.tgz", "integrity": "sha1-NHHenK7DiOXIUOWX5Yom3fN2ArI=", "requires": { - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" + "babel-runtime": "6.26.0", + "babel-template": "6.26.0" } }, "babel-messages": { @@ -570,7 +592,7 @@ "resolved": "https://registry.npmjs.org/babel-messages/-/babel-messages-6.23.0.tgz", "integrity": "sha1-8830cDhYA1sqKVHG7F7fbGLyYw4=", "requires": { - "babel-runtime": "^6.22.0" + "babel-runtime": "6.26.0" } }, "babel-plugin-check-es2015-constants": { @@ -578,7 +600,7 @@ "resolved": "https://registry.npmjs.org/babel-plugin-check-es2015-constants/-/babel-plugin-check-es2015-constants-6.22.0.tgz", "integrity": "sha1-NRV7EBQm/S/9PaP3XH0ekYNbv4o=", "requires": { - "babel-runtime": "^6.22.0" + "babel-runtime": "6.26.0" } }, "babel-plugin-syntax-async-functions": { @@ -641,9 +663,9 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-async-generator-functions/-/babel-plugin-transform-async-generator-functions-6.24.1.tgz", "integrity": "sha1-8FiQAUX9PpkHpt3yjaWfIVJYpds=", "requires": { - "babel-helper-remap-async-to-generator": "^6.24.1", - "babel-plugin-syntax-async-generators": "^6.5.0", - "babel-runtime": "^6.22.0" + "babel-helper-remap-async-to-generator": "6.24.1", + "babel-plugin-syntax-async-generators": "6.13.0", + "babel-runtime": "6.26.0" } }, "babel-plugin-transform-async-to-generator": { @@ -651,9 +673,9 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-async-to-generator/-/babel-plugin-transform-async-to-generator-6.24.1.tgz", "integrity": "sha1-ZTbjeK/2yx1VF6wOQOs+n8jQh2E=", "requires": { - "babel-helper-remap-async-to-generator": "^6.24.1", - "babel-plugin-syntax-async-functions": "^6.8.0", - "babel-runtime": "^6.22.0" + "babel-helper-remap-async-to-generator": "6.24.1", + "babel-plugin-syntax-async-functions": "6.13.0", + "babel-runtime": "6.26.0" } }, "babel-plugin-transform-class-constructor-call": { @@ -661,9 +683,9 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-class-constructor-call/-/babel-plugin-transform-class-constructor-call-6.24.1.tgz", "integrity": "sha1-gNwoVQWsBn3LjWxl4vbxGrd2Xvk=", "requires": { - "babel-plugin-syntax-class-constructor-call": "^6.18.0", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" + "babel-plugin-syntax-class-constructor-call": "6.18.0", + "babel-runtime": "6.26.0", + "babel-template": "6.26.0" } }, "babel-plugin-transform-class-properties": { @@ -671,10 +693,10 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-class-properties/-/babel-plugin-transform-class-properties-6.24.1.tgz", "integrity": "sha1-anl2PqYdM9NvN7YRqp3vgagbRqw=", "requires": { - "babel-helper-function-name": "^6.24.1", - "babel-plugin-syntax-class-properties": "^6.8.0", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" + "babel-helper-function-name": "6.24.1", + "babel-plugin-syntax-class-properties": "6.13.0", + "babel-runtime": "6.26.0", + "babel-template": "6.26.0" } }, "babel-plugin-transform-decorators": { @@ -682,11 +704,11 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-decorators/-/babel-plugin-transform-decorators-6.24.1.tgz", "integrity": "sha1-eIAT2PjGtSIr33s0Q5Df13Vp4k0=", "requires": { - "babel-helper-explode-class": "^6.24.1", - "babel-plugin-syntax-decorators": "^6.13.0", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-types": "^6.24.1" + "babel-helper-explode-class": "6.24.1", + "babel-plugin-syntax-decorators": "6.13.0", + "babel-runtime": "6.26.0", + "babel-template": "6.26.0", + "babel-types": "6.26.0" } }, "babel-plugin-transform-es2015-arrow-functions": { @@ -694,7 +716,7 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-arrow-functions/-/babel-plugin-transform-es2015-arrow-functions-6.22.0.tgz", "integrity": "sha1-RSaSy3EdX3ncf4XkQM5BufJE0iE=", "requires": { - "babel-runtime": "^6.22.0" + "babel-runtime": "6.26.0" } }, "babel-plugin-transform-es2015-block-scoped-functions": { @@ -702,7 +724,7 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-block-scoped-functions/-/babel-plugin-transform-es2015-block-scoped-functions-6.22.0.tgz", "integrity": "sha1-u8UbSflk1wy42OC5ToICRs46YUE=", "requires": { - "babel-runtime": "^6.22.0" + "babel-runtime": "6.26.0" } }, "babel-plugin-transform-es2015-block-scoping": { @@ -710,11 +732,11 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-block-scoping/-/babel-plugin-transform-es2015-block-scoping-6.26.0.tgz", "integrity": "sha1-1w9SmcEwjQXBL0Y4E7CgnnOxiV8=", "requires": { - "babel-runtime": "^6.26.0", - "babel-template": "^6.26.0", - "babel-traverse": "^6.26.0", - "babel-types": "^6.26.0", - "lodash": "^4.17.4" + "babel-runtime": "6.26.0", + "babel-template": "6.26.0", + "babel-traverse": "6.26.0", + "babel-types": "6.26.0", + "lodash": "4.17.5" } }, "babel-plugin-transform-es2015-classes": { @@ -722,15 +744,15 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-classes/-/babel-plugin-transform-es2015-classes-6.24.1.tgz", "integrity": "sha1-WkxYpQyclGHlZLSyo7+ryXolhNs=", "requires": { - "babel-helper-define-map": "^6.24.1", - "babel-helper-function-name": "^6.24.1", - "babel-helper-optimise-call-expression": "^6.24.1", - "babel-helper-replace-supers": "^6.24.1", - "babel-messages": "^6.23.0", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" + "babel-helper-define-map": "6.26.0", + "babel-helper-function-name": "6.24.1", + "babel-helper-optimise-call-expression": "6.24.1", + "babel-helper-replace-supers": "6.24.1", + "babel-messages": "6.23.0", + "babel-runtime": "6.26.0", + "babel-template": "6.26.0", + "babel-traverse": "6.26.0", + "babel-types": "6.26.0" } }, "babel-plugin-transform-es2015-computed-properties": { @@ -738,8 +760,8 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-computed-properties/-/babel-plugin-transform-es2015-computed-properties-6.24.1.tgz", "integrity": "sha1-b+Ko0WiV1WNPTNmZttNICjCBWbM=", "requires": { - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" + "babel-runtime": "6.26.0", + "babel-template": "6.26.0" } }, "babel-plugin-transform-es2015-destructuring": { @@ -747,7 +769,7 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-destructuring/-/babel-plugin-transform-es2015-destructuring-6.23.0.tgz", "integrity": "sha1-mXux8auWf2gtKwh2/jWNYOdlxW0=", "requires": { - "babel-runtime": "^6.22.0" + "babel-runtime": "6.26.0" } }, "babel-plugin-transform-es2015-duplicate-keys": { @@ -755,8 +777,8 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-duplicate-keys/-/babel-plugin-transform-es2015-duplicate-keys-6.24.1.tgz", "integrity": "sha1-c+s9MQypaePvnskcU3QabxV2Qj4=", "requires": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" + "babel-runtime": "6.26.0", + "babel-types": "6.26.0" } }, "babel-plugin-transform-es2015-for-of": { @@ -764,7 +786,7 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-for-of/-/babel-plugin-transform-es2015-for-of-6.23.0.tgz", "integrity": "sha1-9HyVsrYT3x0+zC/bdXNiPHUkhpE=", "requires": { - "babel-runtime": "^6.22.0" + "babel-runtime": "6.26.0" } }, "babel-plugin-transform-es2015-function-name": { @@ -772,9 +794,9 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-function-name/-/babel-plugin-transform-es2015-function-name-6.24.1.tgz", "integrity": "sha1-g0yJhTvDaxrw86TF26qU/Y6sqos=", "requires": { - "babel-helper-function-name": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" + "babel-helper-function-name": "6.24.1", + "babel-runtime": "6.26.0", + "babel-types": "6.26.0" } }, "babel-plugin-transform-es2015-literals": { @@ -782,7 +804,7 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-literals/-/babel-plugin-transform-es2015-literals-6.22.0.tgz", "integrity": "sha1-T1SgLWzWbPkVKAAZox0xklN3yi4=", "requires": { - "babel-runtime": "^6.22.0" + "babel-runtime": "6.26.0" } }, "babel-plugin-transform-es2015-modules-amd": { @@ -790,9 +812,9 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-modules-amd/-/babel-plugin-transform-es2015-modules-amd-6.24.1.tgz", "integrity": "sha1-Oz5UAXI5hC1tGcMBHEvS8AoA0VQ=", "requires": { - "babel-plugin-transform-es2015-modules-commonjs": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" + "babel-plugin-transform-es2015-modules-commonjs": "6.26.0", + "babel-runtime": "6.26.0", + "babel-template": "6.26.0" } }, "babel-plugin-transform-es2015-modules-commonjs": { @@ -800,10 +822,10 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-modules-commonjs/-/babel-plugin-transform-es2015-modules-commonjs-6.26.0.tgz", "integrity": "sha1-DYOUApt9xqvhqX7xgeAHWN0uXYo=", "requires": { - "babel-plugin-transform-strict-mode": "^6.24.1", - "babel-runtime": "^6.26.0", - "babel-template": "^6.26.0", - "babel-types": "^6.26.0" + "babel-plugin-transform-strict-mode": "6.24.1", + "babel-runtime": "6.26.0", + "babel-template": "6.26.0", + "babel-types": "6.26.0" } }, "babel-plugin-transform-es2015-modules-systemjs": { @@ -811,9 +833,9 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-modules-systemjs/-/babel-plugin-transform-es2015-modules-systemjs-6.24.1.tgz", "integrity": "sha1-/4mhQrkRmpBhlfXxBuzzBdlAfSM=", "requires": { - "babel-helper-hoist-variables": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" + "babel-helper-hoist-variables": "6.24.1", + "babel-runtime": "6.26.0", + "babel-template": "6.26.0" } }, "babel-plugin-transform-es2015-modules-umd": { @@ -821,9 +843,9 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-modules-umd/-/babel-plugin-transform-es2015-modules-umd-6.24.1.tgz", "integrity": "sha1-rJl+YoXNGO1hdq22B9YCNErThGg=", "requires": { - "babel-plugin-transform-es2015-modules-amd": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" + "babel-plugin-transform-es2015-modules-amd": "6.24.1", + "babel-runtime": "6.26.0", + "babel-template": "6.26.0" } }, "babel-plugin-transform-es2015-object-super": { @@ -831,8 +853,8 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-object-super/-/babel-plugin-transform-es2015-object-super-6.24.1.tgz", "integrity": "sha1-JM72muIcuDp/hgPa0CH1cusnj40=", "requires": { - "babel-helper-replace-supers": "^6.24.1", - "babel-runtime": "^6.22.0" + "babel-helper-replace-supers": "6.24.1", + "babel-runtime": "6.26.0" } }, "babel-plugin-transform-es2015-parameters": { @@ -840,12 +862,12 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-parameters/-/babel-plugin-transform-es2015-parameters-6.24.1.tgz", "integrity": "sha1-V6w1GrScrxSpfNE7CfZv3wpiXys=", "requires": { - "babel-helper-call-delegate": "^6.24.1", - "babel-helper-get-function-arity": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" + "babel-helper-call-delegate": "6.24.1", + "babel-helper-get-function-arity": "6.24.1", + "babel-runtime": "6.26.0", + "babel-template": "6.26.0", + "babel-traverse": "6.26.0", + "babel-types": "6.26.0" } }, "babel-plugin-transform-es2015-shorthand-properties": { @@ -853,8 +875,8 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-shorthand-properties/-/babel-plugin-transform-es2015-shorthand-properties-6.24.1.tgz", "integrity": "sha1-JPh11nIch2YbvZmkYi5R8U3jiqA=", "requires": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" + "babel-runtime": "6.26.0", + "babel-types": "6.26.0" } }, "babel-plugin-transform-es2015-spread": { @@ -862,7 +884,7 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-spread/-/babel-plugin-transform-es2015-spread-6.22.0.tgz", "integrity": "sha1-1taKmfia7cRTbIGlQujdnxdG+NE=", "requires": { - "babel-runtime": "^6.22.0" + "babel-runtime": "6.26.0" } }, "babel-plugin-transform-es2015-sticky-regex": { @@ -870,9 +892,9 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-sticky-regex/-/babel-plugin-transform-es2015-sticky-regex-6.24.1.tgz", "integrity": "sha1-AMHNsaynERLN8M9hJsLta0V8zbw=", "requires": { - "babel-helper-regex": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" + "babel-helper-regex": "6.26.0", + "babel-runtime": "6.26.0", + "babel-types": "6.26.0" } }, "babel-plugin-transform-es2015-template-literals": { @@ -880,7 +902,7 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-template-literals/-/babel-plugin-transform-es2015-template-literals-6.22.0.tgz", "integrity": "sha1-qEs0UPfp+PH2g51taH2oS7EjbY0=", "requires": { - "babel-runtime": "^6.22.0" + "babel-runtime": "6.26.0" } }, "babel-plugin-transform-es2015-typeof-symbol": { @@ -888,7 +910,7 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-typeof-symbol/-/babel-plugin-transform-es2015-typeof-symbol-6.23.0.tgz", "integrity": "sha1-3sCfHN3/lLUqxz1QXITfWdzOs3I=", "requires": { - "babel-runtime": "^6.22.0" + "babel-runtime": "6.26.0" } }, "babel-plugin-transform-es2015-unicode-regex": { @@ -896,9 +918,9 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-unicode-regex/-/babel-plugin-transform-es2015-unicode-regex-6.24.1.tgz", "integrity": "sha1-04sS9C6nMj9yk4fxinxa4frrNek=", "requires": { - "babel-helper-regex": "^6.24.1", - "babel-runtime": "^6.22.0", - "regexpu-core": "^2.0.0" + "babel-helper-regex": "6.26.0", + "babel-runtime": "6.26.0", + "regexpu-core": "2.0.0" } }, "babel-plugin-transform-exponentiation-operator": { @@ -906,9 +928,9 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-exponentiation-operator/-/babel-plugin-transform-exponentiation-operator-6.24.1.tgz", "integrity": "sha1-KrDJx/MJj6SJB3cruBP+QejeOg4=", "requires": { - "babel-helper-builder-binary-assignment-operator-visitor": "^6.24.1", - "babel-plugin-syntax-exponentiation-operator": "^6.8.0", - "babel-runtime": "^6.22.0" + "babel-helper-builder-binary-assignment-operator-visitor": "6.24.1", + "babel-plugin-syntax-exponentiation-operator": "6.13.0", + "babel-runtime": "6.26.0" } }, "babel-plugin-transform-export-extensions": { @@ -916,8 +938,8 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-export-extensions/-/babel-plugin-transform-export-extensions-6.22.0.tgz", "integrity": "sha1-U3OLR+deghhYnuqUbLvTkQm75lM=", "requires": { - "babel-plugin-syntax-export-extensions": "^6.8.0", - "babel-runtime": "^6.22.0" + "babel-plugin-syntax-export-extensions": "6.13.0", + "babel-runtime": "6.26.0" } }, "babel-plugin-transform-flow-strip-types": { @@ -925,8 +947,8 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-flow-strip-types/-/babel-plugin-transform-flow-strip-types-6.22.0.tgz", "integrity": "sha1-hMtnKTXUNxT9wyvOhFaNh0Qc988=", "requires": { - "babel-plugin-syntax-flow": "^6.18.0", - "babel-runtime": "^6.22.0" + "babel-plugin-syntax-flow": "6.18.0", + "babel-runtime": "6.26.0" } }, "babel-plugin-transform-object-rest-spread": { @@ -934,8 +956,8 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-object-rest-spread/-/babel-plugin-transform-object-rest-spread-6.26.0.tgz", "integrity": "sha1-DzZpLVD+9rfi1LOsFHgTepY7ewY=", "requires": { - "babel-plugin-syntax-object-rest-spread": "^6.8.0", - "babel-runtime": "^6.26.0" + "babel-plugin-syntax-object-rest-spread": "6.13.0", + "babel-runtime": "6.26.0" } }, "babel-plugin-transform-regenerator": { @@ -943,7 +965,7 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-regenerator/-/babel-plugin-transform-regenerator-6.26.0.tgz", "integrity": "sha1-4HA2lvveJ/Cj78rPi03KL3s6jy8=", "requires": { - "regenerator-transform": "^0.10.0" + "regenerator-transform": "0.10.1" } }, "babel-plugin-transform-strict-mode": { @@ -951,8 +973,8 @@ "resolved": "https://registry.npmjs.org/babel-plugin-transform-strict-mode/-/babel-plugin-transform-strict-mode-6.24.1.tgz", "integrity": "sha1-1fr3qleKZbvlkc9e2uBKDGcCB1g=", "requires": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" + "babel-runtime": "6.26.0", + "babel-types": "6.26.0" } }, "babel-preset-es2015": { @@ -960,30 +982,30 @@ "resolved": "https://registry.npmjs.org/babel-preset-es2015/-/babel-preset-es2015-6.24.1.tgz", "integrity": "sha1-1EBQ1rwsn+6nAqrzjXJ6AhBTiTk=", "requires": { - "babel-plugin-check-es2015-constants": "^6.22.0", - "babel-plugin-transform-es2015-arrow-functions": "^6.22.0", - "babel-plugin-transform-es2015-block-scoped-functions": "^6.22.0", - "babel-plugin-transform-es2015-block-scoping": "^6.24.1", - "babel-plugin-transform-es2015-classes": "^6.24.1", - "babel-plugin-transform-es2015-computed-properties": "^6.24.1", - "babel-plugin-transform-es2015-destructuring": "^6.22.0", - "babel-plugin-transform-es2015-duplicate-keys": "^6.24.1", - "babel-plugin-transform-es2015-for-of": "^6.22.0", - "babel-plugin-transform-es2015-function-name": "^6.24.1", - "babel-plugin-transform-es2015-literals": "^6.22.0", - "babel-plugin-transform-es2015-modules-amd": "^6.24.1", - "babel-plugin-transform-es2015-modules-commonjs": "^6.24.1", - "babel-plugin-transform-es2015-modules-systemjs": "^6.24.1", - "babel-plugin-transform-es2015-modules-umd": "^6.24.1", - "babel-plugin-transform-es2015-object-super": "^6.24.1", - "babel-plugin-transform-es2015-parameters": "^6.24.1", - "babel-plugin-transform-es2015-shorthand-properties": "^6.24.1", - "babel-plugin-transform-es2015-spread": "^6.22.0", - "babel-plugin-transform-es2015-sticky-regex": "^6.24.1", - "babel-plugin-transform-es2015-template-literals": "^6.22.0", - "babel-plugin-transform-es2015-typeof-symbol": "^6.22.0", - "babel-plugin-transform-es2015-unicode-regex": "^6.24.1", - "babel-plugin-transform-regenerator": "^6.24.1" + "babel-plugin-check-es2015-constants": "6.22.0", + "babel-plugin-transform-es2015-arrow-functions": "6.22.0", + "babel-plugin-transform-es2015-block-scoped-functions": "6.22.0", + "babel-plugin-transform-es2015-block-scoping": "6.26.0", + "babel-plugin-transform-es2015-classes": "6.24.1", + "babel-plugin-transform-es2015-computed-properties": "6.24.1", + "babel-plugin-transform-es2015-destructuring": "6.23.0", + "babel-plugin-transform-es2015-duplicate-keys": "6.24.1", + "babel-plugin-transform-es2015-for-of": "6.23.0", + "babel-plugin-transform-es2015-function-name": "6.24.1", + "babel-plugin-transform-es2015-literals": "6.22.0", + "babel-plugin-transform-es2015-modules-amd": "6.24.1", + "babel-plugin-transform-es2015-modules-commonjs": "6.26.0", + "babel-plugin-transform-es2015-modules-systemjs": "6.24.1", + "babel-plugin-transform-es2015-modules-umd": "6.24.1", + "babel-plugin-transform-es2015-object-super": "6.24.1", + "babel-plugin-transform-es2015-parameters": "6.24.1", + "babel-plugin-transform-es2015-shorthand-properties": "6.24.1", + "babel-plugin-transform-es2015-spread": "6.22.0", + "babel-plugin-transform-es2015-sticky-regex": "6.24.1", + "babel-plugin-transform-es2015-template-literals": "6.22.0", + "babel-plugin-transform-es2015-typeof-symbol": "6.23.0", + "babel-plugin-transform-es2015-unicode-regex": "6.24.1", + "babel-plugin-transform-regenerator": "6.26.0" } }, "babel-preset-stage-1": { @@ -991,9 +1013,9 @@ "resolved": "https://registry.npmjs.org/babel-preset-stage-1/-/babel-preset-stage-1-6.24.1.tgz", "integrity": "sha1-dpLNfc1oSZB+auSgqFWJz7niv7A=", "requires": { - "babel-plugin-transform-class-constructor-call": "^6.24.1", - "babel-plugin-transform-export-extensions": "^6.22.0", - "babel-preset-stage-2": "^6.24.1" + "babel-plugin-transform-class-constructor-call": "6.24.1", + "babel-plugin-transform-export-extensions": "6.22.0", + "babel-preset-stage-2": "6.24.1" } }, "babel-preset-stage-2": { @@ -1001,10 +1023,10 @@ "resolved": "https://registry.npmjs.org/babel-preset-stage-2/-/babel-preset-stage-2-6.24.1.tgz", "integrity": "sha1-2eKWD7PXEYfw5k7sYrwHdnIZvcE=", "requires": { - "babel-plugin-syntax-dynamic-import": "^6.18.0", - "babel-plugin-transform-class-properties": "^6.24.1", - "babel-plugin-transform-decorators": "^6.24.1", - "babel-preset-stage-3": "^6.24.1" + "babel-plugin-syntax-dynamic-import": "6.18.0", + "babel-plugin-transform-class-properties": "6.24.1", + "babel-plugin-transform-decorators": "6.24.1", + "babel-preset-stage-3": "6.24.1" } }, "babel-preset-stage-3": { @@ -1012,11 +1034,11 @@ "resolved": "https://registry.npmjs.org/babel-preset-stage-3/-/babel-preset-stage-3-6.24.1.tgz", "integrity": "sha1-g2raCp56f6N8sTj7kyb4eTSkg5U=", "requires": { - "babel-plugin-syntax-trailing-function-commas": "^6.22.0", - "babel-plugin-transform-async-generator-functions": "^6.24.1", - "babel-plugin-transform-async-to-generator": "^6.24.1", - "babel-plugin-transform-exponentiation-operator": "^6.24.1", - "babel-plugin-transform-object-rest-spread": "^6.22.0" + "babel-plugin-syntax-trailing-function-commas": "6.22.0", + "babel-plugin-transform-async-generator-functions": "6.24.1", + "babel-plugin-transform-async-to-generator": "6.24.1", + "babel-plugin-transform-exponentiation-operator": "6.24.1", + "babel-plugin-transform-object-rest-spread": "6.26.0" } }, "babel-register": { @@ -1024,13 +1046,13 @@ "resolved": "https://registry.npmjs.org/babel-register/-/babel-register-6.26.0.tgz", "integrity": "sha1-btAhFz4vy0htestFxgCahW9kcHE=", "requires": { - "babel-core": "^6.26.0", - "babel-runtime": "^6.26.0", - "core-js": "^2.5.0", - "home-or-tmp": "^2.0.0", - "lodash": "^4.17.4", - "mkdirp": "^0.5.1", - "source-map-support": "^0.4.15" + "babel-core": "6.26.0", + "babel-runtime": "6.26.0", + "core-js": "2.5.3", + "home-or-tmp": "2.0.0", + "lodash": "4.17.5", + "mkdirp": "0.5.1", + "source-map-support": "0.4.18" }, "dependencies": { "source-map-support": { @@ -1038,7 +1060,7 @@ "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.4.18.tgz", "integrity": "sha512-try0/JqxPLF9nOjvSta7tVondkP5dwgyLDjVoyMDlmjugT2lRZ1OfsrYTkCd2hkDnJTKRbO/Rl3orm8vlsUzbA==", "requires": { - "source-map": "^0.5.6" + "source-map": "0.5.7" } } } @@ -1048,8 +1070,8 @@ "resolved": "https://registry.npmjs.org/babel-runtime/-/babel-runtime-6.26.0.tgz", "integrity": "sha1-llxwWGaOgrVde/4E/yM3vItWR/4=", "requires": { - "core-js": "^2.4.0", - "regenerator-runtime": "^0.11.0" + "core-js": "2.5.3", + "regenerator-runtime": "0.11.1" } }, "babel-template": { @@ -1057,11 +1079,11 @@ "resolved": "https://registry.npmjs.org/babel-template/-/babel-template-6.26.0.tgz", "integrity": "sha1-3gPi0WOWsGn0bdn/+FIfsaDjXgI=", "requires": { - "babel-runtime": "^6.26.0", - "babel-traverse": "^6.26.0", - "babel-types": "^6.26.0", - "babylon": "^6.18.0", - "lodash": "^4.17.4" + "babel-runtime": "6.26.0", + "babel-traverse": "6.26.0", + "babel-types": "6.26.0", + "babylon": "6.18.0", + "lodash": "4.17.5" }, "dependencies": { "babylon": { @@ -1076,15 +1098,15 @@ "resolved": "https://registry.npmjs.org/babel-traverse/-/babel-traverse-6.26.0.tgz", "integrity": "sha1-RqnL1+3MYsjlwGTi0tjQ9ANXZu4=", "requires": { - "babel-code-frame": "^6.26.0", - "babel-messages": "^6.23.0", - "babel-runtime": "^6.26.0", - "babel-types": "^6.26.0", - "babylon": "^6.18.0", - "debug": "^2.6.8", - "globals": "^9.18.0", - "invariant": "^2.2.2", - "lodash": "^4.17.4" + "babel-code-frame": "6.26.0", + "babel-messages": "6.23.0", + "babel-runtime": "6.26.0", + "babel-types": "6.26.0", + "babylon": "6.18.0", + "debug": "2.6.8", + "globals": "9.18.0", + "invariant": "2.2.4", + "lodash": "4.17.5" }, "dependencies": { "babylon": { @@ -1099,10 +1121,10 @@ "resolved": "https://registry.npmjs.org/babel-types/-/babel-types-6.26.0.tgz", "integrity": "sha1-o7Bz+Uq0nrb6Vc1lInozQ4BjJJc=", "requires": { - "babel-runtime": "^6.26.0", - "esutils": "^2.0.2", - "lodash": "^4.17.4", - "to-fast-properties": "^1.0.3" + "babel-runtime": "6.26.0", + "esutils": "2.0.2", + "lodash": "4.17.5", + "to-fast-properties": "1.0.3" } }, "babylon": { @@ -1121,13 +1143,13 @@ "integrity": "sha512-5T6P4xPgpp0YDFvSWwEZ4NoE3aM4QBQXDzmVbraCkFj8zHM+mba8SyqB5DbZWyR7mYHo6Y7BdQo3MoA4m0TeQg==", "dev": true, "requires": { - "cache-base": "^1.0.1", - "class-utils": "^0.3.5", - "component-emitter": "^1.2.1", - "define-property": "^1.0.0", - "isobject": "^3.0.1", - "mixin-deep": "^1.2.0", - "pascalcase": "^0.1.1" + "cache-base": "1.0.1", + "class-utils": "0.3.6", + "component-emitter": "1.2.1", + "define-property": "1.0.0", + "isobject": "3.0.1", + "mixin-deep": "1.3.1", + "pascalcase": "0.1.1" }, "dependencies": { "define-property": { @@ -1136,7 +1158,7 @@ "integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=", "dev": true, "requires": { - "is-descriptor": "^1.0.0" + "is-descriptor": "1.0.2" } }, "is-accessor-descriptor": { @@ -1145,7 +1167,7 @@ "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", "dev": true, "requires": { - "kind-of": "^6.0.0" + "kind-of": "6.0.2" } }, "is-data-descriptor": { @@ -1154,7 +1176,7 @@ "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", "dev": true, "requires": { - "kind-of": "^6.0.0" + "kind-of": "6.0.2" } }, "is-descriptor": { @@ -1163,20 +1185,26 @@ "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", "dev": true, "requires": { - "is-accessor-descriptor": "^1.0.0", - "is-data-descriptor": "^1.0.0", - "kind-of": "^6.0.2" + "is-accessor-descriptor": "1.0.0", + "is-data-descriptor": "1.0.0", + "kind-of": "6.0.2" } } } }, + "base64-js": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-1.3.0.tgz", + "integrity": "sha512-ccav/yGvoa80BQDljCxsmmQ3Xvx60/UpBIij5QN21W3wBi/hhIC9OoO+KLpu9IJTS9j4DRVJ3aDDF9cMSoa2lw==", + "dev": true + }, "bcrypt-pbkdf": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.1.tgz", "integrity": "sha1-Y7xdy2EzG5K8Bf1SiVPDNGKgb40=", "optional": true, "requires": { - "tweetnacl": "^0.14.3" + "tweetnacl": "0.14.5" } }, "big.js": { @@ -1184,11 +1212,6 @@ "resolved": "https://registry.npmjs.org/big.js/-/big.js-3.2.0.tgz", "integrity": "sha512-+hN/Zh2D08Mx65pZ/4g5bsmNiZUuChDiQfTUQ7qJr4/kuopCr88xZsAXv6mBoZEsUI4OuGHlX59qE94K2mMW8Q==" }, - "bignumber.js": { - "version": "git+https://github.com/frozeman/bignumber.js-nolookahead.git#57692b3ecfc98bbdd6b3a516cb2353652ea49934", - "from": "bignumber.js@git+https://github.com/frozeman/bignumber.js-nolookahead.git#57692b3ecfc98bbdd6b3a516cb2353652ea49934", - "dev": true - }, "binary-extensions": { "version": "1.11.0", "resolved": "https://registry.npmjs.org/binary-extensions/-/binary-extensions-1.11.0.tgz", @@ -1200,6 +1223,31 @@ "resolved": "https://registry.npmjs.org/binaryextensions/-/binaryextensions-2.1.1.tgz", "integrity": "sha512-XBaoWE9RW8pPdPQNibZsW2zh8TW6gcarXp1FZPwT8Uop8ScSNldJEWf2k9l3HeTqdrEwsOsFcq74RiJECW34yA==" }, + "bl": { + "version": "1.2.2", + "resolved": "http://registry.npmjs.org/bl/-/bl-1.2.2.tgz", + "integrity": "sha512-e8tQYnZodmebYDWGH7KMRvtzKXaJHx3BbilrgZCfvyLUYdKpK1t5PSPmpkny/SgiTSCnjfLW7v5rlONXVFkQEA==", + "dev": true, + "requires": { + "readable-stream": "2.3.5", + "safe-buffer": "5.1.1" + } + }, + "block-stream": { + "version": "0.0.9", + "resolved": "https://registry.npmjs.org/block-stream/-/block-stream-0.0.9.tgz", + "integrity": "sha1-E+v+d4oDIFz+A3UUgeu0szAMEmo=", + "dev": true, + "requires": { + "inherits": "2.0.3" + } + }, + "bluebird": { + "version": "3.5.3", + "resolved": "https://registry.npmjs.org/bluebird/-/bluebird-3.5.3.tgz", + "integrity": "sha512-/qKPUQlaW1OyR51WeCPBvRnAlnZFUJkCSG5HzGnuIqhgyJtF+T94lFnn33eiazjRm2LAHVy2guNnaq48X9SJuw==", + "dev": true + }, "bn.js": { "version": "4.11.6", "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.11.6.tgz", @@ -1211,15 +1259,15 @@ "integrity": "sha1-h2eKGdhLR9hZuDGZvVm84iKxBFQ=", "requires": { "bytes": "3.0.0", - "content-type": "~1.0.4", + "content-type": "1.0.4", "debug": "2.6.9", - "depd": "~1.1.1", - "http-errors": "~1.6.2", + "depd": "1.1.2", + "http-errors": "1.6.3", "iconv-lite": "0.4.19", - "on-finished": "~2.3.0", + "on-finished": "2.3.0", "qs": "6.5.1", "raw-body": "2.3.2", - "type-is": "~1.6.15" + "type-is": "1.6.16" }, "dependencies": { "debug": { @@ -1237,7 +1285,7 @@ "resolved": "https://registry.npmjs.org/boom/-/boom-4.3.1.tgz", "integrity": "sha1-T4owBctKfjiJ90kDD9JbluAdLjE=", "requires": { - "hoek": "4.x.x" + "hoek": "4.2.1" } }, "boxen": { @@ -1246,13 +1294,13 @@ "integrity": "sha512-TNPjfTr432qx7yOjQyaXm3dSR0MH9vXp7eT1BFSl/C51g+EFnOR9hTg1IreahGBmDNCehscshe45f+C1TBZbLw==", "dev": true, "requires": { - "ansi-align": "^2.0.0", - "camelcase": "^4.0.0", - "chalk": "^2.0.1", - "cli-boxes": "^1.0.0", - "string-width": "^2.0.0", - "term-size": "^1.2.0", - "widest-line": "^2.0.0" + "ansi-align": "2.0.0", + "camelcase": "4.1.0", + "chalk": "2.3.2", + "cli-boxes": "1.0.0", + "string-width": "2.1.1", + "term-size": "1.2.0", + "widest-line": "2.0.0" }, "dependencies": { "ansi-regex": { @@ -1279,8 +1327,8 @@ "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", "dev": true, "requires": { - "is-fullwidth-code-point": "^2.0.0", - "strip-ansi": "^4.0.0" + "is-fullwidth-code-point": "2.0.0", + "strip-ansi": "4.0.0" } }, "strip-ansi": { @@ -1289,7 +1337,7 @@ "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", "dev": true, "requires": { - "ansi-regex": "^3.0.0" + "ansi-regex": "3.0.0" } } } @@ -1299,7 +1347,7 @@ "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", "requires": { - "balanced-match": "^1.0.0", + "balanced-match": "1.0.0", "concat-map": "0.0.1" } }, @@ -1309,16 +1357,16 @@ "integrity": "sha512-aNdbnj9P8PjdXU4ybaWLK2IF3jc/EoDYbC7AazW6to3TRsfXxscC9UXOB5iDiEQrkyIbWp2SLQda4+QAa7nc3w==", "dev": true, "requires": { - "arr-flatten": "^1.1.0", - "array-unique": "^0.3.2", - "extend-shallow": "^2.0.1", - "fill-range": "^4.0.0", - "isobject": "^3.0.1", - "repeat-element": "^1.1.2", - "snapdragon": "^0.8.1", - "snapdragon-node": "^2.0.1", - "split-string": "^3.0.2", - "to-regex": "^3.0.1" + "arr-flatten": "1.1.0", + "array-unique": "0.3.2", + "extend-shallow": "2.0.1", + "fill-range": "4.0.0", + "isobject": "3.0.1", + "repeat-element": "1.1.2", + "snapdragon": "0.8.2", + "snapdragon-node": "2.1.1", + "split-string": "3.1.0", + "to-regex": "3.0.2" }, "dependencies": { "extend-shallow": { @@ -1327,7 +1375,7 @@ "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", "dev": true, "requires": { - "is-extendable": "^0.1.0" + "is-extendable": "0.1.1" } } } @@ -1342,12 +1390,67 @@ "resolved": "https://registry.npmjs.org/browser-stdout/-/browser-stdout-1.3.0.tgz", "integrity": "sha1-81HTKWnTL6XXpVZxVCY9korjvR8=" }, + "browserify-aes": { + "version": "1.2.0", + "resolved": "http://registry.npmjs.org/browserify-aes/-/browserify-aes-1.2.0.tgz", + "integrity": "sha512-+7CHXqGuspUn/Sl5aO7Ea0xWGAtETPXNSAjHo48JfLdPWcMng33Xe4znFvQweqc/uzk5zSOI3H52CYnjCfb5hA==", + "dev": true, + "requires": { + "buffer-xor": "1.0.3", + "cipher-base": "1.0.4", + "create-hash": "1.2.0", + "evp_bytestokey": "1.0.3", + "inherits": "2.0.3", + "safe-buffer": "5.1.1" + } + }, + "browserify-cipher": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/browserify-cipher/-/browserify-cipher-1.0.1.tgz", + "integrity": "sha512-sPhkz0ARKbf4rRQt2hTpAHqn47X3llLkUGn+xEJzLjwY8LRs2p0v7ljvI5EyoRO/mexrNunNECisZs+gw2zz1w==", + "dev": true, + "requires": { + "browserify-aes": "1.2.0", + "browserify-des": "1.0.2", + "evp_bytestokey": "1.0.3" + } + }, + "browserify-des": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/browserify-des/-/browserify-des-1.0.2.tgz", + "integrity": "sha512-BioO1xf3hFwz4kc6iBhI3ieDFompMhrMlnDFC4/0/vd5MokpuAc3R+LYbwTA9A5Yc9pq9UYPqffKpW2ObuwX5A==", + "dev": true, + "requires": { + "cipher-base": "1.0.4", + "des.js": "1.0.0", + "inherits": "2.0.3", + "safe-buffer": "5.1.2" + }, + "dependencies": { + "safe-buffer": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", + "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", + "dev": true + } + } + }, + "browserify-rsa": { + "version": "4.0.1", + "resolved": "http://registry.npmjs.org/browserify-rsa/-/browserify-rsa-4.0.1.tgz", + "integrity": "sha1-IeCr+vbyApzy+vsTNWenAdQTVSQ=", + "dev": true, + "requires": { + "bn.js": "4.11.6", + "randombytes": "2.0.6" + } + }, "browserify-sha3": { "version": "0.0.1", "resolved": "https://registry.npmjs.org/browserify-sha3/-/browserify-sha3-0.0.1.tgz", "integrity": "sha1-P/NKMAbvFcD7NWflQbkaI0ASPRE=", "requires": { - "js-sha3": "^0.3.1" + "js-sha3": "0.3.1" }, "dependencies": { "js-sha3": { @@ -1357,6 +1460,59 @@ } } }, + "browserify-sign": { + "version": "4.0.4", + "resolved": "https://registry.npmjs.org/browserify-sign/-/browserify-sign-4.0.4.tgz", + "integrity": "sha1-qk62jl17ZYuqa/alfmMMvXqT0pg=", + "dev": true, + "requires": { + "bn.js": "4.11.6", + "browserify-rsa": "4.0.1", + "create-hash": "1.2.0", + "create-hmac": "1.1.7", + "elliptic": "6.4.0", + "inherits": "2.0.3", + "parse-asn1": "5.1.1" + } + }, + "buffer": { + "version": "5.2.1", + "resolved": "https://registry.npmjs.org/buffer/-/buffer-5.2.1.tgz", + "integrity": "sha512-c+Ko0loDaFfuPWiL02ls9Xd3GO3cPVmUobQ6t3rXNUk304u6hGq+8N/kFi+QEIKhzK3uwolVhLzszmfLmMLnqg==", + "dev": true, + "requires": { + "base64-js": "1.3.0", + "ieee754": "1.1.12" + } + }, + "buffer-alloc": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/buffer-alloc/-/buffer-alloc-1.2.0.tgz", + "integrity": "sha512-CFsHQgjtW1UChdXgbyJGtnm+O/uLQeZdtbDo8mfUgYXCHSM1wgrVxXm6bSyrUuErEb+4sYVGCzASBRot7zyrow==", + "dev": true, + "requires": { + "buffer-alloc-unsafe": "1.1.0", + "buffer-fill": "1.0.0" + } + }, + "buffer-alloc-unsafe": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/buffer-alloc-unsafe/-/buffer-alloc-unsafe-1.1.0.tgz", + "integrity": "sha512-TEM2iMIEQdJ2yjPJoSIsldnleVaAk1oW3DBVUykyOLsEsFmEc9kn+SFFPz+gl54KQNxlDnAwCXosOS9Okx2xAg==", + "dev": true + }, + "buffer-crc32": { + "version": "0.2.13", + "resolved": "https://registry.npmjs.org/buffer-crc32/-/buffer-crc32-0.2.13.tgz", + "integrity": "sha1-DTM+PwDqxQqhRUq9MO+MKl2ackI=", + "dev": true + }, + "buffer-fill": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/buffer-fill/-/buffer-fill-1.0.0.tgz", + "integrity": "sha1-+PeLdniYiO858gXNY39o5wISKyw=", + "dev": true + }, "buffer-from": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.1.tgz", @@ -1368,6 +1524,12 @@ "resolved": "https://registry.npmjs.org/buffer-to-arraybuffer/-/buffer-to-arraybuffer-0.0.5.tgz", "integrity": "sha1-YGSkD6dutDxyOrqe+PbhIW0QURo=" }, + "buffer-xor": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/buffer-xor/-/buffer-xor-1.0.3.tgz", + "integrity": "sha1-JuYe0UIvtw3ULm42cp7VHYVf6Nk=", + "dev": true + }, "builtin-modules": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/builtin-modules/-/builtin-modules-1.1.1.tgz", @@ -1384,15 +1546,15 @@ "integrity": "sha512-AKcdTnFSWATd5/GCPRxr2ChwIJ85CeyrEyjRHlKxQ56d4XJMGym0uAiKn0xbLOGOl3+yRpOTi484dVCEc5AUzQ==", "dev": true, "requires": { - "collection-visit": "^1.0.0", - "component-emitter": "^1.2.1", - "get-value": "^2.0.6", - "has-value": "^1.0.0", - "isobject": "^3.0.1", - "set-value": "^2.0.0", - "to-object-path": "^0.3.0", - "union-value": "^1.0.0", - "unset-value": "^1.0.0" + "collection-visit": "1.0.0", + "component-emitter": "1.2.1", + "get-value": "2.0.6", + "has-value": "1.0.0", + "isobject": "3.0.1", + "set-value": "2.0.0", + "to-object-path": "0.3.0", + "union-value": "1.0.0", + "unset-value": "1.0.0" } }, "cacheable-request": { @@ -1432,8 +1594,8 @@ "dev": true, "optional": true, "requires": { - "align-text": "^0.1.3", - "lazy-cache": "^1.0.3" + "align-text": "0.1.4", + "lazy-cache": "1.0.4" } }, "chai": { @@ -1442,12 +1604,12 @@ "integrity": "sha1-D2RYS6ZC8PKs4oBiefTwbKI61zw=", "dev": true, "requires": { - "assertion-error": "^1.0.1", - "check-error": "^1.0.1", - "deep-eql": "^3.0.0", - "get-func-name": "^2.0.0", - "pathval": "^1.0.0", - "type-detect": "^4.0.0" + "assertion-error": "1.1.0", + "check-error": "1.0.2", + "deep-eql": "3.0.1", + "get-func-name": "2.0.0", + "pathval": "1.1.0", + "type-detect": "4.0.8" } }, "chai-as-promised": { @@ -1456,7 +1618,7 @@ "integrity": "sha512-azL6xMoi+uxu6z4rhWQ1jbdUhOMhis2PvscD/xjLqNMkv3BPPp2JyyuTHOrf9BOosGpNQ11v6BKv/g57RXbiaA==", "dev": true, "requires": { - "check-error": "^1.0.2" + "check-error": "1.0.2" } }, "chai-bignumber": { @@ -1470,9 +1632,9 @@ "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.3.2.tgz", "integrity": "sha512-ZM4j2/ld/YZDc3Ma8PgN7gyAk+kHMMMyzLNryCPGhWrsfAuDVeuid5bpRFTDgMH9JBK2lA4dyyAkkZYF/WcqDQ==", "requires": { - "ansi-styles": "^3.2.1", - "escape-string-regexp": "^1.0.5", - "supports-color": "^5.3.0" + "ansi-styles": "3.2.1", + "escape-string-regexp": "1.0.5", + "supports-color": "5.3.0" }, "dependencies": { "has-flag": { @@ -1485,7 +1647,7 @@ "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.3.0.tgz", "integrity": "sha512-0aP01LLIskjKs3lq52EC0aGBAJhLq7B2Rd8HC/DR/PtNNpcLilNmHC12O+hu0usQpo7wtHNRqtrhBwtDb0+dNg==", "requires": { - "has-flag": "^3.0.0" + "has-flag": "3.0.0" } } } @@ -1513,18 +1675,18 @@ "integrity": "sha512-zW8iXYZtXMx4kux/nuZVXjkLP+CyIK5Al5FHnj1OgTKGZfp4Oy6/ymtMSKFv3GD8DviEmUPmJg9eFdJ/JzudMg==", "dev": true, "requires": { - "anymatch": "^2.0.0", - "async-each": "^1.0.0", - "braces": "^2.3.0", - "fsevents": "^1.1.2", - "glob-parent": "^3.1.0", - "inherits": "^2.0.1", - "is-binary-path": "^1.0.0", - "is-glob": "^4.0.0", - "normalize-path": "^2.1.1", - "path-is-absolute": "^1.0.0", - "readdirp": "^2.0.0", - "upath": "^1.0.0" + "anymatch": "2.0.0", + "async-each": "1.0.1", + "braces": "2.3.2", + "fsevents": "1.2.3", + "glob-parent": "3.1.0", + "inherits": "2.0.3", + "is-binary-path": "1.0.1", + "is-glob": "4.0.0", + "normalize-path": "2.1.1", + "path-is-absolute": "1.0.1", + "readdirp": "2.1.0", + "upath": "1.0.5" } }, "ci-info": { @@ -1533,16 +1695,26 @@ "integrity": "sha512-SK/846h/Rcy8q9Z9CAwGBLfCJ6EkjJWdpelWDufQpqVDYq2Wnnv8zlSO6AMQap02jvhVruKKpEtQOufo3pFhLg==", "dev": true }, + "cipher-base": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/cipher-base/-/cipher-base-1.0.4.tgz", + "integrity": "sha512-Kkht5ye6ZGmwv40uUDZztayT2ThLQGfnj/T71N/XzeZeo3nf8foyW7zGTsPYkEya3m5f3cAypH+qe7YOrM1U2Q==", + "dev": true, + "requires": { + "inherits": "2.0.3", + "safe-buffer": "5.1.1" + } + }, "class-utils": { "version": "0.3.6", "resolved": "https://registry.npmjs.org/class-utils/-/class-utils-0.3.6.tgz", "integrity": "sha512-qOhPa/Fj7s6TY8H8esGu5QNpMMQxz79h+urzrNYN6mn+9BnxlDGf5QZ+XeCDsxSjPqsSR56XOZOJmpeurnLMeg==", "dev": true, "requires": { - "arr-union": "^3.1.0", - "define-property": "^0.2.5", - "isobject": "^3.0.0", - "static-extend": "^0.1.1" + "arr-union": "3.1.0", + "define-property": "0.2.5", + "isobject": "3.0.1", + "static-extend": "0.1.2" }, "dependencies": { "define-property": { @@ -1551,7 +1723,7 @@ "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", "dev": true, "requires": { - "is-descriptor": "^0.1.0" + "is-descriptor": "0.1.6" } } } @@ -1567,7 +1739,7 @@ "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-2.1.0.tgz", "integrity": "sha1-s12sN2R5+sw+lHR9QdDQ9SOP/LU=", "requires": { - "restore-cursor": "^2.0.0" + "restore-cursor": "2.0.0" } }, "cli-spinners": { @@ -1596,9 +1768,9 @@ "integrity": "sha512-7Qg2Jrep1S/+Q3EceiZtQcDPWxhAvBw+ERf1162v4sikJrvojMHFqXt8QIVha8UlH9rgU0BeWPytZ9/TzYqlUw==", "dev": true, "requires": { - "colors": "^1.1.2", - "object-assign": "^4.1.0", - "string-width": "^2.1.1" + "colors": "1.2.1", + "object-assign": "4.1.1", + "string-width": "2.1.1" }, "dependencies": { "ansi-regex": { @@ -1619,8 +1791,8 @@ "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", "dev": true, "requires": { - "is-fullwidth-code-point": "^2.0.0", - "strip-ansi": "^4.0.0" + "is-fullwidth-code-point": "2.0.0", + "strip-ansi": "4.0.0" } }, "strip-ansi": { @@ -1629,7 +1801,7 @@ "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", "dev": true, "requires": { - "ansi-regex": "^3.0.0" + "ansi-regex": "3.0.0" } } } @@ -1640,7 +1812,7 @@ "integrity": "sha1-nxXPuwcFAFNpIWxiasfQWrkN1XQ=", "requires": { "slice-ansi": "0.0.4", - "string-width": "^1.0.1" + "string-width": "1.0.2" } }, "cli-width": { @@ -1653,9 +1825,9 @@ "resolved": "https://registry.npmjs.org/cliui/-/cliui-3.2.0.tgz", "integrity": "sha1-EgYBU3qRbSmUD5NNo7SNWFo5IT0=", "requires": { - "string-width": "^1.0.1", - "strip-ansi": "^3.0.1", - "wrap-ansi": "^2.0.0" + "string-width": "1.0.2", + "strip-ansi": "3.0.1", + "wrap-ansi": "2.1.0" } }, "clone": { @@ -1673,7 +1845,7 @@ "resolved": "https://registry.npmjs.org/clone-response/-/clone-response-1.0.2.tgz", "integrity": "sha1-0dyXOSAxTfZ/vrlCI7TuNQI56Ws=", "requires": { - "mimic-response": "^1.0.0" + "mimic-response": "1.0.0" } }, "clone-stats": { @@ -1686,9 +1858,9 @@ "resolved": "https://registry.npmjs.org/cloneable-readable/-/cloneable-readable-1.1.2.tgz", "integrity": "sha512-Bq6+4t+lbM8vhTs/Bef5c5AdEMtapp/iFb6+s4/Hh9MVTt8OLKH7ZOOZSCT+Ys7hsHvqv0GuMPJ1lnQJVHvxpg==", "requires": { - "inherits": "^2.0.1", - "process-nextick-args": "^2.0.0", - "readable-stream": "^2.3.5" + "inherits": "2.0.3", + "process-nextick-args": "2.0.0", + "readable-stream": "2.3.5" } }, "co": { @@ -1707,8 +1879,8 @@ "integrity": "sha1-S8A3PBZLwykbTTaMgpzxqApZ3KA=", "dev": true, "requires": { - "map-visit": "^1.0.0", - "object-visit": "^1.0.0" + "map-visit": "1.0.0", + "object-visit": "1.0.1" } }, "color-convert": { @@ -1716,7 +1888,7 @@ "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.1.tgz", "integrity": "sha512-mjGanIiwQJskCC18rPR6OmrZ6fm2Lc7PeGFYwCmy5J34wC6F1PzdGL6xeMfmgicfYcNLGuVFA3WzXtIDCQSZxQ==", "requires": { - "color-name": "^1.1.1" + "color-name": "1.1.3" } }, "color-name": { @@ -1734,7 +1906,7 @@ "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.6.tgz", "integrity": "sha1-cj599ugBrFYTETp+RFqbactjKBg=", "requires": { - "delayed-stream": "~1.0.0" + "delayed-stream": "1.0.0" } }, "commander": { @@ -1764,10 +1936,10 @@ "integrity": "sha512-27HBghJxjiZtIk3Ycvn/4kbJk/1uZuJFfuPEns6LaEvpvG1f0hTea8lilrouyo9mVc2GWdcEZ8OLoGmSADlrCw==", "dev": true, "requires": { - "buffer-from": "^1.0.0", - "inherits": "^2.0.3", - "readable-stream": "^2.2.2", - "typedarray": "^0.0.6" + "buffer-from": "1.1.1", + "inherits": "2.0.3", + "readable-stream": "2.3.5", + "typedarray": "0.0.6" } }, "configstore": { @@ -1776,12 +1948,12 @@ "integrity": "sha512-vtv5HtGjcYUgFrXc6Kx747B83MRRVS5R1VTEQoXvuP+kMI+if6uywV0nDGoiydJRy4yk7h9od5Og0kxx4zUXmw==", "dev": true, "requires": { - "dot-prop": "^4.1.0", - "graceful-fs": "^4.1.2", - "make-dir": "^1.0.0", - "unique-string": "^1.0.0", - "write-file-atomic": "^2.0.0", - "xdg-basedir": "^3.0.0" + "dot-prop": "4.2.0", + "graceful-fs": "4.1.11", + "make-dir": "1.2.0", + "unique-string": "1.0.0", + "write-file-atomic": "2.3.0", + "xdg-basedir": "3.0.0" } }, "content-disposition": { @@ -1809,6 +1981,12 @@ "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz", "integrity": "sha1-4wOogrNCzD7oylE6eZmXNNqzriw=" }, + "cookiejar": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/cookiejar/-/cookiejar-2.1.2.tgz", + "integrity": "sha512-Mw+adcfzPxcPeI+0WlvRrr/3lGVO0bD75SxX6811cxSh1Wbxx7xZBGK1eVtDf6si8rg2lhnUjsVLMFMfbRIuwA==", + "dev": true + }, "copy-descriptor": { "version": "0.1.1", "resolved": "https://registry.npmjs.org/copy-descriptor/-/copy-descriptor-0.1.1.tgz", @@ -1830,8 +2008,18 @@ "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.4.tgz", "integrity": "sha1-K9OB8usgECAQXNUOpZ2mMJBpRoY=", "requires": { - "object-assign": "^4", - "vary": "^1" + "object-assign": "4.1.1", + "vary": "1.1.2" + } + }, + "create-ecdh": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/create-ecdh/-/create-ecdh-4.0.3.tgz", + "integrity": "sha512-GbEHQPMOswGpKXM9kCWVrremUcBmjteUaQ01T9rkKCPDXfUHX0IoP9LpHYo2NPFampa4e+/pFDc3jQdxrxQLaw==", + "dev": true, + "requires": { + "bn.js": "4.11.6", + "elliptic": "6.4.0" } }, "create-error-class": { @@ -1840,7 +2028,34 @@ "integrity": "sha1-Br56vvlHo/FKMP1hBnHUAbyot7Y=", "dev": true, "requires": { - "capture-stack-trace": "^1.0.0" + "capture-stack-trace": "1.0.0" + } + }, + "create-hash": { + "version": "1.2.0", + "resolved": "http://registry.npmjs.org/create-hash/-/create-hash-1.2.0.tgz", + "integrity": "sha512-z00bCGNHDG8mHAkP7CtT1qVu+bFQUPjYq/4Iv3C3kWjTFV10zIjfSoeqXo9Asws8gwSHDGj/hl2u4OGIjapeCg==", + "dev": true, + "requires": { + "cipher-base": "1.0.4", + "inherits": "2.0.3", + "md5.js": "1.3.5", + "ripemd160": "2.0.2", + "sha.js": "2.4.11" + } + }, + "create-hmac": { + "version": "1.1.7", + "resolved": "http://registry.npmjs.org/create-hmac/-/create-hmac-1.1.7.tgz", + "integrity": "sha512-MJG9liiZ+ogc4TzUwuvbER1JRdgvUFSB5+VR/g5h82fGaIRWMWddtKBHi7/sVhfjQZ6SehlyhvQYrcYkaUIpLg==", + "dev": true, + "requires": { + "cipher-base": "1.0.4", + "create-hash": "1.2.0", + "inherits": "2.0.3", + "ripemd160": "2.0.2", + "safe-buffer": "5.1.1", + "sha.js": "2.4.11" } }, "cross-spawn": { @@ -1848,9 +2063,9 @@ "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-5.1.0.tgz", "integrity": "sha1-6L0O/uWPz/b4+UUQoKVUu/ojVEk=", "requires": { - "lru-cache": "^4.0.1", - "shebang-command": "^1.2.0", - "which": "^1.2.9" + "lru-cache": "4.1.2", + "shebang-command": "1.2.0", + "which": "1.3.0" }, "dependencies": { "lru-cache": { @@ -1858,8 +2073,8 @@ "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-4.1.2.tgz", "integrity": "sha512-wgeVXhrDwAWnIF/yZARsFnMBtdFXOg1b8RIrhilp+0iDYN4mdQcNZElDZ0e4B64BhaxeQ5zN7PMyvu7we1kPeQ==", "requires": { - "pseudomap": "^1.0.2", - "yallist": "^2.1.2" + "pseudomap": "1.0.2", + "yallist": "2.1.2" } } } @@ -1875,7 +2090,7 @@ "resolved": "https://registry.npmjs.org/cryptiles/-/cryptiles-3.1.2.tgz", "integrity": "sha1-qJ+7Ig9c4l7FboxKqKT9e1sNKf4=", "requires": { - "boom": "5.x.x" + "boom": "5.2.0" }, "dependencies": { "boom": { @@ -1883,11 +2098,30 @@ "resolved": "https://registry.npmjs.org/boom/-/boom-5.2.0.tgz", "integrity": "sha512-Z5BTk6ZRe4tXXQlkqftmsAUANpXmuwlsF5Oov8ThoMbQRzdGTA1ngYRW160GexgOgjsFOKJz0LYhoNi+2AMBUw==", "requires": { - "hoek": "4.x.x" + "hoek": "4.2.1" } } } }, + "crypto-browserify": { + "version": "3.12.0", + "resolved": "https://registry.npmjs.org/crypto-browserify/-/crypto-browserify-3.12.0.tgz", + "integrity": "sha512-fz4spIh+znjO2VjL+IdhEpRJ3YN6sMzITSBijk6FK2UvTqruSQW+/cCZTSNsMiZNvUeq0CqurF+dAbyiGOY6Wg==", + "dev": true, + "requires": { + "browserify-cipher": "1.0.1", + "browserify-sign": "4.0.4", + "create-ecdh": "4.0.3", + "create-hash": "1.2.0", + "create-hmac": "1.1.7", + "diffie-hellman": "5.0.3", + "inherits": "2.0.3", + "pbkdf2": "3.0.17", + "public-encrypt": "4.0.3", + "randombytes": "2.0.6", + "randomfill": "1.0.4" + } + }, "crypto-js": { "version": "3.1.8", "resolved": "https://registry.npmjs.org/crypto-js/-/crypto-js-3.1.8.tgz", @@ -1910,7 +2144,7 @@ "resolved": "https://registry.npmjs.org/dashdash/-/dashdash-1.14.1.tgz", "integrity": "sha1-hTz6D3y+L+1d4gMmuN1YEDX24vA=", "requires": { - "assert-plus": "^1.0.0" + "assert-plus": "1.0.0" } }, "date-fns": { @@ -1947,12 +2181,101 @@ "resolved": "https://registry.npmjs.org/decode-uri-component/-/decode-uri-component-0.2.0.tgz", "integrity": "sha1-6zkTMzRYd1y4TNGh+uBiEGu4dUU=" }, + "decompress": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/decompress/-/decompress-4.2.0.tgz", + "integrity": "sha1-eu3YVCflqS2s/lVnSnxQXpbQH50=", + "dev": true, + "requires": { + "decompress-tar": "4.1.1", + "decompress-tarbz2": "4.1.1", + "decompress-targz": "4.1.1", + "decompress-unzip": "4.0.1", + "graceful-fs": "4.1.11", + "make-dir": "1.2.0", + "pify": "2.3.0", + "strip-dirs": "2.1.0" + } + }, "decompress-response": { "version": "3.3.0", "resolved": "https://registry.npmjs.org/decompress-response/-/decompress-response-3.3.0.tgz", "integrity": "sha1-gKTdMjdIOEv6JICDYirt7Jgq3/M=", "requires": { - "mimic-response": "^1.0.0" + "mimic-response": "1.0.0" + } + }, + "decompress-tar": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/decompress-tar/-/decompress-tar-4.1.1.tgz", + "integrity": "sha512-JdJMaCrGpB5fESVyxwpCx4Jdj2AagLmv3y58Qy4GE6HMVjWz1FeVQk1Ct4Kye7PftcdOo/7U7UKzYBJgqnGeUQ==", + "dev": true, + "requires": { + "file-type": "5.2.0", + "is-stream": "1.1.0", + "tar-stream": "1.6.2" + } + }, + "decompress-tarbz2": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/decompress-tarbz2/-/decompress-tarbz2-4.1.1.tgz", + "integrity": "sha512-s88xLzf1r81ICXLAVQVzaN6ZmX4A6U4z2nMbOwobxkLoIIfjVMBg7TeguTUXkKeXni795B6y5rnvDw7rxhAq9A==", + "dev": true, + "requires": { + "decompress-tar": "4.1.1", + "file-type": "6.2.0", + "is-stream": "1.1.0", + "seek-bzip": "1.0.5", + "unbzip2-stream": "1.3.1" + }, + "dependencies": { + "file-type": { + "version": "6.2.0", + "resolved": "https://registry.npmjs.org/file-type/-/file-type-6.2.0.tgz", + "integrity": "sha512-YPcTBDV+2Tm0VqjybVd32MHdlEGAtuxS3VAYsumFokDSMG+ROT5wawGlnHDoz7bfMcMDt9hxuXvXwoKUx2fkOg==", + "dev": true + } + } + }, + "decompress-targz": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/decompress-targz/-/decompress-targz-4.1.1.tgz", + "integrity": "sha512-4z81Znfr6chWnRDNfFNqLwPvm4db3WuZkqV+UgXQzSngG3CEKdBkw5jrv3axjjL96glyiiKjsxJG3X6WBZwX3w==", + "dev": true, + "requires": { + "decompress-tar": "4.1.1", + "file-type": "5.2.0", + "is-stream": "1.1.0" + } + }, + "decompress-unzip": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/decompress-unzip/-/decompress-unzip-4.0.1.tgz", + "integrity": "sha1-3qrM39FK6vhVePczroIQ+bSEj2k=", + "dev": true, + "requires": { + "file-type": "3.9.0", + "get-stream": "2.3.1", + "pify": "2.3.0", + "yauzl": "2.10.0" + }, + "dependencies": { + "file-type": { + "version": "3.9.0", + "resolved": "http://registry.npmjs.org/file-type/-/file-type-3.9.0.tgz", + "integrity": "sha1-JXoHg4TR24CHvESdEH1SpSZyuek=", + "dev": true + }, + "get-stream": { + "version": "2.3.1", + "resolved": "http://registry.npmjs.org/get-stream/-/get-stream-2.3.1.tgz", + "integrity": "sha1-Xzj5PzRgCWZu4BUKBUFn+Rvdld4=", + "dev": true, + "requires": { + "object-assign": "4.1.1", + "pinkie-promise": "2.0.1" + } + } } }, "deep-eql": { @@ -1961,7 +2284,7 @@ "integrity": "sha512-+QeIQyN5ZuO+3Uk5DYh6/1eKO0m0YmJFGNmFHGACpf1ClL1nmlV/p4gNgbl2pJGxgXb4faqo6UE+M5ACEMyVcw==", "dev": true, "requires": { - "type-detect": "^4.0.0" + "type-detect": "4.0.8" } }, "deep-extend": { @@ -1981,8 +2304,8 @@ "integrity": "sha512-jwK2UV4cnPpbcG7+VRARKTZPUWowwXA8bzH5NP6ud0oeAxyYPuGZUAC7hMugpCdz4BeSZl2Dl9k66CHJ/46ZYQ==", "dev": true, "requires": { - "is-descriptor": "^1.0.2", - "isobject": "^3.0.1" + "is-descriptor": "1.0.2", + "isobject": "3.0.1" }, "dependencies": { "is-accessor-descriptor": { @@ -1991,7 +2314,7 @@ "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", "dev": true, "requires": { - "kind-of": "^6.0.0" + "kind-of": "6.0.2" } }, "is-data-descriptor": { @@ -2000,7 +2323,7 @@ "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", "dev": true, "requires": { - "kind-of": "^6.0.0" + "kind-of": "6.0.2" } }, "is-descriptor": { @@ -2009,9 +2332,9 @@ "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", "dev": true, "requires": { - "is-accessor-descriptor": "^1.0.0", - "is-data-descriptor": "^1.0.0", - "kind-of": "^6.0.2" + "is-accessor-descriptor": "1.0.0", + "is-data-descriptor": "1.0.0", + "kind-of": "6.0.2" } } } @@ -2026,6 +2349,16 @@ "resolved": "https://registry.npmjs.org/depd/-/depd-1.1.2.tgz", "integrity": "sha1-m81S4UwJd2PnSbJ0xDRu0uVgtak=" }, + "des.js": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/des.js/-/des.js-1.0.0.tgz", + "integrity": "sha1-wHTS4qpqipoH29YfmhXCzYPsjsw=", + "dev": true, + "requires": { + "inherits": "2.0.3", + "minimalistic-assert": "1.0.1" + } + }, "destroy": { "version": "1.0.4", "resolved": "https://registry.npmjs.org/destroy/-/destroy-1.0.4.tgz", @@ -2041,7 +2374,7 @@ "resolved": "https://registry.npmjs.org/detect-indent/-/detect-indent-4.0.0.tgz", "integrity": "sha1-920GQ1LN9Docts5hnE7jqUdd4gg=", "requires": { - "repeating": "^2.0.0" + "repeating": "2.0.1" } }, "diff": { @@ -2049,6 +2382,17 @@ "resolved": "https://registry.npmjs.org/diff/-/diff-3.3.1.tgz", "integrity": "sha512-MKPHZDMB0o6yHyDryUOScqZibp914ksXwAMYMTHj6KO8UeKsRYNJD3oNCKjTqZon+V488P7N/HzXF8t7ZR95ww==" }, + "diffie-hellman": { + "version": "5.0.3", + "resolved": "http://registry.npmjs.org/diffie-hellman/-/diffie-hellman-5.0.3.tgz", + "integrity": "sha512-kqag/Nl+f3GwyK25fhUMYj81BUOrZ9IuJsjIcDE5icNM9FJHAVm3VcUDxdLPoQtTuUylWm6ZIknYJwwaPxsUzg==", + "dev": true, + "requires": { + "bn.js": "4.11.6", + "miller-rabin": "4.0.1", + "randombytes": "2.0.6" + } + }, "dom-walk": { "version": "0.1.1", "resolved": "https://registry.npmjs.org/dom-walk/-/dom-walk-0.1.1.tgz", @@ -2060,7 +2404,7 @@ "integrity": "sha512-tUMXrxlExSW6U2EXiiKGSBVdYgtV8qlHL+C10TsW4PURY/ic+eaysnSkwB4kA/mBlCyy/IKDJ+Lc3wbWeaXtuQ==", "dev": true, "requires": { - "is-obj": "^1.0.0" + "is-obj": "1.0.1" } }, "duplexer": { @@ -2080,7 +2424,7 @@ "integrity": "sha1-D8c6ntXw1Tw4GTOYUj735UN3dQU=", "optional": true, "requires": { - "jsbn": "~0.1.0" + "jsbn": "0.1.1" } }, "editions": { @@ -2108,13 +2452,13 @@ "resolved": "https://registry.npmjs.org/elliptic/-/elliptic-6.4.0.tgz", "integrity": "sha1-ysmvh2LIWDYYcAPI3+GT5eLq5d8=", "requires": { - "bn.js": "^4.4.0", - "brorand": "^1.0.1", - "hash.js": "^1.0.0", - "hmac-drbg": "^1.0.0", - "inherits": "^2.0.1", - "minimalistic-assert": "^1.0.0", - "minimalistic-crypto-utils": "^1.0.0" + "bn.js": "4.11.6", + "brorand": "1.1.0", + "hash.js": "1.1.3", + "hmac-drbg": "1.0.1", + "inherits": "2.0.3", + "minimalistic-assert": "1.0.1", + "minimalistic-crypto-utils": "1.0.1" } }, "emojis-list": { @@ -2127,14 +2471,23 @@ "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-1.0.2.tgz", "integrity": "sha1-rT/0yG7C0CkyL1oCw6mmBslbP1k=" }, + "end-of-stream": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.1.tgz", + "integrity": "sha512-1MkrZNvWTKCaigbn+W15elq2BB/L22nqrSY5DKlo3X6+vclJm8Bb5djXJBmEX6fS3+zCh/F4VBK5Z2KxJt4s2Q==", + "dev": true, + "requires": { + "once": "1.4.0" + } + }, "enhanced-resolve": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/enhanced-resolve/-/enhanced-resolve-4.0.0.tgz", "integrity": "sha512-jox/62b2GofV1qTUQTMPEJSDIGycS43evqYzD/KVtEb9OCoki9cnacUPxCrZa7JfPzZSYOCZhu9O9luaMxAX8g==", "requires": { - "graceful-fs": "^4.1.2", - "memory-fs": "^0.4.0", - "tapable": "^1.0.0" + "graceful-fs": "4.1.11", + "memory-fs": "0.4.1", + "tapable": "1.0.0" } }, "errno": { @@ -2142,7 +2495,7 @@ "resolved": "https://registry.npmjs.org/errno/-/errno-0.1.7.tgz", "integrity": "sha512-MfrRBDWzIWifgq6tJj60gkAwtLNb6sQPlcFrSOflcP1aFmmruKQ2wRnze/8V6kgyz7H3FF8Npzv78mZ7XLLflg==", "requires": { - "prr": "~1.0.1" + "prr": "1.0.1" } }, "error": { @@ -2150,8 +2503,8 @@ "resolved": "https://registry.npmjs.org/error/-/error-7.0.2.tgz", "integrity": "sha1-pfdf/02ZJhJt2sDqXcOOaJFTywI=", "requires": { - "string-template": "~0.2.1", - "xtend": "~4.0.0" + "string-template": "0.2.1", + "xtend": "4.0.1" } }, "error-ex": { @@ -2159,7 +2512,7 @@ "resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.1.tgz", "integrity": "sha1-+FWobOYa3E6GIcPNoh56dhLDqNw=", "requires": { - "is-arrayish": "^0.2.1" + "is-arrayish": "0.2.1" } }, "escape-html": { @@ -2178,11 +2531,11 @@ "integrity": "sha1-WltTr0aTEQvrsIZ6o0MN07cKEBg=", "dev": true, "requires": { - "esprima": "^2.7.1", - "estraverse": "^1.9.1", - "esutils": "^2.0.2", - "optionator": "^0.8.1", - "source-map": "~0.2.0" + "esprima": "2.7.3", + "estraverse": "1.9.3", + "esutils": "2.0.2", + "optionator": "0.8.2", + "source-map": "0.2.0" }, "dependencies": { "esprima": { @@ -2198,7 +2551,7 @@ "dev": true, "optional": true, "requires": { - "amdefine": ">=0.0.4" + "amdefine": "1.0.1" } } } @@ -2224,24 +2577,34 @@ "resolved": "https://registry.npmjs.org/etag/-/etag-1.8.1.tgz", "integrity": "sha1-Qa4u62XvpiJorr/qg6x9eSmbCIc=" }, + "eth-ens-namehash": { + "version": "2.0.8", + "resolved": "https://registry.npmjs.org/eth-ens-namehash/-/eth-ens-namehash-2.0.8.tgz", + "integrity": "sha1-IprEbsqG1S4MmR58sq74P/D2i88=", + "dev": true, + "requires": { + "idna-uts46-hx": "2.3.1", + "js-sha3": "0.5.7" + } + }, "eth-gas-reporter": { "version": "0.1.12", "resolved": "https://registry.npmjs.org/eth-gas-reporter/-/eth-gas-reporter-0.1.12.tgz", "integrity": "sha512-Ao5uiXSA5Ep5fi/YvGCsFJMelMKj0fMJkAvWYzPVe1h3Mg9Z7X3Rs51ovG9izFZH7wSqnqydiC6SKDhZWpxK2g==", "dev": true, "requires": { - "abi-decoder": "^1.0.8", - "cli-table3": "^0.5.0", - "colors": "^1.1.2", - "lodash": "^4.17.4", - "mocha": "^4.1.0", - "req-cwd": "^2.0.0", - "request": "^2.83.0", - "request-promise-native": "^1.0.5", - "sha1": "^1.1.1", - "shelljs": "^0.7.8", - "solidity-parser-antlr": "^0.2.10", - "sync-request": "^6.0.0" + "abi-decoder": "1.2.0", + "cli-table3": "0.5.1", + "colors": "1.2.1", + "lodash": "4.17.5", + "mocha": "4.1.0", + "req-cwd": "2.0.0", + "request": "2.85.0", + "request-promise-native": "1.0.5", + "sha1": "1.1.1", + "shelljs": "0.7.8", + "solidity-parser-antlr": "0.2.15", + "sync-request": "6.0.0" }, "dependencies": { "req-cwd": { @@ -2250,7 +2613,7 @@ "integrity": "sha1-1AgrTURZgDZkD7c93qAe1T20nrw=", "dev": true, "requires": { - "req-from": "^2.0.0" + "req-from": "2.0.0" } }, "req-from": { @@ -2259,7 +2622,7 @@ "integrity": "sha1-10GI5H+TeW9Kpx327jWuaJ8+DnA=", "dev": true, "requires": { - "resolve-from": "^3.0.0" + "resolve-from": "3.0.0" } }, "shelljs": { @@ -2268,9 +2631,9 @@ "integrity": "sha1-3svPh0sNHl+3LhSxZKloMEjprLM=", "dev": true, "requires": { - "glob": "^7.0.0", - "interpret": "^1.0.0", - "rechoir": "^0.6.2" + "glob": "7.1.1", + "interpret": "1.1.0", + "rechoir": "0.6.2" } } } @@ -2280,13 +2643,13 @@ "resolved": "https://registry.npmjs.org/eth-lib/-/eth-lib-0.1.27.tgz", "integrity": "sha512-B8czsfkJYzn2UIEMwjc7Mbj+Cy72V+/OXH/tb44LV8jhrjizQJJ325xMOMyk3+ETa6r6oi0jsUY14+om8mQMWA==", "requires": { - "bn.js": "^4.11.6", - "elliptic": "^6.4.0", - "keccakjs": "^0.2.1", - "nano-json-stream-parser": "^0.1.2", - "servify": "^0.1.12", - "ws": "^3.0.0", - "xhr-request-promise": "^0.1.2" + "bn.js": "4.11.6", + "elliptic": "6.4.0", + "keccakjs": "0.2.1", + "nano-json-stream-parser": "0.1.2", + "servify": "0.1.12", + "ws": "3.3.3", + "xhr-request-promise": "0.1.2" } }, "ethereumjs-testrpc-sc": { @@ -2295,8 +2658,77 @@ "integrity": "sha512-dBTav4AZQ7zuajmICv1k7bEesqS+8f0u0wciXNUJZb842RTBi0lgKEDF8WgZshzv4ThI+XVQSRNV/A+seiK4aA==", "dev": true, "requires": { - "source-map-support": "^0.5.3", - "webpack-cli": "^2.0.9" + "source-map-support": "0.5.4", + "webpack-cli": "2.0.13" + } + }, + "ethers": { + "version": "4.0.0-beta.1", + "resolved": "https://registry.npmjs.org/ethers/-/ethers-4.0.0-beta.1.tgz", + "integrity": "sha512-SoYhktEbLxf+fiux5SfCEwdzWENMvgIbMZD90I62s4GZD9nEjgEWy8ZboI3hck193Vs0bDoTohDISx84f2H2tw==", + "dev": true, + "requires": { + "@types/node": "10.12.18", + "aes-js": "3.0.0", + "bn.js": "4.11.6", + "elliptic": "6.3.3", + "hash.js": "1.1.3", + "js-sha3": "0.5.7", + "scrypt-js": "2.0.3", + "setimmediate": "1.0.4", + "uuid": "2.0.1", + "xmlhttprequest": "1.8.0" + }, + "dependencies": { + "@types/node": { + "version": "10.12.18", + "resolved": "https://registry.npmjs.org/@types/node/-/node-10.12.18.tgz", + "integrity": "sha512-fh+pAqt4xRzPfqA6eh3Z2y6fyZavRIumvjhaCL753+TVkGKGhpPeyrJG2JftD0T9q4GF00KjefsQ+PQNDdWQaQ==", + "dev": true + }, + "elliptic": { + "version": "6.3.3", + "resolved": "https://registry.npmjs.org/elliptic/-/elliptic-6.3.3.tgz", + "integrity": "sha1-VILZZG1UvLif19mU/J4ulWiHbj8=", + "dev": true, + "requires": { + "bn.js": "4.11.6", + "brorand": "1.1.0", + "hash.js": "1.1.3", + "inherits": "2.0.3" + } + }, + "setimmediate": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/setimmediate/-/setimmediate-1.0.4.tgz", + "integrity": "sha1-IOgd5iLUoCWIzgyNqJc8vPHTE48=", + "dev": true + }, + "uuid": { + "version": "2.0.1", + "resolved": "http://registry.npmjs.org/uuid/-/uuid-2.0.1.tgz", + "integrity": "sha1-wqMN7bPlNdcsz4LjQ5QaULqFM6w=", + "dev": true + } + } + }, + "ethjs-abi": { + "version": "0.1.8", + "resolved": "https://registry.npmjs.org/ethjs-abi/-/ethjs-abi-0.1.8.tgz", + "integrity": "sha1-zSiFg+1ijN+tr4re+juh28vKbBg=", + "dev": true, + "requires": { + "bn.js": "4.11.6", + "js-sha3": "0.5.5", + "number-to-bn": "1.7.0" + }, + "dependencies": { + "js-sha3": { + "version": "0.5.5", + "resolved": "https://registry.npmjs.org/js-sha3/-/js-sha3-0.5.5.tgz", + "integrity": "sha1-uvDA6MVK1ZA0R9+Wreekobynmko=", + "dev": true + } } }, "ethjs-unit": { @@ -2314,13 +2746,29 @@ "integrity": "sha1-SrTJoPWlTbkzi0w02Gv86PSzVXE=", "dev": true, "requires": { - "duplexer": "~0.1.1", - "from": "~0", - "map-stream": "~0.1.0", + "duplexer": "0.1.1", + "from": "0.1.7", + "map-stream": "0.1.0", "pause-stream": "0.0.11", - "split": "0.3", - "stream-combiner": "~0.0.4", - "through": "~2.3.1" + "split": "0.3.3", + "stream-combiner": "0.0.4", + "through": "2.3.8" + } + }, + "eventemitter3": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/eventemitter3/-/eventemitter3-1.1.1.tgz", + "integrity": "sha1-R3hr2qCHyvext15zq8XH1UAVjNA=", + "dev": true + }, + "evp_bytestokey": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/evp_bytestokey/-/evp_bytestokey-1.0.3.tgz", + "integrity": "sha512-/f2Go4TognH/KvCISP7OUsHn85hT9nUkxxA9BEWxFn+Oj9o8ZNLm/40hdlgSLyuOimsrTKLUMEorQexp/aPQeA==", + "dev": true, + "requires": { + "md5.js": "1.3.5", + "safe-buffer": "5.1.1" } }, "execa": { @@ -2328,13 +2776,13 @@ "resolved": "https://registry.npmjs.org/execa/-/execa-0.7.0.tgz", "integrity": "sha1-lEvs00zEHuMqY6n68nrVpl/Fl3c=", "requires": { - "cross-spawn": "^5.0.1", - "get-stream": "^3.0.0", - "is-stream": "^1.1.0", - "npm-run-path": "^2.0.0", - "p-finally": "^1.0.0", - "signal-exit": "^3.0.0", - "strip-eof": "^1.0.0" + "cross-spawn": "5.1.0", + "get-stream": "3.0.0", + "is-stream": "1.1.0", + "npm-run-path": "2.0.2", + "p-finally": "1.0.0", + "signal-exit": "3.0.2", + "strip-eof": "1.0.0" } }, "exit-hook": { @@ -2348,13 +2796,13 @@ "integrity": "sha1-t3c14xXOMPa27/D4OwQVGiJEliI=", "dev": true, "requires": { - "debug": "^2.3.3", - "define-property": "^0.2.5", - "extend-shallow": "^2.0.1", - "posix-character-classes": "^0.1.0", - "regex-not": "^1.0.0", - "snapdragon": "^0.8.1", - "to-regex": "^3.0.1" + "debug": "2.6.8", + "define-property": "0.2.5", + "extend-shallow": "2.0.1", + "posix-character-classes": "0.1.1", + "regex-not": "1.0.2", + "snapdragon": "0.8.2", + "to-regex": "3.0.2" }, "dependencies": { "define-property": { @@ -2363,7 +2811,7 @@ "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", "dev": true, "requires": { - "is-descriptor": "^0.1.0" + "is-descriptor": "0.1.6" } }, "extend-shallow": { @@ -2372,7 +2820,7 @@ "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", "dev": true, "requires": { - "is-extendable": "^0.1.0" + "is-extendable": "0.1.1" } } } @@ -2382,7 +2830,7 @@ "resolved": "https://registry.npmjs.org/expand-range/-/expand-range-1.8.2.tgz", "integrity": "sha1-opnv/TNf4nIeuujiV+x5ZE/IUzc=", "requires": { - "fill-range": "^2.1.0" + "fill-range": "2.2.3" }, "dependencies": { "fill-range": { @@ -2390,11 +2838,11 @@ "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-2.2.3.tgz", "integrity": "sha1-ULd9/X5Gm8dJJHCWNpn+eoSFpyM=", "requires": { - "is-number": "^2.1.0", - "isobject": "^2.0.0", - "randomatic": "^1.1.3", - "repeat-element": "^1.1.2", - "repeat-string": "^1.5.2" + "is-number": "2.1.0", + "isobject": "2.1.0", + "randomatic": "1.1.7", + "repeat-element": "1.1.2", + "repeat-string": "1.6.1" } }, "is-number": { @@ -2402,7 +2850,7 @@ "resolved": "https://registry.npmjs.org/is-number/-/is-number-2.1.0.tgz", "integrity": "sha1-Afy7s5NGOlSPL0ZszhbezknbkI8=", "requires": { - "kind-of": "^3.0.2" + "kind-of": "3.2.2" } }, "isobject": { @@ -2418,7 +2866,7 @@ "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", "requires": { - "is-buffer": "^1.1.5" + "is-buffer": "1.1.6" } } } @@ -2428,7 +2876,7 @@ "resolved": "https://registry.npmjs.org/expand-tilde/-/expand-tilde-2.0.2.tgz", "integrity": "sha1-l+gBqgUt8CRU3kawK/YhZCzchQI=", "requires": { - "homedir-polyfill": "^1.0.1" + "homedir-polyfill": "1.0.1" } }, "express": { @@ -2436,36 +2884,36 @@ "resolved": "https://registry.npmjs.org/express/-/express-4.16.3.tgz", "integrity": "sha1-avilAjUNsyRuzEvs9rWjTSL37VM=", "requires": { - "accepts": "~1.3.5", + "accepts": "1.3.5", "array-flatten": "1.1.1", "body-parser": "1.18.2", "content-disposition": "0.5.2", - "content-type": "~1.0.4", + "content-type": "1.0.4", "cookie": "0.3.1", "cookie-signature": "1.0.6", "debug": "2.6.9", - "depd": "~1.1.2", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "etag": "~1.8.1", + "depd": "1.1.2", + "encodeurl": "1.0.2", + "escape-html": "1.0.3", + "etag": "1.8.1", "finalhandler": "1.1.1", "fresh": "0.5.2", "merge-descriptors": "1.0.1", - "methods": "~1.1.2", - "on-finished": "~2.3.0", - "parseurl": "~1.3.2", + "methods": "1.1.2", + "on-finished": "2.3.0", + "parseurl": "1.3.2", "path-to-regexp": "0.1.7", - "proxy-addr": "~2.0.3", + "proxy-addr": "2.0.3", "qs": "6.5.1", - "range-parser": "~1.2.0", + "range-parser": "1.2.0", "safe-buffer": "5.1.1", "send": "0.16.2", "serve-static": "1.13.2", "setprototypeof": "1.1.0", - "statuses": "~1.4.0", - "type-is": "~1.6.16", + "statuses": "1.4.0", + "type-is": "1.6.16", "utils-merge": "1.0.1", - "vary": "~1.1.2" + "vary": "1.1.2" }, "dependencies": { "debug": { @@ -2494,8 +2942,8 @@ "integrity": "sha1-Jqcarwc7OfshJxcnRhMcJwQCjbg=", "dev": true, "requires": { - "assign-symbols": "^1.0.0", - "is-extendable": "^1.0.1" + "assign-symbols": "1.0.0", + "is-extendable": "1.0.1" }, "dependencies": { "is-extendable": { @@ -2504,7 +2952,7 @@ "integrity": "sha512-arnXMxT1hhoKo9k1LZdmlNyJdDDfy2v0fXjFlmok4+i8ul/6WlbVge9bhM74OpNPQPMGUToDtz+KXa1PneJxOA==", "dev": true, "requires": { - "is-plain-object": "^2.0.4" + "is-plain-object": "2.0.4" } } } @@ -2514,9 +2962,9 @@ "resolved": "https://registry.npmjs.org/external-editor/-/external-editor-2.1.0.tgz", "integrity": "sha512-E44iT5QVOUJBKij4IIV3uvxuNlbKS38Tw1HiupxEIHPv9qtC2PrDYohbXV5U+1jnfIXttny8gUhj+oZvflFlzA==", "requires": { - "chardet": "^0.4.0", - "iconv-lite": "^0.4.17", - "tmp": "^0.0.33" + "chardet": "0.4.2", + "iconv-lite": "0.4.19", + "tmp": "0.0.33" } }, "extglob": { @@ -2525,14 +2973,14 @@ "integrity": "sha512-Nmb6QXkELsuBr24CJSkilo6UHHgbekK5UiZgfE6UHD3Eb27YC6oD+bhcT+tJ6cl8dmsgdQxnWlcry8ksBIBLpw==", "dev": true, "requires": { - "array-unique": "^0.3.2", - "define-property": "^1.0.0", - "expand-brackets": "^2.1.4", - "extend-shallow": "^2.0.1", - "fragment-cache": "^0.2.1", - "regex-not": "^1.0.0", - "snapdragon": "^0.8.1", - "to-regex": "^3.0.1" + "array-unique": "0.3.2", + "define-property": "1.0.0", + "expand-brackets": "2.1.4", + "extend-shallow": "2.0.1", + "fragment-cache": "0.2.1", + "regex-not": "1.0.2", + "snapdragon": "0.8.2", + "to-regex": "3.0.2" }, "dependencies": { "define-property": { @@ -2541,7 +2989,7 @@ "integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=", "dev": true, "requires": { - "is-descriptor": "^1.0.0" + "is-descriptor": "1.0.2" } }, "extend-shallow": { @@ -2550,7 +2998,7 @@ "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", "dev": true, "requires": { - "is-extendable": "^0.1.0" + "is-extendable": "0.1.1" } }, "is-accessor-descriptor": { @@ -2559,7 +3007,7 @@ "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", "dev": true, "requires": { - "kind-of": "^6.0.0" + "kind-of": "6.0.2" } }, "is-data-descriptor": { @@ -2568,7 +3016,7 @@ "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", "dev": true, "requires": { - "kind-of": "^6.0.0" + "kind-of": "6.0.2" } }, "is-descriptor": { @@ -2577,9 +3025,9 @@ "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", "dev": true, "requires": { - "is-accessor-descriptor": "^1.0.0", - "is-data-descriptor": "^1.0.0", - "kind-of": "^6.0.2" + "is-accessor-descriptor": "1.0.0", + "is-data-descriptor": "1.0.0", + "kind-of": "6.0.2" } } } @@ -2605,14 +3053,29 @@ "integrity": "sha1-PYpcZog6FqMMqGQ+hR8Zuqd5eRc=", "dev": true }, + "fd-slicer": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/fd-slicer/-/fd-slicer-1.1.0.tgz", + "integrity": "sha1-JcfInLH5B3+IkbvmHY85Dq4lbx4=", + "dev": true, + "requires": { + "pend": "1.2.0" + } + }, "figures": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/figures/-/figures-2.0.0.tgz", "integrity": "sha1-OrGi0qYsi/tDGgyUy3l6L84nyWI=", "requires": { - "escape-string-regexp": "^1.0.5" + "escape-string-regexp": "1.0.5" } }, + "file-type": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/file-type/-/file-type-5.2.0.tgz", + "integrity": "sha1-LdvqfHP/42No365J3DOMBYwritY=", + "dev": true + }, "filename-regex": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/filename-regex/-/filename-regex-2.0.1.tgz", @@ -2624,10 +3087,10 @@ "integrity": "sha1-1USBHUKPmOsGpj3EAtJAPDKMOPc=", "dev": true, "requires": { - "extend-shallow": "^2.0.1", - "is-number": "^3.0.0", - "repeat-string": "^1.6.1", - "to-regex-range": "^2.1.0" + "extend-shallow": "2.0.1", + "is-number": "3.0.0", + "repeat-string": "1.6.1", + "to-regex-range": "2.1.1" }, "dependencies": { "extend-shallow": { @@ -2636,7 +3099,7 @@ "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", "dev": true, "requires": { - "is-extendable": "^0.1.0" + "is-extendable": "0.1.1" } } } @@ -2647,12 +3110,12 @@ "integrity": "sha512-Y1GUDo39ez4aHAw7MysnUD5JzYX+WaIj8I57kO3aEPT1fFRL4sr7mjei97FgnwhAyyzRYmQZaTHb2+9uZ1dPtg==", "requires": { "debug": "2.6.9", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "on-finished": "~2.3.0", - "parseurl": "~1.3.2", - "statuses": "~1.4.0", - "unpipe": "~1.0.0" + "encodeurl": "1.0.2", + "escape-html": "1.0.3", + "on-finished": "2.3.0", + "parseurl": "1.3.2", + "statuses": "1.4.0", + "unpipe": "1.0.0" }, "dependencies": { "debug": { @@ -2675,8 +3138,8 @@ "resolved": "https://registry.npmjs.org/find-up/-/find-up-1.1.2.tgz", "integrity": "sha1-ay6YIrGizgpgq2TWEOzK1TyyTQ8=", "requires": { - "path-exists": "^2.0.0", - "pinkie-promise": "^2.0.0" + "path-exists": "2.1.0", + "pinkie-promise": "2.0.1" } }, "first-chunk-stream": { @@ -2684,7 +3147,7 @@ "resolved": "https://registry.npmjs.org/first-chunk-stream/-/first-chunk-stream-2.0.0.tgz", "integrity": "sha1-G97NuOCDwGZLkZRVgVd6Q6nzHXA=", "requires": { - "readable-stream": "^2.0.2" + "readable-stream": "2.3.5" } }, "flow-parser": { @@ -2697,7 +3160,7 @@ "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.2.tgz", "integrity": "sha1-LEBFC5NI6X8oEyJZO6lnBLmr1NQ=", "requires": { - "is-function": "~1.0.0" + "is-function": "1.0.1" } }, "for-in": { @@ -2710,7 +3173,7 @@ "resolved": "https://registry.npmjs.org/for-own/-/for-own-0.1.5.tgz", "integrity": "sha1-UmXGgaTylNq78XyVCbZ2OqhFEM4=", "requires": { - "for-in": "^1.0.1" + "for-in": "1.0.2" } }, "forever-agent": { @@ -2723,9 +3186,9 @@ "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.3.2.tgz", "integrity": "sha1-SXBJi+YEwgwAXU9cI67NIda0kJk=", "requires": { - "asynckit": "^0.4.0", + "asynckit": "0.4.0", "combined-stream": "1.0.6", - "mime-types": "^2.1.12" + "mime-types": "2.1.18" } }, "forwarded": { @@ -2739,7 +3202,7 @@ "integrity": "sha1-QpD60n8T6Jvn8zeZxrxaCr//DRk=", "dev": true, "requires": { - "map-cache": "^0.2.2" + "map-cache": "0.2.2" } }, "fresh": { @@ -2758,20 +3221,50 @@ "resolved": "https://registry.npmjs.org/from2/-/from2-2.3.0.tgz", "integrity": "sha1-i/tVAr3kpNNs/e6gB/zKIdfjgq8=", "requires": { - "inherits": "^2.0.1", - "readable-stream": "^2.0.0" + "inherits": "2.0.3", + "readable-stream": "2.3.5" } }, + "fs-constants": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/fs-constants/-/fs-constants-1.0.0.tgz", + "integrity": "sha512-y6OAwoSIf7FyjMIv94u+b5rdheZEjzR63GTyZJm5qh4Bi+2YgwLCcI/fPFZkL5PSixOt6ZNKm+w+Hfp/Bciwow==", + "dev": true + }, "fs-extra": { "version": "0.30.0", "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-0.30.0.tgz", "integrity": "sha1-8jP/zAjU2n1DLapEl3aYnbHfk/A=", "requires": { - "graceful-fs": "^4.1.2", - "jsonfile": "^2.1.0", - "klaw": "^1.0.0", - "path-is-absolute": "^1.0.0", - "rimraf": "^2.2.8" + "graceful-fs": "4.1.11", + "jsonfile": "2.4.0", + "klaw": "1.3.1", + "path-is-absolute": "1.0.1", + "rimraf": "2.6.2" + } + }, + "fs-promise": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/fs-promise/-/fs-promise-2.0.3.tgz", + "integrity": "sha1-9k5PhUvPaJqovdy6JokW2z20aFQ=", + "dev": true, + "requires": { + "any-promise": "1.3.0", + "fs-extra": "2.1.2", + "mz": "2.7.0", + "thenify-all": "1.6.0" + }, + "dependencies": { + "fs-extra": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-2.1.2.tgz", + "integrity": "sha1-BGxwFjzvmq1GsOSn+kZ/si1x3jU=", + "dev": true, + "requires": { + "graceful-fs": "4.1.11", + "jsonfile": "2.4.0" + } + } } }, "fs.realpath": { @@ -2786,8 +3279,8 @@ "dev": true, "optional": true, "requires": { - "nan": "^2.9.2", - "node-pre-gyp": "^0.9.0" + "nan": "2.10.0", + "node-pre-gyp": "0.9.1" }, "dependencies": { "abbrev": { @@ -2813,8 +3306,8 @@ "dev": true, "optional": true, "requires": { - "delegates": "^1.0.0", - "readable-stream": "^2.0.6" + "delegates": "1.0.0", + "readable-stream": "2.3.6" } }, "balanced-match": { @@ -2827,7 +3320,7 @@ "bundled": true, "dev": true, "requires": { - "balanced-match": "^1.0.0", + "balanced-match": "1.0.0", "concat-map": "0.0.1" } }, @@ -2891,7 +3384,7 @@ "dev": true, "optional": true, "requires": { - "minipass": "^2.2.1" + "minipass": "2.2.4" } }, "fs.realpath": { @@ -2906,14 +3399,14 @@ "dev": true, "optional": true, "requires": { - "aproba": "^1.0.3", - "console-control-strings": "^1.0.0", - "has-unicode": "^2.0.0", - "object-assign": "^4.1.0", - "signal-exit": "^3.0.0", - "string-width": "^1.0.1", - "strip-ansi": "^3.0.1", - "wide-align": "^1.1.0" + "aproba": "1.2.0", + "console-control-strings": "1.1.0", + "has-unicode": "2.0.1", + "object-assign": "4.1.1", + "signal-exit": "3.0.2", + "string-width": "1.0.2", + "strip-ansi": "3.0.1", + "wide-align": "1.1.2" } }, "glob": { @@ -2922,12 +3415,12 @@ "dev": true, "optional": true, "requires": { - "fs.realpath": "^1.0.0", - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "^3.0.4", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" + "fs.realpath": "1.0.0", + "inflight": "1.0.6", + "inherits": "2.0.3", + "minimatch": "3.0.4", + "once": "1.4.0", + "path-is-absolute": "1.0.1" } }, "has-unicode": { @@ -2942,7 +3435,7 @@ "dev": true, "optional": true, "requires": { - "safer-buffer": "^2.1.0" + "safer-buffer": "2.1.2" } }, "ignore-walk": { @@ -2960,8 +3453,8 @@ "dev": true, "optional": true, "requires": { - "once": "^1.3.0", - "wrappy": "1" + "once": "1.4.0", + "wrappy": "1.0.2" } }, "inherits": { @@ -3007,8 +3500,8 @@ "bundled": true, "dev": true, "requires": { - "safe-buffer": "^5.1.1", - "yallist": "^3.0.0" + "safe-buffer": "5.1.1", + "yallist": "3.0.2" } }, "minizlib": { @@ -3017,7 +3510,7 @@ "dev": true, "optional": true, "requires": { - "minipass": "^2.2.1" + "minipass": "2.2.4" } }, "mkdirp": { @@ -3040,9 +3533,9 @@ "dev": true, "optional": true, "requires": { - "debug": "^2.1.2", - "iconv-lite": "^0.4.4", - "sax": "^1.2.4" + "debug": "2.6.9", + "iconv-lite": "0.4.21", + "sax": "1.2.4" } }, "node-pre-gyp": { @@ -3051,16 +3544,16 @@ "dev": true, "optional": true, "requires": { - "detect-libc": "^1.0.2", - "mkdirp": "^0.5.1", - "needle": "^2.2.0", - "nopt": "^4.0.1", - "npm-packlist": "^1.1.6", - "npmlog": "^4.0.2", - "rc": "^1.1.7", - "rimraf": "^2.6.1", - "semver": "^5.3.0", - "tar": "^4" + "detect-libc": "1.0.3", + "mkdirp": "0.5.1", + "needle": "2.2.0", + "nopt": "4.0.1", + "npm-packlist": "1.1.10", + "npmlog": "4.1.2", + "rc": "1.2.6", + "rimraf": "2.6.2", + "semver": "5.5.0", + "tar": "4.4.1" } }, "nopt": { @@ -3069,8 +3562,8 @@ "dev": true, "optional": true, "requires": { - "abbrev": "1", - "osenv": "^0.1.4" + "abbrev": "1.1.1", + "osenv": "0.1.5" } }, "npm-bundled": { @@ -3095,10 +3588,10 @@ "dev": true, "optional": true, "requires": { - "are-we-there-yet": "~1.1.2", - "console-control-strings": "~1.1.0", - "gauge": "~2.7.3", - "set-blocking": "~2.0.0" + "are-we-there-yet": "1.1.4", + "console-control-strings": "1.1.0", + "gauge": "2.7.4", + "set-blocking": "2.0.0" } }, "number-is-nan": { @@ -3117,7 +3610,7 @@ "bundled": true, "dev": true, "requires": { - "wrappy": "1" + "wrappy": "1.0.2" } }, "os-homedir": { @@ -3138,8 +3631,8 @@ "dev": true, "optional": true, "requires": { - "os-homedir": "^1.0.0", - "os-tmpdir": "^1.0.0" + "os-homedir": "1.0.2", + "os-tmpdir": "1.0.2" } }, "path-is-absolute": { @@ -3160,10 +3653,10 @@ "dev": true, "optional": true, "requires": { - "deep-extend": "~0.4.0", - "ini": "~1.3.0", - "minimist": "^1.2.0", - "strip-json-comments": "~2.0.1" + "deep-extend": "0.4.2", + "ini": "1.3.5", + "minimist": "1.2.0", + "strip-json-comments": "2.0.1" }, "dependencies": { "minimist": { @@ -3180,13 +3673,13 @@ "dev": true, "optional": true, "requires": { - "core-util-is": "~1.0.0", - "inherits": "~2.0.3", - "isarray": "~1.0.0", - "process-nextick-args": "~2.0.0", - "safe-buffer": "~5.1.1", - "string_decoder": "~1.1.1", - "util-deprecate": "~1.0.1" + "core-util-is": "1.0.2", + "inherits": "2.0.3", + "isarray": "1.0.0", + "process-nextick-args": "2.0.0", + "safe-buffer": "5.1.1", + "string_decoder": "1.1.1", + "util-deprecate": "1.0.2" } }, "rimraf": { @@ -3195,7 +3688,7 @@ "dev": true, "optional": true, "requires": { - "glob": "^7.0.5" + "glob": "7.1.2" } }, "safe-buffer": { @@ -3238,9 +3731,9 @@ "bundled": true, "dev": true, "requires": { - "code-point-at": "^1.0.0", - "is-fullwidth-code-point": "^1.0.0", - "strip-ansi": "^3.0.0" + "code-point-at": "1.1.0", + "is-fullwidth-code-point": "1.0.0", + "strip-ansi": "3.0.1" } }, "string_decoder": { @@ -3249,7 +3742,7 @@ "dev": true, "optional": true, "requires": { - "safe-buffer": "~5.1.0" + "safe-buffer": "5.1.1" } }, "strip-ansi": { @@ -3257,7 +3750,7 @@ "bundled": true, "dev": true, "requires": { - "ansi-regex": "^2.0.0" + "ansi-regex": "2.1.1" } }, "strip-json-comments": { @@ -3272,13 +3765,13 @@ "dev": true, "optional": true, "requires": { - "chownr": "^1.0.1", - "fs-minipass": "^1.2.5", - "minipass": "^2.2.4", - "minizlib": "^1.1.0", - "mkdirp": "^0.5.0", - "safe-buffer": "^5.1.1", - "yallist": "^3.0.2" + "chownr": "1.0.1", + "fs-minipass": "1.2.5", + "minipass": "2.2.4", + "minizlib": "1.1.0", + "mkdirp": "0.5.1", + "safe-buffer": "5.1.1", + "yallist": "3.0.2" } }, "util-deprecate": { @@ -3293,7 +3786,7 @@ "dev": true, "optional": true, "requires": { - "string-width": "^1.0.2" + "string-width": "1.0.2" } }, "wrappy": { @@ -3308,13 +3801,25 @@ } } }, - "ganache-cli": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/ganache-cli/-/ganache-cli-6.1.0.tgz", - "integrity": "sha512-FdTeyk4uLRHGeFiMe+Qnh4Hc5KiTVqvRVVvLDFJEVVKC1P1yHhEgZeh9sp1KhuvxSrxToxgJS25UapYQwH4zHw==", + "fstream": { + "version": "1.0.11", + "resolved": "https://registry.npmjs.org/fstream/-/fstream-1.0.11.tgz", + "integrity": "sha1-XB+x8RdHcRTwYyoOtLcbPLD9MXE=", + "dev": true, "requires": { - "source-map-support": "^0.5.3", - "webpack-cli": "^2.0.9" + "graceful-fs": "4.1.11", + "inherits": "2.0.3", + "mkdirp": "0.5.1", + "rimraf": "2.6.2" + } + }, + "ganache-cli": { + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/ganache-cli/-/ganache-cli-6.1.0.tgz", + "integrity": "sha512-FdTeyk4uLRHGeFiMe+Qnh4Hc5KiTVqvRVVvLDFJEVVKC1P1yHhEgZeh9sp1KhuvxSrxToxgJS25UapYQwH4zHw==", + "requires": { + "source-map-support": "0.5.4", + "webpack-cli": "2.0.13" } }, "get-caller-file": { @@ -3350,7 +3855,7 @@ "resolved": "https://registry.npmjs.org/getpass/-/getpass-0.1.7.tgz", "integrity": "sha1-Xv+OPmhNVprkyysSgmBOi6YhSfo=", "requires": { - "assert-plus": "^1.0.0" + "assert-plus": "1.0.0" } }, "gh-got": { @@ -3358,8 +3863,8 @@ "resolved": "https://registry.npmjs.org/gh-got/-/gh-got-6.0.0.tgz", "integrity": "sha512-F/mS+fsWQMo1zfgG9MD8KWvTWPPzzhuVwY++fhQ5Ggd+0P+CAMHtzMZhNxG+TqGfHDChJKsbh6otfMGqO2AKBw==", "requires": { - "got": "^7.0.0", - "is-plain-obj": "^1.1.0" + "got": "7.1.0", + "is-plain-obj": "1.1.0" }, "dependencies": { "got": { @@ -3367,20 +3872,20 @@ "resolved": "https://registry.npmjs.org/got/-/got-7.1.0.tgz", "integrity": "sha512-Y5WMo7xKKq1muPsxD+KmrR8DH5auG7fBdDVueZwETwV6VytKyU9OX/ddpq2/1hp1vIPvVb4T81dKQz3BivkNLw==", "requires": { - "decompress-response": "^3.2.0", - "duplexer3": "^0.1.4", - "get-stream": "^3.0.0", - "is-plain-obj": "^1.1.0", - "is-retry-allowed": "^1.0.0", - "is-stream": "^1.0.0", - "isurl": "^1.0.0-alpha5", - "lowercase-keys": "^1.0.0", - "p-cancelable": "^0.3.0", - "p-timeout": "^1.1.1", - "safe-buffer": "^5.0.1", - "timed-out": "^4.0.0", - "url-parse-lax": "^1.0.0", - "url-to-options": "^1.0.1" + "decompress-response": "3.3.0", + "duplexer3": "0.1.4", + "get-stream": "3.0.0", + "is-plain-obj": "1.1.0", + "is-retry-allowed": "1.1.0", + "is-stream": "1.1.0", + "isurl": "1.0.0", + "lowercase-keys": "1.0.0", + "p-cancelable": "0.3.0", + "p-timeout": "1.2.1", + "safe-buffer": "5.1.1", + "timed-out": "4.0.1", + "url-parse-lax": "1.0.0", + "url-to-options": "1.0.1" } }, "p-cancelable": { @@ -3393,7 +3898,7 @@ "resolved": "https://registry.npmjs.org/p-timeout/-/p-timeout-1.2.1.tgz", "integrity": "sha1-XrOzU7f86Z8QGhA4iAuwVOu+o4Y=", "requires": { - "p-finally": "^1.0.0" + "p-finally": "1.0.0" } } } @@ -3403,7 +3908,7 @@ "resolved": "https://registry.npmjs.org/github-username/-/github-username-4.1.0.tgz", "integrity": "sha1-y+KABBiDIG2kISrp5LXxacML9Bc=", "requires": { - "gh-got": "^6.0.0" + "gh-got": "6.0.0" } }, "glob": { @@ -3411,12 +3916,12 @@ "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.1.tgz", "integrity": "sha1-gFIR3wT6rxxjo2ADBs31reULLsg=", "requires": { - "fs.realpath": "^1.0.0", - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "^3.0.2", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" + "fs.realpath": "1.0.0", + "inflight": "1.0.6", + "inherits": "2.0.3", + "minimatch": "3.0.4", + "once": "1.4.0", + "path-is-absolute": "1.0.1" } }, "glob-all": { @@ -3424,8 +3929,8 @@ "resolved": "https://registry.npmjs.org/glob-all/-/glob-all-3.1.0.tgz", "integrity": "sha1-iRPd+17hrHgSZWJBsD1SF8ZLAqs=", "requires": { - "glob": "^7.0.5", - "yargs": "~1.2.6" + "glob": "7.1.1", + "yargs": "1.2.6" }, "dependencies": { "minimist": { @@ -3438,7 +3943,7 @@ "resolved": "https://registry.npmjs.org/yargs/-/yargs-1.2.6.tgz", "integrity": "sha1-nHtKgv1dWVsr8Xq23MQxNUMv40s=", "requires": { - "minimist": "^0.1.0" + "minimist": "0.1.0" } } } @@ -3448,8 +3953,8 @@ "resolved": "https://registry.npmjs.org/glob-base/-/glob-base-0.3.0.tgz", "integrity": "sha1-27Fk9iIbHAscz4Kuoyi0l98Oo8Q=", "requires": { - "glob-parent": "^2.0.0", - "is-glob": "^2.0.0" + "glob-parent": "2.0.0", + "is-glob": "2.0.1" }, "dependencies": { "glob-parent": { @@ -3457,7 +3962,7 @@ "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-2.0.0.tgz", "integrity": "sha1-gTg9ctsFT8zPUzbaqQLxgvbtuyg=", "requires": { - "is-glob": "^2.0.0" + "is-glob": "2.0.1" } }, "is-extglob": { @@ -3470,7 +3975,7 @@ "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-2.0.1.tgz", "integrity": "sha1-0Jb5JqPe1WAPP9/ZEZjLCIjC2GM=", "requires": { - "is-extglob": "^1.0.0" + "is-extglob": "1.0.0" } } } @@ -3481,8 +3986,8 @@ "integrity": "sha1-nmr2KZ2NO9K9QEMIMr0RPfkGxa4=", "dev": true, "requires": { - "is-glob": "^3.1.0", - "path-dirname": "^1.0.0" + "is-glob": "3.1.0", + "path-dirname": "1.0.2" }, "dependencies": { "is-glob": { @@ -3491,7 +3996,7 @@ "integrity": "sha1-e6WuJCF4BKxwcHuWkiVnSGzD6Eo=", "dev": true, "requires": { - "is-extglob": "^2.1.0" + "is-extglob": "2.1.1" } } } @@ -3501,8 +4006,8 @@ "resolved": "https://registry.npmjs.org/global/-/global-4.3.2.tgz", "integrity": "sha1-52mJJopsdMOJCLEwWxD8DjlOnQ8=", "requires": { - "min-document": "^2.19.0", - "process": "~0.5.1" + "min-document": "2.19.0", + "process": "0.5.2" } }, "global-dirs": { @@ -3511,7 +4016,7 @@ "integrity": "sha1-sxnA3UYH81PzvpzKTHL8FIxJ9EU=", "dev": true, "requires": { - "ini": "^1.3.4" + "ini": "1.3.5" } }, "global-modules": { @@ -3519,9 +4024,9 @@ "resolved": "https://registry.npmjs.org/global-modules/-/global-modules-1.0.0.tgz", "integrity": "sha512-sKzpEkf11GpOFuw0Zzjzmt4B4UZwjOcG757PPvrfhxcLFbq0wpsgpOqxpxtxFiCG4DtG93M6XRVbF2oGdev7bg==", "requires": { - "global-prefix": "^1.0.1", - "is-windows": "^1.0.1", - "resolve-dir": "^1.0.0" + "global-prefix": "1.0.2", + "is-windows": "1.0.2", + "resolve-dir": "1.0.1" } }, "global-prefix": { @@ -3529,11 +4034,11 @@ "resolved": "https://registry.npmjs.org/global-prefix/-/global-prefix-1.0.2.tgz", "integrity": "sha1-2/dDxsFJklk8ZVVoy2btMsASLr4=", "requires": { - "expand-tilde": "^2.0.2", - "homedir-polyfill": "^1.0.1", - "ini": "^1.3.4", - "is-windows": "^1.0.1", - "which": "^1.2.14" + "expand-tilde": "2.0.2", + "homedir-polyfill": "1.0.1", + "ini": "1.3.5", + "is-windows": "1.0.2", + "which": "1.3.0" } }, "globals": { @@ -3546,11 +4051,11 @@ "resolved": "https://registry.npmjs.org/globby/-/globby-6.1.0.tgz", "integrity": "sha1-9abXDoOV4hyFj7BInWTfAkJNUGw=", "requires": { - "array-union": "^1.0.1", - "glob": "^7.0.3", - "object-assign": "^4.0.1", - "pify": "^2.0.0", - "pinkie-promise": "^2.0.0" + "array-union": "1.0.2", + "glob": "7.1.1", + "object-assign": "4.1.1", + "pify": "2.3.0", + "pinkie-promise": "2.0.1" } }, "got": { @@ -3559,17 +4064,17 @@ "integrity": "sha1-JAzQV4WpoY5WHcG0S0HHY+8ejbA=", "dev": true, "requires": { - "create-error-class": "^3.0.0", - "duplexer3": "^0.1.4", - "get-stream": "^3.0.0", - "is-redirect": "^1.0.0", - "is-retry-allowed": "^1.0.0", - "is-stream": "^1.0.0", - "lowercase-keys": "^1.0.0", - "safe-buffer": "^5.0.1", - "timed-out": "^4.0.0", - "unzip-response": "^2.0.1", - "url-parse-lax": "^1.0.0" + "create-error-class": "3.0.2", + "duplexer3": "0.1.4", + "get-stream": "3.0.0", + "is-redirect": "1.0.0", + "is-retry-allowed": "1.1.0", + "is-stream": "1.1.0", + "lowercase-keys": "1.0.0", + "safe-buffer": "5.1.1", + "timed-out": "4.0.1", + "unzip-response": "2.0.1", + "url-parse-lax": "1.0.0" } }, "graceful-fs": { @@ -3577,12 +4082,18 @@ "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.11.tgz", "integrity": "sha1-Dovf5NHduIVNZOBOp8AOKgJuVlg=" }, + "graceful-readlink": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/graceful-readlink/-/graceful-readlink-1.0.1.tgz", + "integrity": "sha1-TK+tdrxi8C+gObL5Tpo906ORpyU=", + "dev": true + }, "grouped-queue": { "version": "0.3.3", "resolved": "https://registry.npmjs.org/grouped-queue/-/grouped-queue-0.3.3.tgz", "integrity": "sha1-wWfSpTGcWg4JZO9qJbfC34mWyFw=", "requires": { - "lodash": "^4.17.2" + "lodash": "4.17.5" } }, "growl": { @@ -3597,10 +4108,10 @@ "integrity": "sha1-Ywo13+ApS8KB7a5v/F0yn8eYLcw=", "dev": true, "requires": { - "async": "^1.4.0", - "optimist": "^0.6.1", - "source-map": "^0.4.4", - "uglify-js": "^2.6" + "async": "1.5.2", + "optimist": "0.6.1", + "source-map": "0.4.4", + "uglify-js": "2.8.29" }, "dependencies": { "async": { @@ -3615,7 +4126,7 @@ "integrity": "sha1-66T12pwNyZneaAMti092FzZSA2s=", "dev": true, "requires": { - "amdefine": ">=0.0.4" + "amdefine": "1.0.1" } } } @@ -3630,8 +4141,8 @@ "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-5.0.3.tgz", "integrity": "sha1-ukAsJmGU8VlW7xXg/PJCmT9qff0=", "requires": { - "ajv": "^5.1.0", - "har-schema": "^2.0.0" + "ajv": "5.5.2", + "har-schema": "2.0.0" } }, "has-ansi": { @@ -3639,7 +4150,7 @@ "resolved": "https://registry.npmjs.org/has-ansi/-/has-ansi-2.0.0.tgz", "integrity": "sha1-NPUEnOHs3ysGSa8+8k5F7TVBbZE=", "requires": { - "ansi-regex": "^2.0.0" + "ansi-regex": "2.1.1" } }, "has-color": { @@ -3663,7 +4174,7 @@ "resolved": "https://registry.npmjs.org/has-to-string-tag-x/-/has-to-string-tag-x-1.4.1.tgz", "integrity": "sha512-vdbKfmw+3LoOYVr+mtxHaX5a96+0f3DljYd8JOqvOLsf5mw2Otda2qCDT9qRqLAhrjyQ0h7ual5nOiASpsGNFw==", "requires": { - "has-symbol-support-x": "^1.4.1" + "has-symbol-support-x": "1.4.2" } }, "has-value": { @@ -3672,9 +4183,9 @@ "integrity": "sha1-GLKB2lhbHFxR3vJMkw7SmgvmsXc=", "dev": true, "requires": { - "get-value": "^2.0.6", - "has-values": "^1.0.0", - "isobject": "^3.0.0" + "get-value": "2.0.6", + "has-values": "1.0.0", + "isobject": "3.0.1" } }, "has-values": { @@ -3683,8 +4194,8 @@ "integrity": "sha1-lbC2P+whRmGab+V/51Yo1aOe/k8=", "dev": true, "requires": { - "is-number": "^3.0.0", - "kind-of": "^4.0.0" + "is-number": "3.0.0", + "kind-of": "4.0.0" }, "dependencies": { "kind-of": { @@ -3693,18 +4204,28 @@ "integrity": "sha1-IIE989cSkosgc3hpGkUGb65y3Vc=", "dev": true, "requires": { - "is-buffer": "^1.1.5" + "is-buffer": "1.1.6" } } } }, + "hash-base": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/hash-base/-/hash-base-3.0.4.tgz", + "integrity": "sha1-X8hoaEfs1zSZQDMZprCj8/auSRg=", + "dev": true, + "requires": { + "inherits": "2.0.3", + "safe-buffer": "5.1.1" + } + }, "hash.js": { "version": "1.1.3", "resolved": "https://registry.npmjs.org/hash.js/-/hash.js-1.1.3.tgz", "integrity": "sha512-/UETyP0W22QILqS+6HowevwhEFJ3MBJnwTf75Qob9Wz9t0DPuisL8kW8YZMK62dHAKE1c1p+gY1TtOLY+USEHA==", "requires": { - "inherits": "^2.0.3", - "minimalistic-assert": "^1.0.0" + "inherits": "2.0.3", + "minimalistic-assert": "1.0.1" } }, "hawk": { @@ -3712,10 +4233,10 @@ "resolved": "https://registry.npmjs.org/hawk/-/hawk-6.0.2.tgz", "integrity": "sha512-miowhl2+U7Qle4vdLqDdPt9m09K6yZhkLDTWGoUiUzrQCn+mHHSmfJgAyGaLRZbPmTqfFFjRV1QWCW0VWUJBbQ==", "requires": { - "boom": "4.x.x", - "cryptiles": "3.x.x", - "hoek": "4.x.x", - "sntp": "2.x.x" + "boom": "4.3.1", + "cryptiles": "3.1.2", + "hoek": "4.2.1", + "sntp": "2.1.0" } }, "he": { @@ -3728,9 +4249,9 @@ "resolved": "https://registry.npmjs.org/hmac-drbg/-/hmac-drbg-1.0.1.tgz", "integrity": "sha1-0nRXAQJabHdabFRXk+1QL8DGSaE=", "requires": { - "hash.js": "^1.0.3", - "minimalistic-assert": "^1.0.0", - "minimalistic-crypto-utils": "^1.0.1" + "hash.js": "1.1.3", + "minimalistic-assert": "1.0.1", + "minimalistic-crypto-utils": "1.0.1" } }, "hoek": { @@ -3743,8 +4264,8 @@ "resolved": "https://registry.npmjs.org/home-or-tmp/-/home-or-tmp-2.0.0.tgz", "integrity": "sha1-42w/LSyufXRqhX440Y1fMqeILbg=", "requires": { - "os-homedir": "^1.0.0", - "os-tmpdir": "^1.0.1" + "os-homedir": "1.0.2", + "os-tmpdir": "1.0.2" } }, "homedir-polyfill": { @@ -3752,7 +4273,7 @@ "resolved": "https://registry.npmjs.org/homedir-polyfill/-/homedir-polyfill-1.0.1.tgz", "integrity": "sha1-TCu8inWJmP7r9e1oWA921GdotLw=", "requires": { - "parse-passwd": "^1.0.0" + "parse-passwd": "1.0.0" } }, "hosted-git-info": { @@ -3766,12 +4287,12 @@ "integrity": "sha1-gvClBr6UJzLsje6+6A50bvVzbbo=", "dev": true, "requires": { - "@types/concat-stream": "^1.6.0", - "@types/node": "^9.4.1", - "caseless": "~0.12.0", - "concat-stream": "^1.4.6", - "http-response-object": "^3.0.1", - "parse-cache-control": "^1.0.1" + "@types/concat-stream": "1.6.0", + "@types/node": "9.6.35", + "caseless": "0.12.0", + "concat-stream": "1.6.2", + "http-response-object": "3.0.1", + "parse-cache-control": "1.0.1" } }, "http-cache-semantics": { @@ -3784,19 +4305,25 @@ "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.6.3.tgz", "integrity": "sha1-i1VoC7S+KDoLW/TqLjhYC+HZMg0=", "requires": { - "depd": "~1.1.2", + "depd": "1.1.2", "inherits": "2.0.3", "setprototypeof": "1.1.0", - "statuses": ">= 1.4.0 < 2" + "statuses": "1.5.0" } }, + "http-https": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/http-https/-/http-https-1.0.0.tgz", + "integrity": "sha1-L5CN1fHbQGjAWM1ubUzjkskTOJs=", + "dev": true + }, "http-response-object": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/http-response-object/-/http-response-object-3.0.1.tgz", "integrity": "sha512-6L0Fkd6TozA8kFSfh9Widst0wfza3U1Ex2RjJ6zNDK0vR1U1auUR6jY4Nn2Xl7CCy0ikFmxW1XcspVpb9RvwTg==", "dev": true, "requires": { - "@types/node": "^9.3.0" + "@types/node": "9.6.35" } }, "http-signature": { @@ -3804,9 +4331,9 @@ "resolved": "https://registry.npmjs.org/http-signature/-/http-signature-1.2.0.tgz", "integrity": "sha1-muzZJRFHcvPZW2WmCruPfBj7rOE=", "requires": { - "assert-plus": "^1.0.0", - "jsprim": "^1.2.2", - "sshpk": "^1.7.0" + "assert-plus": "1.0.0", + "jsprim": "1.4.1", + "sshpk": "1.14.1" } }, "iconv-lite": { @@ -3814,6 +4341,29 @@ "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.19.tgz", "integrity": "sha512-oTZqweIP51xaGPI4uPa56/Pri/480R+mo7SeU+YETByQNhDG55ycFyNLIgta9vXhILrxXDmF7ZGhqZIcuN0gJQ==" }, + "idna-uts46-hx": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/idna-uts46-hx/-/idna-uts46-hx-2.3.1.tgz", + "integrity": "sha512-PWoF9Keq6laYdIRwwCdhTPl60xRqAloYNMQLiyUnG42VjT53oW07BXIRM+NK7eQjzXjAk2gUvX9caRxlnF9TAA==", + "dev": true, + "requires": { + "punycode": "2.1.0" + }, + "dependencies": { + "punycode": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.1.0.tgz", + "integrity": "sha1-X4Y+3Im5bbCQdLrXlHvwkFbKTn0=", + "dev": true + } + } + }, + "ieee754": { + "version": "1.1.12", + "resolved": "https://registry.npmjs.org/ieee754/-/ieee754-1.1.12.tgz", + "integrity": "sha512-GguP+DRY+pJ3soyIiGPTvdiVXjZ+DbXOxGpXn3eMvNW4x4irjqXm4wHKscC+TfxSJ0yw/S1F24tqdMNsMZTiLA==", + "dev": true + }, "ignore-by-default": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/ignore-by-default/-/ignore-by-default-1.0.1.tgz", @@ -3836,7 +4386,7 @@ "resolved": "https://registry.npmjs.org/indent-string/-/indent-string-2.1.0.tgz", "integrity": "sha1-ji1INIdCEhtKghi3oTfppSBJ3IA=", "requires": { - "repeating": "^2.0.0" + "repeating": "2.0.1" } }, "inflight": { @@ -3844,8 +4394,8 @@ "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=", "requires": { - "once": "^1.3.0", - "wrappy": "1" + "once": "1.4.0", + "wrappy": "1.0.2" } }, "inherits": { @@ -3863,19 +4413,19 @@ "resolved": "https://registry.npmjs.org/inquirer/-/inquirer-5.2.0.tgz", "integrity": "sha512-E9BmnJbAKLPGonz0HeWHtbKf+EeSP93paWO3ZYoUpq/aowXvYGjjCSuashhXPpzbArIjBbji39THkxTz9ZeEUQ==", "requires": { - "ansi-escapes": "^3.0.0", - "chalk": "^2.0.0", - "cli-cursor": "^2.1.0", - "cli-width": "^2.0.0", - "external-editor": "^2.1.0", - "figures": "^2.0.0", - "lodash": "^4.3.0", + "ansi-escapes": "3.1.0", + "chalk": "2.3.2", + "cli-cursor": "2.1.0", + "cli-width": "2.2.0", + "external-editor": "2.1.0", + "figures": "2.0.0", + "lodash": "4.17.5", "mute-stream": "0.0.7", - "run-async": "^2.2.0", - "rxjs": "^5.5.2", - "string-width": "^2.1.0", - "strip-ansi": "^4.0.0", - "through": "^2.3.6" + "run-async": "2.3.0", + "rxjs": "5.5.7", + "string-width": "2.1.1", + "strip-ansi": "4.0.0", + "through": "2.3.8" }, "dependencies": { "ansi-regex": { @@ -3893,8 +4443,8 @@ "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", "requires": { - "is-fullwidth-code-point": "^2.0.0", - "strip-ansi": "^4.0.0" + "is-fullwidth-code-point": "2.0.0", + "strip-ansi": "4.0.0" } }, "strip-ansi": { @@ -3902,7 +4452,7 @@ "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", "requires": { - "ansi-regex": "^3.0.0" + "ansi-regex": "3.0.0" } } } @@ -3917,8 +4467,8 @@ "resolved": "https://registry.npmjs.org/into-stream/-/into-stream-3.1.0.tgz", "integrity": "sha1-lvsKk2wSur1v8XUqF9BWFqvQlMY=", "requires": { - "from2": "^2.1.1", - "p-is-promise": "^1.1.0" + "from2": "2.3.0", + "p-is-promise": "1.1.0" } }, "invariant": { @@ -3926,7 +4476,7 @@ "resolved": "https://registry.npmjs.org/invariant/-/invariant-2.2.4.tgz", "integrity": "sha512-phJfQVBuaJM5raOpJjSfkiD6BpbCE4Ns//LaXl6wGYtUBY83nWS6Rf9tXm2e8VaK60JEjYldbPif/A2B1C2gNA==", "requires": { - "loose-envify": "^1.0.0" + "loose-envify": "1.3.1" } }, "invert-kv": { @@ -3945,7 +4495,7 @@ "integrity": "sha1-qeEss66Nh2cn7u84Q/igiXtcmNY=", "dev": true, "requires": { - "kind-of": "^3.0.2" + "kind-of": "3.2.2" }, "dependencies": { "kind-of": { @@ -3954,7 +4504,7 @@ "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", "dev": true, "requires": { - "is-buffer": "^1.1.5" + "is-buffer": "1.1.6" } } } @@ -3970,7 +4520,7 @@ "integrity": "sha1-dfFmQrSA8YenEcgUFh/TpKdlWJg=", "dev": true, "requires": { - "binary-extensions": "^1.0.0" + "binary-extensions": "1.11.0" } }, "is-buffer": { @@ -3983,7 +4533,7 @@ "resolved": "https://registry.npmjs.org/is-builtin-module/-/is-builtin-module-1.0.0.tgz", "integrity": "sha1-VAVy0096wxGfj3bDDLwbHgN6/74=", "requires": { - "builtin-modules": "^1.0.0" + "builtin-modules": "1.1.1" } }, "is-ci": { @@ -3992,7 +4542,7 @@ "integrity": "sha512-c7TnwxLePuqIlxHgr7xtxzycJPegNHFuIrBkwbf8hc58//+Op1CqFkyS+xnIMkwn9UsJIwc174BIjkyBmSpjKg==", "dev": true, "requires": { - "ci-info": "^1.0.0" + "ci-info": "1.1.3" } }, "is-data-descriptor": { @@ -4001,7 +4551,7 @@ "integrity": "sha1-C17mSDiOLIYCgueT8YVv7D8wG1Y=", "dev": true, "requires": { - "kind-of": "^3.0.2" + "kind-of": "3.2.2" }, "dependencies": { "kind-of": { @@ -4010,7 +4560,7 @@ "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", "dev": true, "requires": { - "is-buffer": "^1.1.5" + "is-buffer": "1.1.6" } } } @@ -4021,9 +4571,9 @@ "integrity": "sha512-avDYr0SB3DwO9zsMov0gKCESFYqCnE4hq/4z3TdUlukEy5t9C0YRq7HLrsN52NAcqXKaepeCD0n+B0arnVG3Hg==", "dev": true, "requires": { - "is-accessor-descriptor": "^0.1.6", - "is-data-descriptor": "^0.1.4", - "kind-of": "^5.0.0" + "is-accessor-descriptor": "0.1.6", + "is-data-descriptor": "0.1.4", + "kind-of": "5.1.0" }, "dependencies": { "kind-of": { @@ -4044,7 +4594,7 @@ "resolved": "https://registry.npmjs.org/is-equal-shallow/-/is-equal-shallow-0.1.3.tgz", "integrity": "sha1-IjgJj8Ih3gvPpdnqxMRdY4qhxTQ=", "requires": { - "is-primitive": "^2.0.0" + "is-primitive": "2.0.0" } }, "is-extendable": { @@ -4063,7 +4613,7 @@ "resolved": "https://registry.npmjs.org/is-finite/-/is-finite-1.0.2.tgz", "integrity": "sha1-zGZ3aVYCvlUO8R6LSqYwU0K20Ko=", "requires": { - "number-is-nan": "^1.0.0" + "number-is-nan": "1.0.1" } }, "is-fullwidth-code-point": { @@ -4071,7 +4621,7 @@ "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz", "integrity": "sha1-754xOG8DGn8NZDr4L95QxFfvAMs=", "requires": { - "number-is-nan": "^1.0.0" + "number-is-nan": "1.0.1" } }, "is-function": { @@ -4085,7 +4635,7 @@ "integrity": "sha1-lSHHaEXMJhCoUgPd8ICpWML/q8A=", "dev": true, "requires": { - "is-extglob": "^2.1.1" + "is-extglob": "2.1.1" } }, "is-hex-prefixed": { @@ -4099,10 +4649,16 @@ "integrity": "sha1-Df2Y9akRFxbdU13aZJL2e/PSWoA=", "dev": true, "requires": { - "global-dirs": "^0.1.0", - "is-path-inside": "^1.0.0" + "global-dirs": "0.1.1", + "is-path-inside": "1.0.1" } }, + "is-natural-number": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/is-natural-number/-/is-natural-number-4.0.1.tgz", + "integrity": "sha1-q5124dtM7VHjXeDHLr7PCfc0zeg=", + "dev": true + }, "is-npm": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/is-npm/-/is-npm-1.0.0.tgz", @@ -4114,7 +4670,7 @@ "resolved": "https://registry.npmjs.org/is-number/-/is-number-3.0.0.tgz", "integrity": "sha1-JP1iAaR4LPUFYcgQJ2r8fRLXEZU=", "requires": { - "kind-of": "^3.0.2" + "kind-of": "3.2.2" }, "dependencies": { "kind-of": { @@ -4122,7 +4678,7 @@ "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", "requires": { - "is-buffer": "^1.1.5" + "is-buffer": "1.1.6" } } } @@ -4143,7 +4699,7 @@ "resolved": "https://registry.npmjs.org/is-observable/-/is-observable-0.2.0.tgz", "integrity": "sha1-s2ExHYPG5dcmyr9eJQsCNxBvWuI=", "requires": { - "symbol-observable": "^0.2.2" + "symbol-observable": "0.2.4" }, "dependencies": { "symbol-observable": { @@ -4159,7 +4715,7 @@ "integrity": "sha512-OTiixgpZAT1M4NHgS5IguFp/Vz2VI3U7Goh4/HA1adtwyLtSBrxYlcSYkhpAE07s4fKEcjrFxyvtQBND4vFQyQ==", "dev": true, "requires": { - "is-number": "^4.0.0" + "is-number": "4.0.0" }, "dependencies": { "is-number": { @@ -4176,7 +4732,7 @@ "integrity": "sha1-jvW33lBDej/cprToZe96pVy0gDY=", "dev": true, "requires": { - "path-is-inside": "^1.0.1" + "path-is-inside": "1.0.2" } }, "is-plain-obj": { @@ -4190,7 +4746,7 @@ "integrity": "sha512-h5PpgXkWitc38BBMYawTYMWJHFZJVnBquFE57xFpjB8pJFiF6gZ+bU+WyI/yqXiFR5mdLsgYNaPe8uao6Uv9Og==", "dev": true, "requires": { - "isobject": "^3.0.1" + "isobject": "3.0.1" } }, "is-posix-bracket": { @@ -4224,7 +4780,7 @@ "resolved": "https://registry.npmjs.org/is-scoped/-/is-scoped-1.0.0.tgz", "integrity": "sha1-RJypgpnnEwOCViieyytUDcQ3yzA=", "requires": { - "scoped-regex": "^1.0.0" + "scoped-regex": "1.0.0" } }, "is-stream": { @@ -4274,20 +4830,20 @@ "integrity": "sha1-ZcfXPUxNqE1POsMQuRj7C4Azczs=", "dev": true, "requires": { - "abbrev": "1.0.x", - "async": "1.x", - "escodegen": "1.8.x", - "esprima": "2.7.x", - "glob": "^5.0.15", - "handlebars": "^4.0.1", - "js-yaml": "3.x", - "mkdirp": "0.5.x", - "nopt": "3.x", - "once": "1.x", - "resolve": "1.1.x", - "supports-color": "^3.1.0", - "which": "^1.1.1", - "wordwrap": "^1.0.0" + "abbrev": "1.0.9", + "async": "1.5.2", + "escodegen": "1.8.1", + "esprima": "2.7.3", + "glob": "5.0.15", + "handlebars": "4.0.11", + "js-yaml": "3.11.0", + "mkdirp": "0.5.1", + "nopt": "3.0.6", + "once": "1.4.0", + "resolve": "1.1.7", + "supports-color": "3.1.2", + "which": "1.3.0", + "wordwrap": "1.0.0" }, "dependencies": { "abbrev": { @@ -4314,11 +4870,11 @@ "integrity": "sha1-G8k2ueAvSmA/zCIuz3Yz0wuLk7E=", "dev": true, "requires": { - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "2 || 3", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" + "inflight": "1.0.6", + "inherits": "2.0.3", + "minimatch": "3.0.4", + "once": "1.4.0", + "path-is-absolute": "1.0.1" } }, "nopt": { @@ -4327,7 +4883,7 @@ "integrity": "sha1-xkZdvwirzU2zWTF/eaxopkayj/k=", "dev": true, "requires": { - "abbrev": "1" + "abbrev": "1.0.9" } }, "resolve": { @@ -4343,9 +4899,9 @@ "resolved": "https://registry.npmjs.org/istextorbinary/-/istextorbinary-2.2.1.tgz", "integrity": "sha512-TS+hoFl8Z5FAFMK38nhBkdLt44CclNRgDHWeMgsV8ko3nDlr/9UI2Sf839sW7enijf8oKsZYXRvM8g0it9Zmcw==", "requires": { - "binaryextensions": "2", - "editions": "^1.3.3", - "textextensions": "2" + "binaryextensions": "2.1.1", + "editions": "1.3.4", + "textextensions": "2.2.0" } }, "isurl": { @@ -4353,8 +4909,8 @@ "resolved": "https://registry.npmjs.org/isurl/-/isurl-1.0.0.tgz", "integrity": "sha512-1P/yWsxPlDtn7QeRD+ULKQPaIaN6yF368GZ2vDfv0AL0NwpStafjWCDDdn0k8wgFMWpVAqG7oJhxHnlud42i9w==", "requires": { - "has-to-string-tag-x": "^1.2.0", - "is-object": "^1.0.1" + "has-to-string-tag-x": "1.4.1", + "is-object": "1.0.1" } }, "jade": { @@ -4382,9 +4938,9 @@ } }, "js-sha3": { - "version": "0.5.5", - "resolved": "https://registry.npmjs.org/js-sha3/-/js-sha3-0.5.5.tgz", - "integrity": "sha1-uvDA6MVK1ZA0R9+Wreekobynmko=", + "version": "0.5.7", + "resolved": "https://registry.npmjs.org/js-sha3/-/js-sha3-0.5.7.tgz", + "integrity": "sha1-DU/9gALVMzqrr0oj7tL2N0yfKOc=", "dev": true }, "js-tokens": { @@ -4398,8 +4954,8 @@ "integrity": "sha512-saJstZWv7oNeOyBh3+Dx1qWzhW0+e6/8eDzo7p5rDFqxntSztloLtuKu+Ejhtq82jsilwOIZYsCz+lIjthg1Hw==", "dev": true, "requires": { - "argparse": "^1.0.7", - "esprima": "^4.0.0" + "argparse": "1.0.10", + "esprima": "4.0.0" } }, "jsbn": { @@ -4413,21 +4969,21 @@ "resolved": "https://registry.npmjs.org/jscodeshift/-/jscodeshift-0.5.0.tgz", "integrity": "sha512-JAcQINNMFpdzzpKJN8k5xXjF3XDuckB1/48uScSzcnNyK199iWEc9AxKL9OoX5144M2w5zEx9Qs4/E/eBZZUlw==", "requires": { - "babel-plugin-transform-flow-strip-types": "^6.8.0", - "babel-preset-es2015": "^6.9.0", - "babel-preset-stage-1": "^6.5.0", - "babel-register": "^6.9.0", - "babylon": "^7.0.0-beta.30", - "colors": "^1.1.2", - "flow-parser": "^0.*", - "lodash": "^4.13.1", - "micromatch": "^2.3.7", - "neo-async": "^2.5.0", + "babel-plugin-transform-flow-strip-types": "6.22.0", + "babel-preset-es2015": "6.24.1", + "babel-preset-stage-1": "6.24.1", + "babel-register": "6.26.0", + "babylon": "7.0.0-beta.42", + "colors": "1.2.1", + "flow-parser": "0.68.0", + "lodash": "4.17.5", + "micromatch": "2.3.11", + "neo-async": "2.5.0", "node-dir": "0.1.8", - "nomnom": "^1.8.1", - "recast": "^0.14.1", - "temp": "^0.8.1", - "write-file-atomic": "^1.2.0" + "nomnom": "1.8.1", + "recast": "0.14.7", + "temp": "0.8.3", + "write-file-atomic": "1.3.4" }, "dependencies": { "arr-diff": { @@ -4435,7 +4991,7 @@ "resolved": "https://registry.npmjs.org/arr-diff/-/arr-diff-2.0.0.tgz", "integrity": "sha1-jzuCf5Vai9ZpaX5KQlasPOrjVs8=", "requires": { - "arr-flatten": "^1.0.1" + "arr-flatten": "1.1.0" } }, "array-unique": { @@ -4448,9 +5004,9 @@ "resolved": "https://registry.npmjs.org/braces/-/braces-1.8.5.tgz", "integrity": "sha1-uneWLhLf+WnWt2cR6RS3N4V79qc=", "requires": { - "expand-range": "^1.8.1", - "preserve": "^0.2.0", - "repeat-element": "^1.1.2" + "expand-range": "1.8.2", + "preserve": "0.2.0", + "repeat-element": "1.1.2" } }, "expand-brackets": { @@ -4458,7 +5014,7 @@ "resolved": "https://registry.npmjs.org/expand-brackets/-/expand-brackets-0.1.5.tgz", "integrity": "sha1-3wcoTjQqgHzXM6xa9yQR5YHRF3s=", "requires": { - "is-posix-bracket": "^0.1.0" + "is-posix-bracket": "0.1.1" } }, "extglob": { @@ -4466,7 +5022,7 @@ "resolved": "https://registry.npmjs.org/extglob/-/extglob-0.3.2.tgz", "integrity": "sha1-Lhj/PS9JqydlzskCPwEdqo2DSaE=", "requires": { - "is-extglob": "^1.0.0" + "is-extglob": "1.0.0" } }, "is-extglob": { @@ -4479,7 +5035,7 @@ "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-2.0.1.tgz", "integrity": "sha1-0Jb5JqPe1WAPP9/ZEZjLCIjC2GM=", "requires": { - "is-extglob": "^1.0.0" + "is-extglob": "1.0.0" } }, "kind-of": { @@ -4487,7 +5043,7 @@ "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", "requires": { - "is-buffer": "^1.1.5" + "is-buffer": "1.1.6" } }, "micromatch": { @@ -4495,19 +5051,19 @@ "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-2.3.11.tgz", "integrity": "sha1-hmd8l9FyCzY0MdBNDRUpO9OMFWU=", "requires": { - "arr-diff": "^2.0.0", - "array-unique": "^0.2.1", - "braces": "^1.8.2", - "expand-brackets": "^0.1.4", - "extglob": "^0.3.1", - "filename-regex": "^2.0.0", - "is-extglob": "^1.0.0", - "is-glob": "^2.0.1", - "kind-of": "^3.0.2", - "normalize-path": "^2.0.1", - "object.omit": "^2.0.0", - "parse-glob": "^3.0.4", - "regex-cache": "^0.4.2" + "arr-diff": "2.0.0", + "array-unique": "0.2.1", + "braces": "1.8.5", + "expand-brackets": "0.1.5", + "extglob": "0.3.2", + "filename-regex": "2.0.1", + "is-extglob": "1.0.0", + "is-glob": "2.0.1", + "kind-of": "3.2.2", + "normalize-path": "2.1.1", + "object.omit": "2.0.1", + "parse-glob": "3.0.4", + "regex-cache": "0.4.4" } }, "write-file-atomic": { @@ -4515,9 +5071,9 @@ "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-1.3.4.tgz", "integrity": "sha1-+Aek8LHZ6ROuekgRLmzDrxmRtF8=", "requires": { - "graceful-fs": "^4.1.11", - "imurmurhash": "^0.1.4", - "slide": "^1.1.5" + "graceful-fs": "4.1.11", + "imurmurhash": "0.1.4", + "slide": "1.1.6" } } } @@ -4562,7 +5118,7 @@ "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-2.4.0.tgz", "integrity": "sha1-NzaitCi4e72gzIO1P6PWM6NcKug=", "requires": { - "graceful-fs": "^4.1.6" + "graceful-fs": "4.1.11" } }, "jsprim": { @@ -4581,8 +5137,8 @@ "resolved": "https://registry.npmjs.org/keccakjs/-/keccakjs-0.2.1.tgz", "integrity": "sha1-HWM6+QfvMFu/ny+mFtVsRFYd+k0=", "requires": { - "browserify-sha3": "^0.0.1", - "sha3": "^1.1.0" + "browserify-sha3": "0.0.1", + "sha3": "1.2.0" } }, "keyv": { @@ -4604,7 +5160,7 @@ "resolved": "https://registry.npmjs.org/klaw/-/klaw-1.3.1.tgz", "integrity": "sha1-QIhDO0azsbolnXh4XY6W9zugJDk=", "requires": { - "graceful-fs": "^4.1.9" + "graceful-fs": "4.1.11" } }, "latest-version": { @@ -4613,7 +5169,7 @@ "integrity": "sha1-ogU4P+oyKzO1rjsYq+4NwvNW7hU=", "dev": true, "requires": { - "package-json": "^4.0.0" + "package-json": "4.0.1" } }, "lazy-cache": { @@ -4628,7 +5184,7 @@ "resolved": "https://registry.npmjs.org/lcid/-/lcid-1.0.0.tgz", "integrity": "sha1-MIrMr6C8SDo4Z7S28rlQYlHRuDU=", "requires": { - "invert-kv": "^1.0.0" + "invert-kv": "1.0.0" } }, "levn": { @@ -4637,8 +5193,8 @@ "integrity": "sha1-OwmSTt+fCDwEkP3UwLxEIeBHZO4=", "dev": true, "requires": { - "prelude-ls": "~1.1.2", - "type-check": "~0.3.2" + "prelude-ls": "1.1.2", + "type-check": "0.3.2" } }, "listr": { @@ -4646,23 +5202,23 @@ "resolved": "https://registry.npmjs.org/listr/-/listr-0.13.0.tgz", "integrity": "sha1-ILsLowuuZg7oTMBQPfS+PVYjiH0=", "requires": { - "chalk": "^1.1.3", - "cli-truncate": "^0.2.1", - "figures": "^1.7.0", - "indent-string": "^2.1.0", - "is-observable": "^0.2.0", - "is-promise": "^2.1.0", - "is-stream": "^1.1.0", - "listr-silent-renderer": "^1.1.1", - "listr-update-renderer": "^0.4.0", - "listr-verbose-renderer": "^0.4.0", - "log-symbols": "^1.0.2", - "log-update": "^1.0.2", - "ora": "^0.2.3", - "p-map": "^1.1.1", - "rxjs": "^5.4.2", - "stream-to-observable": "^0.2.0", - "strip-ansi": "^3.0.1" + "chalk": "1.1.3", + "cli-truncate": "0.2.1", + "figures": "1.7.0", + "indent-string": "2.1.0", + "is-observable": "0.2.0", + "is-promise": "2.1.0", + "is-stream": "1.1.0", + "listr-silent-renderer": "1.1.1", + "listr-update-renderer": "0.4.0", + "listr-verbose-renderer": "0.4.1", + "log-symbols": "1.0.2", + "log-update": "1.0.2", + "ora": "0.2.3", + "p-map": "1.2.0", + "rxjs": "5.5.7", + "stream-to-observable": "0.2.0", + "strip-ansi": "3.0.1" }, "dependencies": { "ansi-styles": { @@ -4675,11 +5231,11 @@ "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz", "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=", "requires": { - "ansi-styles": "^2.2.1", - "escape-string-regexp": "^1.0.2", - "has-ansi": "^2.0.0", - "strip-ansi": "^3.0.0", - "supports-color": "^2.0.0" + "ansi-styles": "2.2.1", + "escape-string-regexp": "1.0.5", + "has-ansi": "2.0.0", + "strip-ansi": "3.0.1", + "supports-color": "2.0.0" } }, "figures": { @@ -4687,8 +5243,8 @@ "resolved": "https://registry.npmjs.org/figures/-/figures-1.7.0.tgz", "integrity": "sha1-y+Hjr/zxzUS4DK3+0o3Hk6lwHS4=", "requires": { - "escape-string-regexp": "^1.0.5", - "object-assign": "^4.1.0" + "escape-string-regexp": "1.0.5", + "object-assign": "4.1.1" } }, "log-symbols": { @@ -4696,7 +5252,7 @@ "resolved": "https://registry.npmjs.org/log-symbols/-/log-symbols-1.0.2.tgz", "integrity": "sha1-N2/3tY6jCGoPCfrMdGF+ylAeGhg=", "requires": { - "chalk": "^1.0.0" + "chalk": "1.1.3" } }, "supports-color": { @@ -4716,14 +5272,14 @@ "resolved": "https://registry.npmjs.org/listr-update-renderer/-/listr-update-renderer-0.4.0.tgz", "integrity": "sha1-NE2YDaLKLosUW6MFkI8yrj9MyKc=", "requires": { - "chalk": "^1.1.3", - "cli-truncate": "^0.2.1", - "elegant-spinner": "^1.0.1", - "figures": "^1.7.0", - "indent-string": "^3.0.0", - "log-symbols": "^1.0.2", - "log-update": "^1.0.2", - "strip-ansi": "^3.0.1" + "chalk": "1.1.3", + "cli-truncate": "0.2.1", + "elegant-spinner": "1.0.1", + "figures": "1.7.0", + "indent-string": "3.2.0", + "log-symbols": "1.0.2", + "log-update": "1.0.2", + "strip-ansi": "3.0.1" }, "dependencies": { "ansi-styles": { @@ -4736,11 +5292,11 @@ "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz", "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=", "requires": { - "ansi-styles": "^2.2.1", - "escape-string-regexp": "^1.0.2", - "has-ansi": "^2.0.0", - "strip-ansi": "^3.0.0", - "supports-color": "^2.0.0" + "ansi-styles": "2.2.1", + "escape-string-regexp": "1.0.5", + "has-ansi": "2.0.0", + "strip-ansi": "3.0.1", + "supports-color": "2.0.0" } }, "figures": { @@ -4748,8 +5304,8 @@ "resolved": "https://registry.npmjs.org/figures/-/figures-1.7.0.tgz", "integrity": "sha1-y+Hjr/zxzUS4DK3+0o3Hk6lwHS4=", "requires": { - "escape-string-regexp": "^1.0.5", - "object-assign": "^4.1.0" + "escape-string-regexp": "1.0.5", + "object-assign": "4.1.1" } }, "indent-string": { @@ -4762,7 +5318,7 @@ "resolved": "https://registry.npmjs.org/log-symbols/-/log-symbols-1.0.2.tgz", "integrity": "sha1-N2/3tY6jCGoPCfrMdGF+ylAeGhg=", "requires": { - "chalk": "^1.0.0" + "chalk": "1.1.3" } }, "supports-color": { @@ -4777,10 +5333,10 @@ "resolved": "https://registry.npmjs.org/listr-verbose-renderer/-/listr-verbose-renderer-0.4.1.tgz", "integrity": "sha1-ggb0z21S3cWCfl/RSYng6WWTOjU=", "requires": { - "chalk": "^1.1.3", - "cli-cursor": "^1.0.2", - "date-fns": "^1.27.2", - "figures": "^1.7.0" + "chalk": "1.1.3", + "cli-cursor": "1.0.2", + "date-fns": "1.29.0", + "figures": "1.7.0" }, "dependencies": { "ansi-styles": { @@ -4793,11 +5349,11 @@ "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz", "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=", "requires": { - "ansi-styles": "^2.2.1", - "escape-string-regexp": "^1.0.2", - "has-ansi": "^2.0.0", - "strip-ansi": "^3.0.0", - "supports-color": "^2.0.0" + "ansi-styles": "2.2.1", + "escape-string-regexp": "1.0.5", + "has-ansi": "2.0.0", + "strip-ansi": "3.0.1", + "supports-color": "2.0.0" } }, "cli-cursor": { @@ -4805,7 +5361,7 @@ "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-1.0.2.tgz", "integrity": "sha1-ZNo/fValRBLll5S9Ytw1KV6PKYc=", "requires": { - "restore-cursor": "^1.0.1" + "restore-cursor": "1.0.1" } }, "figures": { @@ -4813,8 +5369,8 @@ "resolved": "https://registry.npmjs.org/figures/-/figures-1.7.0.tgz", "integrity": "sha1-y+Hjr/zxzUS4DK3+0o3Hk6lwHS4=", "requires": { - "escape-string-regexp": "^1.0.5", - "object-assign": "^4.1.0" + "escape-string-regexp": "1.0.5", + "object-assign": "4.1.1" } }, "onetime": { @@ -4827,8 +5383,8 @@ "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-1.0.1.tgz", "integrity": "sha1-NGYfRohjJ/7SmRR5FSJS35LapUE=", "requires": { - "exit-hook": "^1.0.0", - "onetime": "^1.0.0" + "exit-hook": "1.1.1", + "onetime": "1.1.0" } }, "supports-color": { @@ -4843,11 +5399,11 @@ "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-1.1.0.tgz", "integrity": "sha1-lWkFcI1YtLq0wiYbBPWfMcmTdMA=", "requires": { - "graceful-fs": "^4.1.2", - "parse-json": "^2.2.0", - "pify": "^2.0.0", - "pinkie-promise": "^2.0.0", - "strip-bom": "^2.0.0" + "graceful-fs": "4.1.11", + "parse-json": "2.2.0", + "pify": "2.3.0", + "pinkie-promise": "2.0.1", + "strip-bom": "2.0.0" } }, "loader-utils": { @@ -4855,9 +5411,9 @@ "resolved": "https://registry.npmjs.org/loader-utils/-/loader-utils-1.1.0.tgz", "integrity": "sha1-yYrvSIvM7aL/teLeZG1qdUQp9c0=", "requires": { - "big.js": "^3.1.3", - "emojis-list": "^2.0.0", - "json5": "^0.5.0" + "big.js": "3.2.0", + "emojis-list": "2.1.0", + "json5": "0.5.1" } }, "locate-path": { @@ -4865,8 +5421,8 @@ "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-2.0.0.tgz", "integrity": "sha1-K1aLJl7slExtnA3pw9u7ygNUzY4=", "requires": { - "p-locate": "^2.0.0", - "path-exists": "^3.0.0" + "p-locate": "2.0.0", + "path-exists": "3.0.0" }, "dependencies": { "path-exists": { @@ -4891,7 +5447,7 @@ "resolved": "https://registry.npmjs.org/log-symbols/-/log-symbols-2.2.0.tgz", "integrity": "sha512-VeIAFslyIerEJLXHziedo2basKbMKtTw3vfn5IzG0XTjhAVEJyNHnL2p7vc+wBDSdQuUpNw3M2u6xb9QsAY5Eg==", "requires": { - "chalk": "^2.0.1" + "chalk": "2.3.2" } }, "log-update": { @@ -4899,8 +5455,8 @@ "resolved": "https://registry.npmjs.org/log-update/-/log-update-1.0.2.tgz", "integrity": "sha1-GZKfZMQJPS0ucHWh2tivWcKWuNE=", "requires": { - "ansi-escapes": "^1.0.0", - "cli-cursor": "^1.0.2" + "ansi-escapes": "1.4.0", + "cli-cursor": "1.0.2" }, "dependencies": { "ansi-escapes": { @@ -4913,7 +5469,7 @@ "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-1.0.2.tgz", "integrity": "sha1-ZNo/fValRBLll5S9Ytw1KV6PKYc=", "requires": { - "restore-cursor": "^1.0.1" + "restore-cursor": "1.0.1" } }, "onetime": { @@ -4926,8 +5482,8 @@ "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-1.0.1.tgz", "integrity": "sha1-NGYfRohjJ/7SmRR5FSJS35LapUE=", "requires": { - "exit-hook": "^1.0.0", - "onetime": "^1.0.0" + "exit-hook": "1.1.1", + "onetime": "1.1.0" } } } @@ -4943,7 +5499,7 @@ "resolved": "https://registry.npmjs.org/loose-envify/-/loose-envify-1.3.1.tgz", "integrity": "sha1-0aitM/qc4OcT1l/dCsi3SNR4yEg=", "requires": { - "js-tokens": "^3.0.0" + "js-tokens": "3.0.2" } }, "lowercase-keys": { @@ -4962,7 +5518,7 @@ "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-1.2.0.tgz", "integrity": "sha512-aNUAa4UMg/UougV25bbrU4ZaaKNjJ/3/xnvg/twpmKROPdKZPZ9wGgI0opdZzO8q/zUFawoUuixuOv33eZ61Iw==", "requires": { - "pify": "^3.0.0" + "pify": "3.0.0" }, "dependencies": { "pify": { @@ -4990,7 +5546,26 @@ "integrity": "sha1-7Nyo8TFE5mDxtb1B8S80edmN+48=", "dev": true, "requires": { - "object-visit": "^1.0.0" + "object-visit": "1.0.1" + } + }, + "md5.js": { + "version": "1.3.5", + "resolved": "https://registry.npmjs.org/md5.js/-/md5.js-1.3.5.tgz", + "integrity": "sha512-xitP+WxNPcTTOgnTJcrhM0xvdPepipPSf3I8EIpGKeFLjt3PlJLIDG3u8EX53ZIubkb+5U2+3rELYpEhHhzdkg==", + "dev": true, + "requires": { + "hash-base": "3.0.4", + "inherits": "2.0.3", + "safe-buffer": "5.1.2" + }, + "dependencies": { + "safe-buffer": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", + "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", + "dev": true + } } }, "media-typer": { @@ -5003,7 +5578,7 @@ "resolved": "https://registry.npmjs.org/mem/-/mem-1.1.0.tgz", "integrity": "sha1-Xt1StIXKHZAP5kiVUFOZoN+kX3Y=", "requires": { - "mimic-fn": "^1.0.0" + "mimic-fn": "1.2.0" } }, "mem-fs": { @@ -5011,9 +5586,9 @@ "resolved": "https://registry.npmjs.org/mem-fs/-/mem-fs-1.1.3.tgz", "integrity": "sha1-uK6NLj/Lb10/kWXBLUVRoGXZicw=", "requires": { - "through2": "^2.0.0", - "vinyl": "^1.1.0", - "vinyl-file": "^2.0.0" + "through2": "2.0.3", + "vinyl": "1.2.0", + "vinyl-file": "2.0.0" } }, "mem-fs-editor": { @@ -5021,16 +5596,16 @@ "resolved": "https://registry.npmjs.org/mem-fs-editor/-/mem-fs-editor-3.0.2.tgz", "integrity": "sha1-3Qpuryu4prN3QAZ6pUnrUwEFr58=", "requires": { - "commondir": "^1.0.1", - "deep-extend": "^0.4.0", - "ejs": "^2.3.1", - "glob": "^7.0.3", - "globby": "^6.1.0", - "mkdirp": "^0.5.0", - "multimatch": "^2.0.0", - "rimraf": "^2.2.8", - "through2": "^2.0.0", - "vinyl": "^2.0.1" + "commondir": "1.0.1", + "deep-extend": "0.4.2", + "ejs": "2.5.8", + "glob": "7.1.1", + "globby": "6.1.0", + "mkdirp": "0.5.1", + "multimatch": "2.1.0", + "rimraf": "2.6.2", + "through2": "2.0.3", + "vinyl": "2.1.0" }, "dependencies": { "clone": { @@ -5053,12 +5628,12 @@ "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-2.1.0.tgz", "integrity": "sha1-Ah+cLPlR1rk5lDyJ617lrdT9kkw=", "requires": { - "clone": "^2.1.1", - "clone-buffer": "^1.0.0", - "clone-stats": "^1.0.0", - "cloneable-readable": "^1.0.0", - "remove-trailing-separator": "^1.0.1", - "replace-ext": "^1.0.0" + "clone": "2.1.2", + "clone-buffer": "1.0.0", + "clone-stats": "1.0.0", + "cloneable-readable": "1.1.2", + "remove-trailing-separator": "1.1.0", + "replace-ext": "1.0.0" } } } @@ -5068,8 +5643,8 @@ "resolved": "https://registry.npmjs.org/memory-fs/-/memory-fs-0.4.1.tgz", "integrity": "sha1-OpoguEYlI+RHz7x+i7gO1me/xVI=", "requires": { - "errno": "^0.1.3", - "readable-stream": "^2.0.1" + "errno": "0.1.7", + "readable-stream": "2.3.5" } }, "memorystream": { @@ -5093,19 +5668,29 @@ "integrity": "sha512-MWikgl9n9M3w+bpsY3He8L+w9eF9338xRl8IAO5viDizwSzziFEyUzo2xrrloB64ADbTf8uA8vRqqttDTOmccg==", "dev": true, "requires": { - "arr-diff": "^4.0.0", - "array-unique": "^0.3.2", - "braces": "^2.3.1", - "define-property": "^2.0.2", - "extend-shallow": "^3.0.2", - "extglob": "^2.0.4", - "fragment-cache": "^0.2.1", - "kind-of": "^6.0.2", - "nanomatch": "^1.2.9", - "object.pick": "^1.3.0", - "regex-not": "^1.0.0", - "snapdragon": "^0.8.1", - "to-regex": "^3.0.2" + "arr-diff": "4.0.0", + "array-unique": "0.3.2", + "braces": "2.3.2", + "define-property": "2.0.2", + "extend-shallow": "3.0.2", + "extglob": "2.0.4", + "fragment-cache": "0.2.1", + "kind-of": "6.0.2", + "nanomatch": "1.2.9", + "object.pick": "1.3.0", + "regex-not": "1.0.2", + "snapdragon": "0.8.2", + "to-regex": "3.0.2" + } + }, + "miller-rabin": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/miller-rabin/-/miller-rabin-4.0.1.tgz", + "integrity": "sha512-115fLhvZVqWwHPbClyntxEVfVDfl9DLLTuJvq3g2O/Oxi8AiNouAHvDSzHS0viUJc+V5vm3eq91Xwqn9dp4jRA==", + "dev": true, + "requires": { + "bn.js": "4.11.6", + "brorand": "1.1.0" } }, "mime": { @@ -5123,7 +5708,7 @@ "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.18.tgz", "integrity": "sha512-lc/aahn+t4/SWV/qcmumYjymLsWfN3ELhpmVuUFjgsORruuZPVSwAQryq+HHGvO/SI2KVX26bx+En+zhM8g8hQ==", "requires": { - "mime-db": "~1.33.0" + "mime-db": "1.33.0" } }, "mimic-fn": { @@ -5141,7 +5726,7 @@ "resolved": "https://registry.npmjs.org/min-document/-/min-document-2.19.0.tgz", "integrity": "sha1-e9KC4/WELtKVu3SM3Z8f+iyCRoU=", "requires": { - "dom-walk": "^0.1.0" + "dom-walk": "0.1.1" } }, "minimalistic-assert": { @@ -5159,7 +5744,7 @@ "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", "requires": { - "brace-expansion": "^1.1.7" + "brace-expansion": "1.1.11" } }, "minimist": { @@ -5173,8 +5758,8 @@ "integrity": "sha512-8ZItLHeEgaqEvd5lYBXfm4EZSFCX29Jb9K+lAHhDKzReKBQKj3R+7NOF6tjqYi9t4oI8VUfaWITJQm86wnXGNQ==", "dev": true, "requires": { - "for-in": "^1.0.2", - "is-extendable": "^1.0.1" + "for-in": "1.0.2", + "is-extendable": "1.0.1" }, "dependencies": { "is-extendable": { @@ -5183,7 +5768,7 @@ "integrity": "sha512-arnXMxT1hhoKo9k1LZdmlNyJdDDfy2v0fXjFlmok4+i8ul/6WlbVge9bhM74OpNPQPMGUToDtz+KXa1PneJxOA==", "dev": true, "requires": { - "is-plain-object": "^2.0.4" + "is-plain-object": "2.0.4" } } } @@ -5196,6 +5781,15 @@ "minimist": "0.0.8" } }, + "mkdirp-promise": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/mkdirp-promise/-/mkdirp-promise-5.0.1.tgz", + "integrity": "sha1-6bj2jlUsaKnBcTuEiD96HdA5uKE=", + "dev": true, + "requires": { + "mkdirp": "0.5.1" + } + }, "mocha": { "version": "4.1.0", "resolved": "https://registry.npmjs.org/mocha/-/mocha-4.1.0.tgz", @@ -5226,12 +5820,12 @@ "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz", "integrity": "sha512-MJTUg1kjuLeQCJ+ccE4Vpa6kKVXkPYJ2mOCQyUuKLcLQsdrMCpBPUi8qVE6+YuaJkozeA9NusTAw3hLr8Xe5EQ==", "requires": { - "fs.realpath": "^1.0.0", - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "^3.0.4", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" + "fs.realpath": "1.0.0", + "inflight": "1.0.6", + "inherits": "2.0.3", + "minimatch": "3.0.4", + "once": "1.4.0", + "path-is-absolute": "1.0.1" } }, "growl": { @@ -5249,11 +5843,23 @@ "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-4.4.0.tgz", "integrity": "sha512-rKC3+DyXWgK0ZLKwmRsrkyHVZAjNkfzeehuFWdGGcqGDTZFH73+RH6S/RDAAxl9GusSjZSUWYLmT9N5pzXFOXQ==", "requires": { - "has-flag": "^2.0.0" + "has-flag": "2.0.0" } } } }, + "mock-fs": { + "version": "4.7.0", + "resolved": "https://registry.npmjs.org/mock-fs/-/mock-fs-4.7.0.tgz", + "integrity": "sha512-WlQNtUlzMRpvLHf8dqeUmNqfdPjGY29KrJF50Ldb4AcL+vQeR8QH3wQcFMgrhTwb1gHjZn9xggho+84tBskLgA==", + "dev": true + }, + "mout": { + "version": "0.11.1", + "resolved": "https://registry.npmjs.org/mout/-/mout-0.11.1.tgz", + "integrity": "sha1-ujYR318OWx/7/QEWa48C0fX6K5k=", + "dev": true + }, "ms": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", @@ -5264,10 +5870,10 @@ "resolved": "https://registry.npmjs.org/multimatch/-/multimatch-2.1.0.tgz", "integrity": "sha1-nHkGoi+0wCkZ4vX3UWG0zb1LKis=", "requires": { - "array-differ": "^1.0.0", - "array-union": "^1.0.1", - "arrify": "^1.0.0", - "minimatch": "^3.0.0" + "array-differ": "1.0.0", + "array-union": "1.0.2", + "arrify": "1.0.1", + "minimatch": "3.0.4" } }, "mute-stream": { @@ -5275,6 +5881,17 @@ "resolved": "https://registry.npmjs.org/mute-stream/-/mute-stream-0.0.7.tgz", "integrity": "sha1-MHXOk7whuPq0PhvE2n6BFe0ee6s=" }, + "mz": { + "version": "2.7.0", + "resolved": "https://registry.npmjs.org/mz/-/mz-2.7.0.tgz", + "integrity": "sha512-z81GNO7nnYMEhrGh9LeymoE4+Yr0Wn5McHIZMK5cfQCl+NDX08sCZgUc9/6MHni9IWuFLm1Z3HTCXu2z9fN62Q==", + "dev": true, + "requires": { + "any-promise": "1.3.0", + "object-assign": "4.1.1", + "thenify-all": "1.6.0" + } + }, "nan": { "version": "2.10.0", "resolved": "https://registry.npmjs.org/nan/-/nan-2.10.0.tgz", @@ -5291,18 +5908,18 @@ "integrity": "sha512-n8R9bS8yQ6eSXaV6jHUpKzD8gLsin02w1HSFiegwrs9E098Ylhw5jdyKPaYqvHknHaSCKTPp7C8dGCQ0q9koXA==", "dev": true, "requires": { - "arr-diff": "^4.0.0", - "array-unique": "^0.3.2", - "define-property": "^2.0.2", - "extend-shallow": "^3.0.2", - "fragment-cache": "^0.2.1", - "is-odd": "^2.0.0", - "is-windows": "^1.0.2", - "kind-of": "^6.0.2", - "object.pick": "^1.3.0", - "regex-not": "^1.0.0", - "snapdragon": "^0.8.1", - "to-regex": "^3.0.1" + "arr-diff": "4.0.0", + "array-unique": "0.3.2", + "define-property": "2.0.2", + "extend-shallow": "3.0.2", + "fragment-cache": "0.2.1", + "is-odd": "2.0.0", + "is-windows": "1.0.2", + "kind-of": "6.0.2", + "object.pick": "1.3.0", + "regex-not": "1.0.2", + "snapdragon": "0.8.2", + "to-regex": "3.0.2" } }, "negotiator": { @@ -5331,16 +5948,16 @@ "integrity": "sha512-8AtS+wA5u6qoE12LONjqOzUzxAI5ObzSw6U5LgqpaO/0y6wwId4l5dN0ZulYyYdpLZD1MbkBp7GjG1hqaoRqYg==", "dev": true, "requires": { - "chokidar": "^2.0.2", - "debug": "^3.1.0", - "ignore-by-default": "^1.0.1", - "minimatch": "^3.0.4", - "pstree.remy": "^1.1.0", - "semver": "^5.5.0", - "supports-color": "^5.2.0", - "touch": "^3.1.0", - "undefsafe": "^2.0.2", - "update-notifier": "^2.3.0" + "chokidar": "2.0.3", + "debug": "3.1.0", + "ignore-by-default": "1.0.1", + "minimatch": "3.0.4", + "pstree.remy": "1.1.0", + "semver": "5.5.0", + "supports-color": "5.4.0", + "touch": "3.1.0", + "undefsafe": "2.0.2", + "update-notifier": "2.5.0" }, "dependencies": { "debug": { @@ -5364,7 +5981,7 @@ "integrity": "sha512-zjaXglF5nnWpsq470jSv6P9DwPvgLkuapYmfDm3JWOm0vkNTVF2tI4UrN2r6jH1qM/uc/WtxYY1hYoA2dOKj5w==", "dev": true, "requires": { - "has-flag": "^3.0.0" + "has-flag": "3.0.0" } } } @@ -5374,8 +5991,8 @@ "resolved": "https://registry.npmjs.org/nomnom/-/nomnom-1.8.1.tgz", "integrity": "sha1-IVH3Ikcrp55Qp2/BJbuMjy5Nwqc=", "requires": { - "chalk": "~0.4.0", - "underscore": "~1.6.0" + "chalk": "0.4.0", + "underscore": "1.6.0" }, "dependencies": { "ansi-styles": { @@ -5388,9 +6005,9 @@ "resolved": "https://registry.npmjs.org/chalk/-/chalk-0.4.0.tgz", "integrity": "sha1-UZmj3c0MHv4jvAjBsCewYXbgxk8=", "requires": { - "ansi-styles": "~1.0.0", - "has-color": "~0.1.0", - "strip-ansi": "~0.1.0" + "ansi-styles": "1.0.0", + "has-color": "0.1.7", + "strip-ansi": "0.1.1" } }, "strip-ansi": { @@ -5406,7 +6023,7 @@ "integrity": "sha1-bd0hvSoxQXuScn3Vhfim83YI6+4=", "dev": true, "requires": { - "abbrev": "1" + "abbrev": "1.1.1" } }, "normalize-package-data": { @@ -5414,10 +6031,10 @@ "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-2.4.0.tgz", "integrity": "sha512-9jjUFbTPfEy3R/ad/2oNbKtW9Hgovl5O1FvFWKkKblNXoN/Oou6+9+KKohPK13Yc3/TyunyWhJp6gvRNR/PPAw==", "requires": { - "hosted-git-info": "^2.1.4", - "is-builtin-module": "^1.0.0", - "semver": "2 || 3 || 4 || 5", - "validate-npm-package-license": "^3.0.1" + "hosted-git-info": "2.5.0", + "is-builtin-module": "1.0.0", + "semver": "5.5.0", + "validate-npm-package-license": "3.0.1" } }, "normalize-path": { @@ -5425,7 +6042,7 @@ "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-2.1.1.tgz", "integrity": "sha1-GrKLVW4Zg2Oowab35vogE3/mrtk=", "requires": { - "remove-trailing-separator": "^1.0.1" + "remove-trailing-separator": "1.1.0" } }, "normalize-url": { @@ -5433,9 +6050,9 @@ "resolved": "https://registry.npmjs.org/normalize-url/-/normalize-url-2.0.1.tgz", "integrity": "sha512-D6MUW4K/VzoJ4rJ01JFKxDrtY1v9wrgzCX5f2qj/lzH1m/lW6MhUZFKerVsnyjOhOsYzI9Kqqak+10l4LvLpMw==", "requires": { - "prepend-http": "^2.0.0", - "query-string": "^5.0.1", - "sort-keys": "^2.0.0" + "prepend-http": "2.0.0", + "query-string": "5.1.1", + "sort-keys": "2.0.0" }, "dependencies": { "prepend-http": { @@ -5450,7 +6067,7 @@ "resolved": "https://registry.npmjs.org/npm-run-path/-/npm-run-path-2.0.2.tgz", "integrity": "sha1-NakjLfo11wZ7TLLd8jV7GHFTbF8=", "requires": { - "path-key": "^2.0.0" + "path-key": "2.0.1" } }, "number-is-nan": { @@ -5483,9 +6100,9 @@ "integrity": "sha1-fn2Fi3gb18mRpBupde04EnVOmYw=", "dev": true, "requires": { - "copy-descriptor": "^0.1.0", - "define-property": "^0.2.5", - "kind-of": "^3.0.3" + "copy-descriptor": "0.1.1", + "define-property": "0.2.5", + "kind-of": "3.2.2" }, "dependencies": { "define-property": { @@ -5494,7 +6111,7 @@ "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", "dev": true, "requires": { - "is-descriptor": "^0.1.0" + "is-descriptor": "0.1.6" } }, "kind-of": { @@ -5503,7 +6120,7 @@ "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", "dev": true, "requires": { - "is-buffer": "^1.1.5" + "is-buffer": "1.1.6" } } } @@ -5514,7 +6131,7 @@ "integrity": "sha1-95xEk68MU3e1n+OdOV5BBC3QRbs=", "dev": true, "requires": { - "isobject": "^3.0.0" + "isobject": "3.0.1" } }, "object.omit": { @@ -5522,8 +6139,8 @@ "resolved": "https://registry.npmjs.org/object.omit/-/object.omit-2.0.1.tgz", "integrity": "sha1-Gpx0SCnznbuFjHbKNXmuKlTr0fo=", "requires": { - "for-own": "^0.1.4", - "is-extendable": "^0.1.1" + "for-own": "0.1.5", + "is-extendable": "0.1.1" } }, "object.pick": { @@ -5532,7 +6149,16 @@ "integrity": "sha1-h6EKxMFpS9Lhy/U1kaZhQftd10c=", "dev": true, "requires": { - "isobject": "^3.0.1" + "isobject": "3.0.1" + } + }, + "oboe": { + "version": "2.1.3", + "resolved": "https://registry.npmjs.org/oboe/-/oboe-2.1.3.tgz", + "integrity": "sha1-K0hl29Rr6BIlcT9Om/5Lz09oCk8=", + "dev": true, + "requires": { + "http-https": "1.0.0" } }, "on-finished": { @@ -5548,7 +6174,7 @@ "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", "requires": { - "wrappy": "1" + "wrappy": "1.0.2" } }, "onetime": { @@ -5556,7 +6182,7 @@ "resolved": "https://registry.npmjs.org/onetime/-/onetime-2.0.1.tgz", "integrity": "sha1-BnQoIw/WdEOyeUsiu6UotoZ5YtQ=", "requires": { - "mimic-fn": "^1.0.0" + "mimic-fn": "1.2.0" } }, "openzeppelin-solidity": { @@ -5570,8 +6196,8 @@ "integrity": "sha1-2j6nRob6IaGaERwybpDrFaAZZoY=", "dev": true, "requires": { - "minimist": "~0.0.1", - "wordwrap": "~0.0.2" + "minimist": "0.0.8", + "wordwrap": "0.0.3" }, "dependencies": { "wordwrap": { @@ -5588,12 +6214,12 @@ "integrity": "sha1-NkxeQJ0/TWMB1sC0wFu6UBgK62Q=", "dev": true, "requires": { - "deep-is": "~0.1.3", - "fast-levenshtein": "~2.0.4", - "levn": "~0.3.0", - "prelude-ls": "~1.1.2", - "type-check": "~0.3.2", - "wordwrap": "~1.0.0" + "deep-is": "0.1.3", + "fast-levenshtein": "2.0.6", + "levn": "0.3.0", + "prelude-ls": "1.1.2", + "type-check": "0.3.2", + "wordwrap": "1.0.0" } }, "ora": { @@ -5601,10 +6227,10 @@ "resolved": "https://registry.npmjs.org/ora/-/ora-0.2.3.tgz", "integrity": "sha1-N1J9Igrc1Tw5tzVx11QVbV22V6Q=", "requires": { - "chalk": "^1.1.1", - "cli-cursor": "^1.0.2", - "cli-spinners": "^0.1.2", - "object-assign": "^4.0.1" + "chalk": "1.1.3", + "cli-cursor": "1.0.2", + "cli-spinners": "0.1.2", + "object-assign": "4.1.1" }, "dependencies": { "ansi-styles": { @@ -5617,11 +6243,11 @@ "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz", "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=", "requires": { - "ansi-styles": "^2.2.1", - "escape-string-regexp": "^1.0.2", - "has-ansi": "^2.0.0", - "strip-ansi": "^3.0.0", - "supports-color": "^2.0.0" + "ansi-styles": "2.2.1", + "escape-string-regexp": "1.0.5", + "has-ansi": "2.0.0", + "strip-ansi": "3.0.1", + "supports-color": "2.0.0" } }, "cli-cursor": { @@ -5629,7 +6255,7 @@ "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-1.0.2.tgz", "integrity": "sha1-ZNo/fValRBLll5S9Ytw1KV6PKYc=", "requires": { - "restore-cursor": "^1.0.1" + "restore-cursor": "1.0.1" } }, "onetime": { @@ -5642,8 +6268,8 @@ "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-1.0.1.tgz", "integrity": "sha1-NGYfRohjJ/7SmRR5FSJS35LapUE=", "requires": { - "exit-hook": "^1.0.0", - "onetime": "^1.0.0" + "exit-hook": "1.1.1", + "onetime": "1.1.0" } }, "supports-color": { @@ -5668,7 +6294,7 @@ "resolved": "https://registry.npmjs.org/os-locale/-/os-locale-1.4.0.tgz", "integrity": "sha1-IPnxeuKe00XoveWDsT0gCYA8FNk=", "requires": { - "lcid": "^1.0.0" + "lcid": "1.0.0" } }, "os-tmpdir": { @@ -5686,7 +6312,7 @@ "resolved": "https://registry.npmjs.org/p-each-series/-/p-each-series-1.0.0.tgz", "integrity": "sha1-kw89Et0fUOdDRFeiLNbwSsatf3E=", "requires": { - "p-reduce": "^1.0.0" + "p-reduce": "1.0.0" } }, "p-finally": { @@ -5709,7 +6335,7 @@ "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-1.2.0.tgz", "integrity": "sha512-Y/OtIaXtUPr4/YpMv1pCL5L5ed0rumAaAeBSj12F+bSlMdys7i8oQF/GUJmfpTS/QoaRrS/k6pma29haJpsMng==", "requires": { - "p-try": "^1.0.0" + "p-try": "1.0.0" } }, "p-locate": { @@ -5717,7 +6343,7 @@ "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-2.0.0.tgz", "integrity": "sha1-IKAQOyIqcMj9OcwuWAaA893l7EM=", "requires": { - "p-limit": "^1.1.0" + "p-limit": "1.2.0" } }, "p-map": { @@ -5735,7 +6361,7 @@ "resolved": "https://registry.npmjs.org/p-timeout/-/p-timeout-2.0.1.tgz", "integrity": "sha512-88em58dDVB/KzPEx1X0N3LwFfYZPyDc4B6eF38M1rk9VTZMbxXXgjugz8mmwpS9Ox4BDZ+t6t3QP5+/gazweIA==", "requires": { - "p-finally": "^1.0.0" + "p-finally": "1.0.0" } }, "p-try": { @@ -5749,10 +6375,23 @@ "integrity": "sha1-iGmgQBJTZhxMTKPabCEh7VVfXu0=", "dev": true, "requires": { - "got": "^6.7.1", - "registry-auth-token": "^3.0.1", - "registry-url": "^3.0.3", - "semver": "^5.1.0" + "got": "6.7.1", + "registry-auth-token": "3.3.2", + "registry-url": "3.1.0", + "semver": "5.5.0" + } + }, + "parse-asn1": { + "version": "5.1.1", + "resolved": "http://registry.npmjs.org/parse-asn1/-/parse-asn1-5.1.1.tgz", + "integrity": "sha512-KPx7flKXg775zZpnp9SxJlz00gTd4BmJ2yJufSc44gMCRrRQ7NSzAcSJQfifuOLgW6bEi+ftrALtsgALeB2Adw==", + "dev": true, + "requires": { + "asn1.js": "4.10.1", + "browserify-aes": "1.2.0", + "create-hash": "1.2.0", + "evp_bytestokey": "1.0.3", + "pbkdf2": "3.0.17" } }, "parse-cache-control": { @@ -5766,10 +6405,10 @@ "resolved": "https://registry.npmjs.org/parse-glob/-/parse-glob-3.0.4.tgz", "integrity": "sha1-ssN2z7EfNVE7rdFz7wu246OIORw=", "requires": { - "glob-base": "^0.3.0", - "is-dotfile": "^1.0.0", - "is-extglob": "^1.0.0", - "is-glob": "^2.0.0" + "glob-base": "0.3.0", + "is-dotfile": "1.0.3", + "is-extglob": "1.0.0", + "is-glob": "2.0.1" }, "dependencies": { "is-extglob": { @@ -5782,7 +6421,7 @@ "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-2.0.1.tgz", "integrity": "sha1-0Jb5JqPe1WAPP9/ZEZjLCIjC2GM=", "requires": { - "is-extglob": "^1.0.0" + "is-extglob": "1.0.0" } } } @@ -5792,7 +6431,7 @@ "resolved": "https://registry.npmjs.org/parse-headers/-/parse-headers-2.0.1.tgz", "integrity": "sha1-aug6eqJanZtwCswoaYzR8e1+lTY=", "requires": { - "for-each": "^0.3.2", + "for-each": "0.3.2", "trim": "0.0.1" } }, @@ -5801,7 +6440,7 @@ "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-2.2.0.tgz", "integrity": "sha1-9ID0BDTvgHQfhGkJn43qGPVaTck=", "requires": { - "error-ex": "^1.2.0" + "error-ex": "1.3.1" } }, "parse-passwd": { @@ -5831,7 +6470,7 @@ "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-2.1.0.tgz", "integrity": "sha1-D+tsZPD8UY2adU3V77YscCJ2H0s=", "requires": { - "pinkie-promise": "^2.0.0" + "pinkie-promise": "2.0.1" } }, "path-is-absolute": { @@ -5865,9 +6504,9 @@ "resolved": "https://registry.npmjs.org/path-type/-/path-type-1.1.0.tgz", "integrity": "sha1-WcRPfuSR2nBNpBXaWkBwuk+P5EE=", "requires": { - "graceful-fs": "^4.1.2", - "pify": "^2.0.0", - "pinkie-promise": "^2.0.0" + "graceful-fs": "4.1.11", + "pify": "2.3.0", + "pinkie-promise": "2.0.1" } }, "pathval": { @@ -5882,7 +6521,20 @@ "integrity": "sha1-/lo0sMvOErWqaitAPuLnO2AvFEU=", "dev": true, "requires": { - "through": "~2.3" + "through": "2.3.8" + } + }, + "pbkdf2": { + "version": "3.0.17", + "resolved": "https://registry.npmjs.org/pbkdf2/-/pbkdf2-3.0.17.tgz", + "integrity": "sha512-U/il5MsrZp7mGg3mSQfn742na2T+1/vHDCG5/iTI3X9MKUuYUZVLQhyRsg06mCgDBTd57TxzgZt7P+fYfjRLtA==", + "dev": true, + "requires": { + "create-hash": "1.2.0", + "create-hmac": "1.1.7", + "ripemd160": "2.0.2", + "safe-buffer": "5.1.1", + "sha.js": "2.4.11" } }, "pegjs": { @@ -5891,6 +6543,12 @@ "integrity": "sha1-z4uvrm7d/0tafvsYUmnqr0YQ3b0=", "dev": true }, + "pend": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/pend/-/pend-1.2.0.tgz", + "integrity": "sha1-elfrVQpng/kRUzH89GY9XI4AelA=", + "dev": true + }, "performance-now": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/performance-now/-/performance-now-2.1.0.tgz", @@ -5911,7 +6569,7 @@ "resolved": "https://registry.npmjs.org/pinkie-promise/-/pinkie-promise-2.0.1.tgz", "integrity": "sha1-ITXW36ejWMBprJsXh3YogihFD/o=", "requires": { - "pinkie": "^2.0.0" + "pinkie": "2.0.4" } }, "posix-character-classes": { @@ -5967,7 +6625,7 @@ "integrity": "sha512-EIyzM39FpVOMbqgzEHhxdrEhtOSDOtjMZQ0M6iVfCE+kWNgCkAyOdnuCWqfmflylftfadU6FkiMgHZA2kUzwRw==", "dev": true, "requires": { - "asap": "~2.0.6" + "asap": "2.0.6" } }, "proxy-addr": { @@ -5975,7 +6633,7 @@ "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.3.tgz", "integrity": "sha512-jQTChiCJteusULxjBp8+jftSQE5Obdl3k4cnmLA6WXtK6XFuWRnvVL7aCiBqaLPM8c4ph0S4tKna8XvmIwEnXQ==", "requires": { - "forwarded": "~0.1.2", + "forwarded": "0.1.2", "ipaddr.js": "1.6.0" } }, @@ -5990,7 +6648,7 @@ "integrity": "sha1-tCGyQUDWID8e08dplrRCewjowBQ=", "dev": true, "requires": { - "event-stream": "~3.3.0" + "event-stream": "3.3.4" } }, "pseudomap": { @@ -6004,7 +6662,29 @@ "integrity": "sha512-q5I5vLRMVtdWa8n/3UEzZX7Lfghzrg9eG2IKk2ENLSofKRCXVqMvMUHxCKgXNaqH/8ebhBxrqftHWnyTFweJ5Q==", "dev": true, "requires": { - "ps-tree": "^1.1.0" + "ps-tree": "1.1.0" + } + }, + "public-encrypt": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/public-encrypt/-/public-encrypt-4.0.3.tgz", + "integrity": "sha512-zVpa8oKZSz5bTMTFClc1fQOnyyEzpl5ozpi1B5YcvBrdohMjH2rfsBtyXcuNuwjsDIXmBYlF2N5FlJYhR29t8Q==", + "dev": true, + "requires": { + "bn.js": "4.11.6", + "browserify-rsa": "4.0.1", + "create-hash": "1.2.0", + "parse-asn1": "5.1.1", + "randombytes": "2.0.6", + "safe-buffer": "5.1.2" + }, + "dependencies": { + "safe-buffer": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", + "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", + "dev": true + } } }, "punycode": { @@ -6022,9 +6702,9 @@ "resolved": "https://registry.npmjs.org/query-string/-/query-string-5.1.1.tgz", "integrity": "sha512-gjWOsm2SoGlgLEdAGt7a6slVOk9mGiXmPFMqrEhLQ68rhQuBnpfs3+EmlvqKyxnCo9/PPlF+9MtY02S1aFg+Jw==", "requires": { - "decode-uri-component": "^0.2.0", - "object-assign": "^4.1.0", - "strict-uri-encode": "^1.0.0" + "decode-uri-component": "0.2.0", + "object-assign": "4.1.1", + "strict-uri-encode": "1.1.0" } }, "randomatic": { @@ -6032,8 +6712,8 @@ "resolved": "https://registry.npmjs.org/randomatic/-/randomatic-1.1.7.tgz", "integrity": "sha512-D5JUjPyJbaJDkuAazpVnSfVkLlpeO3wDlPROTMLGKG1zMFNFRgrciKo1ltz/AzNTkqE0HzDx655QOL51N06how==", "requires": { - "is-number": "^3.0.0", - "kind-of": "^4.0.0" + "is-number": "3.0.0", + "kind-of": "4.0.0" }, "dependencies": { "kind-of": { @@ -6041,11 +6721,30 @@ "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-4.0.0.tgz", "integrity": "sha1-IIE989cSkosgc3hpGkUGb65y3Vc=", "requires": { - "is-buffer": "^1.1.5" + "is-buffer": "1.1.6" } } } }, + "randombytes": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/randombytes/-/randombytes-2.0.6.tgz", + "integrity": "sha512-CIQ5OFxf4Jou6uOKe9t1AOgqpeU5fd70A8NPdHSGeYXqXsPe6peOwI0cUl88RWZ6sP1vPMV3avd/R6cZ5/sP1A==", + "dev": true, + "requires": { + "safe-buffer": "5.1.1" + } + }, + "randomfill": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/randomfill/-/randomfill-1.0.4.tgz", + "integrity": "sha512-87lcbR8+MhcWcUiQ+9e+Rwx8MyR2P7qnt15ynUlbm3TU/fjbgz4GsvfSUDTemtCCtVCqb4ZcEFlyPNTh9bBTLw==", + "dev": true, + "requires": { + "randombytes": "2.0.6", + "safe-buffer": "5.1.1" + } + }, "randomhex": { "version": "0.1.5", "resolved": "https://registry.npmjs.org/randomhex/-/randomhex-0.1.5.tgz", @@ -6080,7 +6779,7 @@ "depd": "1.1.1", "inherits": "2.0.3", "setprototypeof": "1.0.3", - "statuses": ">= 1.3.1 < 2" + "statuses": "1.5.0" } }, "setprototypeof": { @@ -6096,10 +6795,10 @@ "integrity": "sha1-6xiYnG1PTxYsOZ953dKfODVWgJI=", "dev": true, "requires": { - "deep-extend": "~0.4.0", - "ini": "~1.3.0", - "minimist": "^1.2.0", - "strip-json-comments": "~2.0.1" + "deep-extend": "0.4.2", + "ini": "1.3.5", + "minimist": "1.2.0", + "strip-json-comments": "2.0.1" }, "dependencies": { "minimist": { @@ -6115,8 +6814,8 @@ "resolved": "https://registry.npmjs.org/read-chunk/-/read-chunk-2.1.0.tgz", "integrity": "sha1-agTAkoAF7Z1C4aasVgDhnLx/9lU=", "requires": { - "pify": "^3.0.0", - "safe-buffer": "^5.1.1" + "pify": "3.0.0", + "safe-buffer": "5.1.1" }, "dependencies": { "pify": { @@ -6131,9 +6830,9 @@ "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-1.1.0.tgz", "integrity": "sha1-9f+qXs0pyzHAR0vKfXVra7KePyg=", "requires": { - "load-json-file": "^1.0.0", - "normalize-package-data": "^2.3.2", - "path-type": "^1.0.0" + "load-json-file": "1.1.0", + "normalize-package-data": "2.4.0", + "path-type": "1.1.0" } }, "read-pkg-up": { @@ -6141,8 +6840,8 @@ "resolved": "https://registry.npmjs.org/read-pkg-up/-/read-pkg-up-1.0.1.tgz", "integrity": "sha1-nWPBMnbAZZGNV/ACpX9AobZD+wI=", "requires": { - "find-up": "^1.0.0", - "read-pkg": "^1.0.0" + "find-up": "1.1.2", + "read-pkg": "1.1.0" } }, "readable-stream": { @@ -6150,13 +6849,13 @@ "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.5.tgz", "integrity": "sha512-tK0yDhrkygt/knjowCUiWP9YdV7c5R+8cR0r/kt9ZhBU906Fs6RpQJCEilamRJj1Nx2rWI6LkW9gKqjTkshhEw==", "requires": { - "core-util-is": "~1.0.0", - "inherits": "~2.0.3", - "isarray": "~1.0.0", - "process-nextick-args": "~2.0.0", - "safe-buffer": "~5.1.1", - "string_decoder": "~1.0.3", - "util-deprecate": "~1.0.1" + "core-util-is": "1.0.2", + "inherits": "2.0.3", + "isarray": "1.0.0", + "process-nextick-args": "2.0.0", + "safe-buffer": "5.1.1", + "string_decoder": "1.0.3", + "util-deprecate": "1.0.2" } }, "readdirp": { @@ -6165,10 +6864,10 @@ "integrity": "sha1-TtCtBg3zBzMAxIRANz9y0cxkLXg=", "dev": true, "requires": { - "graceful-fs": "^4.1.2", - "minimatch": "^3.0.2", - "readable-stream": "^2.0.2", - "set-immediate-shim": "^1.0.1" + "graceful-fs": "4.1.11", + "minimatch": "3.0.4", + "readable-stream": "2.3.5", + "set-immediate-shim": "1.0.1" } }, "recast": { @@ -6177,9 +6876,9 @@ "integrity": "sha512-/nwm9pkrcWagN40JeJhkPaRxiHXBRkXyRh/hgU088Z/v+qCy+zIHHY6bC6o7NaKAxPqtE6nD8zBH1LfU0/Wx6A==", "requires": { "ast-types": "0.11.3", - "esprima": "~4.0.0", - "private": "~0.1.5", - "source-map": "~0.6.1" + "esprima": "4.0.0", + "private": "0.1.8", + "source-map": "0.6.1" }, "dependencies": { "source-map": { @@ -6194,7 +6893,7 @@ "resolved": "https://registry.npmjs.org/rechoir/-/rechoir-0.6.2.tgz", "integrity": "sha1-hSBLVNuoLVdC4oyWdW70OvUOM4Q=", "requires": { - "resolve": "^1.1.6" + "resolve": "1.6.0" } }, "regenerate": { @@ -6212,9 +6911,9 @@ "resolved": "https://registry.npmjs.org/regenerator-transform/-/regenerator-transform-0.10.1.tgz", "integrity": "sha512-PJepbvDbuK1xgIgnau7Y90cwaAmO/LCLMI2mPvaXq2heGMR3aWW5/BQvYrhJ8jgmQjXewXvBjzfqKcVOmhjZ6Q==", "requires": { - "babel-runtime": "^6.18.0", - "babel-types": "^6.19.0", - "private": "^0.1.6" + "babel-runtime": "6.26.0", + "babel-types": "6.26.0", + "private": "0.1.8" } }, "regex-cache": { @@ -6222,7 +6921,7 @@ "resolved": "https://registry.npmjs.org/regex-cache/-/regex-cache-0.4.4.tgz", "integrity": "sha512-nVIZwtCjkC9YgvWkpM55B5rBhBYRZhAaJbgcFYXXsHnbZ9UZI9nnVWYZpBlCqv9ho2eZryPnWrZGsOdPwVWXWQ==", "requires": { - "is-equal-shallow": "^0.1.3" + "is-equal-shallow": "0.1.3" } }, "regex-not": { @@ -6231,8 +6930,8 @@ "integrity": "sha512-J6SDjUgDxQj5NusnOtdFxDwN/+HWykR8GELwctJ7mdqhcyy1xEc4SRFHUXvxTp661YaVKAjfRLZ9cCqS6tn32A==", "dev": true, "requires": { - "extend-shallow": "^3.0.2", - "safe-regex": "^1.1.0" + "extend-shallow": "3.0.2", + "safe-regex": "1.1.0" } }, "regexpu-core": { @@ -6240,9 +6939,9 @@ "resolved": "https://registry.npmjs.org/regexpu-core/-/regexpu-core-2.0.0.tgz", "integrity": "sha1-SdA4g3uNz4v6W5pCE5k45uoq4kA=", "requires": { - "regenerate": "^1.2.1", - "regjsgen": "^0.2.0", - "regjsparser": "^0.1.4" + "regenerate": "1.3.3", + "regjsgen": "0.2.0", + "regjsparser": "0.1.5" } }, "registry-auth-token": { @@ -6251,8 +6950,8 @@ "integrity": "sha512-JL39c60XlzCVgNrO+qq68FoNb56w/m7JYvGR2jT5iR1xBrUA3Mfx5Twk5rqTThPmQKMWydGmq8oFtDlxfrmxnQ==", "dev": true, "requires": { - "rc": "^1.1.6", - "safe-buffer": "^5.0.1" + "rc": "1.2.6", + "safe-buffer": "5.1.1" } }, "registry-url": { @@ -6261,7 +6960,7 @@ "integrity": "sha1-PU74cPc93h138M+aOBQyRE4XSUI=", "dev": true, "requires": { - "rc": "^1.0.1" + "rc": "1.2.6" } }, "regjsgen": { @@ -6274,7 +6973,7 @@ "resolved": "https://registry.npmjs.org/regjsparser/-/regjsparser-0.1.5.tgz", "integrity": "sha1-fuj4Tcb6eS0/0K4ijSS9lJ6tIFw=", "requires": { - "jsesc": "~0.5.0" + "jsesc": "0.5.0" } }, "remove-trailing-separator": { @@ -6297,7 +6996,7 @@ "resolved": "https://registry.npmjs.org/repeating/-/repeating-2.0.1.tgz", "integrity": "sha1-UhTFOpJtNVJwdSf7q0FdvAjQbdo=", "requires": { - "is-finite": "^1.0.0" + "is-finite": "1.0.2" } }, "replace-ext": { @@ -6311,7 +7010,7 @@ "integrity": "sha1-DXOurpJm5penj3l2AZZ352rPD/8=", "dev": true, "requires": { - "req-from": "^1.0.1" + "req-from": "1.0.1" } }, "req-from": { @@ -6320,7 +7019,7 @@ "integrity": "sha1-v4HaUUeUfTLRO5R9wSpYrUWHNQ4=", "dev": true, "requires": { - "resolve-from": "^2.0.0" + "resolve-from": "2.0.0" }, "dependencies": { "resolve-from": { @@ -6336,28 +7035,28 @@ "resolved": "https://registry.npmjs.org/request/-/request-2.85.0.tgz", "integrity": "sha512-8H7Ehijd4js+s6wuVPLjwORxD4zeuyjYugprdOXlPSqaApmL/QOy+EB/beICHVCHkGMKNh5rvihb5ov+IDw4mg==", "requires": { - "aws-sign2": "~0.7.0", - "aws4": "^1.6.0", - "caseless": "~0.12.0", - "combined-stream": "~1.0.5", - "extend": "~3.0.1", - "forever-agent": "~0.6.1", - "form-data": "~2.3.1", - "har-validator": "~5.0.3", - "hawk": "~6.0.2", - "http-signature": "~1.2.0", - "is-typedarray": "~1.0.0", - "isstream": "~0.1.2", - "json-stringify-safe": "~5.0.1", - "mime-types": "~2.1.17", - "oauth-sign": "~0.8.2", - "performance-now": "^2.1.0", - "qs": "~6.5.1", - "safe-buffer": "^5.1.1", - "stringstream": "~0.0.5", - "tough-cookie": "~2.3.3", - "tunnel-agent": "^0.6.0", - "uuid": "^3.1.0" + "aws-sign2": "0.7.0", + "aws4": "1.7.0", + "caseless": "0.12.0", + "combined-stream": "1.0.6", + "extend": "3.0.1", + "forever-agent": "0.6.1", + "form-data": "2.3.2", + "har-validator": "5.0.3", + "hawk": "6.0.2", + "http-signature": "1.2.0", + "is-typedarray": "1.0.0", + "isstream": "0.1.2", + "json-stringify-safe": "5.0.1", + "mime-types": "2.1.18", + "oauth-sign": "0.8.2", + "performance-now": "2.1.0", + "qs": "6.5.1", + "safe-buffer": "5.1.1", + "stringstream": "0.0.5", + "tough-cookie": "2.3.4", + "tunnel-agent": "0.6.0", + "uuid": "3.2.1" } }, "request-promise-core": { @@ -6366,7 +7065,7 @@ "integrity": "sha1-Pu4AssWqgyOc+wTFcA2jb4HNCLY=", "dev": true, "requires": { - "lodash": "^4.13.1" + "lodash": "4.17.5" } }, "request-promise-native": { @@ -6376,8 +7075,8 @@ "dev": true, "requires": { "request-promise-core": "1.1.1", - "stealthy-require": "^1.1.0", - "tough-cookie": ">=2.3.3" + "stealthy-require": "1.1.1", + "tough-cookie": "2.3.4" } }, "require-directory": { @@ -6400,7 +7099,7 @@ "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.6.0.tgz", "integrity": "sha512-mw7JQNu5ExIkcw4LPih0owX/TZXjD/ZUF/ZQ/pDnkw3ZKhDcZZw5klmBlj6gVMwjQ3Pz5Jgu7F3d0jcDVuEWdw==", "requires": { - "path-parse": "^1.0.5" + "path-parse": "1.0.5" } }, "resolve-cwd": { @@ -6408,7 +7107,7 @@ "resolved": "https://registry.npmjs.org/resolve-cwd/-/resolve-cwd-2.0.0.tgz", "integrity": "sha1-AKn3OHVW4nA46uIyyqNypqWbZlo=", "requires": { - "resolve-from": "^3.0.0" + "resolve-from": "3.0.0" } }, "resolve-dir": { @@ -6416,8 +7115,8 @@ "resolved": "https://registry.npmjs.org/resolve-dir/-/resolve-dir-1.0.1.tgz", "integrity": "sha1-eaQGRMNivoLybv/nOcm7U4IEb0M=", "requires": { - "expand-tilde": "^2.0.0", - "global-modules": "^1.0.0" + "expand-tilde": "2.0.2", + "global-modules": "1.0.0" } }, "resolve-from": { @@ -6436,7 +7135,7 @@ "resolved": "https://registry.npmjs.org/responselike/-/responselike-1.0.2.tgz", "integrity": "sha1-kYcg7ztjHFZCvgaPFa3lpG9Loec=", "requires": { - "lowercase-keys": "^1.0.0" + "lowercase-keys": "1.0.0" } }, "restore-cursor": { @@ -6444,8 +7143,8 @@ "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-2.0.0.tgz", "integrity": "sha1-n37ih/gv0ybU/RYpI9YhKe7g368=", "requires": { - "onetime": "^2.0.0", - "signal-exit": "^3.0.2" + "onetime": "2.0.1", + "signal-exit": "3.0.2" } }, "ret": { @@ -6461,7 +7160,7 @@ "dev": true, "optional": true, "requires": { - "align-text": "^0.1.1" + "align-text": "0.1.4" } }, "rimraf": { @@ -6469,7 +7168,17 @@ "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.6.2.tgz", "integrity": "sha512-lreewLK/BlghmxtfH36YYVg1i8IAce4TI7oao75I1g245+6BctqTVQiBP3YUJ9C6DQOXJmkYR9X9fCLtCOJc5w==", "requires": { - "glob": "^7.0.5" + "glob": "7.1.1" + } + }, + "ripemd160": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/ripemd160/-/ripemd160-2.0.2.tgz", + "integrity": "sha512-ii4iagi25WusVoiC4B4lq7pbXfAp3D9v5CwfkY33vffw2+pkDjY1D8GaN7spsxvCSx8dkPqOZCEZyfxcmJG2IA==", + "dev": true, + "requires": { + "hash-base": "3.0.4", + "inherits": "2.0.3" } }, "run-async": { @@ -6477,7 +7186,7 @@ "resolved": "https://registry.npmjs.org/run-async/-/run-async-2.3.0.tgz", "integrity": "sha1-A3GrSuC91yDUFm19/aZP96RFpsA=", "requires": { - "is-promise": "^2.1.0" + "is-promise": "2.1.0" } }, "rx-lite": { @@ -6490,7 +7199,7 @@ "resolved": "https://registry.npmjs.org/rx-lite-aggregates/-/rx-lite-aggregates-4.0.8.tgz", "integrity": "sha1-dTuHqJoRyVRnxKwWJsTvxOBcZ74=", "requires": { - "rx-lite": "*" + "rx-lite": "4.0.8" } }, "rxjs": { @@ -6512,7 +7221,7 @@ "integrity": "sha1-QKNmnzsHfR6UPURinhV91IAjvy4=", "dev": true, "requires": { - "ret": "~0.1.10" + "ret": "0.1.15" } }, "scoped-regex": { @@ -6520,6 +7229,60 @@ "resolved": "https://registry.npmjs.org/scoped-regex/-/scoped-regex-1.0.0.tgz", "integrity": "sha1-o0a7Gs1CB65wvXwMfKnlZra63bg=" }, + "scrypt": { + "version": "6.0.3", + "resolved": "https://registry.npmjs.org/scrypt/-/scrypt-6.0.3.tgz", + "integrity": "sha1-BOAUpWgrU/pQwtXM4WfXGcBthw0=", + "dev": true, + "requires": { + "nan": "2.10.0" + } + }, + "scrypt-js": { + "version": "2.0.3", + "resolved": "http://registry.npmjs.org/scrypt-js/-/scrypt-js-2.0.3.tgz", + "integrity": "sha1-uwBAvgMEPamgEqLOqfyfhSz8h9Q=", + "dev": true + }, + "scrypt.js": { + "version": "0.2.0", + "resolved": "http://registry.npmjs.org/scrypt.js/-/scrypt.js-0.2.0.tgz", + "integrity": "sha1-r40UZbcemZARC+38WTuUeeA6ito=", + "dev": true, + "requires": { + "scrypt": "6.0.3", + "scryptsy": "1.2.1" + } + }, + "scryptsy": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/scryptsy/-/scryptsy-1.2.1.tgz", + "integrity": "sha1-oyJfpLJST4AnAHYeKFW987LZIWM=", + "dev": true, + "requires": { + "pbkdf2": "3.0.17" + } + }, + "seek-bzip": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/seek-bzip/-/seek-bzip-1.0.5.tgz", + "integrity": "sha1-z+kXyz0nS8/6x5J1ivUxc+sfq9w=", + "dev": true, + "requires": { + "commander": "2.8.1" + }, + "dependencies": { + "commander": { + "version": "2.8.1", + "resolved": "http://registry.npmjs.org/commander/-/commander-2.8.1.tgz", + "integrity": "sha1-Br42f+v9oMMwqh4qBy09yXYkJdQ=", + "dev": true, + "requires": { + "graceful-readlink": "1.0.1" + } + } + } + }, "semver": { "version": "5.5.0", "resolved": "https://registry.npmjs.org/semver/-/semver-5.5.0.tgz", @@ -6531,7 +7294,7 @@ "integrity": "sha1-S7uEN8jTfksM8aaP1ybsbWRdbTY=", "dev": true, "requires": { - "semver": "^5.0.3" + "semver": "5.5.0" } }, "send": { @@ -6540,18 +7303,18 @@ "integrity": "sha512-E64YFPUssFHEFBvpbbjr44NCLtI1AohxQ8ZSiJjQLskAdKuriYEP6VyGEsRDH8ScozGpkaX1BGvhanqCwkcEZw==", "requires": { "debug": "2.6.9", - "depd": "~1.1.2", - "destroy": "~1.0.4", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "etag": "~1.8.1", + "depd": "1.1.2", + "destroy": "1.0.4", + "encodeurl": "1.0.2", + "escape-html": "1.0.3", + "etag": "1.8.1", "fresh": "0.5.2", - "http-errors": "~1.6.2", + "http-errors": "1.6.3", "mime": "1.4.1", "ms": "2.0.0", - "on-finished": "~2.3.0", - "range-parser": "~1.2.0", - "statuses": "~1.4.0" + "on-finished": "2.3.0", + "range-parser": "1.2.0", + "statuses": "1.4.0" }, "dependencies": { "debug": { @@ -6574,9 +7337,9 @@ "resolved": "https://registry.npmjs.org/serve-static/-/serve-static-1.13.2.tgz", "integrity": "sha512-p/tdJrO4U387R9oMjb1oj7qSMaMfmOyd4j9hOFoxZe2baQszgHcSWjuya/CiT5kgZZKRudHNOA0pYXOl8rQ5nw==", "requires": { - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "parseurl": "~1.3.2", + "encodeurl": "1.0.2", + "escape-html": "1.0.3", + "parseurl": "1.3.2", "send": "0.16.2" } }, @@ -6585,11 +7348,11 @@ "resolved": "https://registry.npmjs.org/servify/-/servify-0.1.12.tgz", "integrity": "sha512-/xE6GvsKKqyo1BAY+KxOWXcLpPsUUyji7Qg3bVD7hh1eRze5bR1uYiuDA/k3Gof1s9BTzQZEJK8sNcNGFIzeWw==", "requires": { - "body-parser": "^1.16.0", - "cors": "^2.8.1", - "express": "^4.14.0", - "request": "^2.79.0", - "xhr": "^2.3.3" + "body-parser": "1.18.2", + "cors": "2.8.4", + "express": "4.16.3", + "request": "2.85.0", + "xhr": "2.4.1" } }, "set-blocking": { @@ -6609,10 +7372,10 @@ "integrity": "sha512-hw0yxk9GT/Hr5yJEYnHNKYXkIA8mVJgd9ditYZCe16ZczcaELYYcfvaXesNACk2O8O0nTiPQcQhGUQj8JLzeeg==", "dev": true, "requires": { - "extend-shallow": "^2.0.1", - "is-extendable": "^0.1.1", - "is-plain-object": "^2.0.3", - "split-string": "^3.0.1" + "extend-shallow": "2.0.1", + "is-extendable": "0.1.1", + "is-plain-object": "2.0.4", + "split-string": "3.1.0" }, "dependencies": { "extend-shallow": { @@ -6621,24 +7384,40 @@ "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", "dev": true, "requires": { - "is-extendable": "^0.1.0" + "is-extendable": "0.1.1" } } } }, + "setimmediate": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/setimmediate/-/setimmediate-1.0.5.tgz", + "integrity": "sha1-KQy7Iy4waULX1+qbg3Mqt4VvgoU=", + "dev": true + }, "setprototypeof": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.1.0.tgz", "integrity": "sha512-BvE/TwpZX4FXExxOxZyRGQQv651MSwmWKZGqvmPcRIjDqWub67kTKuIMx43cZZrS/cBBzwBcNDWoFxt2XEFIpQ==" }, + "sha.js": { + "version": "2.4.11", + "resolved": "http://registry.npmjs.org/sha.js/-/sha.js-2.4.11.tgz", + "integrity": "sha512-QMEp5B7cftE7APOjk5Y6xgrbWu+WkLVQwk8JNjZ8nKRciZaByEW6MubieAiToS7+dwvrjGhH8jRXz3MVd0AYqQ==", + "dev": true, + "requires": { + "inherits": "2.0.3", + "safe-buffer": "5.1.1" + } + }, "sha1": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/sha1/-/sha1-1.1.1.tgz", "integrity": "sha1-rdqnqTFo85PxnrKxUJFhjicA+Eg=", "dev": true, "requires": { - "charenc": ">= 0.0.1", - "crypt": ">= 0.0.1" + "charenc": "0.0.2", + "crypt": "0.0.2" } }, "sha3": { @@ -6646,7 +7425,7 @@ "resolved": "https://registry.npmjs.org/sha3/-/sha3-1.2.0.tgz", "integrity": "sha1-aYnxtwpJhwWHajc+LGKs6WqpOZo=", "requires": { - "nan": "^2.0.5" + "nan": "2.10.0" } }, "shebang-command": { @@ -6654,7 +7433,7 @@ "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-1.2.0.tgz", "integrity": "sha1-RKrGW2lbAzmJaMOfNj/uXer98eo=", "requires": { - "shebang-regex": "^1.0.0" + "shebang-regex": "1.0.0" } }, "shebang-regex": { @@ -6667,9 +7446,9 @@ "resolved": "https://registry.npmjs.org/shelljs/-/shelljs-0.8.1.tgz", "integrity": "sha512-YA/iYtZpzFe5HyWVGrb02FjPxc4EMCfpoU/Phg9fQoyMC72u9598OUBrsU8IrtwAKG0tO8IYaqbaLIw+k3IRGA==", "requires": { - "glob": "^7.0.0", - "interpret": "^1.0.0", - "rechoir": "^0.6.2" + "glob": "7.1.1", + "interpret": "1.1.0", + "rechoir": "0.6.2" } }, "sigmund": { @@ -6693,9 +7472,9 @@ "resolved": "https://registry.npmjs.org/simple-get/-/simple-get-2.7.0.tgz", "integrity": "sha512-RkE9rGPHcxYZ/baYmgJtOSM63vH0Vyq+ma5TijBcLla41SWlh8t6XYIGMR/oeZcmr+/G8k+zrClkkVrtnQ0esg==", "requires": { - "decompress-response": "^3.3.0", - "once": "^1.3.1", - "simple-concat": "^1.0.0" + "decompress-response": "3.3.0", + "once": "1.4.0", + "simple-concat": "1.0.0" } }, "slash": { @@ -6719,14 +7498,14 @@ "integrity": "sha512-FtyOnWN/wCHTVXOMwvSv26d+ko5vWlIDD6zoUJ7LW8vh+ZBC8QdljveRP+crNrtBwioEUWy/4dMtbBjA4ioNlg==", "dev": true, "requires": { - "base": "^0.11.1", - "debug": "^2.2.0", - "define-property": "^0.2.5", - "extend-shallow": "^2.0.1", - "map-cache": "^0.2.2", - "source-map": "^0.5.6", - "source-map-resolve": "^0.5.0", - "use": "^3.1.0" + "base": "0.11.2", + "debug": "2.6.8", + "define-property": "0.2.5", + "extend-shallow": "2.0.1", + "map-cache": "0.2.2", + "source-map": "0.5.7", + "source-map-resolve": "0.5.1", + "use": "3.1.0" }, "dependencies": { "define-property": { @@ -6735,7 +7514,7 @@ "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", "dev": true, "requires": { - "is-descriptor": "^0.1.0" + "is-descriptor": "0.1.6" } }, "extend-shallow": { @@ -6744,7 +7523,7 @@ "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", "dev": true, "requires": { - "is-extendable": "^0.1.0" + "is-extendable": "0.1.1" } } } @@ -6755,9 +7534,9 @@ "integrity": "sha512-O27l4xaMYt/RSQ5TR3vpWCAB5Kb/czIcqUFOM/C4fYcLnbZUc1PkjTAMjof2pBWaSTwOUd6qUHcFGVGj7aIwnw==", "dev": true, "requires": { - "define-property": "^1.0.0", - "isobject": "^3.0.0", - "snapdragon-util": "^3.0.1" + "define-property": "1.0.0", + "isobject": "3.0.1", + "snapdragon-util": "3.0.1" }, "dependencies": { "define-property": { @@ -6766,7 +7545,7 @@ "integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=", "dev": true, "requires": { - "is-descriptor": "^1.0.0" + "is-descriptor": "1.0.2" } }, "is-accessor-descriptor": { @@ -6775,7 +7554,7 @@ "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", "dev": true, "requires": { - "kind-of": "^6.0.0" + "kind-of": "6.0.2" } }, "is-data-descriptor": { @@ -6784,7 +7563,7 @@ "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", "dev": true, "requires": { - "kind-of": "^6.0.0" + "kind-of": "6.0.2" } }, "is-descriptor": { @@ -6793,9 +7572,9 @@ "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", "dev": true, "requires": { - "is-accessor-descriptor": "^1.0.0", - "is-data-descriptor": "^1.0.0", - "kind-of": "^6.0.2" + "is-accessor-descriptor": "1.0.0", + "is-data-descriptor": "1.0.0", + "kind-of": "6.0.2" } } } @@ -6806,7 +7585,7 @@ "integrity": "sha512-mbKkMdQKsjX4BAL4bRYTj21edOf8cN7XHdYUJEe+Zn99hVEYcMvKPct1IqNe7+AZPirn8BCDOQBHQZknqmKlZQ==", "dev": true, "requires": { - "kind-of": "^3.2.0" + "kind-of": "3.2.2" }, "dependencies": { "kind-of": { @@ -6815,7 +7594,7 @@ "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", "dev": true, "requires": { - "is-buffer": "^1.1.5" + "is-buffer": "1.1.6" } } } @@ -6825,7 +7604,7 @@ "resolved": "https://registry.npmjs.org/sntp/-/sntp-2.1.0.tgz", "integrity": "sha512-FL1b58BDrqS3A11lJ0zEdnJ3UOKqVxawAkF3k7F0CVN7VQ34aZrV+G8BZ1WC9ZL7NyrwsW0oviwsWDgRuVYtJg==", "requires": { - "hoek": "4.x.x" + "hoek": "4.2.1" } }, "sol-explore": { @@ -6839,11 +7618,11 @@ "resolved": "https://registry.npmjs.org/solc/-/solc-0.4.24.tgz", "integrity": "sha512-2xd7Cf1HeVwrIb6Bu1cwY2/TaLRodrppCq3l7rhLimFQgmxptXhTC3+/wesVLpB09F1A2kZgvbMOgH7wvhFnBQ==", "requires": { - "fs-extra": "^0.30.0", - "memorystream": "^0.3.1", - "require-from-string": "^1.1.0", - "semver": "^5.3.0", - "yargs": "^4.7.1" + "fs-extra": "0.30.0", + "memorystream": "0.3.1", + "require-from-string": "1.2.1", + "semver": "5.5.0", + "yargs": "4.8.1" } }, "solidity-coverage": { @@ -6852,20 +7631,19 @@ "integrity": "sha512-iA3MT20rh1LllcNwfxAKU3ZBDu8R/4K8jANJAk7BcJU1foOjEh3tYhGqL8w2kRJPIo5XtoW0wxyVt95X2eJk/A==", "dev": true, "requires": { - "death": "^1.1.0", + "death": "1.1.0", "ethereumjs-testrpc-sc": "6.1.2", - "istanbul": "^0.4.5", - "keccakjs": "^0.2.1", - "req-cwd": "^1.0.1", - "shelljs": "^0.7.4", - "sol-explore": "^1.6.2", + "istanbul": "0.4.5", + "keccakjs": "0.2.1", + "req-cwd": "1.0.1", + "shelljs": "0.7.8", + "sol-explore": "1.6.2", "solidity-parser-sc": "0.4.7", - "web3": "^0.18.4" + "web3": "0.18.4" }, "dependencies": { "bignumber.js": { "version": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", - "from": "bignumber.js@git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", "dev": true }, "commander": { @@ -6901,8 +7679,8 @@ "integrity": "sha1-J12O2qxPG7MyZHIInnlJyDlGmd0=", "dev": true, "requires": { - "lru-cache": "2", - "sigmund": "~1.0.0" + "lru-cache": "2.7.3", + "sigmund": "1.0.1" } }, "mocha": { @@ -6929,8 +7707,8 @@ "integrity": "sha1-Spc/Y1uRkPcV0QmH1cAP0oFevj0=", "dev": true, "requires": { - "inherits": "2", - "minimatch": "0.3" + "inherits": "2.0.3", + "minimatch": "0.3.0" } } } @@ -6947,9 +7725,9 @@ "integrity": "sha1-3svPh0sNHl+3LhSxZKloMEjprLM=", "dev": true, "requires": { - "glob": "^7.0.0", - "interpret": "^1.0.0", - "rechoir": "^0.6.2" + "glob": "7.1.1", + "interpret": "1.1.0", + "rechoir": "0.6.2" } }, "solidity-parser-sc": { @@ -6958,9 +7736,9 @@ "integrity": "sha512-wbX2806sm6thZME1aniqLcLH9HYwNwuKke6aw/FEgupCvoT9Iq5PdwuN9OyHWKGBOVeczpM5tCrnRXWNQ04YVw==", "dev": true, "requires": { - "mocha": "^2.4.5", - "pegjs": "^0.10.0", - "yargs": "^4.6.0" + "mocha": "2.5.3", + "pegjs": "0.10.0", + "yargs": "4.8.1" } }, "supports-color": { @@ -6976,101 +7754,11 @@ "dev": true, "requires": { "bignumber.js": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", - "crypto-js": "^3.1.4", - "utf8": "^2.1.1", - "xhr2": "*", - "xmlhttprequest": "*" - } - } - } - }, - "solidity-parser": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/solidity-parser/-/solidity-parser-0.4.0.tgz", - "integrity": "sha1-o0PxPac8kWgyeQNGgOgMSR3jQPo=", - "dev": true, - "requires": { - "mocha": "^2.4.5", - "pegjs": "^0.10.0", - "yargs": "^4.6.0" - }, - "dependencies": { - "commander": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-2.3.0.tgz", - "integrity": "sha1-/UMOiJgy7DU7ms0d4hfBHLPu+HM=", - "dev": true - }, - "debug": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.2.0.tgz", - "integrity": "sha1-+HBX6ZWxofauaklgZkE3vFbwOdo=", - "dev": true, - "requires": { - "ms": "0.7.1" - } - }, - "diff": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/diff/-/diff-1.4.0.tgz", - "integrity": "sha1-fyjS657nsVqX79ic5j3P2qPMur8=", - "dev": true - }, - "escape-string-regexp": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.2.tgz", - "integrity": "sha1-Tbwv5nTnGUnK8/smlc5/LcHZqNE=", - "dev": true - }, - "glob": { - "version": "3.2.11", - "resolved": "https://registry.npmjs.org/glob/-/glob-3.2.11.tgz", - "integrity": "sha1-Spc/Y1uRkPcV0QmH1cAP0oFevj0=", - "dev": true, - "requires": { - "inherits": "2", - "minimatch": "0.3" - } - }, - "minimatch": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-0.3.0.tgz", - "integrity": "sha1-J12O2qxPG7MyZHIInnlJyDlGmd0=", - "dev": true, - "requires": { - "lru-cache": "2", - "sigmund": "~1.0.0" - } - }, - "mocha": { - "version": "2.5.3", - "resolved": "https://registry.npmjs.org/mocha/-/mocha-2.5.3.tgz", - "integrity": "sha1-FhvlvetJZ3HrmzV0UFC2IrWu/Fg=", - "dev": true, - "requires": { - "commander": "2.3.0", - "debug": "2.2.0", - "diff": "1.4.0", - "escape-string-regexp": "1.0.2", - "glob": "3.2.11", - "growl": "1.9.2", - "jade": "0.26.3", - "mkdirp": "0.5.1", - "supports-color": "1.2.0", - "to-iso-string": "0.0.2" + "crypto-js": "3.1.8", + "utf8": "2.1.2", + "xhr2": "0.1.4", + "xmlhttprequest": "1.8.0" } - }, - "ms": { - "version": "0.7.1", - "resolved": "https://registry.npmjs.org/ms/-/ms-0.7.1.tgz", - "integrity": "sha1-nNE8A62/8ltl7/3nzoZO6VIBcJg=", - "dev": true - }, - "supports-color": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-1.2.0.tgz", - "integrity": "sha1-/x7R5hFp0Gs88tWI4YixjYhH4X4=", - "dev": true } } }, @@ -7085,7 +7773,7 @@ "resolved": "https://registry.npmjs.org/sort-keys/-/sort-keys-2.0.0.tgz", "integrity": "sha1-ZYU1WEhh7JfXMNbPQYIuH1ZoQSg=", "requires": { - "is-plain-obj": "^1.0.0" + "is-plain-obj": "1.1.0" } }, "source-map": { @@ -7099,11 +7787,11 @@ "integrity": "sha512-0KW2wvzfxm8NCTb30z0LMNyPqWCdDGE2viwzUaucqJdkTRXtZiSY3I+2A6nVAjmdOy0I4gU8DwnVVGsk9jvP2A==", "dev": true, "requires": { - "atob": "^2.0.0", - "decode-uri-component": "^0.2.0", - "resolve-url": "^0.2.1", - "source-map-url": "^0.4.0", - "urix": "^0.1.0" + "atob": "2.1.1", + "decode-uri-component": "0.2.0", + "resolve-url": "0.2.1", + "source-map-url": "0.4.0", + "urix": "0.1.0" } }, "source-map-support": { @@ -7111,7 +7799,7 @@ "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.4.tgz", "integrity": "sha512-PETSPG6BjY1AHs2t64vS2aqAgu6dMIMXJULWFBGbh2Gr8nVLbCFDo6i/RMMvviIQ2h1Z8+5gQhVKSn2je9nmdg==", "requires": { - "source-map": "^0.6.0" + "source-map": "0.6.1" }, "dependencies": { "source-map": { @@ -7132,7 +7820,7 @@ "resolved": "https://registry.npmjs.org/spdx-correct/-/spdx-correct-1.0.2.tgz", "integrity": "sha1-SzBz2TP/UfORLwOsVRlJikFQ20A=", "requires": { - "spdx-license-ids": "^1.0.2" + "spdx-license-ids": "1.2.2" } }, "spdx-expression-parse": { @@ -7151,7 +7839,7 @@ "integrity": "sha1-zQ7qXmOiEd//frDwkcQTPi0N0o8=", "dev": true, "requires": { - "through": "2" + "through": "2.3.8" } }, "split-string": { @@ -7160,7 +7848,7 @@ "integrity": "sha512-NzNVhJDYpwceVVii8/Hu6DKfD2G+NrQHlS/V/qgv763EYudVwEcMQNxd2lh+0VrUByXN/oJkl5grOhYWvQUYiw==", "dev": true, "requires": { - "extend-shallow": "^3.0.0" + "extend-shallow": "3.0.2" } }, "sprintf-js": { @@ -7174,14 +7862,14 @@ "resolved": "https://registry.npmjs.org/sshpk/-/sshpk-1.14.1.tgz", "integrity": "sha1-Ew9Zde3a2WPx1W+SuaxsUfqfg+s=", "requires": { - "asn1": "~0.2.3", - "assert-plus": "^1.0.0", - "bcrypt-pbkdf": "^1.0.0", - "dashdash": "^1.12.0", - "ecc-jsbn": "~0.1.1", - "getpass": "^0.1.1", - "jsbn": "~0.1.0", - "tweetnacl": "~0.14.0" + "asn1": "0.2.3", + "assert-plus": "1.0.0", + "bcrypt-pbkdf": "1.0.1", + "dashdash": "1.14.1", + "ecc-jsbn": "0.1.1", + "getpass": "0.1.7", + "jsbn": "0.1.1", + "tweetnacl": "0.14.5" } }, "static-extend": { @@ -7190,8 +7878,8 @@ "integrity": "sha1-YICcOcv/VTNyJv1eC1IPNB8ftcY=", "dev": true, "requires": { - "define-property": "^0.2.5", - "object-copy": "^0.1.0" + "define-property": "0.2.5", + "object-copy": "0.1.0" }, "dependencies": { "define-property": { @@ -7200,7 +7888,7 @@ "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", "dev": true, "requires": { - "is-descriptor": "^0.1.0" + "is-descriptor": "0.1.6" } } } @@ -7222,7 +7910,7 @@ "integrity": "sha1-TV5DPBhSYd3mI8o/RMWGvPXErRQ=", "dev": true, "requires": { - "duplexer": "~0.1.1" + "duplexer": "0.1.1" } }, "stream-to-observable": { @@ -7230,7 +7918,7 @@ "resolved": "https://registry.npmjs.org/stream-to-observable/-/stream-to-observable-0.2.0.tgz", "integrity": "sha1-WdbqOT2HwsDdrBCqDVYbxrpvDhA=", "requires": { - "any-observable": "^0.2.0" + "any-observable": "0.2.0" } }, "strict-uri-encode": { @@ -7248,9 +7936,9 @@ "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz", "integrity": "sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=", "requires": { - "code-point-at": "^1.0.0", - "is-fullwidth-code-point": "^1.0.0", - "strip-ansi": "^3.0.0" + "code-point-at": "1.1.0", + "is-fullwidth-code-point": "1.0.0", + "strip-ansi": "3.0.1" } }, "string_decoder": { @@ -7258,7 +7946,7 @@ "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", "integrity": "sha512-4AH6Z5fzNNBcH+6XDMfA/BTt87skxqJlO0lAh3Dker5zThcAxG6mKz+iGu308UKoPPQ8Dcqx/4JhujzltRa+hQ==", "requires": { - "safe-buffer": "~5.1.0" + "safe-buffer": "5.1.1" } }, "stringstream": { @@ -7271,7 +7959,7 @@ "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", "requires": { - "ansi-regex": "^2.0.0" + "ansi-regex": "2.1.1" } }, "strip-bom": { @@ -7279,7 +7967,7 @@ "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-2.0.0.tgz", "integrity": "sha1-YhmoVhZSBJHzV4i9vxRHqZx+aw4=", "requires": { - "is-utf8": "^0.2.0" + "is-utf8": "0.2.1" } }, "strip-bom-stream": { @@ -7287,8 +7975,17 @@ "resolved": "https://registry.npmjs.org/strip-bom-stream/-/strip-bom-stream-2.0.0.tgz", "integrity": "sha1-+H217yYT9paKpUWr/h7HKLaoKco=", "requires": { - "first-chunk-stream": "^2.0.0", - "strip-bom": "^2.0.0" + "first-chunk-stream": "2.0.0", + "strip-bom": "2.0.0" + } + }, + "strip-dirs": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/strip-dirs/-/strip-dirs-2.1.0.tgz", + "integrity": "sha512-JOCxOeKLm2CAS73y/U4ZeZPTkE+gNVCzKt7Eox84Iej1LT/2pTWYpZKJuxwQpvX1LiZb1xokNR7RLfuBAa7T3g==", + "dev": true, + "requires": { + "is-natural-number": "4.0.1" } }, "strip-eof": { @@ -7316,24 +8013,94 @@ "integrity": "sha1-cqJiiU2dQIuVbKBf83su2KbiotU=", "dev": true, "requires": { - "has-flag": "^1.0.0" + "has-flag": "1.0.0" } }, - "symbol-observable": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/symbol-observable/-/symbol-observable-1.0.1.tgz", - "integrity": "sha1-g0D8RwLDEi310iKI+IKD9RPT/dQ=" - }, - "sync-request": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/sync-request/-/sync-request-6.0.0.tgz", - "integrity": "sha512-jGNIAlCi9iU4X3Dm4oQnNQshDD3h0/1A7r79LyqjbjUnj69sX6mShAXlhRXgImsfVKtTcnra1jfzabdZvp+Lmw==", + "swarm-js": { + "version": "0.1.37", + "resolved": "https://registry.npmjs.org/swarm-js/-/swarm-js-0.1.37.tgz", + "integrity": "sha512-G8gi5fcXP/2upwiuOShJ258sIufBVztekgobr3cVgYXObZwJ5AXLqZn52AI+/ffft29pJexF9WNdUxjlkVehoQ==", "dev": true, "requires": { - "http-response-object": "^3.0.1", - "sync-rpc": "^1.2.1", - "then-request": "^6.0.0" - } + "bluebird": "3.5.3", + "buffer": "5.2.1", + "decompress": "4.2.0", + "eth-lib": "0.1.27", + "fs-extra": "2.1.2", + "fs-promise": "2.0.3", + "got": "7.1.0", + "mime-types": "2.1.18", + "mkdirp-promise": "5.0.1", + "mock-fs": "4.7.0", + "setimmediate": "1.0.5", + "tar.gz": "1.0.7", + "xhr-request-promise": "0.1.2" + }, + "dependencies": { + "fs-extra": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-2.1.2.tgz", + "integrity": "sha1-BGxwFjzvmq1GsOSn+kZ/si1x3jU=", + "dev": true, + "requires": { + "graceful-fs": "4.1.11", + "jsonfile": "2.4.0" + } + }, + "got": { + "version": "7.1.0", + "resolved": "https://registry.npmjs.org/got/-/got-7.1.0.tgz", + "integrity": "sha512-Y5WMo7xKKq1muPsxD+KmrR8DH5auG7fBdDVueZwETwV6VytKyU9OX/ddpq2/1hp1vIPvVb4T81dKQz3BivkNLw==", + "dev": true, + "requires": { + "decompress-response": "3.3.0", + "duplexer3": "0.1.4", + "get-stream": "3.0.0", + "is-plain-obj": "1.1.0", + "is-retry-allowed": "1.1.0", + "is-stream": "1.1.0", + "isurl": "1.0.0", + "lowercase-keys": "1.0.0", + "p-cancelable": "0.3.0", + "p-timeout": "1.2.1", + "safe-buffer": "5.1.1", + "timed-out": "4.0.1", + "url-parse-lax": "1.0.0", + "url-to-options": "1.0.1" + } + }, + "p-cancelable": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/p-cancelable/-/p-cancelable-0.3.0.tgz", + "integrity": "sha512-RVbZPLso8+jFeq1MfNvgXtCRED2raz/dKpacfTNxsx6pLEpEomM7gah6VeHSYV3+vo0OAi4MkArtQcWWXuQoyw==", + "dev": true + }, + "p-timeout": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/p-timeout/-/p-timeout-1.2.1.tgz", + "integrity": "sha1-XrOzU7f86Z8QGhA4iAuwVOu+o4Y=", + "dev": true, + "requires": { + "p-finally": "1.0.0" + } + } + } + }, + "symbol-observable": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/symbol-observable/-/symbol-observable-1.0.1.tgz", + "integrity": "sha1-g0D8RwLDEi310iKI+IKD9RPT/dQ=" + }, + "sync-request": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/sync-request/-/sync-request-6.0.0.tgz", + "integrity": "sha512-jGNIAlCi9iU4X3Dm4oQnNQshDD3h0/1A7r79LyqjbjUnj69sX6mShAXlhRXgImsfVKtTcnra1jfzabdZvp+Lmw==", + "dev": true, + "requires": { + "http-response-object": "3.0.1", + "sync-rpc": "1.3.4", + "then-request": "6.0.0" + } }, "sync-rpc": { "version": "1.3.4", @@ -7341,7 +8108,7 @@ "integrity": "sha512-Iug+t1ICVFenUcTnDu8WXFnT+k8IVoLKGh8VA3eXUtl2Rt9SjKX3YEv33OenABqpTPL9QEaHv1+CNn2LK8vMow==", "dev": true, "requires": { - "get-port": "^3.1.0" + "get-port": "3.2.0" } }, "tapable": { @@ -7349,13 +8116,60 @@ "resolved": "https://registry.npmjs.org/tapable/-/tapable-1.0.0.tgz", "integrity": "sha512-dQRhbNQkRnaqauC7WqSJ21EEksgT0fYZX2lqXzGkpo8JNig9zGZTYoMGvyI2nWmXlE2VSVXVDu7wLVGu/mQEsg==" }, + "tar": { + "version": "2.2.1", + "resolved": "http://registry.npmjs.org/tar/-/tar-2.2.1.tgz", + "integrity": "sha1-jk0qJWwOIYXGsYrWlK7JaLg8sdE=", + "dev": true, + "requires": { + "block-stream": "0.0.9", + "fstream": "1.0.11", + "inherits": "2.0.3" + } + }, + "tar-stream": { + "version": "1.6.2", + "resolved": "https://registry.npmjs.org/tar-stream/-/tar-stream-1.6.2.tgz", + "integrity": "sha512-rzS0heiNf8Xn7/mpdSVVSMAWAoy9bfb1WOTYC78Z0UQKeKa/CWS8FOq0lKGNa8DWKAn9gxjCvMLYc5PGXYlK2A==", + "dev": true, + "requires": { + "bl": "1.2.2", + "buffer-alloc": "1.2.0", + "end-of-stream": "1.4.1", + "fs-constants": "1.0.0", + "readable-stream": "2.3.5", + "to-buffer": "1.1.1", + "xtend": "4.0.1" + } + }, + "tar.gz": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/tar.gz/-/tar.gz-1.0.7.tgz", + "integrity": "sha512-uhGatJvds/3diZrETqMj4RxBR779LKlIE74SsMcn5JProZsfs9j0QBwWO1RW+IWNJxS2x8Zzra1+AW6OQHWphg==", + "dev": true, + "requires": { + "bluebird": "2.11.0", + "commander": "2.11.0", + "fstream": "1.0.11", + "mout": "0.11.1", + "tar": "2.2.1" + }, + "dependencies": { + "bluebird": { + "version": "2.11.0", + "resolved": "http://registry.npmjs.org/bluebird/-/bluebird-2.11.0.tgz", + "integrity": "sha1-U0uQM8AiyVecVro7Plpcqvu2UOE=", + "dev": true + } + } + }, "temp": { "version": "0.8.3", "resolved": "https://registry.npmjs.org/temp/-/temp-0.8.3.tgz", "integrity": "sha1-4Ma8TSa5AxJEEOT+2BEDAU38H1k=", "requires": { - "os-tmpdir": "^1.0.0", - "rimraf": "~2.2.6" + "os-tmpdir": "1.0.2", + "rimraf": "2.2.8" }, "dependencies": { "rimraf": { @@ -7371,7 +8185,7 @@ "integrity": "sha1-RYuDiH8oj8Vtb/+/rSYuJmOO+mk=", "dev": true, "requires": { - "execa": "^0.7.0" + "execa": "0.7.0" } }, "text-table": { @@ -7390,17 +8204,17 @@ "integrity": "sha512-xA+7uEMc+jsQIoyySJ93Ad08Kuqnik7u6jLS5hR91Z3smAoCfL3M8/MqMlobAa9gzBfO9pA88A/AntfepkkMJQ==", "dev": true, "requires": { - "@types/concat-stream": "^1.6.0", + "@types/concat-stream": "1.6.0", "@types/form-data": "0.0.33", - "@types/node": "^8.0.0", - "@types/qs": "^6.2.31", - "caseless": "~0.12.0", - "concat-stream": "^1.6.0", - "form-data": "^2.2.0", - "http-basic": "^7.0.0", - "http-response-object": "^3.0.1", - "promise": "^8.0.0", - "qs": "^6.4.0" + "@types/node": "8.10.36", + "@types/qs": "6.5.1", + "caseless": "0.12.0", + "concat-stream": "1.6.2", + "form-data": "2.3.2", + "http-basic": "7.0.0", + "http-response-object": "3.0.1", + "promise": "8.0.2", + "qs": "6.5.1" }, "dependencies": { "@types/node": { @@ -7411,6 +8225,24 @@ } } }, + "thenify": { + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/thenify/-/thenify-3.3.0.tgz", + "integrity": "sha1-5p44obq+lpsBCCB5eLn2K4hgSDk=", + "dev": true, + "requires": { + "any-promise": "1.3.0" + } + }, + "thenify-all": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/thenify-all/-/thenify-all-1.6.0.tgz", + "integrity": "sha1-GhkY1ALY/D+Y+/I02wvMjMEOlyY=", + "dev": true, + "requires": { + "thenify": "3.3.0" + } + }, "through": { "version": "2.3.8", "resolved": "https://registry.npmjs.org/through/-/through-2.3.8.tgz", @@ -7421,8 +8253,8 @@ "resolved": "https://registry.npmjs.org/through2/-/through2-2.0.3.tgz", "integrity": "sha1-AARWmzfHx0ujnEPzzteNGtlBQL4=", "requires": { - "readable-stream": "^2.1.5", - "xtend": "~4.0.1" + "readable-stream": "2.3.5", + "xtend": "4.0.1" } }, "timed-out": { @@ -7435,9 +8267,15 @@ "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.0.33.tgz", "integrity": "sha512-jRCJlojKnZ3addtTOjdIqoRuPEKBvNXcGYqzO6zWZX8KfKEpnGY5jfggJQ3EjKuu8D4bJRr0y+cYJFmYbImXGw==", "requires": { - "os-tmpdir": "~1.0.2" + "os-tmpdir": "1.0.2" } }, + "to-buffer": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/to-buffer/-/to-buffer-1.1.1.tgz", + "integrity": "sha512-lx9B5iv7msuFYE3dytT+KE5tap+rNYw+K4jVkb9R/asAb+pbBSM17jtunHplhBe6RRJdZx3Pn2Jph24O32mOVg==", + "dev": true + }, "to-fast-properties": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/to-fast-properties/-/to-fast-properties-1.0.3.tgz", @@ -7455,7 +8293,7 @@ "integrity": "sha1-KXWIt7Dn4KwI4E5nL4XB9JmeF68=", "dev": true, "requires": { - "kind-of": "^3.0.2" + "kind-of": "3.2.2" }, "dependencies": { "kind-of": { @@ -7464,7 +8302,7 @@ "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", "dev": true, "requires": { - "is-buffer": "^1.1.5" + "is-buffer": "1.1.6" } } } @@ -7475,10 +8313,10 @@ "integrity": "sha512-FWtleNAtZ/Ki2qtqej2CXTOayOH9bHDQF+Q48VpWyDXjbYxA4Yz8iDB31zXOBUlOHHKidDbqGVrTUvQMPmBGBw==", "dev": true, "requires": { - "define-property": "^2.0.2", - "extend-shallow": "^3.0.2", - "regex-not": "^1.0.2", - "safe-regex": "^1.1.0" + "define-property": "2.0.2", + "extend-shallow": "3.0.2", + "regex-not": "1.0.2", + "safe-regex": "1.1.0" } }, "to-regex-range": { @@ -7487,8 +8325,8 @@ "integrity": "sha1-fIDBe53+vlmeJzZ+DU3VWQFB2zg=", "dev": true, "requires": { - "is-number": "^3.0.0", - "repeat-string": "^1.6.1" + "is-number": "3.0.0", + "repeat-string": "1.6.1" } }, "touch": { @@ -7497,7 +8335,7 @@ "integrity": "sha512-WBx8Uy5TLtOSRtIq+M03/sKDrXCLHxwDcquSP2c43Le03/9serjQBIztjRz6FkJez9D/hleyAXTBGLwwZUw9lA==", "dev": true, "requires": { - "nopt": "~1.0.10" + "nopt": "1.0.10" } }, "tough-cookie": { @@ -7505,7 +8343,7 @@ "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.3.4.tgz", "integrity": "sha512-TZ6TTfI5NtZnuyy/Kecv+CnoROnyXn2DN97LontgQpCwsX2XyLYCC0ENhYkehSOwAp8rTQKc/NUIF7BkQ5rKLA==", "requires": { - "punycode": "^1.4.1" + "punycode": "1.4.1" } }, "trim": { @@ -7523,76 +8361,103 @@ "resolved": "https://registry.npmjs.org/truffle/-/truffle-4.1.11.tgz", "integrity": "sha512-VNhc6jexZeM92sNJJr4U8ln3uJ/mJEQO/0y9ZLYc4pccyIskPtl+3r4mzymgGM/Mq5v6MpoQVD6NZgHUVKX+Dw==", "requires": { - "mocha": "^4.1.0", - "original-require": "^1.0.1", + "mocha": "4.1.0", + "original-require": "1.0.1", "solc": "0.4.24" } }, "truffle-blockchain-utils": { - "version": "0.0.4", - "resolved": "https://registry.npmjs.org/truffle-blockchain-utils/-/truffle-blockchain-utils-0.0.4.tgz", - "integrity": "sha512-wgRrhwqh0aea08Hz28hUV4tuF2uTVQH/e9kBou+WK04cqrutB5cxQVQ6HGjeZLltxBYOFvhrGOOq4l3WJFnPEA==", + "version": "0.0.5", + "resolved": "https://registry.npmjs.org/truffle-blockchain-utils/-/truffle-blockchain-utils-0.0.5.tgz", + "integrity": "sha1-pOXAZNrdafeCoTfz0nbSEJXaekc=", "dev": true }, "truffle-config": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/truffle-config/-/truffle-config-1.0.4.tgz", - "integrity": "sha512-E8pvJNAIjs7LNsjkYeS2dgoOnLoSBrTwb1xF5lJwfvZmGMFpKvVL1sa5jpFxozpf/WkRn/rfxy8zTdb3pq16jA==", + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/truffle-config/-/truffle-config-1.1.0.tgz", + "integrity": "sha512-KKCfDitKwSyHbB88K/usnV/mMawgFeKG/oVGv6bu0+CS2afwk9+Lgk0zPe8IityjcRQNPUH1wxvU7XN06q3N2Q==", "dev": true, "requires": { - "find-up": "^2.1.0", - "lodash": "^4.17.4", - "original-require": "^1.0.0", - "truffle-error": "^0.0.2", - "truffle-provider": "^0.0.4" + "configstore": "4.0.0", + "find-up": "2.1.0", + "lodash": "4.17.10", + "original-require": "1.0.1", + "truffle-error": "0.0.3", + "truffle-provider": "0.1.0" }, "dependencies": { + "configstore": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/configstore/-/configstore-4.0.0.tgz", + "integrity": "sha512-CmquAXFBocrzaSM8mtGPMM/HiWmyIpr4CcJl/rgY2uCObZ/S7cKU0silxslqJejl+t/T9HS8E0PUNQD81JGUEQ==", + "dev": true, + "requires": { + "dot-prop": "4.2.0", + "graceful-fs": "4.1.11", + "make-dir": "1.2.0", + "unique-string": "1.0.0", + "write-file-atomic": "2.3.0", + "xdg-basedir": "3.0.0" + } + }, "find-up": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", "dev": true, "requires": { - "locate-path": "^2.0.0" + "locate-path": "2.0.0" } + }, + "lodash": { + "version": "4.17.10", + "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.10.tgz", + "integrity": "sha512-UejweD1pDoXu+AD825lWwp4ZGtSwgnpZxb3JDViD7StjQz+Nb/6l093lx4OQ0foGWNRoc19mWy7BzL+UAK2iVg==", + "dev": true } } }, "truffle-contract": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/truffle-contract/-/truffle-contract-3.0.4.tgz", - "integrity": "sha512-/1LCtJFf5Jvm5Rv88T0d/rZSKvaiW/yO1SHXLGJgKzLsiG1F/2spFs4HrI1mRxP00opfrYXloEmLtkVV/kcndQ==", + "version": "3.0.7", + "resolved": "https://registry.npmjs.org/truffle-contract/-/truffle-contract-3.0.7.tgz", + "integrity": "sha512-av4MTJDP29PI3oVh8TrvRzRHt+nZJH8ODSiil/TfcXrKMSes52DTA5LHj00siLvcadkxUgoEZfEZ04qqhNGoiA==", "dev": true, "requires": { "ethjs-abi": "0.1.8", - "truffle-blockchain-utils": "^0.0.4", - "truffle-contract-schema": "^2.0.0", - "truffle-error": "0.0.2", - "web3": "^0.20.1" + "truffle-blockchain-utils": "0.0.5", + "truffle-contract-schema": "2.0.2", + "truffle-error": "0.0.3", + "web3": "0.20.6" }, "dependencies": { - "ethjs-abi": { - "version": "0.1.8", - "resolved": "https://registry.npmjs.org/ethjs-abi/-/ethjs-abi-0.1.8.tgz", - "integrity": "sha1-zSiFg+1ijN+tr4re+juh28vKbBg=", + "bignumber.js": { + "version": "git+https://github.com/frozeman/bignumber.js-nolookahead.git#57692b3ecfc98bbdd6b3a516cb2353652ea49934", + "dev": true + }, + "web3": { + "version": "0.20.6", + "resolved": "http://registry.npmjs.org/web3/-/web3-0.20.6.tgz", + "integrity": "sha1-PpcwauAk+yThCj11yIQwJWIhUSA=", "dev": true, "requires": { - "bn.js": "4.11.6", - "js-sha3": "0.5.5", - "number-to-bn": "1.7.0" + "bignumber.js": "git+https://github.com/frozeman/bignumber.js-nolookahead.git#57692b3ecfc98bbdd6b3a516cb2353652ea49934", + "crypto-js": "3.1.8", + "utf8": "2.1.2", + "xhr2": "0.1.4", + "xmlhttprequest": "1.8.0" } } } }, "truffle-contract-schema": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/truffle-contract-schema/-/truffle-contract-schema-2.0.0.tgz", - "integrity": "sha512-nLlspmu1GKDaluWksBwitHi/7Z3IpRjmBYeO9N+T1nVJD2V4IWJaptCKP1NqnPiJA+FChB7+F7pI6Br51/FtXQ==", + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/truffle-contract-schema/-/truffle-contract-schema-2.0.2.tgz", + "integrity": "sha512-8mYAu0Y7wgMqcIa612dxiN9pzr6rq2YxZCzPizvqyDq+/rGWy8s0irl/T7i92a/4ME1V5ddNFf3+86uIlYbPUg==", "dev": true, "requires": { - "ajv": "^5.1.1", - "crypto-js": "^3.1.9-1", - "debug": "^3.1.0" + "ajv": "5.5.2", + "crypto-js": "3.1.9-1", + "debug": "3.2.6" }, "dependencies": { "crypto-js": { @@ -7602,79 +8467,136 @@ "dev": true }, "debug": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", - "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", + "version": "3.2.6", + "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.6.tgz", + "integrity": "sha512-mel+jf7nrtEl5Pn1Qx46zARXKDpBbvzezse7p7LqINmdoIk8PYP5SySaxEmYv6TZ0JyEKA1hsCId6DIhgITtWQ==", "dev": true, "requires": { - "ms": "2.0.0" + "ms": "2.1.1" } + }, + "ms": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.1.tgz", + "integrity": "sha512-tgp+dl5cGk28utYktBsrFqA7HKgrhgPsg6Z/EfhWI4gl1Hwq8B/GmY/0oXZ6nF8hDVesS/FpnYaD/kOWhYQvyg==", + "dev": true } } }, "truffle-error": { - "version": "0.0.2", - "resolved": "https://registry.npmjs.org/truffle-error/-/truffle-error-0.0.2.tgz", - "integrity": "sha1-AbGJt4UFVmrhaJwjnHyi3RIc/kw=", + "version": "0.0.3", + "resolved": "https://registry.npmjs.org/truffle-error/-/truffle-error-0.0.3.tgz", + "integrity": "sha1-S/VSQuFN7uHHGUkycJGC3v8sl8o=", "dev": true }, "truffle-expect": { - "version": "0.0.3", - "resolved": "https://registry.npmjs.org/truffle-expect/-/truffle-expect-0.0.3.tgz", - "integrity": "sha1-m3XO80O9WW5+XbyHj18bLjGKlEw=", + "version": "0.0.4", + "resolved": "https://registry.npmjs.org/truffle-expect/-/truffle-expect-0.0.4.tgz", + "integrity": "sha1-1bJ63qTFUvQ7cNwAh3I2t7aMdcg=", "dev": true }, "truffle-flattener": { - "version": "1.2.3", - "resolved": "https://registry.npmjs.org/truffle-flattener/-/truffle-flattener-1.2.3.tgz", - "integrity": "sha512-DisthKMI1qH+Xbw/S84CLPGeXz/kMkVUxBpz8Elj2kI4paVjEFEFwrq0juQHwxr2w/046r2tUT5usCE38Bw6Qw==", + "version": "1.2.10", + "resolved": "https://registry.npmjs.org/truffle-flattener/-/truffle-flattener-1.2.10.tgz", + "integrity": "sha512-YZTez8gghcI/87tALjR4tLEX5wztZ6ycazIOJlMerGrcep1I5vOCqwgSYI4HZOyRbBUGLMOnuGckX+oIVhaTaw==", "dev": true, "requires": { - "find-up": "^2.1.0", - "semver": "^5.4.1", - "solidity-parser": "^0.4.0", - "truffle-config": "^1.0.2", - "truffle-resolver": "^4.0.1", + "chalk": "2.4.1", + "find-up": "2.1.0", + "mkdirp": "0.5.1", + "semver": "5.5.0", + "solidity-parser-antlr": "0.3.3", + "truffle-config": "1.1.0", + "truffle-resolver": "4.0.5", "tsort": "0.0.1" }, "dependencies": { + "chalk": { + "version": "2.4.1", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.1.tgz", + "integrity": "sha512-ObN6h1v2fTJSmUXoS3nMQ92LbDK9be4TV+6G+omQlGJFdcUX5heKi1LZ1YnRMIgwTLEj3E24bT6tYni50rlCfQ==", + "dev": true, + "requires": { + "ansi-styles": "3.2.1", + "escape-string-regexp": "1.0.5", + "supports-color": "5.5.0" + } + }, "find-up": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", "dev": true, "requires": { - "locate-path": "^2.0.0" + "locate-path": "2.0.0" + } + }, + "has-flag": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", + "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=", + "dev": true + }, + "solidity-parser-antlr": { + "version": "0.3.3", + "resolved": "https://registry.npmjs.org/solidity-parser-antlr/-/solidity-parser-antlr-0.3.3.tgz", + "integrity": "sha512-RNUc18pjf7DLWs//WF+V+VnvrbetEbNFUYxm2JFbXU62G9WSu+nVyDxV5r+FG4wu8jom17vLdM/3I7bMBGfZ9g==", + "dev": true + }, + "supports-color": { + "version": "5.5.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", + "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", + "dev": true, + "requires": { + "has-flag": "3.0.0" } } } }, "truffle-provider": { - "version": "0.0.4", - "resolved": "https://registry.npmjs.org/truffle-provider/-/truffle-provider-0.0.4.tgz", - "integrity": "sha512-yVxxjocxnJcFspQ0T4Rjq/1wvvm3iLxidb6oa1EAX5LsnSQLPG8wAM5+JLlJ4FDBsqJdZLGOq1RR5Ln/w7x5JA==", + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/truffle-provider/-/truffle-provider-0.1.0.tgz", + "integrity": "sha512-3jphFU3WmgIj9/Na83pvDcR+kv1pytD2HbhK6L9ImJrzUQUHTFMZeF02NfahrdEe/ptbiwGo+OXgE0akTCPc5Q==", "dev": true, "requires": { - "truffle-error": "^0.0.2", - "web3": "^0.20.1" + "truffle-error": "0.0.3", + "web3": "1.0.0-beta.37" } }, "truffle-provisioner": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/truffle-provisioner/-/truffle-provisioner-0.1.0.tgz", - "integrity": "sha1-Ap5SScEBUwBzhTXgT97ZMaU8T2I=", + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/truffle-provisioner/-/truffle-provisioner-0.1.1.tgz", + "integrity": "sha1-WoMn1iUR7yPJUNOqhiYQp8N34qo=", "dev": true }, "truffle-resolver": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/truffle-resolver/-/truffle-resolver-4.0.2.tgz", - "integrity": "sha512-HKRd45HSfAqb9/BCOgYq4zkyl2lF40MvPDIGhyoPXFj5/9PSFzclyTkkMOdb+Rnm7oC1vY4cE1/k453lgf81Kw==", + "version": "4.0.5", + "resolved": "https://registry.npmjs.org/truffle-resolver/-/truffle-resolver-4.0.5.tgz", + "integrity": "sha512-aqPxo+bpL9yjfpSptvkV35WmkceBY4HbQGiUT2Rhx9cttNi0dQnPWL89inpQnBEqr1aLP9LxbZ+sai0PHKAD0w==", "dev": true, "requires": { - "async": "^2.1.4", - "truffle-contract": "^3.0.4", - "truffle-expect": "0.0.3", - "truffle-provisioner": "^0.1.0" + "async": "2.6.1", + "truffle-contract": "3.0.7", + "truffle-expect": "0.0.4", + "truffle-provisioner": "0.1.1" + }, + "dependencies": { + "async": { + "version": "2.6.1", + "resolved": "https://registry.npmjs.org/async/-/async-2.6.1.tgz", + "integrity": "sha512-fNEiL2+AZt6AlAw/29Cr0UDe4sRAHCpEHh54WMz+Bb7QfNcFw4h3loofyJpLeQs4Yx7yuqu/2dLgM5hKOs6HlQ==", + "dev": true, + "requires": { + "lodash": "4.17.11" + } + }, + "lodash": { + "version": "4.17.11", + "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.11.tgz", + "integrity": "sha512-cQKh8igo5QUhZ7lg38DYWAxMvjSAKG0A8wGSVimP07SIUEK2UO+arSRKbRZWtelMtN5V0Hkwh5ryOto/SshYIg==", + "dev": true + } } }, "tsort": { @@ -7688,7 +8610,7 @@ "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.6.0.tgz", "integrity": "sha1-J6XeoGs2sEoKmWZ3SykIaPD8QP0=", "requires": { - "safe-buffer": "^5.0.1" + "safe-buffer": "5.1.1" } }, "tweetnacl": { @@ -7703,7 +8625,7 @@ "integrity": "sha1-WITKtRLPHTVeP7eE8wgEsrUg23I=", "dev": true, "requires": { - "prelude-ls": "~1.1.2" + "prelude-ls": "1.1.2" } }, "type-detect": { @@ -7718,7 +8640,7 @@ "integrity": "sha512-HRkVv/5qY2G6I8iab9cI7v1bOIdhm94dVjQCPFElW9W+3GeDOSHmy2EBYe4VTApuzolPcmgFTN3ftVJRKR2J9Q==", "requires": { "media-typer": "0.3.0", - "mime-types": "~2.1.18" + "mime-types": "2.1.18" } }, "typedarray": { @@ -7727,6 +8649,15 @@ "integrity": "sha1-hnrHTjhkGHsdPUfZlqeOxciDB3c=", "dev": true }, + "typedarray-to-buffer": { + "version": "3.1.5", + "resolved": "https://registry.npmjs.org/typedarray-to-buffer/-/typedarray-to-buffer-3.1.5.tgz", + "integrity": "sha512-zdu8XMNEDepKKR+XYOXAVPtWui0ly0NtohUscw+UmaHiAWT8hrV1rr//H6V+0DvJ3OQ19S979M0laLfX8rm82Q==", + "dev": true, + "requires": { + "is-typedarray": "1.0.0" + } + }, "uglify-js": { "version": "2.8.29", "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-2.8.29.tgz", @@ -7734,9 +8665,9 @@ "dev": true, "optional": true, "requires": { - "source-map": "~0.5.1", - "uglify-to-browserify": "~1.0.0", - "yargs": "~3.10.0" + "source-map": "0.5.7", + "uglify-to-browserify": "1.0.2", + "yargs": "3.10.0" }, "dependencies": { "camelcase": { @@ -7753,8 +8684,8 @@ "dev": true, "optional": true, "requires": { - "center-align": "^0.1.1", - "right-align": "^0.1.1", + "center-align": "0.1.3", + "right-align": "0.1.3", "wordwrap": "0.0.2" } }, @@ -7779,9 +8710,9 @@ "dev": true, "optional": true, "requires": { - "camelcase": "^1.0.2", - "cliui": "^2.1.0", - "decamelize": "^1.0.0", + "camelcase": "1.2.1", + "cliui": "2.1.0", + "decamelize": "1.2.0", "window-size": "0.1.0" } } @@ -7799,13 +8730,42 @@ "resolved": "https://registry.npmjs.org/ultron/-/ultron-1.1.1.tgz", "integrity": "sha512-UIEXBNeYmKptWH6z8ZnqTeS8fV74zG0/eRU9VGkpzz+LIJNs8W/zM/L+7ctCkRrgbNnnR0xxw4bKOr0cW0N0Og==" }, + "unbzip2-stream": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/unbzip2-stream/-/unbzip2-stream-1.3.1.tgz", + "integrity": "sha512-fIZnvdjblYs7Cru/xC6tCPVhz7JkYcVQQkePwMLyQELzYTds2Xn8QefPVnvdVhhZqubxNA1cASXEH5wcK0Bucw==", + "dev": true, + "requires": { + "buffer": "3.6.0", + "through": "2.3.8" + }, + "dependencies": { + "base64-js": { + "version": "0.0.8", + "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-0.0.8.tgz", + "integrity": "sha1-EQHpVE9KdrG8OybUUsqW16NeeXg=", + "dev": true + }, + "buffer": { + "version": "3.6.0", + "resolved": "http://registry.npmjs.org/buffer/-/buffer-3.6.0.tgz", + "integrity": "sha1-pyyTb3e5a/UvX357RnGAYoVR3vs=", + "dev": true, + "requires": { + "base64-js": "0.0.8", + "ieee754": "1.1.12", + "isarray": "1.0.0" + } + } + } + }, "undefsafe": { "version": "2.0.2", "resolved": "https://registry.npmjs.org/undefsafe/-/undefsafe-2.0.2.tgz", "integrity": "sha1-Il9rngM3Zj4Njnz9aG/Cg2zKznY=", "dev": true, "requires": { - "debug": "^2.2.0" + "debug": "2.6.8" } }, "underscore": { @@ -7819,10 +8779,10 @@ "integrity": "sha1-XHHDTLW61dzr4+oM0IIHulqhrqQ=", "dev": true, "requires": { - "arr-union": "^3.1.0", - "get-value": "^2.0.6", - "is-extendable": "^0.1.1", - "set-value": "^0.4.3" + "arr-union": "3.1.0", + "get-value": "2.0.6", + "is-extendable": "0.1.1", + "set-value": "0.4.3" }, "dependencies": { "extend-shallow": { @@ -7831,7 +8791,7 @@ "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", "dev": true, "requires": { - "is-extendable": "^0.1.0" + "is-extendable": "0.1.1" } }, "set-value": { @@ -7840,10 +8800,10 @@ "integrity": "sha1-fbCPnT0i3H945Trzw79GZuzfzPE=", "dev": true, "requires": { - "extend-shallow": "^2.0.1", - "is-extendable": "^0.1.1", - "is-plain-object": "^2.0.1", - "to-object-path": "^0.3.0" + "extend-shallow": "2.0.1", + "is-extendable": "0.1.1", + "is-plain-object": "2.0.4", + "to-object-path": "0.3.0" } } } @@ -7854,7 +8814,7 @@ "integrity": "sha1-nhBXzKhRq7kzmPizOuGHuZyuwRo=", "dev": true, "requires": { - "crypto-random-string": "^1.0.0" + "crypto-random-string": "1.0.0" } }, "unpipe": { @@ -7868,8 +8828,8 @@ "integrity": "sha1-g3aHP30jNRef+x5vw6jtDfyKtVk=", "dev": true, "requires": { - "has-value": "^0.3.1", - "isobject": "^3.0.0" + "has-value": "0.3.1", + "isobject": "3.0.1" }, "dependencies": { "has-value": { @@ -7878,9 +8838,9 @@ "integrity": "sha1-ex9YutpiyoJ+wKIHgCVlSEWZXh8=", "dev": true, "requires": { - "get-value": "^2.0.3", - "has-values": "^0.1.4", - "isobject": "^2.0.0" + "get-value": "2.0.6", + "has-values": "0.1.4", + "isobject": "2.1.0" }, "dependencies": { "isobject": { @@ -7925,16 +8885,16 @@ "integrity": "sha512-gwMdhgJHGuj/+wHJJs9e6PcCszpxR1b236igrOkUofGhqJuG+amlIKwApH1IW1WWl7ovZxsX49lMBWLxSdm5Dw==", "dev": true, "requires": { - "boxen": "^1.2.1", - "chalk": "^2.0.1", - "configstore": "^3.0.0", - "import-lazy": "^2.1.0", - "is-ci": "^1.0.10", - "is-installed-globally": "^0.1.0", - "is-npm": "^1.0.0", - "latest-version": "^3.0.0", - "semver-diff": "^2.0.0", - "xdg-basedir": "^3.0.0" + "boxen": "1.3.0", + "chalk": "2.3.2", + "configstore": "3.1.2", + "import-lazy": "2.1.0", + "is-ci": "1.1.0", + "is-installed-globally": "0.1.0", + "is-npm": "1.0.0", + "latest-version": "3.1.0", + "semver-diff": "2.1.0", + "xdg-basedir": "3.0.0" } }, "urix": { @@ -7948,7 +8908,7 @@ "resolved": "https://registry.npmjs.org/url-parse-lax/-/url-parse-lax-1.0.0.tgz", "integrity": "sha1-evjzA2Rem9eaJy56FKxovAYJ2nM=", "requires": { - "prepend-http": "^1.0.1" + "prepend-http": "1.0.4" } }, "url-set-query": { @@ -7967,7 +8927,7 @@ "integrity": "sha512-6UJEQM/L+mzC3ZJNM56Q4DFGLX/evKGRg15UJHGB9X5j5Z3AFbgZvjUh2yq/UJUY4U5dh7Fal++XbNg1uzpRAw==", "dev": true, "requires": { - "kind-of": "^6.0.2" + "kind-of": "6.0.2" } }, "utf8": { @@ -8001,8 +8961,8 @@ "resolved": "https://registry.npmjs.org/validate-npm-package-license/-/validate-npm-package-license-3.0.1.tgz", "integrity": "sha1-KAS6vnEq0zeUWaz74kdGqywwP7w=", "requires": { - "spdx-correct": "~1.0.0", - "spdx-expression-parse": "~1.0.0" + "spdx-correct": "1.0.2", + "spdx-expression-parse": "1.0.4" } }, "vary": { @@ -8015,9 +8975,9 @@ "resolved": "https://registry.npmjs.org/verror/-/verror-1.10.0.tgz", "integrity": "sha1-OhBcoXBTr1XW4nDB+CiGguGNpAA=", "requires": { - "assert-plus": "^1.0.0", + "assert-plus": "1.0.0", "core-util-is": "1.0.2", - "extsprintf": "^1.2.0" + "extsprintf": "1.3.0" } }, "vinyl": { @@ -8025,8 +8985,8 @@ "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-1.2.0.tgz", "integrity": "sha1-XIgDbPVl5d8FVYv8kR+GVt8hiIQ=", "requires": { - "clone": "^1.0.0", - "clone-stats": "^0.0.1", + "clone": "1.0.4", + "clone-stats": "0.0.1", "replace-ext": "0.0.1" } }, @@ -8035,105 +8995,807 @@ "resolved": "https://registry.npmjs.org/vinyl-file/-/vinyl-file-2.0.0.tgz", "integrity": "sha1-p+v1/779obfRjRQPyweyI++2dRo=", "requires": { - "graceful-fs": "^4.1.2", - "pify": "^2.3.0", - "pinkie-promise": "^2.0.0", - "strip-bom": "^2.0.0", - "strip-bom-stream": "^2.0.0", - "vinyl": "^1.1.0" + "graceful-fs": "4.1.11", + "pify": "2.3.0", + "pinkie-promise": "2.0.1", + "strip-bom": "2.0.0", + "strip-bom-stream": "2.0.0", + "vinyl": "1.2.0" } }, "web3": { - "version": "0.20.5", - "resolved": "https://registry.npmjs.org/web3/-/web3-0.20.5.tgz", - "integrity": "sha1-xQSNNfe/TixMKAzlH7u8lRKQsWU=", + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3/-/web3-1.0.0-beta.37.tgz", + "integrity": "sha512-8XLgUspdzicC/xHG82TLrcF/Fxzj2XYNJ1KTYnepOI77bj5rvpsxxwHYBWQ6/JOjk0HkZqoBfnXWgcIHCDhZhQ==", "dev": true, "requires": { - "bignumber.js": "git+https://github.com/frozeman/bignumber.js-nolookahead.git#57692b3ecfc98bbdd6b3a516cb2353652ea49934", - "crypto-js": "^3.1.4", - "utf8": "^2.1.1", - "xhr2": "*", - "xmlhttprequest": "*" - } - }, - "web3-utils": { - "version": "1.0.0-beta.34", - "resolved": "https://registry.npmjs.org/web3-utils/-/web3-utils-1.0.0-beta.34.tgz", - "integrity": "sha1-lBH8OarvOcpOBhafdiKX2f8CCXA=", - "requires": { - "bn.js": "4.11.6", - "eth-lib": "0.1.27", - "ethjs-unit": "0.1.6", - "number-to-bn": "1.7.0", - "randomhex": "0.1.5", - "underscore": "1.8.3", - "utf8": "2.1.1" + "web3-bzz": "1.0.0-beta.37", + "web3-core": "1.0.0-beta.37", + "web3-eth": "1.0.0-beta.37", + "web3-eth-personal": "1.0.0-beta.37", + "web3-net": "1.0.0-beta.37", + "web3-shh": "1.0.0-beta.37", + "web3-utils": "1.0.0-beta.37" }, "dependencies": { "underscore": { "version": "1.8.3", - "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", - "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=" + "resolved": "http://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", + "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=", + "dev": true }, "utf8": { "version": "2.1.1", - "resolved": "https://registry.npmjs.org/utf8/-/utf8-2.1.1.tgz", - "integrity": "sha1-LgHbAvfY0JRPdxBPFgnrDDBM92g=" + "resolved": "http://registry.npmjs.org/utf8/-/utf8-2.1.1.tgz", + "integrity": "sha1-LgHbAvfY0JRPdxBPFgnrDDBM92g=", + "dev": true + }, + "web3-utils": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-utils/-/web3-utils-1.0.0-beta.37.tgz", + "integrity": "sha512-kA1fyhO8nKgU21wi30oJQ/ssvu+9srMdjOTKbHYbQe4ATPcr5YNwwrxG3Bcpbu1bEwRUVKHCkqi+wTvcAWBdlQ==", + "dev": true, + "requires": { + "bn.js": "4.11.6", + "eth-lib": "0.1.27", + "ethjs-unit": "0.1.6", + "number-to-bn": "1.7.0", + "randomhex": "0.1.5", + "underscore": "1.8.3", + "utf8": "2.1.1" + } } } }, - "webpack-addons": { - "version": "1.1.5", - "resolved": "https://registry.npmjs.org/webpack-addons/-/webpack-addons-1.1.5.tgz", - "integrity": "sha512-MGO0nVniCLFAQz1qv22zM02QPjcpAoJdy7ED0i3Zy7SY1IecgXCm460ib7H/Wq7e9oL5VL6S2BxaObxwIcag0g==", + "web3-bzz": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-bzz/-/web3-bzz-1.0.0-beta.37.tgz", + "integrity": "sha512-E+dho49Nsm/QpQvYWOF35YDsQrMvLB19AApENxhlQsu6HpWQt534DQul0t3Y/aAh8rlKD6Kanxt8LhHDG3vejQ==", + "dev": true, "requires": { - "jscodeshift": "^0.4.0" + "got": "7.1.0", + "swarm-js": "0.1.37", + "underscore": "1.8.3" }, "dependencies": { - "arr-diff": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/arr-diff/-/arr-diff-2.0.0.tgz", - "integrity": "sha1-jzuCf5Vai9ZpaX5KQlasPOrjVs8=", + "got": { + "version": "7.1.0", + "resolved": "https://registry.npmjs.org/got/-/got-7.1.0.tgz", + "integrity": "sha512-Y5WMo7xKKq1muPsxD+KmrR8DH5auG7fBdDVueZwETwV6VytKyU9OX/ddpq2/1hp1vIPvVb4T81dKQz3BivkNLw==", + "dev": true, "requires": { - "arr-flatten": "^1.0.1" + "decompress-response": "3.3.0", + "duplexer3": "0.1.4", + "get-stream": "3.0.0", + "is-plain-obj": "1.1.0", + "is-retry-allowed": "1.1.0", + "is-stream": "1.1.0", + "isurl": "1.0.0", + "lowercase-keys": "1.0.0", + "p-cancelable": "0.3.0", + "p-timeout": "1.2.1", + "safe-buffer": "5.1.1", + "timed-out": "4.0.1", + "url-parse-lax": "1.0.0", + "url-to-options": "1.0.1" } }, - "array-unique": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/array-unique/-/array-unique-0.2.1.tgz", - "integrity": "sha1-odl8yvy8JiXMcPrc6zalDFiwGlM=" - }, - "ast-types": { - "version": "0.10.1", - "resolved": "https://registry.npmjs.org/ast-types/-/ast-types-0.10.1.tgz", - "integrity": "sha512-UY7+9DPzlJ9VM8eY0b2TUZcZvF+1pO0hzMtAyjBYKhOmnvRlqYNYnWdtsMj0V16CGaMlpL0G1jnLbLo4AyotuQ==" - }, - "async": { - "version": "1.5.2", - "resolved": "https://registry.npmjs.org/async/-/async-1.5.2.tgz", - "integrity": "sha1-7GphrlZIDAw8skHJVhjiCJL5Zyo=" - }, - "babylon": { - "version": "6.18.0", - "resolved": "https://registry.npmjs.org/babylon/-/babylon-6.18.0.tgz", - "integrity": "sha512-q/UEjfGJ2Cm3oKV71DJz9d25TPnq5rhBVL2Q4fA5wcC3jcrdn7+SssEybFIxwAvvP+YCsCYNKughoF33GxgycQ==" + "p-cancelable": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/p-cancelable/-/p-cancelable-0.3.0.tgz", + "integrity": "sha512-RVbZPLso8+jFeq1MfNvgXtCRED2raz/dKpacfTNxsx6pLEpEomM7gah6VeHSYV3+vo0OAi4MkArtQcWWXuQoyw==", + "dev": true }, - "braces": { - "version": "1.8.5", - "resolved": "https://registry.npmjs.org/braces/-/braces-1.8.5.tgz", - "integrity": "sha1-uneWLhLf+WnWt2cR6RS3N4V79qc=", + "p-timeout": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/p-timeout/-/p-timeout-1.2.1.tgz", + "integrity": "sha1-XrOzU7f86Z8QGhA4iAuwVOu+o4Y=", + "dev": true, "requires": { - "expand-range": "^1.8.1", - "preserve": "^0.2.0", - "repeat-element": "^1.1.2" + "p-finally": "1.0.0" } }, - "expand-brackets": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/expand-brackets/-/expand-brackets-0.1.5.tgz", - "integrity": "sha1-3wcoTjQqgHzXM6xa9yQR5YHRF3s=", + "underscore": { + "version": "1.8.3", + "resolved": "http://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", + "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=", + "dev": true + } + } + }, + "web3-core": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-core/-/web3-core-1.0.0-beta.37.tgz", + "integrity": "sha512-cIwEqCj7OJyefQNauI0HOgW4sSaOQ98V99H2/HEIlnCZylsDzfw7gtQUdwnRFiIyIxjbWy3iWsjwDPoXNPZBYg==", + "dev": true, + "requires": { + "web3-core-helpers": "1.0.0-beta.37", + "web3-core-method": "1.0.0-beta.37", + "web3-core-requestmanager": "1.0.0-beta.37", + "web3-utils": "1.0.0-beta.37" + }, + "dependencies": { + "underscore": { + "version": "1.8.3", + "resolved": "http://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", + "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=", + "dev": true + }, + "utf8": { + "version": "2.1.1", + "resolved": "http://registry.npmjs.org/utf8/-/utf8-2.1.1.tgz", + "integrity": "sha1-LgHbAvfY0JRPdxBPFgnrDDBM92g=", + "dev": true + }, + "web3-utils": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-utils/-/web3-utils-1.0.0-beta.37.tgz", + "integrity": "sha512-kA1fyhO8nKgU21wi30oJQ/ssvu+9srMdjOTKbHYbQe4ATPcr5YNwwrxG3Bcpbu1bEwRUVKHCkqi+wTvcAWBdlQ==", + "dev": true, "requires": { - "is-posix-bracket": "^0.1.0" + "bn.js": "4.11.6", + "eth-lib": "0.1.27", + "ethjs-unit": "0.1.6", + "number-to-bn": "1.7.0", + "randomhex": "0.1.5", + "underscore": "1.8.3", + "utf8": "2.1.1" + } + } + } + }, + "web3-core-helpers": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-core-helpers/-/web3-core-helpers-1.0.0-beta.37.tgz", + "integrity": "sha512-efaLOzN28RMnbugnyelgLwPWWaSwElQzcAJ/x3PZu+uPloM/lE5x0YuBKvIh7/PoSMlHqtRWj1B8CpuQOUQ5Ew==", + "dev": true, + "requires": { + "underscore": "1.8.3", + "web3-eth-iban": "1.0.0-beta.37", + "web3-utils": "1.0.0-beta.37" + }, + "dependencies": { + "underscore": { + "version": "1.8.3", + "resolved": "http://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", + "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=", + "dev": true + }, + "utf8": { + "version": "2.1.1", + "resolved": "http://registry.npmjs.org/utf8/-/utf8-2.1.1.tgz", + "integrity": "sha1-LgHbAvfY0JRPdxBPFgnrDDBM92g=", + "dev": true + }, + "web3-utils": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-utils/-/web3-utils-1.0.0-beta.37.tgz", + "integrity": "sha512-kA1fyhO8nKgU21wi30oJQ/ssvu+9srMdjOTKbHYbQe4ATPcr5YNwwrxG3Bcpbu1bEwRUVKHCkqi+wTvcAWBdlQ==", + "dev": true, + "requires": { + "bn.js": "4.11.6", + "eth-lib": "0.1.27", + "ethjs-unit": "0.1.6", + "number-to-bn": "1.7.0", + "randomhex": "0.1.5", + "underscore": "1.8.3", + "utf8": "2.1.1" + } + } + } + }, + "web3-core-method": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-core-method/-/web3-core-method-1.0.0-beta.37.tgz", + "integrity": "sha512-pKWFUeqnVmzx3VrZg+CseSdrl/Yrk2ioid/HzolNXZE6zdoITZL0uRjnsbqXGEzgRRd1Oe/pFndpTlRsnxXloA==", + "dev": true, + "requires": { + "underscore": "1.8.3", + "web3-core-helpers": "1.0.0-beta.37", + "web3-core-promievent": "1.0.0-beta.37", + "web3-core-subscriptions": "1.0.0-beta.37", + "web3-utils": "1.0.0-beta.37" + }, + "dependencies": { + "underscore": { + "version": "1.8.3", + "resolved": "http://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", + "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=", + "dev": true + }, + "utf8": { + "version": "2.1.1", + "resolved": "http://registry.npmjs.org/utf8/-/utf8-2.1.1.tgz", + "integrity": "sha1-LgHbAvfY0JRPdxBPFgnrDDBM92g=", + "dev": true + }, + "web3-utils": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-utils/-/web3-utils-1.0.0-beta.37.tgz", + "integrity": "sha512-kA1fyhO8nKgU21wi30oJQ/ssvu+9srMdjOTKbHYbQe4ATPcr5YNwwrxG3Bcpbu1bEwRUVKHCkqi+wTvcAWBdlQ==", + "dev": true, + "requires": { + "bn.js": "4.11.6", + "eth-lib": "0.1.27", + "ethjs-unit": "0.1.6", + "number-to-bn": "1.7.0", + "randomhex": "0.1.5", + "underscore": "1.8.3", + "utf8": "2.1.1" + } + } + } + }, + "web3-core-promievent": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-core-promievent/-/web3-core-promievent-1.0.0-beta.37.tgz", + "integrity": "sha512-GTF2r1lP8nJBeA5Gxq5yZpJy9l8Fb9CXGZPfF8jHvaRdQHtm2Z+NDhqYmF833lcdkokRSyfPcXlz1mlWeClFpg==", + "dev": true, + "requires": { + "any-promise": "1.3.0", + "eventemitter3": "1.1.1" + } + }, + "web3-core-requestmanager": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-core-requestmanager/-/web3-core-requestmanager-1.0.0-beta.37.tgz", + "integrity": "sha512-66VUqye5BGp1Zz1r8psCxdNH+GtTjaFwroum2Osx+wbC5oRjAiXkkadiitf6wRb+edodjEMPn49u7B6WGNuewQ==", + "dev": true, + "requires": { + "underscore": "1.8.3", + "web3-core-helpers": "1.0.0-beta.37", + "web3-providers-http": "1.0.0-beta.37", + "web3-providers-ipc": "1.0.0-beta.37", + "web3-providers-ws": "1.0.0-beta.37" + }, + "dependencies": { + "underscore": { + "version": "1.8.3", + "resolved": "http://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", + "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=", + "dev": true + } + } + }, + "web3-core-subscriptions": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-core-subscriptions/-/web3-core-subscriptions-1.0.0-beta.37.tgz", + "integrity": "sha512-FdXl8so9kwkRRWziuCSpFsAuAdg9KvpXa1fQlT16uoGcYYfxwFO/nkwyBGQzkZt7emShI2IRugcazyPCZDwkOA==", + "dev": true, + "requires": { + "eventemitter3": "1.1.1", + "underscore": "1.8.3", + "web3-core-helpers": "1.0.0-beta.37" + }, + "dependencies": { + "underscore": { + "version": "1.8.3", + "resolved": "http://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", + "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=", + "dev": true + } + } + }, + "web3-eth": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-eth/-/web3-eth-1.0.0-beta.37.tgz", + "integrity": "sha512-Eb3aGtkz3G9q+Z9DKgSQNbn/u8RtcZQQ0R4sW9hy5KK47GoT6vab5c6DiD3QWzI0BzitHzR5Ji+3VHf/hPUGgw==", + "dev": true, + "requires": { + "underscore": "1.8.3", + "web3-core": "1.0.0-beta.37", + "web3-core-helpers": "1.0.0-beta.37", + "web3-core-method": "1.0.0-beta.37", + "web3-core-subscriptions": "1.0.0-beta.37", + "web3-eth-abi": "1.0.0-beta.37", + "web3-eth-accounts": "1.0.0-beta.37", + "web3-eth-contract": "1.0.0-beta.37", + "web3-eth-ens": "1.0.0-beta.37", + "web3-eth-iban": "1.0.0-beta.37", + "web3-eth-personal": "1.0.0-beta.37", + "web3-net": "1.0.0-beta.37", + "web3-utils": "1.0.0-beta.37" + }, + "dependencies": { + "underscore": { + "version": "1.8.3", + "resolved": "http://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", + "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=", + "dev": true + }, + "utf8": { + "version": "2.1.1", + "resolved": "http://registry.npmjs.org/utf8/-/utf8-2.1.1.tgz", + "integrity": "sha1-LgHbAvfY0JRPdxBPFgnrDDBM92g=", + "dev": true + }, + "web3-utils": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-utils/-/web3-utils-1.0.0-beta.37.tgz", + "integrity": "sha512-kA1fyhO8nKgU21wi30oJQ/ssvu+9srMdjOTKbHYbQe4ATPcr5YNwwrxG3Bcpbu1bEwRUVKHCkqi+wTvcAWBdlQ==", + "dev": true, + "requires": { + "bn.js": "4.11.6", + "eth-lib": "0.1.27", + "ethjs-unit": "0.1.6", + "number-to-bn": "1.7.0", + "randomhex": "0.1.5", + "underscore": "1.8.3", + "utf8": "2.1.1" + } + } + } + }, + "web3-eth-abi": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-eth-abi/-/web3-eth-abi-1.0.0-beta.37.tgz", + "integrity": "sha512-g9DKZGM2OqwKp/tX3W/yihcj7mQCtJ6CXyZXEIZfuDyRBED/iSEIFfieDOd+yo16sokLMig6FG7ADhhu+19hdA==", + "dev": true, + "requires": { + "ethers": "4.0.0-beta.1", + "underscore": "1.8.3", + "web3-utils": "1.0.0-beta.37" + }, + "dependencies": { + "underscore": { + "version": "1.8.3", + "resolved": "http://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", + "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=", + "dev": true + }, + "utf8": { + "version": "2.1.1", + "resolved": "http://registry.npmjs.org/utf8/-/utf8-2.1.1.tgz", + "integrity": "sha1-LgHbAvfY0JRPdxBPFgnrDDBM92g=", + "dev": true + }, + "web3-utils": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-utils/-/web3-utils-1.0.0-beta.37.tgz", + "integrity": "sha512-kA1fyhO8nKgU21wi30oJQ/ssvu+9srMdjOTKbHYbQe4ATPcr5YNwwrxG3Bcpbu1bEwRUVKHCkqi+wTvcAWBdlQ==", + "dev": true, + "requires": { + "bn.js": "4.11.6", + "eth-lib": "0.1.27", + "ethjs-unit": "0.1.6", + "number-to-bn": "1.7.0", + "randomhex": "0.1.5", + "underscore": "1.8.3", + "utf8": "2.1.1" + } + } + } + }, + "web3-eth-accounts": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-eth-accounts/-/web3-eth-accounts-1.0.0-beta.37.tgz", + "integrity": "sha512-uvbHL62/zwo4GDmwKdqH9c/EgYd8QVnAfpVw8D3epSISpgbONNY7Hr4MRMSd/CqAP12l2Ls9JVQGLhhC83bW6g==", + "dev": true, + "requires": { + "any-promise": "1.3.0", + "crypto-browserify": "3.12.0", + "eth-lib": "0.2.7", + "scrypt.js": "0.2.0", + "underscore": "1.8.3", + "uuid": "2.0.1", + "web3-core": "1.0.0-beta.37", + "web3-core-helpers": "1.0.0-beta.37", + "web3-core-method": "1.0.0-beta.37", + "web3-utils": "1.0.0-beta.37" + }, + "dependencies": { + "eth-lib": { + "version": "0.2.7", + "resolved": "https://registry.npmjs.org/eth-lib/-/eth-lib-0.2.7.tgz", + "integrity": "sha1-L5Pxex4jrsN1nNSj/iDBKGo/wco=", + "dev": true, + "requires": { + "bn.js": "4.11.6", + "elliptic": "6.4.0", + "xhr-request-promise": "0.1.2" + } + }, + "underscore": { + "version": "1.8.3", + "resolved": "http://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", + "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=", + "dev": true + }, + "utf8": { + "version": "2.1.1", + "resolved": "http://registry.npmjs.org/utf8/-/utf8-2.1.1.tgz", + "integrity": "sha1-LgHbAvfY0JRPdxBPFgnrDDBM92g=", + "dev": true + }, + "uuid": { + "version": "2.0.1", + "resolved": "http://registry.npmjs.org/uuid/-/uuid-2.0.1.tgz", + "integrity": "sha1-wqMN7bPlNdcsz4LjQ5QaULqFM6w=", + "dev": true + }, + "web3-utils": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-utils/-/web3-utils-1.0.0-beta.37.tgz", + "integrity": "sha512-kA1fyhO8nKgU21wi30oJQ/ssvu+9srMdjOTKbHYbQe4ATPcr5YNwwrxG3Bcpbu1bEwRUVKHCkqi+wTvcAWBdlQ==", + "dev": true, + "requires": { + "bn.js": "4.11.6", + "eth-lib": "0.1.27", + "ethjs-unit": "0.1.6", + "number-to-bn": "1.7.0", + "randomhex": "0.1.5", + "underscore": "1.8.3", + "utf8": "2.1.1" + }, + "dependencies": { + "eth-lib": { + "version": "0.1.27", + "resolved": "https://registry.npmjs.org/eth-lib/-/eth-lib-0.1.27.tgz", + "integrity": "sha512-B8czsfkJYzn2UIEMwjc7Mbj+Cy72V+/OXH/tb44LV8jhrjizQJJ325xMOMyk3+ETa6r6oi0jsUY14+om8mQMWA==", + "dev": true, + "requires": { + "bn.js": "4.11.6", + "elliptic": "6.4.0", + "keccakjs": "0.2.1", + "nano-json-stream-parser": "0.1.2", + "servify": "0.1.12", + "ws": "3.3.3", + "xhr-request-promise": "0.1.2" + } + } + } + } + } + }, + "web3-eth-contract": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-eth-contract/-/web3-eth-contract-1.0.0-beta.37.tgz", + "integrity": "sha512-h1B3A8Z/C7BlnTCHkrWbXZQTViDxfR12lKMeTkT8Sqj5phFmxrBlPE4ORy4lf1Dk5b23mZYE0r/IRACx4ThCrQ==", + "dev": true, + "requires": { + "underscore": "1.8.3", + "web3-core": "1.0.0-beta.37", + "web3-core-helpers": "1.0.0-beta.37", + "web3-core-method": "1.0.0-beta.37", + "web3-core-promievent": "1.0.0-beta.37", + "web3-core-subscriptions": "1.0.0-beta.37", + "web3-eth-abi": "1.0.0-beta.37", + "web3-utils": "1.0.0-beta.37" + }, + "dependencies": { + "underscore": { + "version": "1.8.3", + "resolved": "http://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", + "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=", + "dev": true + }, + "utf8": { + "version": "2.1.1", + "resolved": "http://registry.npmjs.org/utf8/-/utf8-2.1.1.tgz", + "integrity": "sha1-LgHbAvfY0JRPdxBPFgnrDDBM92g=", + "dev": true + }, + "web3-utils": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-utils/-/web3-utils-1.0.0-beta.37.tgz", + "integrity": "sha512-kA1fyhO8nKgU21wi30oJQ/ssvu+9srMdjOTKbHYbQe4ATPcr5YNwwrxG3Bcpbu1bEwRUVKHCkqi+wTvcAWBdlQ==", + "dev": true, + "requires": { + "bn.js": "4.11.6", + "eth-lib": "0.1.27", + "ethjs-unit": "0.1.6", + "number-to-bn": "1.7.0", + "randomhex": "0.1.5", + "underscore": "1.8.3", + "utf8": "2.1.1" + } + } + } + }, + "web3-eth-ens": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-eth-ens/-/web3-eth-ens-1.0.0-beta.37.tgz", + "integrity": "sha512-dR3UkrVzdRrJhfP57xBPx0CMiVnCcYFvh+u2XMkGydrhHgupSUkjqGr89xry/j1T0BkuN9mikpbyhdCVMXqMbg==", + "dev": true, + "requires": { + "eth-ens-namehash": "2.0.8", + "underscore": "1.8.3", + "web3-core": "1.0.0-beta.37", + "web3-core-helpers": "1.0.0-beta.37", + "web3-core-promievent": "1.0.0-beta.37", + "web3-eth-abi": "1.0.0-beta.37", + "web3-eth-contract": "1.0.0-beta.37", + "web3-utils": "1.0.0-beta.37" + }, + "dependencies": { + "underscore": { + "version": "1.8.3", + "resolved": "http://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", + "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=", + "dev": true + }, + "utf8": { + "version": "2.1.1", + "resolved": "http://registry.npmjs.org/utf8/-/utf8-2.1.1.tgz", + "integrity": "sha1-LgHbAvfY0JRPdxBPFgnrDDBM92g=", + "dev": true + }, + "web3-utils": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-utils/-/web3-utils-1.0.0-beta.37.tgz", + "integrity": "sha512-kA1fyhO8nKgU21wi30oJQ/ssvu+9srMdjOTKbHYbQe4ATPcr5YNwwrxG3Bcpbu1bEwRUVKHCkqi+wTvcAWBdlQ==", + "dev": true, + "requires": { + "bn.js": "4.11.6", + "eth-lib": "0.1.27", + "ethjs-unit": "0.1.6", + "number-to-bn": "1.7.0", + "randomhex": "0.1.5", + "underscore": "1.8.3", + "utf8": "2.1.1" + } + } + } + }, + "web3-eth-iban": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-eth-iban/-/web3-eth-iban-1.0.0-beta.37.tgz", + "integrity": "sha512-WQRniGJFxH/XCbd7miO6+jnUG+6bvuzfeufPIiOtCbeIC1ypp1kSqER8YVBDrTyinU1xnf1U5v0KBZ2yiWBJxQ==", + "dev": true, + "requires": { + "bn.js": "4.11.6", + "web3-utils": "1.0.0-beta.37" + }, + "dependencies": { + "underscore": { + "version": "1.8.3", + "resolved": "http://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", + "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=", + "dev": true + }, + "utf8": { + "version": "2.1.1", + "resolved": "http://registry.npmjs.org/utf8/-/utf8-2.1.1.tgz", + "integrity": "sha1-LgHbAvfY0JRPdxBPFgnrDDBM92g=", + "dev": true + }, + "web3-utils": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-utils/-/web3-utils-1.0.0-beta.37.tgz", + "integrity": "sha512-kA1fyhO8nKgU21wi30oJQ/ssvu+9srMdjOTKbHYbQe4ATPcr5YNwwrxG3Bcpbu1bEwRUVKHCkqi+wTvcAWBdlQ==", + "dev": true, + "requires": { + "bn.js": "4.11.6", + "eth-lib": "0.1.27", + "ethjs-unit": "0.1.6", + "number-to-bn": "1.7.0", + "randomhex": "0.1.5", + "underscore": "1.8.3", + "utf8": "2.1.1" + } + } + } + }, + "web3-eth-personal": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-eth-personal/-/web3-eth-personal-1.0.0-beta.37.tgz", + "integrity": "sha512-B4dZpGbD+nGnn48i6nJBqrQ+HB7oDmd+Q3wGRKOsHSK5HRWO/KwYeA7wgwamMAElkut50lIsT9EJl4Apfk3G5Q==", + "dev": true, + "requires": { + "web3-core": "1.0.0-beta.37", + "web3-core-helpers": "1.0.0-beta.37", + "web3-core-method": "1.0.0-beta.37", + "web3-net": "1.0.0-beta.37", + "web3-utils": "1.0.0-beta.37" + }, + "dependencies": { + "underscore": { + "version": "1.8.3", + "resolved": "http://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", + "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=", + "dev": true + }, + "utf8": { + "version": "2.1.1", + "resolved": "http://registry.npmjs.org/utf8/-/utf8-2.1.1.tgz", + "integrity": "sha1-LgHbAvfY0JRPdxBPFgnrDDBM92g=", + "dev": true + }, + "web3-utils": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-utils/-/web3-utils-1.0.0-beta.37.tgz", + "integrity": "sha512-kA1fyhO8nKgU21wi30oJQ/ssvu+9srMdjOTKbHYbQe4ATPcr5YNwwrxG3Bcpbu1bEwRUVKHCkqi+wTvcAWBdlQ==", + "dev": true, + "requires": { + "bn.js": "4.11.6", + "eth-lib": "0.1.27", + "ethjs-unit": "0.1.6", + "number-to-bn": "1.7.0", + "randomhex": "0.1.5", + "underscore": "1.8.3", + "utf8": "2.1.1" + } + } + } + }, + "web3-net": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-net/-/web3-net-1.0.0-beta.37.tgz", + "integrity": "sha512-xG/uBtMdDa1UMXw9KjDUgf3fXA/fDEJUYUS0TDn+U9PMgngA+UVECHNNvQTrVVDxEky38V3sahwIDiopNsQdsw==", + "dev": true, + "requires": { + "web3-core": "1.0.0-beta.37", + "web3-core-method": "1.0.0-beta.37", + "web3-utils": "1.0.0-beta.37" + }, + "dependencies": { + "underscore": { + "version": "1.8.3", + "resolved": "http://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", + "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=", + "dev": true + }, + "utf8": { + "version": "2.1.1", + "resolved": "http://registry.npmjs.org/utf8/-/utf8-2.1.1.tgz", + "integrity": "sha1-LgHbAvfY0JRPdxBPFgnrDDBM92g=", + "dev": true + }, + "web3-utils": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-utils/-/web3-utils-1.0.0-beta.37.tgz", + "integrity": "sha512-kA1fyhO8nKgU21wi30oJQ/ssvu+9srMdjOTKbHYbQe4ATPcr5YNwwrxG3Bcpbu1bEwRUVKHCkqi+wTvcAWBdlQ==", + "dev": true, + "requires": { + "bn.js": "4.11.6", + "eth-lib": "0.1.27", + "ethjs-unit": "0.1.6", + "number-to-bn": "1.7.0", + "randomhex": "0.1.5", + "underscore": "1.8.3", + "utf8": "2.1.1" + } + } + } + }, + "web3-providers-http": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-providers-http/-/web3-providers-http-1.0.0-beta.37.tgz", + "integrity": "sha512-FM/1YDB1jtZuTo78habFj7S9tNHoqt0UipdyoQV29b8LkGKZV9Vs3is8L24hzuj1j/tbwkcAH+ewIseHwu0DTg==", + "dev": true, + "requires": { + "web3-core-helpers": "1.0.0-beta.37", + "xhr2-cookies": "1.1.0" + } + }, + "web3-providers-ipc": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-providers-ipc/-/web3-providers-ipc-1.0.0-beta.37.tgz", + "integrity": "sha512-NdRPRxYMIU0C3u18NI8u4bwbhI9pCg5nRgDGYcmSAx5uOBxiYcQy+hb0WkJRRhBoyIXJmy+s26FoH8904+UnPg==", + "dev": true, + "requires": { + "oboe": "2.1.3", + "underscore": "1.8.3", + "web3-core-helpers": "1.0.0-beta.37" + }, + "dependencies": { + "underscore": { + "version": "1.8.3", + "resolved": "http://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", + "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=", + "dev": true + } + } + }, + "web3-providers-ws": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-providers-ws/-/web3-providers-ws-1.0.0-beta.37.tgz", + "integrity": "sha512-8p6ZLv+1JYa5Vs8oBn33Nn3VGFBbF+wVfO+b78RJS1Qf1uIOzjFVDk3XwYDD7rlz9G5BKpxhaQw+6EGQ7L02aw==", + "dev": true, + "requires": { + "underscore": "1.8.3", + "web3-core-helpers": "1.0.0-beta.37", + "websocket": "git://github.com/frozeman/WebSocket-Node.git#6c72925e3f8aaaea8dc8450f97627e85263999f2" + }, + "dependencies": { + "underscore": { + "version": "1.8.3", + "resolved": "http://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", + "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=", + "dev": true + } + } + }, + "web3-shh": { + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-shh/-/web3-shh-1.0.0-beta.37.tgz", + "integrity": "sha512-h5STG/xqZNQWtCLYOu7NiMqwqPea8SfkKQUPUFxXKIPVCFVKpHuQEwW1qcPQRJMLhlQIv17xuoUe1A+RzDNbrw==", + "dev": true, + "requires": { + "web3-core": "1.0.0-beta.37", + "web3-core-method": "1.0.0-beta.37", + "web3-core-subscriptions": "1.0.0-beta.37", + "web3-net": "1.0.0-beta.37" + } + }, + "web3-utils": { + "version": "1.0.0-beta.34", + "resolved": "https://registry.npmjs.org/web3-utils/-/web3-utils-1.0.0-beta.34.tgz", + "integrity": "sha1-lBH8OarvOcpOBhafdiKX2f8CCXA=", + "requires": { + "bn.js": "4.11.6", + "eth-lib": "0.1.27", + "ethjs-unit": "0.1.6", + "number-to-bn": "1.7.0", + "randomhex": "0.1.5", + "underscore": "1.8.3", + "utf8": "2.1.1" + }, + "dependencies": { + "underscore": { + "version": "1.8.3", + "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", + "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=" + }, + "utf8": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/utf8/-/utf8-2.1.1.tgz", + "integrity": "sha1-LgHbAvfY0JRPdxBPFgnrDDBM92g=" + } + } + }, + "webpack-addons": { + "version": "1.1.5", + "resolved": "https://registry.npmjs.org/webpack-addons/-/webpack-addons-1.1.5.tgz", + "integrity": "sha512-MGO0nVniCLFAQz1qv22zM02QPjcpAoJdy7ED0i3Zy7SY1IecgXCm460ib7H/Wq7e9oL5VL6S2BxaObxwIcag0g==", + "requires": { + "jscodeshift": "0.4.1" + }, + "dependencies": { + "arr-diff": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/arr-diff/-/arr-diff-2.0.0.tgz", + "integrity": "sha1-jzuCf5Vai9ZpaX5KQlasPOrjVs8=", + "requires": { + "arr-flatten": "1.1.0" + } + }, + "array-unique": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/array-unique/-/array-unique-0.2.1.tgz", + "integrity": "sha1-odl8yvy8JiXMcPrc6zalDFiwGlM=" + }, + "ast-types": { + "version": "0.10.1", + "resolved": "https://registry.npmjs.org/ast-types/-/ast-types-0.10.1.tgz", + "integrity": "sha512-UY7+9DPzlJ9VM8eY0b2TUZcZvF+1pO0hzMtAyjBYKhOmnvRlqYNYnWdtsMj0V16CGaMlpL0G1jnLbLo4AyotuQ==" + }, + "async": { + "version": "1.5.2", + "resolved": "https://registry.npmjs.org/async/-/async-1.5.2.tgz", + "integrity": "sha1-7GphrlZIDAw8skHJVhjiCJL5Zyo=" + }, + "babylon": { + "version": "6.18.0", + "resolved": "https://registry.npmjs.org/babylon/-/babylon-6.18.0.tgz", + "integrity": "sha512-q/UEjfGJ2Cm3oKV71DJz9d25TPnq5rhBVL2Q4fA5wcC3jcrdn7+SssEybFIxwAvvP+YCsCYNKughoF33GxgycQ==" + }, + "braces": { + "version": "1.8.5", + "resolved": "https://registry.npmjs.org/braces/-/braces-1.8.5.tgz", + "integrity": "sha1-uneWLhLf+WnWt2cR6RS3N4V79qc=", + "requires": { + "expand-range": "1.8.2", + "preserve": "0.2.0", + "repeat-element": "1.1.2" + } + }, + "expand-brackets": { + "version": "0.1.5", + "resolved": "https://registry.npmjs.org/expand-brackets/-/expand-brackets-0.1.5.tgz", + "integrity": "sha1-3wcoTjQqgHzXM6xa9yQR5YHRF3s=", + "requires": { + "is-posix-bracket": "0.1.1" } }, "extglob": { @@ -8141,7 +9803,7 @@ "resolved": "https://registry.npmjs.org/extglob/-/extglob-0.3.2.tgz", "integrity": "sha1-Lhj/PS9JqydlzskCPwEdqo2DSaE=", "requires": { - "is-extglob": "^1.0.0" + "is-extglob": "1.0.0" } }, "is-extglob": { @@ -8154,7 +9816,7 @@ "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-2.0.1.tgz", "integrity": "sha1-0Jb5JqPe1WAPP9/ZEZjLCIjC2GM=", "requires": { - "is-extglob": "^1.0.0" + "is-extglob": "1.0.0" } }, "jscodeshift": { @@ -8162,21 +9824,21 @@ "resolved": "https://registry.npmjs.org/jscodeshift/-/jscodeshift-0.4.1.tgz", "integrity": "sha512-iOX6If+hsw0q99V3n31t4f5VlD1TQZddH08xbT65ZqA7T4Vkx68emrDZMUOLVvCEAJ6NpAk7DECe3fjC/t52AQ==", "requires": { - "async": "^1.5.0", - "babel-plugin-transform-flow-strip-types": "^6.8.0", - "babel-preset-es2015": "^6.9.0", - "babel-preset-stage-1": "^6.5.0", - "babel-register": "^6.9.0", - "babylon": "^6.17.3", - "colors": "^1.1.2", - "flow-parser": "^0.*", - "lodash": "^4.13.1", - "micromatch": "^2.3.7", + "async": "1.5.2", + "babel-plugin-transform-flow-strip-types": "6.22.0", + "babel-preset-es2015": "6.24.1", + "babel-preset-stage-1": "6.24.1", + "babel-register": "6.26.0", + "babylon": "6.18.0", + "colors": "1.2.1", + "flow-parser": "0.68.0", + "lodash": "4.17.5", + "micromatch": "2.3.11", "node-dir": "0.1.8", - "nomnom": "^1.8.1", - "recast": "^0.12.5", - "temp": "^0.8.1", - "write-file-atomic": "^1.2.0" + "nomnom": "1.8.1", + "recast": "0.12.9", + "temp": "0.8.3", + "write-file-atomic": "1.3.4" } }, "kind-of": { @@ -8184,7 +9846,7 @@ "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", "requires": { - "is-buffer": "^1.1.5" + "is-buffer": "1.1.6" } }, "micromatch": { @@ -8192,19 +9854,19 @@ "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-2.3.11.tgz", "integrity": "sha1-hmd8l9FyCzY0MdBNDRUpO9OMFWU=", "requires": { - "arr-diff": "^2.0.0", - "array-unique": "^0.2.1", - "braces": "^1.8.2", - "expand-brackets": "^0.1.4", - "extglob": "^0.3.1", - "filename-regex": "^2.0.0", - "is-extglob": "^1.0.0", - "is-glob": "^2.0.1", - "kind-of": "^3.0.2", - "normalize-path": "^2.0.1", - "object.omit": "^2.0.0", - "parse-glob": "^3.0.4", - "regex-cache": "^0.4.2" + "arr-diff": "2.0.0", + "array-unique": "0.2.1", + "braces": "1.8.5", + "expand-brackets": "0.1.5", + "extglob": "0.3.2", + "filename-regex": "2.0.1", + "is-extglob": "1.0.0", + "is-glob": "2.0.1", + "kind-of": "3.2.2", + "normalize-path": "2.1.1", + "object.omit": "2.0.1", + "parse-glob": "3.0.4", + "regex-cache": "0.4.4" } }, "recast": { @@ -8213,10 +9875,10 @@ "integrity": "sha512-y7ANxCWmMW8xLOaiopiRDlyjQ9ajKRENBH+2wjntIbk3A6ZR1+BLQttkmSHMY7Arl+AAZFwJ10grg2T6f1WI8A==", "requires": { "ast-types": "0.10.1", - "core-js": "^2.4.1", - "esprima": "~4.0.0", - "private": "~0.1.5", - "source-map": "~0.6.1" + "core-js": "2.5.3", + "esprima": "4.0.0", + "private": "0.1.8", + "source-map": "0.6.1" } }, "source-map": { @@ -8229,9 +9891,9 @@ "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-1.3.4.tgz", "integrity": "sha1-+Aek8LHZ6ROuekgRLmzDrxmRtF8=", "requires": { - "graceful-fs": "^4.1.11", - "imurmurhash": "^0.1.4", - "slide": "^1.1.5" + "graceful-fs": "4.1.11", + "imurmurhash": "0.1.4", + "slide": "1.1.6" } } } @@ -8241,31 +9903,31 @@ "resolved": "https://registry.npmjs.org/webpack-cli/-/webpack-cli-2.0.13.tgz", "integrity": "sha512-0lnOi3yla8FsZVuMsbfnNRB/8DlfuDugKdekC+4ykydZG0+UOidMi5J5LLWN4c0VJ8PqC19yMXXkYyCq78OuqA==", "requires": { - "chalk": "^2.3.2", - "cross-spawn": "^6.0.5", - "diff": "^3.5.0", - "enhanced-resolve": "^4.0.0", - "glob-all": "^3.1.0", - "global-modules": "^1.0.0", - "got": "^8.2.0", - "inquirer": "^5.1.0", - "interpret": "^1.0.4", - "jscodeshift": "^0.5.0", - "listr": "^0.13.0", - "loader-utils": "^1.1.0", - "lodash": "^4.17.5", - "log-symbols": "^2.2.0", - "mkdirp": "^0.5.1", - "p-each-series": "^1.0.0", - "p-lazy": "^1.0.0", - "prettier": "^1.5.3", - "resolve-cwd": "^2.0.0", - "supports-color": "^5.3.0", - "v8-compile-cache": "^1.1.2", - "webpack-addons": "^1.1.5", - "yargs": "^11.0.0", - "yeoman-environment": "^2.0.0", - "yeoman-generator": "^2.0.3" + "chalk": "2.3.2", + "cross-spawn": "6.0.5", + "diff": "3.5.0", + "enhanced-resolve": "4.0.0", + "glob-all": "3.1.0", + "global-modules": "1.0.0", + "got": "8.3.0", + "inquirer": "5.2.0", + "interpret": "1.1.0", + "jscodeshift": "0.5.0", + "listr": "0.13.0", + "loader-utils": "1.1.0", + "lodash": "4.17.5", + "log-symbols": "2.2.0", + "mkdirp": "0.5.1", + "p-each-series": "1.0.0", + "p-lazy": "1.0.0", + "prettier": "1.11.1", + "resolve-cwd": "2.0.0", + "supports-color": "5.3.0", + "v8-compile-cache": "1.1.2", + "webpack-addons": "1.1.5", + "yargs": "11.0.0", + "yeoman-environment": "2.0.5", + "yeoman-generator": "2.0.3" }, "dependencies": { "ansi-regex": { @@ -8283,9 +9945,9 @@ "resolved": "https://registry.npmjs.org/cliui/-/cliui-4.0.0.tgz", "integrity": "sha512-nY3W5Gu2racvdDk//ELReY+dHjb9PlIcVDFXP72nVIhq2Gy3LuVXYwJoPVudwQnv1shtohpgkdCKT2YaKY0CKw==", "requires": { - "string-width": "^2.1.1", - "strip-ansi": "^4.0.0", - "wrap-ansi": "^2.0.0" + "string-width": "2.1.1", + "strip-ansi": "4.0.0", + "wrap-ansi": "2.1.0" } }, "cross-spawn": { @@ -8293,11 +9955,11 @@ "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-6.0.5.tgz", "integrity": "sha512-eTVLrBSt7fjbDygz805pMnstIs2VTBNkRm0qxZd+M7A5XDdxVRWO5MxGBXZhjY4cqLYLdtrGqRf8mBPmzwSpWQ==", "requires": { - "nice-try": "^1.0.4", - "path-key": "^2.0.1", - "semver": "^5.5.0", - "shebang-command": "^1.2.0", - "which": "^1.2.9" + "nice-try": "1.0.4", + "path-key": "2.0.1", + "semver": "5.5.0", + "shebang-command": "1.2.0", + "which": "1.3.0" } }, "diff": { @@ -8310,7 +9972,7 @@ "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", "requires": { - "locate-path": "^2.0.0" + "locate-path": "2.0.0" } }, "got": { @@ -8318,23 +9980,23 @@ "resolved": "https://registry.npmjs.org/got/-/got-8.3.0.tgz", "integrity": "sha512-kBNy/S2CGwrYgDSec5KTWGKUvupwkkTVAjIsVFF2shXO13xpZdFP4d4kxa//CLX2tN/rV0aYwK8vY6UKWGn2vQ==", "requires": { - "@sindresorhus/is": "^0.7.0", - "cacheable-request": "^2.1.1", - "decompress-response": "^3.3.0", - "duplexer3": "^0.1.4", - "get-stream": "^3.0.0", - "into-stream": "^3.1.0", - "is-retry-allowed": "^1.1.0", - "isurl": "^1.0.0-alpha5", - "lowercase-keys": "^1.0.0", - "mimic-response": "^1.0.0", - "p-cancelable": "^0.4.0", - "p-timeout": "^2.0.1", - "pify": "^3.0.0", - "safe-buffer": "^5.1.1", - "timed-out": "^4.0.1", - "url-parse-lax": "^3.0.0", - "url-to-options": "^1.0.1" + "@sindresorhus/is": "0.7.0", + "cacheable-request": "2.1.4", + "decompress-response": "3.3.0", + "duplexer3": "0.1.4", + "get-stream": "3.0.0", + "into-stream": "3.1.0", + "is-retry-allowed": "1.1.0", + "isurl": "1.0.0", + "lowercase-keys": "1.0.0", + "mimic-response": "1.0.0", + "p-cancelable": "0.4.0", + "p-timeout": "2.0.1", + "pify": "3.0.0", + "safe-buffer": "5.1.1", + "timed-out": "4.0.1", + "url-parse-lax": "3.0.0", + "url-to-options": "1.0.1" } }, "has-flag": { @@ -8352,9 +10014,9 @@ "resolved": "https://registry.npmjs.org/os-locale/-/os-locale-2.1.0.tgz", "integrity": "sha512-3sslG3zJbEYcaC4YVAvDorjGxc7tv6KVATnLPZONiljsUncvihe9BQoVCEs0RZ1kmf4Hk9OBqlZfJZWI4GanKA==", "requires": { - "execa": "^0.7.0", - "lcid": "^1.0.0", - "mem": "^1.1.0" + "execa": "0.7.0", + "lcid": "1.0.0", + "mem": "1.1.0" } }, "pify": { @@ -8372,8 +10034,8 @@ "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", "requires": { - "is-fullwidth-code-point": "^2.0.0", - "strip-ansi": "^4.0.0" + "is-fullwidth-code-point": "2.0.0", + "strip-ansi": "4.0.0" } }, "strip-ansi": { @@ -8381,7 +10043,7 @@ "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", "requires": { - "ansi-regex": "^3.0.0" + "ansi-regex": "3.0.0" } }, "supports-color": { @@ -8389,7 +10051,7 @@ "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.3.0.tgz", "integrity": "sha512-0aP01LLIskjKs3lq52EC0aGBAJhLq7B2Rd8HC/DR/PtNNpcLilNmHC12O+hu0usQpo7wtHNRqtrhBwtDb0+dNg==", "requires": { - "has-flag": "^3.0.0" + "has-flag": "3.0.0" } }, "url-parse-lax": { @@ -8397,7 +10059,7 @@ "resolved": "https://registry.npmjs.org/url-parse-lax/-/url-parse-lax-3.0.0.tgz", "integrity": "sha1-FrXK/Afb42dsGxmZF3gj1lA6yww=", "requires": { - "prepend-http": "^2.0.0" + "prepend-http": "2.0.0" } }, "which-module": { @@ -8410,18 +10072,18 @@ "resolved": "https://registry.npmjs.org/yargs/-/yargs-11.0.0.tgz", "integrity": "sha512-Rjp+lMYQOWtgqojx1dEWorjCofi1YN7AoFvYV7b1gx/7dAAeuI4kN5SZiEvr0ZmsZTOpDRcCqrpI10L31tFkBw==", "requires": { - "cliui": "^4.0.0", - "decamelize": "^1.1.1", - "find-up": "^2.1.0", - "get-caller-file": "^1.0.1", - "os-locale": "^2.0.0", - "require-directory": "^2.1.1", - "require-main-filename": "^1.0.1", - "set-blocking": "^2.0.0", - "string-width": "^2.0.0", - "which-module": "^2.0.0", - "y18n": "^3.2.1", - "yargs-parser": "^9.0.2" + "cliui": "4.0.0", + "decamelize": "1.2.0", + "find-up": "2.1.0", + "get-caller-file": "1.0.2", + "os-locale": "2.1.0", + "require-directory": "2.1.1", + "require-main-filename": "1.0.1", + "set-blocking": "2.0.0", + "string-width": "2.1.1", + "which-module": "2.0.0", + "y18n": "3.2.1", + "yargs-parser": "9.0.2" } }, "yargs-parser": { @@ -8429,17 +10091,27 @@ "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-9.0.2.tgz", "integrity": "sha1-nM9qQ0YP5O1Aqbto9I1DuKaMwHc=", "requires": { - "camelcase": "^4.1.0" + "camelcase": "4.1.0" } } } }, + "websocket": { + "version": "git://github.com/frozeman/WebSocket-Node.git#6c72925e3f8aaaea8dc8450f97627e85263999f2", + "dev": true, + "requires": { + "debug": "2.6.8", + "nan": "2.10.0", + "typedarray-to-buffer": "3.1.5", + "yaeti": "0.0.6" + } + }, "which": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/which/-/which-1.3.0.tgz", "integrity": "sha512-xcJpopdamTuY5duC/KnTTNBraPK54YwpenP4lzxU8H91GudWpFv38u0CKjclE1Wi2EH2EDz5LRcHcKbCIzqGyg==", "requires": { - "isexe": "^2.0.0" + "isexe": "2.0.0" } }, "which-module": { @@ -8453,7 +10125,7 @@ "integrity": "sha1-AUKk6KJD+IgsAjOqDgKBqnYVInM=", "dev": true, "requires": { - "string-width": "^2.1.1" + "string-width": "2.1.1" }, "dependencies": { "ansi-regex": { @@ -8474,8 +10146,8 @@ "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", "dev": true, "requires": { - "is-fullwidth-code-point": "^2.0.0", - "strip-ansi": "^4.0.0" + "is-fullwidth-code-point": "2.0.0", + "strip-ansi": "4.0.0" } }, "strip-ansi": { @@ -8484,7 +10156,7 @@ "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", "dev": true, "requires": { - "ansi-regex": "^3.0.0" + "ansi-regex": "3.0.0" } } } @@ -8505,8 +10177,8 @@ "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-2.1.0.tgz", "integrity": "sha1-2Pw9KE3QV5T+hJc8rs3Rz4JP3YU=", "requires": { - "string-width": "^1.0.1", - "strip-ansi": "^3.0.1" + "string-width": "1.0.2", + "strip-ansi": "3.0.1" } }, "wrappy": { @@ -8520,9 +10192,9 @@ "integrity": "sha512-xuPeK4OdjWqtfi59ylvVL0Yn35SF3zgcAcv7rBPFHVaEapaDr4GdGgm3j7ckTwH9wHL7fGmgfAnb0+THrHb8tA==", "dev": true, "requires": { - "graceful-fs": "^4.1.11", - "imurmurhash": "^0.1.4", - "signal-exit": "^3.0.2" + "graceful-fs": "4.1.11", + "imurmurhash": "0.1.4", + "signal-exit": "3.0.2" } }, "ws": { @@ -8530,9 +10202,9 @@ "resolved": "https://registry.npmjs.org/ws/-/ws-3.3.3.tgz", "integrity": "sha512-nnWLa/NwZSt4KQJu51MYlCcSQ5g7INpOrOMt4XV8j4dqTXdmlUmSHQ8/oLC069ckre0fRsgfvsKwbTdtKLCDkA==", "requires": { - "async-limiter": "~1.0.0", - "safe-buffer": "~5.1.0", - "ultron": "~1.1.0" + "async-limiter": "1.0.0", + "safe-buffer": "5.1.1", + "ultron": "1.1.1" } }, "xdg-basedir": { @@ -8546,10 +10218,10 @@ "resolved": "https://registry.npmjs.org/xhr/-/xhr-2.4.1.tgz", "integrity": "sha512-pAIU5vBr9Hiy5cpFIbPnwf0C18ZF86DBsZKrlsf87N5De/JbA6RJ83UP/cv+aljl4S40iRVMqP4pr4sF9Dnj0A==", "requires": { - "global": "~4.3.0", - "is-function": "^1.0.1", - "parse-headers": "^2.0.0", - "xtend": "^4.0.0" + "global": "4.3.2", + "is-function": "1.0.1", + "parse-headers": "2.0.1", + "xtend": "4.0.1" } }, "xhr-request": { @@ -8557,13 +10229,13 @@ "resolved": "https://registry.npmjs.org/xhr-request/-/xhr-request-1.1.0.tgz", "integrity": "sha512-Y7qzEaR3FDtL3fP30k9wO/e+FBnBByZeybKOhASsGP30NIkRAAkKD/sCnLvgEfAIEC1rcmK7YG8f4oEnIrrWzA==", "requires": { - "buffer-to-arraybuffer": "^0.0.5", - "object-assign": "^4.1.1", - "query-string": "^5.0.1", - "simple-get": "^2.7.0", - "timed-out": "^4.0.1", - "url-set-query": "^1.0.0", - "xhr": "^2.0.4" + "buffer-to-arraybuffer": "0.0.5", + "object-assign": "4.1.1", + "query-string": "5.1.1", + "simple-get": "2.7.0", + "timed-out": "4.0.1", + "url-set-query": "1.0.0", + "xhr": "2.4.1" } }, "xhr-request-promise": { @@ -8571,7 +10243,7 @@ "resolved": "https://registry.npmjs.org/xhr-request-promise/-/xhr-request-promise-0.1.2.tgz", "integrity": "sha1-NDxE0e53JrhkgGloLQ+EDIO0Jh0=", "requires": { - "xhr-request": "^1.0.1" + "xhr-request": "1.1.0" } }, "xhr2": { @@ -8580,6 +10252,15 @@ "integrity": "sha1-f4dliEdxbbUCYyOBL4GMras4el8=", "dev": true }, + "xhr2-cookies": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/xhr2-cookies/-/xhr2-cookies-1.1.0.tgz", + "integrity": "sha1-fXdEnQmZGX8VXLc7I99yUF7YnUg=", + "dev": true, + "requires": { + "cookiejar": "2.1.2" + } + }, "xmlhttprequest": { "version": "1.8.0", "resolved": "https://registry.npmjs.org/xmlhttprequest/-/xmlhttprequest-1.8.0.tgz", @@ -8596,6 +10277,12 @@ "resolved": "https://registry.npmjs.org/y18n/-/y18n-3.2.1.tgz", "integrity": "sha1-bRX7qITAhnnA136I53WegR4H+kE=" }, + "yaeti": { + "version": "0.0.6", + "resolved": "https://registry.npmjs.org/yaeti/-/yaeti-0.0.6.tgz", + "integrity": "sha1-8m9ITXJoTPQr7ft2lwqhYI+/lXc=", + "dev": true + }, "yallist": { "version": "2.1.2", "resolved": "https://registry.npmjs.org/yallist/-/yallist-2.1.2.tgz", @@ -8606,20 +10293,20 @@ "resolved": "https://registry.npmjs.org/yargs/-/yargs-4.8.1.tgz", "integrity": "sha1-wMQpJMpKqmsObaFznfshZDn53cA=", "requires": { - "cliui": "^3.2.0", - "decamelize": "^1.1.1", - "get-caller-file": "^1.0.1", - "lodash.assign": "^4.0.3", - "os-locale": "^1.4.0", - "read-pkg-up": "^1.0.1", - "require-directory": "^2.1.1", - "require-main-filename": "^1.0.1", - "set-blocking": "^2.0.0", - "string-width": "^1.0.1", - "which-module": "^1.0.0", - "window-size": "^0.2.0", - "y18n": "^3.2.1", - "yargs-parser": "^2.4.1" + "cliui": "3.2.0", + "decamelize": "1.2.0", + "get-caller-file": "1.0.2", + "lodash.assign": "4.2.0", + "os-locale": "1.4.0", + "read-pkg-up": "1.0.1", + "require-directory": "2.1.1", + "require-main-filename": "1.0.1", + "set-blocking": "2.0.0", + "string-width": "1.0.2", + "which-module": "1.0.0", + "window-size": "0.2.0", + "y18n": "3.2.1", + "yargs-parser": "2.4.1" } }, "yargs-parser": { @@ -8627,8 +10314,18 @@ "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-2.4.1.tgz", "integrity": "sha1-hVaN488VD/SfpRgl8DqMiA3cxcQ=", "requires": { - "camelcase": "^3.0.0", - "lodash.assign": "^4.0.6" + "camelcase": "3.0.0", + "lodash.assign": "4.2.0" + } + }, + "yauzl": { + "version": "2.10.0", + "resolved": "https://registry.npmjs.org/yauzl/-/yauzl-2.10.0.tgz", + "integrity": "sha1-x+sXyT4RLLEIb6bY5R+wZnt5pfk=", + "dev": true, + "requires": { + "buffer-crc32": "0.2.13", + "fd-slicer": "1.1.0" } }, "yeoman-environment": { @@ -8636,19 +10333,19 @@ "resolved": "https://registry.npmjs.org/yeoman-environment/-/yeoman-environment-2.0.5.tgz", "integrity": "sha512-6/W7/B54OPHJXob0n0+pmkwFsirC8cokuQkPSmT/D0lCcSxkKtg/BA6ZnjUBIwjuGqmw3DTrT4en++htaUju5g==", "requires": { - "chalk": "^2.1.0", - "debug": "^3.1.0", - "diff": "^3.3.1", - "escape-string-regexp": "^1.0.2", - "globby": "^6.1.0", - "grouped-queue": "^0.3.3", - "inquirer": "^3.3.0", - "is-scoped": "^1.0.0", - "lodash": "^4.17.4", - "log-symbols": "^2.1.0", - "mem-fs": "^1.1.0", - "text-table": "^0.2.0", - "untildify": "^3.0.2" + "chalk": "2.3.2", + "debug": "3.1.0", + "diff": "3.5.0", + "escape-string-regexp": "1.0.5", + "globby": "6.1.0", + "grouped-queue": "0.3.3", + "inquirer": "3.3.0", + "is-scoped": "1.0.0", + "lodash": "4.17.5", + "log-symbols": "2.2.0", + "mem-fs": "1.1.3", + "text-table": "0.2.0", + "untildify": "3.0.2" }, "dependencies": { "ansi-regex": { @@ -8674,20 +10371,20 @@ "resolved": "https://registry.npmjs.org/inquirer/-/inquirer-3.3.0.tgz", "integrity": "sha512-h+xtnyk4EwKvFWHrUYsWErEVR+igKtLdchu+o0Z1RL7VU/jVMFbYir2bp6bAj8efFNxWqHX0dIss6fJQ+/+qeQ==", "requires": { - "ansi-escapes": "^3.0.0", - "chalk": "^2.0.0", - "cli-cursor": "^2.1.0", - "cli-width": "^2.0.0", - "external-editor": "^2.0.4", - "figures": "^2.0.0", - "lodash": "^4.3.0", + "ansi-escapes": "3.1.0", + "chalk": "2.3.2", + "cli-cursor": "2.1.0", + "cli-width": "2.2.0", + "external-editor": "2.1.0", + "figures": "2.0.0", + "lodash": "4.17.5", "mute-stream": "0.0.7", - "run-async": "^2.2.0", - "rx-lite": "^4.0.8", - "rx-lite-aggregates": "^4.0.8", - "string-width": "^2.1.0", - "strip-ansi": "^4.0.0", - "through": "^2.3.6" + "run-async": "2.3.0", + "rx-lite": "4.0.8", + "rx-lite-aggregates": "4.0.8", + "string-width": "2.1.1", + "strip-ansi": "4.0.0", + "through": "2.3.8" } }, "is-fullwidth-code-point": { @@ -8700,8 +10397,8 @@ "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", "requires": { - "is-fullwidth-code-point": "^2.0.0", - "strip-ansi": "^4.0.0" + "is-fullwidth-code-point": "2.0.0", + "strip-ansi": "4.0.0" } }, "strip-ansi": { @@ -8709,7 +10406,7 @@ "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", "requires": { - "ansi-regex": "^3.0.0" + "ansi-regex": "3.0.0" } } } @@ -8719,31 +10416,31 @@ "resolved": "https://registry.npmjs.org/yeoman-generator/-/yeoman-generator-2.0.3.tgz", "integrity": "sha512-mODmrZ26a94djmGZZuIiomSGlN4wULdou29ZwcySupb2e9FdvoCl7Ps2FqHFjEHio3kOl/iBeaNqrnx3C3NwWg==", "requires": { - "async": "^2.6.0", - "chalk": "^2.3.0", - "cli-table": "^0.3.1", - "cross-spawn": "^5.1.0", - "dargs": "^5.1.0", - "dateformat": "^3.0.2", - "debug": "^3.1.0", - "detect-conflict": "^1.0.0", - "error": "^7.0.2", - "find-up": "^2.1.0", - "github-username": "^4.0.0", - "istextorbinary": "^2.1.0", - "lodash": "^4.17.4", - "make-dir": "^1.1.0", - "mem-fs-editor": "^3.0.2", - "minimist": "^1.2.0", - "pretty-bytes": "^4.0.2", - "read-chunk": "^2.1.0", - "read-pkg-up": "^3.0.0", - "rimraf": "^2.6.2", - "run-async": "^2.0.0", - "shelljs": "^0.8.0", - "text-table": "^0.2.0", - "through2": "^2.0.0", - "yeoman-environment": "^2.0.5" + "async": "2.6.0", + "chalk": "2.3.2", + "cli-table": "0.3.1", + "cross-spawn": "5.1.0", + "dargs": "5.1.0", + "dateformat": "3.0.3", + "debug": "3.1.0", + "detect-conflict": "1.0.1", + "error": "7.0.2", + "find-up": "2.1.0", + "github-username": "4.1.0", + "istextorbinary": "2.2.1", + "lodash": "4.17.5", + "make-dir": "1.2.0", + "mem-fs-editor": "3.0.2", + "minimist": "1.2.0", + "pretty-bytes": "4.0.2", + "read-chunk": "2.1.0", + "read-pkg-up": "3.0.0", + "rimraf": "2.6.2", + "run-async": "2.3.0", + "shelljs": "0.8.1", + "text-table": "0.2.0", + "through2": "2.0.3", + "yeoman-environment": "2.0.5" }, "dependencies": { "debug": { @@ -8759,7 +10456,7 @@ "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", "requires": { - "locate-path": "^2.0.0" + "locate-path": "2.0.0" } }, "load-json-file": { @@ -8767,10 +10464,10 @@ "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-4.0.0.tgz", "integrity": "sha1-L19Fq5HjMhYjT9U62rZo607AmTs=", "requires": { - "graceful-fs": "^4.1.2", - "parse-json": "^4.0.0", - "pify": "^3.0.0", - "strip-bom": "^3.0.0" + "graceful-fs": "4.1.11", + "parse-json": "4.0.0", + "pify": "3.0.0", + "strip-bom": "3.0.0" } }, "minimist": { @@ -8783,8 +10480,8 @@ "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-4.0.0.tgz", "integrity": "sha1-vjX1Qlvh9/bHRxhPmKeIy5lHfuA=", "requires": { - "error-ex": "^1.3.1", - "json-parse-better-errors": "^1.0.1" + "error-ex": "1.3.1", + "json-parse-better-errors": "1.0.1" } }, "path-type": { @@ -8792,7 +10489,7 @@ "resolved": "https://registry.npmjs.org/path-type/-/path-type-3.0.0.tgz", "integrity": "sha512-T2ZUsdZFHgA3u4e5PfPbjd7HDDpxPnQb5jN0SrDsjNSuVXHJqtwTnWqG0B1jZrgmJ/7lj1EmVIByWt1gxGkWvg==", "requires": { - "pify": "^3.0.0" + "pify": "3.0.0" } }, "pify": { @@ -8805,9 +10502,9 @@ "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-3.0.0.tgz", "integrity": "sha1-nLxoaXj+5l0WwA4rGcI3/Pbjg4k=", "requires": { - "load-json-file": "^4.0.0", - "normalize-package-data": "^2.3.2", - "path-type": "^3.0.0" + "load-json-file": "4.0.0", + "normalize-package-data": "2.4.0", + "path-type": "3.0.0" } }, "read-pkg-up": { @@ -8815,8 +10512,8 @@ "resolved": "https://registry.npmjs.org/read-pkg-up/-/read-pkg-up-3.0.0.tgz", "integrity": "sha1-PtSWaF26D4/hGNBpHcUfSh/5bwc=", "requires": { - "find-up": "^2.0.0", - "read-pkg": "^3.0.0" + "find-up": "2.1.0", + "read-pkg": "3.0.0" } }, "strip-bom": { diff --git a/package.json b/package.json index 299b5b46e..05fba92a9 100644 --- a/package.json +++ b/package.json @@ -25,6 +25,6 @@ "eth-gas-reporter": "^0.1.12", "nodemon": "^1.17.3", "solidity-coverage": "^0.4.15", - "truffle-flattener": "^1.2.3" + "truffle-flattener": "^1.2.10" } } From 6b9ce95bccb7dbfa584935c9d198248d2a7b00a0 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 14 Jan 2019 09:34:09 -0300 Subject: [PATCH 045/187] Update getFee to use callcode --- contracts/upgradeable_contracts/RewardableBridge.sol | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/contracts/upgradeable_contracts/RewardableBridge.sol b/contracts/upgradeable_contracts/RewardableBridge.sol index b3a0610f3..f75021958 100644 --- a/contracts/upgradeable_contracts/RewardableBridge.sol +++ b/contracts/upgradeable_contracts/RewardableBridge.sol @@ -15,7 +15,7 @@ contract RewardableBridge is Ownable, OwnedUpgradeability { bytes memory callData = abi.encodeWithSignature("getFee()"); address feeManager = feeManagerContract(); assembly { - let result := delegatecall(gas, feeManager, add(callData, 0x20), mload(callData), 0, 32) + let result := callcode(gas, feeManager, 0x0, add(callData, 0x20), mload(callData), 0, 32) fee := mload(0) switch result From 687afe8e13bd6892b6fb34de9839ffbfb56cbd37 Mon Sep 17 00:00:00 2001 From: Tal Beja Date: Mon, 14 Jan 2019 14:40:06 +0200 Subject: [PATCH 046/187] update BridgMapper contract --- .../upgradeable_contracts/BridgeMapper.sol | 63 ++++++++++++------- 1 file changed, 39 insertions(+), 24 deletions(-) diff --git a/contracts/upgradeable_contracts/BridgeMapper.sol b/contracts/upgradeable_contracts/BridgeMapper.sol index 03d3cb440..ee6337102 100644 --- a/contracts/upgradeable_contracts/BridgeMapper.sol +++ b/contracts/upgradeable_contracts/BridgeMapper.sol @@ -5,15 +5,14 @@ import "../upgradeability/EternalStorage.sol"; contract BridgeMapper is EternalStorage, Ownable { - event NewBridgeDeployed(address indexed homeBridge, address indexed foreignBridge, address indexed homeToken, address indexed foreignToken, uint256 homeStratBlock, uint256 foreignStartBlock); + event BridgeMappingAdded(address indexed foreignToken, address homeToken, address foreignBridge, address homeBridge, uint256 foreignStartBlock, uint256 homeStartBlock); + event BridgeMappingRemoved(address indexed foreignToken); function homeBridgeByForeignToken(address _foreignToken) public view returns(address) { return addressStorage[keccak256(abi.encodePacked("homeBridgeByForeignToken", _foreignToken))]; } - function setHomeBridgeByForeignToken(address _foreignToken, address _homeBridge) internal onlyOwner { - require(_foreignToken != address(0)); - require(_homeBridge != address(0)); + function setHomeBridgeByForeignToken(address _foreignToken, address _homeBridge) internal { addressStorage[keccak256(abi.encodePacked("homeBridgeByForeignToken", _foreignToken))] = _homeBridge; } @@ -21,9 +20,7 @@ contract BridgeMapper is EternalStorage, Ownable { return addressStorage[keccak256(abi.encodePacked("foreignBridgeByForeignToken", _foreignToken))]; } - function setForeignBridgeByForeignToken(address _foreignToken, address _foreignBridge) internal onlyOwner { - require(_foreignToken != address(0)); - require(_foreignBridge != address(0)); + function setForeignBridgeByForeignToken(address _foreignToken, address _foreignBridge) internal { addressStorage[keccak256(abi.encodePacked("foreignBridgeByForeignToken", _foreignToken))] = _foreignBridge; } @@ -31,39 +28,57 @@ contract BridgeMapper is EternalStorage, Ownable { return addressStorage[keccak256(abi.encodePacked("homeTokenByForeignToken", _foreignToken))]; } - function setHomeTokenByForeignToken(address _foreignToken, address _homeToken) internal onlyOwner { - require(_foreignToken != address(0)); - require(_homeToken != address(0)); + function setHomeTokenByForeignToken(address _foreignToken, address _homeToken) internal { addressStorage[keccak256(abi.encodePacked("homeTokenByForeignToken", _foreignToken))] = _homeToken; } - function homeStratBlockByForeignToken(address _foreignToken) public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("homeStratBlockByForeignToken", _foreignToken))]; + function homeStartBlockByForeignToken(address _foreignToken) public view returns(uint256) { + return uintStorage[keccak256(abi.encodePacked("homeStartBlockByForeignToken", _foreignToken))]; } - function setHomeStratBlockByForeignToken(address _foreignToken, uint256 _homeStratBlock) internal onlyOwner { - require(_foreignToken != address(0)); - require(_homeStratBlock != 0); - uintStorage[keccak256(abi.encodePacked("homeStratBlockByForeignToken", _foreignToken))] = _homeStratBlock; + function setHomeStartBlockByForeignToken(address _foreignToken, uint256 _homeStartBlock) internal { + uintStorage[keccak256(abi.encodePacked("homeStartBlockByForeignToken", _foreignToken))] = _homeStartBlock; } function foreignStartBlockByForeignToken(address _foreignToken) public view returns(uint256) { return uintStorage[keccak256(abi.encodePacked("foreignStartBlockByForeignToken", _foreignToken))]; } - function setForeignStartBlockByForeignToken(address _foreignToken, uint256 _foreignStartBlock) internal onlyOwner { - require(_foreignToken != address(0)); - require(_foreignStartBlock != 0); + function setForeignStartBlockByForeignToken(address _foreignToken, uint256 _foreignStartBlock) internal { uintStorage[keccak256(abi.encodePacked("foreignStartBlockByForeignToken", _foreignToken))] = _foreignStartBlock; } - function addBridgeMapping(address _homeBridge, address _foreignBridge, address _homeToken, address _foreignToken, uint256 _homeStratBlock, uint256 _foreignStartBlock) public onlyOwner { - setHomeBridgeByForeignToken(_foreignToken, _homeBridge); - setForeignBridgeByForeignToken(_foreignToken, _foreignBridge); + function addBridgeMapping(address _foreignToken, address _homeToken, address _foreignBridge, address _homeBridge, uint256 _foreignStartBlock, uint256 _homeStartBlock) public onlyOwner { + require(_foreignToken != address(0)); + require(_homeToken != address(0)); + require(_foreignBridge != address(0)); + require(_homeBridge != address(0)); + require(_foreignStartBlock > 0); + require(_homeStartBlock > 0); setHomeTokenByForeignToken(_foreignToken, _homeToken); - setHomeStratBlockByForeignToken(_foreignToken, _homeStratBlock); + setForeignBridgeByForeignToken(_foreignToken, _foreignBridge); + setHomeBridgeByForeignToken(_foreignToken, _homeBridge); setForeignStartBlockByForeignToken(_foreignToken, _foreignStartBlock); - emit NewBridgeDeployed(_homeBridge, _foreignBridge, _homeToken, _foreignToken, _homeStratBlock, _foreignStartBlock); + setHomeStartBlockByForeignToken(_foreignToken, _homeStartBlock); + emit BridgeMappingAdded(_foreignToken, _homeToken, _foreignBridge, _homeBridge, _foreignStartBlock, _homeStartBlock); + } + + function removeBridgeMapping(address _foreignToken) public onlyOwner { + require(_foreignToken != address(0)); + setHomeTokenByForeignToken(_foreignToken, address(0)); + setForeignBridgeByForeignToken(_foreignToken, address(0)); + setHomeBridgeByForeignToken(_foreignToken, address(0)); + setForeignStartBlockByForeignToken(_foreignToken, 0); + setHomeStartBlockByForeignToken(_foreignToken, 0); + emit BridgeMappingRemoved(_foreignToken); + } + + function getBridgeMapperVersion() public pure returns(uint64 major, uint64 minor, uint64 patch) { + return (1, 0, 0); + } + + constructor() public { + setOwner(msg.sender); } } \ No newline at end of file From ee666a15f304de8187c7de8e058ce4314bf38932 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 14 Jan 2019 09:42:19 -0300 Subject: [PATCH 047/187] Update setFee modifier to onlyOwner --- .../RewardableBridge.sol | 5 ++-- test/erc_to_native/home_bridge.test.js | 24 +++++++------------ 2 files changed, 10 insertions(+), 19 deletions(-) diff --git a/contracts/upgradeable_contracts/RewardableBridge.sol b/contracts/upgradeable_contracts/RewardableBridge.sol index f75021958..2bf47cfe2 100644 --- a/contracts/upgradeable_contracts/RewardableBridge.sol +++ b/contracts/upgradeable_contracts/RewardableBridge.sol @@ -1,12 +1,11 @@ pragma solidity 0.4.24; -import "./OwnedUpgradeability.sol"; import "./Ownable.sol"; -contract RewardableBridge is Ownable, OwnedUpgradeability { +contract RewardableBridge is Ownable { - function setFee(uint256 _fee) external onlyIfOwnerOfProxy { + function setFee(uint256 _fee) external onlyOwner { require(feeManagerContract().delegatecall(abi.encodeWithSignature("setFee(uint256)", _fee))); } diff --git a/test/erc_to_native/home_bridge.test.js b/test/erc_to_native/home_bridge.test.js index 74b486fbb..8feebb25e 100644 --- a/test/erc_to_native/home_bridge.test.js +++ b/test/erc_to_native/home_bridge.test.js @@ -795,7 +795,6 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { describe('#feeManager', async () => { let homeBridge, rewardableValidators let owner = accounts[9] - let proxyOwner = accounts[0] let validators = [accounts[1]] let rewards = [accounts[2]] let requiredSignatures = 1 @@ -831,7 +830,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled // When - await homeBridge.setFee(fee, { from: proxyOwner }).should.be.fulfilled + await homeBridge.setFee(fee, { from: owner }).should.be.fulfilled // Then const bridgeFee = await homeBridge.getFee() @@ -842,7 +841,6 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { it('should distribute fee to validator', async () => { // Initialize const owner = accounts[9] - const proxyOwner = accounts[0] const validators = [accounts[1]] const rewards = [accounts[2]] const requiredSignatures = 1 @@ -864,7 +862,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) const feeManager = await FeeManagerErcToNative.new() await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled - await homeBridge.setFee(feeInWei, { from: proxyOwner }).should.be.fulfilled + await homeBridge.setFee(feeInWei, { from: owner }).should.be.fulfilled const recipient = accounts[5]; const value = halfEther; @@ -896,7 +894,6 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { it('should distribute fee to 3 validators', async () => { // Initialize const owner = accounts[9] - const proxyOwner = accounts[0] const validators = [accounts[1], accounts[2], accounts[3]] const rewards = [accounts[4], accounts[5], accounts[6]] const requiredSignatures = 2 @@ -921,7 +918,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const feePerValidator = web3.toBigNumber(166666666666666) const feeManager = await FeeManagerErcToNative.new() await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled - await homeBridge.setFee(feeInWei, { from: proxyOwner }).should.be.fulfilled + await homeBridge.setFee(feeInWei, { from: owner }).should.be.fulfilled const recipient = accounts[8]; const balanceBefore = await web3.eth.getBalance(recipient) @@ -965,7 +962,6 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { it('should distribute fee to 5 validators', async () => { // Initialize const owner = accounts[0] - const proxyOwner = accounts[0] const validators = [accounts[0], accounts[1], accounts[2], accounts[3], accounts[4]] const rewards = [accounts[5], accounts[6], accounts[7], accounts[8], accounts[9]] const requiredSignatures = 5 @@ -990,7 +986,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const feePerValidator = feeAmount.div(web3.toBigNumber(5)) const feeManager = await FeeManagerErcToNative.new() await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled - await homeBridge.setFee(feeInWei, { from: proxyOwner }).should.be.fulfilled + await homeBridge.setFee(feeInWei, { from: owner }).should.be.fulfilled const recipient = "0xf4bef13f9f4f2b203faf0c3cbbaabe1afe056955"; const balanceBefore = await web3.eth.getBalance(recipient) @@ -1044,7 +1040,6 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { describe('#feeManager_fallback', function () { let homeBridge, rewardableValidators let owner = accounts[9] - let proxyOwner = accounts[0] let validators = [accounts[1]] let rewards = [accounts[2]] let requiredSignatures = 1 @@ -1068,7 +1063,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) const feeManager = await FeeManagerErcToNative.new() await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled - await homeBridge.setFee(feeInWei, { from: proxyOwner }).should.be.fulfilled + await homeBridge.setFee(feeInWei, { from: owner }).should.be.fulfilled // When const { logs } = await homeBridge.sendTransaction({ from: recipient, value }).should.be.fulfilled @@ -1088,7 +1083,6 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { it('should distribute fee to validator', async () => { // Initialize const owner = accounts[9] - const proxyOwner = accounts[0] const validators = [accounts[1]] const rewards = [accounts[2]] const requiredSignatures = 1 @@ -1107,7 +1101,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) const feeManager = await FeeManagerErcToNative.new() await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled - await homeBridge.setFee(feeInWei, { from: proxyOwner }).should.be.fulfilled + await homeBridge.setFee(feeInWei, { from: owner }).should.be.fulfilled const recipient = accounts[5]; const initialValue = halfEther @@ -1144,7 +1138,6 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { it('should distribute fee to 3 validators', async () => { // Initialize const owner = accounts[9] - const proxyOwner = accounts[0] const validators = [accounts[1], accounts[2], accounts[3]] const rewards = [accounts[4], accounts[5], accounts[6]] const requiredSignatures = 3 @@ -1164,7 +1157,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const feeManager = await FeeManagerErcToNative.new() const feePerValidator = web3.toBigNumber(166666666666666) await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled - await homeBridge.setFee(feeInWei, { from: proxyOwner }).should.be.fulfilled + await homeBridge.setFee(feeInWei, { from: owner }).should.be.fulfilled const recipient = accounts[7]; const initialValue = halfEther @@ -1210,7 +1203,6 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { it('should distribute fee to 5 validators', async () => { // Initialize const owner = accounts[0] - const proxyOwner = accounts[0] const validators = [accounts[0], accounts[1], accounts[2], accounts[3], accounts[4]] const rewards = [accounts[5], accounts[6], accounts[7], accounts[8], accounts[9]] const requiredSignatures = 5 @@ -1229,7 +1221,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) const feeManager = await FeeManagerErcToNative.new() await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled - await homeBridge.setFee(feeInWei, { from: proxyOwner }).should.be.fulfilled + await homeBridge.setFee(feeInWei, { from: owner }).should.be.fulfilled const recipient = accounts[0]; const initialValue = halfEther From 4b8f53a01459a6c31768acad7a8acbe8f079f4ad Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 14 Jan 2019 10:19:03 -0300 Subject: [PATCH 048/187] Refactor BaseFeeManager fee direction --- .../upgradeable_contracts/BaseFeeManager.sol | 16 ++++++++++------ 1 file changed, 10 insertions(+), 6 deletions(-) diff --git a/contracts/upgradeable_contracts/BaseFeeManager.sol b/contracts/upgradeable_contracts/BaseFeeManager.sol index af8781e07..77e81f6c6 100644 --- a/contracts/upgradeable_contracts/BaseFeeManager.sol +++ b/contracts/upgradeable_contracts/BaseFeeManager.sol @@ -8,6 +8,10 @@ import "../IRewardableValidators.sol"; contract BaseFeeManager is EternalStorage { using SafeMath for uint256; + bytes32 public constant REWARD_FOR_TRANSFERRING_FROM_HOME = keccak256(abi.encodePacked("reward-transferring-from-home")); + + bytes32 public constant REWARD_FOR_TRANSFERRING_FROM_FOREIGN = keccak256(abi.encodePacked("reward-transferring-from-foreign")); + event FeeUpdated(uint256 fee); function calculateFee(uint256 _value, bool _recover) external view returns(uint256) { @@ -29,26 +33,26 @@ contract BaseFeeManager is EternalStorage { } function distributeFeeFromAffirmation(uint256 _fee) external { - distributeFeeProportionally(_fee, true); + distributeFeeProportionally(_fee, REWARD_FOR_TRANSFERRING_FROM_FOREIGN); } function distributeFeeFromSignatures(uint256 _fee) external { - distributeFeeProportionally(_fee, false); + distributeFeeProportionally(_fee, REWARD_FOR_TRANSFERRING_FROM_HOME); } - function distributeFeeProportionally(uint256 _fee, bool _isAffirmation) internal { + function distributeFeeProportionally(uint256 _fee, bytes32 _direction) internal { IRewardableValidators validators = rewardableValidatorContract(); address [] memory validatorList = validators.validatorList(); uint256 feePerValidator = _fee.div(validatorList.length); for (uint256 i = 0; i < validatorList.length; i++) { address rewardAddress = validators.getValidatorRewardAddress(validatorList[i]); - onFeeDistribution(rewardAddress, feePerValidator, _isAffirmation); + onFeeDistribution(rewardAddress, feePerValidator, _direction); } } - function onFeeDistribution(address _rewardAddress, uint256 _fee, bool _isAffirmation) internal { - if (_isAffirmation) { + function onFeeDistribution(address _rewardAddress, uint256 _fee, bytes32 _direction) internal { + if (_direction == REWARD_FOR_TRANSFERRING_FROM_FOREIGN) { onAffirmationFeeDistribution(_rewardAddress, _fee); } else { onSignatureFeeDistribution(_rewardAddress, _fee); From 71870e0076fb801699c5c337bf52f221a214c83a Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 14 Jan 2019 12:16:32 -0300 Subject: [PATCH 049/187] Add random fee distribution on remaining fee difference --- .../upgradeable_contracts/BaseFeeManager.sol | 18 +++++- test/erc_to_native/home_bridge.test.js | 56 ++++++++++++++++--- 2 files changed, 65 insertions(+), 9 deletions(-) diff --git a/contracts/upgradeable_contracts/BaseFeeManager.sol b/contracts/upgradeable_contracts/BaseFeeManager.sol index 77e81f6c6..93c462265 100644 --- a/contracts/upgradeable_contracts/BaseFeeManager.sol +++ b/contracts/upgradeable_contracts/BaseFeeManager.sol @@ -40,14 +40,28 @@ contract BaseFeeManager is EternalStorage { distributeFeeProportionally(_fee, REWARD_FOR_TRANSFERRING_FROM_HOME); } + function random(uint256 _count) public view returns(uint256) { + return uint256(blockhash(block.number.sub(1))) % _count; + } + function distributeFeeProportionally(uint256 _fee, bytes32 _direction) internal { IRewardableValidators validators = rewardableValidatorContract(); - address [] memory validatorList = validators.validatorList(); + address[] memory validatorList = validators.validatorList(); uint256 feePerValidator = _fee.div(validatorList.length); + uint256 randomValidatorIndex; + uint256 diff = _fee.sub(feePerValidator.mul(validatorList.length)); + if (diff > 0) { + randomValidatorIndex = random(validatorList.length); + } + for (uint256 i = 0; i < validatorList.length; i++) { + uint256 feeToDistribute = feePerValidator; + if (diff > 0 && randomValidatorIndex == i) { + feeToDistribute = feeToDistribute.add(diff); + } address rewardAddress = validators.getValidatorRewardAddress(validatorList[i]); - onFeeDistribution(rewardAddress, feePerValidator, _direction); + onFeeDistribution(rewardAddress, feeToDistribute, _direction); } } diff --git a/test/erc_to_native/home_bridge.test.js b/test/erc_to_native/home_bridge.test.js index 8feebb25e..c97a275f0 100644 --- a/test/erc_to_native/home_bridge.test.js +++ b/test/erc_to_native/home_bridge.test.js @@ -899,6 +899,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const requiredSignatures = 2 const rewardableValidators = await RewardableValidators.new() const homeBridgeImpl = await HomeBridge.new(); + const blockRewardContract = await BlockReward.new() const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled const homeBridge = await HomeBridge.at(storageProxy.address); @@ -906,16 +907,20 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled await blockRewardContract.sendTransaction({ from: accounts[0], - value: oneEther + value: halfEther }).should.be.fulfilled // Given + const initialBlockRewardBalance = await web3.eth.getBalance(blockRewardContract.address) + initialBlockRewardBalance.should.be.bignumber.equal(halfEther) + const value = halfEther; // 0.1% fee const fee = 0.001 const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) // totalFee / 3 const feePerValidator = web3.toBigNumber(166666666666666) + const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) const feeManager = await FeeManagerErcToNative.new() await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setFee(feeInWei, { from: owner }).should.be.fulfilled @@ -955,9 +960,18 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) - updatedBalanceRewardAddress1.should.be.bignumber.equal(initialBalanceRewardAddress1.add(feePerValidator)) - updatedBalanceRewardAddress2.should.be.bignumber.equal(initialBalanceRewardAddress2.add(feePerValidator)) - updatedBalanceRewardAddress3.should.be.bignumber.equal(initialBalanceRewardAddress3.add(feePerValidator)) + expect( + updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidator)) + || updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidatorPlusDiff))).to.equal(true) + expect( + updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidator)) + || updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidatorPlusDiff))).to.equal(true) + expect( + updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidator)) + || updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidatorPlusDiff))).to.equal(true) + + const blockRewardBalance = await web3.eth.getBalance(blockRewardContract.address) + blockRewardBalance.should.be.bignumber.equal('0') }) it('should distribute fee to 5 validators', async () => { // Initialize @@ -1156,6 +1170,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) const feeManager = await FeeManagerErcToNative.new() const feePerValidator = web3.toBigNumber(166666666666666) + const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setFee(feeInWei, { from: owner }).should.be.fulfilled @@ -1196,9 +1211,18 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) - updatedBalanceRewardAddress1.should.be.bignumber.equal(initialBalanceRewardAddress1.add(feePerValidator)) - updatedBalanceRewardAddress2.should.be.bignumber.equal(initialBalanceRewardAddress2.add(feePerValidator)) - updatedBalanceRewardAddress3.should.be.bignumber.equal(initialBalanceRewardAddress3.add(feePerValidator)) + const bridgeBalance = await web3.eth.getBalance(homeBridge.address) + bridgeBalance.should.be.bignumber.equal('0') + + expect( + updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidator)) + || updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidatorPlusDiff))).to.equal(true) + expect( + updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidator)) + || updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidatorPlusDiff))).to.equal(true) + expect( + updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidator)) + || updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidatorPlusDiff))).to.equal(true) }) it('should distribute fee to 5 validators', async () => { // Initialize @@ -1276,4 +1300,22 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { updatedBalanceRewardAddress5.should.be.bignumber.equal(initialBalanceRewardAddress5.add(feePerValidator)) }) }) + describe('#FeeManager_random', async () => { + it('should return value between 0 and 3', async () => { + // Given + const feeManager = await FeeManagerErcToNative.new() + + for (let i = 0; i < 10; i++) { + // send Tx to generate new blocks + await feeManager.setFee(0).should.be.fulfilled + + // When + const result = await feeManager.random(3); + + // Then + result.should.be.bignumber.gte(0); + result.should.be.bignumber.lt(3); + } + }) + }) }) From 161c24fb62d3ecbeafe0cc0b429a1cc3ecdb08e4 Mon Sep 17 00:00:00 2001 From: Tal Beja Date: Tue, 15 Jan 2019 16:01:12 +0200 Subject: [PATCH 050/187] both home and foreign bridge factory (wih deployment scripts) --- contracts/IBridgeValidators.sol | 1 + contracts/IForeignBridge.sol | 7 + contracts/IHomeBridge.sol | 7 + contracts/upgradeability/EternalStorage.sol | 8 + .../upgradeable_contracts/BridgeMapper.sol | 4 +- .../BridgeValidators.sol | 4 +- .../{Ownable.sol => EternalOwnable.sol} | 4 +- .../factories/ForeignBridgeFactory.sol | 138 +++++++++++ .../factories/HomeBridgeFactory.sol | 180 +++++++++++++++ deploy/.env.example | 5 + deploy/deploy.js | 38 +++- deploy/src/deploymentUtils.js | 1 + deploy/src/factories/foreign.js | 159 +++++++++++++ deploy/src/factories/home.js | 215 ++++++++++++++++++ deploy/src/loadEnv.js | 12 +- flatten.sh | 5 + 16 files changed, 780 insertions(+), 8 deletions(-) create mode 100644 contracts/IForeignBridge.sol create mode 100644 contracts/IHomeBridge.sol rename contracts/upgradeable_contracts/{Ownable.sol => EternalOwnable.sol} (95%) create mode 100644 contracts/upgradeable_contracts/factories/ForeignBridgeFactory.sol create mode 100644 contracts/upgradeable_contracts/factories/HomeBridgeFactory.sol create mode 100644 deploy/src/factories/foreign.js create mode 100644 deploy/src/factories/home.js diff --git a/contracts/IBridgeValidators.sol b/contracts/IBridgeValidators.sol index 2732ae41e..775e94194 100644 --- a/contracts/IBridgeValidators.sol +++ b/contracts/IBridgeValidators.sol @@ -2,6 +2,7 @@ pragma solidity 0.4.24; interface IBridgeValidators { + function initialize(uint256 _requiredSignatures, address[] _initialValidators, address _owner) public returns(bool); function isValidator(address _validator) public view returns(bool); function requiredSignatures() public view returns(uint256); function owner() public view returns(address); diff --git a/contracts/IForeignBridge.sol b/contracts/IForeignBridge.sol new file mode 100644 index 000000000..8697e3a15 --- /dev/null +++ b/contracts/IForeignBridge.sol @@ -0,0 +1,7 @@ +pragma solidity 0.4.24; + +contract IForeignBridge { + + function initialize(address _validatorContract, address _erc20token, uint256 _requiredBlockConfirmations, uint256 _gasPrice) public returns(bool); + +} diff --git a/contracts/IHomeBridge.sol b/contracts/IHomeBridge.sol new file mode 100644 index 000000000..8ac8556f9 --- /dev/null +++ b/contracts/IHomeBridge.sol @@ -0,0 +1,7 @@ +pragma solidity 0.4.24; + +contract IHomeBridge { + + function initialize(address _validatorContract, uint256 _dailyLimit, uint256 _maxPerTx, uint256 _minPerTx, uint256 _homeGasPrice, uint256 _requiredBlockConfirmations, address _erc677token) public returns(bool); + +} diff --git a/contracts/upgradeability/EternalStorage.sol b/contracts/upgradeability/EternalStorage.sol index a8702dcab..b9d6c0e1f 100644 --- a/contracts/upgradeability/EternalStorage.sol +++ b/contracts/upgradeability/EternalStorage.sol @@ -14,4 +14,12 @@ contract EternalStorage { mapping(bytes32 => bool) internal boolStorage; mapping(bytes32 => int256) internal intStorage; + + mapping(bytes32 => uint256[]) internal uintArrayStorage; + mapping(bytes32 => string[]) internal stringArrayStorage; + mapping(bytes32 => address[]) internal addressArrayStorage; + //mapping(bytes32 => bytes[]) internal bytesArrayStorage; + mapping(bytes32 => bool[]) internal boolArrayStorage; + mapping(bytes32 => int256[]) internal intArrayStorage; + mapping(bytes32 => bytes32[]) internal bytes32ArrayStorage; } diff --git a/contracts/upgradeable_contracts/BridgeMapper.sol b/contracts/upgradeable_contracts/BridgeMapper.sol index ee6337102..73f6768a5 100644 --- a/contracts/upgradeable_contracts/BridgeMapper.sol +++ b/contracts/upgradeable_contracts/BridgeMapper.sol @@ -1,9 +1,9 @@ pragma solidity 0.4.24; -import "./Ownable.sol"; +import "./EternalOwnable.sol"; import "../upgradeability/EternalStorage.sol"; -contract BridgeMapper is EternalStorage, Ownable { +contract BridgeMapper is EternalStorage, EternalOwnable { event BridgeMappingAdded(address indexed foreignToken, address homeToken, address foreignBridge, address homeBridge, uint256 foreignStartBlock, uint256 homeStartBlock); event BridgeMappingRemoved(address indexed foreignToken); diff --git a/contracts/upgradeable_contracts/BridgeValidators.sol b/contracts/upgradeable_contracts/BridgeValidators.sol index d3ee1edba..45bc60b90 100644 --- a/contracts/upgradeable_contracts/BridgeValidators.sol +++ b/contracts/upgradeable_contracts/BridgeValidators.sol @@ -1,12 +1,12 @@ pragma solidity 0.4.24; -import "./Ownable.sol"; +import "./EternalOwnable.sol"; import "../IBridgeValidators.sol"; import "../libraries/SafeMath.sol"; import "../upgradeability/EternalStorage.sol"; -contract BridgeValidators is IBridgeValidators, EternalStorage, Ownable { +contract BridgeValidators is IBridgeValidators, EternalStorage, EternalOwnable { using SafeMath for uint256; event ValidatorAdded (address indexed validator); diff --git a/contracts/upgradeable_contracts/Ownable.sol b/contracts/upgradeable_contracts/EternalOwnable.sol similarity index 95% rename from contracts/upgradeable_contracts/Ownable.sol rename to contracts/upgradeable_contracts/EternalOwnable.sol index 35ccf44fb..4a8ddca56 100644 --- a/contracts/upgradeable_contracts/Ownable.sol +++ b/contracts/upgradeable_contracts/EternalOwnable.sol @@ -4,10 +4,10 @@ import "../upgradeability/EternalStorage.sol"; /** - * @title Ownable + * @title EternalOwnable * @dev This contract has an owner address providing basic authorization control */ -contract Ownable is EternalStorage { +contract EternalOwnable is EternalStorage { /** * @dev Event to show ownership has been transferred * @param previousOwner representing the address of the previous owner diff --git a/contracts/upgradeable_contracts/factories/ForeignBridgeFactory.sol b/contracts/upgradeable_contracts/factories/ForeignBridgeFactory.sol new file mode 100644 index 000000000..3682e8640 --- /dev/null +++ b/contracts/upgradeable_contracts/factories/ForeignBridgeFactory.sol @@ -0,0 +1,138 @@ +pragma solidity 0.4.24; + +import "../../IBridgeValidators.sol"; +import "../../IForeignBridge.sol"; +import "../../upgradeability/EternalStorageProxy.sol"; +import "../../upgradeability/EternalStorage.sol"; +import "../EternalOwnable.sol"; + +contract ForeignBridgeFactory is EternalStorage, EternalOwnable { + + function initialize(address _owner, + address _bridgeValidatorsImplementation, + uint256 _requiredSignatures, + address[] _initialValidators, + address _bridgeValidatorsOwner, + address _bridgeValidatorsProxyOwner, + address _foreignBridgeErcToErcImplementation, + uint256 _requiredBlockConfirmations, + uint256 _gasPrice, + address _foreignBridgeProxyOwner) public { + + require(_owner != address(0)); + require(_bridgeValidatorsImplementation != address(0)); + require(_requiredSignatures >= 1); + require(_bridgeValidatorsOwner != address(0)); + require(_bridgeValidatorsProxyOwner != address(0)); + require(_foreignBridgeErcToErcImplementation != address(0)); + require(_requiredBlockConfirmations > 0); + require(_foreignBridgeProxyOwner != address(0)); + + setOwner(_owner); + setBridgeValidatorsImplementation(_bridgeValidatorsImplementation); + setRequiredSignatures(_requiredSignatures); + setInitialValidators(_initialValidators); + setBridgeValidatorsOwner(_bridgeValidatorsOwner); + setBridgeValidatorsProxyOwner(_bridgeValidatorsProxyOwner); + setForeignBridgeErcToErcImplementation(_foreignBridgeErcToErcImplementation); + setRequiredBlockConfirmations(_requiredBlockConfirmations); + setGasPrice(_gasPrice); + setForeignBridgeProxyOwner(_foreignBridgeProxyOwner); + } + + function deployForeignBridge(address _erc20Token) public onlyOwner { + // deploy new EternalStorageProxy + EternalStorageProxy proxy = new EternalStorageProxy(); + // connect it to the static BridgeValidators implementation + proxy.upgradeTo(1, bridgeValidatorsImplementation()); + // cast proxy as IBridgeValidators + IBridgeValidators bridgeValidators = IBridgeValidators(proxy); + // initialize bridgeValidators + bridgeValidators.initialize(requiredSignatures(), initialValidators(), bridgeValidatorsOwner()); + // transger proxy upgradeability admin + proxy.transferProxyOwnership(bridgeValidatorsProxyOwner()); + // deploy new EternalStorageProxy + proxy = new EternalStorageProxy(); + // connect it to the static ForeignBridgeErcToErc implementation + proxy.upgradeTo(1, foreignBridgeErcToErcImplementation()); + // cast proxy as IForeignBridge + IForeignBridge foreignBridge = IForeignBridge(proxy); + // initialize foreignBridge + foreignBridge.initialize(bridgeValidators, _erc20Token, requiredBlockConfirmations(), gasPrice()); + // transger proxy upgradeability admin + proxy.transferProxyOwnership(foreignBridgeProxyOwner()); + } + + + function bridgeValidatorsImplementation() public view returns(address) { + return addressStorage[keccak256(abi.encodePacked("bridgeValidatorsImplementation"))]; + } + + function setBridgeValidatorsImplementation(address _bridgeValidatorsImplementation) public onlyOwner { + addressStorage[keccak256(abi.encodePacked("bridgeValidatorsImplementation"))] = _bridgeValidatorsImplementation; + } + + function requiredSignatures() public view returns(uint256) { + return uintStorage[keccak256(abi.encodePacked("requiredSignatures"))]; + } + + function setRequiredSignatures(uint256 _requiredSignatures) public onlyOwner { + uintStorage[keccak256(abi.encodePacked("requiredSignatures"))] = _requiredSignatures; + } + + function initialValidators() public view returns(address[]) { + return addressArrayStorage[keccak256(abi.encodePacked("initialValidators"))]; + } + + function setInitialValidators(address[] _initialValidators) public onlyOwner { + addressArrayStorage[keccak256(abi.encodePacked("initialValidators"))] = _initialValidators; + } + + function bridgeValidatorsOwner() public view returns(address) { + return addressStorage[keccak256(abi.encodePacked("bridgeValidatorsOwner"))]; + } + + function setBridgeValidatorsOwner(address _bridgeValidatorsOwner) public onlyOwner { + addressStorage[keccak256(abi.encodePacked("bridgeValidatorsOwner"))] = _bridgeValidatorsOwner; + } + + function bridgeValidatorsProxyOwner() public view returns(address) { + return addressStorage[keccak256(abi.encodePacked("bridgeValidatorsProxyOwner"))]; + } + + function setBridgeValidatorsProxyOwner(address _bridgeValidatorsProxyOwner) public onlyOwner { + addressStorage[keccak256(abi.encodePacked("bridgeValidatorsProxyOwner"))] = _bridgeValidatorsProxyOwner; + } + + function foreignBridgeErcToErcImplementation() public view returns(address) { + return addressStorage[keccak256(abi.encodePacked("foreignBridgeErcToErcImplementation"))]; + } + + function setForeignBridgeErcToErcImplementation(address _foreignBridgeErcToErcImplementation) public onlyOwner { + addressStorage[keccak256(abi.encodePacked("foreignBridgeErcToErcImplementation"))] = _foreignBridgeErcToErcImplementation; + } + + function requiredBlockConfirmations() public view returns(uint256) { + return uintStorage[keccak256(abi.encodePacked("requiredBlockConfirmations"))]; + } + + function setRequiredBlockConfirmations(uint256 _requiredBlockConfirmations) public onlyOwner { + uintStorage[keccak256(abi.encodePacked("requiredBlockConfirmations"))] = _requiredBlockConfirmations; + } + + function gasPrice() public view returns(uint256) { + return uintStorage[keccak256(abi.encodePacked("gasPrice"))]; + } + + function setGasPrice(uint256 _gasPrice) public onlyOwner { + uintStorage[keccak256(abi.encodePacked("gasPrice"))] = _gasPrice; + } + + function foreignBridgeProxyOwner() public view returns(address) { + return addressStorage[keccak256(abi.encodePacked("foreignBridgeProxyOwner"))]; + } + + function setForeignBridgeProxyOwner(address _foreignBridgeProxyOwner) public onlyOwner { + addressStorage[keccak256(abi.encodePacked("foreignBridgeProxyOwner"))] = _foreignBridgeProxyOwner; + } +} \ No newline at end of file diff --git a/contracts/upgradeable_contracts/factories/HomeBridgeFactory.sol b/contracts/upgradeable_contracts/factories/HomeBridgeFactory.sol new file mode 100644 index 000000000..4416c14b2 --- /dev/null +++ b/contracts/upgradeable_contracts/factories/HomeBridgeFactory.sol @@ -0,0 +1,180 @@ +pragma solidity 0.4.24; + +import "../../IBridgeValidators.sol"; +import "../../IHomeBridge.sol"; +import "../../upgradeability/EternalStorageProxy.sol"; +import "../../upgradeability/EternalStorage.sol"; +import "../../ERC677BridgeToken.sol"; +import "../EternalOwnable.sol"; + +contract HomeBridgeFactory is EternalStorage, EternalOwnable { + + function initialize(address _owner, + address _bridgeValidatorsImplementation, + uint256 _requiredSignatures, + address[] _initialValidators, + address _bridgeValidatorsOwner, + address _bridgeValidatorsProxyOwner, + address _homeBridgeErcToErcImplementation, + uint256 _requiredBlockConfirmations, + uint256 _gasPrice, + uint256 _dailyLimit, + uint256 _maxPerTx, + uint256 _minPerTx, + address _homeBridgeProxyOwner) public { + + require(_owner != address(0)); + require(_bridgeValidatorsImplementation != address(0)); + require(_requiredSignatures >= 1); + require(_bridgeValidatorsOwner != address(0)); + require(_bridgeValidatorsProxyOwner != address(0)); + require(_homeBridgeErcToErcImplementation != address(0)); + require(_requiredBlockConfirmations > 0); + require(_dailyLimit > 0); + require(_maxPerTx > 0); + require(_minPerTx > 0); + require(_homeBridgeProxyOwner != address(0)); + + setOwner(_owner); + setBridgeValidatorsImplementation(_bridgeValidatorsImplementation); + setRequiredSignatures(_requiredSignatures); + setInitialValidators(_initialValidators); + setBridgeValidatorsOwner(_bridgeValidatorsOwner); + setBridgeValidatorsProxyOwner(_bridgeValidatorsProxyOwner); + setHomeBridgeErcToErcImplementation(_homeBridgeErcToErcImplementation); + setRequiredBlockConfirmations(_requiredBlockConfirmations); + setGasPrice(_gasPrice); + setDailyLimit(_dailyLimit); + setMaxPerTx(_maxPerTx); + setMinPerTx(_minPerTx); + setHomeBridgeProxyOwner(_homeBridgeProxyOwner); + } + + function deployHomeBridge(string _tokenName, string _tokenSymbol, uint8 _tokenDecimals) public onlyOwner { + // deploy new EternalStorageProxy + EternalStorageProxy proxy = new EternalStorageProxy(); + // connect it to the static BridgeValidators implementation + proxy.upgradeTo(1, bridgeValidatorsImplementation()); + // cast proxy as IBridgeValidators + IBridgeValidators bridgeValidators = IBridgeValidators(proxy); + // initialize bridgeValidators + bridgeValidators.initialize(requiredSignatures(), initialValidators(), bridgeValidatorsOwner()); + // transger proxy upgradeability admin + proxy.transferProxyOwnership(bridgeValidatorsProxyOwner()); + // deploy new EternalStorageProxy + proxy = new EternalStorageProxy(); + // connect it to the static homeBridgeErcToErc implementation + proxy.upgradeTo(1, homeBridgeErcToErcImplementation()); + // deploy erc677 token bridge token + ERC677BridgeToken token = new ERC677BridgeToken(_tokenName, _tokenSymbol, _tokenDecimals); + // set token bridge contract + token.setBridgeContract(proxy); + // transger token ownership to the bridge + token.transferOwnership(proxy); + // cast proxy as IHomeBridge + IHomeBridge homeBridge = IHomeBridge(proxy); + // initialize homeBridge + homeBridge.initialize(bridgeValidators, dailyLimit(), maxPerTx(), minPerTx(), gasPrice(), requiredBlockConfirmations(), token); + // transger proxy upgradeability admin + proxy.transferProxyOwnership(homeBridgeProxyOwner()); + } + + + function bridgeValidatorsImplementation() public view returns(address) { + return addressStorage[keccak256(abi.encodePacked("bridgeValidatorsImplementation"))]; + } + + function setBridgeValidatorsImplementation(address _bridgeValidatorsImplementation) public onlyOwner { + addressStorage[keccak256(abi.encodePacked("bridgeValidatorsImplementation"))] = _bridgeValidatorsImplementation; + } + + function requiredSignatures() public view returns(uint256) { + return uintStorage[keccak256(abi.encodePacked("requiredSignatures"))]; + } + + function setRequiredSignatures(uint256 _requiredSignatures) public onlyOwner { + uintStorage[keccak256(abi.encodePacked("requiredSignatures"))] = _requiredSignatures; + } + + function initialValidators() public view returns(address[]) { + return addressArrayStorage[keccak256(abi.encodePacked("initialValidators"))]; + } + + function setInitialValidators(address[] _initialValidators) public onlyOwner { + addressArrayStorage[keccak256(abi.encodePacked("initialValidators"))] = _initialValidators; + } + + function bridgeValidatorsOwner() public view returns(address) { + return addressStorage[keccak256(abi.encodePacked("bridgeValidatorsOwner"))]; + } + + function setBridgeValidatorsOwner(address _bridgeValidatorsOwner) public onlyOwner { + addressStorage[keccak256(abi.encodePacked("bridgeValidatorsOwner"))] = _bridgeValidatorsOwner; + } + + function bridgeValidatorsProxyOwner() public view returns(address) { + return addressStorage[keccak256(abi.encodePacked("bridgeValidatorsProxyOwner"))]; + } + + function setBridgeValidatorsProxyOwner(address _bridgeValidatorsProxyOwner) public onlyOwner { + addressStorage[keccak256(abi.encodePacked("bridgeValidatorsProxyOwner"))] = _bridgeValidatorsProxyOwner; + } + + function homeBridgeErcToErcImplementation() public view returns(address) { + return addressStorage[keccak256(abi.encodePacked("homeBridgeErcToErcImplementation"))]; + } + + function setHomeBridgeErcToErcImplementation(address _homeBridgeErcToErcImplementation) public onlyOwner { + addressStorage[keccak256(abi.encodePacked("homeBridgeErcToErcImplementation"))] = _homeBridgeErcToErcImplementation; + } + + function requiredBlockConfirmations() public view returns(uint256) { + return uintStorage[keccak256(abi.encodePacked("requiredBlockConfirmations"))]; + } + + function setRequiredBlockConfirmations(uint256 _requiredBlockConfirmations) public onlyOwner { + uintStorage[keccak256(abi.encodePacked("requiredBlockConfirmations"))] = _requiredBlockConfirmations; + } + + function gasPrice() public view returns(uint256) { + return uintStorage[keccak256(abi.encodePacked("gasPrice"))]; + } + + function setGasPrice(uint256 _gasPrice) public onlyOwner { + uintStorage[keccak256(abi.encodePacked("gasPrice"))] = _gasPrice; + } + + function dailyLimit() public view returns(uint256) { + return uintStorage[keccak256(abi.encodePacked("dailyLimit"))]; + } + + function setDailyLimit(uint256 _dailyLimit) public onlyOwner { + uintStorage[keccak256(abi.encodePacked("dailyLimit"))] = _dailyLimit; + } + + function maxPerTx() public view returns(uint256) { + return uintStorage[keccak256(abi.encodePacked("maxPerTx"))]; + } + + function setMaxPerTx(uint256 _maxPerTx) public onlyOwner { + uintStorage[keccak256(abi.encodePacked("maxPerTx"))] = _maxPerTx; + } + + function minPerTx() public view returns(uint256) { + return uintStorage[keccak256(abi.encodePacked("minPerTx"))]; + } + + function setMinPerTx(uint256 _minPerTx) public onlyOwner { + uintStorage[keccak256(abi.encodePacked("minPerTx"))] = _minPerTx; + } + + + + function homeBridgeProxyOwner() public view returns(address) { + return addressStorage[keccak256(abi.encodePacked("homeBridgeProxyOwner"))]; + } + + function setHomeBridgeProxyOwner(address _homeBridgeProxyOwner) public onlyOwner { + addressStorage[keccak256(abi.encodePacked("homeBridgeProxyOwner"))] = _homeBridgeProxyOwner; + } +} \ No newline at end of file diff --git a/deploy/.env.example b/deploy/.env.example index 954064a0f..a212d8378 100644 --- a/deploy/.env.example +++ b/deploy/.env.example @@ -12,8 +12,11 @@ BRIDGEABLE_TOKEN_DECIMALS="18" HOME_RPC_URL=https://sokol.poa.network HOME_OWNER_MULTISIG=0x +HOME_OWNER_FACTORY=0x HOME_UPGRADEABLE_ADMIN_VALIDATORS=0x HOME_UPGRADEABLE_ADMIN_BRIDGE=0x +HOME_UPGRADEABLE_ADMIN_FACTORY=0x +HOME_UPGRADEABLE_ADMIN_MAPPER=0x HOME_DAILY_LIMIT=30000000000000000000000000 HOME_MAX_AMOUNT_PER_TX=1500000000000000000000000 HOME_MIN_AMOUNT_PER_TX=500000000000000000 @@ -25,8 +28,10 @@ BLOCK_REWARD_ADDRESS= FOREIGN_RPC_URL=https://sokol.poa.network FOREIGN_OWNER_MULTISIG=0x +FOREIGN_OWNER_FACTORY=0x FOREIGN_UPGRADEABLE_ADMIN_VALIDATORS=0x FOREIGN_UPGRADEABLE_ADMIN_BRIDGE=0x +FOREIGN_UPGRADEABLE_ADMIN_FACTORY=0x FOREIGN_DAILY_LIMIT=15000000000000000000000000 FOREIGN_MAX_AMOUNT_PER_TX=750000000000000000000000 FOREIGN_MIN_AMOUNT_PER_TX=500000000000000000 diff --git a/deploy/deploy.js b/deploy/deploy.js index d953aef58..f06216473 100644 --- a/deploy/deploy.js +++ b/deploy/deploy.js @@ -111,6 +111,39 @@ async function deployErcToNative() { console.log('Contracts Deployment have been saved to `bridgeDeploymentResults.json`') } +async function deployFactory() { + const deployHome = require('./src/factories/home') + const deployForeign = require('./src/factories/foreign') + + const { homeFactory, mapper } = await deployHome() + const { foreignFactory } = await deployForeign() + console.log('\nDeployment has been completed.\n\n') + console.log(`[ Home ] HomeFactory: ${homeFactory.address} at block ${homeFactory.deployedBlockNumber}`) + console.log(`[ Home ] mapper: ${mapper.address}`) + console.log( + `[ Foreign ] ForeignFactory: ${foreignFactory.address} at block ${ + foreignFactory.deployedBlockNumber + }` + ) + fs.writeFileSync( + deployResultsPath, + JSON.stringify( + { + homeFactory: { + ...homeFactory, + mapper + }, + foreignFactory: { + ...foreignFactory + } + }, + null, + 4 + ) + ) + console.log('Contracts Deployment have been saved to `bridgeDeploymentResults.json`') +} + async function main() { console.log(`Bridge mode: ${BRIDGE_MODE}`) switch (BRIDGE_MODE) { @@ -123,9 +156,12 @@ async function main() { case 'ERC_TO_NATIVE': await deployErcToNative() break + case 'FACTORY': + await deployFactory() + break default: console.log(BRIDGE_MODE) - throw new Error('Please specify BRIDGE_MODE: NATIVE_TO_ERC or ERC_TO_ERC') + throw new Error('Please specify BRIDGE_MODE: NATIVE_TO_ERC or ERC_TO_ERC or ERC_TO_NATIVE or FACTORY') } } diff --git a/deploy/src/deploymentUtils.js b/deploy/src/deploymentUtils.js index 1d111bd50..449133164 100644 --- a/deploy/src/deploymentUtils.js +++ b/deploy/src/deploymentUtils.js @@ -109,6 +109,7 @@ async function sendNodeRequest(url, method, signedData) { }) }) const json = await request.json() + // console.log('json', json) if (method === 'eth_sendRawTransaction') { assert.equal(json.result.length, 66, `Tx wasn't sent ${json}`) } diff --git a/deploy/src/factories/foreign.js b/deploy/src/factories/foreign.js new file mode 100644 index 000000000..3d1b0c191 --- /dev/null +++ b/deploy/src/factories/foreign.js @@ -0,0 +1,159 @@ +const assert = require('assert') +const Web3Utils = require('web3-utils') +const env = require('../loadEnv') + +const { deployContract, privateKeyToAddress, sendRawTxForeign } = require('../deploymentUtils') +const { web3Foreign, deploymentPrivateKey, FOREIGN_RPC_URL } = require('../web3') + +const EternalStorageProxy = require('../../../build/contracts/EternalStorageProxy.json') +const ForeignBridgeFactory = require('../../../build/contracts/ForeignBridgeFactory.json') +const BridgeValidators = require('../../../build/contracts/BridgeValidators.json') +const ForeignBridge = require('../../../build/contracts/ForeignBridgeErcToErc.json') + +const VALIDATORS = env.VALIDATORS.split(' ') + +const { + DEPLOYMENT_ACCOUNT_PRIVATE_KEY, + REQUIRED_NUMBER_OF_VALIDATORS, + FOREIGN_OWNER_MULTISIG, + FOREIGN_OWNER_FACTORY, + FOREIGN_UPGRADEABLE_ADMIN_VALIDATORS, + FOREIGN_UPGRADEABLE_ADMIN_BRIDGE, + FOREIGN_UPGRADEABLE_ADMIN_FACTORY, + FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS, + FOREIGN_GAS_PRICE +} = env + +let { + FOREIGN_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS, + FOREIGN_BRIDGE_IMPLEMENTATION_ADDRESS +} = env + +const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVATE_KEY) + +async function deployForeign() { + let foreignNonce = await web3Foreign.eth.getTransactionCount(DEPLOYMENT_ACCOUNT_ADDRESS) + console.log('========================================') + console.log('deploying ForeignBridgeFactory') + console.log('========================================\n') + + if (!FOREIGN_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS) { + console.log('deploying bridge validators implementation') + const bridgeValidatorsImplementationForeign = await deployContract(BridgeValidators, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + network: 'foreign', + nonce: foreignNonce + }) + foreignNonce++ + FOREIGN_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS = bridgeValidatorsImplementationForeign.options.address + } + console.log('[Foreign] bridge validators implementation address: ', FOREIGN_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS) + + if (!FOREIGN_BRIDGE_IMPLEMENTATION_ADDRESS) { + console.log('deploying foreign bridge implementation') + const foreignBridgeImplementationForeign = await deployContract(ForeignBridge, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + network: 'foreign', + nonce: foreignNonce + }) + foreignNonce++ + FOREIGN_BRIDGE_IMPLEMENTATION_ADDRESS = foreignBridgeImplementationForeign.options.address + } + console.log('[Foreign] foreign bridge implementation address: ', FOREIGN_BRIDGE_IMPLEMENTATION_ADDRESS) + + console.log('deploying storage for foreign bridge factory') + const storageBridgeFactoryForeign = await deployContract(EternalStorageProxy, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + network: 'foreign', + nonce: foreignNonce + }) + foreignNonce++ + console.log('[Foreign] BridgeFactory Storage: ', storageBridgeFactoryForeign.options.address) + + console.log('\ndeploying implementation for foreign bridge factory') + const bridgeFactoryForeign = await deployContract(ForeignBridgeFactory, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + network: 'foreign', + nonce: foreignNonce + }) + foreignNonce++ + console.log( + '[Foreign] BridgeFactory Implementation: ', + bridgeFactoryForeign.options.address + ) + console.log('\nhooking up eternal storage to BridgeFactory') + const upgradeToForeignFactoryData = await storageBridgeFactoryForeign.methods + .upgradeTo('1', bridgeFactoryForeign.options.address) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + const txUpgradeToForeignFactory = await sendRawTxForeign({ + data: upgradeToForeignFactoryData, + nonce: foreignNonce, + to: storageBridgeFactoryForeign.options.address, + privateKey: deploymentPrivateKey, + url: FOREIGN_RPC_URL + }) + assert.equal(Web3Utils.hexToNumber(txUpgradeToForeignFactory.status), 1, 'Transaction Failed') + foreignNonce++ + + console.log('\ninitializing Foreign Bridge Factory with following parameters:\n') + console.log( + `FOREIGN_OWNER_FACTORY: ${FOREIGN_OWNER_FACTORY}, + FOREIGN_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS: ${FOREIGN_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS}, + REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, + VALIDATORS: ${VALIDATORS}, + FOREIGN_OWNER_MULTISIG: ${FOREIGN_OWNER_MULTISIG}, + FOREIGN_UPGRADEABLE_ADMIN_VALIDATORS: ${FOREIGN_UPGRADEABLE_ADMIN_VALIDATORS}, + FOREIGN_BRIDGE_IMPLEMENTATION_ADDRESS: ${FOREIGN_BRIDGE_IMPLEMENTATION_ADDRESS}, + FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS" ${FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS}, + FOREIGN_GAS_PRICE: ${FOREIGN_GAS_PRICE}, + FOREIGN_UPGRADEABLE_ADMIN_BRIDGE: ${FOREIGN_UPGRADEABLE_ADMIN_BRIDGE}` + ) + bridgeFactoryForeign.options.address = storageBridgeFactoryForeign.options.address + const initializeForeignData = await bridgeFactoryForeign.methods + .initialize( + FOREIGN_OWNER_FACTORY, + FOREIGN_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS, + REQUIRED_NUMBER_OF_VALIDATORS, + VALIDATORS, + FOREIGN_OWNER_MULTISIG, + FOREIGN_UPGRADEABLE_ADMIN_VALIDATORS, + FOREIGN_BRIDGE_IMPLEMENTATION_ADDRESS, + FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS, + FOREIGN_GAS_PRICE, + FOREIGN_UPGRADEABLE_ADMIN_BRIDGE + ) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + const txInitializeForeign = await sendRawTxForeign({ + data: initializeForeignData, + nonce: foreignNonce, + to: bridgeFactoryForeign.options.address, + privateKey: deploymentPrivateKey, + url: FOREIGN_RPC_URL + }) + assert.equal(Web3Utils.hexToNumber(txInitializeForeign.status), 1, 'Transaction Failed') + foreignNonce++ + + console.log('\nTransferring ownership of FactoryProxy\n') + const factoryForeignOwnershipData = await storageBridgeFactoryForeign.methods + .transferProxyOwnership(FOREIGN_UPGRADEABLE_ADMIN_FACTORY) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + const txFactoryForeignOwnershipData = await sendRawTxForeign({ + data: factoryForeignOwnershipData, + nonce: foreignNonce, + to: storageBridgeFactoryForeign.options.address, + privateKey: deploymentPrivateKey, + url: FOREIGN_RPC_URL + }) + assert.equal(Web3Utils.hexToNumber(txFactoryForeignOwnershipData.status), 1, 'Transaction Failed') + foreignNonce++ + + console.log('\nForeign Deployment Factory completed\n') + return { + foreignFactory: { + address: storageBridgeFactoryForeign.options.address, + deployedBlockNumber: Web3Utils.hexToNumber(storageBridgeFactoryForeign.deployedBlockNumber) + } + } +} + +module.exports = deployForeign diff --git a/deploy/src/factories/home.js b/deploy/src/factories/home.js new file mode 100644 index 000000000..70116a5fd --- /dev/null +++ b/deploy/src/factories/home.js @@ -0,0 +1,215 @@ +const assert = require('assert') +const Web3Utils = require('web3-utils') +const env = require('../loadEnv') + +const { deployContract, privateKeyToAddress, sendRawTxHome } = require('../deploymentUtils') +const { web3Home, deploymentPrivateKey, HOME_RPC_URL } = require('../web3') + +const EternalStorageProxy = require('../../../build/contracts/EternalStorageProxy.json') +const HomeBridgeFactory = require('../../../build/contracts/HomeBridgeFactory.json') +const BridgeValidators = require('../../../build/contracts/BridgeValidators.json') +const HomeBridge = require('../../../build/contracts/HomeBridgeErcToErc.json') +const BridgeMapper = require('../../../build/contracts/BridgeMapper.json') + +const VALIDATORS = env.VALIDATORS.split(' ') + +const { + DEPLOYMENT_ACCOUNT_PRIVATE_KEY, + REQUIRED_NUMBER_OF_VALIDATORS, + HOME_OWNER_MULTISIG, + HOME_OWNER_FACTORY, + HOME_UPGRADEABLE_ADMIN_VALIDATORS, + HOME_UPGRADEABLE_ADMIN_BRIDGE, + HOME_UPGRADEABLE_ADMIN_FACTORY, + HOME_UPGRADEABLE_ADMIN_MAPPER, + HOME_DAILY_LIMIT, + HOME_MAX_AMOUNT_PER_TX, + HOME_MIN_AMOUNT_PER_TX, + HOME_REQUIRED_BLOCK_CONFIRMATIONS, + HOME_GAS_PRICE, +} = env + +let { + HOME_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS, + HOME_BRIDGE_IMPLEMENTATION_ADDRESS +} = env + +const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVATE_KEY) + +async function deployHome() { + let homeNonce = await web3Home.eth.getTransactionCount(DEPLOYMENT_ACCOUNT_ADDRESS) + + if (!HOME_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS) { + console.log('deploying bridge validators implementation') + const bridgeValidatorsImplementationHome = await deployContract(BridgeValidators, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + network: 'home', + nonce: homeNonce + }) + homeNonce++ + HOME_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS = bridgeValidatorsImplementationHome.options.address + } + console.log('[Home] bridge validators implementation address: ', HOME_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS) + + if (!HOME_BRIDGE_IMPLEMENTATION_ADDRESS) { + console.log('deploying home bridge implementation') + const homeBridgeImplementationHome = await deployContract(HomeBridge, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + network: 'home', + nonce: homeNonce + }) + homeNonce++ + HOME_BRIDGE_IMPLEMENTATION_ADDRESS = homeBridgeImplementationHome.options.address + } + console.log('[Home] home bridge implementation address: ', HOME_BRIDGE_IMPLEMENTATION_ADDRESS) + + console.log('deploying storage for home bridge factory') + const storageBridgeFactoryHome = await deployContract(EternalStorageProxy, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + network: 'home', + nonce: homeNonce + }) + homeNonce++ + console.log('[Home] BridgeFactory Storage: ', storageBridgeFactoryHome.options.address) + + console.log('\ndeploying implementation for home bridge factory') + const bridgeFactoryHome = await deployContract(HomeBridgeFactory, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + network: 'home', + nonce: homeNonce + }) + homeNonce++ + console.log( + '[Home] BridgeFactory Implementation: ', + bridgeFactoryHome.options.address + ) + console.log('\nhooking up eternal storage to BridgeFactory') + const upgradeToHomeFactoryData = await storageBridgeFactoryHome.methods + .upgradeTo('1', bridgeFactoryHome.options.address) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + const txUpgradeToHomeFactory = await sendRawTxHome({ + data: upgradeToHomeFactoryData, + nonce: homeNonce, + to: storageBridgeFactoryHome.options.address, + privateKey: deploymentPrivateKey, + url: HOME_RPC_URL + }) + assert.equal(Web3Utils.hexToNumber(txUpgradeToHomeFactory.status), 1, 'Transaction Failed') + homeNonce++ + + console.log('\ninitializing Home Bridge Factory with following parameters:\n') + console.log( + `HOME_OWNER_FACTORY: ${HOME_OWNER_FACTORY}, + HOME_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS: ${HOME_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS}, + REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, + VALIDATORS: ${VALIDATORS}, + HOME_OWNER_MULTISIG: ${HOME_OWNER_MULTISIG}, + HOME_UPGRADEABLE_ADMIN_VALIDATORS: ${HOME_UPGRADEABLE_ADMIN_VALIDATORS}, + HOME_BRIDGE_IMPLEMENTATION_ADDRESS: ${HOME_BRIDGE_IMPLEMENTATION_ADDRESS}, + HOME_REQUIRED_BLOCK_CONFIRMATIONS" ${HOME_REQUIRED_BLOCK_CONFIRMATIONS}, + HOME_GAS_PRICE: ${HOME_GAS_PRICE}, + HOME_DAILY_LIMIT: ${HOME_DAILY_LIMIT}, + HOME_MAX_AMOUNT_PER_TX: ${HOME_MAX_AMOUNT_PER_TX}, + HOME_MIN_AMOUNT_PER_TX: ${HOME_MIN_AMOUNT_PER_TX}, + HOME_UPGRADEABLE_ADMIN_BRIDGE: ${HOME_UPGRADEABLE_ADMIN_BRIDGE}` + ) + bridgeFactoryHome.options.address = storageBridgeFactoryHome.options.address + const initializeHomeData = await bridgeFactoryHome.methods + .initialize( + HOME_OWNER_FACTORY, + HOME_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS, + REQUIRED_NUMBER_OF_VALIDATORS, + VALIDATORS, + HOME_OWNER_MULTISIG, + HOME_UPGRADEABLE_ADMIN_VALIDATORS, + HOME_BRIDGE_IMPLEMENTATION_ADDRESS, + HOME_REQUIRED_BLOCK_CONFIRMATIONS, + HOME_GAS_PRICE, + HOME_DAILY_LIMIT, + HOME_MAX_AMOUNT_PER_TX, + HOME_MIN_AMOUNT_PER_TX, + HOME_UPGRADEABLE_ADMIN_BRIDGE + ) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + const txInitializeHome = await sendRawTxHome({ + data: initializeHomeData, + nonce: homeNonce, + to: bridgeFactoryHome.options.address, + privateKey: deploymentPrivateKey, + url: HOME_RPC_URL + }) + assert.equal(Web3Utils.hexToNumber(txInitializeHome.status), 1, 'Transaction Failed') + homeNonce++ + + console.log('\nTransferring ownership of FactoryProxy\n') + const factoryHomeOwnershipData = await storageBridgeFactoryHome.methods + .transferProxyOwnership(HOME_UPGRADEABLE_ADMIN_FACTORY) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + const txFactoryHomeOwnershipData = await sendRawTxHome({ + data: factoryHomeOwnershipData, + nonce: homeNonce, + to: storageBridgeFactoryHome.options.address, + privateKey: deploymentPrivateKey, + url: HOME_RPC_URL + }) + assert.equal(Web3Utils.hexToNumber(txFactoryHomeOwnershipData.status), 1, 'Transaction Failed') + homeNonce++ + + console.log('deploying storage for bridge mapper') + const storageBridgeMapperHome = await deployContract(EternalStorageProxy, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + network: 'home', + nonce: homeNonce + }) + homeNonce++ + console.log('[Home] BridgeMapper Storage: ', storageBridgeMapperHome.options.address) + + console.log('\ndeploying implementation for bridge mapper') + const bridgeMapperHome = await deployContract(BridgeMapper, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + network: 'home', + nonce: homeNonce + }) + homeNonce++ + console.log( + '[Home] BridgeMapper Implementation: ', + bridgeMapperHome.options.address + ) + console.log('\nhooking up eternal storage to BridgeMapper') + const upgradeToBridgeMapperData = await storageBridgeMapperHome.methods + .upgradeTo('1', bridgeMapperHome.options.address) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + const txUpgradeToBridgeMapper = await sendRawTxHome({ + data: upgradeToBridgeMapperData, + nonce: homeNonce, + to: storageBridgeMapperHome.options.address, + privateKey: deploymentPrivateKey, + url: HOME_RPC_URL + }) + assert.equal(Web3Utils.hexToNumber(txUpgradeToBridgeMapper.status), 1, 'Transaction Failed') + homeNonce++ + + console.log('\nTransferring ownership of MapperProxy\n') + const mapperOwnershipData = await storageBridgeMapperHome.methods + .transferProxyOwnership(HOME_UPGRADEABLE_ADMIN_MAPPER) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + const txMapperOwnershipData = await sendRawTxHome({ + data: mapperOwnershipData, + nonce: homeNonce, + to: storageBridgeMapperHome.options.address, + privateKey: deploymentPrivateKey, + url: HOME_RPC_URL + }) + assert.equal(Web3Utils.hexToNumber(txMapperOwnershipData.status), 1, 'Transaction Failed') + homeNonce++ + + console.log('\nHome Deployment Factory completed\n') + return { + homeFactory: { + address: storageBridgeFactoryHome.options.address, + deployedBlockNumber: Web3Utils.hexToNumber(storageBridgeFactoryHome.deployedBlockNumber) + }, + mapper: {address: storageBridgeMapperHome.options.address } + } +} +module.exports = deployHome diff --git a/deploy/src/loadEnv.js b/deploy/src/loadEnv.js index 2645a0568..e7f1cbfc2 100644 --- a/deploy/src/loadEnv.js +++ b/deploy/src/loadEnv.js @@ -7,7 +7,7 @@ const envalid = require('envalid') const { ZERO_ADDRESS } = require('./constants') // Validations and constants -const validBridgeModes = ['NATIVE_TO_ERC', 'ERC_TO_ERC', 'ERC_TO_NATIVE'] +const validBridgeModes = ['NATIVE_TO_ERC', 'ERC_TO_ERC', 'ERC_TO_NATIVE', 'FACTORY'] const bigNumValidator = envalid.makeValidator(x => toBN(x)) const validateAddress = address => { if (isAddress(address)) { @@ -82,6 +82,16 @@ if (BRIDGE_MODE === 'ERC_TO_NATIVE') { }) } } +if(BRIDGE_MODE === 'FACROTY') { + validations = { + ...validations, + HOME_OWNER_FACTORY: addressValidator(), + HOME_UPGRADEABLE_ADMIN_FACTORY: addressValidator(), + HOME_UPGRADEABLE_ADMIN_MAPPER: addressValidator(), + FOREIGN_OWNER_FACTORY: addressValidator(), + FOREIGN_UPGRADEABLE_ADMIN_FACTORY: addressValidator() + } +} const env = envalid.cleanEnv(process.env, validations) diff --git a/flatten.sh b/flatten.sh index 1f1fe20da..55f847252 100755 --- a/flatten.sh +++ b/flatten.sh @@ -7,6 +7,7 @@ fi mkdir -p flats/native_to_erc20 mkdir -p flats/erc20_to_erc20 mkdir -p flats/erc20_to_native +mkdir -p flats/factories ./node_modules/.bin/truffle-flattener contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol > flats/native_to_erc20/ForeignBridgeNativeToErc_flat.sol ./node_modules/.bin/truffle-flattener contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol > flats/native_to_erc20/HomeBridgeNativeToErc_flat.sol @@ -19,4 +20,8 @@ mkdir -p flats/erc20_to_native ./node_modules/.bin/truffle-flattener contracts/upgradeability/EternalStorageProxy.sol > flats/EternalStorageProxy_flat.sol ./node_modules/.bin/truffle-flattener contracts/upgradeable_contracts/BridgeValidators.sol > flats/BridgeValidators_flat.sol +./node_modules/.bin/truffle-flattener contracts/upgradeable_contracts/BridgeMapper.sol > flats/BridgeMapper_flat.sol ./node_modules/.bin/truffle-flattener contracts/ERC677BridgeToken.sol > flats/ERC677BridgeToken_flat.sol + +./node_modules/.bin/truffle-flattener contracts/upgradeable_contracts/factories/ForeignBridgeFactory.sol > flats/factories/ForeignBridgeFactory_flat.sol +./node_modules/.bin/truffle-flattener contracts/upgradeable_contracts/factories/HomeBridgeFactory.sol > flats/factories/HomeBridgeFactory_flat.sol From 182a483436fef82e53c94485fc475d77366ff5c3 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 15 Jan 2019 16:52:48 -0300 Subject: [PATCH 051/187] Add rewardableInitialize on HomeBridgeErcToNative --- .../erc20_to_native/HomeBridgeErcToNative.sol | 98 +++++++++++++++---- test/erc_to_native/home_bridge.test.js | 81 +++++++++++++++ 2 files changed, 161 insertions(+), 18 deletions(-) diff --git a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol index 897a8a874..94b15c4ea 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol @@ -47,24 +47,53 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, address _owner ) public returns(bool) { - require(!isInitialized()); - require(_validatorContract != address(0) && isContract(_validatorContract)); - require(_requiredBlockConfirmations > 0); - require(_minPerTx > 0 && _maxPerTx > _minPerTx && _dailyLimit > _maxPerTx); - require(_blockReward == address(0) || isContract(_blockReward)); - require(_foreignMaxPerTx < _foreignDailyLimit); - require(_owner != address(0)); - addressStorage[keccak256(abi.encodePacked("validatorContract"))] = _validatorContract; - uintStorage[keccak256(abi.encodePacked("deployedAtBlock"))] = block.number; - uintStorage[keccak256(abi.encodePacked("dailyLimit"))] = _dailyLimit; - uintStorage[keccak256(abi.encodePacked("maxPerTx"))] = _maxPerTx; - uintStorage[keccak256(abi.encodePacked("minPerTx"))] = _minPerTx; - uintStorage[keccak256(abi.encodePacked("gasPrice"))] = _homeGasPrice; - uintStorage[keccak256(abi.encodePacked("requiredBlockConfirmations"))] = _requiredBlockConfirmations; - addressStorage[keccak256(abi.encodePacked("blockRewardContract"))] = _blockReward; - uintStorage[keccak256(abi.encodePacked("executionDailyLimit"))] = _foreignDailyLimit; - uintStorage[keccak256(abi.encodePacked("executionMaxPerTx"))] = _foreignMaxPerTx; - setOwner(_owner); + _initialize( + _validatorContract, + _dailyLimit, + _maxPerTx, + _minPerTx, + _homeGasPrice, + _requiredBlockConfirmations, + _blockReward, + _foreignDailyLimit, + _foreignMaxPerTx, + _owner + ); + setInitialize(true); + + return isInitialized(); + } + + function rewardableInitialize ( + address _validatorContract, + uint256 _dailyLimit, + uint256 _maxPerTx, + uint256 _minPerTx, + uint256 _homeGasPrice, + uint256 _requiredBlockConfirmations, + address _blockReward, + uint256 _foreignDailyLimit, + uint256 _foreignMaxPerTx, + address _owner, + address _feeManager, + uint256 _fee + ) public returns(bool) + { + _initialize( + _validatorContract, + _dailyLimit, + _maxPerTx, + _minPerTx, + _homeGasPrice, + _requiredBlockConfirmations, + _blockReward, + _foreignDailyLimit, + _foreignMaxPerTx, + _owner + ); + require(isContract(_feeManager)); + addressStorage[keccak256(abi.encodePacked("feeManagerContract"))] = _feeManager; + require(_feeManager.delegatecall(abi.encodeWithSignature("setFee(uint256)", _fee))); setInitialize(true); return isInitialized(); @@ -87,6 +116,39 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, addressStorage[keccak256(abi.encodePacked("blockRewardContract"))] = _blockReward; } + function _initialize ( + address _validatorContract, + uint256 _dailyLimit, + uint256 _maxPerTx, + uint256 _minPerTx, + uint256 _homeGasPrice, + uint256 _requiredBlockConfirmations, + address _blockReward, + uint256 _foreignDailyLimit, + uint256 _foreignMaxPerTx, + address _owner + ) internal + { + require(!isInitialized()); + require(_validatorContract != address(0) && isContract(_validatorContract)); + require(_requiredBlockConfirmations > 0); + require(_minPerTx > 0 && _maxPerTx > _minPerTx && _dailyLimit > _maxPerTx); + require(_blockReward == address(0) || isContract(_blockReward)); + require(_foreignMaxPerTx < _foreignDailyLimit); + require(_owner != address(0)); + addressStorage[keccak256(abi.encodePacked("validatorContract"))] = _validatorContract; + uintStorage[keccak256(abi.encodePacked("deployedAtBlock"))] = block.number; + uintStorage[keccak256(abi.encodePacked("dailyLimit"))] = _dailyLimit; + uintStorage[keccak256(abi.encodePacked("maxPerTx"))] = _maxPerTx; + uintStorage[keccak256(abi.encodePacked("minPerTx"))] = _minPerTx; + uintStorage[keccak256(abi.encodePacked("gasPrice"))] = _homeGasPrice; + uintStorage[keccak256(abi.encodePacked("requiredBlockConfirmations"))] = _requiredBlockConfirmations; + addressStorage[keccak256(abi.encodePacked("blockRewardContract"))] = _blockReward; + uintStorage[keccak256(abi.encodePacked("executionDailyLimit"))] = _foreignDailyLimit; + uintStorage[keccak256(abi.encodePacked("executionMaxPerTx"))] = _foreignMaxPerTx; + setOwner(_owner); + } + function onExecuteAffirmation(address _recipient, uint256 _value) internal returns(bool) { setTotalExecutedPerDay(getCurrentDay(), totalExecutedPerDay(getCurrentDay()).add(_value)); IBlockReward blockReward = blockRewardContract(); diff --git a/test/erc_to_native/home_bridge.test.js b/test/erc_to_native/home_bridge.test.js index c97a275f0..429d9eec2 100644 --- a/test/erc_to_native/home_bridge.test.js +++ b/test/erc_to_native/home_bridge.test.js @@ -146,6 +146,87 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { }) }) + describe('#rewardableInitialize', async() => { + let feeManager, fee + beforeEach(async () => { + feeManager = await FeeManagerErcToNative.new() + homeContract = await HomeBridge.new() + fee = web3.toBigNumber(web3.toWei(0.001, "ether")) + }) + it('sets variables', async () => { + ZERO_ADDRESS.should.be.equal(await homeContract.validatorContract()) + '0'.should.be.bignumber.equal(await homeContract.deployedAtBlock()) + '0'.should.be.bignumber.equal(await homeContract.dailyLimit()) + '0'.should.be.bignumber.equal(await homeContract.maxPerTx()) + false.should.be.equal(await homeContract.isInitialized()) + ZERO_ADDRESS.should.be.equal(await homeContract.blockRewardContract()) + + await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.fulfilled + + true.should.be.equal(await homeContract.isInitialized()) + validatorContract.address.should.be.equal(await homeContract.validatorContract()) + blockRewardContract.address.should.be.equal(await homeContract.blockRewardContract()); + (await homeContract.deployedAtBlock()).should.be.bignumber.above(0) + '3'.should.be.bignumber.equal(await homeContract.dailyLimit()) + '2'.should.be.bignumber.equal(await homeContract.maxPerTx()) + '1'.should.be.bignumber.equal(await homeContract.minPerTx()) + const contractGasPrice = await homeContract.gasPrice() + contractGasPrice.should.be.bignumber.equal(gasPrice) + const bridgeMode = '0x18762d46' // 4 bytes of keccak256('erc-to-native-core') + const mode = await homeContract.getBridgeMode(); + mode.should.be.equal(bridgeMode) + const [major, minor, patch] = await homeContract.getBridgeInterfacesVersion() + major.should.be.bignumber.gte(0) + minor.should.be.bignumber.gte(0) + patch.should.be.bignumber.gte(0) + + const feeManagerContract = await homeContract.feeManagerContract() + feeManagerContract.should.be.equals(feeManager.address) + const bridgeFee = await homeContract.getFee() + bridgeFee.should.be.bignumber.equal(fee) + }) + + it('cant initialize with invalid arguments', async () => { + false.should.be.equal(await homeContract.isInitialized()) + await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, 0, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.rejectedWith(ERROR_MSG); + await homeContract.rewardableInitialize(owner, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.rejectedWith(ERROR_MSG); + await homeContract.rewardableInitialize(ZERO_ADDRESS, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.rejectedWith(ERROR_MSG); + await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, owner, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.rejectedWith(ERROR_MSG); + await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, halfEther, oneEther, owner, feeManager.address, fee).should.be.rejectedWith(ERROR_MSG); + await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, ZERO_ADDRESS, fee).should.be.rejectedWith(ERROR_MSG); + await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.fulfilled; + true.should.be.equal(await homeContract.isInitialized()) + }) + + it('can update fee contract', async () => { + await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.fulfilled; + + // Given + const newFeeManager = await FeeManagerErcToNative.new() + + // When + await homeContract.setFeeManagerContract(newFeeManager.address, { from: owner }).should.be.fulfilled + + // Then + const feeManagerContract = await homeContract.feeManagerContract() + feeManagerContract.should.be.equals(newFeeManager.address) + }) + + it('can update fee', async () => { + await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.fulfilled; + + // Given + const newFee = web3.toBigNumber(web3.toWei(0.1, "ether")) + + // When + await homeContract.setFee(newFee, { from: owner }).should.be.fulfilled + + // Then + const bridgeFee = await homeContract.getFee() + bridgeFee.should.be.bignumber.equal(newFee) + }) + }) + describe('#fallback', async () => { beforeEach(async () => { homeContract = await HomeBridge.new() From 38ebcf16babdf837e1d65d9dd17924eb9f93d697 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 15 Jan 2019 16:55:21 -0300 Subject: [PATCH 052/187] Add rewardable bridge options on deploy script for erc-to-native mode --- deploy/.env.example | 12 +++- deploy/README.md | 12 ++++ deploy/src/erc_to_native/home.js | 116 +++++++++++++++++++++++-------- deploy/src/loadEnv.js | 20 +++++- 4 files changed, 129 insertions(+), 31 deletions(-) diff --git a/deploy/.env.example b/deploy/.env.example index 8145284f6..dc487f5c8 100644 --- a/deploy/.env.example +++ b/deploy/.env.example @@ -1,7 +1,7 @@ #BRIDGE_MODE=ERC_TO_ERC BRIDGE_MODE=NATIVE_TO_ERC DEPLOYMENT_ACCOUNT_PRIVATE_KEY=67..14 -DEPLOYMENT_GAS_LIMIT=5000000 +DEPLOYMENT_GAS_LIMIT=6000000 HOME_DEPLOYMENT_GAS_PRICE=10000000000 FOREIGN_DEPLOYMENT_GAS_PRICE=10000000000 GET_RECEIPT_INTERVAL_IN_MILLISECONDS=3000 @@ -39,6 +39,16 @@ REQUIRED_NUMBER_OF_VALIDATORS=1 #If several validators are used, list them separated by space without quotes #E.g. VALIDATORS=0x 0x 0x VALIDATORS=0x +#for erc_to_native mode +#Set to true if RewardableValidators will be used and fee will be charged +REWARDABLE_VALIDATORS=false +#If REWARDABLE_VALIDATORS=true, list validators accounts were rewards should be transferred separated by space without quotes +#E.g. VALIDATORS_REWARD_ACCOUNTS=0x 0x 0x +VALIDATORS_REWARD_ACCOUNTS=0x + +# Fee to be charged for each transfer: +# E.g. 0.1% fee +BRIDGE_FEE=0.001 #for bridge native_to_erc mode DEPLOY_REWARDABLE_TOKEN=false diff --git a/deploy/README.md b/deploy/README.md index 780627147..e6d6ec390 100644 --- a/deploy/README.md +++ b/deploy/README.md @@ -328,4 +328,16 @@ REQUIRED_NUMBER_OF_VALIDATORS=1 # the Foreign network to confirm that the finalized agreement was transferred # correctly to the Foreign network. VALIDATORS=0x 0x 0x + + +# The flag defining whether to use RewardableValidators contract and set a fee manager contract +REWARDABLE_VALIDATORS=false +# List validators accounts were rewards should be transferred separated by space without quotes +# Makes sense only when REWARDABLE_VALIDATORS=true +VALIDATORS_REWARD_ACCOUNTS=0x 0x 0x + +# Fee to be charged for each transfer +# Makes sense only when REWARDABLE_VALIDATORS=true +# e.g. 0.1% fee +BRIDGE_FEE=0.001 ``` diff --git a/deploy/src/erc_to_native/home.js b/deploy/src/erc_to_native/home.js index 2040b953a..c3aa123ff 100644 --- a/deploy/src/erc_to_native/home.js +++ b/deploy/src/erc_to_native/home.js @@ -7,9 +7,12 @@ const { web3Home, deploymentPrivateKey, HOME_RPC_URL } = require('../web3') const EternalStorageProxy = require('../../../build/contracts/EternalStorageProxy.json') const BridgeValidators = require('../../../build/contracts/BridgeValidators.json') +const RewardableValidators = require('../../../build/contracts/RewardableValidators.json') +const FeeManagerErcToNative = require('../../../build/contracts/FeeManagerErcToNative.json') const HomeBridge = require('../../../build/contracts/HomeBridgeErcToNative.json') const VALIDATORS = env.VALIDATORS.split(' ') +const VALIDATORS_REWARD_ACCOUNTS = env.VALIDATORS_REWARD_ACCOUNTS.split(' ') const { BLOCK_REWARD_ADDRESS, @@ -24,11 +27,15 @@ const { HOME_MIN_AMOUNT_PER_TX, HOME_REQUIRED_BLOCK_CONFIRMATIONS, FOREIGN_DAILY_LIMIT, - FOREIGN_MAX_AMOUNT_PER_TX + FOREIGN_MAX_AMOUNT_PER_TX, + REWARDABLE_VALIDATORS, + BRIDGE_FEE } = env const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVATE_KEY) +const useRewardableValidators = REWARDABLE_VALIDATORS === 'true' + async function deployHome() { let homeNonce = await web3Home.eth.getTransactionCount(DEPLOYMENT_ACCOUNT_ADDRESS) console.log('deploying storage for home validators') @@ -40,7 +47,8 @@ async function deployHome() { homeNonce++ console.log('\ndeploying implementation for home validators') - const bridgeValidatorsHome = await deployContract(BridgeValidators, [], { + const bridgeValidatorsContract = useRewardableValidators ? RewardableValidators : BridgeValidators + const bridgeValidatorsHome = await deployContract(bridgeValidatorsContract, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, nonce: homeNonce }) @@ -62,13 +70,31 @@ async function deployHome() { homeNonce++ console.log('\ninitializing Home Bridge Validators with following parameters:\n') - console.log( - `REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, VALIDATORS: ${VALIDATORS}` - ) bridgeValidatorsHome.options.address = storageValidatorsHome.options.address - const initializeData = await bridgeValidatorsHome.methods - .initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, HOME_VALIDATORS_OWNER) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + + let initializeData + + if (useRewardableValidators) { + console.log( + `REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, VALIDATORS: ${VALIDATORS}, VALIDATORS_REWARD_ACCOUNTS: ${VALIDATORS_REWARD_ACCOUNTS}, HOME_VALIDATORS_OWNER: ${HOME_VALIDATORS_OWNER}` + ) + initializeData = await bridgeValidatorsHome.methods + .initialize( + REQUIRED_NUMBER_OF_VALIDATORS, + VALIDATORS, + VALIDATORS_REWARD_ACCOUNTS, + HOME_VALIDATORS_OWNER + ) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + } else { + console.log( + `REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, VALIDATORS: ${VALIDATORS}` + ) + initializeData = await bridgeValidatorsHome.methods + .initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, HOME_VALIDATORS_OWNER) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + } + const txInitialize = await sendRawTxHome({ data: initializeData, nonce: homeNonce, @@ -123,31 +149,63 @@ async function deployHome() { assert.strictEqual(Web3Utils.hexToNumber(txUpgradeToHomeBridge.status), 1, 'Transaction Failed') homeNonce++ - console.log('\ninitializing Home Bridge with following parameters:\n') - console.log(`Home Validators: ${storageValidatorsHome.options.address}, + let initializeHomeBridgeData + homeBridgeImplementation.options.address = homeBridgeStorage.options.address + + if (useRewardableValidators) { + console.log('\ndeploying implementation for fee manager') + const feeManager = await deployContract(FeeManagerErcToNative, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + nonce: homeNonce + }) + console.log('[Home] feeManager Implementation: ', feeManager.options.address) + homeNonce++ + + const feeInWei = Web3Utils.toWei(BRIDGE_FEE.toString(), 'ether') + console.log('\ninitializing Home Bridge with fee contract:\n') + initializeHomeBridgeData = await homeBridgeImplementation.methods + .rewardableInitialize( + storageValidatorsHome.options.address, + HOME_DAILY_LIMIT, + HOME_MAX_AMOUNT_PER_TX, + HOME_MIN_AMOUNT_PER_TX, + HOME_GAS_PRICE, + HOME_REQUIRED_BLOCK_CONFIRMATIONS, + BLOCK_REWARD_ADDRESS, + FOREIGN_DAILY_LIMIT, + FOREIGN_MAX_AMOUNT_PER_TX, + HOME_BRIDGE_OWNER, + feeManager.options.address, + feeInWei + ) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + } else { + console.log('\ninitializing Home Bridge with following parameters:\n') + console.log(`Home Validators: ${storageValidatorsHome.options.address}, HOME_DAILY_LIMIT : ${HOME_DAILY_LIMIT} which is ${Web3Utils.fromWei(HOME_DAILY_LIMIT)} in eth, HOME_MAX_AMOUNT_PER_TX: ${HOME_MAX_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( - HOME_MAX_AMOUNT_PER_TX - )} in eth, + HOME_MAX_AMOUNT_PER_TX + )} in eth, HOME_MIN_AMOUNT_PER_TX: ${HOME_MIN_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( - HOME_MIN_AMOUNT_PER_TX - )} in eth, + HOME_MIN_AMOUNT_PER_TX + )} in eth, HOME_GAS_PRICE: ${HOME_GAS_PRICE}, HOME_REQUIRED_BLOCK_CONFIRMATIONS : ${HOME_REQUIRED_BLOCK_CONFIRMATIONS}`) - homeBridgeImplementation.options.address = homeBridgeStorage.options.address - const initializeHomeBridgeData = await homeBridgeImplementation.methods - .initialize( - storageValidatorsHome.options.address, - HOME_DAILY_LIMIT, - HOME_MAX_AMOUNT_PER_TX, - HOME_MIN_AMOUNT_PER_TX, - HOME_GAS_PRICE, - HOME_REQUIRED_BLOCK_CONFIRMATIONS, - BLOCK_REWARD_ADDRESS, - FOREIGN_DAILY_LIMIT, - FOREIGN_MAX_AMOUNT_PER_TX, - HOME_BRIDGE_OWNER - ) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + initializeHomeBridgeData = await homeBridgeImplementation.methods + .initialize( + storageValidatorsHome.options.address, + HOME_DAILY_LIMIT, + HOME_MAX_AMOUNT_PER_TX, + HOME_MIN_AMOUNT_PER_TX, + HOME_GAS_PRICE, + HOME_REQUIRED_BLOCK_CONFIRMATIONS, + BLOCK_REWARD_ADDRESS, + FOREIGN_DAILY_LIMIT, + FOREIGN_MAX_AMOUNT_PER_TX, + HOME_BRIDGE_OWNER + ) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + } + const txInitializeHomeBridge = await sendRawTxHome({ data: initializeHomeBridgeData, nonce: homeNonce, diff --git a/deploy/src/loadEnv.js b/deploy/src/loadEnv.js index 8b3d9f36e..cc07c48a5 100644 --- a/deploy/src/loadEnv.js +++ b/deploy/src/loadEnv.js @@ -22,7 +22,7 @@ const addressesValidator = envalid.makeValidator(addresses => { return addresses }) -const { BRIDGE_MODE } = process.env +const { BRIDGE_MODE, REWARDABLE_VALIDATORS, VALIDATORS, VALIDATORS_REWARD_ACCOUNTS } = process.env if (!validBridgeModes.includes(BRIDGE_MODE)) { throw new Error(`Invalid bridge mode: ${BRIDGE_MODE}`) @@ -86,6 +86,24 @@ if (BRIDGE_MODE === 'ERC_TO_NATIVE') { } } +if (REWARDABLE_VALIDATORS === 'true') { + const validatorsLength = VALIDATORS ? VALIDATORS.split(' ').length : 0 + const validatorsRewardLength = VALIDATORS_REWARD_ACCOUNTS + ? VALIDATORS_REWARD_ACCOUNTS.split(' ').length + : 0 + if (validatorsLength !== validatorsRewardLength) { + throw new Error( + `List of rewards accounts (${validatorsRewardLength} accounts) should be the same length as list of validators (${validatorsLength} accounts)` + ) + } + + validations = { + ...validations, + VALIDATORS_REWARD_ACCOUNTS: addressesValidator(), + BRIDGE_FEE: envalid.num() + } +} + const env = envalid.cleanEnv(process.env, validations) module.exports = env From b092a355c761e1fe0fc8f0b3a27a3427dac39036 Mon Sep 17 00:00:00 2001 From: Tal Beja Date: Wed, 16 Jan 2019 14:19:40 +0200 Subject: [PATCH 053/187] move `setOwner` to `initialize` instead of constractor inbridgeMapper --- .../upgradeable_contracts/BridgeMapper.sol | 4 ++-- deploy/.env.example | 1 + deploy/src/factories/home.js | 17 +++++++++++++++++ deploy/src/loadEnv.js | 1 + 4 files changed, 21 insertions(+), 2 deletions(-) diff --git a/contracts/upgradeable_contracts/BridgeMapper.sol b/contracts/upgradeable_contracts/BridgeMapper.sol index 73f6768a5..cfacda0f9 100644 --- a/contracts/upgradeable_contracts/BridgeMapper.sol +++ b/contracts/upgradeable_contracts/BridgeMapper.sol @@ -77,8 +77,8 @@ contract BridgeMapper is EternalStorage, EternalOwnable { return (1, 0, 0); } - constructor() public { - setOwner(msg.sender); + function initialize(address _owner) public { + setOwner(_owner); } } \ No newline at end of file diff --git a/deploy/.env.example b/deploy/.env.example index a212d8378..3b8dac8dc 100644 --- a/deploy/.env.example +++ b/deploy/.env.example @@ -13,6 +13,7 @@ BRIDGEABLE_TOKEN_DECIMALS="18" HOME_RPC_URL=https://sokol.poa.network HOME_OWNER_MULTISIG=0x HOME_OWNER_FACTORY=0x +HOME_OWNER_MAPPER=0x HOME_UPGRADEABLE_ADMIN_VALIDATORS=0x HOME_UPGRADEABLE_ADMIN_BRIDGE=0x HOME_UPGRADEABLE_ADMIN_FACTORY=0x diff --git a/deploy/src/factories/home.js b/deploy/src/factories/home.js index 70116a5fd..1e248c437 100644 --- a/deploy/src/factories/home.js +++ b/deploy/src/factories/home.js @@ -18,6 +18,7 @@ const { REQUIRED_NUMBER_OF_VALIDATORS, HOME_OWNER_MULTISIG, HOME_OWNER_FACTORY, + HOME_OWNER_MAPPER, HOME_UPGRADEABLE_ADMIN_VALIDATORS, HOME_UPGRADEABLE_ADMIN_BRIDGE, HOME_UPGRADEABLE_ADMIN_FACTORY, @@ -175,6 +176,7 @@ async function deployHome() { '[Home] BridgeMapper Implementation: ', bridgeMapperHome.options.address ) + console.log('\nhooking up eternal storage to BridgeMapper') const upgradeToBridgeMapperData = await storageBridgeMapperHome.methods .upgradeTo('1', bridgeMapperHome.options.address) @@ -189,6 +191,21 @@ async function deployHome() { assert.equal(Web3Utils.hexToNumber(txUpgradeToBridgeMapper.status), 1, 'Transaction Failed') homeNonce++ + console.log('\ninitializing BridgeMapper:') + bridgeMapperHome.options.address = storageBridgeMapperHome.options.address + const initializeBridgeMapperData = await bridgeMapperHome.methods + .initialize(HOME_OWNER_MAPPER) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + const txInitializeBridgeMapper = await sendRawTxHome({ + data: initializeBridgeMapperData, + nonce: homeNonce, + to: bridgeMapperHome.options.address, + privateKey: deploymentPrivateKey, + url: HOME_RPC_URL + }) + assert.equal(Web3Utils.hexToNumber(txInitializeBridgeMapper.status), 1, 'Transaction Failed') + homeNonce++ + console.log('\nTransferring ownership of MapperProxy\n') const mapperOwnershipData = await storageBridgeMapperHome.methods .transferProxyOwnership(HOME_UPGRADEABLE_ADMIN_MAPPER) diff --git a/deploy/src/loadEnv.js b/deploy/src/loadEnv.js index e7f1cbfc2..c5fc9a676 100644 --- a/deploy/src/loadEnv.js +++ b/deploy/src/loadEnv.js @@ -86,6 +86,7 @@ if(BRIDGE_MODE === 'FACROTY') { validations = { ...validations, HOME_OWNER_FACTORY: addressValidator(), + HOME_OWNER_MAPPER: addressValidator(), HOME_UPGRADEABLE_ADMIN_FACTORY: addressValidator(), HOME_UPGRADEABLE_ADMIN_MAPPER: addressValidator(), FOREIGN_OWNER_FACTORY: addressValidator(), From 03fead7ad1d0a8622e411ce69eecb4439343f8b0 Mon Sep 17 00:00:00 2001 From: Tal Beja Date: Thu, 17 Jan 2019 10:08:43 +0200 Subject: [PATCH 054/187] rename FACTORY to ERC_TO_ERC_MULTIPLE --- deploy/deploy.js | 4 ++-- deploy/src/loadEnv.js | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/deploy/deploy.js b/deploy/deploy.js index f06216473..50a3c493f 100644 --- a/deploy/deploy.js +++ b/deploy/deploy.js @@ -156,12 +156,12 @@ async function main() { case 'ERC_TO_NATIVE': await deployErcToNative() break - case 'FACTORY': + case 'ERC_TO_ERC_MULTIPLE': await deployFactory() break default: console.log(BRIDGE_MODE) - throw new Error('Please specify BRIDGE_MODE: NATIVE_TO_ERC or ERC_TO_ERC or ERC_TO_NATIVE or FACTORY') + throw new Error('Please specify BRIDGE_MODE: NATIVE_TO_ERC or ERC_TO_ERC or ERC_TO_NATIVE or ERC_TO_ERC_MULTIPLE') } } diff --git a/deploy/src/loadEnv.js b/deploy/src/loadEnv.js index c5fc9a676..90173e766 100644 --- a/deploy/src/loadEnv.js +++ b/deploy/src/loadEnv.js @@ -7,7 +7,7 @@ const envalid = require('envalid') const { ZERO_ADDRESS } = require('./constants') // Validations and constants -const validBridgeModes = ['NATIVE_TO_ERC', 'ERC_TO_ERC', 'ERC_TO_NATIVE', 'FACTORY'] +const validBridgeModes = ['NATIVE_TO_ERC', 'ERC_TO_ERC', 'ERC_TO_NATIVE', 'ERC_TO_ERC_MULTIPLE'] const bigNumValidator = envalid.makeValidator(x => toBN(x)) const validateAddress = address => { if (isAddress(address)) { @@ -82,7 +82,7 @@ if (BRIDGE_MODE === 'ERC_TO_NATIVE') { }) } } -if(BRIDGE_MODE === 'FACROTY') { +if(BRIDGE_MODE === 'ERC_TO_ERC_MULTIPLE') { validations = { ...validations, HOME_OWNER_FACTORY: addressValidator(), From c1c08809547144635efdd4188a1ff546ba1208b5 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Thu, 17 Jan 2019 12:46:38 -0300 Subject: [PATCH 055/187] Update gas consumption on ERC-TO-NATIVE --- docs/ERC-TO-NATIVE-WITH-REWARD.md | 56 +++++++++++++++++++++++++++++++ docs/ERC-TO-NATIVE.md | 55 ++++++++++++++++++++++++++++++ 2 files changed, 111 insertions(+) create mode 100644 docs/ERC-TO-NATIVE-WITH-REWARD.md create mode 100644 docs/ERC-TO-NATIVE.md diff --git a/docs/ERC-TO-NATIVE-WITH-REWARD.md b/docs/ERC-TO-NATIVE-WITH-REWARD.md new file mode 100644 index 000000000..799f74fa5 --- /dev/null +++ b/docs/ERC-TO-NATIVE-WITH-REWARD.md @@ -0,0 +1,56 @@ +## Gas Consumption `ERC-TO-NATIVE` Bridge Mode with Reward contract + +#### Deployment +##### Home + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +EternalStorageProxy|deployment|378510|378510|378510 +RewardableValidators|deployment|1615790|1615790|1615790 +EternalStorageProxy|upgradeTo|35871|30924|30913 +RewardableValidators|initialize|202711|423292|318008 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +EternalStorageProxy|deployment|378510|378510|378510 +HomeBridgeErcToNative|deployment|5155405|5155405|5155405 +EternalStorageProxy|upgradeTo|35871|30924|30913 +FeeManagerErcToNative|deployment|849694|849694|849694 +HomeBridgeErcToNative|rewardableInitialize|327016|327080|327064 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +Total| |9040684|9251435|9146113 + +##### Foreign + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +EternalStorageProxy|deployment|378510|378510|378510 +BridgeValidators|deployment|1351491|1351491|1351491 +EternalStorageProxy|upgradeTo|35871|30924|30913 +BridgeValidators|initialize|210762|306607|270900 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +EternalStorageProxy|deployment|378510|378510|378510 +ForeignBridgeErcToNative|deployment|2863900|2863900|2863900 +EternalStorageProxy|upgradeTo|35871|30924|30913 +ForeignBridgeErcToNative|initialize|239130|239130|239130 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +Total| |5555351|5641302|5555351 5641302 5605573 + +#### Usage + +##### Validators + + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +To sign at the Home (each validator)| +HomeBridgeErcToNative|submitSignature|159926|307729|219658 +To relay signatures from the Home to the Foreign (one validator)| +ForeignBridgeErcToNative|executeSignatures|83142|140737|114527 +To sign and relay from the Foreign to the Home (each validator)| +HomeBridgeErcToNative|executeAffirmation|67422|318558|142697 + +##### Users + + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +To request transfer from the Home to the Foreign| +HomeBridgeErcToNative|fallback|83622|83622|83622 +To request transfer from the Foreign to the Home| +ERC677BridgeToken|transfer|37691|86589|55000 + diff --git a/docs/ERC-TO-NATIVE.md b/docs/ERC-TO-NATIVE.md new file mode 100644 index 000000000..bd354b12d --- /dev/null +++ b/docs/ERC-TO-NATIVE.md @@ -0,0 +1,55 @@ +## Gas Consumption `ERC-TO-NATIVE` Bridge Mode + +#### Deployment +##### Home + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +EternalStorageProxy|deployment|378510|378510|378510 +BridgeValidators|deployment|1351491|1351491|1351491 +EternalStorageProxy|upgradeTo|35871|30924|30913 +BridgeValidators|initialize|210762|306607|270900 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +EternalStorageProxy|deployment|378510|378510|378510 +HomeBridgeErcToNative|deployment|5155405|5155405|5155405 +EternalStorageProxy|upgradeTo|35871|30924|30913 +HomeBridgeErcToNative|initialize|264356|281376|278561 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +Total| |7872082|7975053|7936509 + +##### Foreign + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +EternalStorageProxy|deployment|378510|378510|378510 +BridgeValidators|deployment|1351491|1351491|1351491 +EternalStorageProxy|upgradeTo|35871|30924|30913 +BridgeValidators|initialize|210762|306607|270900 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +EternalStorageProxy|deployment|378510|378510|378510 +ForeignBridgeErcToNative|deployment|2863900|2863900|2863900 +EternalStorageProxy|upgradeTo|35871|30924|30913 +ForeignBridgeErcToNative|initialize|239130|239130|239130 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +Total| |5555351|5641302|5605573 + +#### Usage + +##### Validators + + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +To sign at the Home (each validator)| +HomeBridgeErcToNative|submitSignature|159926|275699|221104 +To relay signatures from the Home to the Foreign (one validator)| +ForeignBridgeErcToNative|executeSignatures|83142|140737|114527 +To sign and relay from the Foreign to the Home (each validator)| +HomeBridgeErcToNative|executeAffirmation|67379|166131|110341 + +##### Users + + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +To request transfer from the Home to the Foreign| +HomeBridgeErcToNative|fallback|81045|81045|81045 +To request transfer from the Foreign to the Home| +ERC677BridgeToken|transfer|37691|86589|55000 + From 7191c75b74802bd96415ce4cecb2abe5e9e53b34 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Thu, 17 Jan 2019 12:47:04 -0300 Subject: [PATCH 056/187] Refactor gas consumptions docs --- GAS_CONSUMPTION.md | 178 ++---------------------------------------- docs/ERC-TO-ERC.md | 58 ++++++++++++++ docs/NATIVE-TO-ERC.md | 59 ++++++++++++++ 3 files changed, 122 insertions(+), 173 deletions(-) create mode 100644 docs/ERC-TO-ERC.md create mode 100644 docs/NATIVE-TO-ERC.md diff --git a/GAS_CONSUMPTION.md b/GAS_CONSUMPTION.md index 88cc9ae49..24c5cbfa7 100644 --- a/GAS_CONSUMPTION.md +++ b/GAS_CONSUMPTION.md @@ -1,174 +1,6 @@ -## Gas Consumption +## Gas Consumption by Bridge Mode -### `NATIVE-TO-ERC` Bridge Mode - -#### Deployment -##### Home - Contract | Method | Min | Max | Avg ----- | ---- | ---- | ---- | ---- -EternalStorageProxy|deployment|378510|378510|378510 -BridgeValidators|deployment|1144207|1144207|1144207 -EternalStorageProxy|upgradeTo|35871|30924|30913 -BridgeValidators|initialize|187738|280847|253949 -EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -EternalStorageProxy|deployment|378510|378510|378510 -HomeBridgeNativeToErc|deployment|3327263|3327263|3327263 -EternalStorageProxy|upgradeTo|35871|30924|30913 -HomeBridgeNativeToErc|initialize|190051|190947|190755 -EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |5739327|5823438|5796326 - -##### Foreign - Contract | Method | Min | Max | Avg ----- | ---- | ---- | ---- | ---- -ERC677BridgeToken|deployment|1498202|1499226|1498829 -EternalStorageProxy|deployment|378510|378510|378510 -BridgeValidators|deployment|1144207|1144207|1144207 -EternalStorageProxy|upgradeTo|35871|30924|30913 -BridgeValidators|initialize|187738|280847|253949 -EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -EternalStorageProxy|deployment|378510|378510|378510 -ForeignBridgeNativeToErc|deployment|2768705|2768705|2768705 -EternalStorageProxy|upgradeTo|35871|30924|30913 -ForeignBridgeNativeToErc|initialize|213493|213557|213549 -ERC677BridgeToken|setBridgeContract|29432|44432|39432 -ERC677BridgeToken|transferOwnership|30860|30924|30913 -EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |6762705|6862072|6829736 - -#### Usage - -##### Validators - - Contract | Method | Min | Max | Avg ----- | ---- | ---- | ---- | ---- -To sign at the Home (each validator)| -HomeBridgeNativeToErc|submitSignature|159362|275135|220127 -To relay signatures from the Home to the Foreign (one validator)| -ForeignBridgeNativeToErc|executeSignatures|89201|146127|120917 -To sign and relay from the Foreign to the Home (each validator)| -HomeBridgeNativeToErc|executeAffirmation|64314|107669|83596 - -##### Users - - Contract | Method | Min | Max | Avg ----- | ---- | ---- | ---- | ---- -To request transfer from the Home to the Foreign| -HomeBridgeNativeToErc|fallback|46982|46982|46982 -To request transfer from the Foreign to the Home| -ERC677BridgeToken|transferAndCall|58370|166206|92399 - - -### `ERC-TO-ERC` Bridge Mode - -#### Deployment -##### Home - Contract | Method | Min | Max | Avg ----- | ---- | ---- | ---- | ---- -EternalStorageProxy|deployment|378510|378510|378510 -BridgeValidators|deployment|1144207|1144207|1144207 -EternalStorageProxy|upgradeTo|35871|30924|30913 -BridgeValidators|initialize|187738|280847|253949 -EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -EternalStorageProxy|deployment|378510|378510|378510 -HomeBridgeErcToErc|deployment|3528509|3528509|3528509 -EternalStorageProxy|upgradeTo|35871|30924|30913 -ERC677BridgeToken|deployment|1498202|1499226|1498829 -ERC677BridgeToken|setBridgeContract|29432|44432|39432 -ERC677BridgeToken|transferOwnership|30860|30924|30913 -HomeBridgeErcToErc|initialize|212299|213195|213003 -EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |7521315|7621514|7588994 - -##### Foreign - Contract | Method | Min | Max | Avg ----- | ---- | ---- | ---- | ---- -EternalStorageProxy|deployment|378510|378510|378510 -BridgeValidators|deployment|1144207|1144207|1144207 -EternalStorageProxy|upgradeTo|35871|30924|30913 -BridgeValidators|initialize|187738|280847|253949 -EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -EternalStorageProxy|deployment|378510|378510|378510 -ForeignBridgeErcToErc|deployment|2449436|2449436|2449436 -EternalStorageProxy|upgradeTo|35871|30924|30913 -ForeignBridgeErcToErc|initialize|150614|150614|150614 -EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |4822063|4905278|4878358 - -#### Usage - -##### Validators - - Contract | Method | Min | Max | Avg ----- | ---- | ---- | ---- | ---- -To sign at the Home (each validator)| -HomeBridgeErcToErc|submitSignature|159386|275159|220171 -To relay signatures from the Home to the Foreign (one validator)| -ForeignBridgeErcToErc|executeSignatures|73779|115769|93027 -To sign and relay from the Foreign to the Home (each validator)| -HomeBridgeErcToErc|executeAffirmation|79336|134607|108215 - -##### Users - - Contract | Method | Min | Max | Avg ----- | ---- | ---- | ---- | ---- -To request transfer from the Home to the Foreign| -ERC677BridgeToken|transferAndCall|58370|166206|92399 -To request transfer from the Foreign to the Home| -ERC677BridgeToken|transfer|37691|86589|55000 - - -### `ERC-TO-NATIVE` Bridge Mode - -#### Deployment -##### Home - Contract | Method | Min | Max | Avg ----- | ---- | ---- | ---- | ---- -EternalStorageProxy|deployment|378510|378510|378510 -BridgeValidators|deployment|1144207|1144207|1144207 -EternalStorageProxy|upgradeTo|35871|30924|30913 -BridgeValidators|initialize|187738|280847|253949 -EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -EternalStorageProxy|deployment|378510|378510|378510 -HomeBridgeErcToNative|deployment|3757420|3757420|3757420 -EternalStorageProxy|upgradeTo|35871|30924|30913 -HomeBridgeErcToNative|initialize|196910|213930|210795 -EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |6176343|6276578|6246523 - -##### Foreign - Contract | Method | Min | Max | Avg ----- | ---- | ---- | ---- | ---- -EternalStorageProxy|deployment|378510|378510|378510 -BridgeValidators|deployment|1144207|1144207|1144207 -EternalStorageProxy|upgradeTo|35871|30924|30913 -BridgeValidators|initialize|187738|280847|253949 -EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -EternalStorageProxy|deployment|378510|378510|378510 -ForeignBridgeErcToNative|deployment|2449564|2449564|2449564 -EternalStorageProxy|upgradeTo|35871|30924|30913 -ForeignBridgeErcToNative|initialize|150614|150614|150614 -EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| | - -#### Usage - -##### Validators - - Contract | Method | Min | Max | Avg ----- | ---- | ---- | ---- | ---- -To sign at the Home (each validator)| -HomeBridgeErcToNative|submitSignature|159428|275201|220206 -To relay signatures from the Home to the Foreign (one validator)| -ForeignBridgeErcToNative|executeSignatures|73779|115769|92985 -To sign and relay from the Foreign to the Home (each validator)| -HomeBridgeErcToNative|executeAffirmation|64380|140744|97562 - -##### Users - - Contract | Method | Min | Max | Avg ----- | ---- | ---- | ---- | ---- -To request transfer from the Home to the Foreign| -HomeBridgeErcToNative|fallback|80174|80174|80174 -To request transfer from the Foreign to the Home| -ERC677BridgeToken|transfer|37691|86589|55000 +- [NATIVE-TO-ERC](docs/NATIVE-TO-ERC.md) +- [ERC-TO-ERC](docs/ERC-TO-ERC.md) +- [ERC-TO-NATIVE](docs/ERC-TO-NATIVE.md) +- [ERC-TO-NATIVE-WITH-REWARD](docs/ERC-TO-NATIVE-WITH-REWARD.md) diff --git a/docs/ERC-TO-ERC.md b/docs/ERC-TO-ERC.md new file mode 100644 index 000000000..cf624bafa --- /dev/null +++ b/docs/ERC-TO-ERC.md @@ -0,0 +1,58 @@ +## Gas Consumption `ERC-TO-ERC` Bridge Mode + +#### Deployment +##### Home + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +EternalStorageProxy|deployment|378510|378510|378510 +BridgeValidators|deployment|1144207|1144207|1144207 +EternalStorageProxy|upgradeTo|35871|30924|30913 +BridgeValidators|initialize|187738|280847|253949 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +EternalStorageProxy|deployment|378510|378510|378510 +HomeBridgeErcToErc|deployment|3528509|3528509|3528509 +EternalStorageProxy|upgradeTo|35871|30924|30913 +ERC677BridgeToken|deployment|1498202|1499226|1498829 +ERC677BridgeToken|setBridgeContract|29432|44432|39432 +ERC677BridgeToken|transferOwnership|30860|30924|30913 +HomeBridgeErcToErc|initialize|212299|213195|213003 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +Total| |7521315|7621514|7588994 + +##### Foreign + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +EternalStorageProxy|deployment|378510|378510|378510 +BridgeValidators|deployment|1144207|1144207|1144207 +EternalStorageProxy|upgradeTo|35871|30924|30913 +BridgeValidators|initialize|187738|280847|253949 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +EternalStorageProxy|deployment|378510|378510|378510 +ForeignBridgeErcToErc|deployment|2449436|2449436|2449436 +EternalStorageProxy|upgradeTo|35871|30924|30913 +ForeignBridgeErcToErc|initialize|150614|150614|150614 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +Total| |4822063|4905278|4878358 + +#### Usage + +##### Validators + + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +To sign at the Home (each validator)| +HomeBridgeErcToErc|submitSignature|159386|275159|220171 +To relay signatures from the Home to the Foreign (one validator)| +ForeignBridgeErcToErc|executeSignatures|73779|115769|93027 +To sign and relay from the Foreign to the Home (each validator)| +HomeBridgeErcToErc|executeAffirmation|79336|134607|108215 + +##### Users + + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +To request transfer from the Home to the Foreign| +ERC677BridgeToken|transferAndCall|58370|166206|92399 +To request transfer from the Foreign to the Home| +ERC677BridgeToken|transfer|37691|86589|55000 + diff --git a/docs/NATIVE-TO-ERC.md b/docs/NATIVE-TO-ERC.md new file mode 100644 index 000000000..0c980a94f --- /dev/null +++ b/docs/NATIVE-TO-ERC.md @@ -0,0 +1,59 @@ +## Gas Consumption `NATIVE-TO-ERC` Bridge Mode + +#### Deployment +##### Home + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +EternalStorageProxy|deployment|378510|378510|378510 +BridgeValidators|deployment|1144207|1144207|1144207 +EternalStorageProxy|upgradeTo|35871|30924|30913 +BridgeValidators|initialize|187738|280847|253949 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +EternalStorageProxy|deployment|378510|378510|378510 +HomeBridgeNativeToErc|deployment|3327263|3327263|3327263 +EternalStorageProxy|upgradeTo|35871|30924|30913 +HomeBridgeNativeToErc|initialize|190051|190947|190755 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +Total| |5739327|5823438|5796326 + +##### Foreign + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +ERC677BridgeToken|deployment|1498202|1499226|1498829 +EternalStorageProxy|deployment|378510|378510|378510 +BridgeValidators|deployment|1144207|1144207|1144207 +EternalStorageProxy|upgradeTo|35871|30924|30913 +BridgeValidators|initialize|187738|280847|253949 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +EternalStorageProxy|deployment|378510|378510|378510 +ForeignBridgeNativeToErc|deployment|2768705|2768705|2768705 +EternalStorageProxy|upgradeTo|35871|30924|30913 +ForeignBridgeNativeToErc|initialize|213493|213557|213549 +ERC677BridgeToken|setBridgeContract|29432|44432|39432 +ERC677BridgeToken|transferOwnership|30860|30924|30913 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +Total| |6762705|6862072|6829736 + +#### Usage + +##### Validators + + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +To sign at the Home (each validator)| +HomeBridgeNativeToErc|submitSignature|159362|275135|220127 +To relay signatures from the Home to the Foreign (one validator)| +ForeignBridgeNativeToErc|executeSignatures|89201|146127|120917 +To sign and relay from the Foreign to the Home (each validator)| +HomeBridgeNativeToErc|executeAffirmation|64314|107669|83596 + +##### Users + + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +To request transfer from the Home to the Foreign| +HomeBridgeNativeToErc|fallback|46982|46982|46982 +To request transfer from the Foreign to the Home| +ERC677BridgeToken|transferAndCall|58370|166206|92399 + + From 7aee850cdb2a720842ace31000d51f0d8a63d527 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Thu, 17 Jan 2019 12:56:00 -0300 Subject: [PATCH 057/187] Fix ERC-TO-NATIVE foreign gas consumption doc --- docs/ERC-TO-NATIVE-WITH-REWARD.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/ERC-TO-NATIVE-WITH-REWARD.md b/docs/ERC-TO-NATIVE-WITH-REWARD.md index 799f74fa5..bf68068f9 100644 --- a/docs/ERC-TO-NATIVE-WITH-REWARD.md +++ b/docs/ERC-TO-NATIVE-WITH-REWARD.md @@ -30,7 +30,7 @@ ForeignBridgeErcToNative|deployment|2863900|2863900|2863900 EternalStorageProxy|upgradeTo|35871|30924|30913 ForeignBridgeErcToNative|initialize|239130|239130|239130 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |5555351|5641302|5555351 5641302 5605573 +Total| |5555351|5641302|5605573 #### Usage From dd6417f46c1d6838cdb0a4f09e4ea3e460c029b2 Mon Sep 17 00:00:00 2001 From: Tal Beja Date: Sun, 20 Jan 2019 16:10:17 +0200 Subject: [PATCH 058/187] change `bridgeFactory` requirments. change`bridgeFactory` event to emit block number and home token. --- .../factories/ForeignBridgeFactory.sol | 11 ++++++----- .../factories/HomeBridgeFactory.sol | 12 ++++++------ deploy/deploy.js | 2 +- deploy/src/factories/home.js | 7 +++++-- 4 files changed, 18 insertions(+), 14 deletions(-) diff --git a/contracts/upgradeable_contracts/factories/ForeignBridgeFactory.sol b/contracts/upgradeable_contracts/factories/ForeignBridgeFactory.sol index b9dc03962..6db24efbd 100644 --- a/contracts/upgradeable_contracts/factories/ForeignBridgeFactory.sol +++ b/contracts/upgradeable_contracts/factories/ForeignBridgeFactory.sol @@ -8,7 +8,7 @@ import "../EternalOwnable.sol"; contract ForeignBridgeFactory is EternalStorage, EternalOwnable { - event ForeignBridgeDeployed(address indexed _foreignBridge, address indexed _foreignValidators); + event ForeignBridgeDeployed(address indexed _foreignBridge, address indexed _foreignValidators, uint256 _blockNumber); function getBridgeFactoryVersion() public pure returns(uint64 major, uint64 minor, uint64 patch) { return (2, 2, 0); @@ -27,16 +27,17 @@ contract ForeignBridgeFactory is EternalStorage, EternalOwnable { uint256 _homeMaxPerTx, address _foreignBridgeOwner, address _foreignProxyOwner) public { + require(_owner != address(0)); require(_bridgeValidatorsImplementation != address(0)); require(_requiredSignatures >= 1); require(_bridgeValidatorsOwner != address(0)); require(_foreignBridgeErcToErcImplementation != address(0)); - require(_requiredBlockConfirmations > 0); + require(_requiredBlockConfirmations != 0); + require(_gasPrice > 0); require(_foreignMaxPerTx >= 0); - require(_homeDailyLimit >= 0); - require(_homeMaxPerTx >= 0); + require(_homeMaxPerTx < _homeDailyLimit); require(_foreignBridgeOwner != address(0)); require(_foreignProxyOwner != address(0)); @@ -78,7 +79,7 @@ contract ForeignBridgeFactory is EternalStorage, EternalOwnable { // transger proxy upgradeability admin proxy.transferProxyOwnership(foreignBridgeProxyOwner()); // emit event - emit ForeignBridgeDeployed(foreignBridge, bridgeValidators); + emit ForeignBridgeDeployed(foreignBridge, bridgeValidators, block.number); } diff --git a/contracts/upgradeable_contracts/factories/HomeBridgeFactory.sol b/contracts/upgradeable_contracts/factories/HomeBridgeFactory.sol index b780b8f40..e065200ca 100644 --- a/contracts/upgradeable_contracts/factories/HomeBridgeFactory.sol +++ b/contracts/upgradeable_contracts/factories/HomeBridgeFactory.sol @@ -9,7 +9,7 @@ import "../EternalOwnable.sol"; contract HomeBridgeFactory is EternalStorage, EternalOwnable { - event HomeBridgeDeployed(address indexed _homeBridge, address indexed _homeValidators); + event HomeBridgeDeployed(address indexed _homeBridge, address indexed _homeValidators, address indexed _token, uint256 _blockNumber); function getBridgeFactoryVersion() public pure returns(uint64 major, uint64 minor, uint64 patch) { return (2, 2, 0); @@ -31,16 +31,16 @@ contract HomeBridgeFactory is EternalStorage, EternalOwnable { address _homeBridgeOwner, address _homeProxyOwner) public { + require(_owner != address(0)); require(_bridgeValidatorsImplementation != address(0)); require(_requiredSignatures >= 1); require(_bridgeValidatorsOwner != address(0)); require(_homeBridgeErcToErcImplementation != address(0)); + require(_gasPrice > 0); require(_requiredBlockConfirmations > 0); - require(_dailyLimit >= 0); - require(_maxPerTx >= 0); - require(_minPerTx >= 0); - require(_foreignDailyLimit >= 0); + require(_minPerTx > 0 && _maxPerTx > _minPerTx && _dailyLimit > _maxPerTx); + require(_foreignMaxPerTx < _foreignDailyLimit); require(_homeBridgeOwner != address(0)); require(_homeProxyOwner != address(0)); @@ -90,7 +90,7 @@ contract HomeBridgeFactory is EternalStorage, EternalOwnable { // transger proxy upgradeability admin proxy.transferProxyOwnership(homeBridgeProxyOwner()); // emit event - emit HomeBridgeDeployed(homeBridge, bridgeValidators); + emit HomeBridgeDeployed(homeBridge, bridgeValidators, token, block.number); } diff --git a/deploy/deploy.js b/deploy/deploy.js index 1eecd87c4..2d0a34d7c 100644 --- a/deploy/deploy.js +++ b/deploy/deploy.js @@ -118,7 +118,7 @@ async function deployFactory() { const { foreignFactory } = await deployForeign() console.log('\nDeployment has been completed.\n\n') console.log(`[ Home ] HomeFactory: ${homeFactory.address} at block ${homeFactory.deployedBlockNumber}`) - console.log(`[ Home ] mapper: ${mapper.address}`) + console.log(`[ Home ] mapper: ${mapper.address} at block ${mapper.deployedBlockNumber}`) console.log( `[ Foreign ] ForeignFactory: ${foreignFactory.address} at block ${ foreignFactory.deployedBlockNumber diff --git a/deploy/src/factories/home.js b/deploy/src/factories/home.js index 76c46f0af..5d6934a3c 100644 --- a/deploy/src/factories/home.js +++ b/deploy/src/factories/home.js @@ -106,7 +106,7 @@ async function deployHome() { VALIDATORS: ${VALIDATORS}, HOME_VALIDATORS_OWNER: ${HOME_VALIDATORS_OWNER}, HOME_BRIDGE_IMPLEMENTATION_ADDRESS: ${HOME_BRIDGE_IMPLEMENTATION_ADDRESS}, - HOME_REQUIRED_BLOCK_CONFIRMATIONS" ${HOME_REQUIRED_BLOCK_CONFIRMATIONS}, + HOME_REQUIRED_BLOCK_CONFIRMATIONS: ${HOME_REQUIRED_BLOCK_CONFIRMATIONS}, HOME_GAS_PRICE: ${HOME_GAS_PRICE}, HOME_DAILY_LIMIT: ${HOME_DAILY_LIMIT}, HOME_MAX_AMOUNT_PER_TX: ${HOME_MAX_AMOUNT_PER_TX}, @@ -230,7 +230,10 @@ async function deployHome() { address: storageBridgeFactoryHome.options.address, deployedBlockNumber: Web3Utils.hexToNumber(storageBridgeFactoryHome.deployedBlockNumber) }, - mapper: {address: storageBridgeMapperHome.options.address } + mapper: { + address: storageBridgeMapperHome.options.address, + deployedBlockNumber: Web3Utils.hexToNumber(storageBridgeMapperHome.deployedBlockNumber) + } } } module.exports = deployHome From 0576f184e2820c47be346aa6e18c2ee0bcc2931c Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 22 Jan 2019 11:10:28 -0300 Subject: [PATCH 059/187] Add internal setFee method on RewardableBridge --- contracts/upgradeable_contracts/RewardableBridge.sol | 6 +++++- .../erc20_to_native/HomeBridgeErcToNative.sol | 2 +- 2 files changed, 6 insertions(+), 2 deletions(-) diff --git a/contracts/upgradeable_contracts/RewardableBridge.sol b/contracts/upgradeable_contracts/RewardableBridge.sol index 2bf47cfe2..fdae05f6e 100644 --- a/contracts/upgradeable_contracts/RewardableBridge.sol +++ b/contracts/upgradeable_contracts/RewardableBridge.sol @@ -6,7 +6,7 @@ import "./Ownable.sol"; contract RewardableBridge is Ownable { function setFee(uint256 _fee) external onlyOwner { - require(feeManagerContract().delegatecall(abi.encodeWithSignature("setFee(uint256)", _fee))); + _setFee(feeManagerContract(), _fee); } function getFee() public view returns(uint256) { @@ -32,6 +32,10 @@ contract RewardableBridge is Ownable { addressStorage[keccak256(abi.encodePacked("feeManagerContract"))] = _feeManager; } + function _setFee(address _feeManager, uint256 _fee) internal { + require(_feeManager.delegatecall(abi.encodeWithSignature("setFee(uint256)", _fee))); + } + function isContract(address _addr) internal view returns (bool) { uint length; diff --git a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol index 94b15c4ea..5bd2f4e93 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol @@ -93,7 +93,7 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, ); require(isContract(_feeManager)); addressStorage[keccak256(abi.encodePacked("feeManagerContract"))] = _feeManager; - require(_feeManager.delegatecall(abi.encodeWithSignature("setFee(uint256)", _fee))); + _setFee(_feeManager, _fee); setInitialize(true); return isInitialized(); From 51a31be31f1e70380159b78a7ac6cd8b2b7eecdd Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 22 Jan 2019 11:20:55 -0300 Subject: [PATCH 060/187] Rename variable on erc-to-native home deploy script --- deploy/src/erc_to_native/home.js | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/deploy/src/erc_to_native/home.js b/deploy/src/erc_to_native/home.js index c3aa123ff..c1badbc55 100644 --- a/deploy/src/erc_to_native/home.js +++ b/deploy/src/erc_to_native/home.js @@ -34,7 +34,7 @@ const { const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVATE_KEY) -const useRewardableValidators = REWARDABLE_VALIDATORS === 'true' +const isRewardableBridge = REWARDABLE_VALIDATORS === 'true' async function deployHome() { let homeNonce = await web3Home.eth.getTransactionCount(DEPLOYMENT_ACCOUNT_ADDRESS) @@ -47,7 +47,7 @@ async function deployHome() { homeNonce++ console.log('\ndeploying implementation for home validators') - const bridgeValidatorsContract = useRewardableValidators ? RewardableValidators : BridgeValidators + const bridgeValidatorsContract = isRewardableBridge ? RewardableValidators : BridgeValidators const bridgeValidatorsHome = await deployContract(bridgeValidatorsContract, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, nonce: homeNonce @@ -74,7 +74,7 @@ async function deployHome() { let initializeData - if (useRewardableValidators) { + if (isRewardableBridge) { console.log( `REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, VALIDATORS: ${VALIDATORS}, VALIDATORS_REWARD_ACCOUNTS: ${VALIDATORS_REWARD_ACCOUNTS}, HOME_VALIDATORS_OWNER: ${HOME_VALIDATORS_OWNER}` ) @@ -152,7 +152,7 @@ async function deployHome() { let initializeHomeBridgeData homeBridgeImplementation.options.address = homeBridgeStorage.options.address - if (useRewardableValidators) { + if (isRewardableBridge) { console.log('\ndeploying implementation for fee manager') const feeManager = await deployContract(FeeManagerErcToNative, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, From 228aaf183ab278c18fefc7a6e44b3c934f06425c Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 22 Jan 2019 11:51:08 -0300 Subject: [PATCH 061/187] Add HOME_REWARDABLE and FOREIGN_REWARDABLE env vars --- deploy/.env.example | 8 +++++--- deploy/README.md | 10 ++++++---- deploy/src/erc_to_native/home.js | 4 ++-- deploy/src/loadEnv.js | 16 ++++++++++++++-- 4 files changed, 27 insertions(+), 11 deletions(-) diff --git a/deploy/.env.example b/deploy/.env.example index dc487f5c8..42f7cf8ed 100644 --- a/deploy/.env.example +++ b/deploy/.env.example @@ -40,9 +40,11 @@ REQUIRED_NUMBER_OF_VALIDATORS=1 #E.g. VALIDATORS=0x 0x 0x VALIDATORS=0x #for erc_to_native mode -#Set to true if RewardableValidators will be used and fee will be charged -REWARDABLE_VALIDATORS=false -#If REWARDABLE_VALIDATORS=true, list validators accounts were rewards should be transferred separated by space without quotes +#Set to true if fee will be charged on home side +HOME_REWARDABLE=false +#Set to true if fee will be charged on foreign side +FOREIGN_REWARDABLE=false +#If HOME_REWARDABLE or FOREIGN_REWARDABLE set to true, list validators accounts were rewards should be transferred separated by space without quotes #E.g. VALIDATORS_REWARD_ACCOUNTS=0x 0x 0x VALIDATORS_REWARD_ACCOUNTS=0x diff --git a/deploy/README.md b/deploy/README.md index e6d6ec390..4f71dc325 100644 --- a/deploy/README.md +++ b/deploy/README.md @@ -330,14 +330,16 @@ REQUIRED_NUMBER_OF_VALIDATORS=1 VALIDATORS=0x 0x 0x -# The flag defining whether to use RewardableValidators contract and set a fee manager contract -REWARDABLE_VALIDATORS=false +# The flag defining whether to use RewardableValidators contract and set a fee manager contract on Home network +HOME_REWARDABLE=false +# The flag defining whether to use RewardableValidators contract and set a fee manager contract on Foreign network +FOREIGN_REWARDABLE=false # List validators accounts were rewards should be transferred separated by space without quotes -# Makes sense only when REWARDABLE_VALIDATORS=true +# Makes sense only when HOME_REWARDABLE=true or FOREIGN_REWARDABLE=true VALIDATORS_REWARD_ACCOUNTS=0x 0x 0x # Fee to be charged for each transfer -# Makes sense only when REWARDABLE_VALIDATORS=true +# Makes sense only when HOME_REWARDABLE=true or FOREIGN_REWARDABLE=true # e.g. 0.1% fee BRIDGE_FEE=0.001 ``` diff --git a/deploy/src/erc_to_native/home.js b/deploy/src/erc_to_native/home.js index c1badbc55..66f3ffaef 100644 --- a/deploy/src/erc_to_native/home.js +++ b/deploy/src/erc_to_native/home.js @@ -28,13 +28,13 @@ const { HOME_REQUIRED_BLOCK_CONFIRMATIONS, FOREIGN_DAILY_LIMIT, FOREIGN_MAX_AMOUNT_PER_TX, - REWARDABLE_VALIDATORS, + HOME_REWARDABLE, BRIDGE_FEE } = env const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVATE_KEY) -const isRewardableBridge = REWARDABLE_VALIDATORS === 'true' +const isRewardableBridge = HOME_REWARDABLE === 'true' async function deployHome() { let homeNonce = await web3Home.eth.getTransactionCount(DEPLOYMENT_ACCOUNT_ADDRESS) diff --git a/deploy/src/loadEnv.js b/deploy/src/loadEnv.js index cc07c48a5..8bdca0bd8 100644 --- a/deploy/src/loadEnv.js +++ b/deploy/src/loadEnv.js @@ -22,7 +22,13 @@ const addressesValidator = envalid.makeValidator(addresses => { return addresses }) -const { BRIDGE_MODE, REWARDABLE_VALIDATORS, VALIDATORS, VALIDATORS_REWARD_ACCOUNTS } = process.env +const { + BRIDGE_MODE, + HOME_REWARDABLE, + FOREIGN_REWARDABLE, + VALIDATORS, + VALIDATORS_REWARD_ACCOUNTS +} = process.env if (!validBridgeModes.includes(BRIDGE_MODE)) { throw new Error(`Invalid bridge mode: ${BRIDGE_MODE}`) @@ -84,9 +90,15 @@ if (BRIDGE_MODE === 'ERC_TO_NATIVE') { default: ZERO_ADDRESS }) } + + if (FOREIGN_REWARDABLE === 'true') { + throw new Error( + `Collecting fees on Foreign Network on ${BRIDGE_MODE} bridge mode is not supported.` + ) + } } -if (REWARDABLE_VALIDATORS === 'true') { +if (HOME_REWARDABLE === 'true' || FOREIGN_REWARDABLE === 'true') { const validatorsLength = VALIDATORS ? VALIDATORS.split(' ').length : 0 const validatorsRewardLength = VALIDATORS_REWARD_ACCOUNTS ? VALIDATORS_REWARD_ACCOUNTS.split(' ').length From bdc24f976f515cc1e8560ee531648d048786858c Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 22 Jan 2019 12:09:14 -0300 Subject: [PATCH 062/187] Add HOME_TRANSACTIONS_FEE and FOREIGN_TRANSACTIONS_FEE env vars --- deploy/.env.example | 7 ++++--- deploy/README.md | 10 +++++++--- deploy/src/erc_to_native/home.js | 4 ++-- deploy/src/loadEnv.js | 29 +++++++++++++++++++---------- 4 files changed, 32 insertions(+), 18 deletions(-) diff --git a/deploy/.env.example b/deploy/.env.example index 42f7cf8ed..2f5a7e886 100644 --- a/deploy/.env.example +++ b/deploy/.env.example @@ -48,10 +48,11 @@ FOREIGN_REWARDABLE=false #E.g. VALIDATORS_REWARD_ACCOUNTS=0x 0x 0x VALIDATORS_REWARD_ACCOUNTS=0x -# Fee to be charged for each transfer: +# Fee to be charged for each transfer on Home: # E.g. 0.1% fee -BRIDGE_FEE=0.001 - +HOME_TRANSACTIONS_FEE=0.001 +# Fee to be charged for each transfer on Foreign: +FOREIGN_TRANSACTIONS_FEE=0.001 #for bridge native_to_erc mode DEPLOY_REWARDABLE_TOKEN=false DPOS_VALIDATOR_SET_ADDRESS= diff --git a/deploy/README.md b/deploy/README.md index 4f71dc325..d792d2ad8 100644 --- a/deploy/README.md +++ b/deploy/README.md @@ -338,8 +338,12 @@ FOREIGN_REWARDABLE=false # Makes sense only when HOME_REWARDABLE=true or FOREIGN_REWARDABLE=true VALIDATORS_REWARD_ACCOUNTS=0x 0x 0x -# Fee to be charged for each transfer -# Makes sense only when HOME_REWARDABLE=true or FOREIGN_REWARDABLE=true +# Fee to be charged for each transfer on Home network +# Makes sense only when HOME_REWARDABLE=true +# e.g. 0.1% fee +HOME_TRANSACTIONS_FEE=0.001 +# Fee to be charged for each transfer on Foreign network +# Makes sense only when FOREIGN_REWARDABLE=true # e.g. 0.1% fee -BRIDGE_FEE=0.001 +FOREIGN_TRANSACTIONS_FEE=0.001 ``` diff --git a/deploy/src/erc_to_native/home.js b/deploy/src/erc_to_native/home.js index 66f3ffaef..b6851bc98 100644 --- a/deploy/src/erc_to_native/home.js +++ b/deploy/src/erc_to_native/home.js @@ -29,7 +29,7 @@ const { FOREIGN_DAILY_LIMIT, FOREIGN_MAX_AMOUNT_PER_TX, HOME_REWARDABLE, - BRIDGE_FEE + HOME_TRANSACTIONS_FEE } = env const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVATE_KEY) @@ -161,7 +161,7 @@ async function deployHome() { console.log('[Home] feeManager Implementation: ', feeManager.options.address) homeNonce++ - const feeInWei = Web3Utils.toWei(BRIDGE_FEE.toString(), 'ether') + const feeInWei = Web3Utils.toWei(HOME_TRANSACTIONS_FEE.toString(), 'ether') console.log('\ninitializing Home Bridge with fee contract:\n') initializeHomeBridgeData = await homeBridgeImplementation.methods .rewardableInitialize( diff --git a/deploy/src/loadEnv.js b/deploy/src/loadEnv.js index 8bdca0bd8..71764ca75 100644 --- a/deploy/src/loadEnv.js +++ b/deploy/src/loadEnv.js @@ -21,6 +21,15 @@ const addressesValidator = envalid.makeValidator(addresses => { addresses.split(' ').forEach(validateAddress) return addresses }) +const validateRewardableAddresses = (validators, rewards) => { + const validatorsLength = validators ? validators.split(' ').length : 0 + const validatorsRewardLength = rewards ? rewards.split(' ').length : 0 + if (validatorsLength !== validatorsRewardLength) { + throw new Error( + `List of rewards accounts (${validatorsRewardLength} accounts) should be the same length as list of validators (${validatorsLength} accounts)` + ) + } +} const { BRIDGE_MODE, @@ -98,21 +107,21 @@ if (BRIDGE_MODE === 'ERC_TO_NATIVE') { } } -if (HOME_REWARDABLE === 'true' || FOREIGN_REWARDABLE === 'true') { - const validatorsLength = VALIDATORS ? VALIDATORS.split(' ').length : 0 - const validatorsRewardLength = VALIDATORS_REWARD_ACCOUNTS - ? VALIDATORS_REWARD_ACCOUNTS.split(' ').length - : 0 - if (validatorsLength !== validatorsRewardLength) { - throw new Error( - `List of rewards accounts (${validatorsRewardLength} accounts) should be the same length as list of validators (${validatorsLength} accounts)` - ) +if (HOME_REWARDABLE === 'true') { + validateRewardableAddresses(VALIDATORS, VALIDATORS_REWARD_ACCOUNTS) + validations = { + ...validations, + VALIDATORS_REWARD_ACCOUNTS: addressesValidator(), + HOME_TRANSACTIONS_FEE: envalid.num() } +} +if (FOREIGN_REWARDABLE === 'true') { + validateRewardableAddresses(VALIDATORS, VALIDATORS_REWARD_ACCOUNTS) validations = { ...validations, VALIDATORS_REWARD_ACCOUNTS: addressesValidator(), - BRIDGE_FEE: envalid.num() + FOREIGN_TRANSACTIONS_FEE: envalid.num() } } From e0bf48958fef5f0706f6cf79b0818d987f8c1030 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 22 Jan 2019 12:32:05 -0300 Subject: [PATCH 063/187] Improve validators and reward address log on deploy script --- deploy/src/deploymentUtils.js | 10 +++++++++- deploy/src/erc_to_native/home.js | 10 ++++++++-- 2 files changed, 17 insertions(+), 3 deletions(-) diff --git a/deploy/src/deploymentUtils.js b/deploy/src/deploymentUtils.js index 3d06a86fd..82241e470 100644 --- a/deploy/src/deploymentUtils.js +++ b/deploy/src/deploymentUtils.js @@ -140,6 +140,13 @@ function privateKeyToAddress(privateKey) { return new Web3().eth.accounts.privateKeyToAccount(add0xPrefix(privateKey)).address } +function logValidatorsAndRewardAccounts(validators, rewards) { + console.log(`VALIDATORS\n==========`) + validators.forEach((validator, index) => { + console.log(`${index + 1}: ${validator}, reward address ${rewards[index]}`) + }) +} + module.exports = { deployContract, sendNodeRequest, @@ -147,5 +154,6 @@ module.exports = { sendRawTx, sendRawTxHome, sendRawTxForeign, - privateKeyToAddress + privateKeyToAddress, + logValidatorsAndRewardAccounts } diff --git a/deploy/src/erc_to_native/home.js b/deploy/src/erc_to_native/home.js index b6851bc98..b5290ffe2 100644 --- a/deploy/src/erc_to_native/home.js +++ b/deploy/src/erc_to_native/home.js @@ -2,7 +2,12 @@ const assert = require('assert') const Web3Utils = require('web3-utils') const env = require('../loadEnv') -const { deployContract, privateKeyToAddress, sendRawTxHome } = require('../deploymentUtils') +const { + deployContract, + privateKeyToAddress, + sendRawTxHome, + logValidatorsAndRewardAccounts +} = require('../deploymentUtils') const { web3Home, deploymentPrivateKey, HOME_RPC_URL } = require('../web3') const EternalStorageProxy = require('../../../build/contracts/EternalStorageProxy.json') @@ -76,8 +81,9 @@ async function deployHome() { if (isRewardableBridge) { console.log( - `REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, VALIDATORS: ${VALIDATORS}, VALIDATORS_REWARD_ACCOUNTS: ${VALIDATORS_REWARD_ACCOUNTS}, HOME_VALIDATORS_OWNER: ${HOME_VALIDATORS_OWNER}` + `REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, HOME_VALIDATORS_OWNER: ${HOME_VALIDATORS_OWNER}` ) + logValidatorsAndRewardAccounts(VALIDATORS, VALIDATORS_REWARD_ACCOUNTS) initializeData = await bridgeValidatorsHome.methods .initialize( REQUIRED_NUMBER_OF_VALIDATORS, From e56b51d669abd2465d51ab56b7269b43c774a4b3 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 22 Jan 2019 12:51:39 -0300 Subject: [PATCH 064/187] Update home bridge initialization log on erc-to-native deploy script --- deploy/src/erc_to_native/home.js | 30 +++++++++++++++++++++++++++++- 1 file changed, 29 insertions(+), 1 deletion(-) diff --git a/deploy/src/erc_to_native/home.js b/deploy/src/erc_to_native/home.js index b5290ffe2..e37427a2a 100644 --- a/deploy/src/erc_to_native/home.js +++ b/deploy/src/erc_to_native/home.js @@ -169,6 +169,25 @@ async function deployHome() { const feeInWei = Web3Utils.toWei(HOME_TRANSACTIONS_FEE.toString(), 'ether') console.log('\ninitializing Home Bridge with fee contract:\n') + console.log(`Home Validators: ${storageValidatorsHome.options.address}, + HOME_DAILY_LIMIT : ${HOME_DAILY_LIMIT} which is ${Web3Utils.fromWei(HOME_DAILY_LIMIT)} in eth, + HOME_MAX_AMOUNT_PER_TX: ${HOME_MAX_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( + HOME_MAX_AMOUNT_PER_TX + )} in eth, + HOME_MIN_AMOUNT_PER_TX: ${HOME_MIN_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( + HOME_MIN_AMOUNT_PER_TX + )} in eth, + HOME_GAS_PRICE: ${HOME_GAS_PRICE}, HOME_REQUIRED_BLOCK_CONFIRMATIONS : ${HOME_REQUIRED_BLOCK_CONFIRMATIONS}, + BLOCK_REWARD_ADDRESS: ${BLOCK_REWARD_ADDRESS}, + FOREIGN_DAILY_LIMIT: ${FOREIGN_DAILY_LIMIT} which is ${Web3Utils.fromWei( + FOREIGN_DAILY_LIMIT + )} in eth, + FOREIGN_MAX_AMOUNT_PER_TX: ${FOREIGN_MAX_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( + FOREIGN_MAX_AMOUNT_PER_TX + )} in eth, + HOME_BRIDGE_OWNER: ${HOME_BRIDGE_OWNER}, + Fee Manager: ${feeManager.options.address}, + Fee: ${feeInWei} which is ${HOME_TRANSACTIONS_FEE * 100}%`) initializeHomeBridgeData = await homeBridgeImplementation.methods .rewardableInitialize( storageValidatorsHome.options.address, @@ -195,7 +214,16 @@ async function deployHome() { HOME_MIN_AMOUNT_PER_TX: ${HOME_MIN_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( HOME_MIN_AMOUNT_PER_TX )} in eth, - HOME_GAS_PRICE: ${HOME_GAS_PRICE}, HOME_REQUIRED_BLOCK_CONFIRMATIONS : ${HOME_REQUIRED_BLOCK_CONFIRMATIONS}`) + HOME_GAS_PRICE: ${HOME_GAS_PRICE}, HOME_REQUIRED_BLOCK_CONFIRMATIONS : ${HOME_REQUIRED_BLOCK_CONFIRMATIONS}, + BLOCK_REWARD_ADDRESS: ${BLOCK_REWARD_ADDRESS}, + FOREIGN_DAILY_LIMIT: ${FOREIGN_DAILY_LIMIT} which is ${Web3Utils.fromWei( + FOREIGN_DAILY_LIMIT + )} in eth, + FOREIGN_MAX_AMOUNT_PER_TX: ${FOREIGN_MAX_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( + FOREIGN_MAX_AMOUNT_PER_TX + )} in eth, + HOME_BRIDGE_OWNER: ${HOME_BRIDGE_OWNER} + `) initializeHomeBridgeData = await homeBridgeImplementation.methods .initialize( storageValidatorsHome.options.address, From 74743cbd8741ea51ffffad27474c22f185ceab13 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 22 Jan 2019 14:24:48 -0300 Subject: [PATCH 065/187] Update HomeBridgeErcToNative gas usage docs --- docs/ERC-TO-NATIVE-WITH-REWARD.md | 6 +++--- docs/ERC-TO-NATIVE.md | 4 ++-- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/docs/ERC-TO-NATIVE-WITH-REWARD.md b/docs/ERC-TO-NATIVE-WITH-REWARD.md index bf68068f9..fb616c18e 100644 --- a/docs/ERC-TO-NATIVE-WITH-REWARD.md +++ b/docs/ERC-TO-NATIVE-WITH-REWARD.md @@ -10,12 +10,12 @@ EternalStorageProxy|upgradeTo|35871|30924|30913 RewardableValidators|initialize|202711|423292|318008 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 EternalStorageProxy|deployment|378510|378510|378510 -HomeBridgeErcToNative|deployment|5155405|5155405|5155405 +HomeBridgeErcToNative|deployment|5088498|5088498|5088498 EternalStorageProxy|upgradeTo|35871|30924|30913 FeeManagerErcToNative|deployment|849694|849694|849694 -HomeBridgeErcToNative|rewardableInitialize|327016|327080|327064 +HomeBridgeErcToNative|rewardableInitialize|327113|327177|327161 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |9040684|9251435|9146113 +Total| |8973874|9184625|9079303 ##### Foreign Contract | Method | Min | Max | Avg diff --git a/docs/ERC-TO-NATIVE.md b/docs/ERC-TO-NATIVE.md index bd354b12d..b4a0877f7 100644 --- a/docs/ERC-TO-NATIVE.md +++ b/docs/ERC-TO-NATIVE.md @@ -10,11 +10,11 @@ EternalStorageProxy|upgradeTo|35871|30924|30913 BridgeValidators|initialize|210762|306607|270900 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 EternalStorageProxy|deployment|378510|378510|378510 -HomeBridgeErcToNative|deployment|5155405|5155405|5155405 +HomeBridgeErcToNative|deployment|5088498|5088498|5088498 EternalStorageProxy|upgradeTo|35871|30924|30913 HomeBridgeErcToNative|initialize|264356|281376|278561 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |7872082|7975053|7936509 +Total| |7805175|7908146|7869602 ##### Foreign Contract | Method | Min | Max | Avg From 6d6b549003499cd0d8e4bd3b4a75c039b9d2753f Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 23 Jan 2019 10:06:30 -0300 Subject: [PATCH 066/187] Add REWARD_MANAGEMENT.md --- README.md | 3 +++ REWARD_MANAGEMENT.md | 21 +++++++++++++++++++++ 2 files changed, 24 insertions(+) create mode 100644 REWARD_MANAGEMENT.md diff --git a/README.md b/README.md index def139c3f..f0f6c3e1a 100644 --- a/README.md +++ b/README.md @@ -129,6 +129,9 @@ docker-compose down ### Gas Consumption The [GAS_CONSUMPTION](GAS_CONSUMPTION.md) file includes Min, Max, and Avg gas consumption figures for contracts associated with each bridge mode. +### Reward Management +The [REWARD_MANAGEMENT](REWARD_MANAGEMENT.md) file includes information on how rewards are distributed among the validators on each bridge mode. + ### Testing environment To test the bridge scripts in ERC20-to-ERC20 mode on a testnet like Sokol or Kovan, you must deploy an ERC20 token to the foreign network. This can be done by running the following command: diff --git a/REWARD_MANAGEMENT.md b/REWARD_MANAGEMENT.md new file mode 100644 index 000000000..270655cf1 --- /dev/null +++ b/REWARD_MANAGEMENT.md @@ -0,0 +1,21 @@ +# Reward Management + +## NATIVE-TO-ERC + +### Home to Foreign transfer +Fees are calculated and distributed on Foreign network. Validators will receive ERC20 tokens. +![native-erc-hometoforeign](https://user-images.githubusercontent.com/4614574/51607402-4bda6180-1ef3-11e9-91e3-50fe5d35d296.png) + +### Foreign to Home transfer +Fees are calculated and distributed on Home network. Validators will receive native coins. +![native-erc-foreigntohome](https://user-images.githubusercontent.com/4614574/51607428-5d236e00-1ef3-11e9-8083-3669899c7252.png) + +## ERC-TO-NATIVE + +### Foreign to Home transfer +Fees are calculated and distributed on Home network. Validators will receive native coins. +![erc-native-foreigntohome](https://user-images.githubusercontent.com/4614574/51607498-9065fd00-1ef3-11e9-8212-fc1ba16ae91a.png) + +### Home to Foreign transfer +Fees are calculated and distributed on Home network. Validators will receive native coins. +![erc-native-hometoforeign](https://user-images.githubusercontent.com/4614574/51607508-96f47480-1ef3-11e9-93a1-0f1111793f2a.png) From 164c8e662f8aea2e8da644531466a43c749882b1 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 21 Jan 2019 17:05:28 -0300 Subject: [PATCH 067/187] Add Native-to-Erc fee manager --- .../native_to_erc20/FeeManagerNativeToErc.sol | 23 ++++ .../ForeignBridgeNativeToErc.sol | 93 ++++++++++++--- .../native_to_erc20/HomeBridgeNativeToErc.sol | 110 ++++++++++++++---- 3 files changed, 189 insertions(+), 37 deletions(-) create mode 100644 contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErc.sol diff --git a/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErc.sol new file mode 100644 index 000000000..d20c1ac96 --- /dev/null +++ b/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErc.sol @@ -0,0 +1,23 @@ +pragma solidity 0.4.24; + +import "../BaseFeeManager.sol"; +import "../../IBurnableMintableERC677Token.sol"; +import "../Sacrifice.sol"; + + +contract FeeManagerNativeToErc is BaseFeeManager { + + function erc677token() public view returns(IBurnableMintableERC677Token) { + return IBurnableMintableERC677Token(addressStorage[keccak256(abi.encodePacked("erc677token"))]); + } + + function onAffirmationFeeDistribution(address _rewardAddress, uint256 _fee) internal { + if (!_rewardAddress.send(_fee)) { + (new Sacrifice).value(_fee)(_rewardAddress); + } + } + + function onSignatureFeeDistribution(address _rewardAddress, uint256 _fee) internal { + erc677token().mint(_rewardAddress, _fee); + } +} diff --git a/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol index 3b52049a2..ee31180e4 100644 --- a/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol +++ b/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol @@ -6,9 +6,10 @@ import "../../ERC677Receiver.sol"; import "../BasicForeignBridge.sol"; import "openzeppelin-solidity/contracts/token/ERC20/ERC20Basic.sol"; import "../ERC677Bridge.sol"; +import "../RewardableBridge.sol"; -contract ForeignBridgeNativeToErc is ERC677Receiver, BasicBridge, BasicForeignBridge, ERC677Bridge { +contract ForeignBridgeNativeToErc is ERC677Receiver, BasicBridge, BasicForeignBridge, ERC677Bridge, RewardableBridge { /// Event created on money withdraw. event UserRequestForAffirmation(address recipient, uint256 value); @@ -25,6 +26,75 @@ contract ForeignBridgeNativeToErc is ERC677Receiver, BasicBridge, BasicForeignBr uint256 _homeMaxPerTx, address _owner ) public returns(bool) { + _initialize( + _validatorContract, + _erc677token, + _dailyLimit, + _maxPerTx, + _minPerTx, + _foreignGasPrice, + _requiredBlockConfirmations, + _homeDailyLimit, + _homeMaxPerTx, + _owner + ); + setInitialize(true); + return isInitialized(); + } + + function rewardableInitialize( + address _validatorContract, + address _erc677token, + uint256 _dailyLimit, + uint256 _maxPerTx, + uint256 _minPerTx, + uint256 _foreignGasPrice, + uint256 _requiredBlockConfirmations, + uint256 _homeDailyLimit, + uint256 _homeMaxPerTx, + address _owner, + address _feeManager, + uint256 _fee + ) public returns(bool) { + _initialize( + _validatorContract, + _erc677token, + _dailyLimit, + _maxPerTx, + _minPerTx, + _foreignGasPrice, + _requiredBlockConfirmations, + _homeDailyLimit, + _homeMaxPerTx, + _owner + ); + require(isContract(_feeManager)); + addressStorage[keccak256(abi.encodePacked("feeManagerContract"))] = _feeManager; + require(_feeManager.delegatecall(abi.encodeWithSignature("setFee(uint256)", _fee))); + setInitialize(true); + return isInitialized(); + } + + function getBridgeMode() public pure returns(bytes4 _data) { + return bytes4(keccak256(abi.encodePacked("native-to-erc-core"))); + } + + function claimTokensFromErc677(address _token, address _to) external onlyIfOwnerOfProxy { + erc677token().claimTokens(_token, _to); + } + + function _initialize( + address _validatorContract, + address _erc677token, + uint256 _dailyLimit, + uint256 _maxPerTx, + uint256 _minPerTx, + uint256 _foreignGasPrice, + uint256 _requiredBlockConfirmations, + uint256 _homeDailyLimit, + uint256 _homeMaxPerTx, + address _owner + ) internal { require(!isInitialized()); require(_validatorContract != address(0) && isContract(_validatorContract)); require(_minPerTx > 0 && _maxPerTx > _minPerTx && _dailyLimit > _maxPerTx); @@ -42,21 +112,18 @@ contract ForeignBridgeNativeToErc is ERC677Receiver, BasicBridge, BasicForeignBr uintStorage[keccak256(abi.encodePacked("executionDailyLimit"))] = _homeDailyLimit; uintStorage[keccak256(abi.encodePacked("executionMaxPerTx"))] = _homeMaxPerTx; setOwner(_owner); - setInitialize(true); - return isInitialized(); - } - - function getBridgeMode() public pure returns(bytes4 _data) { - return bytes4(keccak256(abi.encodePacked("native-to-erc-core"))); - } - - function claimTokensFromErc677(address _token, address _to) external onlyIfOwnerOfProxy { - erc677token().claimTokens(_token, _to); } - function onExecuteMessage(address _recipient, uint256 _amount) internal returns(bool){ + function onExecuteMessage(address _recipient, uint256 _amount) internal returns(bool) { setTotalExecutedPerDay(getCurrentDay(), totalExecutedPerDay(getCurrentDay()).add(_amount)); - return erc677token().mint(_recipient, _amount); + uint256 valueToMint = _amount; + address feeManager = feeManagerContract(); + if (feeManager != address(0)) { + uint256 fee = calculateFee(valueToMint, false, feeManager); + distributeFeeFromSignatures(fee, feeManager); + valueToMint = valueToMint.sub(fee); + } + return erc677token().mint(_recipient, valueToMint); } function fireEventOnTokenTransfer(address _from, uint256 _value) internal { diff --git a/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol index e561c4c4f..811e48365 100644 --- a/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol +++ b/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol @@ -4,14 +4,19 @@ import "../../libraries/Message.sol"; import "../BasicBridge.sol"; import "../../upgradeability/EternalStorage.sol"; import "../BasicHomeBridge.sol"; +import "../RewardableBridge.sol"; +import "../Sacrifice.sol"; -contract Sacrifice { - constructor(address _recipient) public payable { - selfdestruct(_recipient); - } -} -contract HomeBridgeNativeToErc is EternalStorage, BasicBridge, BasicHomeBridge { +contract HomeBridgeNativeToErc is EternalStorage, BasicBridge, BasicHomeBridge, RewardableBridge { + + function () public payable { + require(msg.value > 0); + require(msg.data.length == 0); + require(withinLimit(msg.value)); + setTotalSpentPerDay(getCurrentDay(), totalSpentPerDay(getCurrentDay()).add(msg.value)); + emit UserRequestForSignature(msg.sender, msg.value); + } function initialize ( address _validatorContract, @@ -23,8 +28,70 @@ contract HomeBridgeNativeToErc is EternalStorage, BasicBridge, BasicHomeBridge { uint256 _foreignDailyLimit, uint256 _foreignMaxPerTx, address _owner - ) public - returns(bool) + ) public returns(bool) + { + _initialize( + _validatorContract, + _dailyLimit, + _maxPerTx, + _minPerTx, + _homeGasPrice, + _requiredBlockConfirmations, + _foreignDailyLimit, + _foreignMaxPerTx, + _owner + ); + setInitialize(true); + return isInitialized(); + } + + function rewardableInitialize ( + address _validatorContract, + uint256 _dailyLimit, + uint256 _maxPerTx, + uint256 _minPerTx, + uint256 _homeGasPrice, + uint256 _requiredBlockConfirmations, + uint256 _foreignDailyLimit, + uint256 _foreignMaxPerTx, + address _owner, + address _feeManager, + uint256 _fee + ) public returns(bool) + { + _initialize( + _validatorContract, + _dailyLimit, + _maxPerTx, + _minPerTx, + _homeGasPrice, + _requiredBlockConfirmations, + _foreignDailyLimit, + _foreignMaxPerTx, + _owner + ); + require(isContract(_feeManager)); + addressStorage[keccak256(abi.encodePacked("feeManagerContract"))] = _feeManager; + require(_feeManager.delegatecall(abi.encodeWithSignature("setFee(uint256)", _fee))); + setInitialize(true); + return isInitialized(); + } + + function getBridgeMode() public pure returns(bytes4 _data) { + return bytes4(keccak256(abi.encodePacked("native-to-erc-core"))); + } + + function _initialize ( + address _validatorContract, + uint256 _dailyLimit, + uint256 _maxPerTx, + uint256 _minPerTx, + uint256 _homeGasPrice, + uint256 _requiredBlockConfirmations, + uint256 _foreignDailyLimit, + uint256 _foreignMaxPerTx, + address _owner + ) internal { require(!isInitialized()); require(_validatorContract != address(0) && isContract(_validatorContract)); @@ -43,26 +110,21 @@ contract HomeBridgeNativeToErc is EternalStorage, BasicBridge, BasicHomeBridge { uintStorage[keccak256(abi.encodePacked("executionDailyLimit"))] = _foreignDailyLimit; uintStorage[keccak256(abi.encodePacked("executionMaxPerTx"))] = _foreignMaxPerTx; setOwner(_owner); - setInitialize(true); - return isInitialized(); - } - - function () public payable { - require(msg.value > 0); - require(msg.data.length == 0); - require(withinLimit(msg.value)); - setTotalSpentPerDay(getCurrentDay(), totalSpentPerDay(getCurrentDay()).add(msg.value)); - emit UserRequestForSignature(msg.sender, msg.value); - } - - function getBridgeMode() public pure returns(bytes4 _data) { - return bytes4(keccak256(abi.encodePacked("native-to-erc-core"))); } function onExecuteAffirmation(address _recipient, uint256 _value) internal returns(bool) { setTotalExecutedPerDay(getCurrentDay(), totalExecutedPerDay(getCurrentDay()).add(_value)); - if (!_recipient.send(_value)) { - (new Sacrifice).value(_value)(_recipient); + uint256 valueToTransfer = _value; + + address feeManager = feeManagerContract(); + if (feeManager != address(0)) { + uint256 fee = calculateFee(valueToTransfer, false, feeManager); + distributeFeeFromAffirmation(fee, feeManager); + valueToTransfer = valueToTransfer.sub(fee); + } + + if (!_recipient.send(valueToTransfer)) { + (new Sacrifice).value(valueToTransfer)(_recipient); } return true; } From 112632af401fa1d6dd9c325749fcda8143673584 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 22 Jan 2019 10:50:30 -0300 Subject: [PATCH 068/187] Add tests for FeeManagerNativeToErc on Foreign bridge --- test/native_to_erc/foreign_bridge_test.js | 250 ++++++++++++++++++++++ 1 file changed, 250 insertions(+) diff --git a/test/native_to_erc/foreign_bridge_test.js b/test/native_to_erc/foreign_bridge_test.js index a71bbb9d4..747957925 100644 --- a/test/native_to_erc/foreign_bridge_test.js +++ b/test/native_to_erc/foreign_bridge_test.js @@ -2,6 +2,8 @@ const ForeignBridge = artifacts.require("ForeignBridgeNativeToErc.sol"); const ForeignBridgeV2 = artifacts.require("ForeignBridgeV2.sol"); const BridgeValidators = artifacts.require("BridgeValidators.sol"); const EternalStorageProxy = artifacts.require("EternalStorageProxy.sol"); +const FeeManagerNativeToErc = artifacts.require("FeeManagerNativeToErc.sol"); +const RewardableValidators = artifacts.require("RewardableValidators.sol"); const POA20 = artifacts.require("ERC677BridgeToken.sol"); const {ERROR_MSG, ZERO_ADDRESS, ERROR_MSG_OPCODE} = require('../setup'); @@ -510,4 +512,252 @@ contract('ForeignBridge', async (accounts) => { '150'.should.be.bignumber.equal(await tokenSecond.balanceOf(accounts[3])) }) }) + + describe('#rewardableInitialize', async() => { + let fee, foreignBridge, token, rewardableValidators + let validators = [accounts[1]] + let rewards = [accounts[2]] + let requiredSignatures = 1 + beforeEach(async () => { + token = await POA20.new("POA ERC20 Foundation", "POA20", 18) + rewardableValidators = await RewardableValidators.new() + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled + foreignBridge = await ForeignBridge.new() + fee = web3.toBigNumber(web3.toWei(0.001, "ether")) + }) + it('sets variables', async () => { + const feeManager = await FeeManagerNativeToErc.new() + ZERO_ADDRESS.should.be.equal(await foreignBridge.validatorContract()) + '0'.should.be.bignumber.equal(await foreignBridge.deployedAtBlock()) + '0'.should.be.bignumber.equal(await foreignBridge.dailyLimit()) + '0'.should.be.bignumber.equal(await foreignBridge.maxPerTx()) + false.should.be.equal(await foreignBridge.isInitialized()) + + await foreignBridge.rewardableInitialize(ZERO_ADDRESS, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, fee).should.be.rejectedWith(ERROR_MSG); + await foreignBridge.rewardableInitialize(rewardableValidators.address, ZERO_ADDRESS, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, fee).should.be.rejectedWith(ERROR_MSG); + await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, 0, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, fee).should.be.rejectedWith(ERROR_MSG); + await foreignBridge.rewardableInitialize(owner, token.address, oneEther, halfEther, minPerTx, requireBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, fee).should.be.rejectedWith(ERROR_MSG); + await foreignBridge.rewardableInitialize(rewardableValidators.address, owner, oneEther, halfEther, minPerTx, requireBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, fee).should.be.rejectedWith(ERROR_MSG); + await foreignBridge.rewardableInitialize(rewardableValidators.address, owner, oneEther, halfEther, minPerTx, requireBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, owner, ZERO_ADDRESS, fee).should.be.rejectedWith(ERROR_MSG); + await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, fee).should.be.fulfilled; + + true.should.be.equal(await foreignBridge.isInitialized()) + rewardableValidators.address.should.be.equal(await foreignBridge.validatorContract()); + (await foreignBridge.deployedAtBlock()).should.be.bignumber.above(0); + oneEther.should.be.bignumber.equal(await foreignBridge.dailyLimit()) + halfEther.should.be.bignumber.equal(await foreignBridge.maxPerTx()) + minPerTx.should.be.bignumber.equal(await foreignBridge.minPerTx()) + const bridgeMode = '0x92a8d7fe' // 4 bytes of keccak256('native-to-erc-core') + const mode = await foreignBridge.getBridgeMode(); + mode.should.be.equal(bridgeMode) + const [major, minor, patch] = await foreignBridge.getBridgeInterfacesVersion() + major.should.be.bignumber.gte(0) + minor.should.be.bignumber.gte(0) + patch.should.be.bignumber.gte(0) + + const feeManagerContract = await foreignBridge.feeManagerContract() + feeManagerContract.should.be.equals(feeManager.address) + const bridgeFee = await foreignBridge.getFee() + bridgeFee.should.be.bignumber.equal(fee) + }) + + it('can update fee contract', async () => { + const feeManager = await FeeManagerNativeToErc.new() + await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, fee).should.be.fulfilled; + + // Given + const newFeeManager = await FeeManagerNativeToErc.new() + + // When + await foreignBridge.setFeeManagerContract(newFeeManager.address, { from: owner }).should.be.fulfilled + + // Then + const feeManagerContract = await foreignBridge.feeManagerContract() + feeManagerContract.should.be.equals(newFeeManager.address) + }) + + it('can update fee', async () => { + const feeManager = await FeeManagerNativeToErc.new() + await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, fee).should.be.fulfilled; + + // Given + const newFee = web3.toBigNumber(web3.toWei(0.1, "ether")) + + // When + await foreignBridge.setFee(newFee, { from: owner }).should.be.fulfilled + + // Then + const bridgeFee = await foreignBridge.getFee() + bridgeFee.should.be.bignumber.equal(newFee) + }) + }) + + describe('#RewardableBridge_executeSignatures', async () => { + let feeManager, foreignBridge, token, rewardableValidators + beforeEach(async () => { + feeManager = await FeeManagerNativeToErc.new() + token = await POA20.new("POA ERC20 Foundation", "POA20", 18) + rewardableValidators = await RewardableValidators.new() + foreignBridge = await ForeignBridge.new() + }) + it('should distribute fee to validator', async () => { + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const value = halfEther + const finalUserValue = value.mul(web3.toBigNumber(1-fee)); + const feeAmount = value.mul(web3.toBigNumber(fee)) + + const validators = [accounts[1]] + const rewards = [accounts[2]] + const requiredSignatures = 1 + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled + await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, feeInWei).should.be.fulfilled; + await token.transferOwnership(foreignBridge.address); + + const recipientAccount = accounts[3]; + const balanceBefore = await token.balanceOf(recipientAccount) + const initialBalanceRewardAddress = await token.balanceOf(rewards[0]) + const totalSupplyBefore = await token.totalSupply() + const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; + const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); + const signature = await sign(validators[0], message) + const vrs = signatureToVRS(signature); + + const { logs } = await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.fulfilled + logs[0].event.should.be.equal("RelayedMessage") + logs[0].args.recipient.should.be.equal(recipientAccount) + logs[0].args.value.should.be.bignumber.equal(value) + logs[0].args.transactionHash.should.be.equal(transactionHash); + + const balanceAfter = await token.balanceOf(recipientAccount); + const totalSupplyAfter = await token.totalSupply(); + balanceAfter.should.be.bignumber.equal(balanceBefore.add(finalUserValue)) + totalSupplyAfter.should.be.bignumber.equal(totalSupplyBefore.add(value)) + + const updatedBalanceRewardAddress = await token.balanceOf(rewards[0]) + updatedBalanceRewardAddress.should.be.bignumber.equal(initialBalanceRewardAddress.add(feeAmount)) + }) + it('should distribute fee to 3 validators', async () => { + // Given + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feePerValidator = web3.toBigNumber(166666666666666) + const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) + const value = halfEther + const finalUserValue = value.mul(web3.toBigNumber(1-fee)); + + const validators = [accounts[1], accounts[2], accounts[3]] + const rewards = [accounts[4], accounts[5], accounts[6]] + const requiredSignatures = 3 + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled + await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, feeInWei).should.be.fulfilled; + await token.transferOwnership(foreignBridge.address); + + const recipientAccount = accounts[7]; + const balanceBefore = await token.balanceOf(recipientAccount) + const totalSupplyBefore = await token.totalSupply() + + const initialBalanceRewardAddress1 = await token.balanceOf(rewards[0]) + const initialBalanceRewardAddress2 = await token.balanceOf(rewards[1]) + const initialBalanceRewardAddress3 = await token.balanceOf(rewards[2]) + + const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; + const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); + const signature1 = await sign(validators[0], message) + const signature2 = await sign(validators[1], message) + const signature3 = await sign(validators[2], message) + const vrs = signatureToVRS(signature1); + const vrs2 = signatureToVRS(signature2); + const vrs3 = signatureToVRS(signature3); + + // When + const { logs } = await foreignBridge.executeSignatures([vrs.v, vrs2.v, vrs3.v], [vrs.r, vrs2.r, vrs3.r], [vrs.s, vrs2.s, vrs3.s], message).should.be.fulfilled + + // Then + logs[0].event.should.be.equal("RelayedMessage") + logs[0].args.recipient.should.be.equal(recipientAccount) + logs[0].args.value.should.be.bignumber.equal(value) + logs[0].args.transactionHash.should.be.equal(transactionHash); + + const balanceAfter = await token.balanceOf(recipientAccount); + const totalSupplyAfter = await token.totalSupply(); + balanceAfter.should.be.bignumber.equal(balanceBefore.add(finalUserValue)) + totalSupplyAfter.should.be.bignumber.equal(totalSupplyBefore.add(value)) + + const updatedBalanceRewardAddress1 = await token.balanceOf(rewards[0]) + const updatedBalanceRewardAddress2 = await token.balanceOf(rewards[1]) + const updatedBalanceRewardAddress3 = await token.balanceOf(rewards[2]) + + expect( + updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidator)) + || updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidatorPlusDiff))).to.equal(true) + expect( + updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidator)) + || updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidatorPlusDiff))).to.equal(true) + expect( + updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidator)) + || updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidatorPlusDiff))).to.equal(true) + }) + it('should distribute fee to 5 validators', async () => { + // Given + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const value = halfEther + const feeAmount = value.mul(web3.toBigNumber(fee)) + const feePerValidator = feeAmount.div(web3.toBigNumber(5)) + const finalUserValue = value.mul(web3.toBigNumber(1-fee)); + + const validators = [accounts[0], accounts[1], accounts[2], accounts[3], accounts[4]] + const rewards = [accounts[5], accounts[6], accounts[7], accounts[8], accounts[9]] + const requiredSignatures = 3 + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled + await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, feeInWei).should.be.fulfilled; + await token.transferOwnership(foreignBridge.address); + + const recipientAccount = accounts[0]; + const balanceBefore = await token.balanceOf(recipientAccount) + const totalSupplyBefore = await token.totalSupply() + + const initialBalanceRewardAddress1 = await token.balanceOf(rewards[0]) + const initialBalanceRewardAddress2 = await token.balanceOf(rewards[1]) + const initialBalanceRewardAddress3 = await token.balanceOf(rewards[2]) + const initialBalanceRewardAddress4 = await token.balanceOf(rewards[3]) + const initialBalanceRewardAddress5 = await token.balanceOf(rewards[4]) + + const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; + const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); + const signature1 = await sign(validators[0], message) + const signature2 = await sign(validators[1], message) + const signature3 = await sign(validators[2], message) + const vrs = signatureToVRS(signature1); + const vrs2 = signatureToVRS(signature2); + const vrs3 = signatureToVRS(signature3); + + // When + const { logs } = await foreignBridge.executeSignatures([vrs.v, vrs2.v, vrs3.v], [vrs.r, vrs2.r, vrs3.r], [vrs.s, vrs2.s, vrs3.s], message).should.be.fulfilled + + // Then + logs[0].event.should.be.equal("RelayedMessage") + logs[0].args.recipient.should.be.equal(recipientAccount) + logs[0].args.value.should.be.bignumber.equal(value) + logs[0].args.transactionHash.should.be.equal(transactionHash); + + const balanceAfter = await token.balanceOf(recipientAccount); + const totalSupplyAfter = await token.totalSupply(); + balanceAfter.should.be.bignumber.equal(balanceBefore.add(finalUserValue)) + totalSupplyAfter.should.be.bignumber.equal(totalSupplyBefore.add(value)) + + const updatedBalanceRewardAddress1 = await token.balanceOf(rewards[0]) + const updatedBalanceRewardAddress2 = await token.balanceOf(rewards[1]) + const updatedBalanceRewardAddress3 = await token.balanceOf(rewards[2]) + const updatedBalanceRewardAddress4 = await token.balanceOf(rewards[3]) + const updatedBalanceRewardAddress5 = await token.balanceOf(rewards[4]) + + updatedBalanceRewardAddress1.should.be.bignumber.equal(initialBalanceRewardAddress1.add(feePerValidator)) + updatedBalanceRewardAddress2.should.be.bignumber.equal(initialBalanceRewardAddress2.add(feePerValidator)) + updatedBalanceRewardAddress3.should.be.bignumber.equal(initialBalanceRewardAddress3.add(feePerValidator)) + updatedBalanceRewardAddress4.should.be.bignumber.equal(initialBalanceRewardAddress4.add(feePerValidator)) + updatedBalanceRewardAddress5.should.be.bignumber.equal(initialBalanceRewardAddress5.add(feePerValidator)) + }) + }) }) From 348b168c9ad6683fadba1c7f7b8f6a3f6a0a59a8 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 22 Jan 2019 16:56:21 -0300 Subject: [PATCH 069/187] Add tests for FeeManagerNativeToErc on Home bridge --- test/native_to_erc/home_bridge_test.js | 277 +++++++++++++++++++++++++ 1 file changed, 277 insertions(+) diff --git a/test/native_to_erc/home_bridge_test.js b/test/native_to_erc/home_bridge_test.js index 3980b6c50..2a798aff8 100644 --- a/test/native_to_erc/home_bridge_test.js +++ b/test/native_to_erc/home_bridge_test.js @@ -3,6 +3,8 @@ const HomeBridge = artifacts.require("HomeBridgeNativeToErc.sol"); const EternalStorageProxy = artifacts.require("EternalStorageProxy.sol"); const BridgeValidators = artifacts.require("BridgeValidators.sol"); const RevertFallback = artifacts.require("RevertFallback.sol"); +const FeeManagerNativeToErc = artifacts.require("FeeManagerNativeToErc.sol"); +const RewardableValidators = artifacts.require("RewardableValidators.sol"); const {ERROR_MSG, ZERO_ADDRESS} = require('../setup'); const {createMessage, sign, signatureToVRS} = require('../helpers/helpers'); const minPerTx = web3.toBigNumber(web3.toWei(0.01, "ether")); @@ -554,4 +556,279 @@ contract('HomeBridge', async (accounts) => { '104'.should.be.bignumber.equal(requiredMessageLength) }) }) + + describe('#rewardableInitialize', async() => { + let fee, homeBridge, rewardableValidators + let validators = [accounts[1]] + let rewards = [accounts[2]] + let requiredSignatures = 1 + beforeEach(async () => { + rewardableValidators = await RewardableValidators.new() + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled + homeBridge = await HomeBridge.new() + fee = web3.toBigNumber(web3.toWei(0.001, "ether")) + }) + it('sets variables', async () => { + const feeManager = await FeeManagerNativeToErc.new() + ZERO_ADDRESS.should.be.equal(await homeBridge.validatorContract()) + '0'.should.be.bignumber.equal(await homeBridge.deployedAtBlock()) + '0'.should.be.bignumber.equal(await homeBridge.dailyLimit()) + '0'.should.be.bignumber.equal(await homeBridge.maxPerTx()) + false.should.be.equal(await homeBridge.isInitialized()) + + await homeBridge.rewardableInitialize(ZERO_ADDRESS, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.rejectedWith(ERROR_MSG); + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, 0, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.rejectedWith(ERROR_MSG); + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, 0, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.rejectedWith(ERROR_MSG); + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, ZERO_ADDRESS, fee).should.be.rejectedWith(ERROR_MSG); + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.fulfilled; + + true.should.be.equal(await homeBridge.isInitialized()) + rewardableValidators.address.should.be.equal(await homeBridge.validatorContract()); + (await homeBridge.deployedAtBlock()).should.be.bignumber.above(0); + oneEther.should.be.bignumber.equal(await homeBridge.dailyLimit()) + halfEther.should.be.bignumber.equal(await homeBridge.maxPerTx()) + minPerTx.should.be.bignumber.equal(await homeBridge.minPerTx()) + const bridgeMode = '0x92a8d7fe' // 4 bytes of keccak256('native-to-erc-core') + const mode = await homeBridge.getBridgeMode(); + mode.should.be.equal(bridgeMode) + const [major, minor, patch] = await homeBridge.getBridgeInterfacesVersion() + major.should.be.bignumber.gte(0) + minor.should.be.bignumber.gte(0) + patch.should.be.bignumber.gte(0) + + const feeManagerContract = await homeBridge.feeManagerContract() + feeManagerContract.should.be.equals(feeManager.address) + const bridgeFee = await homeBridge.getFee() + bridgeFee.should.be.bignumber.equal(fee) + }) + + it('can update fee contract', async () => { + const feeManager = await FeeManagerNativeToErc.new() + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.fulfilled; + + // Given + const newFeeManager = await FeeManagerNativeToErc.new() + + // When + await homeBridge.setFeeManagerContract(newFeeManager.address, { from: owner }).should.be.fulfilled + + // Then + const feeManagerContract = await homeBridge.feeManagerContract() + feeManagerContract.should.be.equals(newFeeManager.address) + }) + + it('can update fee', async () => { + const feeManager = await FeeManagerNativeToErc.new() + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.fulfilled; + + // Given + const newFee = web3.toBigNumber(web3.toWei(0.1, "ether")) + + // When + await homeBridge.setFee(newFee, { from: owner }).should.be.fulfilled + + // Then + const bridgeFee = await homeBridge.getFee() + bridgeFee.should.be.bignumber.equal(newFee) + }) + }) + + describe('#feeManager_ExecuteAffirmation', async () => { + it('should distribute fee to validator', async () => { + // Initialize + const owner = accounts[9] + const validators = [accounts[1]] + const rewards = [accounts[2]] + const requiredSignatures = 1 + const rewardableValidators = await RewardableValidators.new() + const homeBridge = await HomeBridge.new(); + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + const feeManager = await FeeManagerNativeToErc.new() + + // Given + // 0.1% fee + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const value = halfEther; + const finalUserValue = value.mul(web3.toBigNumber(1-fee)); + const feeAmount = value.mul(web3.toBigNumber(fee)) + + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei).should.be.fulfilled; + await homeBridge.sendTransaction({ + from: accounts[0], + value: halfEther + }).should.be.fulfilled + + + const recipient = accounts[5]; + const balanceBefore = await web3.eth.getBalance(recipient) + const rewardAddressBalanceBefore = await web3.eth.getBalance(rewards[0]) + const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + + // When + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled + + // Then + logs[0].event.should.be.equal("SignedForAffirmation"); + logs[0].args.should.be.deep.equal({ + signer: validators[0], + transactionHash + }); + logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].args.should.be.deep.equal({ + recipient, + value, + transactionHash + }) + const balanceAfter = await web3.eth.getBalance(recipient) + const rewardAddressBalanceAfter = await web3.eth.getBalance(rewards[0]) + + rewardAddressBalanceAfter.should.be.bignumber.equal(rewardAddressBalanceBefore.add(feeAmount)) + balanceAfter.should.be.bignumber.equal(balanceBefore.add(finalUserValue)) + }) + it('should distribute fee to 3 validators', async () => { + // Given + const owner = accounts[9] + const validators = [accounts[1], accounts[2], accounts[3]] + const rewards = [accounts[4], accounts[5], accounts[6]] + const requiredSignatures = 2 + const rewardableValidators = await RewardableValidators.new() + + const value = halfEther; + // 0.1% fee + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feePerValidator = web3.toBigNumber(166666666666666) + const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) + const finalUserValue = value.mul(web3.toBigNumber(1-fee)); + + const homeBridge = await HomeBridge.new() + const feeManager = await FeeManagerNativeToErc.new() + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei).should.be.fulfilled; + await homeBridge.sendTransaction({ + from: accounts[0], + value: halfEther + }).should.be.fulfilled + + const recipient = accounts[8]; + const balanceBefore = await web3.eth.getBalance(recipient) + + const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const initialBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const initialBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + + const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + + // When + const { logs: logsValidator1 } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[1]}).should.be.fulfilled + + // Then + logsValidator1.length.should.be.equals(1) + + logs[0].event.should.be.equal("SignedForAffirmation"); + logs[0].args.should.be.deep.equal({ + signer: validators[1], + transactionHash + }); + logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].args.should.be.deep.equal({ + recipient, + value, + transactionHash + }) + const balanceAfter = await web3.eth.getBalance(recipient) + balanceAfter.should.be.bignumber.equal(balanceBefore.add(finalUserValue)) + + const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + + expect( + updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidator)) + || updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidatorPlusDiff))).to.equal(true) + expect( + updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidator)) + || updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidatorPlusDiff))).to.equal(true) + expect( + updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidator)) + || updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidatorPlusDiff))).to.equal(true) + + const homeBridgeBalance = await web3.eth.getBalance(homeBridge.address) + homeBridgeBalance.should.be.bignumber.equal('0') + }) + it('should distribute fee to 5 validators', async () => { + // Given + const owner = accounts[0] + const validators = [accounts[0], accounts[1], accounts[2], accounts[3], accounts[4]] + const rewards = [accounts[5], accounts[6], accounts[7], accounts[8], accounts[9]] + const requiredSignatures = 5 + + const value = halfEther; + // 0.1% fee + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeAmount = value.mul(web3.toBigNumber(fee)) + const feePerValidator = feeAmount.div(web3.toBigNumber(5)) + + const rewardableValidators = await RewardableValidators.new() + const homeBridge = await HomeBridge.new() + const feeManager = await FeeManagerNativeToErc.new() + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei).should.be.fulfilled; + await homeBridge.sendTransaction({ + from: accounts[0], + value: halfEther + }).should.be.fulfilled + + const recipient = "0xf4bef13f9f4f2b203faf0c3cbbaabe1afe056955"; + const balanceBefore = await web3.eth.getBalance(recipient) + + const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const initialBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const initialBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + const initialBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) + const initialBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) + + + const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + + // When + const { logs: logsValidator1 } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[1]}).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[2]}).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[3]}).should.be.fulfilled + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[4]}).should.be.fulfilled + + // Then + logsValidator1.length.should.be.equals(1) + + logs[0].event.should.be.equal("SignedForAffirmation"); + logs[0].args.should.be.deep.equal({ + signer: validators[4], + transactionHash + }); + logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].args.should.be.deep.equal({ + recipient, + value, + transactionHash + }) + const balanceAfter = await web3.eth.getBalance(recipient) + balanceAfter.should.be.bignumber.equal(balanceBefore.add(value.sub(feeAmount))) + + const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + const updatedBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) + const updatedBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) + + updatedBalanceRewardAddress1.should.be.bignumber.equal(initialBalanceRewardAddress1.add(feePerValidator)) + updatedBalanceRewardAddress2.should.be.bignumber.equal(initialBalanceRewardAddress2.add(feePerValidator)) + updatedBalanceRewardAddress3.should.be.bignumber.equal(initialBalanceRewardAddress3.add(feePerValidator)) + updatedBalanceRewardAddress4.should.be.bignumber.equal(initialBalanceRewardAddress4.add(feePerValidator)) + updatedBalanceRewardAddress5.should.be.bignumber.equal(initialBalanceRewardAddress5.add(feePerValidator)) + }) + }) }) From 8d995fb72b040ccbf76d4e11b049ab20b4b21a09 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 23 Jan 2019 10:52:36 -0300 Subject: [PATCH 070/187] Fix rewardableInitialize on NativeToErc contracts --- .../native_to_erc20/ForeignBridgeNativeToErc.sol | 2 +- .../native_to_erc20/HomeBridgeNativeToErc.sol | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol index ee31180e4..278b5f5d4 100644 --- a/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol +++ b/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol @@ -70,7 +70,7 @@ contract ForeignBridgeNativeToErc is ERC677Receiver, BasicBridge, BasicForeignBr ); require(isContract(_feeManager)); addressStorage[keccak256(abi.encodePacked("feeManagerContract"))] = _feeManager; - require(_feeManager.delegatecall(abi.encodeWithSignature("setFee(uint256)", _fee))); + _setFee(_feeManager, _fee); setInitialize(true); return isInitialized(); } diff --git a/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol index 811e48365..0a3486dba 100644 --- a/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol +++ b/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol @@ -72,7 +72,7 @@ contract HomeBridgeNativeToErc is EternalStorage, BasicBridge, BasicHomeBridge, ); require(isContract(_feeManager)); addressStorage[keccak256(abi.encodePacked("feeManagerContract"))] = _feeManager; - require(_feeManager.delegatecall(abi.encodeWithSignature("setFee(uint256)", _fee))); + _setFee(_feeManager, _fee); setInitialize(true); return isInitialized(); } From 41216b5e3c2b5e0beb9ddc937758e901677ef5f4 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 23 Jan 2019 13:41:02 -0300 Subject: [PATCH 071/187] Add rewardable bridge options on deploy script for native-to-erc mode --- deploy/README.md | 17 +++ deploy/src/loadEnv.js | 11 +- deploy/src/native_to_erc/foreign.js | 168 ++++++++++++++++++++++------ deploy/src/native_to_erc/home.js | 152 ++++++++++++++++++++----- 4 files changed, 282 insertions(+), 66 deletions(-) diff --git a/deploy/README.md b/deploy/README.md index d792d2ad8..dad4fcce3 100644 --- a/deploy/README.md +++ b/deploy/README.md @@ -124,6 +124,23 @@ REQUIRED_NUMBER_OF_VALIDATORS=1 # correctly to the Foreign network. VALIDATORS=0x 0x 0x +# The flag defining whether to use RewardableValidators contract and set a fee manager contract on Home network +HOME_REWARDABLE=false +# The flag defining whether to use RewardableValidators contract and set a fee manager contract on Foreign network +FOREIGN_REWARDABLE=false +# List validators accounts were rewards should be transferred separated by space without quotes +# Makes sense only when HOME_REWARDABLE=true or FOREIGN_REWARDABLE=true +VALIDATORS_REWARD_ACCOUNTS=0x 0x 0x + +# Fee to be charged for each transfer on Home network +# Makes sense only when HOME_REWARDABLE=true +# e.g. 0.1% fee +HOME_TRANSACTIONS_FEE=0.001 +# Fee to be charged for each transfer on Foreign network +# Makes sense only when FOREIGN_REWARDABLE=true +# e.g. 0.1% fee +FOREIGN_TRANSACTIONS_FEE=0.001 + # The flag defining whether to use ERC677BridgeTokenRewardable contract instead of # ERC677BridgeToken. DEPLOY_REWARDABLE_TOKEN=false diff --git a/deploy/src/loadEnv.js b/deploy/src/loadEnv.js index 71764ca75..12a36fbb4 100644 --- a/deploy/src/loadEnv.js +++ b/deploy/src/loadEnv.js @@ -36,7 +36,8 @@ const { HOME_REWARDABLE, FOREIGN_REWARDABLE, VALIDATORS, - VALIDATORS_REWARD_ACCOUNTS + VALIDATORS_REWARD_ACCOUNTS, + DEPLOY_REWARDABLE_TOKEN } = process.env if (!validBridgeModes.includes(BRIDGE_MODE)) { @@ -78,9 +79,15 @@ if (BRIDGE_MODE === 'NATIVE_TO_ERC') { FOREIGN_MAX_AMOUNT_PER_TX: bigNumValidator(), FOREIGN_MIN_AMOUNT_PER_TX: bigNumValidator(), DEPLOY_REWARDABLE_TOKEN: envalid.bool(), - DPOS_VALIDATOR_SET_ADDRESS: addressValidator(), BLOCK_REWARD_ADDRESS: addressValidator() } + + if (DEPLOY_REWARDABLE_TOKEN === 'true') { + validations = { + ...validations, + DPOS_VALIDATOR_SET_ADDRESS: addressValidator() + } + } } if (BRIDGE_MODE === 'ERC_TO_ERC') { validations = { diff --git a/deploy/src/native_to_erc/foreign.js b/deploy/src/native_to_erc/foreign.js index 0b70c62bf..357f113f1 100644 --- a/deploy/src/native_to_erc/foreign.js +++ b/deploy/src/native_to_erc/foreign.js @@ -2,16 +2,24 @@ const assert = require('assert') const Web3Utils = require('web3-utils') const env = require('../loadEnv') -const { deployContract, privateKeyToAddress, sendRawTxForeign } = require('../deploymentUtils') +const { + deployContract, + privateKeyToAddress, + sendRawTxForeign, + logValidatorsAndRewardAccounts +} = require('../deploymentUtils') const { web3Foreign, deploymentPrivateKey, FOREIGN_RPC_URL } = require('../web3') const ERC677BridgeToken = require('../../../build/contracts/ERC677BridgeToken.json') const ERC677BridgeTokenRewardable = require('../../../build/contracts/ERC677BridgeTokenRewardable.json') const EternalStorageProxy = require('../../../build/contracts/EternalStorageProxy.json') const BridgeValidators = require('../../../build/contracts/BridgeValidators.json') +const RewardableValidators = require('../../../build/contracts/RewardableValidators.json') +const FeeManagerNativeToErc = require('../../../build/contracts/FeeManagerNativeToErc.json') const ForeignBridge = require('../../../build/contracts/ForeignBridgeNativeToErc.json') const VALIDATORS = env.VALIDATORS.split(' ') +const VALIDATORS_REWARD_ACCOUNTS = env.VALIDATORS_REWARD_ACCOUNTS.split(' ') const { DEPLOYMENT_ACCOUNT_PRIVATE_KEY, @@ -31,11 +39,15 @@ const { HOME_MAX_AMOUNT_PER_TX, DEPLOY_REWARDABLE_TOKEN, BLOCK_REWARD_ADDRESS, - DPOS_VALIDATOR_SET_ADDRESS + DPOS_VALIDATOR_SET_ADDRESS, + FOREIGN_REWARDABLE, + FOREIGN_TRANSACTIONS_FEE } = env const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVATE_KEY) +const isRewardableBridge = FOREIGN_REWARDABLE === 'true' + async function deployForeign() { let foreignNonce = await web3Foreign.eth.getTransactionCount(DEPLOYMENT_ACCOUNT_ADDRESS) console.log('========================================') @@ -61,7 +73,8 @@ async function deployForeign() { console.log('[Foreign] BridgeValidators Storage: ', storageValidatorsForeign.options.address) console.log('\ndeploying implementation for foreign validators') - const bridgeValidatorsForeign = await deployContract(BridgeValidators, [], { + const bridgeValidatorsContract = isRewardableBridge ? RewardableValidators : BridgeValidators + const bridgeValidatorsForeign = await deployContract(bridgeValidatorsContract, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, network: 'foreign', nonce: foreignNonce @@ -91,13 +104,32 @@ async function deployForeign() { foreignNonce++ console.log('\ninitializing Foreign Bridge Validators with following parameters:\n') - console.log( - `REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, VALIDATORS: ${VALIDATORS}` - ) bridgeValidatorsForeign.options.address = storageValidatorsForeign.options.address - const initializeForeignData = await bridgeValidatorsForeign.methods - .initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, FOREIGN_VALIDATORS_OWNER) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + + let initializeForeignData + + if (isRewardableBridge) { + console.log( + `REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, FOREIGN_VALIDATORS_OWNER: ${FOREIGN_VALIDATORS_OWNER}` + ) + logValidatorsAndRewardAccounts(VALIDATORS, VALIDATORS_REWARD_ACCOUNTS) + initializeForeignData = await bridgeValidatorsForeign.methods + .initialize( + REQUIRED_NUMBER_OF_VALIDATORS, + VALIDATORS, + VALIDATORS_REWARD_ACCOUNTS, + FOREIGN_VALIDATORS_OWNER + ) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + } else { + console.log( + `REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, VALIDATORS: ${VALIDATORS}, FOREIGN_VALIDATORS_OWNER: ${FOREIGN_VALIDATORS_OWNER}` + ) + initializeForeignData = await bridgeValidatorsForeign.methods + .initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, FOREIGN_VALIDATORS_OWNER) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + } + const txInitializeForeign = await sendRawTxForeign({ data: initializeForeignData, nonce: foreignNonce, @@ -165,33 +197,93 @@ async function deployForeign() { ) foreignNonce++ - console.log('\ninitializing Foreign Bridge with following parameters:\n') - console.log(`Foreign Validators: ${storageValidatorsForeign.options.address}, + let initializeFBridgeData + foreignBridgeImplementation.options.address = foreignBridgeStorage.options.address + + if (isRewardableBridge) { + console.log('\ndeploying implementation for fee manager') + const feeManager = await deployContract(FeeManagerNativeToErc, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + network: 'foreign', + nonce: foreignNonce + }) + console.log('[Foreign] feeManager Implementation: ', feeManager.options.address) + foreignNonce++ + + const feeInWei = Web3Utils.toWei(FOREIGN_TRANSACTIONS_FEE.toString(), 'ether') + + console.log('\ninitializing Foreign Bridge with fee contract:\n') + console.log(`Foreign Validators: ${storageValidatorsForeign.options.address}, + FOREIGN_DAILY_LIMIT : ${FOREIGN_DAILY_LIMIT} which is ${Web3Utils.fromWei( + FOREIGN_DAILY_LIMIT + )} in eth, + FOREIGN_MAX_AMOUNT_PER_TX: ${FOREIGN_MAX_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( + FOREIGN_MAX_AMOUNT_PER_TX + )} in eth, + FOREIGN_MIN_AMOUNT_PER_TX: ${FOREIGN_MIN_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( + FOREIGN_MIN_AMOUNT_PER_TX + )} in eth, + FOREIGN_GAS_PRICE: ${FOREIGN_GAS_PRICE}, FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS : ${FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS}, + HOME_DAILY_LIMIT: ${HOME_DAILY_LIMIT} which is ${Web3Utils.fromWei(HOME_DAILY_LIMIT)} in eth, + HOME_MAX_AMOUNT_PER_TX: ${HOME_MAX_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( + HOME_MAX_AMOUNT_PER_TX + )} in eth, + FOREIGN_BRIDGE_OWNER: ${FOREIGN_BRIDGE_OWNER}, + Fee Manager: ${feeManager.options.address}, + Fee: ${feeInWei} which is ${FOREIGN_TRANSACTIONS_FEE * 100}%`) + + initializeFBridgeData = await foreignBridgeImplementation.methods + .rewardableInitialize( + storageValidatorsForeign.options.address, + erc677bridgeToken.options.address, + FOREIGN_DAILY_LIMIT, + FOREIGN_MAX_AMOUNT_PER_TX, + FOREIGN_MIN_AMOUNT_PER_TX, + FOREIGN_GAS_PRICE, + FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS, + HOME_DAILY_LIMIT, + HOME_MAX_AMOUNT_PER_TX, + FOREIGN_BRIDGE_OWNER, + feeManager.options.address, + feeInWei + ) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + } else { + console.log('\ninitializing Foreign Bridge with following parameters:\n') + console.log(`Foreign Validators: ${storageValidatorsForeign.options.address}, FOREIGN_DAILY_LIMIT : ${FOREIGN_DAILY_LIMIT} which is ${Web3Utils.fromWei( - FOREIGN_DAILY_LIMIT - )} in eth, + FOREIGN_DAILY_LIMIT + )} in eth, FOREIGN_MAX_AMOUNT_PER_TX: ${FOREIGN_MAX_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( - FOREIGN_MAX_AMOUNT_PER_TX - )} in eth, + FOREIGN_MAX_AMOUNT_PER_TX + )} in eth, FOREIGN_MIN_AMOUNT_PER_TX: ${FOREIGN_MIN_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( - FOREIGN_MIN_AMOUNT_PER_TX - )} in eth + FOREIGN_MIN_AMOUNT_PER_TX + )} in eth, + FOREIGN_GAS_PRICE: ${FOREIGN_GAS_PRICE}, FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS : ${FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS}, + HOME_DAILY_LIMIT: ${HOME_DAILY_LIMIT} which is ${Web3Utils.fromWei(HOME_DAILY_LIMIT)} in eth, + HOME_MAX_AMOUNT_PER_TX: ${HOME_MAX_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( + HOME_MAX_AMOUNT_PER_TX + )} in eth, + FOREIGN_BRIDGE_OWNER: ${FOREIGN_BRIDGE_OWNER} `) - foreignBridgeImplementation.options.address = foreignBridgeStorage.options.address - const initializeFBridgeData = await foreignBridgeImplementation.methods - .initialize( - storageValidatorsForeign.options.address, - erc677bridgeToken.options.address, - FOREIGN_DAILY_LIMIT, - FOREIGN_MAX_AMOUNT_PER_TX, - FOREIGN_MIN_AMOUNT_PER_TX, - FOREIGN_GAS_PRICE, - FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS, - HOME_DAILY_LIMIT, - HOME_MAX_AMOUNT_PER_TX, - FOREIGN_BRIDGE_OWNER - ) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + + initializeFBridgeData = await foreignBridgeImplementation.methods + .initialize( + storageValidatorsForeign.options.address, + erc677bridgeToken.options.address, + FOREIGN_DAILY_LIMIT, + FOREIGN_MAX_AMOUNT_PER_TX, + FOREIGN_MIN_AMOUNT_PER_TX, + FOREIGN_GAS_PRICE, + FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS, + HOME_DAILY_LIMIT, + HOME_MAX_AMOUNT_PER_TX, + FOREIGN_BRIDGE_OWNER + ) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + } + const txInitializeBridge = await sendRawTxForeign({ data: initializeFBridgeData, nonce: foreignNonce, @@ -228,7 +320,11 @@ async function deployForeign() { privateKey: deploymentPrivateKey, url: FOREIGN_RPC_URL }) - assert.equal(Web3Utils.hexToNumber(setBlockRewardContract.status), 1, 'Transaction Failed') + assert.strictEqual( + Web3Utils.hexToNumber(setBlockRewardContract.status), + 1, + 'Transaction Failed' + ) foreignNonce++ console.log('\nset ValidatorSet contract on ERC677BridgeTokenRewardable') @@ -242,7 +338,11 @@ async function deployForeign() { privateKey: deploymentPrivateKey, url: FOREIGN_RPC_URL }) - assert.equal(Web3Utils.hexToNumber(setValidatorSetContract.status), 1, 'Transaction Failed') + assert.strictEqual( + Web3Utils.hexToNumber(setValidatorSetContract.status), + 1, + 'Transaction Failed' + ) foreignNonce++ } diff --git a/deploy/src/native_to_erc/home.js b/deploy/src/native_to_erc/home.js index a8002587d..29e69e8cb 100644 --- a/deploy/src/native_to_erc/home.js +++ b/deploy/src/native_to_erc/home.js @@ -2,14 +2,22 @@ const assert = require('assert') const Web3Utils = require('web3-utils') const env = require('../loadEnv') -const { deployContract, privateKeyToAddress, sendRawTxHome } = require('../deploymentUtils') +const { + deployContract, + privateKeyToAddress, + sendRawTxHome, + logValidatorsAndRewardAccounts +} = require('../deploymentUtils') const { web3Home, deploymentPrivateKey, HOME_RPC_URL } = require('../web3') const EternalStorageProxy = require('../../../build/contracts/EternalStorageProxy.json') const BridgeValidators = require('../../../build/contracts/BridgeValidators.json') +const RewardableValidators = require('../../../build/contracts/RewardableValidators.json') +const FeeManagerNativeToErc = require('../../../build/contracts/FeeManagerNativeToErc.json') const HomeBridge = require('../../../build/contracts/HomeBridgeNativeToErc.json') const VALIDATORS = env.VALIDATORS.split(' ') +const VALIDATORS_REWARD_ACCOUNTS = env.VALIDATORS_REWARD_ACCOUNTS.split(' ') const { DEPLOYMENT_ACCOUNT_PRIVATE_KEY, @@ -23,11 +31,15 @@ const { HOME_MIN_AMOUNT_PER_TX, HOME_REQUIRED_BLOCK_CONFIRMATIONS, FOREIGN_DAILY_LIMIT, - FOREIGN_MAX_AMOUNT_PER_TX + FOREIGN_MAX_AMOUNT_PER_TX, + HOME_REWARDABLE, + HOME_TRANSACTIONS_FEE } = env const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVATE_KEY) +const isRewardableBridge = HOME_REWARDABLE === 'true' + async function deployHome() { let homeNonce = await web3Home.eth.getTransactionCount(DEPLOYMENT_ACCOUNT_ADDRESS) console.log('deploying storage for home validators') @@ -39,7 +51,8 @@ async function deployHome() { homeNonce++ console.log('\ndeploying implementation for home validators') - const bridgeValidatorsHome = await deployContract(BridgeValidators, [], { + const bridgeValidatorsContract = isRewardableBridge ? RewardableValidators : BridgeValidators + const bridgeValidatorsHome = await deployContract(bridgeValidatorsContract, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, nonce: homeNonce }) @@ -61,13 +74,32 @@ async function deployHome() { homeNonce++ console.log('\ninitializing Home Bridge Validators with following parameters:\n') - console.log( - `REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, VALIDATORS: ${VALIDATORS}` - ) bridgeValidatorsHome.options.address = storageValidatorsHome.options.address - const initializeData = await bridgeValidatorsHome.methods - .initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, HOME_VALIDATORS_OWNER) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + + let initializeData + + if (isRewardableBridge) { + console.log( + `REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, HOME_VALIDATORS_OWNER: ${HOME_VALIDATORS_OWNER}` + ) + logValidatorsAndRewardAccounts(VALIDATORS, VALIDATORS_REWARD_ACCOUNTS) + initializeData = await bridgeValidatorsHome.methods + .initialize( + REQUIRED_NUMBER_OF_VALIDATORS, + VALIDATORS, + VALIDATORS_REWARD_ACCOUNTS, + HOME_VALIDATORS_OWNER + ) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + } else { + console.log( + `REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, VALIDATORS: ${VALIDATORS}, HOME_VALIDATORS_OWNER: ${HOME_VALIDATORS_OWNER}` + ) + initializeData = await bridgeValidatorsHome.methods + .initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, HOME_VALIDATORS_OWNER) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + } + const txInitialize = await sendRawTxHome({ data: initializeData, nonce: homeNonce, @@ -122,31 +154,91 @@ async function deployHome() { assert.strictEqual(Web3Utils.hexToNumber(txUpgradeToHomeBridge.status), 1, 'Transaction Failed') homeNonce++ - console.log('\ninitializing Home Bridge with following parameters:\n') - console.log(`Home Validators: ${storageValidatorsHome.options.address}, + let initializeHomeBridgeData + homeBridgeImplementation.options.address = homeBridgeStorage.options.address + + if (isRewardableBridge) { + console.log('\ndeploying implementation for fee manager') + const feeManager = await deployContract(FeeManagerNativeToErc, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + nonce: homeNonce + }) + console.log('[Home] feeManager Implementation: ', feeManager.options.address) + homeNonce++ + + const feeInWei = Web3Utils.toWei(HOME_TRANSACTIONS_FEE.toString(), 'ether') + + console.log('\ninitializing Home Bridge with fee contract:\n') + console.log(`Home Validators: ${storageValidatorsHome.options.address}, + HOME_DAILY_LIMIT : ${HOME_DAILY_LIMIT} which is ${Web3Utils.fromWei(HOME_DAILY_LIMIT)} in eth, + HOME_MAX_AMOUNT_PER_TX: ${HOME_MAX_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( + HOME_MAX_AMOUNT_PER_TX + )} in eth, + HOME_MIN_AMOUNT_PER_TX: ${HOME_MIN_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( + HOME_MIN_AMOUNT_PER_TX + )} in eth, + HOME_GAS_PRICE: ${HOME_GAS_PRICE}, HOME_REQUIRED_BLOCK_CONFIRMATIONS : ${HOME_REQUIRED_BLOCK_CONFIRMATIONS}, + FOREIGN_DAILY_LIMIT: ${FOREIGN_DAILY_LIMIT} which is ${Web3Utils.fromWei( + FOREIGN_DAILY_LIMIT + )} in eth, + FOREIGN_MAX_AMOUNT_PER_TX: ${FOREIGN_MAX_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( + FOREIGN_MAX_AMOUNT_PER_TX + )} in eth, + HOME_BRIDGE_OWNER: ${HOME_BRIDGE_OWNER}, + Fee Manager: ${feeManager.options.address}, + Fee: ${feeInWei} which is ${HOME_TRANSACTIONS_FEE * 100}%`) + + homeBridgeImplementation.options.address = homeBridgeStorage.options.address + initializeHomeBridgeData = await homeBridgeImplementation.methods + .rewardableInitialize( + storageValidatorsHome.options.address, + HOME_DAILY_LIMIT, + HOME_MAX_AMOUNT_PER_TX, + HOME_MIN_AMOUNT_PER_TX, + HOME_GAS_PRICE, + HOME_REQUIRED_BLOCK_CONFIRMATIONS, + FOREIGN_DAILY_LIMIT, + FOREIGN_MAX_AMOUNT_PER_TX, + HOME_BRIDGE_OWNER, + feeManager.options.address, + feeInWei + ) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + } else { + console.log('\ninitializing Home Bridge with following parameters:\n') + console.log(`Home Validators: ${storageValidatorsHome.options.address}, HOME_DAILY_LIMIT : ${HOME_DAILY_LIMIT} which is ${Web3Utils.fromWei(HOME_DAILY_LIMIT)} in eth, HOME_MAX_AMOUNT_PER_TX: ${HOME_MAX_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( - HOME_MAX_AMOUNT_PER_TX - )} in eth, + HOME_MAX_AMOUNT_PER_TX + )} in eth, HOME_MIN_AMOUNT_PER_TX: ${HOME_MIN_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( - HOME_MIN_AMOUNT_PER_TX - )} in eth, - HOME_GAS_PRICE: ${HOME_GAS_PRICE}, HOME_REQUIRED_BLOCK_CONFIRMATIONS : ${HOME_REQUIRED_BLOCK_CONFIRMATIONS} + HOME_MIN_AMOUNT_PER_TX + )} in eth, + HOME_GAS_PRICE: ${HOME_GAS_PRICE}, HOME_REQUIRED_BLOCK_CONFIRMATIONS : ${HOME_REQUIRED_BLOCK_CONFIRMATIONS}, + FOREIGN_DAILY_LIMIT: ${FOREIGN_DAILY_LIMIT} which is ${Web3Utils.fromWei( + FOREIGN_DAILY_LIMIT + )} in eth, + FOREIGN_MAX_AMOUNT_PER_TX: ${FOREIGN_MAX_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( + FOREIGN_MAX_AMOUNT_PER_TX + )} in eth, + HOME_BRIDGE_OWNER: ${HOME_BRIDGE_OWNER} `) - homeBridgeImplementation.options.address = homeBridgeStorage.options.address - const initializeHomeBridgeData = await homeBridgeImplementation.methods - .initialize( - storageValidatorsHome.options.address, - HOME_DAILY_LIMIT, - HOME_MAX_AMOUNT_PER_TX, - HOME_MIN_AMOUNT_PER_TX, - HOME_GAS_PRICE, - HOME_REQUIRED_BLOCK_CONFIRMATIONS, - FOREIGN_DAILY_LIMIT, - FOREIGN_MAX_AMOUNT_PER_TX, - HOME_BRIDGE_OWNER - ) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + homeBridgeImplementation.options.address = homeBridgeStorage.options.address + initializeHomeBridgeData = await homeBridgeImplementation.methods + .initialize( + storageValidatorsHome.options.address, + HOME_DAILY_LIMIT, + HOME_MAX_AMOUNT_PER_TX, + HOME_MIN_AMOUNT_PER_TX, + HOME_GAS_PRICE, + HOME_REQUIRED_BLOCK_CONFIRMATIONS, + FOREIGN_DAILY_LIMIT, + FOREIGN_MAX_AMOUNT_PER_TX, + HOME_BRIDGE_OWNER + ) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + } + const txInitializeHomeBridge = await sendRawTxHome({ data: initializeHomeBridgeData, nonce: homeNonce, From ae7cad2208d468d63a2b18fb0259532515fe2249 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 29 Jan 2019 10:13:18 -0300 Subject: [PATCH 072/187] Update gas consumption NATIVE-TO-ERC --- GAS_CONSUMPTION.md | 1 + docs/NATIVE-TO-ERC-WITH-REWARD.md | 59 +++++++++++++++++++++++++++++++ docs/NATIVE-TO-ERC.md | 32 ++++++++--------- 3 files changed, 75 insertions(+), 17 deletions(-) create mode 100644 docs/NATIVE-TO-ERC-WITH-REWARD.md diff --git a/GAS_CONSUMPTION.md b/GAS_CONSUMPTION.md index 24c5cbfa7..165d6d138 100644 --- a/GAS_CONSUMPTION.md +++ b/GAS_CONSUMPTION.md @@ -1,6 +1,7 @@ ## Gas Consumption by Bridge Mode - [NATIVE-TO-ERC](docs/NATIVE-TO-ERC.md) +- [NATIVE-TO-ERC-WITH-REWARD](docs/NATIVE-TO-ERC-WITH-REWARD.md) - [ERC-TO-ERC](docs/ERC-TO-ERC.md) - [ERC-TO-NATIVE](docs/ERC-TO-NATIVE.md) - [ERC-TO-NATIVE-WITH-REWARD](docs/ERC-TO-NATIVE-WITH-REWARD.md) diff --git a/docs/NATIVE-TO-ERC-WITH-REWARD.md b/docs/NATIVE-TO-ERC-WITH-REWARD.md new file mode 100644 index 000000000..99b0df278 --- /dev/null +++ b/docs/NATIVE-TO-ERC-WITH-REWARD.md @@ -0,0 +1,59 @@ +## Gas Consumption `NATIVE-TO-ERC` Bridge Mode with Reward contract + +#### Deployment +##### Home + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +EternalStorageProxy|deployment|378510|378510|378510 +RewardableValidators|deployment|1615790|1615790|1615790 +EternalStorageProxy|upgradeTo|35871|30924|30913 +RewardableValidators|initialize|202711|423292|318008 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +EternalStorageProxy|deployment|378510|378510|378510 +HomeBridgeNativeToErc|deployment|4193535|4193535|4193535 +EternalStorageProxy|upgradeTo|35871|30924|30913 +FeeManagerNativeToErc|deployment|861773|861773|861773 +HomeBridgeNativeToErc|rewardableInitialize|305520|305584|305563 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +Total| |8069397|8280148|8174821 + +##### Foreign + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +ERC677BridgeToken|deployment|1463536|1464560|1464170 +EternalStorageProxy|deployment|378510|378510|378510 +RewardableValidators|deployment|1615790|1615790|1615790 +EternalStorageProxy|upgradeTo|35871|30924|30913 +RewardableValidators|initialize|202711|423292|318008 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +EternalStorageProxy|deployment|378510|378510|378510 +ForeignBridgeNativeToErc|deployment|3534781|3534781|3534781 +EternalStorageProxy|upgradeTo|35871|30924|30913 +FeeManagerNativeToErc|deployment|861773|861773|861773 +ForeignBridgeNativeToErc|rewardableInitialize|327843|327907|327896 +ERC677BridgeToken|setBridgeContract|29432|44432|39432 +ERC677BridgeToken|transferOwnership|30860|30924|30913 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +Total| |8956794|9183633|9072915 + +#### Usage + +##### Validators + + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +To sign at the Home (each validator)| +HomeBridgeNativeToErc|submitSignature|159814|275587|220654 +To relay signatures from the Home to the Foreign (one validator)| +ForeignBridgeNativeToErc|executeSignatures|193143|374488|288553 +To sign and relay from the Foreign to the Home (each validator)| +HomeBridgeNativeToErc|executeAffirmation|67290|205460|108687 + +##### Users + + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +To request transfer from the Home to the Foreign| +HomeBridgeNativeToErc|fallback|46982|46982|46982 +To request transfer from the Foreign to the Home| +ERC677BridgeToken|transferAndCall|58654|166206|92597 diff --git a/docs/NATIVE-TO-ERC.md b/docs/NATIVE-TO-ERC.md index 0c980a94f..09cff7f7c 100644 --- a/docs/NATIVE-TO-ERC.md +++ b/docs/NATIVE-TO-ERC.md @@ -5,34 +5,34 @@ Contract | Method | Min | Max | Avg ---- | ---- | ---- | ---- | ---- EternalStorageProxy|deployment|378510|378510|378510 -BridgeValidators|deployment|1144207|1144207|1144207 +BridgeValidators|deployment|1351491|1351491|1351491 EternalStorageProxy|upgradeTo|35871|30924|30913 -BridgeValidators|initialize|187738|280847|253949 +BridgeValidators|initialize|210762|306607|270900 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 EternalStorageProxy|deployment|378510|378510|378510 -HomeBridgeNativeToErc|deployment|3327263|3327263|3327263 +HomeBridgeNativeToErc|deployment|4193535|4193535|4193535 EternalStorageProxy|upgradeTo|35871|30924|30913 -HomeBridgeNativeToErc|initialize|190051|190947|190755 +HomeBridgeNativeToErc|initialize|257416|258312|258003 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |5739327|5823438|5796326 +Total| |6903272|6990119|6954081 ##### Foreign Contract | Method | Min | Max | Avg ---- | ---- | ---- | ---- | ---- -ERC677BridgeToken|deployment|1498202|1499226|1498829 +ERC677BridgeToken|deployment|1463536|1464560|1464170 EternalStorageProxy|deployment|378510|378510|378510 -BridgeValidators|deployment|1144207|1144207|1144207 +BridgeValidators|deployment|1351491|1351491|1351491 EternalStorageProxy|upgradeTo|35871|30924|30913 -BridgeValidators|initialize|187738|280847|253949 +BridgeValidators|initialize|210762|306607|270900 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 EternalStorageProxy|deployment|378510|378510|378510 -ForeignBridgeNativeToErc|deployment|2768705|2768705|2768705 +ForeignBridgeNativeToErc|deployment|3534781|3534781|3534781 EternalStorageProxy|upgradeTo|35871|30924|30913 -ForeignBridgeNativeToErc|initialize|213493|213557|213549 +ForeignBridgeNativeToErc|initialize|281275|281339|281328 ERC677BridgeToken|setBridgeContract|29432|44432|39432 ERC677BridgeToken|transferOwnership|30860|30924|30913 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |6762705|6862072|6829736 +Total| |7792205|7894308|7853167 #### Usage @@ -41,11 +41,11 @@ Total| |6762705|6862072|6829736 Contract | Method | Min | Max | Avg ---- | ---- | ---- | ---- | ---- To sign at the Home (each validator)| -HomeBridgeNativeToErc|submitSignature|159362|275135|220127 +HomeBridgeNativeToErc|submitSignature|159814|275587|220654 To relay signatures from the Home to the Foreign (one validator)| -ForeignBridgeNativeToErc|executeSignatures|89201|146127|120917 +ForeignBridgeNativeToErc|executeSignatures|99365|172087|138314 To sign and relay from the Foreign to the Home (each validator)| -HomeBridgeNativeToErc|executeAffirmation|64314|107669|83596 +HomeBridgeNativeToErc|executeAffirmation|67247|132985|101980 ##### Users @@ -54,6 +54,4 @@ HomeBridgeNativeToErc|executeAffirmation|64314|107669|83596 To request transfer from the Home to the Foreign| HomeBridgeNativeToErc|fallback|46982|46982|46982 To request transfer from the Foreign to the Home| -ERC677BridgeToken|transferAndCall|58370|166206|92399 - - +ERC677BridgeToken|transferAndCall|58654|166206|92597 From a90babf2deccb778a560b94a9bbf38ea45de2b04 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Fri, 1 Feb 2019 10:08:48 -0300 Subject: [PATCH 073/187] Add getFeeManagerMode method --- contracts/upgradeable_contracts/BaseFeeManager.sol | 2 ++ .../upgradeable_contracts/RewardableBridge.sol | 14 ++++++++++++++ .../erc20_to_native/FeeManagerErcToNative.sol | 4 ++++ .../native_to_erc20/FeeManagerNativeToErc.sol | 4 ++++ test/erc_to_native/home_bridge.test.js | 12 ++++++++++++ test/native_to_erc/foreign_bridge_test.js | 13 +++++++++++++ test/native_to_erc/home_bridge_test.js | 12 ++++++++++++ 7 files changed, 61 insertions(+) diff --git a/contracts/upgradeable_contracts/BaseFeeManager.sol b/contracts/upgradeable_contracts/BaseFeeManager.sol index 93c462265..258ba2afa 100644 --- a/contracts/upgradeable_contracts/BaseFeeManager.sol +++ b/contracts/upgradeable_contracts/BaseFeeManager.sol @@ -40,6 +40,8 @@ contract BaseFeeManager is EternalStorage { distributeFeeProportionally(_fee, REWARD_FOR_TRANSFERRING_FROM_HOME); } + function getFeeManagerMode() public pure returns(bytes4); + function random(uint256 _count) public view returns(uint256) { return uint256(blockhash(block.number.sub(1))) % _count; } diff --git a/contracts/upgradeable_contracts/RewardableBridge.sol b/contracts/upgradeable_contracts/RewardableBridge.sol index fdae05f6e..0d094acc7 100644 --- a/contracts/upgradeable_contracts/RewardableBridge.sol +++ b/contracts/upgradeable_contracts/RewardableBridge.sol @@ -23,6 +23,20 @@ contract RewardableBridge is Ownable { return fee; } + function getFeeManagerMode() public view returns(bytes4) { + bytes4 mode; + bytes memory callData = abi.encodeWithSignature("getFeeManagerMode()"); + address feeManager = feeManagerContract(); + assembly { + let result := callcode(gas, feeManager, 0x0, add(callData, 0x20), mload(callData), 0, 4) + mode := mload(0) + + switch result + case 0 { revert(0, 0) } + } + return mode; + } + function feeManagerContract() public view returns(address) { return addressStorage[keccak256(abi.encodePacked("feeManagerContract"))]; } diff --git a/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol index 645241a33..be80bdd03 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol @@ -7,6 +7,10 @@ import "../Sacrifice.sol"; contract FeeManagerErcToNative is BaseFeeManager { + function getFeeManagerMode() public pure returns(bytes4) { + return bytes4(keccak256(abi.encodePacked("manages-both-directions"))); + } + function blockRewardContract() internal view returns(IBlockReward) { return IBlockReward(addressStorage[keccak256(abi.encodePacked("blockRewardContract"))]); } diff --git a/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErc.sol index d20c1ac96..a1f5b4c4e 100644 --- a/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErc.sol +++ b/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErc.sol @@ -7,6 +7,10 @@ import "../Sacrifice.sol"; contract FeeManagerNativeToErc is BaseFeeManager { + function getFeeManagerMode() public pure returns(bytes4) { + return bytes4(keccak256(abi.encodePacked("manages-one-direction"))); + } + function erc677token() public view returns(IBurnableMintableERC677Token) { return IBurnableMintableERC677Token(addressStorage[keccak256(abi.encodePacked("erc677token"))]); } diff --git a/test/erc_to_native/home_bridge.test.js b/test/erc_to_native/home_bridge.test.js index 429d9eec2..73a4c5270 100644 --- a/test/erc_to_native/home_bridge.test.js +++ b/test/erc_to_native/home_bridge.test.js @@ -917,6 +917,18 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const bridgeFee = await homeBridge.getFee() bridgeFee.should.be.bignumber.equal(fee) }) + it('should be able to get fee manager mode', async () => { + // Given + const feeManager = await FeeManagerErcToNative.new() + const bothDirectionsModeHash = '0xd7de965f' + + // When + await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled + + // Then + const feeManagerMode = await homeBridge.getFeeManagerMode() + feeManagerMode.should.be.equals(bothDirectionsModeHash) + }) }) describe('#feeManager_ExecuteAffirmation', async () => { it('should distribute fee to validator', async () => { diff --git a/test/native_to_erc/foreign_bridge_test.js b/test/native_to_erc/foreign_bridge_test.js index 747957925..d570a0737 100644 --- a/test/native_to_erc/foreign_bridge_test.js +++ b/test/native_to_erc/foreign_bridge_test.js @@ -590,6 +590,19 @@ contract('ForeignBridge', async (accounts) => { const bridgeFee = await foreignBridge.getFee() bridgeFee.should.be.bignumber.equal(newFee) }) + + it('should be able to get fee manager mode', async () => { + // Given + const feeManager = await FeeManagerNativeToErc.new() + const oneDirectionsModeHash = '0xf2aed8f7' + + // When + await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, fee).should.be.fulfilled; + + // Then + const feeManagerMode = await foreignBridge.getFeeManagerMode() + feeManagerMode.should.be.equals(oneDirectionsModeHash) + }) }) describe('#RewardableBridge_executeSignatures', async () => { diff --git a/test/native_to_erc/home_bridge_test.js b/test/native_to_erc/home_bridge_test.js index 2a798aff8..84323ca29 100644 --- a/test/native_to_erc/home_bridge_test.js +++ b/test/native_to_erc/home_bridge_test.js @@ -631,6 +631,18 @@ contract('HomeBridge', async (accounts) => { const bridgeFee = await homeBridge.getFee() bridgeFee.should.be.bignumber.equal(newFee) }) + it('should be able to get fee manager mode', async () => { + // Given + const feeManager = await FeeManagerNativeToErc.new() + const oneDirectionsModeHash = '0xf2aed8f7' + + // When + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.fulfilled; + + // Then + const feeManagerMode = await homeBridge.getFeeManagerMode() + feeManagerMode.should.be.equals(oneDirectionsModeHash) + }) }) describe('#feeManager_ExecuteAffirmation', async () => { From e1787e63095fdfaf5450d40b4f13bbd295636a2c Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Fri, 1 Feb 2019 17:06:19 -0300 Subject: [PATCH 074/187] Refactor fee into homeFee and foreignFee --- .../upgradeable_contracts/BaseFeeManager.sol | 29 +++++--- contracts/upgradeable_contracts/FeeTypes.sol | 7 ++ .../RewardableBridge.sol | 34 ++++++--- .../erc20_to_native/HomeBridgeErcToNative.sol | 12 +-- .../ForeignBridgeNativeToErc.sol | 8 +- .../native_to_erc20/HomeBridgeNativeToErc.sol | 8 +- test/erc_to_native/home_bridge.test.js | 73 +++++++++++-------- test/native_to_erc/foreign_bridge_test.js | 52 +++++++------ test/native_to_erc/home_bridge_test.js | 48 +++++++----- 9 files changed, 171 insertions(+), 100 deletions(-) create mode 100644 contracts/upgradeable_contracts/FeeTypes.sol diff --git a/contracts/upgradeable_contracts/BaseFeeManager.sol b/contracts/upgradeable_contracts/BaseFeeManager.sol index 258ba2afa..52eb98865 100644 --- a/contracts/upgradeable_contracts/BaseFeeManager.sol +++ b/contracts/upgradeable_contracts/BaseFeeManager.sol @@ -3,19 +3,21 @@ pragma solidity 0.4.24; import "../upgradeability/EternalStorage.sol"; import "../libraries/SafeMath.sol"; import "../IRewardableValidators.sol"; +import "./FeeTypes.sol"; -contract BaseFeeManager is EternalStorage { +contract BaseFeeManager is EternalStorage, FeeTypes { using SafeMath for uint256; bytes32 public constant REWARD_FOR_TRANSFERRING_FROM_HOME = keccak256(abi.encodePacked("reward-transferring-from-home")); bytes32 public constant REWARD_FOR_TRANSFERRING_FROM_FOREIGN = keccak256(abi.encodePacked("reward-transferring-from-foreign")); - event FeeUpdated(uint256 fee); + event HomeFeeUpdated(uint256 fee); + event ForeignFeeUpdated(uint256 fee); - function calculateFee(uint256 _value, bool _recover) external view returns(uint256) { - uint256 fee = getFee(); + function calculateFee(uint256 _value, bool _recover, bytes32 _feeType) external view returns(uint256) { + uint256 fee = _feeType == HOME_FEE ? getHomeFee() : getForeignFee(); uint256 eth = 1 ether; if (!_recover) { return _value.mul(fee).div(eth); @@ -23,13 +25,22 @@ contract BaseFeeManager is EternalStorage { return _value.mul(fee).div(eth.sub(fee)); } - function setFee(uint256 _fee) external { - uintStorage[keccak256(abi.encodePacked("fee"))] = _fee; - emit FeeUpdated(_fee); + function setHomeFee(uint256 _fee) external { + uintStorage[keccak256(abi.encodePacked("homeFee"))] = _fee; + emit HomeFeeUpdated(_fee); } - function getFee() public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("fee"))]; + function getHomeFee() public view returns(uint256) { + return uintStorage[keccak256(abi.encodePacked("homeFee"))]; + } + + function setForeignFee(uint256 _fee) external { + uintStorage[keccak256(abi.encodePacked("foreignFee"))] = _fee; + emit ForeignFeeUpdated(_fee); + } + + function getForeignFee() public view returns(uint256) { + return uintStorage[keccak256(abi.encodePacked("foreignFee"))]; } function distributeFeeFromAffirmation(uint256 _fee) external { diff --git a/contracts/upgradeable_contracts/FeeTypes.sol b/contracts/upgradeable_contracts/FeeTypes.sol new file mode 100644 index 000000000..7cc977490 --- /dev/null +++ b/contracts/upgradeable_contracts/FeeTypes.sol @@ -0,0 +1,7 @@ +pragma solidity 0.4.24; + + +contract FeeTypes { + bytes32 internal constant HOME_FEE = keccak256(abi.encodePacked("home-fee")); + bytes32 internal constant FOREIGN_FEE = keccak256(abi.encodePacked("foreign-fee")); +} diff --git a/contracts/upgradeable_contracts/RewardableBridge.sol b/contracts/upgradeable_contracts/RewardableBridge.sol index 0d094acc7..3de2ef6b9 100644 --- a/contracts/upgradeable_contracts/RewardableBridge.sol +++ b/contracts/upgradeable_contracts/RewardableBridge.sol @@ -1,18 +1,33 @@ pragma solidity 0.4.24; import "./Ownable.sol"; +import "./FeeTypes.sol"; -contract RewardableBridge is Ownable { +contract RewardableBridge is Ownable, FeeTypes { - function setFee(uint256 _fee) external onlyOwner { - _setFee(feeManagerContract(), _fee); + function setHomeFee(uint256 _fee) external onlyOwner { + _setFee(feeManagerContract(), _fee, HOME_FEE); } - function getFee() public view returns(uint256) { + function setForeignFee(uint256 _fee) external onlyOwner { + _setFee(feeManagerContract(), _fee, FOREIGN_FEE); + } + + function getHomeFee() public view returns(uint256) { + return _getFee(HOME_FEE); + } + + function getForeignFee() public view returns(uint256) { + return _getFee(FOREIGN_FEE); + } + + function _getFee(bytes32 _feeType) public view returns(uint256) { uint256 fee; - bytes memory callData = abi.encodeWithSignature("getFee()"); address feeManager = feeManagerContract(); + string memory method = _feeType == HOME_FEE ? "getHomeFee()" : "getForeignFee()"; + bytes memory callData = abi.encodeWithSignature(method); + assembly { let result := callcode(gas, feeManager, 0x0, add(callData, 0x20), mload(callData), 0, 32) fee := mload(0) @@ -46,8 +61,9 @@ contract RewardableBridge is Ownable { addressStorage[keccak256(abi.encodePacked("feeManagerContract"))] = _feeManager; } - function _setFee(address _feeManager, uint256 _fee) internal { - require(_feeManager.delegatecall(abi.encodeWithSignature("setFee(uint256)", _fee))); + function _setFee(address _feeManager, uint256 _fee, bytes32 _feeType) internal { + string memory method = _feeType == HOME_FEE ? "setHomeFee(uint256)" : "setForeignFee(uint256)"; + require(_feeManager.delegatecall(abi.encodeWithSignature(method, _fee))); } function isContract(address _addr) internal view returns (bool) @@ -57,9 +73,9 @@ contract RewardableBridge is Ownable { return length > 0; } - function calculateFee(uint256 _value, bool _recover, address _impl) internal view returns(uint256) { + function calculateFee(uint256 _value, bool _recover, address _impl, bytes32 _feeType) internal view returns(uint256) { uint256 fee; - bytes memory callData = abi.encodeWithSignature("calculateFee(uint256,bool)", _value, _recover); + bytes memory callData = abi.encodeWithSignature("calculateFee(uint256,bool,bytes32)", _value, _recover, _feeType); assembly { let result := callcode(gas, _impl, 0x0, add(callData, 0x20), mload(callData), 0, 32) fee := mload(0) diff --git a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol index 5bd2f4e93..e4e1cd4eb 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol @@ -26,7 +26,7 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, uint256 valueToTransfer = msg.value; address feeManager = feeManagerContract(); if (feeManager != address(0)) { - uint256 fee = calculateFee(valueToTransfer, false, feeManager); + uint256 fee = calculateFee(valueToTransfer, false, feeManager, HOME_FEE); valueToTransfer = valueToTransfer.sub(fee); } setTotalBurntCoins(totalBurntCoins().add(valueToTransfer)); @@ -76,7 +76,8 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, uint256 _foreignMaxPerTx, address _owner, address _feeManager, - uint256 _fee + uint256 _homeFee, + uint256 _foreignFee ) public returns(bool) { _initialize( @@ -93,7 +94,8 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, ); require(isContract(_feeManager)); addressStorage[keccak256(abi.encodePacked("feeManagerContract"))] = _feeManager; - _setFee(_feeManager, _fee); + _setFee(_feeManager, _homeFee, HOME_FEE); + _setFee(_feeManager, _foreignFee, FOREIGN_FEE); setInitialize(true); return isInitialized(); @@ -157,7 +159,7 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, address feeManager = feeManagerContract(); if (feeManager != address(0)) { - uint256 fee = calculateFee(valueToMint, false, feeManager); + uint256 fee = calculateFee(valueToMint, false, feeManager, FOREIGN_FEE); distributeFeeFromAffirmation(fee, feeManager); valueToMint = valueToMint.sub(fee); } @@ -173,7 +175,7 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, bytes32 txHash; address contractAddress; (recipient, amount, txHash, contractAddress) = Message.parseMessage(_message); - uint256 fee = calculateFee(amount, true, feeManager); + uint256 fee = calculateFee(amount, true, feeManager, HOME_FEE); distributeFeeFromSignatures(fee, feeManager); } } diff --git a/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol index 278b5f5d4..77b12b9c2 100644 --- a/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol +++ b/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol @@ -54,7 +54,8 @@ contract ForeignBridgeNativeToErc is ERC677Receiver, BasicBridge, BasicForeignBr uint256 _homeMaxPerTx, address _owner, address _feeManager, - uint256 _fee + uint256 _homeFee, + uint256 _foreignFee ) public returns(bool) { _initialize( _validatorContract, @@ -70,7 +71,8 @@ contract ForeignBridgeNativeToErc is ERC677Receiver, BasicBridge, BasicForeignBr ); require(isContract(_feeManager)); addressStorage[keccak256(abi.encodePacked("feeManagerContract"))] = _feeManager; - _setFee(_feeManager, _fee); + _setFee(_feeManager, _homeFee, HOME_FEE); + _setFee(_feeManager, _foreignFee, FOREIGN_FEE); setInitialize(true); return isInitialized(); } @@ -119,7 +121,7 @@ contract ForeignBridgeNativeToErc is ERC677Receiver, BasicBridge, BasicForeignBr uint256 valueToMint = _amount; address feeManager = feeManagerContract(); if (feeManager != address(0)) { - uint256 fee = calculateFee(valueToMint, false, feeManager); + uint256 fee = calculateFee(valueToMint, false, feeManager, HOME_FEE); distributeFeeFromSignatures(fee, feeManager); valueToMint = valueToMint.sub(fee); } diff --git a/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol index 0a3486dba..fe8ec7dbe 100644 --- a/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol +++ b/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol @@ -56,7 +56,8 @@ contract HomeBridgeNativeToErc is EternalStorage, BasicBridge, BasicHomeBridge, uint256 _foreignMaxPerTx, address _owner, address _feeManager, - uint256 _fee + uint256 _homeFee, + uint256 _foreignFee ) public returns(bool) { _initialize( @@ -72,7 +73,8 @@ contract HomeBridgeNativeToErc is EternalStorage, BasicBridge, BasicHomeBridge, ); require(isContract(_feeManager)); addressStorage[keccak256(abi.encodePacked("feeManagerContract"))] = _feeManager; - _setFee(_feeManager, _fee); + _setFee(_feeManager, _homeFee, HOME_FEE); + _setFee(_feeManager, _foreignFee, FOREIGN_FEE); setInitialize(true); return isInitialized(); } @@ -118,7 +120,7 @@ contract HomeBridgeNativeToErc is EternalStorage, BasicBridge, BasicHomeBridge, address feeManager = feeManagerContract(); if (feeManager != address(0)) { - uint256 fee = calculateFee(valueToTransfer, false, feeManager); + uint256 fee = calculateFee(valueToTransfer, false, feeManager, FOREIGN_FEE); distributeFeeFromAffirmation(fee, feeManager); valueToTransfer = valueToTransfer.sub(fee); } diff --git a/test/erc_to_native/home_bridge.test.js b/test/erc_to_native/home_bridge.test.js index 73a4c5270..7e856ccff 100644 --- a/test/erc_to_native/home_bridge.test.js +++ b/test/erc_to_native/home_bridge.test.js @@ -147,11 +147,12 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { }) describe('#rewardableInitialize', async() => { - let feeManager, fee + let feeManager, homeFee, foreignFee beforeEach(async () => { feeManager = await FeeManagerErcToNative.new() homeContract = await HomeBridge.new() - fee = web3.toBigNumber(web3.toWei(0.001, "ether")) + homeFee = web3.toBigNumber(web3.toWei(0.001, "ether")) + foreignFee = web3.toBigNumber(web3.toWei(0.002, "ether")) }) it('sets variables', async () => { ZERO_ADDRESS.should.be.equal(await homeContract.validatorContract()) @@ -161,7 +162,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { false.should.be.equal(await homeContract.isInitialized()) ZERO_ADDRESS.should.be.equal(await homeContract.blockRewardContract()) - await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.fulfilled + await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled true.should.be.equal(await homeContract.isInitialized()) validatorContract.address.should.be.equal(await homeContract.validatorContract()) @@ -182,24 +183,26 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const feeManagerContract = await homeContract.feeManagerContract() feeManagerContract.should.be.equals(feeManager.address) - const bridgeFee = await homeContract.getFee() - bridgeFee.should.be.bignumber.equal(fee) + const bridgeHomeFee = await homeContract.getHomeFee() + bridgeHomeFee.should.be.bignumber.equal(homeFee) + const bridgeForeignFee = await homeContract.getForeignFee() + bridgeForeignFee.should.be.bignumber.equal(foreignFee) }) it('cant initialize with invalid arguments', async () => { false.should.be.equal(await homeContract.isInitialized()) - await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, 0, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.rejectedWith(ERROR_MSG); - await homeContract.rewardableInitialize(owner, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.rejectedWith(ERROR_MSG); - await homeContract.rewardableInitialize(ZERO_ADDRESS, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.rejectedWith(ERROR_MSG); - await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, owner, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.rejectedWith(ERROR_MSG); - await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, halfEther, oneEther, owner, feeManager.address, fee).should.be.rejectedWith(ERROR_MSG); - await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, ZERO_ADDRESS, fee).should.be.rejectedWith(ERROR_MSG); - await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.fulfilled; + await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, 0, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); + await homeContract.rewardableInitialize(owner, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); + await homeContract.rewardableInitialize(ZERO_ADDRESS, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); + await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, owner, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); + await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, halfEther, oneEther, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); + await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, ZERO_ADDRESS, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); + await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; true.should.be.equal(await homeContract.isInitialized()) }) it('can update fee contract', async () => { - await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.fulfilled; + await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; // Given const newFeeManager = await FeeManagerErcToNative.new() @@ -213,17 +216,21 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { }) it('can update fee', async () => { - await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.fulfilled; + await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; // Given - const newFee = web3.toBigNumber(web3.toWei(0.1, "ether")) + const newHomeFee = web3.toBigNumber(web3.toWei(0.1, "ether")) + const newForeignFee = web3.toBigNumber(web3.toWei(0.2, "ether")) // When - await homeContract.setFee(newFee, { from: owner }).should.be.fulfilled + await homeContract.setHomeFee(newHomeFee, { from: owner }).should.be.fulfilled + await homeContract.setForeignFee(newForeignFee, { from: owner }).should.be.fulfilled // Then - const bridgeFee = await homeContract.getFee() - bridgeFee.should.be.bignumber.equal(newFee) + const bridgeHomeFee = await homeContract.getHomeFee() + bridgeHomeFee.should.be.bignumber.equal(newHomeFee) + const bridgeForeignFee = await homeContract.getForeignFee() + bridgeForeignFee.should.be.bignumber.equal(newForeignFee) }) }) @@ -903,19 +910,23 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const feeManagerContract = await homeBridge.feeManagerContract() feeManagerContract.should.be.equals(feeManager.address) }) - it('should be able to set and get fee', async () => { + it('should be able to set and get fees', async () => { // Given // 10% fee - const fee = web3.toBigNumber(web3.toWei(0.1, "ether")) + const homeFee = web3.toBigNumber(web3.toWei(0.1, "ether")) + const foreignFee = web3.toBigNumber(web3.toWei(0.2, "ether")) const feeManager = await FeeManagerErcToNative.new() await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled // When - await homeBridge.setFee(fee, { from: owner }).should.be.fulfilled + await homeBridge.setHomeFee(homeFee, { from: owner }).should.be.fulfilled + await homeBridge.setForeignFee(foreignFee, { from: owner }).should.be.fulfilled // Then - const bridgeFee = await homeBridge.getFee() - bridgeFee.should.be.bignumber.equal(fee) + const bridgeHomeFee = await homeBridge.getHomeFee() + bridgeHomeFee.should.be.bignumber.equal(homeFee) + const bridgeForeignFee = await homeBridge.getForeignFee() + bridgeForeignFee.should.be.bignumber.equal(foreignFee) }) it('should be able to get fee manager mode', async () => { // Given @@ -955,7 +966,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) const feeManager = await FeeManagerErcToNative.new() await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled - await homeBridge.setFee(feeInWei, { from: owner }).should.be.fulfilled + await homeBridge.setForeignFee(feeInWei, { from: owner }).should.be.fulfilled const recipient = accounts[5]; const value = halfEther; @@ -1016,7 +1027,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) const feeManager = await FeeManagerErcToNative.new() await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled - await homeBridge.setFee(feeInWei, { from: owner }).should.be.fulfilled + await homeBridge.setForeignFee(feeInWei, { from: owner }).should.be.fulfilled const recipient = accounts[8]; const balanceBefore = await web3.eth.getBalance(recipient) @@ -1093,7 +1104,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const feePerValidator = feeAmount.div(web3.toBigNumber(5)) const feeManager = await FeeManagerErcToNative.new() await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled - await homeBridge.setFee(feeInWei, { from: owner }).should.be.fulfilled + await homeBridge.setForeignFee(feeInWei, { from: owner }).should.be.fulfilled const recipient = "0xf4bef13f9f4f2b203faf0c3cbbaabe1afe056955"; const balanceBefore = await web3.eth.getBalance(recipient) @@ -1170,7 +1181,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) const feeManager = await FeeManagerErcToNative.new() await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled - await homeBridge.setFee(feeInWei, { from: owner }).should.be.fulfilled + await homeBridge.setHomeFee(feeInWei, { from: owner }).should.be.fulfilled // When const { logs } = await homeBridge.sendTransaction({ from: recipient, value }).should.be.fulfilled @@ -1208,7 +1219,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) const feeManager = await FeeManagerErcToNative.new() await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled - await homeBridge.setFee(feeInWei, { from: owner }).should.be.fulfilled + await homeBridge.setHomeFee(feeInWei, { from: owner }).should.be.fulfilled const recipient = accounts[5]; const initialValue = halfEther @@ -1265,7 +1276,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const feePerValidator = web3.toBigNumber(166666666666666) const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled - await homeBridge.setFee(feeInWei, { from: owner }).should.be.fulfilled + await homeBridge.setHomeFee(feeInWei, { from: owner }).should.be.fulfilled const recipient = accounts[7]; const initialValue = halfEther @@ -1338,7 +1349,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) const feeManager = await FeeManagerErcToNative.new() await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled - await homeBridge.setFee(feeInWei, { from: owner }).should.be.fulfilled + await homeBridge.setHomeFee(feeInWei, { from: owner }).should.be.fulfilled const recipient = accounts[0]; const initialValue = halfEther @@ -1400,7 +1411,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { for (let i = 0; i < 10; i++) { // send Tx to generate new blocks - await feeManager.setFee(0).should.be.fulfilled + await feeManager.setHomeFee(0).should.be.fulfilled // When const result = await feeManager.random(3); diff --git a/test/native_to_erc/foreign_bridge_test.js b/test/native_to_erc/foreign_bridge_test.js index d570a0737..3e998db4f 100644 --- a/test/native_to_erc/foreign_bridge_test.js +++ b/test/native_to_erc/foreign_bridge_test.js @@ -514,7 +514,7 @@ contract('ForeignBridge', async (accounts) => { }) describe('#rewardableInitialize', async() => { - let fee, foreignBridge, token, rewardableValidators + let homeFee, foreignFee, foreignBridge, token, rewardableValidators let validators = [accounts[1]] let rewards = [accounts[2]] let requiredSignatures = 1 @@ -523,7 +523,8 @@ contract('ForeignBridge', async (accounts) => { rewardableValidators = await RewardableValidators.new() await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled foreignBridge = await ForeignBridge.new() - fee = web3.toBigNumber(web3.toWei(0.001, "ether")) + homeFee = web3.toBigNumber(web3.toWei(0.001, "ether")) + foreignFee = web3.toBigNumber(web3.toWei(0.002, "ether")) }) it('sets variables', async () => { const feeManager = await FeeManagerNativeToErc.new() @@ -533,13 +534,13 @@ contract('ForeignBridge', async (accounts) => { '0'.should.be.bignumber.equal(await foreignBridge.maxPerTx()) false.should.be.equal(await foreignBridge.isInitialized()) - await foreignBridge.rewardableInitialize(ZERO_ADDRESS, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, fee).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.rewardableInitialize(rewardableValidators.address, ZERO_ADDRESS, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, fee).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, 0, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, fee).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.rewardableInitialize(owner, token.address, oneEther, halfEther, minPerTx, requireBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, fee).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.rewardableInitialize(rewardableValidators.address, owner, oneEther, halfEther, minPerTx, requireBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, fee).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.rewardableInitialize(rewardableValidators.address, owner, oneEther, halfEther, minPerTx, requireBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, owner, ZERO_ADDRESS, fee).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, fee).should.be.fulfilled; + await foreignBridge.rewardableInitialize(ZERO_ADDRESS, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); + await foreignBridge.rewardableInitialize(rewardableValidators.address, ZERO_ADDRESS, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); + await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, 0, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); + await foreignBridge.rewardableInitialize(owner, token.address, oneEther, halfEther, minPerTx, requireBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); + await foreignBridge.rewardableInitialize(rewardableValidators.address, owner, oneEther, halfEther, minPerTx, requireBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); + await foreignBridge.rewardableInitialize(rewardableValidators.address, owner, oneEther, halfEther, minPerTx, requireBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, owner, ZERO_ADDRESS, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); + await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; true.should.be.equal(await foreignBridge.isInitialized()) rewardableValidators.address.should.be.equal(await foreignBridge.validatorContract()); @@ -557,13 +558,15 @@ contract('ForeignBridge', async (accounts) => { const feeManagerContract = await foreignBridge.feeManagerContract() feeManagerContract.should.be.equals(feeManager.address) - const bridgeFee = await foreignBridge.getFee() - bridgeFee.should.be.bignumber.equal(fee) + const bridgeHomeFee = await foreignBridge.getHomeFee() + bridgeHomeFee.should.be.bignumber.equal(homeFee) + const bridgeForeignFee = await foreignBridge.getForeignFee() + bridgeForeignFee.should.be.bignumber.equal(foreignFee) }) it('can update fee contract', async () => { const feeManager = await FeeManagerNativeToErc.new() - await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, fee).should.be.fulfilled; + await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; // Given const newFeeManager = await FeeManagerNativeToErc.new() @@ -578,17 +581,21 @@ contract('ForeignBridge', async (accounts) => { it('can update fee', async () => { const feeManager = await FeeManagerNativeToErc.new() - await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, fee).should.be.fulfilled; + await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; // Given - const newFee = web3.toBigNumber(web3.toWei(0.1, "ether")) + const newHomeFee = web3.toBigNumber(web3.toWei(0.1, "ether")) + const newForeignFee = web3.toBigNumber(web3.toWei(0.2, "ether")) // When - await foreignBridge.setFee(newFee, { from: owner }).should.be.fulfilled + await foreignBridge.setHomeFee(newHomeFee, { from: owner }).should.be.fulfilled + await foreignBridge.setForeignFee(newForeignFee, { from: owner }).should.be.fulfilled // Then - const bridgeFee = await foreignBridge.getFee() - bridgeFee.should.be.bignumber.equal(newFee) + const bridgeHomeFee = await foreignBridge.getHomeFee() + bridgeHomeFee.should.be.bignumber.equal(newHomeFee) + const bridgeForeignFee = await foreignBridge.getForeignFee() + bridgeForeignFee.should.be.bignumber.equal(newForeignFee) }) it('should be able to get fee manager mode', async () => { @@ -597,7 +604,7 @@ contract('ForeignBridge', async (accounts) => { const oneDirectionsModeHash = '0xf2aed8f7' // When - await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, fee).should.be.fulfilled; + await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; // Then const feeManagerMode = await foreignBridge.getFeeManagerMode() @@ -616,6 +623,7 @@ contract('ForeignBridge', async (accounts) => { it('should distribute fee to validator', async () => { const fee = 0.001 const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeNotUsedInWei = web3.toBigNumber(web3.toWei(0.5, "ether")) const value = halfEther const finalUserValue = value.mul(web3.toBigNumber(1-fee)); const feeAmount = value.mul(web3.toBigNumber(fee)) @@ -624,7 +632,7 @@ contract('ForeignBridge', async (accounts) => { const rewards = [accounts[2]] const requiredSignatures = 1 await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled - await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, feeInWei).should.be.fulfilled; + await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, feeInWei, feeNotUsedInWei).should.be.fulfilled; await token.transferOwnership(foreignBridge.address); const recipientAccount = accounts[3]; @@ -654,6 +662,7 @@ contract('ForeignBridge', async (accounts) => { // Given const fee = 0.001 const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeNotUsedInWei = web3.toBigNumber(web3.toWei(0.5, "ether")) const feePerValidator = web3.toBigNumber(166666666666666) const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) const value = halfEther @@ -663,7 +672,7 @@ contract('ForeignBridge', async (accounts) => { const rewards = [accounts[4], accounts[5], accounts[6]] const requiredSignatures = 3 await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled - await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, feeInWei).should.be.fulfilled; + await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, feeInWei, feeNotUsedInWei).should.be.fulfilled; await token.transferOwnership(foreignBridge.address); const recipientAccount = accounts[7]; @@ -715,6 +724,7 @@ contract('ForeignBridge', async (accounts) => { // Given const fee = 0.001 const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeNotUsedInWei = web3.toBigNumber(web3.toWei(0.5, "ether")) const value = halfEther const feeAmount = value.mul(web3.toBigNumber(fee)) const feePerValidator = feeAmount.div(web3.toBigNumber(5)) @@ -724,7 +734,7 @@ contract('ForeignBridge', async (accounts) => { const rewards = [accounts[5], accounts[6], accounts[7], accounts[8], accounts[9]] const requiredSignatures = 3 await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled - await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, feeInWei).should.be.fulfilled; + await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, feeInWei, feeNotUsedInWei).should.be.fulfilled; await token.transferOwnership(foreignBridge.address); const recipientAccount = accounts[0]; diff --git a/test/native_to_erc/home_bridge_test.js b/test/native_to_erc/home_bridge_test.js index 84323ca29..301557821 100644 --- a/test/native_to_erc/home_bridge_test.js +++ b/test/native_to_erc/home_bridge_test.js @@ -558,7 +558,7 @@ contract('HomeBridge', async (accounts) => { }) describe('#rewardableInitialize', async() => { - let fee, homeBridge, rewardableValidators + let homeFee, foreignFee, homeBridge, rewardableValidators let validators = [accounts[1]] let rewards = [accounts[2]] let requiredSignatures = 1 @@ -566,7 +566,8 @@ contract('HomeBridge', async (accounts) => { rewardableValidators = await RewardableValidators.new() await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled homeBridge = await HomeBridge.new() - fee = web3.toBigNumber(web3.toWei(0.001, "ether")) + homeFee = web3.toBigNumber(web3.toWei(0.001, "ether")) + foreignFee = web3.toBigNumber(web3.toWei(0.002, "ether")) }) it('sets variables', async () => { const feeManager = await FeeManagerNativeToErc.new() @@ -576,11 +577,11 @@ contract('HomeBridge', async (accounts) => { '0'.should.be.bignumber.equal(await homeBridge.maxPerTx()) false.should.be.equal(await homeBridge.isInitialized()) - await homeBridge.rewardableInitialize(ZERO_ADDRESS, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.rejectedWith(ERROR_MSG); - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, 0, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.rejectedWith(ERROR_MSG); - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, 0, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.rejectedWith(ERROR_MSG); - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, ZERO_ADDRESS, fee).should.be.rejectedWith(ERROR_MSG); - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.fulfilled; + await homeBridge.rewardableInitialize(ZERO_ADDRESS, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, 0, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, 0, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, ZERO_ADDRESS, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; true.should.be.equal(await homeBridge.isInitialized()) rewardableValidators.address.should.be.equal(await homeBridge.validatorContract()); @@ -598,13 +599,15 @@ contract('HomeBridge', async (accounts) => { const feeManagerContract = await homeBridge.feeManagerContract() feeManagerContract.should.be.equals(feeManager.address) - const bridgeFee = await homeBridge.getFee() - bridgeFee.should.be.bignumber.equal(fee) + const bridgeHomeFee = await homeBridge.getHomeFee() + bridgeHomeFee.should.be.bignumber.equal(homeFee) + const bridgeForeignFee = await homeBridge.getForeignFee() + bridgeForeignFee.should.be.bignumber.equal(foreignFee) }) it('can update fee contract', async () => { const feeManager = await FeeManagerNativeToErc.new() - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.fulfilled; + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; // Given const newFeeManager = await FeeManagerNativeToErc.new() @@ -619,17 +622,21 @@ contract('HomeBridge', async (accounts) => { it('can update fee', async () => { const feeManager = await FeeManagerNativeToErc.new() - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.fulfilled; + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; // Given - const newFee = web3.toBigNumber(web3.toWei(0.1, "ether")) + const newHomeFee = web3.toBigNumber(web3.toWei(0.1, "ether")) + const newForeignFee = web3.toBigNumber(web3.toWei(0.2, "ether")) // When - await homeBridge.setFee(newFee, { from: owner }).should.be.fulfilled + await homeBridge.setHomeFee(newHomeFee, { from: owner }).should.be.fulfilled + await homeBridge.setForeignFee(newForeignFee, { from: owner }).should.be.fulfilled // Then - const bridgeFee = await homeBridge.getFee() - bridgeFee.should.be.bignumber.equal(newFee) + const bridgeHomeFee = await homeBridge.getHomeFee() + bridgeHomeFee.should.be.bignumber.equal(newHomeFee) + const bridgeForeignFee = await homeBridge.getForeignFee() + bridgeForeignFee.should.be.bignumber.equal(newForeignFee) }) it('should be able to get fee manager mode', async () => { // Given @@ -637,7 +644,7 @@ contract('HomeBridge', async (accounts) => { const oneDirectionsModeHash = '0xf2aed8f7' // When - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, fee).should.be.fulfilled; + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; // Then const feeManagerMode = await homeBridge.getFeeManagerMode() @@ -661,11 +668,12 @@ contract('HomeBridge', async (accounts) => { // 0.1% fee const fee = 0.001 const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeNotUsedInWei = web3.toBigNumber(web3.toWei(0.5, "ether")) const value = halfEther; const finalUserValue = value.mul(web3.toBigNumber(1-fee)); const feeAmount = value.mul(web3.toBigNumber(fee)) - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei).should.be.fulfilled; + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeNotUsedInWei, feeInWei).should.be.fulfilled; await homeBridge.sendTransaction({ from: accounts[0], value: halfEther @@ -710,6 +718,7 @@ contract('HomeBridge', async (accounts) => { // 0.1% fee const fee = 0.001 const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeNotUsedInWei = web3.toBigNumber(web3.toWei(0.5, "ether")) const feePerValidator = web3.toBigNumber(166666666666666) const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) const finalUserValue = value.mul(web3.toBigNumber(1-fee)); @@ -717,7 +726,7 @@ contract('HomeBridge', async (accounts) => { const homeBridge = await HomeBridge.new() const feeManager = await FeeManagerNativeToErc.new() await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei).should.be.fulfilled; + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeNotUsedInWei, feeInWei).should.be.fulfilled; await homeBridge.sendTransaction({ from: accounts[0], value: halfEther @@ -781,6 +790,7 @@ contract('HomeBridge', async (accounts) => { // 0.1% fee const fee = 0.001 const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeNotUsedInWei = web3.toBigNumber(web3.toWei(0.5, "ether")) const feeAmount = value.mul(web3.toBigNumber(fee)) const feePerValidator = feeAmount.div(web3.toBigNumber(5)) @@ -788,7 +798,7 @@ contract('HomeBridge', async (accounts) => { const homeBridge = await HomeBridge.new() const feeManager = await FeeManagerNativeToErc.new() await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei).should.be.fulfilled; + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeNotUsedInWei, feeInWei).should.be.fulfilled; await homeBridge.sendTransaction({ from: accounts[0], value: halfEther From 34a4960a469e0f3339ede84281b17c710fc29c04 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Fri, 1 Feb 2019 17:07:43 -0300 Subject: [PATCH 075/187] Update deploy script to use home and foreign fee on rewardableInitialize --- deploy/src/erc_to_native/home.js | 12 ++++++++---- deploy/src/loadEnv.js | 12 ++---------- deploy/src/native_to_erc/foreign.js | 10 +++++++--- deploy/src/native_to_erc/home.js | 12 ++++++++---- 4 files changed, 25 insertions(+), 21 deletions(-) diff --git a/deploy/src/erc_to_native/home.js b/deploy/src/erc_to_native/home.js index e37427a2a..44f9cf724 100644 --- a/deploy/src/erc_to_native/home.js +++ b/deploy/src/erc_to_native/home.js @@ -34,7 +34,8 @@ const { FOREIGN_DAILY_LIMIT, FOREIGN_MAX_AMOUNT_PER_TX, HOME_REWARDABLE, - HOME_TRANSACTIONS_FEE + HOME_TRANSACTIONS_FEE, + FOREIGN_TRANSACTIONS_FEE } = env const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVATE_KEY) @@ -167,7 +168,8 @@ async function deployHome() { console.log('[Home] feeManager Implementation: ', feeManager.options.address) homeNonce++ - const feeInWei = Web3Utils.toWei(HOME_TRANSACTIONS_FEE.toString(), 'ether') + const homeFeeInWei = Web3Utils.toWei(HOME_TRANSACTIONS_FEE.toString(), 'ether') + const foreignFeeInWei = Web3Utils.toWei(FOREIGN_TRANSACTIONS_FEE.toString(), 'ether') console.log('\ninitializing Home Bridge with fee contract:\n') console.log(`Home Validators: ${storageValidatorsHome.options.address}, HOME_DAILY_LIMIT : ${HOME_DAILY_LIMIT} which is ${Web3Utils.fromWei(HOME_DAILY_LIMIT)} in eth, @@ -187,7 +189,8 @@ async function deployHome() { )} in eth, HOME_BRIDGE_OWNER: ${HOME_BRIDGE_OWNER}, Fee Manager: ${feeManager.options.address}, - Fee: ${feeInWei} which is ${HOME_TRANSACTIONS_FEE * 100}%`) + Home Fee: ${homeFeeInWei} which is ${HOME_TRANSACTIONS_FEE * 100}% + Foreign Fee: ${homeFeeInWei} which is ${FOREIGN_TRANSACTIONS_FEE * 100}%`) initializeHomeBridgeData = await homeBridgeImplementation.methods .rewardableInitialize( storageValidatorsHome.options.address, @@ -201,7 +204,8 @@ async function deployHome() { FOREIGN_MAX_AMOUNT_PER_TX, HOME_BRIDGE_OWNER, feeManager.options.address, - feeInWei + homeFeeInWei, + foreignFeeInWei ) .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) } else { diff --git a/deploy/src/loadEnv.js b/deploy/src/loadEnv.js index 12a36fbb4..d95b86f74 100644 --- a/deploy/src/loadEnv.js +++ b/deploy/src/loadEnv.js @@ -114,20 +114,12 @@ if (BRIDGE_MODE === 'ERC_TO_NATIVE') { } } -if (HOME_REWARDABLE === 'true') { - validateRewardableAddresses(VALIDATORS, VALIDATORS_REWARD_ACCOUNTS) - validations = { - ...validations, - VALIDATORS_REWARD_ACCOUNTS: addressesValidator(), - HOME_TRANSACTIONS_FEE: envalid.num() - } -} - -if (FOREIGN_REWARDABLE === 'true') { +if (HOME_REWARDABLE === 'true' || FOREIGN_REWARDABLE === 'true') { validateRewardableAddresses(VALIDATORS, VALIDATORS_REWARD_ACCOUNTS) validations = { ...validations, VALIDATORS_REWARD_ACCOUNTS: addressesValidator(), + HOME_TRANSACTIONS_FEE: envalid.num(), FOREIGN_TRANSACTIONS_FEE: envalid.num() } } diff --git a/deploy/src/native_to_erc/foreign.js b/deploy/src/native_to_erc/foreign.js index 357f113f1..e74587059 100644 --- a/deploy/src/native_to_erc/foreign.js +++ b/deploy/src/native_to_erc/foreign.js @@ -41,6 +41,7 @@ const { BLOCK_REWARD_ADDRESS, DPOS_VALIDATOR_SET_ADDRESS, FOREIGN_REWARDABLE, + HOME_TRANSACTIONS_FEE, FOREIGN_TRANSACTIONS_FEE } = env @@ -210,7 +211,8 @@ async function deployForeign() { console.log('[Foreign] feeManager Implementation: ', feeManager.options.address) foreignNonce++ - const feeInWei = Web3Utils.toWei(FOREIGN_TRANSACTIONS_FEE.toString(), 'ether') + const homeFeeInWei = Web3Utils.toWei(HOME_TRANSACTIONS_FEE.toString(), 'ether') + const foreignFeeInWei = Web3Utils.toWei(FOREIGN_TRANSACTIONS_FEE.toString(), 'ether') console.log('\ninitializing Foreign Bridge with fee contract:\n') console.log(`Foreign Validators: ${storageValidatorsForeign.options.address}, @@ -230,7 +232,8 @@ async function deployForeign() { )} in eth, FOREIGN_BRIDGE_OWNER: ${FOREIGN_BRIDGE_OWNER}, Fee Manager: ${feeManager.options.address}, - Fee: ${feeInWei} which is ${FOREIGN_TRANSACTIONS_FEE * 100}%`) + Home Fee: ${homeFeeInWei} which is ${HOME_TRANSACTIONS_FEE * 100}% + Foreign Fee: ${homeFeeInWei} which is ${FOREIGN_TRANSACTIONS_FEE * 100}%`) initializeFBridgeData = await foreignBridgeImplementation.methods .rewardableInitialize( @@ -245,7 +248,8 @@ async function deployForeign() { HOME_MAX_AMOUNT_PER_TX, FOREIGN_BRIDGE_OWNER, feeManager.options.address, - feeInWei + homeFeeInWei, + foreignFeeInWei ) .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) } else { diff --git a/deploy/src/native_to_erc/home.js b/deploy/src/native_to_erc/home.js index 29e69e8cb..5b37772b6 100644 --- a/deploy/src/native_to_erc/home.js +++ b/deploy/src/native_to_erc/home.js @@ -33,7 +33,8 @@ const { FOREIGN_DAILY_LIMIT, FOREIGN_MAX_AMOUNT_PER_TX, HOME_REWARDABLE, - HOME_TRANSACTIONS_FEE + HOME_TRANSACTIONS_FEE, + FOREIGN_TRANSACTIONS_FEE } = env const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVATE_KEY) @@ -166,7 +167,8 @@ async function deployHome() { console.log('[Home] feeManager Implementation: ', feeManager.options.address) homeNonce++ - const feeInWei = Web3Utils.toWei(HOME_TRANSACTIONS_FEE.toString(), 'ether') + const homeFeeInWei = Web3Utils.toWei(HOME_TRANSACTIONS_FEE.toString(), 'ether') + const foreignFeeInWei = Web3Utils.toWei(FOREIGN_TRANSACTIONS_FEE.toString(), 'ether') console.log('\ninitializing Home Bridge with fee contract:\n') console.log(`Home Validators: ${storageValidatorsHome.options.address}, @@ -186,7 +188,8 @@ async function deployHome() { )} in eth, HOME_BRIDGE_OWNER: ${HOME_BRIDGE_OWNER}, Fee Manager: ${feeManager.options.address}, - Fee: ${feeInWei} which is ${HOME_TRANSACTIONS_FEE * 100}%`) + Home Fee: ${homeFeeInWei} which is ${HOME_TRANSACTIONS_FEE * 100}% + Foreign Fee: ${homeFeeInWei} which is ${FOREIGN_TRANSACTIONS_FEE * 100}%`) homeBridgeImplementation.options.address = homeBridgeStorage.options.address initializeHomeBridgeData = await homeBridgeImplementation.methods @@ -201,7 +204,8 @@ async function deployHome() { FOREIGN_MAX_AMOUNT_PER_TX, HOME_BRIDGE_OWNER, feeManager.options.address, - feeInWei + homeFeeInWei, + foreignFeeInWei ) .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) } else { From 8f13920c5105555199962538e372e59e57d9938e Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Sun, 3 Feb 2019 14:42:35 +0200 Subject: [PATCH 076/187] Update deploy/src/deploymentUtils.js Co-Authored-By: bejavu --- deploy/src/deploymentUtils.js | 1 - 1 file changed, 1 deletion(-) diff --git a/deploy/src/deploymentUtils.js b/deploy/src/deploymentUtils.js index 0a5656fd8..3d06a86fd 100644 --- a/deploy/src/deploymentUtils.js +++ b/deploy/src/deploymentUtils.js @@ -109,7 +109,6 @@ async function sendNodeRequest(url, method, signedData) { }) }) const json = await request.json() - // console.log('json', json) if (method === 'eth_sendRawTransaction') { assert.strictEqual(json.result.length, 66, `Tx wasn't sent ${json}`) } From 715f438326d1eb150c3f5add557b985d22aa9c72 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Sun, 3 Feb 2019 14:43:07 +0200 Subject: [PATCH 077/187] Update deploy/.env.example Co-Authored-By: bejavu --- deploy/.env.example | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/deploy/.env.example b/deploy/.env.example index e1bd1ff47..d5ce11546 100644 --- a/deploy/.env.example +++ b/deploy/.env.example @@ -12,7 +12,7 @@ BRIDGEABLE_TOKEN_DECIMALS=18 HOME_RPC_URL=https://sokol.poa.network # HOME_OWNER_MULTISIG=0x -HOME_BRIDGE_OWNER=0x ## +HOME_BRIDGE_OWNER=0x HOME_VALIDATORS_OWNER=0x ## HOME_FACTORY_OWNER=0x HOME_MAPPER_OWNER=0x From 23683564c51c273bb5c606c7b29007c3eab84368 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Sun, 3 Feb 2019 14:43:17 +0200 Subject: [PATCH 078/187] Update deploy/.env.example Co-Authored-By: bejavu --- deploy/.env.example | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/deploy/.env.example b/deploy/.env.example index d5ce11546..99c39bb72 100644 --- a/deploy/.env.example +++ b/deploy/.env.example @@ -13,7 +13,7 @@ BRIDGEABLE_TOKEN_DECIMALS=18 HOME_RPC_URL=https://sokol.poa.network # HOME_OWNER_MULTISIG=0x HOME_BRIDGE_OWNER=0x -HOME_VALIDATORS_OWNER=0x ## +HOME_VALIDATORS_OWNER=0x HOME_FACTORY_OWNER=0x HOME_MAPPER_OWNER=0x HOME_UPGRADEABLE_ADMIN=0x ## From 90a9f3832bdb36bf408f670ffbcfa0467b34df78 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Sun, 3 Feb 2019 14:43:26 +0200 Subject: [PATCH 079/187] Update deploy/.env.example Co-Authored-By: bejavu --- deploy/.env.example | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/deploy/.env.example b/deploy/.env.example index 99c39bb72..425e6623a 100644 --- a/deploy/.env.example +++ b/deploy/.env.example @@ -16,7 +16,7 @@ HOME_BRIDGE_OWNER=0x HOME_VALIDATORS_OWNER=0x HOME_FACTORY_OWNER=0x HOME_MAPPER_OWNER=0x -HOME_UPGRADEABLE_ADMIN=0x ## +HOME_UPGRADEABLE_ADMIN=0x # HOME_UPGRADEABLE_ADMIN_VALIDATORS=0x # HOME_UPGRADEABLE_ADMIN_BRIDGE=0x # HOME_UPGRADEABLE_ADMIN_FACTORY=0x From 8f8604bde1f5eda30096cc2b9701ce03b99f540c Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Sun, 3 Feb 2019 14:43:43 +0200 Subject: [PATCH 080/187] Update deploy/.env.example Co-Authored-By: bejavu --- deploy/.env.example | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/deploy/.env.example b/deploy/.env.example index 425e6623a..86de6666f 100644 --- a/deploy/.env.example +++ b/deploy/.env.example @@ -31,7 +31,7 @@ HOME_GAS_PRICE=1000000000 BLOCK_REWARD_ADDRESS= FOREIGN_RPC_URL=https://sokol.poa.network -FOREIGN_BRIDGE_OWNER=0x ## +FOREIGN_BRIDGE_OWNER=0x FOREIGN_VALIDATORS_OWNER=0x ## # FOREIGN_OWNER_MULTISIG=0x FOREIGN_FACTORY_OWNER=0x From 9960b72b69b6036e99e3e5d82e9b583cb3d52207 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Sun, 3 Feb 2019 14:43:52 +0200 Subject: [PATCH 081/187] Update deploy/.env.example Co-Authored-By: bejavu --- deploy/.env.example | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/deploy/.env.example b/deploy/.env.example index 86de6666f..5fb7b9b25 100644 --- a/deploy/.env.example +++ b/deploy/.env.example @@ -32,7 +32,7 @@ BLOCK_REWARD_ADDRESS= FOREIGN_RPC_URL=https://sokol.poa.network FOREIGN_BRIDGE_OWNER=0x -FOREIGN_VALIDATORS_OWNER=0x ## +FOREIGN_VALIDATORS_OWNER=0x # FOREIGN_OWNER_MULTISIG=0x FOREIGN_FACTORY_OWNER=0x FOREIGN_UPGRADEABLE_ADMIN=0x ## From 6d6c7b42ecd94bc7b21d18b033ecfdeec590f2e5 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Sun, 3 Feb 2019 14:44:03 +0200 Subject: [PATCH 082/187] Update deploy/.env.example Co-Authored-By: bejavu --- deploy/.env.example | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/deploy/.env.example b/deploy/.env.example index 5fb7b9b25..091776904 100644 --- a/deploy/.env.example +++ b/deploy/.env.example @@ -35,7 +35,7 @@ FOREIGN_BRIDGE_OWNER=0x FOREIGN_VALIDATORS_OWNER=0x # FOREIGN_OWNER_MULTISIG=0x FOREIGN_FACTORY_OWNER=0x -FOREIGN_UPGRADEABLE_ADMIN=0x ## +FOREIGN_UPGRADEABLE_ADMIN=0x # FOREIGN_UPGRADEABLE_ADMIN_VALIDATORS=0x # FOREIGN_UPGRADEABLE_ADMIN_BRIDGE=0x # FOREIGN_UPGRADEABLE_ADMIN_FACTORY=0x From f822d5f5cba6f6a877605489ecefa7202ad8dadb Mon Sep 17 00:00:00 2001 From: Tal Beja Date: Sun, 3 Feb 2019 16:28:39 +0200 Subject: [PATCH 083/187] * add initialize checkers to the factories and mapper contracts * set owner to be `msg.sender` at the start of the initialize method and then to the `_owner` param to alow setting deferent owner then `msg.sender` * update the .env.example file to support the new variables and remove the redundet ones. * extract similar logic from the factories to a new `BasicBridgeFactory` contract. * update deply readme. --- .../upgradeable_contracts/BridgeMapper.sol | 13 +- .../factories/BasicBridgeFactory.sol | 101 ++++++ .../factories/ForeignBridgeFactory.sol | 284 ++++++--------- .../factories/HomeBridgeFactory.sol | 336 +++++++----------- deploy/.env.example | 15 +- deploy/README.md | 102 ++++++ 6 files changed, 449 insertions(+), 402 deletions(-) create mode 100644 contracts/upgradeable_contracts/factories/BasicBridgeFactory.sol diff --git a/contracts/upgradeable_contracts/BridgeMapper.sol b/contracts/upgradeable_contracts/BridgeMapper.sol index eaa9b11ca..f3b1e9f7f 100644 --- a/contracts/upgradeable_contracts/BridgeMapper.sol +++ b/contracts/upgradeable_contracts/BridgeMapper.sol @@ -48,6 +48,14 @@ contract BridgeMapper is EternalStorage, EternalOwnable { uintStorage[keccak256(abi.encodePacked("foreignStartBlockByForeignToken", _foreignToken))] = _foreignStartBlock; } + function setInitialize(bool _status) internal { + boolStorage[keccak256(abi.encodePacked("isInitialized"))] = _status; + } + + function isInitialized() public view returns(bool) { + return boolStorage[keccak256(abi.encodePacked("isInitialized"))]; + } + function addBridgeMapping(address _foreignToken, address _homeToken, address _foreignBridge, address _homeBridge, uint256 _foreignStartBlock, uint256 _homeStartBlock) public onlyOwner { require(_foreignToken != address(0)); require(_homeToken != address(0)); @@ -77,8 +85,11 @@ contract BridgeMapper is EternalStorage, EternalOwnable { return (2, 2, 0); } - function initialize(address _owner) public { + function initialize(address _owner) public returns(bool) { + require(!isInitialized()); setOwner(_owner); + setInitialize(true); + return isInitialized(); } } \ No newline at end of file diff --git a/contracts/upgradeable_contracts/factories/BasicBridgeFactory.sol b/contracts/upgradeable_contracts/factories/BasicBridgeFactory.sol new file mode 100644 index 000000000..f16da02e8 --- /dev/null +++ b/contracts/upgradeable_contracts/factories/BasicBridgeFactory.sol @@ -0,0 +1,101 @@ +pragma solidity 0.4.24; + +import "../../upgradeability/EternalStorage.sol"; +import "../EternalOwnable.sol"; + +contract BasicBridgeFactory is EternalStorage, EternalOwnable { + + function getBridgeFactoryVersion() public pure returns(uint64 major, uint64 minor, uint64 patch) { + return (2, 2, 0); + } + + function bridgeValidatorsImplementation() public view returns(address) { + return addressStorage[keccak256(abi.encodePacked("bridgeValidatorsImplementation"))]; + } + + function setBridgeValidatorsImplementation(address _bridgeValidatorsImplementation) public onlyOwner { + addressStorage[keccak256(abi.encodePacked("bridgeValidatorsImplementation"))] = _bridgeValidatorsImplementation; + } + + function requiredSignatures() public view returns(uint256) { + return uintStorage[keccak256(abi.encodePacked("requiredSignatures"))]; + } + + function setRequiredSignatures(uint256 _requiredSignatures) public onlyOwner { + require(initialValidators().length >= _requiredSignatures); + uintStorage[keccak256(abi.encodePacked("requiredSignatures"))] = _requiredSignatures; + } + + function initialValidators() public view returns(address[]) { + return addressArrayStorage[keccak256(abi.encodePacked("initialValidators"))]; + } + + function setInitialValidators(address[] _initialValidators) public onlyOwner { + require(_initialValidators.length >= requiredSignatures()); + addressArrayStorage[keccak256(abi.encodePacked("initialValidators"))] = _initialValidators; + } + + function bridgeValidatorsOwner() public view returns(address) { + return addressStorage[keccak256(abi.encodePacked("bridgeValidatorsOwner"))]; + } + + function setBridgeValidatorsOwner(address _bridgeValidatorsOwner) public onlyOwner { + addressStorage[keccak256(abi.encodePacked("bridgeValidatorsOwner"))] = _bridgeValidatorsOwner; + } + + function bridgeValidatorsProxyOwner() public view returns(address) { + return addressStorage[keccak256(abi.encodePacked("bridgeValidatorsProxyOwner"))]; + } + + function setBridgeValidatorsProxyOwner(address _bridgeValidatorsProxyOwner) public onlyOwner { + addressStorage[keccak256(abi.encodePacked("bridgeValidatorsProxyOwner"))] = _bridgeValidatorsProxyOwner; + } + + function requiredBlockConfirmations() public view returns(uint256) { + return uintStorage[keccak256(abi.encodePacked("requiredBlockConfirmations"))]; + } + + function setRequiredBlockConfirmations(uint256 _requiredBlockConfirmations) public onlyOwner { + uintStorage[keccak256(abi.encodePacked("requiredBlockConfirmations"))] = _requiredBlockConfirmations; + } + + function gasPrice() public view returns(uint256) { + return uintStorage[keccak256(abi.encodePacked("gasPrice"))]; + } + + function setGasPrice(uint256 _gasPrice) public onlyOwner { + uintStorage[keccak256(abi.encodePacked("gasPrice"))] = _gasPrice; + } + + function homeDailyLimit() public view returns(uint256) { + return uintStorage[keccak256(abi.encodePacked("homeDailyLimit"))]; + } + + function setHomeDailyLimit(uint256 _homeDailyLimit) public onlyOwner { + uintStorage[keccak256(abi.encodePacked("homeDailyLimit"))] = _homeDailyLimit; + } + + function homeMaxPerTx() public view returns(uint256) { + return uintStorage[keccak256(abi.encodePacked("homeMaxPerTx"))]; + } + + function setHomeMaxPerTx(uint256 _homeMaxPerTx) public onlyOwner { + uintStorage[keccak256(abi.encodePacked("homeMaxPerTx"))] = _homeMaxPerTx; + } + + function foreignMaxPerTx() public view returns(uint256) { + return uintStorage[keccak256(abi.encodePacked("foreignMaxPerTx"))]; + } + + function setForeignMaxPerTx(uint256 _foreignMaxPerTx) public onlyOwner { + uintStorage[keccak256(abi.encodePacked("foreignMaxPerTx"))] = _foreignMaxPerTx; + } + + function setInitialize(bool _status) internal { + boolStorage[keccak256(abi.encodePacked("isInitialized"))] = _status; + } + + function isInitialized() public view returns(bool) { + return boolStorage[keccak256(abi.encodePacked("isInitialized"))]; + } +} \ No newline at end of file diff --git a/contracts/upgradeable_contracts/factories/ForeignBridgeFactory.sol b/contracts/upgradeable_contracts/factories/ForeignBridgeFactory.sol index 6db24efbd..b2f754659 100644 --- a/contracts/upgradeable_contracts/factories/ForeignBridgeFactory.sol +++ b/contracts/upgradeable_contracts/factories/ForeignBridgeFactory.sol @@ -3,187 +3,105 @@ pragma solidity 0.4.24; import "../../IBridgeValidators.sol"; import "../../IForeignBridge.sol"; import "../../upgradeability/EternalStorageProxy.sol"; -import "../../upgradeability/EternalStorage.sol"; -import "../EternalOwnable.sol"; - -contract ForeignBridgeFactory is EternalStorage, EternalOwnable { - - event ForeignBridgeDeployed(address indexed _foreignBridge, address indexed _foreignValidators, uint256 _blockNumber); - - function getBridgeFactoryVersion() public pure returns(uint64 major, uint64 minor, uint64 patch) { - return (2, 2, 0); - } - - function initialize(address _owner, - address _bridgeValidatorsImplementation, - uint256 _requiredSignatures, - address[] _initialValidators, - address _bridgeValidatorsOwner, - address _foreignBridgeErcToErcImplementation, - uint256 _requiredBlockConfirmations, - uint256 _gasPrice, - uint256 _foreignMaxPerTx, - uint256 _homeDailyLimit, - uint256 _homeMaxPerTx, - address _foreignBridgeOwner, - address _foreignProxyOwner) public { - - - require(_owner != address(0)); - require(_bridgeValidatorsImplementation != address(0)); - require(_requiredSignatures >= 1); - require(_bridgeValidatorsOwner != address(0)); - require(_foreignBridgeErcToErcImplementation != address(0)); - require(_requiredBlockConfirmations != 0); - require(_gasPrice > 0); - require(_foreignMaxPerTx >= 0); - require(_homeMaxPerTx < _homeDailyLimit); - require(_foreignBridgeOwner != address(0)); - require(_foreignProxyOwner != address(0)); - - setOwner(_owner); - setBridgeValidatorsImplementation(_bridgeValidatorsImplementation); - setRequiredSignatures(_requiredSignatures); - setInitialValidators(_initialValidators); - setBridgeValidatorsOwner(_bridgeValidatorsOwner); - setBridgeValidatorsProxyOwner(_foreignProxyOwner); - setForeignBridgeErcToErcImplementation(_foreignBridgeErcToErcImplementation); - setRequiredBlockConfirmations(_requiredBlockConfirmations); - setGasPrice(_gasPrice); - setForeignMaxPerTx(_foreignMaxPerTx); - setHomeDailyLimit(_homeDailyLimit); - setHomeMaxPerTx(_homeMaxPerTx); - setForeignBridgeOwner(_foreignBridgeOwner); - setForeignBridgeProxyOwner(_foreignProxyOwner); - } - - function deployForeignBridge(address _erc20Token) public onlyOwner { - // deploy new EternalStorageProxy - EternalStorageProxy proxy = new EternalStorageProxy(); - // connect it to the static BridgeValidators implementation - proxy.upgradeTo(1, bridgeValidatorsImplementation()); - // cast proxy as IBridgeValidators - IBridgeValidators bridgeValidators = IBridgeValidators(proxy); - // initialize bridgeValidators - bridgeValidators.initialize(requiredSignatures(), initialValidators(), bridgeValidatorsOwner()); - // transger proxy upgradeability admin - proxy.transferProxyOwnership(bridgeValidatorsProxyOwner()); - // deploy new EternalStorageProxy - proxy = new EternalStorageProxy(); - // connect it to the static ForeignBridgeErcToErc implementation - proxy.upgradeTo(1, foreignBridgeErcToErcImplementation()); - // cast proxy as IForeignBridge - IForeignBridge foreignBridge = IForeignBridge(proxy); - // initialize foreignBridge - foreignBridge.initialize(bridgeValidators, _erc20Token, requiredBlockConfirmations(), gasPrice(), foreignMaxPerTx(), homeDailyLimit(), homeMaxPerTx(), foreignBridgeOwner()); - // transger proxy upgradeability admin - proxy.transferProxyOwnership(foreignBridgeProxyOwner()); - // emit event - emit ForeignBridgeDeployed(foreignBridge, bridgeValidators, block.number); - } - - - function bridgeValidatorsImplementation() public view returns(address) { - return addressStorage[keccak256(abi.encodePacked("bridgeValidatorsImplementation"))]; - } - - function setBridgeValidatorsImplementation(address _bridgeValidatorsImplementation) public onlyOwner { - addressStorage[keccak256(abi.encodePacked("bridgeValidatorsImplementation"))] = _bridgeValidatorsImplementation; - } - - function requiredSignatures() public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("requiredSignatures"))]; - } - - function setRequiredSignatures(uint256 _requiredSignatures) public onlyOwner { - uintStorage[keccak256(abi.encodePacked("requiredSignatures"))] = _requiredSignatures; - } - - function initialValidators() public view returns(address[]) { - return addressArrayStorage[keccak256(abi.encodePacked("initialValidators"))]; - } - - function setInitialValidators(address[] _initialValidators) public onlyOwner { - addressArrayStorage[keccak256(abi.encodePacked("initialValidators"))] = _initialValidators; - } - - function bridgeValidatorsOwner() public view returns(address) { - return addressStorage[keccak256(abi.encodePacked("bridgeValidatorsOwner"))]; - } - - function setBridgeValidatorsOwner(address _bridgeValidatorsOwner) public onlyOwner { - addressStorage[keccak256(abi.encodePacked("bridgeValidatorsOwner"))] = _bridgeValidatorsOwner; - } - - function bridgeValidatorsProxyOwner() public view returns(address) { - return addressStorage[keccak256(abi.encodePacked("bridgeValidatorsProxyOwner"))]; - } - - function setBridgeValidatorsProxyOwner(address _bridgeValidatorsProxyOwner) public onlyOwner { - addressStorage[keccak256(abi.encodePacked("bridgeValidatorsProxyOwner"))] = _bridgeValidatorsProxyOwner; - } - - function foreignBridgeErcToErcImplementation() public view returns(address) { - return addressStorage[keccak256(abi.encodePacked("foreignBridgeErcToErcImplementation"))]; - } - - function setForeignBridgeErcToErcImplementation(address _foreignBridgeErcToErcImplementation) public onlyOwner { - addressStorage[keccak256(abi.encodePacked("foreignBridgeErcToErcImplementation"))] = _foreignBridgeErcToErcImplementation; - } - - function requiredBlockConfirmations() public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("requiredBlockConfirmations"))]; - } - - function setRequiredBlockConfirmations(uint256 _requiredBlockConfirmations) public onlyOwner { - uintStorage[keccak256(abi.encodePacked("requiredBlockConfirmations"))] = _requiredBlockConfirmations; - } - - function gasPrice() public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("gasPrice"))]; - } - - function setGasPrice(uint256 _gasPrice) public onlyOwner { - uintStorage[keccak256(abi.encodePacked("gasPrice"))] = _gasPrice; - } - - function foreignMaxPerTx() public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("foreignMaxPerTx"))]; - } - - function setForeignMaxPerTx(uint256 _foreignMaxPerTx) public onlyOwner { - uintStorage[keccak256(abi.encodePacked("foreignMaxPerTx"))] = _foreignMaxPerTx; - } - - function homeDailyLimit() public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("homeDailyLimit"))]; - } - - function setHomeDailyLimit(uint256 _homeDailyLimit) public onlyOwner { - uintStorage[keccak256(abi.encodePacked("homeDailyLimit"))] = _homeDailyLimit; - } - - function homeMaxPerTx() public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("homeMaxPerTx"))]; - } - - function setHomeMaxPerTx(uint256 _homeMaxPerTx) public onlyOwner { - uintStorage[keccak256(abi.encodePacked("homeMaxPerTx"))] = _homeMaxPerTx; - } - - function foreignBridgeOwner() public view returns(address) { - return addressStorage[keccak256(abi.encodePacked("foreignBridgeOwner"))]; - } - - function setForeignBridgeOwner(address _foreignBridgeOwner) public onlyOwner { - addressStorage[keccak256(abi.encodePacked("foreignBridgeOwner"))] = _foreignBridgeOwner; - } - - function foreignBridgeProxyOwner() public view returns(address) { - return addressStorage[keccak256(abi.encodePacked("foreignBridgeProxyOwner"))]; - } - - function setForeignBridgeProxyOwner(address _foreignBridgeProxyOwner) public onlyOwner { - addressStorage[keccak256(abi.encodePacked("foreignBridgeProxyOwner"))] = _foreignBridgeProxyOwner; - } +import "./BasicBridgeFactory.sol"; + +contract ForeignBridgeFactory is BasicBridgeFactory { + + event ForeignBridgeDeployed(address indexed _foreignBridge, address indexed _foreignValidators, uint256 _blockNumber); + + function initialize(address _owner, + address _bridgeValidatorsImplementation, + uint256 _requiredSignatures, + address[] _initialValidators, + address _bridgeValidatorsOwner, + address _foreignBridgeErcToErcImplementation, + uint256 _requiredBlockConfirmations, + uint256 _gasPrice, + uint256 _foreignMaxPerTx, + uint256 _homeDailyLimit, + uint256 _homeMaxPerTx, + address _foreignBridgeOwner, + address _foreignProxyOwner) public returns(bool) { + + require(!isInitialized()); + require(_owner != address(0)); + require(_bridgeValidatorsImplementation != address(0)); + require(_requiredSignatures >= 1); + require(_bridgeValidatorsOwner != address(0)); + require(_foreignBridgeErcToErcImplementation != address(0)); + require(_requiredBlockConfirmations != 0); + require(_gasPrice > 0); + require(_foreignMaxPerTx >= 0); + require(_homeMaxPerTx < _homeDailyLimit); + require(_foreignBridgeOwner != address(0)); + require(_foreignProxyOwner != address(0)); + require(_initialValidators.length >= _requiredSignatures); + + setOwner(msg.sender); // set just to have access to the setters. + setBridgeValidatorsImplementation(_bridgeValidatorsImplementation); + setInitialValidators(_initialValidators); + setRequiredSignatures(_requiredSignatures); + setBridgeValidatorsOwner(_bridgeValidatorsOwner); + setBridgeValidatorsProxyOwner(_foreignProxyOwner); + setForeignBridgeErcToErcImplementation(_foreignBridgeErcToErcImplementation); + setRequiredBlockConfirmations(_requiredBlockConfirmations); + setGasPrice(_gasPrice); + setForeignMaxPerTx(_foreignMaxPerTx); + setHomeDailyLimit(_homeDailyLimit); + setHomeMaxPerTx(_homeMaxPerTx); + setForeignBridgeOwner(_foreignBridgeOwner); + setForeignBridgeProxyOwner(_foreignProxyOwner); + setInitialize(true); + setOwner(_owner); // set to the real owner. + return isInitialized(); + } + + function deployForeignBridge(address _erc20Token) public onlyOwner { + // deploy new EternalStorageProxy + EternalStorageProxy proxy = new EternalStorageProxy(); + // connect it to the static BridgeValidators implementation + proxy.upgradeTo(1, bridgeValidatorsImplementation()); + // cast proxy as IBridgeValidators + IBridgeValidators bridgeValidators = IBridgeValidators(proxy); + // initialize bridgeValidators + bridgeValidators.initialize(requiredSignatures(), initialValidators(), bridgeValidatorsOwner()); + // transger proxy upgradeability admin + proxy.transferProxyOwnership(bridgeValidatorsProxyOwner()); + // deploy new EternalStorageProxy + proxy = new EternalStorageProxy(); + // connect it to the static ForeignBridgeErcToErc implementation + proxy.upgradeTo(1, foreignBridgeErcToErcImplementation()); + // cast proxy as IForeignBridge + IForeignBridge foreignBridge = IForeignBridge(proxy); + // initialize foreignBridge + foreignBridge.initialize(bridgeValidators, _erc20Token, requiredBlockConfirmations(), gasPrice(), foreignMaxPerTx(), homeDailyLimit(), homeMaxPerTx(), foreignBridgeOwner()); + // transger proxy upgradeability admin + proxy.transferProxyOwnership(foreignBridgeProxyOwner()); + // emit event + emit ForeignBridgeDeployed(foreignBridge, bridgeValidators, block.number); + } + + function foreignBridgeErcToErcImplementation() public view returns(address) { + return addressStorage[keccak256(abi.encodePacked("foreignBridgeErcToErcImplementation"))]; + } + + function setForeignBridgeErcToErcImplementation(address _foreignBridgeErcToErcImplementation) public onlyOwner { + addressStorage[keccak256(abi.encodePacked("foreignBridgeErcToErcImplementation"))] = _foreignBridgeErcToErcImplementation; + } + + function foreignBridgeOwner() public view returns(address) { + return addressStorage[keccak256(abi.encodePacked("foreignBridgeOwner"))]; + } + + function setForeignBridgeOwner(address _foreignBridgeOwner) public onlyOwner { + addressStorage[keccak256(abi.encodePacked("foreignBridgeOwner"))] = _foreignBridgeOwner; + } + + function foreignBridgeProxyOwner() public view returns(address) { + return addressStorage[keccak256(abi.encodePacked("foreignBridgeProxyOwner"))]; + } + + function setForeignBridgeProxyOwner(address _foreignBridgeProxyOwner) public onlyOwner { + addressStorage[keccak256(abi.encodePacked("foreignBridgeProxyOwner"))] = _foreignBridgeProxyOwner; + } } \ No newline at end of file diff --git a/contracts/upgradeable_contracts/factories/HomeBridgeFactory.sol b/contracts/upgradeable_contracts/factories/HomeBridgeFactory.sol index e065200ca..efdeee6ed 100644 --- a/contracts/upgradeable_contracts/factories/HomeBridgeFactory.sol +++ b/contracts/upgradeable_contracts/factories/HomeBridgeFactory.sol @@ -3,214 +3,132 @@ pragma solidity 0.4.24; import "../../IBridgeValidators.sol"; import "../../IHomeBridge.sol"; import "../../upgradeability/EternalStorageProxy.sol"; -import "../../upgradeability/EternalStorage.sol"; import "../../ERC677BridgeToken.sol"; -import "../EternalOwnable.sol"; - -contract HomeBridgeFactory is EternalStorage, EternalOwnable { - - event HomeBridgeDeployed(address indexed _homeBridge, address indexed _homeValidators, address indexed _token, uint256 _blockNumber); - - function getBridgeFactoryVersion() public pure returns(uint64 major, uint64 minor, uint64 patch) { - return (2, 2, 0); - } - - function initialize(address _owner, - address _bridgeValidatorsImplementation, - uint256 _requiredSignatures, - address[] _initialValidators, - address _bridgeValidatorsOwner, - address _homeBridgeErcToErcImplementation, - uint256 _requiredBlockConfirmations, - uint256 _gasPrice, - uint256 _dailyLimit, - uint256 _maxPerTx, - uint256 _minPerTx, - uint256 _foreignDailyLimit, - uint256 _foreignMaxPerTx, - address _homeBridgeOwner, - address _homeProxyOwner) public { - - - require(_owner != address(0)); - require(_bridgeValidatorsImplementation != address(0)); - require(_requiredSignatures >= 1); - require(_bridgeValidatorsOwner != address(0)); - require(_homeBridgeErcToErcImplementation != address(0)); - require(_gasPrice > 0); - require(_requiredBlockConfirmations > 0); - require(_minPerTx > 0 && _maxPerTx > _minPerTx && _dailyLimit > _maxPerTx); - require(_foreignMaxPerTx < _foreignDailyLimit); - require(_homeBridgeOwner != address(0)); - require(_homeProxyOwner != address(0)); - - setOwner(_owner); - setBridgeValidatorsImplementation(_bridgeValidatorsImplementation); - setRequiredSignatures(_requiredSignatures); - setInitialValidators(_initialValidators); - setBridgeValidatorsOwner(_bridgeValidatorsOwner); - setBridgeValidatorsProxyOwner(_homeProxyOwner); - setHomeBridgeErcToErcImplementation(_homeBridgeErcToErcImplementation); - setRequiredBlockConfirmations(_requiredBlockConfirmations); - setGasPrice(_gasPrice); - setDailyLimit(_dailyLimit); - setMaxPerTx(_maxPerTx); - setMinPerTx(_minPerTx); - setForeignDailyLimit(_foreignDailyLimit); - setForeignMaxPerTx(_foreignMaxPerTx); - setHomeBridgeOwner(_homeBridgeOwner); - setHomeBridgeProxyOwner(_homeProxyOwner); - } - - function deployHomeBridge(string _tokenName, string _tokenSymbol, uint8 _tokenDecimals) public onlyOwner { - // deploy new EternalStorageProxy - EternalStorageProxy proxy = new EternalStorageProxy(); - // connect it to the static BridgeValidators implementation - proxy.upgradeTo(1, bridgeValidatorsImplementation()); - // cast proxy as IBridgeValidators - IBridgeValidators bridgeValidators = IBridgeValidators(proxy); - // initialize bridgeValidators - bridgeValidators.initialize(requiredSignatures(), initialValidators(), bridgeValidatorsOwner()); - // transger proxy upgradeability admin - proxy.transferProxyOwnership(bridgeValidatorsProxyOwner()); - // deploy new EternalStorageProxy - proxy = new EternalStorageProxy(); - // connect it to the static homeBridgeErcToErc implementation - proxy.upgradeTo(1, homeBridgeErcToErcImplementation()); - // deploy erc677 token bridge token - ERC677BridgeToken token = new ERC677BridgeToken(_tokenName, _tokenSymbol, _tokenDecimals); - // set token bridge contract - token.setBridgeContract(proxy); - // transger token ownership to the bridge - token.transferOwnership(proxy); - // cast proxy as IHomeBridge - IHomeBridge homeBridge = IHomeBridge(proxy); - // initialize homeBridge - homeBridge.initialize(bridgeValidators, dailyLimit(), maxPerTx(), minPerTx(), gasPrice(), requiredBlockConfirmations(), token, foreignDailyLimit(), foreignMaxPerTx(), homeBridgeOwner()); - // transger proxy upgradeability admin - proxy.transferProxyOwnership(homeBridgeProxyOwner()); - // emit event - emit HomeBridgeDeployed(homeBridge, bridgeValidators, token, block.number); - } - - - function bridgeValidatorsImplementation() public view returns(address) { - return addressStorage[keccak256(abi.encodePacked("bridgeValidatorsImplementation"))]; - } - - function setBridgeValidatorsImplementation(address _bridgeValidatorsImplementation) public onlyOwner { - addressStorage[keccak256(abi.encodePacked("bridgeValidatorsImplementation"))] = _bridgeValidatorsImplementation; - } - - function requiredSignatures() public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("requiredSignatures"))]; - } - - function setRequiredSignatures(uint256 _requiredSignatures) public onlyOwner { - uintStorage[keccak256(abi.encodePacked("requiredSignatures"))] = _requiredSignatures; - } - - function initialValidators() public view returns(address[]) { - return addressArrayStorage[keccak256(abi.encodePacked("initialValidators"))]; - } - - function setInitialValidators(address[] _initialValidators) public onlyOwner { - addressArrayStorage[keccak256(abi.encodePacked("initialValidators"))] = _initialValidators; - } - - function bridgeValidatorsOwner() public view returns(address) { - return addressStorage[keccak256(abi.encodePacked("bridgeValidatorsOwner"))]; - } - - function setBridgeValidatorsOwner(address _bridgeValidatorsOwner) public onlyOwner { - addressStorage[keccak256(abi.encodePacked("bridgeValidatorsOwner"))] = _bridgeValidatorsOwner; - } - - function bridgeValidatorsProxyOwner() public view returns(address) { - return addressStorage[keccak256(abi.encodePacked("bridgeValidatorsProxyOwner"))]; - } - - function setBridgeValidatorsProxyOwner(address _bridgeValidatorsProxyOwner) public onlyOwner { - addressStorage[keccak256(abi.encodePacked("bridgeValidatorsProxyOwner"))] = _bridgeValidatorsProxyOwner; - } - - function homeBridgeErcToErcImplementation() public view returns(address) { - return addressStorage[keccak256(abi.encodePacked("homeBridgeErcToErcImplementation"))]; - } - - function setHomeBridgeErcToErcImplementation(address _homeBridgeErcToErcImplementation) public onlyOwner { - addressStorage[keccak256(abi.encodePacked("homeBridgeErcToErcImplementation"))] = _homeBridgeErcToErcImplementation; - } - - function requiredBlockConfirmations() public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("requiredBlockConfirmations"))]; - } - - function setRequiredBlockConfirmations(uint256 _requiredBlockConfirmations) public onlyOwner { - uintStorage[keccak256(abi.encodePacked("requiredBlockConfirmations"))] = _requiredBlockConfirmations; - } - - function gasPrice() public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("gasPrice"))]; - } - - function setGasPrice(uint256 _gasPrice) public onlyOwner { - uintStorage[keccak256(abi.encodePacked("gasPrice"))] = _gasPrice; - } - - function dailyLimit() public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("dailyLimit"))]; - } - - function setDailyLimit(uint256 _dailyLimit) public onlyOwner { - uintStorage[keccak256(abi.encodePacked("dailyLimit"))] = _dailyLimit; - } - - function maxPerTx() public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("maxPerTx"))]; - } - - function setMaxPerTx(uint256 _maxPerTx) public onlyOwner { - uintStorage[keccak256(abi.encodePacked("maxPerTx"))] = _maxPerTx; - } - - function minPerTx() public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("minPerTx"))]; - } - - function setMinPerTx(uint256 _minPerTx) public onlyOwner { - uintStorage[keccak256(abi.encodePacked("minPerTx"))] = _minPerTx; - } - - function foreignDailyLimit() public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("foreignDailyLimit"))]; - } - - function setForeignDailyLimit(uint256 _foreignDailyLimit) public onlyOwner { - uintStorage[keccak256(abi.encodePacked("foreignDailyLimit"))] = _foreignDailyLimit; - } - - function foreignMaxPerTx() public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("foreignMaxPerTx"))]; - } - - function setForeignMaxPerTx(uint256 _foreignMaxPerTx) public onlyOwner { - uintStorage[keccak256(abi.encodePacked("foreignMaxPerTx"))] = _foreignMaxPerTx; - } - - function homeBridgeOwner() public view returns(address) { - return addressStorage[keccak256(abi.encodePacked("homeBridgeOwner"))]; - } - - function setHomeBridgeOwner(address _homeBridgeOwner) public onlyOwner { - addressStorage[keccak256(abi.encodePacked("homeBridgeOwner"))] = _homeBridgeOwner; - } - - function homeBridgeProxyOwner() public view returns(address) { - return addressStorage[keccak256(abi.encodePacked("homeBridgeProxyOwner"))]; - } - - function setHomeBridgeProxyOwner(address _homeBridgeProxyOwner) public onlyOwner { - addressStorage[keccak256(abi.encodePacked("homeBridgeProxyOwner"))] = _homeBridgeProxyOwner; - } +import "./BasicBridgeFactory.sol"; + +contract HomeBridgeFactory is BasicBridgeFactory { + + event HomeBridgeDeployed(address indexed _homeBridge, address indexed _homeValidators, address indexed _token, uint256 _blockNumber); + + function initialize(address _owner, + address _bridgeValidatorsImplementation, + uint256 _requiredSignatures, + address[] _initialValidators, + address _bridgeValidatorsOwner, + address _homeBridgeErcToErcImplementation, + uint256 _requiredBlockConfirmations, + uint256 _gasPrice, + uint256 _homeDailyLimit, + uint256 _homeMaxPerTx, + uint256 _minPerTx, + uint256 _foreignDailyLimit, + uint256 _foreignMaxPerTx, + address _homeBridgeOwner, + address _homeProxyOwner) public { + + + require(!isInitialized()); + require(_owner != address(0)); + require(_bridgeValidatorsImplementation != address(0)); + require(_requiredSignatures >= 1); + require(_bridgeValidatorsOwner != address(0)); + require(_homeBridgeErcToErcImplementation != address(0)); + require(_gasPrice > 0); + require(_requiredBlockConfirmations > 0); + require(_minPerTx > 0 && _homeMaxPerTx > _minPerTx && _homeDailyLimit > _homeMaxPerTx); + require(_foreignMaxPerTx < _foreignDailyLimit); + require(_homeBridgeOwner != address(0)); + require(_homeProxyOwner != address(0)); + require(_initialValidators.length >= _requiredSignatures); + + setOwner(msg.sender); // set just to have access to the setters. + setBridgeValidatorsImplementation(_bridgeValidatorsImplementation); + setInitialValidators(_initialValidators); + setRequiredSignatures(_requiredSignatures); + setBridgeValidatorsOwner(_bridgeValidatorsOwner); + setBridgeValidatorsProxyOwner(_homeProxyOwner); + setHomeBridgeErcToErcImplementation(_homeBridgeErcToErcImplementation); + setRequiredBlockConfirmations(_requiredBlockConfirmations); + setGasPrice(_gasPrice); + setHomeDailyLimit(_homeDailyLimit); + setHomeMaxPerTx(_homeMaxPerTx); + setMinPerTx(_minPerTx); + setForeignDailyLimit(_foreignDailyLimit); + setForeignMaxPerTx(_foreignMaxPerTx); + setHomeBridgeOwner(_homeBridgeOwner); + setHomeBridgeProxyOwner(_homeProxyOwner); + setInitialize(true); + setOwner(_owner); // set to the real owner. + } + + function deployHomeBridge(string _tokenName, string _tokenSymbol, uint8 _tokenDecimals) public onlyOwner { + // deploy new EternalStorageProxy + EternalStorageProxy proxy = new EternalStorageProxy(); + // connect it to the static BridgeValidators implementation + proxy.upgradeTo(1, bridgeValidatorsImplementation()); + // cast proxy as IBridgeValidators + IBridgeValidators bridgeValidators = IBridgeValidators(proxy); + // initialize bridgeValidators + bridgeValidators.initialize(requiredSignatures(), initialValidators(), bridgeValidatorsOwner()); + // transger proxy upgradeability admin + proxy.transferProxyOwnership(bridgeValidatorsProxyOwner()); + // deploy new EternalStorageProxy + proxy = new EternalStorageProxy(); + // connect it to the static homeBridgeErcToErc implementation + proxy.upgradeTo(1, homeBridgeErcToErcImplementation()); + // deploy erc677 token bridge token + ERC677BridgeToken token = new ERC677BridgeToken(_tokenName, _tokenSymbol, _tokenDecimals); + // set token bridge contract + token.setBridgeContract(proxy); + // transger token ownership to the bridge + token.transferOwnership(proxy); + // cast proxy as IHomeBridge + IHomeBridge homeBridge = IHomeBridge(proxy); + // initialize homeBridge + homeBridge.initialize(bridgeValidators, homeDailyLimit(), homeMaxPerTx(), minPerTx(), gasPrice(), requiredBlockConfirmations(), token, foreignDailyLimit(), foreignMaxPerTx(), homeBridgeOwner()); + // transger proxy upgradeability admin + proxy.transferProxyOwnership(homeBridgeProxyOwner()); + // emit event + emit HomeBridgeDeployed(homeBridge, bridgeValidators, token, block.number); + } + + function homeBridgeErcToErcImplementation() public view returns(address) { + return addressStorage[keccak256(abi.encodePacked("homeBridgeErcToErcImplementation"))]; + } + + function setHomeBridgeErcToErcImplementation(address _homeBridgeErcToErcImplementation) public onlyOwner { + addressStorage[keccak256(abi.encodePacked("homeBridgeErcToErcImplementation"))] = _homeBridgeErcToErcImplementation; + } + + function minPerTx() public view returns(uint256) { + return uintStorage[keccak256(abi.encodePacked("minPerTx"))]; + } + + function setMinPerTx(uint256 _minPerTx) public onlyOwner { + uintStorage[keccak256(abi.encodePacked("minPerTx"))] = _minPerTx; + } + + function foreignDailyLimit() public view returns(uint256) { + return uintStorage[keccak256(abi.encodePacked("foreignDailyLimit"))]; + } + + function setForeignDailyLimit(uint256 _foreignDailyLimit) public onlyOwner { + uintStorage[keccak256(abi.encodePacked("foreignDailyLimit"))] = _foreignDailyLimit; + } + + function homeBridgeOwner() public view returns(address) { + return addressStorage[keccak256(abi.encodePacked("homeBridgeOwner"))]; + } + + function setHomeBridgeOwner(address _homeBridgeOwner) public onlyOwner { + addressStorage[keccak256(abi.encodePacked("homeBridgeOwner"))] = _homeBridgeOwner; + } + + function homeBridgeProxyOwner() public view returns(address) { + return addressStorage[keccak256(abi.encodePacked("homeBridgeProxyOwner"))]; + } + + function setHomeBridgeProxyOwner(address _homeBridgeProxyOwner) public onlyOwner { + addressStorage[keccak256(abi.encodePacked("homeBridgeProxyOwner"))] = _homeBridgeProxyOwner; + } } \ No newline at end of file diff --git a/deploy/.env.example b/deploy/.env.example index 091776904..c31ef42b3 100644 --- a/deploy/.env.example +++ b/deploy/.env.example @@ -11,16 +11,11 @@ BRIDGEABLE_TOKEN_SYMBOL=TEST BRIDGEABLE_TOKEN_DECIMALS=18 HOME_RPC_URL=https://sokol.poa.network -# HOME_OWNER_MULTISIG=0x HOME_BRIDGE_OWNER=0x HOME_VALIDATORS_OWNER=0x HOME_FACTORY_OWNER=0x HOME_MAPPER_OWNER=0x HOME_UPGRADEABLE_ADMIN=0x -# HOME_UPGRADEABLE_ADMIN_VALIDATORS=0x -# HOME_UPGRADEABLE_ADMIN_BRIDGE=0x -# HOME_UPGRADEABLE_ADMIN_FACTORY=0x -# HOME_UPGRADEABLE_ADMIN_MAPPER=0x HOME_DAILY_LIMIT=30000000000000000000000000 HOME_MAX_AMOUNT_PER_TX=1500000000000000000000000 HOME_MIN_AMOUNT_PER_TX=500000000000000000 @@ -33,12 +28,8 @@ BLOCK_REWARD_ADDRESS= FOREIGN_RPC_URL=https://sokol.poa.network FOREIGN_BRIDGE_OWNER=0x FOREIGN_VALIDATORS_OWNER=0x -# FOREIGN_OWNER_MULTISIG=0x FOREIGN_FACTORY_OWNER=0x FOREIGN_UPGRADEABLE_ADMIN=0x -# FOREIGN_UPGRADEABLE_ADMIN_VALIDATORS=0x -# FOREIGN_UPGRADEABLE_ADMIN_BRIDGE=0x -# FOREIGN_UPGRADEABLE_ADMIN_FACTORY=0x FOREIGN_DAILY_LIMIT=15000000000000000000000000 FOREIGN_MAX_AMOUNT_PER_TX=750000000000000000000000 FOREIGN_MIN_AMOUNT_PER_TX=500000000000000000 @@ -47,6 +38,12 @@ FOREIGN_GAS_PRICE=10000000000 #for bridge erc_to_erc and erc_to_native mode ERC20_TOKEN_ADDRESS= +#Optional Implemetation addresses for ERC_TO_ERC_MULTIPLE mode +HOME_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS=0x +HOME_BRIDGE_IMPLEMENTATION_ADDRESS=0x +FOREIGN_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS=0x +FOREIGN_BRIDGE_IMPLEMENTATION_ADDRESS=0x + REQUIRED_NUMBER_OF_VALIDATORS=1 #If several validators are used, list them separated by space without quotes #E.g. VALIDATORS=0x 0x 0x diff --git a/deploy/README.md b/deploy/README.md index 780627147..8ddcc8729 100644 --- a/deploy/README.md +++ b/deploy/README.md @@ -329,3 +329,105 @@ REQUIRED_NUMBER_OF_VALIDATORS=1 # correctly to the Foreign network. VALIDATORS=0x 0x 0x ``` + +## `ERC_TO_ERC_MULTIPLE` Bridge Mode Configuration Example. + +This example of an `.env` file for the `erc-to-erc-multiple` bridge mode includes comments describing each parameter. + +```bash +# The type of bridge. Defines set of contracts to be deployed. +BRIDGE_MODE=ERC_TO_ERC_MULTIPLE + +# The private key hex value of the account responsible for contracts +# deployments and initial configuration. The account's balance must contain +# funds from both networks. +DEPLOYMENT_ACCOUNT_PRIVATE_KEY=67..14 +# The "gas" parameter set in every deployment/configuration transaction. +DEPLOYMENT_GAS_LIMIT=5000000 +# The "gasPrice" parameter set in every deployment/configuration transaction on +# Home network (in Wei). +HOME_DEPLOYMENT_GAS_PRICE=10000000000 +# The "gasPrice" parameter set in every deployment/configuration transaction on +# Foreign network (in Wei). +FOREIGN_DEPLOYMENT_GAS_PRICE=10000000000 +# The timeout limit to wait for receipt of the deployment/configuration +# transaction. +GET_RECEIPT_INTERVAL_IN_MILLISECONDS=3000 + +# The RPC channel to a Home node able to handle deployment/configuration +# transactions. +HOME_RPC_URL=https://rpc.fuse.io +# The address of an administrator on the Home network who can change bridge +# parameters and a validator's contract. For extra security we recommended using +HOME_BRIDGE_OWNER=0x +HOME_VALIDATORS_OWNER=0x +# the home factory owner +HOME_FACTORY_OWNER=0x +# the home mapper owner +HOME_MAPPER_OWNER=0x +# The address from which upgradable contract can be upgraded on Home. +HOME_UPGRADEABLE_ADMIN=0x +# The daily transaction limit in Wei. As soon as this limit is exceeded, any +# transaction which requests to relay assets will fail. +HOME_DAILY_LIMIT=30000000000000000000000000 +# The maximum limit for one transaction in Wei. If a single transaction tries to +# relay funds exceeding this limit it will fail. +HOME_MAX_AMOUNT_PER_TX=1500000000000000000000000 +# The minimum limit for one transaction in Wei. If a transaction tries to relay +# funds below this limit it will fail. This is required to prevent dryout +# validator accounts. +HOME_MIN_AMOUNT_PER_TX=500000000000000000 +# The finalization threshold. The number of blocks issued after the block with +# the corresponding deposit transaction to guarantee the transaction will not be +# rolled back. +HOME_REQUIRED_BLOCK_CONFIRMATIONS=1 +# The default gas price (in Wei) used to send Home Network signature +# transactions for deposit or withdrawal confirmations. This price is used if +# the Gas price oracle is unreachable. +HOME_GAS_PRICE=1000000000 + +# The RPC channel to a Foreign node able to handle deployment/configuration +# transactions. +FOREIGN_RPC_URL=https://ropsten.infura.io +# The address of an administrator on the Foreign network who can change bridge +# parameters and the validator's contract. For extra security we recommended +# using a multi-sig wallet contract address here. +FOREIGN_BRIDGE_OWNER=0x +FOREIGN_VALIDATORS_OWNER=0x +# the foreign factory owner +FOREIGN_FACTORY_OWNER=0x +# The address from which upgradable contract can be upgraded on Foreign. +FOREIGN_UPGRADEABLE_ADMIN=0x +# These three parameters are not used in this mode, but the deployment script +# requires it to be set to some value. +FOREIGN_DAILY_LIMIT=30000000000000000000000000 +FOREIGN_MAX_AMOUNT_PER_TX=1500000000000000000000000 +FOREIGN_MIN_AMOUNT_PER_TX=500000000000000000 +# The finalization threshold. The number of blocks issued after the block with +# the corresponding deposit transaction to guarantee the transaction will not be +# rolled back. +FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS=8 +# The default gas price (in Wei) used to send Foreign network transactions +# finalizing asset deposits. This price is used if the Gas price oracle is +# unreachable. +FOREIGN_GAS_PRICE=10000000000 +# The address of the existing ERC20 compatible token in the Foreign network to +# be exchanged to the ERC20/ERC677 token deployed on Home. +ERC20_TOKEN_ADDRESS=0x + +# The minimum number of validators required to send their signatures confirming +# the relay of assets. The same number of validators is expected on both sides +# of the bridge. +REQUIRED_NUMBER_OF_VALIDATORS=1 +# The set of validators' addresses. It is assumed that signatures from these +# addresses are collected on the Home side. The same addresses will be used on +# the Foreign network to confirm that the finalized agreement was transferred +# correctly to the Foreign network. +VALIDATORS=0x 0x 0x + +# implementation addresses - optional: +#FOREIGN_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS=0x +#FOREIGN_BRIDGE_IMPLEMENTATION_ADDRESS=0x +#HOME_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS=0x +#HOME_BRIDGE_IMPLEMENTATION_ADDRESS=0x +``` \ No newline at end of file From 63d1b1788b538765e2d865197e07c583dae1056b Mon Sep 17 00:00:00 2001 From: Victor Baranov Date: Mon, 4 Feb 2019 13:35:07 +0300 Subject: [PATCH 084/187] Replace poa.infura.io with core.poa.network --- deploy/README.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/deploy/README.md b/deploy/README.md index 50b38b473..99b033318 100644 --- a/deploy/README.md +++ b/deploy/README.md @@ -58,7 +58,7 @@ BRIDGEABLE_TOKEN_DECIMALS=18 # The RPC channel to a Home node able to handle deployment/configuration # transactions. -HOME_RPC_URL=https://poa.infura.io +HOME_RPC_URL=https://core.poa.network # Address on Home network with permissions to change parameters of the bridge contract. # For extra security we recommended using a multi-sig wallet contract address here. HOME_BRIDGE_OWNER=0x @@ -160,7 +160,7 @@ BRIDGEABLE_TOKEN_DECIMALS=18 # The RPC channel to a Home node able to handle deployment/configuration # transactions. -HOME_RPC_URL=https://poa.infura.io +HOME_RPC_URL=https://core.poa.network # Address on Home network with permissions to change parameters of the bridge contract. # For extra security we recommended using a multi-sig wallet contract address here. HOME_BRIDGE_OWNER=0x @@ -251,7 +251,7 @@ GET_RECEIPT_INTERVAL_IN_MILLISECONDS=3000 # The RPC channel to a Home node able to handle deployment/configuration # transactions. -HOME_RPC_URL=https://poa.infura.io +HOME_RPC_URL=https://core.poa.network # Address on Home network with permissions to change parameters of the bridge contract. # For extra security we recommended using a multi-sig wallet contract address here. HOME_BRIDGE_OWNER=0x From b209667f10030882c9b3f58d8eb9024c22939d53 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 4 Feb 2019 09:57:43 -0300 Subject: [PATCH 085/187] Update gas consumption --- docs/ERC-TO-NATIVE-WITH-REWARD.md | 8 ++++---- docs/ERC-TO-NATIVE.md | 4 ++-- docs/NATIVE-TO-ERC-WITH-REWARD.md | 16 ++++++++-------- docs/NATIVE-TO-ERC.md | 8 ++++---- 4 files changed, 18 insertions(+), 18 deletions(-) diff --git a/docs/ERC-TO-NATIVE-WITH-REWARD.md b/docs/ERC-TO-NATIVE-WITH-REWARD.md index fb616c18e..5e0eca817 100644 --- a/docs/ERC-TO-NATIVE-WITH-REWARD.md +++ b/docs/ERC-TO-NATIVE-WITH-REWARD.md @@ -10,12 +10,12 @@ EternalStorageProxy|upgradeTo|35871|30924|30913 RewardableValidators|initialize|202711|423292|318008 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 EternalStorageProxy|deployment|378510|378510|378510 -HomeBridgeErcToNative|deployment|5088498|5088498|5088498 +HomeBridgeErcToNative|deployment|5653534|5653534|5653534 EternalStorageProxy|upgradeTo|35871|30924|30913 -FeeManagerErcToNative|deployment|849694|849694|849694 -HomeBridgeErcToNative|rewardableInitialize|327113|327177|327161 +FeeManagerErcToNative|deployment|1068197|1068197|1068197 +HomeBridgeErcToNative|rewardableInitialize|353084|353148|353132 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |8973874|9184625|9079303 +Total| |9783384|9994135|9888813 ##### Foreign Contract | Method | Min | Max | Avg diff --git a/docs/ERC-TO-NATIVE.md b/docs/ERC-TO-NATIVE.md index b4a0877f7..53e3b83d5 100644 --- a/docs/ERC-TO-NATIVE.md +++ b/docs/ERC-TO-NATIVE.md @@ -10,11 +10,11 @@ EternalStorageProxy|upgradeTo|35871|30924|30913 BridgeValidators|initialize|210762|306607|270900 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 EternalStorageProxy|deployment|378510|378510|378510 -HomeBridgeErcToNative|deployment|5088498|5088498|5088498 +HomeBridgeErcToNative|deployment|5653534|5653534|5653534 EternalStorageProxy|upgradeTo|35871|30924|30913 HomeBridgeErcToNative|initialize|264356|281376|278561 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |7805175|7908146|7869602 +Total| |8370211|8473182|8434638 ##### Foreign Contract | Method | Min | Max | Avg diff --git a/docs/NATIVE-TO-ERC-WITH-REWARD.md b/docs/NATIVE-TO-ERC-WITH-REWARD.md index 99b0df278..dd8c91f65 100644 --- a/docs/NATIVE-TO-ERC-WITH-REWARD.md +++ b/docs/NATIVE-TO-ERC-WITH-REWARD.md @@ -10,12 +10,12 @@ EternalStorageProxy|upgradeTo|35871|30924|30913 RewardableValidators|initialize|202711|423292|318008 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 EternalStorageProxy|deployment|378510|378510|378510 -HomeBridgeNativeToErc|deployment|4193535|4193535|4193535 +HomeBridgeNativeToErc|deployment|4709570|4709570|4709570 EternalStorageProxy|upgradeTo|35871|30924|30913 -FeeManagerNativeToErc|deployment|861773|861773|861773 -HomeBridgeNativeToErc|rewardableInitialize|305520|305584|305563 +FeeManagerNativeToErc|deployment|1079956|1079956|1079956 +HomeBridgeNativeToErc|rewardableInitialize|330597|330725|330679 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |8069397|8280148|8174821 +Total| |8828692|9039507|8934155 ##### Foreign Contract | Method | Min | Max | Avg @@ -27,14 +27,14 @@ EternalStorageProxy|upgradeTo|35871|30924|30913 RewardableValidators|initialize|202711|423292|318008 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 EternalStorageProxy|deployment|378510|378510|378510 -ForeignBridgeNativeToErc|deployment|3534781|3534781|3534781 +ForeignBridgeNativeToErc|deployment|4056029|4056029|4056029 EternalStorageProxy|upgradeTo|35871|30924|30913 -FeeManagerNativeToErc|deployment|861773|861773|861773 -ForeignBridgeNativeToErc|rewardableInitialize|327843|327907|327896 +FeeManagerNativeToErc|deployment|1079956|1079956|1079956 +ForeignBridgeNativeToErc|rewardableInitialize|354062|354126|354080 ERC677BridgeToken|setBridgeContract|29432|44432|39432 ERC677BridgeToken|transferOwnership|30860|30924|30913 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |8956794|9183633|9072915 +Total| |9722444|9949283|9838530 #### Usage diff --git a/docs/NATIVE-TO-ERC.md b/docs/NATIVE-TO-ERC.md index 09cff7f7c..2c9e49d01 100644 --- a/docs/NATIVE-TO-ERC.md +++ b/docs/NATIVE-TO-ERC.md @@ -10,11 +10,11 @@ EternalStorageProxy|upgradeTo|35871|30924|30913 BridgeValidators|initialize|210762|306607|270900 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 EternalStorageProxy|deployment|378510|378510|378510 -HomeBridgeNativeToErc|deployment|4193535|4193535|4193535 +HomeBridgeNativeToErc|deployment|4709570|4709570|4709570 EternalStorageProxy|upgradeTo|35871|30924|30913 HomeBridgeNativeToErc|initialize|257416|258312|258003 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |6903272|6990119|6954081 +Total| |7419307|7506154|7470116 ##### Foreign Contract | Method | Min | Max | Avg @@ -26,13 +26,13 @@ EternalStorageProxy|upgradeTo|35871|30924|30913 BridgeValidators|initialize|210762|306607|270900 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 EternalStorageProxy|deployment|378510|378510|378510 -ForeignBridgeNativeToErc|deployment|3534781|3534781|3534781 +ForeignBridgeNativeToErc|deployment|4056029|4056029|4056029 EternalStorageProxy|upgradeTo|35871|30924|30913 ForeignBridgeNativeToErc|initialize|281275|281339|281328 ERC677BridgeToken|setBridgeContract|29432|44432|39432 ERC677BridgeToken|transferOwnership|30860|30924|30913 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |7792205|7894308|7853167 +Total| |8313453|8415556|8374415 #### Usage From b54cd53c87b9a5e5a871b5571718827473cc5add Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 4 Feb 2019 14:24:53 -0300 Subject: [PATCH 086/187] Update fee parameter docs --- deploy/.env.example | 4 ++-- deploy/README.md | 14 +++++++------- 2 files changed, 9 insertions(+), 9 deletions(-) diff --git a/deploy/.env.example b/deploy/.env.example index 2f5a7e886..62d114a8b 100644 --- a/deploy/.env.example +++ b/deploy/.env.example @@ -48,10 +48,10 @@ FOREIGN_REWARDABLE=false #E.g. VALIDATORS_REWARD_ACCOUNTS=0x 0x 0x VALIDATORS_REWARD_ACCOUNTS=0x -# Fee to be charged for each transfer on Home: +# Fee to be taken for every transaction directed from the Home network to the Foreign network # E.g. 0.1% fee HOME_TRANSACTIONS_FEE=0.001 -# Fee to be charged for each transfer on Foreign: +# Fee to be taken for every transaction directed from the Foreign network to the Home network FOREIGN_TRANSACTIONS_FEE=0.001 #for bridge native_to_erc mode DEPLOY_REWARDABLE_TOKEN=false diff --git a/deploy/README.md b/deploy/README.md index dad4fcce3..e959e0a3f 100644 --- a/deploy/README.md +++ b/deploy/README.md @@ -132,12 +132,12 @@ FOREIGN_REWARDABLE=false # Makes sense only when HOME_REWARDABLE=true or FOREIGN_REWARDABLE=true VALIDATORS_REWARD_ACCOUNTS=0x 0x 0x -# Fee to be charged for each transfer on Home network -# Makes sense only when HOME_REWARDABLE=true +# Fee to be taken for every transaction directed from the Home network to the Foreign network +# Makes sense only when FOREIGN_REWARDABLE=true # e.g. 0.1% fee HOME_TRANSACTIONS_FEE=0.001 -# Fee to be charged for each transfer on Foreign network -# Makes sense only when FOREIGN_REWARDABLE=true +# Fee to be taken for every transaction directed from the Foreign network to the Home network +# Makes sense only when HOME_REWARDABLE=true # e.g. 0.1% fee FOREIGN_TRANSACTIONS_FEE=0.001 @@ -355,12 +355,12 @@ FOREIGN_REWARDABLE=false # Makes sense only when HOME_REWARDABLE=true or FOREIGN_REWARDABLE=true VALIDATORS_REWARD_ACCOUNTS=0x 0x 0x -# Fee to be charged for each transfer on Home network +# Fee to be taken for every transaction directed from the Home network to the Foreign network # Makes sense only when HOME_REWARDABLE=true # e.g. 0.1% fee HOME_TRANSACTIONS_FEE=0.001 -# Fee to be charged for each transfer on Foreign network -# Makes sense only when FOREIGN_REWARDABLE=true +# Fee to be taken for every transaction directed from the Foreign network to the Home network +# Makes sense only when HOME_REWARDABLE=true # e.g. 0.1% fee FOREIGN_TRANSACTIONS_FEE=0.001 ``` From 78d6c3b632de432332eeb08242b6a48fe3bcb70f Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 4 Feb 2019 15:07:49 -0300 Subject: [PATCH 087/187] Refactor RewardableBridge --- .../RewardableBridge.sol | 18 +-------------- .../erc20_to_native/HomeBridgeErcToNative.sol | 4 ++-- .../RewardableHomeBridgeErcToNative.sol | 23 +++++++++++++++++++ .../ForeignBridgeNativeToErc.sol | 4 ++-- .../native_to_erc20/HomeBridgeNativeToErc.sol | 4 ++-- .../RewardableForeignBridgeNativeToErc.sol | 15 ++++++++++++ .../RewardableHomeBridgeNativeToErc.sol | 15 ++++++++++++ test/native_to_erc/foreign_bridge_test.js | 6 ----- test/native_to_erc/home_bridge_test.js | 6 ----- 9 files changed, 60 insertions(+), 35 deletions(-) create mode 100644 contracts/upgradeable_contracts/erc20_to_native/RewardableHomeBridgeErcToNative.sol create mode 100644 contracts/upgradeable_contracts/native_to_erc20/RewardableForeignBridgeNativeToErc.sol create mode 100644 contracts/upgradeable_contracts/native_to_erc20/RewardableHomeBridgeNativeToErc.sol diff --git a/contracts/upgradeable_contracts/RewardableBridge.sol b/contracts/upgradeable_contracts/RewardableBridge.sol index 3de2ef6b9..d21aeff26 100644 --- a/contracts/upgradeable_contracts/RewardableBridge.sol +++ b/contracts/upgradeable_contracts/RewardableBridge.sol @@ -6,23 +6,7 @@ import "./FeeTypes.sol"; contract RewardableBridge is Ownable, FeeTypes { - function setHomeFee(uint256 _fee) external onlyOwner { - _setFee(feeManagerContract(), _fee, HOME_FEE); - } - - function setForeignFee(uint256 _fee) external onlyOwner { - _setFee(feeManagerContract(), _fee, FOREIGN_FEE); - } - - function getHomeFee() public view returns(uint256) { - return _getFee(HOME_FEE); - } - - function getForeignFee() public view returns(uint256) { - return _getFee(FOREIGN_FEE); - } - - function _getFee(bytes32 _feeType) public view returns(uint256) { + function _getFee(bytes32 _feeType) internal view returns(uint256) { uint256 fee; address feeManager = feeManagerContract(); string memory method = _feeType == HOME_FEE ? "getHomeFee()" : "getForeignFee()"; diff --git a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol index e4e1cd4eb..a396fcd89 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol @@ -8,10 +8,10 @@ import "../../ERC677Receiver.sol"; import "../BasicHomeBridge.sol"; import "../ERC677Bridge.sol"; import "../OverdrawManagement.sol"; -import "../RewardableBridge.sol"; +import "./RewardableHomeBridgeErcToNative.sol"; -contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, OverdrawManagement, RewardableBridge { +contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, OverdrawManagement, RewardableHomeBridgeErcToNative { event AmountLimitExceeded(address recipient, uint256 value, bytes32 transactionHash); diff --git a/contracts/upgradeable_contracts/erc20_to_native/RewardableHomeBridgeErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/RewardableHomeBridgeErcToNative.sol new file mode 100644 index 000000000..8d0df3d0b --- /dev/null +++ b/contracts/upgradeable_contracts/erc20_to_native/RewardableHomeBridgeErcToNative.sol @@ -0,0 +1,23 @@ +pragma solidity 0.4.24; + +import "../RewardableBridge.sol"; + + +contract RewardableHomeBridgeErcToNative is RewardableBridge { + + function setHomeFee(uint256 _fee) external onlyOwner { + _setFee(feeManagerContract(), _fee, HOME_FEE); + } + + function setForeignFee(uint256 _fee) external onlyOwner { + _setFee(feeManagerContract(), _fee, FOREIGN_FEE); + } + + function getHomeFee() public view returns(uint256) { + return _getFee(HOME_FEE); + } + + function getForeignFee() public view returns(uint256) { + return _getFee(FOREIGN_FEE); + } +} diff --git a/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol index 77b12b9c2..da935e5dc 100644 --- a/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol +++ b/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol @@ -6,10 +6,10 @@ import "../../ERC677Receiver.sol"; import "../BasicForeignBridge.sol"; import "openzeppelin-solidity/contracts/token/ERC20/ERC20Basic.sol"; import "../ERC677Bridge.sol"; -import "../RewardableBridge.sol"; +import "./RewardableForeignBridgeNativeToErc.sol"; -contract ForeignBridgeNativeToErc is ERC677Receiver, BasicBridge, BasicForeignBridge, ERC677Bridge, RewardableBridge { +contract ForeignBridgeNativeToErc is ERC677Receiver, BasicBridge, BasicForeignBridge, ERC677Bridge, RewardableForeignBridgeNativeToErc { /// Event created on money withdraw. event UserRequestForAffirmation(address recipient, uint256 value); diff --git a/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol index fe8ec7dbe..49601fbbe 100644 --- a/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol +++ b/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol @@ -4,11 +4,11 @@ import "../../libraries/Message.sol"; import "../BasicBridge.sol"; import "../../upgradeability/EternalStorage.sol"; import "../BasicHomeBridge.sol"; -import "../RewardableBridge.sol"; +import "./RewardableHomeBridgeNativeToErc.sol"; import "../Sacrifice.sol"; -contract HomeBridgeNativeToErc is EternalStorage, BasicBridge, BasicHomeBridge, RewardableBridge { +contract HomeBridgeNativeToErc is EternalStorage, BasicBridge, BasicHomeBridge, RewardableHomeBridgeNativeToErc { function () public payable { require(msg.value > 0); diff --git a/contracts/upgradeable_contracts/native_to_erc20/RewardableForeignBridgeNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/RewardableForeignBridgeNativeToErc.sol new file mode 100644 index 000000000..f7c2dd996 --- /dev/null +++ b/contracts/upgradeable_contracts/native_to_erc20/RewardableForeignBridgeNativeToErc.sol @@ -0,0 +1,15 @@ +pragma solidity 0.4.24; + +import "../RewardableBridge.sol"; + + +contract RewardableForeignBridgeNativeToErc is RewardableBridge { + + function setHomeFee(uint256 _fee) external onlyOwner { + _setFee(feeManagerContract(), _fee, HOME_FEE); + } + + function getHomeFee() public view returns(uint256) { + return _getFee(HOME_FEE); + } +} diff --git a/contracts/upgradeable_contracts/native_to_erc20/RewardableHomeBridgeNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/RewardableHomeBridgeNativeToErc.sol new file mode 100644 index 000000000..f6f9085c0 --- /dev/null +++ b/contracts/upgradeable_contracts/native_to_erc20/RewardableHomeBridgeNativeToErc.sol @@ -0,0 +1,15 @@ +pragma solidity 0.4.24; + +import "../RewardableBridge.sol"; + + +contract RewardableHomeBridgeNativeToErc is RewardableBridge { + + function setForeignFee(uint256 _fee) external onlyOwner { + _setFee(feeManagerContract(), _fee, FOREIGN_FEE); + } + + function getForeignFee() public view returns(uint256) { + return _getFee(FOREIGN_FEE); + } +} diff --git a/test/native_to_erc/foreign_bridge_test.js b/test/native_to_erc/foreign_bridge_test.js index 3e998db4f..bfc361dfc 100644 --- a/test/native_to_erc/foreign_bridge_test.js +++ b/test/native_to_erc/foreign_bridge_test.js @@ -560,8 +560,6 @@ contract('ForeignBridge', async (accounts) => { feeManagerContract.should.be.equals(feeManager.address) const bridgeHomeFee = await foreignBridge.getHomeFee() bridgeHomeFee.should.be.bignumber.equal(homeFee) - const bridgeForeignFee = await foreignBridge.getForeignFee() - bridgeForeignFee.should.be.bignumber.equal(foreignFee) }) it('can update fee contract', async () => { @@ -585,17 +583,13 @@ contract('ForeignBridge', async (accounts) => { // Given const newHomeFee = web3.toBigNumber(web3.toWei(0.1, "ether")) - const newForeignFee = web3.toBigNumber(web3.toWei(0.2, "ether")) // When await foreignBridge.setHomeFee(newHomeFee, { from: owner }).should.be.fulfilled - await foreignBridge.setForeignFee(newForeignFee, { from: owner }).should.be.fulfilled // Then const bridgeHomeFee = await foreignBridge.getHomeFee() bridgeHomeFee.should.be.bignumber.equal(newHomeFee) - const bridgeForeignFee = await foreignBridge.getForeignFee() - bridgeForeignFee.should.be.bignumber.equal(newForeignFee) }) it('should be able to get fee manager mode', async () => { diff --git a/test/native_to_erc/home_bridge_test.js b/test/native_to_erc/home_bridge_test.js index 301557821..ce42296c1 100644 --- a/test/native_to_erc/home_bridge_test.js +++ b/test/native_to_erc/home_bridge_test.js @@ -599,8 +599,6 @@ contract('HomeBridge', async (accounts) => { const feeManagerContract = await homeBridge.feeManagerContract() feeManagerContract.should.be.equals(feeManager.address) - const bridgeHomeFee = await homeBridge.getHomeFee() - bridgeHomeFee.should.be.bignumber.equal(homeFee) const bridgeForeignFee = await homeBridge.getForeignFee() bridgeForeignFee.should.be.bignumber.equal(foreignFee) }) @@ -625,16 +623,12 @@ contract('HomeBridge', async (accounts) => { await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; // Given - const newHomeFee = web3.toBigNumber(web3.toWei(0.1, "ether")) const newForeignFee = web3.toBigNumber(web3.toWei(0.2, "ether")) // When - await homeBridge.setHomeFee(newHomeFee, { from: owner }).should.be.fulfilled await homeBridge.setForeignFee(newForeignFee, { from: owner }).should.be.fulfilled // Then - const bridgeHomeFee = await homeBridge.getHomeFee() - bridgeHomeFee.should.be.bignumber.equal(newHomeFee) const bridgeForeignFee = await homeBridge.getForeignFee() bridgeForeignFee.should.be.bignumber.equal(newForeignFee) }) From 5a69e97ffadc798c93b4f074cea7404a04e980e6 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 4 Feb 2019 15:33:05 -0300 Subject: [PATCH 088/187] Fix rewardableInitialize methods --- .../ForeignBridgeNativeToErc.sol | 4 +-- .../native_to_erc20/HomeBridgeNativeToErc.sol | 2 -- deploy/src/erc_to_native/home.js | 2 +- deploy/src/native_to_erc/foreign.js | 10 ++---- deploy/src/native_to_erc/home.js | 6 +--- test/native_to_erc/foreign_bridge_test.js | 32 ++++++++----------- test/native_to_erc/home_bridge_test.js | 28 +++++++--------- 7 files changed, 32 insertions(+), 52 deletions(-) diff --git a/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol index da935e5dc..1821b279c 100644 --- a/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol +++ b/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol @@ -54,8 +54,7 @@ contract ForeignBridgeNativeToErc is ERC677Receiver, BasicBridge, BasicForeignBr uint256 _homeMaxPerTx, address _owner, address _feeManager, - uint256 _homeFee, - uint256 _foreignFee + uint256 _homeFee ) public returns(bool) { _initialize( _validatorContract, @@ -72,7 +71,6 @@ contract ForeignBridgeNativeToErc is ERC677Receiver, BasicBridge, BasicForeignBr require(isContract(_feeManager)); addressStorage[keccak256(abi.encodePacked("feeManagerContract"))] = _feeManager; _setFee(_feeManager, _homeFee, HOME_FEE); - _setFee(_feeManager, _foreignFee, FOREIGN_FEE); setInitialize(true); return isInitialized(); } diff --git a/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol index 49601fbbe..6b225fd56 100644 --- a/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol +++ b/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol @@ -56,7 +56,6 @@ contract HomeBridgeNativeToErc is EternalStorage, BasicBridge, BasicHomeBridge, uint256 _foreignMaxPerTx, address _owner, address _feeManager, - uint256 _homeFee, uint256 _foreignFee ) public returns(bool) { @@ -73,7 +72,6 @@ contract HomeBridgeNativeToErc is EternalStorage, BasicBridge, BasicHomeBridge, ); require(isContract(_feeManager)); addressStorage[keccak256(abi.encodePacked("feeManagerContract"))] = _feeManager; - _setFee(_feeManager, _homeFee, HOME_FEE); _setFee(_feeManager, _foreignFee, FOREIGN_FEE); setInitialize(true); return isInitialized(); diff --git a/deploy/src/erc_to_native/home.js b/deploy/src/erc_to_native/home.js index 44f9cf724..6a29343a8 100644 --- a/deploy/src/erc_to_native/home.js +++ b/deploy/src/erc_to_native/home.js @@ -190,7 +190,7 @@ async function deployHome() { HOME_BRIDGE_OWNER: ${HOME_BRIDGE_OWNER}, Fee Manager: ${feeManager.options.address}, Home Fee: ${homeFeeInWei} which is ${HOME_TRANSACTIONS_FEE * 100}% - Foreign Fee: ${homeFeeInWei} which is ${FOREIGN_TRANSACTIONS_FEE * 100}%`) + Foreign Fee: ${foreignFeeInWei} which is ${FOREIGN_TRANSACTIONS_FEE * 100}%`) initializeHomeBridgeData = await homeBridgeImplementation.methods .rewardableInitialize( storageValidatorsHome.options.address, diff --git a/deploy/src/native_to_erc/foreign.js b/deploy/src/native_to_erc/foreign.js index e74587059..a85ed8289 100644 --- a/deploy/src/native_to_erc/foreign.js +++ b/deploy/src/native_to_erc/foreign.js @@ -41,8 +41,7 @@ const { BLOCK_REWARD_ADDRESS, DPOS_VALIDATOR_SET_ADDRESS, FOREIGN_REWARDABLE, - HOME_TRANSACTIONS_FEE, - FOREIGN_TRANSACTIONS_FEE + HOME_TRANSACTIONS_FEE } = env const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVATE_KEY) @@ -212,7 +211,6 @@ async function deployForeign() { foreignNonce++ const homeFeeInWei = Web3Utils.toWei(HOME_TRANSACTIONS_FEE.toString(), 'ether') - const foreignFeeInWei = Web3Utils.toWei(FOREIGN_TRANSACTIONS_FEE.toString(), 'ether') console.log('\ninitializing Foreign Bridge with fee contract:\n') console.log(`Foreign Validators: ${storageValidatorsForeign.options.address}, @@ -232,8 +230,7 @@ async function deployForeign() { )} in eth, FOREIGN_BRIDGE_OWNER: ${FOREIGN_BRIDGE_OWNER}, Fee Manager: ${feeManager.options.address}, - Home Fee: ${homeFeeInWei} which is ${HOME_TRANSACTIONS_FEE * 100}% - Foreign Fee: ${homeFeeInWei} which is ${FOREIGN_TRANSACTIONS_FEE * 100}%`) + Home Fee: ${homeFeeInWei} which is ${HOME_TRANSACTIONS_FEE * 100}%`) initializeFBridgeData = await foreignBridgeImplementation.methods .rewardableInitialize( @@ -248,8 +245,7 @@ async function deployForeign() { HOME_MAX_AMOUNT_PER_TX, FOREIGN_BRIDGE_OWNER, feeManager.options.address, - homeFeeInWei, - foreignFeeInWei + homeFeeInWei ) .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) } else { diff --git a/deploy/src/native_to_erc/home.js b/deploy/src/native_to_erc/home.js index 5b37772b6..0a12024be 100644 --- a/deploy/src/native_to_erc/home.js +++ b/deploy/src/native_to_erc/home.js @@ -33,7 +33,6 @@ const { FOREIGN_DAILY_LIMIT, FOREIGN_MAX_AMOUNT_PER_TX, HOME_REWARDABLE, - HOME_TRANSACTIONS_FEE, FOREIGN_TRANSACTIONS_FEE } = env @@ -167,7 +166,6 @@ async function deployHome() { console.log('[Home] feeManager Implementation: ', feeManager.options.address) homeNonce++ - const homeFeeInWei = Web3Utils.toWei(HOME_TRANSACTIONS_FEE.toString(), 'ether') const foreignFeeInWei = Web3Utils.toWei(FOREIGN_TRANSACTIONS_FEE.toString(), 'ether') console.log('\ninitializing Home Bridge with fee contract:\n') @@ -188,8 +186,7 @@ async function deployHome() { )} in eth, HOME_BRIDGE_OWNER: ${HOME_BRIDGE_OWNER}, Fee Manager: ${feeManager.options.address}, - Home Fee: ${homeFeeInWei} which is ${HOME_TRANSACTIONS_FEE * 100}% - Foreign Fee: ${homeFeeInWei} which is ${FOREIGN_TRANSACTIONS_FEE * 100}%`) + Foreign Fee: ${foreignFeeInWei} which is ${FOREIGN_TRANSACTIONS_FEE * 100}%`) homeBridgeImplementation.options.address = homeBridgeStorage.options.address initializeHomeBridgeData = await homeBridgeImplementation.methods @@ -204,7 +201,6 @@ async function deployHome() { FOREIGN_MAX_AMOUNT_PER_TX, HOME_BRIDGE_OWNER, feeManager.options.address, - homeFeeInWei, foreignFeeInWei ) .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) diff --git a/test/native_to_erc/foreign_bridge_test.js b/test/native_to_erc/foreign_bridge_test.js index bfc361dfc..0a1fb406f 100644 --- a/test/native_to_erc/foreign_bridge_test.js +++ b/test/native_to_erc/foreign_bridge_test.js @@ -514,7 +514,7 @@ contract('ForeignBridge', async (accounts) => { }) describe('#rewardableInitialize', async() => { - let homeFee, foreignFee, foreignBridge, token, rewardableValidators + let homeFee, foreignBridge, token, rewardableValidators let validators = [accounts[1]] let rewards = [accounts[2]] let requiredSignatures = 1 @@ -524,7 +524,6 @@ contract('ForeignBridge', async (accounts) => { await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled foreignBridge = await ForeignBridge.new() homeFee = web3.toBigNumber(web3.toWei(0.001, "ether")) - foreignFee = web3.toBigNumber(web3.toWei(0.002, "ether")) }) it('sets variables', async () => { const feeManager = await FeeManagerNativeToErc.new() @@ -534,13 +533,13 @@ contract('ForeignBridge', async (accounts) => { '0'.should.be.bignumber.equal(await foreignBridge.maxPerTx()) false.should.be.equal(await foreignBridge.isInitialized()) - await foreignBridge.rewardableInitialize(ZERO_ADDRESS, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.rewardableInitialize(rewardableValidators.address, ZERO_ADDRESS, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, 0, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.rewardableInitialize(owner, token.address, oneEther, halfEther, minPerTx, requireBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.rewardableInitialize(rewardableValidators.address, owner, oneEther, halfEther, minPerTx, requireBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.rewardableInitialize(rewardableValidators.address, owner, oneEther, halfEther, minPerTx, requireBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, owner, ZERO_ADDRESS, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + await foreignBridge.rewardableInitialize(ZERO_ADDRESS, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee).should.be.rejectedWith(ERROR_MSG); + await foreignBridge.rewardableInitialize(rewardableValidators.address, ZERO_ADDRESS, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee).should.be.rejectedWith(ERROR_MSG); + await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, 0, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee).should.be.rejectedWith(ERROR_MSG); + await foreignBridge.rewardableInitialize(owner, token.address, oneEther, halfEther, minPerTx, requireBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee).should.be.rejectedWith(ERROR_MSG); + await foreignBridge.rewardableInitialize(rewardableValidators.address, owner, oneEther, halfEther, minPerTx, requireBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee).should.be.rejectedWith(ERROR_MSG); + await foreignBridge.rewardableInitialize(rewardableValidators.address, owner, oneEther, halfEther, minPerTx, requireBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, owner, ZERO_ADDRESS, homeFee).should.be.rejectedWith(ERROR_MSG); + await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee).should.be.fulfilled; true.should.be.equal(await foreignBridge.isInitialized()) rewardableValidators.address.should.be.equal(await foreignBridge.validatorContract()); @@ -564,7 +563,7 @@ contract('ForeignBridge', async (accounts) => { it('can update fee contract', async () => { const feeManager = await FeeManagerNativeToErc.new() - await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee).should.be.fulfilled; // Given const newFeeManager = await FeeManagerNativeToErc.new() @@ -579,7 +578,7 @@ contract('ForeignBridge', async (accounts) => { it('can update fee', async () => { const feeManager = await FeeManagerNativeToErc.new() - await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee).should.be.fulfilled; // Given const newHomeFee = web3.toBigNumber(web3.toWei(0.1, "ether")) @@ -598,7 +597,7 @@ contract('ForeignBridge', async (accounts) => { const oneDirectionsModeHash = '0xf2aed8f7' // When - await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee).should.be.fulfilled; // Then const feeManagerMode = await foreignBridge.getFeeManagerMode() @@ -617,7 +616,6 @@ contract('ForeignBridge', async (accounts) => { it('should distribute fee to validator', async () => { const fee = 0.001 const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) - const feeNotUsedInWei = web3.toBigNumber(web3.toWei(0.5, "ether")) const value = halfEther const finalUserValue = value.mul(web3.toBigNumber(1-fee)); const feeAmount = value.mul(web3.toBigNumber(fee)) @@ -626,7 +624,7 @@ contract('ForeignBridge', async (accounts) => { const rewards = [accounts[2]] const requiredSignatures = 1 await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled - await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, feeInWei, feeNotUsedInWei).should.be.fulfilled; + await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, feeInWei).should.be.fulfilled; await token.transferOwnership(foreignBridge.address); const recipientAccount = accounts[3]; @@ -656,7 +654,6 @@ contract('ForeignBridge', async (accounts) => { // Given const fee = 0.001 const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) - const feeNotUsedInWei = web3.toBigNumber(web3.toWei(0.5, "ether")) const feePerValidator = web3.toBigNumber(166666666666666) const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) const value = halfEther @@ -666,7 +663,7 @@ contract('ForeignBridge', async (accounts) => { const rewards = [accounts[4], accounts[5], accounts[6]] const requiredSignatures = 3 await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled - await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, feeInWei, feeNotUsedInWei).should.be.fulfilled; + await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, feeInWei).should.be.fulfilled; await token.transferOwnership(foreignBridge.address); const recipientAccount = accounts[7]; @@ -718,7 +715,6 @@ contract('ForeignBridge', async (accounts) => { // Given const fee = 0.001 const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) - const feeNotUsedInWei = web3.toBigNumber(web3.toWei(0.5, "ether")) const value = halfEther const feeAmount = value.mul(web3.toBigNumber(fee)) const feePerValidator = feeAmount.div(web3.toBigNumber(5)) @@ -728,7 +724,7 @@ contract('ForeignBridge', async (accounts) => { const rewards = [accounts[5], accounts[6], accounts[7], accounts[8], accounts[9]] const requiredSignatures = 3 await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled - await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, feeInWei, feeNotUsedInWei).should.be.fulfilled; + await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, feeInWei).should.be.fulfilled; await token.transferOwnership(foreignBridge.address); const recipientAccount = accounts[0]; diff --git a/test/native_to_erc/home_bridge_test.js b/test/native_to_erc/home_bridge_test.js index ce42296c1..3846e3519 100644 --- a/test/native_to_erc/home_bridge_test.js +++ b/test/native_to_erc/home_bridge_test.js @@ -558,7 +558,7 @@ contract('HomeBridge', async (accounts) => { }) describe('#rewardableInitialize', async() => { - let homeFee, foreignFee, homeBridge, rewardableValidators + let foreignFee, homeBridge, rewardableValidators let validators = [accounts[1]] let rewards = [accounts[2]] let requiredSignatures = 1 @@ -566,7 +566,6 @@ contract('HomeBridge', async (accounts) => { rewardableValidators = await RewardableValidators.new() await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled homeBridge = await HomeBridge.new() - homeFee = web3.toBigNumber(web3.toWei(0.001, "ether")) foreignFee = web3.toBigNumber(web3.toWei(0.002, "ether")) }) it('sets variables', async () => { @@ -577,11 +576,11 @@ contract('HomeBridge', async (accounts) => { '0'.should.be.bignumber.equal(await homeBridge.maxPerTx()) false.should.be.equal(await homeBridge.isInitialized()) - await homeBridge.rewardableInitialize(ZERO_ADDRESS, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, 0, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, 0, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, ZERO_ADDRESS, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + await homeBridge.rewardableInitialize(ZERO_ADDRESS, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, foreignFee).should.be.rejectedWith(ERROR_MSG); + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, 0, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, foreignFee).should.be.rejectedWith(ERROR_MSG); + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, 0, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, foreignFee).should.be.rejectedWith(ERROR_MSG); + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, ZERO_ADDRESS, foreignFee).should.be.rejectedWith(ERROR_MSG); + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, foreignFee).should.be.fulfilled; true.should.be.equal(await homeBridge.isInitialized()) rewardableValidators.address.should.be.equal(await homeBridge.validatorContract()); @@ -605,7 +604,7 @@ contract('HomeBridge', async (accounts) => { it('can update fee contract', async () => { const feeManager = await FeeManagerNativeToErc.new() - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, foreignFee).should.be.fulfilled; // Given const newFeeManager = await FeeManagerNativeToErc.new() @@ -620,7 +619,7 @@ contract('HomeBridge', async (accounts) => { it('can update fee', async () => { const feeManager = await FeeManagerNativeToErc.new() - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, foreignFee).should.be.fulfilled; // Given const newForeignFee = web3.toBigNumber(web3.toWei(0.2, "ether")) @@ -638,7 +637,7 @@ contract('HomeBridge', async (accounts) => { const oneDirectionsModeHash = '0xf2aed8f7' // When - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, foreignFee).should.be.fulfilled; // Then const feeManagerMode = await homeBridge.getFeeManagerMode() @@ -662,12 +661,11 @@ contract('HomeBridge', async (accounts) => { // 0.1% fee const fee = 0.001 const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) - const feeNotUsedInWei = web3.toBigNumber(web3.toWei(0.5, "ether")) const value = halfEther; const finalUserValue = value.mul(web3.toBigNumber(1-fee)); const feeAmount = value.mul(web3.toBigNumber(fee)) - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeNotUsedInWei, feeInWei).should.be.fulfilled; + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei).should.be.fulfilled; await homeBridge.sendTransaction({ from: accounts[0], value: halfEther @@ -712,7 +710,6 @@ contract('HomeBridge', async (accounts) => { // 0.1% fee const fee = 0.001 const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) - const feeNotUsedInWei = web3.toBigNumber(web3.toWei(0.5, "ether")) const feePerValidator = web3.toBigNumber(166666666666666) const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) const finalUserValue = value.mul(web3.toBigNumber(1-fee)); @@ -720,7 +717,7 @@ contract('HomeBridge', async (accounts) => { const homeBridge = await HomeBridge.new() const feeManager = await FeeManagerNativeToErc.new() await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeNotUsedInWei, feeInWei).should.be.fulfilled; + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei).should.be.fulfilled; await homeBridge.sendTransaction({ from: accounts[0], value: halfEther @@ -784,7 +781,6 @@ contract('HomeBridge', async (accounts) => { // 0.1% fee const fee = 0.001 const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) - const feeNotUsedInWei = web3.toBigNumber(web3.toWei(0.5, "ether")) const feeAmount = value.mul(web3.toBigNumber(fee)) const feePerValidator = feeAmount.div(web3.toBigNumber(5)) @@ -792,7 +788,7 @@ contract('HomeBridge', async (accounts) => { const homeBridge = await HomeBridge.new() const feeManager = await FeeManagerNativeToErc.new() await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeNotUsedInWei, feeInWei).should.be.fulfilled; + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei).should.be.fulfilled; await homeBridge.sendTransaction({ from: accounts[0], value: halfEther From f9e3193646b7d27d49b5d0a399f1dfedaffa2f04 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 4 Feb 2019 16:00:16 -0300 Subject: [PATCH 089/187] Update gas consumption docs --- docs/ERC-TO-NATIVE-WITH-REWARD.md | 4 ++-- docs/ERC-TO-NATIVE.md | 4 ++-- docs/NATIVE-TO-ERC-WITH-REWARD.md | 12 ++++++------ docs/NATIVE-TO-ERC.md | 8 ++++---- 4 files changed, 14 insertions(+), 14 deletions(-) diff --git a/docs/ERC-TO-NATIVE-WITH-REWARD.md b/docs/ERC-TO-NATIVE-WITH-REWARD.md index 5e0eca817..518aee20d 100644 --- a/docs/ERC-TO-NATIVE-WITH-REWARD.md +++ b/docs/ERC-TO-NATIVE-WITH-REWARD.md @@ -10,12 +10,12 @@ EternalStorageProxy|upgradeTo|35871|30924|30913 RewardableValidators|initialize|202711|423292|318008 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 EternalStorageProxy|deployment|378510|378510|378510 -HomeBridgeErcToNative|deployment|5653534|5653534|5653534 +HomeBridgeErcToNative|deployment|5644337|5644337|5644337 EternalStorageProxy|upgradeTo|35871|30924|30913 FeeManagerErcToNative|deployment|1068197|1068197|1068197 HomeBridgeErcToNative|rewardableInitialize|353084|353148|353132 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |9783384|9994135|9888813 +Total| |9774187|9984938|9879616 ##### Foreign Contract | Method | Min | Max | Avg diff --git a/docs/ERC-TO-NATIVE.md b/docs/ERC-TO-NATIVE.md index 53e3b83d5..7f4e5814c 100644 --- a/docs/ERC-TO-NATIVE.md +++ b/docs/ERC-TO-NATIVE.md @@ -10,11 +10,11 @@ EternalStorageProxy|upgradeTo|35871|30924|30913 BridgeValidators|initialize|210762|306607|270900 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 EternalStorageProxy|deployment|378510|378510|378510 -HomeBridgeErcToNative|deployment|5653534|5653534|5653534 +HomeBridgeErcToNative|deployment|5644337|5644337|5644337 EternalStorageProxy|upgradeTo|35871|30924|30913 HomeBridgeErcToNative|initialize|264356|281376|278561 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |8370211|8473182|8434638 +Total| |8361014|8463985|8425441 ##### Foreign Contract | Method | Min | Max | Avg diff --git a/docs/NATIVE-TO-ERC-WITH-REWARD.md b/docs/NATIVE-TO-ERC-WITH-REWARD.md index dd8c91f65..7dc969e98 100644 --- a/docs/NATIVE-TO-ERC-WITH-REWARD.md +++ b/docs/NATIVE-TO-ERC-WITH-REWARD.md @@ -10,12 +10,12 @@ EternalStorageProxy|upgradeTo|35871|30924|30913 RewardableValidators|initialize|202711|423292|318008 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 EternalStorageProxy|deployment|378510|378510|378510 -HomeBridgeNativeToErc|deployment|4709570|4709570|4709570 +HomeBridgeNativeToErc|deployment|4594464|4594464|4594464 EternalStorageProxy|upgradeTo|35871|30924|30913 FeeManagerNativeToErc|deployment|1079956|1079956|1079956 -HomeBridgeNativeToErc|rewardableInitialize|330597|330725|330679 +HomeBridgeNativeToErc|rewardableInitialize|306629|306693|306647 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |8828692|9039507|8934155 +Total| |8689618|8900369|8795017 ##### Foreign Contract | Method | Min | Max | Avg @@ -27,14 +27,14 @@ EternalStorageProxy|upgradeTo|35871|30924|30913 RewardableValidators|initialize|202711|423292|318008 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 EternalStorageProxy|deployment|378510|378510|378510 -ForeignBridgeNativeToErc|deployment|4056029|4056029|4056029 +ForeignBridgeNativeToErc|deployment|3930131|3930131|3930131 EternalStorageProxy|upgradeTo|35871|30924|30913 FeeManagerNativeToErc|deployment|1079956|1079956|1079956 -ForeignBridgeNativeToErc|rewardableInitialize|354062|354126|354080 +ForeignBridgeNativeToErc|rewardableInitialize|329022|329086|329077 ERC677BridgeToken|setBridgeContract|29432|44432|39432 ERC677BridgeToken|transferOwnership|30860|30924|30913 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |9722444|9949283|9838530 +Total| |9571506|9798345|9687629 #### Usage diff --git a/docs/NATIVE-TO-ERC.md b/docs/NATIVE-TO-ERC.md index 2c9e49d01..de1f8882e 100644 --- a/docs/NATIVE-TO-ERC.md +++ b/docs/NATIVE-TO-ERC.md @@ -10,11 +10,11 @@ EternalStorageProxy|upgradeTo|35871|30924|30913 BridgeValidators|initialize|210762|306607|270900 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 EternalStorageProxy|deployment|378510|378510|378510 -HomeBridgeNativeToErc|deployment|4709570|4709570|4709570 +HomeBridgeNativeToErc|deployment|4594464|4594464|4594464 EternalStorageProxy|upgradeTo|35871|30924|30913 HomeBridgeNativeToErc|initialize|257416|258312|258003 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |7419307|7506154|7470116 +Total| |7304201|7391048|7355010 ##### Foreign Contract | Method | Min | Max | Avg @@ -26,13 +26,13 @@ EternalStorageProxy|upgradeTo|35871|30924|30913 BridgeValidators|initialize|210762|306607|270900 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 EternalStorageProxy|deployment|378510|378510|378510 -ForeignBridgeNativeToErc|deployment|4056029|4056029|4056029 +ForeignBridgeNativeToErc|deployment|3930131|3930131|3930131 EternalStorageProxy|upgradeTo|35871|30924|30913 ForeignBridgeNativeToErc|initialize|281275|281339|281328 ERC677BridgeToken|setBridgeContract|29432|44432|39432 ERC677BridgeToken|transferOwnership|30860|30924|30913 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |8313453|8415556|8374415 +Total| |8187555|8289658|8248517 #### Usage From 27db88f4891a393554d4aaf4915fdafdfce5cc61 Mon Sep 17 00:00:00 2001 From: Vadim Date: Mon, 11 Feb 2019 10:39:34 +0300 Subject: [PATCH 090/187] Override `transfer` and `transferFrom` in `ERC677BridgeTokenRewardable` To deny transfer tokens to ValidatorSet contract directly. --- contracts/ERC677BridgeTokenRewardable.sol | 10 ++++++++ test/poa20_test.js | 28 +++++++++++++++++++++++ 2 files changed, 38 insertions(+) diff --git a/contracts/ERC677BridgeTokenRewardable.sol b/contracts/ERC677BridgeTokenRewardable.sol index 41b95947d..3caf2ac7d 100644 --- a/contracts/ERC677BridgeTokenRewardable.sol +++ b/contracts/ERC677BridgeTokenRewardable.sol @@ -63,4 +63,14 @@ contract ERC677BridgeTokenRewardable is ERC677BridgeToken { emit Transfer(validatorSetContract, _staker, _amount); } + function transfer(address _to, uint256 _value) public returns(bool) { + require(_to != validatorSetContract); + return super.transfer(_to, _value); + } + + function transferFrom(address _from, address _to, uint256 _value) public returns(bool) { + require(_to != validatorSetContract); + return super.transferFrom(_from, _to, _value); + } + } diff --git a/test/poa20_test.js b/test/poa20_test.js index 57e9995b8..1df1459c9 100644 --- a/test/poa20_test.js +++ b/test/poa20_test.js @@ -330,8 +330,36 @@ async function testERC677BridgeToken(accounts, rewardable) { await token.setBridgeContract(foreignNativeToErcBridge.address).should.be.fulfilled; await token.transfer(foreignNativeToErcBridge.address, lessThanMin, {from: user}).should.be.rejectedWith(ERROR_MSG); }) + + if (rewardable) { + it('fail to send tokens to ValidatorSet contract directly', async () => { + const amount = web3.toWei(1, "ether"); + const validatorSetContractAddress = accounts[2]; + const arbitraryAccountAddress = accounts[3]; + await token.setValidatorSetContractMock(validatorSetContractAddress, {from: owner}).should.be.fulfilled; + await token.mint(user, amount, {from: owner}).should.be.fulfilled; + await token.transfer(validatorSetContractAddress, amount, {from: user}).should.be.rejectedWith(ERROR_MSG); + await token.transfer(arbitraryAccountAddress, amount, {from: user}).should.be.fulfilled; + }); + } }) + if (rewardable) { + describe('#transferFrom', async() => { + it('fail to send tokens to ValidatorSet contract directly', async () => { + const amount = web3.toWei(1, "ether"); + const user2 = accounts[2]; + const validatorSetContractAddress = accounts[3]; + const arbitraryAccountAddress = accounts[4]; + await token.setValidatorSetContractMock(validatorSetContractAddress, {from: owner}).should.be.fulfilled; + await token.mint(user, amount, {from: owner}).should.be.fulfilled; + await token.approve(user2, amount, {from: user}).should.be.fulfilled; + await token.transferFrom(user, validatorSetContractAddress, amount, {from: user2}).should.be.rejectedWith(ERROR_MSG); + await token.transferFrom(user, arbitraryAccountAddress, amount, {from: user2}).should.be.fulfilled; + }); + }); + } + describe("#burn", async () => { it('can burn', async() => { await token.burn(100, {from: owner}).should.be.rejectedWith(ERROR_MSG); From aa8776aa753880f1ddeb8004d0f3dc011a5210dc Mon Sep 17 00:00:00 2001 From: Tal Beja Date: Mon, 11 Feb 2019 15:30:02 +0200 Subject: [PATCH 091/187] added an option to make a double proxy implementation so it will be an easy replacement of the implementation contracts in all deployed bridges at once --- deploy/.env.example | 1 + deploy/src/factories/foreign.js | 81 ++++++++++++++++++++++++++++++++- deploy/src/factories/home.js | 81 ++++++++++++++++++++++++++++++++- 3 files changed, 161 insertions(+), 2 deletions(-) diff --git a/deploy/.env.example b/deploy/.env.example index c31ef42b3..d6fe492d1 100644 --- a/deploy/.env.example +++ b/deploy/.env.example @@ -43,6 +43,7 @@ HOME_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS=0x HOME_BRIDGE_IMPLEMENTATION_ADDRESS=0x FOREIGN_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS=0x FOREIGN_BRIDGE_IMPLEMENTATION_ADDRESS=0x +DOUBLE_PROXY_IMPLEMENTATIONS= REQUIRED_NUMBER_OF_VALIDATORS=1 #If several validators are used, list them separated by space without quotes diff --git a/deploy/src/factories/foreign.js b/deploy/src/factories/foreign.js index be9575d2c..1ffc2b771 100644 --- a/deploy/src/factories/foreign.js +++ b/deploy/src/factories/foreign.js @@ -23,7 +23,8 @@ const { FOREIGN_GAS_PRICE, FOREIGN_MAX_AMOUNT_PER_TX, HOME_DAILY_LIMIT, - HOME_MAX_AMOUNT_PER_TX + HOME_MAX_AMOUNT_PER_TX, + DOUBLE_PROXY_IMPLEMENTATIONS } = env let { @@ -48,6 +49,45 @@ async function deployForeign() { }) foreignNonce++ FOREIGN_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS = bridgeValidatorsImplementationForeign.options.address + + if (DOUBLE_PROXY_IMPLEMENTATIONS) { + console.log('deploying bridge validators proxy') + const implProxy = await deployContract(EternalStorageProxy, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + network: 'foreign', + nonce: foreignNonce + }) + foreignNonce++ + + console.log('\nhooking up eternal storage to implementation') + const upgradeToImpl = await implProxy.methods + .upgradeTo('1', FOREIGN_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + const txUpgradeToImpl = await sendRawTxForeign({ + data: upgradeToImpl, + nonce: foreignNonce, + to: implProxy.options.address, + privateKey: deploymentPrivateKey, + url: FOREIGN_RPC_URL + }) + assert.equal(Web3Utils.hexToNumber(txUpgradeToImpl.status), 1, 'Transaction Failed') + foreignNonce++ + FOREIGN_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS = implProxy.options.address + + console.log('\nTransferring ownership of Proxy\n') + const ownershipData = await implProxy.methods + .transferProxyOwnership(FOREIGN_UPGRADEABLE_ADMIN) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + const txOwnershipData = await sendRawTxForeign({ + data: ownershipData, + nonce: foreignNonce, + to: implProxy.options.address, + privateKey: deploymentPrivateKey, + url: FOREIGN_RPC_URL + }) + assert.equal(Web3Utils.hexToNumber(txOwnershipData.status), 1, 'Transaction Failed') + foreignNonce++ + } } console.log('[Foreign] bridge validators implementation address: ', FOREIGN_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS) @@ -60,6 +100,45 @@ async function deployForeign() { }) foreignNonce++ FOREIGN_BRIDGE_IMPLEMENTATION_ADDRESS = foreignBridgeImplementationForeign.options.address + + if (DOUBLE_PROXY_IMPLEMENTATIONS) { + console.log('deploying foreign bridge proxy') + const implProxy = await deployContract(EternalStorageProxy, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + network: 'foreign', + nonce: foreignNonce + }) + foreignNonce++ + + console.log('\nhooking up eternal storage to implementation') + const upgradeToImpl = await implProxy.methods + .upgradeTo('1', FOREIGN_BRIDGE_IMPLEMENTATION_ADDRESS) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + const txUpgradeToImpl = await sendRawTxForeign({ + data: upgradeToImpl, + nonce: foreignNonce, + to: implProxy.options.address, + privateKey: deploymentPrivateKey, + url: FOREIGN_RPC_URL + }) + assert.equal(Web3Utils.hexToNumber(txUpgradeToImpl.status), 1, 'Transaction Failed') + foreignNonce++ + FOREIGN_BRIDGE_IMPLEMENTATION_ADDRESS = implProxy.options.address + + console.log('\nTransferring ownership of Proxy\n') + const ownershipData = await implProxy.methods + .transferProxyOwnership(FOREIGN_UPGRADEABLE_ADMIN) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + const txOwnershipData = await sendRawTxForeign({ + data: ownershipData, + nonce: foreignNonce, + to: implProxy.options.address, + privateKey: deploymentPrivateKey, + url: FOREIGN_RPC_URL + }) + assert.equal(Web3Utils.hexToNumber(txOwnershipData.status), 1, 'Transaction Failed') + foreignNonce++ + } } console.log('[Foreign] foreign bridge implementation address: ', FOREIGN_BRIDGE_IMPLEMENTATION_ADDRESS) diff --git a/deploy/src/factories/home.js b/deploy/src/factories/home.js index 5d6934a3c..0f411de7f 100644 --- a/deploy/src/factories/home.js +++ b/deploy/src/factories/home.js @@ -27,7 +27,8 @@ const { HOME_REQUIRED_BLOCK_CONFIRMATIONS, HOME_GAS_PRICE, FOREIGN_DAILY_LIMIT, - FOREIGN_MAX_AMOUNT_PER_TX + FOREIGN_MAX_AMOUNT_PER_TX, + DOUBLE_PROXY_IMPLEMENTATIONS } = env let { @@ -49,6 +50,45 @@ async function deployHome() { }) homeNonce++ HOME_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS = bridgeValidatorsImplementationHome.options.address + + if (DOUBLE_PROXY_IMPLEMENTATIONS) { + console.log('deploying bridge validators proxy') + const implProxy = await deployContract(EternalStorageProxy, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + network: 'home', + nonce: homeNonce + }) + homeNonce++ + + console.log('\nhooking up eternal storage to implementation') + const upgradeToImpl = await implProxy.methods + .upgradeTo('1', HOME_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + const txUpgradeToImpl = await sendRawTxHome({ + data: upgradeToImpl, + nonce: homeNonce, + to: implProxy.options.address, + privateKey: deploymentPrivateKey, + url: HOME_RPC_URL + }) + assert.equal(Web3Utils.hexToNumber(txUpgradeToImpl.status), 1, 'Transaction Failed') + homeNonce++ + HOME_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS = implProxy.options.address + + console.log('\nTransferring ownership of Proxy\n') + const ownershipData = await implProxy.methods + .transferProxyOwnership(HOME_UPGRADEABLE_ADMIN) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + const txOwnershipData = await sendRawTxHome({ + data: ownershipData, + nonce: homeNonce, + to: implProxy.options.address, + privateKey: deploymentPrivateKey, + url: HOME_RPC_URL + }) + assert.equal(Web3Utils.hexToNumber(txOwnershipData.status), 1, 'Transaction Failed') + homeNonce++ + } } console.log('[Home] bridge validators implementation address: ', HOME_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS) @@ -61,6 +101,45 @@ async function deployHome() { }) homeNonce++ HOME_BRIDGE_IMPLEMENTATION_ADDRESS = homeBridgeImplementationHome.options.address + + if (DOUBLE_PROXY_IMPLEMENTATIONS) { + console.log('deploying home bridge proxy') + const implProxy = await deployContract(EternalStorageProxy, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + network: 'home', + nonce: homeNonce + }) + homeNonce++ + + console.log('\nhooking up eternal storage to implementation') + const upgradeToImpl = await implProxy.methods + .upgradeTo('1', HOME_BRIDGE_IMPLEMENTATION_ADDRESS) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + const txUpgradeToImpl = await sendRawTxHome({ + data: upgradeToImpl, + nonce: homeNonce, + to: implProxy.options.address, + privateKey: deploymentPrivateKey, + url: HOME_RPC_URL + }) + assert.equal(Web3Utils.hexToNumber(txUpgradeToImpl.status), 1, 'Transaction Failed') + homeNonce++ + HOME_BRIDGE_IMPLEMENTATION_ADDRESS = implProxy.options.address + + console.log('\nTransferring ownership of Proxy\n') + const ownershipData = await implProxy.methods + .transferProxyOwnership(HOME_UPGRADEABLE_ADMIN) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + const txOwnershipData = await sendRawTxHome({ + data: ownershipData, + nonce: homeNonce, + to: implProxy.options.address, + privateKey: deploymentPrivateKey, + url: HOME_RPC_URL + }) + assert.equal(Web3Utils.hexToNumber(txOwnershipData.status), 1, 'Transaction Failed') + homeNonce++ + } } console.log('[Home] home bridge implementation address: ', HOME_BRIDGE_IMPLEMENTATION_ADDRESS) From 102fcf254ca846c6d708b2f987d7a5a6aa5c1cf0 Mon Sep 17 00:00:00 2001 From: Tal Beja Date: Sun, 17 Feb 2019 11:58:50 +0200 Subject: [PATCH 092/187] unify events of bridge maper --- contracts/upgradeable_contracts/BridgeMapper.sol | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/contracts/upgradeable_contracts/BridgeMapper.sol b/contracts/upgradeable_contracts/BridgeMapper.sol index f3b1e9f7f..61b41d320 100644 --- a/contracts/upgradeable_contracts/BridgeMapper.sol +++ b/contracts/upgradeable_contracts/BridgeMapper.sol @@ -5,8 +5,7 @@ import "../upgradeability/EternalStorage.sol"; contract BridgeMapper is EternalStorage, EternalOwnable { - event BridgeMappingAdded(address indexed foreignToken, address homeToken, address foreignBridge, address homeBridge, uint256 foreignStartBlock, uint256 homeStartBlock); - event BridgeMappingRemoved(address indexed foreignToken); + event BridgeMappingUpdated(address indexed foreignToken, address homeToken, address foreignBridge, address homeBridge, uint256 foreignStartBlock, uint256 homeStartBlock); function homeBridgeByForeignToken(address _foreignToken) public view returns(address) { return addressStorage[keccak256(abi.encodePacked("homeBridgeByForeignToken", _foreignToken))]; @@ -68,7 +67,7 @@ contract BridgeMapper is EternalStorage, EternalOwnable { setHomeBridgeByForeignToken(_foreignToken, _homeBridge); setForeignStartBlockByForeignToken(_foreignToken, _foreignStartBlock); setHomeStartBlockByForeignToken(_foreignToken, _homeStartBlock); - emit BridgeMappingAdded(_foreignToken, _homeToken, _foreignBridge, _homeBridge, _foreignStartBlock, _homeStartBlock); + emit BridgeMappingUpdated(_foreignToken, _homeToken, _foreignBridge, _homeBridge, _foreignStartBlock, _homeStartBlock); } function removeBridgeMapping(address _foreignToken) public onlyOwner { @@ -78,7 +77,7 @@ contract BridgeMapper is EternalStorage, EternalOwnable { setHomeBridgeByForeignToken(_foreignToken, address(0)); setForeignStartBlockByForeignToken(_foreignToken, 0); setHomeStartBlockByForeignToken(_foreignToken, 0); - emit BridgeMappingRemoved(_foreignToken); + emit BridgeMappingUpdated(_foreignToken, address(0), address(0), address(0), 0, 0); } function getBridgeMapperVersion() public pure returns(uint64 major, uint64 minor, uint64 patch) { From 2bf00cee0e61644dfa84f2d7bd51894759123907 Mon Sep 17 00:00:00 2001 From: Tal Beja Date: Sun, 17 Feb 2019 13:30:21 +0200 Subject: [PATCH 093/187] prety env --- deploy/.env.example | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/deploy/.env.example b/deploy/.env.example index d6fe492d1..91869f282 100644 --- a/deploy/.env.example +++ b/deploy/.env.example @@ -43,7 +43,9 @@ HOME_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS=0x HOME_BRIDGE_IMPLEMENTATION_ADDRESS=0x FOREIGN_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS=0x FOREIGN_BRIDGE_IMPLEMENTATION_ADDRESS=0x -DOUBLE_PROXY_IMPLEMENTATIONS= + +#encapsulate implementation in double proxy for easier upgrades. +DOUBLE_PROXY_IMPLEMENTATIONS=0x REQUIRED_NUMBER_OF_VALIDATORS=1 #If several validators are used, list them separated by space without quotes From 02de67af72121d2f19bbb0d1b49b9535179741f6 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 18 Feb 2019 14:55:01 -0300 Subject: [PATCH 094/187] Upgrade node version to 10.15 --- .nvmrc | 1 + Dockerfile | 2 +- deploy/.nvmrc | 2 +- deploy/package-lock.json | 3085 ++++++---- deploy/package.json | 2 +- package-lock.json | 11266 +++++++++++++------------------------ package.json | 4 +- 7 files changed, 5719 insertions(+), 8643 deletions(-) create mode 100644 .nvmrc diff --git a/.nvmrc b/.nvmrc new file mode 100644 index 000000000..ec3053c8d --- /dev/null +++ b/.nvmrc @@ -0,0 +1 @@ +10.15 diff --git a/Dockerfile b/Dockerfile index 476323109..992dc94c7 100644 --- a/Dockerfile +++ b/Dockerfile @@ -1,4 +1,4 @@ -FROM node:8 +FROM node:10 WORKDIR /contracts diff --git a/deploy/.nvmrc b/deploy/.nvmrc index fa97ecedc..ec3053c8d 100644 --- a/deploy/.nvmrc +++ b/deploy/.nvmrc @@ -1 +1 @@ -8.9 +10.15 diff --git a/deploy/package-lock.json b/deploy/package-lock.json index a63423650..a5b02bbbc 100644 --- a/deploy/package-lock.json +++ b/deploy/package-lock.json @@ -24,6 +24,25 @@ "js-tokens": "^4.0.0" } }, + "@babel/parser": { + "version": "7.2.3", + "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.2.3.tgz", + "integrity": "sha512-0LyEcVlfCoFmci8mXx8A5oIkpkOgyo8dRHtxBnK9RRBwxO2+JZPNsqtVEZQ7mJFPxnXF9lfmU24mHOPI0qnlkA==" + }, + "@mrmlnc/readdir-enhanced": { + "version": "2.2.1", + "resolved": "https://registry.npmjs.org/@mrmlnc/readdir-enhanced/-/readdir-enhanced-2.2.1.tgz", + "integrity": "sha512-bPHp6Ji8b41szTOcaP63VlnbbO5Ny6dwAATtY6JTjh5N2OLrb5Qk/Th5cRkRQhkWCt+EJsYrNB0MiL+Gpn6e3g==", + "requires": { + "call-me-maybe": "^1.0.1", + "glob-to-regexp": "^0.3.0" + } + }, + "@nodelib/fs.stat": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/@nodelib/fs.stat/-/fs.stat-1.1.3.tgz", + "integrity": "sha512-shAmDyaQC4H92APFoIaVDHCx5bStIocgvbwQyxPRrbUY20V1EYTbSDchWbuwlMG3V17cprZhA6+78JfB+3DTPw==" + }, "accepts": { "version": "1.3.5", "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.5.tgz", @@ -34,54 +53,32 @@ } }, "acorn": { - "version": "5.5.3", - "resolved": "https://registry.npmjs.org/acorn/-/acorn-5.5.3.tgz", - "integrity": "sha512-jd5MkIUlbbmb07nXH0DT3y7rDVtkzDi4XZOUVWAer8ajmF/DTSSbl5oNFyDOl/OXA33Bl79+ypHhl2pN20VeOQ==" + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/acorn/-/acorn-6.1.0.tgz", + "integrity": "sha512-MW/FjM+IvU9CgBzjO3UIPCE2pyEwUsoFl+VGdczOPEdxfGFjuKny/gN54mOuX7Qxmb9Rg9MCn2oKiSUeW+pjrw==", + "dev": true }, "acorn-jsx": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-4.1.1.tgz", - "integrity": "sha512-JY+iV6r+cO21KtntVvFkD+iqjtdpRUpGqKWgfkCdZq1R+kbreEl8EcdcJR4SmiIgsIQT33s6QzheQ9a275Q8xw==", - "dev": true, - "requires": { - "acorn": "^5.0.3" - } - }, - "acorn-object-rest-spread": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/acorn-object-rest-spread/-/acorn-object-rest-spread-1.1.0.tgz", - "integrity": "sha1-eGma790Y7DGCyq2t9S4ml8BI9HY=", - "requires": { - "acorn": "^5.0.3" - } + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-5.0.1.tgz", + "integrity": "sha512-HJ7CfNHrfJLlNTzIEUTj43LNWGkqpRLxm3YjAlcD0ACydk9XynzYsCBHxut+iqt+1aBXkx9UP/w/ZqMr13XIzg==", + "dev": true }, "ajv": { - "version": "5.5.2", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-5.5.2.tgz", - "integrity": "sha1-c7Xuyj+rZT49P5Qis0GtQiBdyWU=", + "version": "6.9.1", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.9.1.tgz", + "integrity": "sha512-XDN92U311aINL77ieWHmqCcNlwjoP5cHXDxIxbf2MaPYuCXOHS7gHH8jktxeK5omgd52XbSTX6a4Piwd1pQmzA==", "requires": { - "co": "^4.6.0", - "fast-deep-equal": "^1.0.0", + "fast-deep-equal": "^2.0.1", "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.3.0" + "json-schema-traverse": "^0.4.1", + "uri-js": "^4.2.2" } }, - "ajv-keywords": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-3.2.0.tgz", - "integrity": "sha1-6GuBnGAs+IIa1jdBNpjx3sAhhHo=", - "dev": true - }, - "amdefine": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/amdefine/-/amdefine-1.0.1.tgz", - "integrity": "sha1-SlKCrBZHKek2Gbz9OtFR+BfOkfU=", - "optional": true - }, "ansi-escapes": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-3.1.0.tgz", - "integrity": "sha512-UgAb8H9D41AQnu/PbWlCofQVcnV4Gs2bBJi9eZPxfU/hgglFh3SMDMENRIqdr7H6XFnXdoknctFByVsCOotTVw==", + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-3.2.0.tgz", + "integrity": "sha512-cBhpre4ma+U0T1oM5fXg7Dy1Jw7zzwv7lt/GoCpr+hDQJoYnKVPLL4dCvSEFMmQurOQvSrwT7SL/DAlhBI97RQ==", "dev": true }, "ansi-regex": { @@ -112,6 +109,21 @@ "sprintf-js": "~1.0.2" } }, + "arr-diff": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/arr-diff/-/arr-diff-4.0.0.tgz", + "integrity": "sha1-1kYQdP6/7HHn4VI1dhoyml3HxSA=" + }, + "arr-flatten": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/arr-flatten/-/arr-flatten-1.1.0.tgz", + "integrity": "sha512-L3hKV5R/p5o81R7O02IGnwpDmkp6E982XhtbuwSe3O4qOtMMMtodicASA1Cny2U+aCXcNpml+m4dPsvsJ3jatg==" + }, + "arr-union": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/arr-union/-/arr-union-3.1.0.tgz", + "integrity": "sha1-45sJrqne+Gao8gbiiK9jkZuuOcQ=" + }, "array-flatten": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-1.1.1.tgz", @@ -130,16 +142,23 @@ "resolved": "https://registry.npmjs.org/array-uniq/-/array-uniq-1.0.3.tgz", "integrity": "sha1-r2rId6Jcx/dOBYiUdThY39sk/bY=" }, + "array-unique": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/array-unique/-/array-unique-0.3.2.tgz", + "integrity": "sha1-qJS3XUvE9s1nnvMkSp/Y9Gri1Cg=" + }, "arrify": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/arrify/-/arrify-1.0.1.tgz", - "integrity": "sha1-iYUI2iIm84DfkEcoRWhJwVAaSw0=", - "dev": true + "integrity": "sha1-iYUI2iIm84DfkEcoRWhJwVAaSw0=" }, "asn1": { - "version": "0.2.3", - "resolved": "https://registry.npmjs.org/asn1/-/asn1-0.2.3.tgz", - "integrity": "sha1-2sh4dxPJlmhJ/IGAd36+nB3fO4Y=" + "version": "0.2.4", + "resolved": "https://registry.npmjs.org/asn1/-/asn1-0.2.4.tgz", + "integrity": "sha512-jxwzQpLQjSmWXgwaCZE9Nz+glAG01yF1QnWgbhGwHI5A6FRIEY6IVqtHhIepHqI7/kyEyQEagBC5mBEFlIYvdg==", + "requires": { + "safer-buffer": "~2.1.0" + } }, "asn1.js": { "version": "4.10.1", @@ -156,6 +175,17 @@ "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=" }, + "assign-symbols": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/assign-symbols/-/assign-symbols-1.0.0.tgz", + "integrity": "sha1-WWZ/QfrdTyDMvCu5a41Pf3jsA2c=" + }, + "astral-regex": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/astral-regex/-/astral-regex-1.0.0.tgz", + "integrity": "sha512-+Ryf6g3BKoRc7jfp7ad8tM4TtMiaWvbF/1/sQcZPkkS7ag3D5nMBCe2UfOTONtAkaG0tO0ij3C5Lwmf1EiyjHg==", + "dev": true + }, "async-limiter": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/async-limiter/-/async-limiter-1.0.0.tgz", @@ -166,23 +196,28 @@ "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", "integrity": "sha1-x57Zf380y48robyXkLzDZkdLS3k=" }, + "atob": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/atob/-/atob-2.1.2.tgz", + "integrity": "sha512-Wm6ukoaOGJi/73p/cl2GvLjTI5JM1k/O14isD73YML8StrH/7/lRFgmg8nICZgD3bZZvjwCGxtMOD3wWNAu8cg==" + }, "aws-sign2": { "version": "0.7.0", "resolved": "https://registry.npmjs.org/aws-sign2/-/aws-sign2-0.7.0.tgz", "integrity": "sha1-tG6JCTSpWR8tL2+G1+ap8bP+dqg=" }, "aws4": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.6.0.tgz", - "integrity": "sha1-g+9cqGCysy5KDe7e6MdxudtXRx4=" + "version": "1.8.0", + "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.8.0.tgz", + "integrity": "sha512-ReZxvNHIOv88FlT7rxcXIIC0fPt4KZqZbOlivyWtXLt8ESx84zd3kMC6iK5jVeS2qt+g7ftS7ye4fi06X5rtRQ==" }, "babel-runtime": { - "version": "6.25.0", - "resolved": "https://registry.npmjs.org/babel-runtime/-/babel-runtime-6.25.0.tgz", - "integrity": "sha1-M7mOql1IK7AajRqmtDetKwGuxBw=", + "version": "6.26.0", + "resolved": "https://registry.npmjs.org/babel-runtime/-/babel-runtime-6.26.0.tgz", + "integrity": "sha1-llxwWGaOgrVde/4E/yM3vItWR/4=", "requires": { "core-js": "^2.4.0", - "regenerator-runtime": "^0.10.0" + "regenerator-runtime": "^0.11.0" } }, "balanced-match": { @@ -190,24 +225,76 @@ "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz", "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=" }, + "base": { + "version": "0.11.2", + "resolved": "https://registry.npmjs.org/base/-/base-0.11.2.tgz", + "integrity": "sha512-5T6P4xPgpp0YDFvSWwEZ4NoE3aM4QBQXDzmVbraCkFj8zHM+mba8SyqB5DbZWyR7mYHo6Y7BdQo3MoA4m0TeQg==", + "requires": { + "cache-base": "^1.0.1", + "class-utils": "^0.3.5", + "component-emitter": "^1.2.1", + "define-property": "^1.0.0", + "isobject": "^3.0.1", + "mixin-deep": "^1.2.0", + "pascalcase": "^0.1.1" + }, + "dependencies": { + "define-property": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-1.0.0.tgz", + "integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=", + "requires": { + "is-descriptor": "^1.0.0" + } + }, + "is-accessor-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz", + "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-data-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz", + "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-descriptor": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz", + "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", + "requires": { + "is-accessor-descriptor": "^1.0.0", + "is-data-descriptor": "^1.0.0", + "kind-of": "^6.0.2" + } + } + } + }, "base64-js": { - "version": "1.2.3", - "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-1.2.3.tgz", - "integrity": "sha512-MsAhsUW1GxCdgYSO6tAfZrNapmUKk7mWx/k5mFY/A1gBtkaCaNapTg+FExCw1r9yeaZhqx/xPg43xgTFH6KL5w==" + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-1.3.0.tgz", + "integrity": "sha512-ccav/yGvoa80BQDljCxsmmQ3Xvx60/UpBIij5QN21W3wBi/hhIC9OoO+KLpu9IJTS9j4DRVJ3aDDF9cMSoa2lw==" }, "bcrypt-pbkdf": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.1.tgz", - "integrity": "sha1-Y7xdy2EzG5K8Bf1SiVPDNGKgb40=", - "optional": true, + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.2.tgz", + "integrity": "sha1-pDAdOJtqQ/m2f/PKEaP2Y342Dp4=", "requires": { "tweetnacl": "^0.14.3" } }, "bindings": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/bindings/-/bindings-1.3.0.tgz", - "integrity": "sha512-DpLh5EzMR2kzvX1KIlVC0VkC3iZtHKTgdtZ0a3pglBZdaQFjt5S9g9xd1lE+YvXyfd6mtCeRnrUfOLYiTMlNSw==" + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/bindings/-/bindings-1.4.0.tgz", + "integrity": "sha512-7znEVX22Djn+nYjxCWKDne0RRloa9XfYa84yk3s+HkE3LpDYZmhArYr9O9huBoHY3/oXispx5LorIX7Sl2CgSQ==", + "requires": { + "file-uri-to-path": "1.0.0" + } }, "bip66": { "version": "1.1.5", @@ -235,9 +322,9 @@ } }, "bluebird": { - "version": "3.5.1", - "resolved": "https://registry.npmjs.org/bluebird/-/bluebird-3.5.1.tgz", - "integrity": "sha512-MKiLiV+I1AA596t9w1sQJ8jkiSr5+ZKi0WKrYGUn6d1Fx+Ij4tIj+m2WMQSGczs5jZVxV339chE8iwk6F64wjA==" + "version": "3.5.3", + "resolved": "https://registry.npmjs.org/bluebird/-/bluebird-3.5.3.tgz", + "integrity": "sha512-/qKPUQlaW1OyR51WeCPBvRnAlnZFUJkCSG5HzGnuIqhgyJtF+T94lFnn33eiazjRm2LAHVy2guNnaq48X9SJuw==" }, "bn.js": { "version": "4.11.8", @@ -245,28 +332,20 @@ "integrity": "sha512-ItfYfPLkWHUjckQCk8xC+LwxgK8NYcXywGigJgSwOP8Y2iyWT4f2vsZnoOXTTbo+o5yXmIUJ4gn5538SO5S3gA==" }, "body-parser": { - "version": "1.18.2", - "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.18.2.tgz", - "integrity": "sha1-h2eKGdhLR9hZuDGZvVm84iKxBFQ=", + "version": "1.18.3", + "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.18.3.tgz", + "integrity": "sha1-WykhmP/dVTs6DyDe0FkrlWlVyLQ=", "requires": { "bytes": "3.0.0", "content-type": "~1.0.4", "debug": "2.6.9", - "depd": "~1.1.1", - "http-errors": "~1.6.2", - "iconv-lite": "0.4.19", + "depd": "~1.1.2", + "http-errors": "~1.6.3", + "iconv-lite": "0.4.23", "on-finished": "~2.3.0", - "qs": "6.5.1", - "raw-body": "2.3.2", - "type-is": "~1.6.15" - } - }, - "boom": { - "version": "4.3.1", - "resolved": "https://registry.npmjs.org/boom/-/boom-4.3.1.tgz", - "integrity": "sha1-T4owBctKfjiJ90kDD9JbluAdLjE=", - "requires": { - "hoek": "4.x.x" + "qs": "6.5.2", + "raw-body": "2.3.3", + "type-is": "~1.6.16" } }, "brace-expansion": { @@ -278,15 +357,42 @@ "concat-map": "0.0.1" } }, + "braces": { + "version": "2.3.2", + "resolved": "https://registry.npmjs.org/braces/-/braces-2.3.2.tgz", + "integrity": "sha512-aNdbnj9P8PjdXU4ybaWLK2IF3jc/EoDYbC7AazW6to3TRsfXxscC9UXOB5iDiEQrkyIbWp2SLQda4+QAa7nc3w==", + "requires": { + "arr-flatten": "^1.1.0", + "array-unique": "^0.3.2", + "extend-shallow": "^2.0.1", + "fill-range": "^4.0.0", + "isobject": "^3.0.1", + "repeat-element": "^1.1.2", + "snapdragon": "^0.8.1", + "snapdragon-node": "^2.0.1", + "split-string": "^3.0.2", + "to-regex": "^3.0.1" + }, + "dependencies": { + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "requires": { + "is-extendable": "^0.1.0" + } + } + } + }, "brorand": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/brorand/-/brorand-1.1.0.tgz", "integrity": "sha1-EsJe/kCkXjwyPrhnWgoM5XsiNx8=" }, "browserify-aes": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/browserify-aes/-/browserify-aes-1.1.1.tgz", - "integrity": "sha512-UGnTYAnB2a3YuYKIRy1/4FB2HdM866E0qC46JXvVTYKlBlZlnvfpSfY6OKfXZAkv70eJ2a1SqzpAo5CRhZGDFg==", + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/browserify-aes/-/browserify-aes-1.2.0.tgz", + "integrity": "sha512-+7CHXqGuspUn/Sl5aO7Ea0xWGAtETPXNSAjHo48JfLdPWcMng33Xe4znFvQweqc/uzk5zSOI3H52CYnjCfb5hA==", "requires": { "buffer-xor": "^1.0.3", "cipher-base": "^1.0.0", @@ -297,9 +403,9 @@ } }, "browserify-cipher": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/browserify-cipher/-/browserify-cipher-1.0.0.tgz", - "integrity": "sha1-mYgkSHS/XtTijalWZtzWasj8Njo=", + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/browserify-cipher/-/browserify-cipher-1.0.1.tgz", + "integrity": "sha512-sPhkz0ARKbf4rRQt2hTpAHqn47X3llLkUGn+xEJzLjwY8LRs2p0v7ljvI5EyoRO/mexrNunNECisZs+gw2zz1w==", "requires": { "browserify-aes": "^1.0.4", "browserify-des": "^1.0.0", @@ -307,13 +413,14 @@ } }, "browserify-des": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/browserify-des/-/browserify-des-1.0.0.tgz", - "integrity": "sha1-2qJ3cXRwki7S/hhZQRihdUOXId0=", + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/browserify-des/-/browserify-des-1.0.2.tgz", + "integrity": "sha512-BioO1xf3hFwz4kc6iBhI3ieDFompMhrMlnDFC4/0/vd5MokpuAc3R+LYbwTA9A5Yc9pq9UYPqffKpW2ObuwX5A==", "requires": { "cipher-base": "^1.0.1", "des.js": "^1.0.0", - "inherits": "^2.0.1" + "inherits": "^2.0.1", + "safe-buffer": "^5.1.2" } }, "browserify-rsa": { @@ -326,11 +433,12 @@ } }, "browserify-sha3": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/browserify-sha3/-/browserify-sha3-0.0.1.tgz", - "integrity": "sha1-P/NKMAbvFcD7NWflQbkaI0ASPRE=", + "version": "0.0.4", + "resolved": "https://registry.npmjs.org/browserify-sha3/-/browserify-sha3-0.0.4.tgz", + "integrity": "sha1-CGxHuMgjFsnUcCLCYYWVRXbdjiY=", "requires": { - "js-sha3": "^0.3.1" + "js-sha3": "^0.6.1", + "safe-buffer": "^5.1.1" } }, "browserify-sign": { @@ -348,19 +456,38 @@ } }, "buffer": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/buffer/-/buffer-5.1.0.tgz", - "integrity": "sha512-YkIRgwsZwJWTnyQrsBTWefizHh+8GYj3kbL1BTiAQ/9pwpino0G7B2gp5tx/FUBqUlvtxV85KNR3mwfAtv15Yw==", + "version": "5.2.1", + "resolved": "https://registry.npmjs.org/buffer/-/buffer-5.2.1.tgz", + "integrity": "sha512-c+Ko0loDaFfuPWiL02ls9Xd3GO3cPVmUobQ6t3rXNUk304u6hGq+8N/kFi+QEIKhzK3uwolVhLzszmfLmMLnqg==", "requires": { "base64-js": "^1.0.2", "ieee754": "^1.1.4" } }, + "buffer-alloc": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/buffer-alloc/-/buffer-alloc-1.2.0.tgz", + "integrity": "sha512-CFsHQgjtW1UChdXgbyJGtnm+O/uLQeZdtbDo8mfUgYXCHSM1wgrVxXm6bSyrUuErEb+4sYVGCzASBRot7zyrow==", + "requires": { + "buffer-alloc-unsafe": "^1.1.0", + "buffer-fill": "^1.0.0" + } + }, + "buffer-alloc-unsafe": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/buffer-alloc-unsafe/-/buffer-alloc-unsafe-1.1.0.tgz", + "integrity": "sha512-TEM2iMIEQdJ2yjPJoSIsldnleVaAk1oW3DBVUykyOLsEsFmEc9kn+SFFPz+gl54KQNxlDnAwCXosOS9Okx2xAg==" + }, "buffer-crc32": { "version": "0.2.13", "resolved": "https://registry.npmjs.org/buffer-crc32/-/buffer-crc32-0.2.13.tgz", "integrity": "sha1-DTM+PwDqxQqhRUq9MO+MKl2ackI=" }, + "buffer-fill": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/buffer-fill/-/buffer-fill-1.0.0.tgz", + "integrity": "sha1-+PeLdniYiO858gXNY39o5wISKyw=" + }, "buffer-to-arraybuffer": { "version": "0.0.5", "resolved": "https://registry.npmjs.org/buffer-to-arraybuffer/-/buffer-to-arraybuffer-0.0.5.tgz", @@ -371,12 +498,6 @@ "resolved": "https://registry.npmjs.org/buffer-xor/-/buffer-xor-1.0.3.tgz", "integrity": "sha1-JuYe0UIvtw3ULm42cp7VHYVf6Nk=" }, - "builtin-modules": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/builtin-modules/-/builtin-modules-1.1.1.tgz", - "integrity": "sha1-Jw8HbFpywC9bZaR9+Uxf46J4iS8=", - "dev": true - }, "byline": { "version": "5.0.0", "resolved": "https://registry.npmjs.org/byline/-/byline-5.0.0.tgz", @@ -387,19 +508,31 @@ "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.0.0.tgz", "integrity": "sha1-0ygVQE1olpn4Wk6k+odV3ROpYEg=" }, - "caller-path": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/caller-path/-/caller-path-0.1.0.tgz", - "integrity": "sha1-lAhe9jWB7NPaqSREqP6U6CV3dR8=", - "dev": true, + "cache-base": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/cache-base/-/cache-base-1.0.1.tgz", + "integrity": "sha512-AKcdTnFSWATd5/GCPRxr2ChwIJ85CeyrEyjRHlKxQ56d4XJMGym0uAiKn0xbLOGOl3+yRpOTi484dVCEc5AUzQ==", "requires": { - "callsites": "^0.2.0" + "collection-visit": "^1.0.0", + "component-emitter": "^1.2.1", + "get-value": "^2.0.6", + "has-value": "^1.0.0", + "isobject": "^3.0.1", + "set-value": "^2.0.0", + "to-object-path": "^0.3.0", + "union-value": "^1.0.0", + "unset-value": "^1.0.0" } }, + "call-me-maybe": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/call-me-maybe/-/call-me-maybe-1.0.1.tgz", + "integrity": "sha1-JtII6onje1y95gJQoV8DHBak1ms=" + }, "callsites": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/callsites/-/callsites-0.2.0.tgz", - "integrity": "sha1-r6uWJikQp/M8GaV3WCXGnzTjUMo=", + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/callsites/-/callsites-3.0.0.tgz", + "integrity": "sha512-tWnkwu9YEq2uzlBDI4RcLn8jrFvF9AOi8PxDNU3hZZjJcjkcRAq3vCI+vZcg1SuxISDYe86k9VZFwAxDiJGoAw==", "dev": true }, "caseless": { @@ -408,13 +541,13 @@ "integrity": "sha1-G2gcIf+EAzyCZUMJBolCDRhxUdw=" }, "chalk": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.1.0.tgz", - "integrity": "sha512-LUHGS/dge4ujbXMJrnihYMcL4AoOweGnw9Tp3kQuqy1Kx5c1qKjqvMJZ6nVJPMWJtKCTN72ZogH3oeSO9g9rXQ==", + "version": "2.4.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz", + "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==", "requires": { - "ansi-styles": "^3.1.0", + "ansi-styles": "^3.2.1", "escape-string-regexp": "^1.0.5", - "supports-color": "^4.0.0" + "supports-color": "^5.3.0" } }, "chardet": { @@ -432,11 +565,26 @@ "safe-buffer": "^5.0.1" } }, - "circular-json": { - "version": "0.3.3", - "resolved": "https://registry.npmjs.org/circular-json/-/circular-json-0.3.3.tgz", - "integrity": "sha512-UZK3NBx2Mca+b5LsG7bY183pHWt5Y1xts4P3Pz7ENTwGVnJOUWbRb3ocjvX7hx9tq/yTAdclXm9sZ38gNuem4A==", - "dev": true + "class-utils": { + "version": "0.3.6", + "resolved": "https://registry.npmjs.org/class-utils/-/class-utils-0.3.6.tgz", + "integrity": "sha512-qOhPa/Fj7s6TY8H8esGu5QNpMMQxz79h+urzrNYN6mn+9BnxlDGf5QZ+XeCDsxSjPqsSR56XOZOJmpeurnLMeg==", + "requires": { + "arr-union": "^3.1.0", + "define-property": "^0.2.5", + "isobject": "^3.0.0", + "static-extend": "^0.1.1" + }, + "dependencies": { + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "requires": { + "is-descriptor": "^0.1.0" + } + } + } }, "cli-cursor": { "version": "2.1.0", @@ -453,17 +601,21 @@ "integrity": "sha1-/xnt6Kml5XkyQUewwR8PvLq+1jk=", "dev": true }, - "co": { - "version": "4.6.0", - "resolved": "https://registry.npmjs.org/co/-/co-4.6.0.tgz", - "integrity": "sha1-bqa989hTrlTMuOR7+gvz+QMfsYQ=" + "collection-visit": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/collection-visit/-/collection-visit-1.0.0.tgz", + "integrity": "sha1-S8A3PBZLwykbTTaMgpzxqApZ3KA=", + "requires": { + "map-visit": "^1.0.0", + "object-visit": "^1.0.0" + } }, "color-convert": { - "version": "1.9.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.1.tgz", - "integrity": "sha512-mjGanIiwQJskCC18rPR6OmrZ6fm2Lc7PeGFYwCmy5J34wC6F1PzdGL6xeMfmgicfYcNLGuVFA3WzXtIDCQSZxQ==", + "version": "1.9.3", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.3.tgz", + "integrity": "sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==", "requires": { - "color-name": "^1.1.1" + "color-name": "1.1.3" } }, "color-name": { @@ -472,9 +624,9 @@ "integrity": "sha1-p9BVi9icQveV3UIyj3QIMcpTvCU=" }, "combined-stream": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.6.tgz", - "integrity": "sha1-cj599ugBrFYTETp+RFqbactjKBg=", + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.7.tgz", + "integrity": "sha512-brWl9y6vOB1xYPZcpZde3N9zDByXTosAeMDo4p1wzo6UMOX4vumB+TP1RZ76sfE6Md68Q0NJSrE/gbezd4Ul+w==", "requires": { "delayed-stream": "~1.0.0" } @@ -487,6 +639,11 @@ "graceful-readlink": ">= 1.0.0" } }, + "component-emitter": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/component-emitter/-/component-emitter-1.2.1.tgz", + "integrity": "sha1-E3kY1teCg/ffemt8WmPhQOaUJeY=" + }, "concat-map": { "version": "0.0.1", "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", @@ -518,10 +675,15 @@ "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz", "integrity": "sha1-4wOogrNCzD7oylE6eZmXNNqzriw=" }, + "copy-descriptor": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/copy-descriptor/-/copy-descriptor-0.1.1.tgz", + "integrity": "sha1-Z29us8OZl8LuGsOpJP1hJHSPV40=" + }, "core-js": { - "version": "2.5.4", - "resolved": "https://registry.npmjs.org/core-js/-/core-js-2.5.4.tgz", - "integrity": "sha1-8si/GB8qgLkvNgEhQpzmOi8K6uA=" + "version": "2.6.5", + "resolved": "https://registry.npmjs.org/core-js/-/core-js-2.6.5.tgz", + "integrity": "sha512-klh/kDpwX8hryYL14M9w/xei6vrv6sE8gTHDG7/T/+SEovB/G4ejwcfE/CBzO6Edsu+OETZMZ3wcX/EjUkrl5A==" }, "core-util-is": { "version": "1.0.2", @@ -529,38 +691,39 @@ "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=" }, "cors": { - "version": "2.8.4", - "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.4.tgz", - "integrity": "sha1-K9OB8usgECAQXNUOpZ2mMJBpRoY=", + "version": "2.8.5", + "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.5.tgz", + "integrity": "sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==", "requires": { "object-assign": "^4", "vary": "^1" } }, "create-ecdh": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/create-ecdh/-/create-ecdh-4.0.0.tgz", - "integrity": "sha1-iIxyNZbN92EvZJgjPuvXo1MBc30=", + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/create-ecdh/-/create-ecdh-4.0.3.tgz", + "integrity": "sha512-GbEHQPMOswGpKXM9kCWVrremUcBmjteUaQ01T9rkKCPDXfUHX0IoP9LpHYo2NPFampa4e+/pFDc3jQdxrxQLaw==", "requires": { "bn.js": "^4.1.0", "elliptic": "^6.0.0" } }, "create-hash": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/create-hash/-/create-hash-1.1.3.tgz", - "integrity": "sha1-YGBCrIuSYnUPSDyt2rD1gZFy2P0=", + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/create-hash/-/create-hash-1.2.0.tgz", + "integrity": "sha512-z00bCGNHDG8mHAkP7CtT1qVu+bFQUPjYq/4Iv3C3kWjTFV10zIjfSoeqXo9Asws8gwSHDGj/hl2u4OGIjapeCg==", "requires": { "cipher-base": "^1.0.1", "inherits": "^2.0.1", - "ripemd160": "^2.0.0", + "md5.js": "^1.3.4", + "ripemd160": "^2.0.1", "sha.js": "^2.4.0" } }, "create-hmac": { - "version": "1.1.6", - "resolved": "https://registry.npmjs.org/create-hmac/-/create-hmac-1.1.6.tgz", - "integrity": "sha1-rLniIaThe9sHbpBlfEK5PjcmzwY=", + "version": "1.1.7", + "resolved": "https://registry.npmjs.org/create-hmac/-/create-hmac-1.1.7.tgz", + "integrity": "sha512-MJG9liiZ+ogc4TzUwuvbER1JRdgvUFSB5+VR/g5h82fGaIRWMWddtKBHi7/sVhfjQZ6SehlyhvQYrcYkaUIpLg==", "requires": { "cipher-base": "^1.0.3", "create-hash": "^1.1.0", @@ -581,32 +744,6 @@ "semver": "^5.5.0", "shebang-command": "^1.2.0", "which": "^1.2.9" - }, - "dependencies": { - "semver": { - "version": "5.5.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.5.1.tgz", - "integrity": "sha512-PqpAxfrEhlSUWge8dwIp4tZnQ25DIOthpiaHNIthsjEFQD6EvqUKUDM7L8O2rShkFccYo1VjJR0coWfNkCubRw==", - "dev": true - } - } - }, - "cryptiles": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/cryptiles/-/cryptiles-3.1.2.tgz", - "integrity": "sha1-qJ+7Ig9c4l7FboxKqKT9e1sNKf4=", - "requires": { - "boom": "5.x.x" - }, - "dependencies": { - "boom": { - "version": "5.2.0", - "resolved": "https://registry.npmjs.org/boom/-/boom-5.2.0.tgz", - "integrity": "sha512-Z5BTk6ZRe4tXXQlkqftmsAUANpXmuwlsF5Oov8ThoMbQRzdGTA1ngYRW160GexgOgjsFOKJz0LYhoNi+2AMBUw==", - "requires": { - "hoek": "4.x.x" - } - } } }, "crypto-browserify": { @@ -661,6 +798,13 @@ "make-dir": "^1.0.0", "pify": "^2.3.0", "strip-dirs": "^2.0.0" + }, + "dependencies": { + "pify": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", + "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=" + } } }, "decompress-response": { @@ -734,6 +878,11 @@ "object-assign": "^4.0.1", "pinkie-promise": "^2.0.0" } + }, + "pify": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", + "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=" } } }, @@ -751,33 +900,39 @@ "object-keys": "^1.0.12" } }, - "del": { - "version": "2.2.2", - "resolved": "https://registry.npmjs.org/del/-/del-2.2.2.tgz", - "integrity": "sha1-wSyYHQZ4RshLyvhiz/kw2Qf/0ag=", - "dev": true, + "define-property": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-2.0.2.tgz", + "integrity": "sha512-jwK2UV4cnPpbcG7+VRARKTZPUWowwXA8bzH5NP6ud0oeAxyYPuGZUAC7hMugpCdz4BeSZl2Dl9k66CHJ/46ZYQ==", "requires": { - "globby": "^5.0.0", - "is-path-cwd": "^1.0.0", - "is-path-in-cwd": "^1.0.0", - "object-assign": "^4.0.1", - "pify": "^2.0.0", - "pinkie-promise": "^2.0.0", - "rimraf": "^2.2.8" + "is-descriptor": "^1.0.2", + "isobject": "^3.0.1" }, "dependencies": { - "globby": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/globby/-/globby-5.0.0.tgz", - "integrity": "sha1-69hGZ8oNuzMLmbz8aOrCvFQ3Dg0=", - "dev": true, + "is-accessor-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz", + "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", "requires": { - "array-union": "^1.0.1", - "arrify": "^1.0.0", - "glob": "^7.0.3", - "object-assign": "^4.0.1", - "pify": "^2.0.0", - "pinkie-promise": "^2.0.0" + "kind-of": "^6.0.0" + } + }, + "is-data-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz", + "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-descriptor": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz", + "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", + "requires": { + "is-accessor-descriptor": "^1.0.0", + "is-data-descriptor": "^1.0.0", + "kind-of": "^6.0.2" } } } @@ -807,19 +962,28 @@ "integrity": "sha1-l4hXRCxEdJ5CBmE+N5RiBYJqvYA=" }, "diffie-hellman": { - "version": "5.0.2", - "resolved": "https://registry.npmjs.org/diffie-hellman/-/diffie-hellman-5.0.2.tgz", - "integrity": "sha1-tYNXOScM/ias9jIJn97SoH8gnl4=", + "version": "5.0.3", + "resolved": "https://registry.npmjs.org/diffie-hellman/-/diffie-hellman-5.0.3.tgz", + "integrity": "sha512-kqag/Nl+f3GwyK25fhUMYj81BUOrZ9IuJsjIcDE5icNM9FJHAVm3VcUDxdLPoQtTuUylWm6ZIknYJwwaPxsUzg==", "requires": { "bn.js": "^4.1.0", "miller-rabin": "^4.0.0", "randombytes": "^2.0.0" } }, + "dir-glob": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/dir-glob/-/dir-glob-2.0.0.tgz", + "integrity": "sha512-37qirFDz8cA5fimp9feo43fSuRo2gHwaIn6dXL8Ber1dGwUosDrGZeCCXq57WnIqE4aQ+u3eQZzsk1yOzhdwag==", + "requires": { + "arrify": "^1.0.1", + "path-type": "^3.0.0" + } + }, "doctrine": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-2.1.0.tgz", - "integrity": "sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==", + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-3.0.0.tgz", + "integrity": "sha512-yS+Q5i3hBf7GBkd4KG8a7eBNNWNGLTaEwwYWUijIYM7zrlYDM0BFXHjjPWlWZ1Rg7UaddZeIDmi9jF3HmqiQ2w==", "dev": true, "requires": { "esutils": "^2.0.2" @@ -851,12 +1015,12 @@ "integrity": "sha1-7gHdHKwO08vH/b6jfcCo8c4ALOI=" }, "ecc-jsbn": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/ecc-jsbn/-/ecc-jsbn-0.1.1.tgz", - "integrity": "sha1-D8c6ntXw1Tw4GTOYUj735UN3dQU=", - "optional": true, + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/ecc-jsbn/-/ecc-jsbn-0.1.2.tgz", + "integrity": "sha1-OoOpBOVDUyh4dMVkt1SThoSamMk=", "requires": { - "jsbn": "~0.1.0" + "jsbn": "~0.1.0", + "safer-buffer": "^2.1.0" } }, "ee-first": { @@ -865,9 +1029,9 @@ "integrity": "sha1-WQxhFWsK4vTwJVcyoViyZrxWsh0=" }, "elliptic": { - "version": "6.4.0", - "resolved": "https://registry.npmjs.org/elliptic/-/elliptic-6.4.0.tgz", - "integrity": "sha1-ysmvh2LIWDYYcAPI3+GT5eLq5d8=", + "version": "6.4.1", + "resolved": "https://registry.npmjs.org/elliptic/-/elliptic-6.4.1.tgz", + "integrity": "sha512-BsXLz5sqX8OHcsh7CqBMztyXARmGQ3LWPtGjJi6DiJHq5C/qvi9P3OqgswKSDftbu8+IoI/QDTAm2fFnQ9SZSQ==", "requires": { "bn.js": "^4.4.0", "brorand": "^1.0.1", @@ -878,6 +1042,12 @@ "minimalistic-crypto-utils": "^1.0.0" } }, + "emoji-regex": { + "version": "7.0.3", + "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-7.0.3.tgz", + "integrity": "sha512-CwBLREIQ7LvYFB0WyRvwhq5N5qPhc6PMjD6bYggFlI5YyDgl+0vxq5VHbMOFqLg7hfWzmu8T5Z1QofhmTIhItA==", + "dev": true + }, "encodeurl": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-1.0.2.tgz", @@ -892,20 +1062,20 @@ } }, "envalid": { - "version": "4.1.4", - "resolved": "https://registry.npmjs.org/envalid/-/envalid-4.1.4.tgz", - "integrity": "sha512-Xz1fNmcAFLQsUcYgoN2YmXkl9hGfLFXpvTHJKEBW/Nsqj+/4WoFnGf6wbdxJXIx5aKpdapf8XJCGrCRfrk2OZg==", - "requires": { - "chalk": "2.1.0", - "dotenv": "4.0.0", - "meant": "1.0.0", - "validator": "9.4.1" + "version": "4.2.2", + "resolved": "https://registry.npmjs.org/envalid/-/envalid-4.2.2.tgz", + "integrity": "sha512-D6RV00pb4c/eKzslI8bwCeLhBrD9GzNrAa2QRoSto9LdwEQXhsHUKfI61areFi6LvLDVFmlHnrk/SD34UJiMpg==", + "requires": { + "chalk": "^2.4.1", + "dotenv": "^6.2.0", + "meant": "^1.0.1", + "validator": "^10.11.0" }, "dependencies": { "dotenv": { - "version": "4.0.0", - "resolved": "http://registry.npmjs.org/dotenv/-/dotenv-4.0.0.tgz", - "integrity": "sha1-hk7xN5rO1Vzm+V3r7NzhefegzR0=" + "version": "6.2.0", + "resolved": "https://registry.npmjs.org/dotenv/-/dotenv-6.2.0.tgz", + "integrity": "sha512-HygQCKUBSFl8wKQZBSemMywRWcEDNidvNbjGVyZu3nbZ8qq9ubiPoGLMdRDpfSrpkkm9BXYFkpKxxFX38o/76w==" } } }, @@ -919,27 +1089,28 @@ } }, "es-abstract": { - "version": "1.12.0", - "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.12.0.tgz", - "integrity": "sha512-C8Fx/0jFmV5IPoMOFPA9P9G5NtqW+4cOPit3MIuvR2t7Ag2K15EJTpxnHAYTzL+aYQJIESYeXZmDBfOBE1HcpA==", + "version": "1.13.0", + "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.13.0.tgz", + "integrity": "sha512-vDZfg/ykNxQVwup/8E1BZhVzFfBxs9NqMzGcvIJrqg5k2/5Za2bWo40dK2J1pgLngZ7c+Shh8lwYtLGyrwPutg==", "dev": true, "requires": { - "es-to-primitive": "^1.1.1", + "es-to-primitive": "^1.2.0", "function-bind": "^1.1.1", - "has": "^1.0.1", - "is-callable": "^1.1.3", - "is-regex": "^1.0.4" + "has": "^1.0.3", + "is-callable": "^1.1.4", + "is-regex": "^1.0.4", + "object-keys": "^1.0.12" } }, "es-to-primitive": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/es-to-primitive/-/es-to-primitive-1.1.1.tgz", - "integrity": "sha1-RTVSSKiJeQNLZ5Lhm7gfK3l13Q0=", + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/es-to-primitive/-/es-to-primitive-1.2.0.tgz", + "integrity": "sha512-qZryBOJjV//LaxLTV6UC//WewneB3LcXOL9NP++ozKVXsIIIpm/2c13UDiD9Jp2eThsecw9m3jPqDwTyobcdbg==", "dev": true, "requires": { - "is-callable": "^1.1.1", + "is-callable": "^1.1.4", "is-date-object": "^1.0.1", - "is-symbol": "^1.0.1" + "is-symbol": "^1.0.2" } }, "escape-html": { @@ -953,94 +1124,74 @@ "integrity": "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=" }, "escodegen": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/escodegen/-/escodegen-1.8.1.tgz", - "integrity": "sha1-WltTr0aTEQvrsIZ6o0MN07cKEBg=", + "version": "1.11.0", + "resolved": "https://registry.npmjs.org/escodegen/-/escodegen-1.11.0.tgz", + "integrity": "sha512-IeMV45ReixHS53K/OmfKAIztN/igDHzTJUhZM3k1jMhIZWjk45SMwAtBsEXiJp3vSPmTcu6CXn7mDvFHRN66fw==", "requires": { - "esprima": "^2.7.1", - "estraverse": "^1.9.1", + "esprima": "^3.1.3", + "estraverse": "^4.2.0", "esutils": "^2.0.2", "optionator": "^0.8.1", - "source-map": "~0.2.0" + "source-map": "~0.6.1" } }, "eslint": { - "version": "5.6.0", - "resolved": "https://registry.npmjs.org/eslint/-/eslint-5.6.0.tgz", - "integrity": "sha512-/eVYs9VVVboX286mBK7bbKnO1yamUy2UCRjiY6MryhQL2PaaXCExsCQ2aO83OeYRhU2eCU/FMFP+tVMoOrzNrA==", + "version": "5.14.1", + "resolved": "https://registry.npmjs.org/eslint/-/eslint-5.14.1.tgz", + "integrity": "sha512-CyUMbmsjxedx8B0mr79mNOqetvkbij/zrXnFeK2zc3pGRn3/tibjiNAv/3UxFEyfMDjh+ZqTrJrEGBFiGfD5Og==", "dev": true, "requires": { "@babel/code-frame": "^7.0.0", - "ajv": "^6.5.3", + "ajv": "^6.9.1", "chalk": "^2.1.0", "cross-spawn": "^6.0.5", - "debug": "^3.1.0", - "doctrine": "^2.1.0", + "debug": "^4.0.1", + "doctrine": "^3.0.0", "eslint-scope": "^4.0.0", "eslint-utils": "^1.3.1", "eslint-visitor-keys": "^1.0.0", - "espree": "^4.0.0", + "espree": "^5.0.1", "esquery": "^1.0.1", "esutils": "^2.0.2", - "file-entry-cache": "^2.0.0", + "file-entry-cache": "^5.0.1", "functional-red-black-tree": "^1.0.1", "glob": "^7.1.2", "globals": "^11.7.0", "ignore": "^4.0.6", + "import-fresh": "^3.0.0", "imurmurhash": "^0.1.4", - "inquirer": "^6.1.0", - "is-resolvable": "^1.1.0", + "inquirer": "^6.2.2", "js-yaml": "^3.12.0", "json-stable-stringify-without-jsonify": "^1.0.1", "levn": "^0.3.0", - "lodash": "^4.17.5", + "lodash": "^4.17.11", "minimatch": "^3.0.4", "mkdirp": "^0.5.1", "natural-compare": "^1.4.0", "optionator": "^0.8.2", "path-is-inside": "^1.0.2", - "pluralize": "^7.0.0", "progress": "^2.0.0", - "regexpp": "^2.0.0", - "require-uncached": "^1.0.3", + "regexpp": "^2.0.1", "semver": "^5.5.1", "strip-ansi": "^4.0.0", "strip-json-comments": "^2.0.1", - "table": "^4.0.3", + "table": "^5.2.3", "text-table": "^0.2.0" }, "dependencies": { - "ajv": { - "version": "6.5.3", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.5.3.tgz", - "integrity": "sha512-LqZ9wY+fx3UMiiPd741yB2pj3hhil+hQc8taf4o2QGRFpWgZ2V5C8HA165DY9sS3fJwsk7uT7ZlFEyC3Ig3lLg==", - "dev": true, - "requires": { - "fast-deep-equal": "^2.0.1", - "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.4.1", - "uri-js": "^4.2.2" - } - }, "debug": { - "version": "3.2.5", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.5.tgz", - "integrity": "sha512-D61LaDQPQkxJ5AUM2mbSJRbPkNs/TmdmOeLAi1hgDkpDfIfetSrjmWhccwtuResSwMbACjx/xXQofvM9CE/aeg==", + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.1.1.tgz", + "integrity": "sha512-pYAIzeRo8J6KPEaJ0VWOh5Pzkbw/RetuzehGM7QRRX5he4fPHx2rdKMB256ehJCkX+XRQm16eZLqLNS8RSZXZw==", "dev": true, "requires": { "ms": "^2.1.1" } }, - "fast-deep-equal": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-2.0.1.tgz", - "integrity": "sha1-ewUhjd+WZ79/Nwv3/bLLFf3Qqkk=", - "dev": true - }, - "json-schema-traverse": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", - "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", + "ignore": { + "version": "4.0.6", + "resolved": "https://registry.npmjs.org/ignore/-/ignore-4.0.6.tgz", + "integrity": "sha512-cyFDKrqc/YdcWFniJhzI42+AzS+gNwmUzOSFcRCQYwySuBBBy/KjuxWLZ/FHEH6Moq1NizMOBWyTcv8O4OZIMg==", "dev": true }, "ms": { @@ -1048,12 +1199,6 @@ "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.1.tgz", "integrity": "sha512-tgp+dl5cGk28utYktBsrFqA7HKgrhgPsg6Z/EfhWI4gl1Hwq8B/GmY/0oXZ6nF8hDVesS/FpnYaD/kOWhYQvyg==", "dev": true - }, - "semver": { - "version": "5.5.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.5.1.tgz", - "integrity": "sha512-PqpAxfrEhlSUWge8dwIp4tZnQ25DIOthpiaHNIthsjEFQD6EvqUKUDM7L8O2rShkFccYo1VjJR0coWfNkCubRw==", - "dev": true } } }, @@ -1069,9 +1214,9 @@ } }, "eslint-config-prettier": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/eslint-config-prettier/-/eslint-config-prettier-3.0.1.tgz", - "integrity": "sha512-vA0TB8HCx/idHXfKHYcg9J98p0Q8nkfNwNAoP7e+ywUidn6ScaFS5iqncZAHPz+/a0A/tp657ulFHFx/2JDP4Q==", + "version": "3.6.0", + "resolved": "https://registry.npmjs.org/eslint-config-prettier/-/eslint-config-prettier-3.6.0.tgz", + "integrity": "sha512-ixJ4U3uTLXwJts4rmSVW/lMXjlGwCijhBJHk8iVqKKSifeI0qgFEfWl8L63isfc8Od7EiBALF6BX3jKLluf/jQ==", "dev": true, "requires": { "get-stdin": "^6.0.0" @@ -1085,55 +1230,44 @@ "requires": { "debug": "^2.6.9", "resolve": "^1.5.0" - }, - "dependencies": { - "resolve": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.8.1.tgz", - "integrity": "sha512-AicPrAC7Qu1JxPCZ9ZgCZlY35QgFnNqc+0LtbRNxnVw4TXvjQ72wnuL9JQcEBgXkI9JM8MsT9kaQoHcpCRJOYA==", - "dev": true, - "requires": { - "path-parse": "^1.0.5" - } - } } }, "eslint-module-utils": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/eslint-module-utils/-/eslint-module-utils-2.2.0.tgz", - "integrity": "sha1-snA2LNiLGkitMIl2zn+lTphBF0Y=", + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/eslint-module-utils/-/eslint-module-utils-2.3.0.tgz", + "integrity": "sha512-lmDJgeOOjk8hObTysjqH7wyMi+nsHwwvfBykwfhjR1LNdd7C2uFJBvx4OpWYpXOw4df1yE1cDEVd1yLHitk34w==", "dev": true, "requires": { "debug": "^2.6.8", - "pkg-dir": "^1.0.0" + "pkg-dir": "^2.0.0" } }, "eslint-plugin-es": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/eslint-plugin-es/-/eslint-plugin-es-1.3.1.tgz", - "integrity": "sha512-9XcVyZiQRVeFjqHw8qHNDAZcQLqaHlOGGpeYqzYh8S4JYCWTCO3yzyen8yVmA5PratfzTRWDwCOFphtDEG+w/w==", + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/eslint-plugin-es/-/eslint-plugin-es-1.4.0.tgz", + "integrity": "sha512-XfFmgFdIUDgvaRAlaXUkxrRg5JSADoRC8IkKLc/cISeR3yHVMefFHQZpcyXXEUUPHfy5DwviBcrfqlyqEwlQVw==", "dev": true, "requires": { "eslint-utils": "^1.3.0", - "regexpp": "^2.0.0" + "regexpp": "^2.0.1" } }, "eslint-plugin-import": { - "version": "2.14.0", - "resolved": "https://registry.npmjs.org/eslint-plugin-import/-/eslint-plugin-import-2.14.0.tgz", - "integrity": "sha512-FpuRtniD/AY6sXByma2Wr0TXvXJ4nA/2/04VPlfpmUDPOpOY264x+ILiwnrk/k4RINgDAyFZByxqPUbSQ5YE7g==", + "version": "2.16.0", + "resolved": "https://registry.npmjs.org/eslint-plugin-import/-/eslint-plugin-import-2.16.0.tgz", + "integrity": "sha512-z6oqWlf1x5GkHIFgrSvtmudnqM6Q60KM4KvpWi5ubonMjycLjndvd5+8VAZIsTlHC03djdgJuyKG6XO577px6A==", "dev": true, "requires": { "contains-path": "^0.1.0", - "debug": "^2.6.8", + "debug": "^2.6.9", "doctrine": "1.5.0", - "eslint-import-resolver-node": "^0.3.1", - "eslint-module-utils": "^2.2.0", - "has": "^1.0.1", - "lodash": "^4.17.4", - "minimatch": "^3.0.3", + "eslint-import-resolver-node": "^0.3.2", + "eslint-module-utils": "^2.3.0", + "has": "^1.0.3", + "lodash": "^4.17.11", + "minimatch": "^3.0.4", "read-pkg-up": "^2.0.0", - "resolve": "^1.6.0" + "resolve": "^1.9.0" }, "dependencies": { "doctrine": { @@ -1147,12 +1281,12 @@ } }, "resolve": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.8.1.tgz", - "integrity": "sha512-AicPrAC7Qu1JxPCZ9ZgCZlY35QgFnNqc+0LtbRNxnVw4TXvjQ72wnuL9JQcEBgXkI9JM8MsT9kaQoHcpCRJOYA==", + "version": "1.10.0", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.10.0.tgz", + "integrity": "sha512-3sUr9aq5OfSg2S9pNtPA9hL1FVEAjvfOC4leW0SNf/mpnaakz2a9femSd6LqAww2RaFctwyf1lCqnTHuF1rxDg==", "dev": true, "requires": { - "path-parse": "^1.0.5" + "path-parse": "^1.0.6" } } } @@ -1171,27 +1305,27 @@ "semver": "^5.5.0" }, "dependencies": { + "ignore": { + "version": "4.0.6", + "resolved": "https://registry.npmjs.org/ignore/-/ignore-4.0.6.tgz", + "integrity": "sha512-cyFDKrqc/YdcWFniJhzI42+AzS+gNwmUzOSFcRCQYwySuBBBy/KjuxWLZ/FHEH6Moq1NizMOBWyTcv8O4OZIMg==", + "dev": true + }, "resolve": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.8.1.tgz", - "integrity": "sha512-AicPrAC7Qu1JxPCZ9ZgCZlY35QgFnNqc+0LtbRNxnVw4TXvjQ72wnuL9JQcEBgXkI9JM8MsT9kaQoHcpCRJOYA==", + "version": "1.10.0", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.10.0.tgz", + "integrity": "sha512-3sUr9aq5OfSg2S9pNtPA9hL1FVEAjvfOC4leW0SNf/mpnaakz2a9femSd6LqAww2RaFctwyf1lCqnTHuF1rxDg==", "dev": true, "requires": { - "path-parse": "^1.0.5" + "path-parse": "^1.0.6" } - }, - "semver": { - "version": "5.5.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.5.1.tgz", - "integrity": "sha512-PqpAxfrEhlSUWge8dwIp4tZnQ25DIOthpiaHNIthsjEFQD6EvqUKUDM7L8O2rShkFccYo1VjJR0coWfNkCubRw==", - "dev": true } } }, "eslint-plugin-prettier": { - "version": "2.6.2", - "resolved": "https://registry.npmjs.org/eslint-plugin-prettier/-/eslint-plugin-prettier-2.6.2.tgz", - "integrity": "sha512-tGek5clmW5swrAx1mdPYM8oThrBE83ePh7LeseZHBWfHVGrHPhKn7Y5zgRMbU/9D5Td9K4CEmUPjGxA7iw98Og==", + "version": "2.7.0", + "resolved": "https://registry.npmjs.org/eslint-plugin-prettier/-/eslint-plugin-prettier-2.7.0.tgz", + "integrity": "sha512-CStQYJgALoQBw3FsBzH0VOVDRnJ/ZimUlpLm226U8qgqYJfPOY/CPK6wyRInMxh73HSKg5wyRwdS4BVYYHwokA==", "dev": true, "requires": { "fast-diff": "^1.1.1", @@ -1212,14 +1346,6 @@ "requires": { "esrecurse": "^4.1.0", "estraverse": "^4.1.1" - }, - "dependencies": { - "estraverse": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-4.2.0.tgz", - "integrity": "sha1-De4/7TH81GlhjOc0IJn8GvoL2xM=", - "dev": true - } } }, "eslint-utils": { @@ -1235,27 +1361,20 @@ "dev": true }, "espree": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/espree/-/espree-4.0.0.tgz", - "integrity": "sha512-kapdTCt1bjmspxStVKX6huolXVV5ZfyZguY1lcfhVVZstce3bqxH9mcLzNn3/mlgW6wQ732+0fuG9v7h0ZQoKg==", + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/espree/-/espree-5.0.1.tgz", + "integrity": "sha512-qWAZcWh4XE/RwzLJejfcofscgMc9CamR6Tn1+XRXNzrvUSSbiAjGOI/fggztjIi7y9VLPqnICMIPiGyr8JaZ0A==", "dev": true, "requires": { - "acorn": "^5.6.0", - "acorn-jsx": "^4.1.1" - }, - "dependencies": { - "acorn": { - "version": "5.7.3", - "resolved": "https://registry.npmjs.org/acorn/-/acorn-5.7.3.tgz", - "integrity": "sha512-T/zvzYRfbVojPWahDsE5evJdHb3oJoQfFbsrKM7w5Zcs++Tr257tia3BmMP8XYVjp1S9RZXQMh7gao96BlqZOw==", - "dev": true - } + "acorn": "^6.0.7", + "acorn-jsx": "^5.0.0", + "eslint-visitor-keys": "^1.0.0" } }, "esprima": { - "version": "2.7.3", - "resolved": "https://registry.npmjs.org/esprima/-/esprima-2.7.3.tgz", - "integrity": "sha1-luO3DVd59q1JzQMmc9HDEnZ7pYE=" + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/esprima/-/esprima-3.1.3.tgz", + "integrity": "sha1-/cpRzuYTOJXjyI1TXOSdv/YqRjM=" }, "esquery": { "version": "1.0.1", @@ -1264,14 +1383,6 @@ "dev": true, "requires": { "estraverse": "^4.0.0" - }, - "dependencies": { - "estraverse": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-4.2.0.tgz", - "integrity": "sha1-De4/7TH81GlhjOc0IJn8GvoL2xM=", - "dev": true - } } }, "esrecurse": { @@ -1281,20 +1392,12 @@ "dev": true, "requires": { "estraverse": "^4.1.0" - }, - "dependencies": { - "estraverse": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-4.2.0.tgz", - "integrity": "sha1-De4/7TH81GlhjOc0IJn8GvoL2xM=", - "dev": true - } } }, "estraverse": { - "version": "1.9.3", - "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-1.9.3.tgz", - "integrity": "sha1-r2fy3JIlgkFZUJJgkaQAXSnJu0Q=" + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-4.2.0.tgz", + "integrity": "sha1-De4/7TH81GlhjOc0IJn8GvoL2xM=" }, "esutils": { "version": "2.0.2", @@ -1326,18 +1429,18 @@ "integrity": "sha1-L9w1dvIykDNYl26znaeDIT/5Uj8=" }, "ethereumjs-tx": { - "version": "1.3.4", - "resolved": "https://registry.npmjs.org/ethereumjs-tx/-/ethereumjs-tx-1.3.4.tgz", - "integrity": "sha512-kOgUd5jC+0tgV7t52UDECMMz9Uf+Lro+6fSpCvzWemtXfMEcwI3EOxf5mVPMRbTFkMMhuERokNNVF3jItAjidg==", + "version": "1.3.7", + "resolved": "https://registry.npmjs.org/ethereumjs-tx/-/ethereumjs-tx-1.3.7.tgz", + "integrity": "sha512-wvLMxzt1RPhAQ9Yi3/HKZTn0FZYpnsmQdbKYfUUpi4j1SEIcbkd9tndVjcPrufY3V7j2IebOpC00Zp2P/Ay2kA==", "requires": { "ethereum-common": "^0.0.18", "ethereumjs-util": "^5.0.0" } }, "ethereumjs-util": { - "version": "5.1.5", - "resolved": "https://registry.npmjs.org/ethereumjs-util/-/ethereumjs-util-5.1.5.tgz", - "integrity": "sha512-xPaSEATYJpMTCGowIt0oMZwFP4R1bxd6QsWgkcDvFL0JtXsr39p32WEcD14RscCjfP41YXZPCVWA4yAg0nrJmw==", + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/ethereumjs-util/-/ethereumjs-util-5.2.0.tgz", + "integrity": "sha512-CJAKdI0wgMbQFLlLRtZKGcy/L6pzVRgelIZqRqNbuVFM3K9VEnyfbcvz0ncWMRNCe4kaHWjwRYQcYMucmwsnWA==", "requires": { "bn.js": "^4.11.0", "create-hash": "^1.1.2", @@ -1365,9 +1468,9 @@ } }, "ethjs-util": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/ethjs-util/-/ethjs-util-0.1.4.tgz", - "integrity": "sha1-HItoeSV0RO9NPz+7rC3tEs2ZfZM=", + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/ethjs-util/-/ethjs-util-0.1.6.tgz", + "integrity": "sha512-CUnVOQq7gSpDHZVVrQW8ExxUETWrnrvXYvYz55wOU8Uj4VCgw56XC2B/fVqQN+f7gmrnRHSLVnFAwsCuNwji8w==", "requires": { "is-hex-prefixed": "1.0.0", "strip-hex-prefix": "1.0.0" @@ -1387,21 +1490,53 @@ "safe-buffer": "^5.1.1" } }, - "expand-template": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/expand-template/-/expand-template-1.0.3.tgz", - "integrity": "sha1-bDAzIxd6YrGyLAcCefeGEoe2mxo=" - }, - "express": { - "version": "4.16.3", - "resolved": "https://registry.npmjs.org/express/-/express-4.16.3.tgz", - "integrity": "sha1-avilAjUNsyRuzEvs9rWjTSL37VM=", + "expand-brackets": { + "version": "2.1.4", + "resolved": "https://registry.npmjs.org/expand-brackets/-/expand-brackets-2.1.4.tgz", + "integrity": "sha1-t3c14xXOMPa27/D4OwQVGiJEliI=", "requires": { - "accepts": "~1.3.5", - "array-flatten": "1.1.1", - "body-parser": "1.18.2", - "content-disposition": "0.5.2", - "content-type": "~1.0.4", + "debug": "^2.3.3", + "define-property": "^0.2.5", + "extend-shallow": "^2.0.1", + "posix-character-classes": "^0.1.0", + "regex-not": "^1.0.0", + "snapdragon": "^0.8.1", + "to-regex": "^3.0.1" + }, + "dependencies": { + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "requires": { + "is-descriptor": "^0.1.0" + } + }, + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "requires": { + "is-extendable": "^0.1.0" + } + } + } + }, + "expand-template": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/expand-template/-/expand-template-1.1.1.tgz", + "integrity": "sha512-cebqLtV8KOZfw0UI8TEFWxtczxxC1jvyUvx6H4fyp1K1FN7A4Q+uggVUlOsI1K8AGU0rwOGqP8nCapdrw8CYQg==" + }, + "express": { + "version": "4.16.4", + "resolved": "https://registry.npmjs.org/express/-/express-4.16.4.tgz", + "integrity": "sha512-j12Uuyb4FMrd/qQAm6uCHAkPtO8FDTRJZBDd5D2KOL2eLaz1yUNdUB/NOIyq0iU4q4cFarsUCrnFDPBcnksuOg==", + "requires": { + "accepts": "~1.3.5", + "array-flatten": "1.1.1", + "body-parser": "1.18.3", + "content-disposition": "0.5.2", + "content-type": "~1.0.4", "cookie": "0.3.1", "cookie-signature": "1.0.6", "debug": "2.6.9", @@ -1416,10 +1551,10 @@ "on-finished": "~2.3.0", "parseurl": "~1.3.2", "path-to-regexp": "0.1.7", - "proxy-addr": "~2.0.3", - "qs": "6.5.1", + "proxy-addr": "~2.0.4", + "qs": "6.5.2", "range-parser": "~1.2.0", - "safe-buffer": "5.1.1", + "safe-buffer": "5.1.2", "send": "0.16.2", "serve-static": "1.13.2", "setprototypeof": "1.1.0", @@ -1429,11 +1564,6 @@ "vary": "~1.1.2" }, "dependencies": { - "setprototypeof": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.1.0.tgz", - "integrity": "sha512-BvE/TwpZX4FXExxOxZyRGQQv651MSwmWKZGqvmPcRIjDqWub67kTKuIMx43cZZrS/cBBzwBcNDWoFxt2XEFIpQ==" - }, "statuses": { "version": "1.4.0", "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.4.0.tgz", @@ -1442,9 +1572,28 @@ } }, "extend": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.1.tgz", - "integrity": "sha1-p1Xqe8Gt/MWjHOfnYtuq3F5jZEQ=" + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz", + "integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==" + }, + "extend-shallow": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-3.0.2.tgz", + "integrity": "sha1-Jqcarwc7OfshJxcnRhMcJwQCjbg=", + "requires": { + "assign-symbols": "^1.0.0", + "is-extendable": "^1.0.1" + }, + "dependencies": { + "is-extendable": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-1.0.1.tgz", + "integrity": "sha512-arnXMxT1hhoKo9k1LZdmlNyJdDDfy2v0fXjFlmok4+i8ul/6WlbVge9bhM74OpNPQPMGUToDtz+KXa1PneJxOA==", + "requires": { + "is-plain-object": "^2.0.4" + } + } + } }, "external-editor": { "version": "3.0.3", @@ -1468,22 +1617,94 @@ } } }, + "extglob": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/extglob/-/extglob-2.0.4.tgz", + "integrity": "sha512-Nmb6QXkELsuBr24CJSkilo6UHHgbekK5UiZgfE6UHD3Eb27YC6oD+bhcT+tJ6cl8dmsgdQxnWlcry8ksBIBLpw==", + "requires": { + "array-unique": "^0.3.2", + "define-property": "^1.0.0", + "expand-brackets": "^2.1.4", + "extend-shallow": "^2.0.1", + "fragment-cache": "^0.2.1", + "regex-not": "^1.0.0", + "snapdragon": "^0.8.1", + "to-regex": "^3.0.1" + }, + "dependencies": { + "define-property": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-1.0.0.tgz", + "integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=", + "requires": { + "is-descriptor": "^1.0.0" + } + }, + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "requires": { + "is-extendable": "^0.1.0" + } + }, + "is-accessor-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz", + "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-data-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz", + "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-descriptor": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz", + "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", + "requires": { + "is-accessor-descriptor": "^1.0.0", + "is-data-descriptor": "^1.0.0", + "kind-of": "^6.0.2" + } + } + } + }, "extsprintf": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/extsprintf/-/extsprintf-1.3.0.tgz", "integrity": "sha1-lpGEQOMEGnpBT4xS48V06zw+HgU=" }, "fast-deep-equal": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-1.1.0.tgz", - "integrity": "sha1-wFNHeBfIa1HaqFPIHgWbcz0CNhQ=" + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-2.0.1.tgz", + "integrity": "sha1-ewUhjd+WZ79/Nwv3/bLLFf3Qqkk=" }, "fast-diff": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/fast-diff/-/fast-diff-1.1.2.tgz", - "integrity": "sha512-KaJUt+M9t1qaIteSvjc6P3RbMdXsNhK61GRftR6SNxqmhthcd9MGIi4T+o0jD8LUSpSnSKXE20nLtJ3fOHxQig==", + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/fast-diff/-/fast-diff-1.2.0.tgz", + "integrity": "sha512-xJuoT5+L99XlZ8twedaRf6Ax2TgQVxvgZOYoPKqZufmJib0tL2tegPBOZb1pVNgIhlqDlA0eO0c3wBvQcmzx4w==", "dev": true }, + "fast-glob": { + "version": "2.2.6", + "resolved": "https://registry.npmjs.org/fast-glob/-/fast-glob-2.2.6.tgz", + "integrity": "sha512-0BvMaZc1k9F+MeWWMe8pL6YltFzZYcJsYU7D4JyDA6PAczaXvxqQQ/z+mDF7/4Mw01DeUc+i3CTKajnkANkV4w==", + "requires": { + "@mrmlnc/readdir-enhanced": "^2.2.1", + "@nodelib/fs.stat": "^1.1.2", + "glob-parent": "^3.1.0", + "is-glob": "^4.0.0", + "merge2": "^1.2.3", + "micromatch": "^3.1.10" + } + }, "fast-json-stable-stringify": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.0.0.tgz", @@ -1495,9 +1716,9 @@ "integrity": "sha1-PYpcZog6FqMMqGQ+hR8Zuqd5eRc=" }, "fd-slicer": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/fd-slicer/-/fd-slicer-1.0.1.tgz", - "integrity": "sha1-i1vL2ewyfFBBv5qwI/1nUPEXfmU=", + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/fd-slicer/-/fd-slicer-1.1.0.tgz", + "integrity": "sha1-JcfInLH5B3+IkbvmHY85Dq4lbx4=", "requires": { "pend": "~1.2.0" } @@ -1512,13 +1733,12 @@ } }, "file-entry-cache": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/file-entry-cache/-/file-entry-cache-2.0.0.tgz", - "integrity": "sha1-w5KZDD5oR4PYOLjISkXYoEhFg2E=", + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/file-entry-cache/-/file-entry-cache-5.0.1.tgz", + "integrity": "sha512-bCg29ictuBaKUwwArK4ouCaqDgLZcysCFLmM/Yn/FDoqndh/9vNuQfXRDvTuXKLxfD/JtZQGKFT8MGcJBK644g==", "dev": true, "requires": { - "flat-cache": "^1.2.1", - "object-assign": "^4.0.1" + "flat-cache": "^2.0.1" } }, "file-type": { @@ -1526,6 +1746,32 @@ "resolved": "https://registry.npmjs.org/file-type/-/file-type-5.2.0.tgz", "integrity": "sha1-LdvqfHP/42No365J3DOMBYwritY=" }, + "file-uri-to-path": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/file-uri-to-path/-/file-uri-to-path-1.0.0.tgz", + "integrity": "sha512-0Zt+s3L7Vf1biwWZ29aARiVYLx7iMGnEUl9x33fbB/j3jR81u/O2LbqK+Bm1CDSNDKVtJ/YjwY7TUd5SkeLQLw==" + }, + "fill-range": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-4.0.0.tgz", + "integrity": "sha1-1USBHUKPmOsGpj3EAtJAPDKMOPc=", + "requires": { + "extend-shallow": "^2.0.1", + "is-number": "^3.0.0", + "repeat-string": "^1.6.1", + "to-regex-range": "^2.1.0" + }, + "dependencies": { + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "requires": { + "is-extendable": "^0.1.0" + } + } + } + }, "finalhandler": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/finalhandler/-/finalhandler-1.1.1.tgz", @@ -1548,47 +1794,56 @@ } }, "find-up": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-1.1.2.tgz", - "integrity": "sha1-ay6YIrGizgpgq2TWEOzK1TyyTQ8=", + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", + "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", "dev": true, "requires": { - "path-exists": "^2.0.0", - "pinkie-promise": "^2.0.0" + "locate-path": "^2.0.0" } }, "flat-cache": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/flat-cache/-/flat-cache-1.3.0.tgz", - "integrity": "sha1-0wMLMrOBVPTjt+nHCfSQ9++XxIE=", + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/flat-cache/-/flat-cache-2.0.1.tgz", + "integrity": "sha512-LoQe6yDuUMDzQAEH8sgmh4Md6oZnc/7PjtwjNFSzveXqSHt6ka9fPBuso7IGf9Rz4uqnSnWiFH2B/zj24a5ReA==", "dev": true, "requires": { - "circular-json": "^0.3.1", - "del": "^2.0.2", - "graceful-fs": "^4.1.2", - "write": "^0.2.1" + "flatted": "^2.0.0", + "rimraf": "2.6.3", + "write": "1.0.3" } }, + "flatted": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/flatted/-/flatted-2.0.0.tgz", + "integrity": "sha512-R+H8IZclI8AAkSBRQJLVOsxwAoHd6WC40b4QTNWIjzAa6BXOBfQcM587MXDTVPeYaopFNWHUFLx7eNmHDSxMWg==", + "dev": true + }, "for-each": { - "version": "0.3.2", - "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.2.tgz", - "integrity": "sha1-LEBFC5NI6X8oEyJZO6lnBLmr1NQ=", + "version": "0.3.3", + "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.3.tgz", + "integrity": "sha512-jqYfLp7mo9vIyQf8ykW2v7A+2N4QjeCeI5+Dz9XraiO1ign81wjiH7Fb9vSOWvQfNtmSa4H2RoQTrrXivdUZmw==", "requires": { - "is-function": "~1.0.0" + "is-callable": "^1.1.3" } }, + "for-in": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/for-in/-/for-in-1.0.2.tgz", + "integrity": "sha1-gQaNKVqBQuwKxybG4iAMMPttXoA=" + }, "forever-agent": { "version": "0.6.1", "resolved": "https://registry.npmjs.org/forever-agent/-/forever-agent-0.6.1.tgz", "integrity": "sha1-+8cfDEGt6zf5bFd60e1C2P2sypE=" }, "form-data": { - "version": "2.3.2", - "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.3.2.tgz", - "integrity": "sha1-SXBJi+YEwgwAXU9cI67NIda0kJk=", + "version": "2.3.3", + "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.3.3.tgz", + "integrity": "sha512-1lLKB2Mu3aGP1Q/2eCOx0fNbRMe7XdwktwOruhfqqd0rIJWwN4Dh+E3hrPSlDCXnSR7UtZ1N38rVXm+6+MEhJQ==", "requires": { "asynckit": "^0.4.0", - "combined-stream": "1.0.6", + "combined-stream": "^1.0.6", "mime-types": "^2.1.12" } }, @@ -1597,18 +1852,41 @@ "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.1.2.tgz", "integrity": "sha1-mMI9qxF1ZXuMBXPozszZGw/xjIQ=" }, + "fragment-cache": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/fragment-cache/-/fragment-cache-0.2.1.tgz", + "integrity": "sha1-QpD60n8T6Jvn8zeZxrxaCr//DRk=", + "requires": { + "map-cache": "^0.2.2" + } + }, "fresh": { "version": "0.5.2", "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.5.2.tgz", "integrity": "sha1-PYyt2Q2XZWn6g1qx+OSyOhBWBac=" }, + "from2": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/from2/-/from2-2.3.0.tgz", + "integrity": "sha1-i/tVAr3kpNNs/e6gB/zKIdfjgq8=", + "requires": { + "inherits": "^2.0.1", + "readable-stream": "^2.0.0" + } + }, + "fs-constants": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/fs-constants/-/fs-constants-1.0.0.tgz", + "integrity": "sha512-y6OAwoSIf7FyjMIv94u+b5rdheZEjzR63GTyZJm5qh4Bi+2YgwLCcI/fPFZkL5PSixOt6ZNKm+w+Hfp/Bciwow==" + }, "fs-extra": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-2.1.2.tgz", - "integrity": "sha1-BGxwFjzvmq1GsOSn+kZ/si1x3jU=", + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-7.0.1.tgz", + "integrity": "sha512-YJDaCJZEnBmcbw13fvdAM9AwNOJwOzrE4pqMqBq5nFiEqXUqHwlK4B+3pUw6JNvfSPtX05xFHtYy/1ni01eGCw==", "requires": { "graceful-fs": "^4.1.2", - "jsonfile": "^2.1.0" + "jsonfile": "^4.0.0", + "universalify": "^0.1.0" } }, "fs-promise": { @@ -1620,6 +1898,25 @@ "fs-extra": "^2.0.0", "mz": "^2.6.0", "thenify-all": "^1.6.0" + }, + "dependencies": { + "fs-extra": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-2.1.2.tgz", + "integrity": "sha1-BGxwFjzvmq1GsOSn+kZ/si1x3jU=", + "requires": { + "graceful-fs": "^4.1.2", + "jsonfile": "^2.1.0" + } + }, + "jsonfile": { + "version": "2.4.0", + "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-2.4.0.tgz", + "integrity": "sha1-NzaitCi4e72gzIO1P6PWM6NcKug=", + "requires": { + "graceful-fs": "^4.1.6" + } + } } }, "fs.realpath": { @@ -1661,6 +1958,11 @@ "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-3.0.0.tgz", "integrity": "sha1-jpQ9E1jcN1VQVOy+LtsFqhdO3hQ=" }, + "get-value": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/get-value/-/get-value-2.0.6.tgz", + "integrity": "sha1-3BXKHGcjh8p2vTesCjlbogQqLCg=" + }, "getpass": { "version": "0.1.7", "resolved": "https://registry.npmjs.org/getpass/-/getpass-0.1.7.tgz", @@ -1670,9 +1972,9 @@ } }, "glob": { - "version": "7.1.2", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz", - "integrity": "sha512-MJTUg1kjuLeQCJ+ccE4Vpa6kKVXkPYJ2mOCQyUuKLcLQsdrMCpBPUi8qVE6+YuaJkozeA9NusTAw3hLr8Xe5EQ==", + "version": "7.1.3", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.3.tgz", + "integrity": "sha512-vcfuiIxogLV4DlGBHIUOwI0IbrJ8HWPc4MU7HzviGeNho/UJDfi6B5p3sHeWIQ0KGIU0Jpxi5ZHxemQfLkkAwQ==", "requires": { "fs.realpath": "^1.0.0", "inflight": "^1.0.4", @@ -1682,6 +1984,30 @@ "path-is-absolute": "^1.0.0" } }, + "glob-parent": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-3.1.0.tgz", + "integrity": "sha1-nmr2KZ2NO9K9QEMIMr0RPfkGxa4=", + "requires": { + "is-glob": "^3.1.0", + "path-dirname": "^1.0.0" + }, + "dependencies": { + "is-glob": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-3.1.0.tgz", + "integrity": "sha1-e6WuJCF4BKxwcHuWkiVnSGzD6Eo=", + "requires": { + "is-extglob": "^2.1.0" + } + } + } + }, + "glob-to-regexp": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/glob-to-regexp/-/glob-to-regexp-0.3.0.tgz", + "integrity": "sha1-jFoUlNIGbFcMw7/kSWF1rMTVAqs=" + }, "global": { "version": "4.3.2", "resolved": "https://registry.npmjs.org/global/-/global-4.3.2.tgz", @@ -1692,21 +2018,23 @@ } }, "globals": { - "version": "11.7.0", - "resolved": "https://registry.npmjs.org/globals/-/globals-11.7.0.tgz", - "integrity": "sha512-K8BNSPySfeShBQXsahYB/AbbWruVOTyVpgoIDnl8odPpeSfP2J5QO2oLFFdl2j7GfDCtZj2bMKar2T49itTPCg==", + "version": "11.11.0", + "resolved": "https://registry.npmjs.org/globals/-/globals-11.11.0.tgz", + "integrity": "sha512-WHq43gS+6ufNOEqlrDBxVEbb8ntfXrfAUU2ZOpCxrBdGKW3gyv8mCxAfIBD0DroPKGrJ2eSsXsLtY9MPntsyTw==", "dev": true }, "globby": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/globby/-/globby-6.1.0.tgz", - "integrity": "sha1-9abXDoOV4hyFj7BInWTfAkJNUGw=", + "version": "8.0.2", + "resolved": "https://registry.npmjs.org/globby/-/globby-8.0.2.tgz", + "integrity": "sha512-yTzMmKygLp8RUpG1Ymu2VXPSJQZjNAZPD4ywgYEaG7e4tBJeUQBO8OpXrf1RCNcEs5alsoJYPAMiIHP0cmeC7w==", "requires": { "array-union": "^1.0.1", - "glob": "^7.0.3", - "object-assign": "^4.0.1", - "pify": "^2.0.0", - "pinkie-promise": "^2.0.0" + "dir-glob": "2.0.0", + "fast-glob": "^2.0.2", + "glob": "^7.1.2", + "ignore": "^3.3.5", + "pify": "^3.0.0", + "slash": "^1.0.0" } }, "got": { @@ -1731,9 +2059,9 @@ } }, "graceful-fs": { - "version": "4.1.11", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.11.tgz", - "integrity": "sha1-Dovf5NHduIVNZOBOp8AOKgJuVlg=" + "version": "4.1.15", + "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.15.tgz", + "integrity": "sha512-6uHUhOPEBgQ24HM+r6b/QwWfZq+yiFcipKFrOFiBEnWdy5sdzYoi+pJeQaPI5qOLRFqWmAXUPQNsielzdLoecA==" }, "graceful-readlink": { "version": "1.0.1", @@ -1746,11 +2074,11 @@ "integrity": "sha1-qUwiJOvKwEeCoNkDVSHyRzW37JI=" }, "har-validator": { - "version": "5.0.3", - "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-5.0.3.tgz", - "integrity": "sha1-ukAsJmGU8VlW7xXg/PJCmT9qff0=", + "version": "5.1.3", + "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-5.1.3.tgz", + "integrity": "sha512-sNvOCzEQNr/qrvJgc3UG/kD4QtlHycrzwS+6mfTrrSq97BvaYcPZZI1ZSqGSPR73Cxn4LKTD4PttRwfU7jWq5g==", "requires": { - "ajv": "^5.1.0", + "ajv": "^6.5.5", "har-schema": "^2.0.0" } }, @@ -1764,9 +2092,9 @@ } }, "has-flag": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-2.0.0.tgz", - "integrity": "sha1-6CB68cx7MNRGzHC3NLXovhj4jVE=" + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", + "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=" }, "has-symbol-support-x": { "version": "1.4.2", @@ -1787,32 +2115,51 @@ "has-symbol-support-x": "^1.4.1" } }, - "hash-base": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/hash-base/-/hash-base-2.0.2.tgz", - "integrity": "sha1-ZuodhW206KVHDK32/OI65SRO8uE=", + "has-value": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/has-value/-/has-value-1.0.0.tgz", + "integrity": "sha1-GLKB2lhbHFxR3vJMkw7SmgvmsXc=", "requires": { - "inherits": "^2.0.1" + "get-value": "^2.0.6", + "has-values": "^1.0.0", + "isobject": "^3.0.0" } }, - "hash.js": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/hash.js/-/hash.js-1.1.3.tgz", - "integrity": "sha512-/UETyP0W22QILqS+6HowevwhEFJ3MBJnwTf75Qob9Wz9t0DPuisL8kW8YZMK62dHAKE1c1p+gY1TtOLY+USEHA==", + "has-values": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/has-values/-/has-values-1.0.0.tgz", + "integrity": "sha1-lbC2P+whRmGab+V/51Yo1aOe/k8=", "requires": { - "inherits": "^2.0.3", - "minimalistic-assert": "^1.0.0" + "is-number": "^3.0.0", + "kind-of": "^4.0.0" + }, + "dependencies": { + "kind-of": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-4.0.0.tgz", + "integrity": "sha1-IIE989cSkosgc3hpGkUGb65y3Vc=", + "requires": { + "is-buffer": "^1.1.5" + } + } } }, - "hawk": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/hawk/-/hawk-6.0.2.tgz", - "integrity": "sha512-miowhl2+U7Qle4vdLqDdPt9m09K6yZhkLDTWGoUiUzrQCn+mHHSmfJgAyGaLRZbPmTqfFFjRV1QWCW0VWUJBbQ==", + "hash-base": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/hash-base/-/hash-base-3.0.4.tgz", + "integrity": "sha1-X8hoaEfs1zSZQDMZprCj8/auSRg=", "requires": { - "boom": "4.x.x", - "cryptiles": "3.x.x", - "hoek": "4.x.x", - "sntp": "2.x.x" + "inherits": "^2.0.1", + "safe-buffer": "^5.0.1" + } + }, + "hash.js": { + "version": "1.1.7", + "resolved": "https://registry.npmjs.org/hash.js/-/hash.js-1.1.7.tgz", + "integrity": "sha512-taOaskGt4z4SOANNseOviYDvjEJinIkRgmp7LbKP2YTTmVxWBl87s/uzK9r+44BclBSp2X7K1hqeNfz9JbBeXA==", + "requires": { + "inherits": "^2.0.3", + "minimalistic-assert": "^1.0.1" } }, "hmac-drbg": { @@ -1825,11 +2172,6 @@ "minimalistic-crypto-utils": "^1.0.1" } }, - "hoek": { - "version": "4.2.1", - "resolved": "https://registry.npmjs.org/hoek/-/hoek-4.2.1.tgz", - "integrity": "sha512-QLg82fGkfnJ/4iy1xZ81/9SIJiq1NGFUMGs6ParyjBZr6jW2Ufj/snDqTHixNlHdPNwN2RLVD0Pi3igeK9+JfA==" - }, "hosted-git-info": { "version": "2.7.1", "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-2.7.1.tgz", @@ -1837,21 +2179,14 @@ "dev": true }, "http-errors": { - "version": "1.6.2", - "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.6.2.tgz", - "integrity": "sha1-CgAsyFcHGSp+eUbO7cERVfYOxzY=", + "version": "1.6.3", + "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.6.3.tgz", + "integrity": "sha1-i1VoC7S+KDoLW/TqLjhYC+HZMg0=", "requires": { - "depd": "1.1.1", + "depd": "~1.1.2", "inherits": "2.0.3", - "setprototypeof": "1.0.3", - "statuses": ">= 1.3.1 < 2" - }, - "dependencies": { - "depd": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/depd/-/depd-1.1.1.tgz", - "integrity": "sha1-V4O04cRZ8G+lyif5kfPQbnoxA1k=" - } + "setprototypeof": "1.1.0", + "statuses": ">= 1.4.0 < 2" } }, "http-https": { @@ -1870,20 +2205,32 @@ } }, "iconv-lite": { - "version": "0.4.19", - "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.19.tgz", - "integrity": "sha512-oTZqweIP51xaGPI4uPa56/Pri/480R+mo7SeU+YETByQNhDG55ycFyNLIgta9vXhILrxXDmF7ZGhqZIcuN0gJQ==" + "version": "0.4.23", + "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.23.tgz", + "integrity": "sha512-neyTUVFtahjf0mB3dZT77u+8O0QB89jFdnBkd5P1JgYPbPaia3gXXOVL2fq8VyU2gMMD7SaN7QukTB/pmXYvDA==", + "requires": { + "safer-buffer": ">= 2.1.2 < 3" + } }, "ieee754": { - "version": "1.1.11", - "resolved": "https://registry.npmjs.org/ieee754/-/ieee754-1.1.11.tgz", - "integrity": "sha512-VhDzCKN7K8ufStx/CLj5/PDTMgph+qwN5Pkd5i0sGnVwk56zJ0lkT8Qzi1xqWLS0Wp29DgDtNeS7v8/wMoZeHg==" + "version": "1.1.12", + "resolved": "https://registry.npmjs.org/ieee754/-/ieee754-1.1.12.tgz", + "integrity": "sha512-GguP+DRY+pJ3soyIiGPTvdiVXjZ+DbXOxGpXn3eMvNW4x4irjqXm4wHKscC+TfxSJ0yw/S1F24tqdMNsMZTiLA==" }, "ignore": { - "version": "4.0.6", - "resolved": "https://registry.npmjs.org/ignore/-/ignore-4.0.6.tgz", - "integrity": "sha512-cyFDKrqc/YdcWFniJhzI42+AzS+gNwmUzOSFcRCQYwySuBBBy/KjuxWLZ/FHEH6Moq1NizMOBWyTcv8O4OZIMg==", - "dev": true + "version": "3.3.10", + "resolved": "https://registry.npmjs.org/ignore/-/ignore-3.3.10.tgz", + "integrity": "sha512-Pgs951kaMm5GXP7MOvxERINe3gsaVjUWFm+UZPSq9xYriQAksyhg0csnS0KXSNRD5NmNdapXEpjxG49+AKh/ug==" + }, + "import-fresh": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/import-fresh/-/import-fresh-3.0.0.tgz", + "integrity": "sha512-pOnA9tfM3Uwics+SaBLCNyZZZbK+4PTu0OPZtLlMIrv17EdBoC15S9Kn8ckJ9TZTyKb3ywNE5y1yeDxxGA7nTQ==", + "dev": true, + "requires": { + "parent-module": "^1.0.0", + "resolve-from": "^4.0.0" + } }, "imurmurhash": { "version": "0.1.4", @@ -1911,30 +2258,74 @@ "integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=" }, "inquirer": { - "version": "6.2.0", - "resolved": "https://registry.npmjs.org/inquirer/-/inquirer-6.2.0.tgz", - "integrity": "sha512-QIEQG4YyQ2UYZGDC4srMZ7BjHOmNk1lR2JQj5UknBapklm6WHA+VVH7N+sUdX3A7NeCfGF8o4X1S3Ao7nAcIeg==", + "version": "6.2.2", + "resolved": "https://registry.npmjs.org/inquirer/-/inquirer-6.2.2.tgz", + "integrity": "sha512-Z2rREiXA6cHRR9KBOarR3WuLlFzlIfAEIiB45ll5SSadMg7WqOh1MKEjjndfuH5ewXdixWCxqnVfGOQzPeiztA==", "dev": true, "requires": { - "ansi-escapes": "^3.0.0", - "chalk": "^2.0.0", + "ansi-escapes": "^3.2.0", + "chalk": "^2.4.2", "cli-cursor": "^2.1.0", "cli-width": "^2.0.0", - "external-editor": "^3.0.0", + "external-editor": "^3.0.3", "figures": "^2.0.0", - "lodash": "^4.17.10", + "lodash": "^4.17.11", "mute-stream": "0.0.7", "run-async": "^2.2.0", - "rxjs": "^6.1.0", + "rxjs": "^6.4.0", "string-width": "^2.1.0", - "strip-ansi": "^4.0.0", + "strip-ansi": "^5.0.0", "through": "^2.3.6" + }, + "dependencies": { + "ansi-regex": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-4.0.0.tgz", + "integrity": "sha512-iB5Dda8t/UqpPI/IjsejXu5jOGDrzn41wJyljwPH65VCIbk6+1BzFIMJGFwTNrYXT1CrD+B4l19U7awiQ8rk7w==", + "dev": true + }, + "strip-ansi": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-5.0.0.tgz", + "integrity": "sha512-Uu7gQyZI7J7gn5qLn1Np3G9vcYGTVqB+lFTytnDJv83dd8T22aGH451P3jueT2/QemInJDfxHB5Tde5OzgG1Ow==", + "dev": true, + "requires": { + "ansi-regex": "^4.0.0" + } + } + } + }, + "into-stream": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/into-stream/-/into-stream-4.0.0.tgz", + "integrity": "sha512-i29KNyE5r0Y/UQzcQ0IbZO1MYJ53Jn0EcFRZPj5FzWKYH17kDFEOwuA+3jroymOI06SW1dEDnly9A1CAreC5dg==", + "requires": { + "from2": "^2.1.1", + "p-is-promise": "^2.0.0" } }, "ipaddr.js": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.6.0.tgz", - "integrity": "sha1-4/o1e3c9phnybpXwSdBVxyeW+Gs=" + "version": "1.8.0", + "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.8.0.tgz", + "integrity": "sha1-6qM9bd16zo9/b+DJygRA5wZzix4=" + }, + "is-accessor-descriptor": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-0.1.6.tgz", + "integrity": "sha1-qeEss66Nh2cn7u84Q/igiXtcmNY=", + "requires": { + "kind-of": "^3.0.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "requires": { + "is-buffer": "^1.1.5" + } + } + } }, "is-arrayish": { "version": "0.2.1", @@ -1942,20 +2333,33 @@ "integrity": "sha1-d8mYQFJ6qOyxqLppe4BkWnqSap0=", "dev": true }, - "is-builtin-module": { - "version": "1.0.0", - "resolved": "http://registry.npmjs.org/is-builtin-module/-/is-builtin-module-1.0.0.tgz", - "integrity": "sha1-VAVy0096wxGfj3bDDLwbHgN6/74=", - "dev": true, - "requires": { - "builtin-modules": "^1.0.0" - } + "is-buffer": { + "version": "1.1.6", + "resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-1.1.6.tgz", + "integrity": "sha512-NcdALwpXkTm5Zvvbk7owOUSvVvBKDgKP5/ewfXEznmQFfs4ZRmanOeKBTjRVjka3QFoN6XJ+9F3USqfHqTaU5w==" }, "is-callable": { "version": "1.1.4", "resolved": "https://registry.npmjs.org/is-callable/-/is-callable-1.1.4.tgz", - "integrity": "sha512-r5p9sxJjYnArLjObpjA4xu5EKI3CuKHkJXMhT7kwbpUyIFD1n5PMAsoPvWnvtZiNz7LjkYDRZhd7FlI0eMijEA==", - "dev": true + "integrity": "sha512-r5p9sxJjYnArLjObpjA4xu5EKI3CuKHkJXMhT7kwbpUyIFD1n5PMAsoPvWnvtZiNz7LjkYDRZhd7FlI0eMijEA==" + }, + "is-data-descriptor": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-0.1.4.tgz", + "integrity": "sha1-C17mSDiOLIYCgueT8YVv7D8wG1Y=", + "requires": { + "kind-of": "^3.0.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "requires": { + "is-buffer": "^1.1.5" + } + } + } }, "is-date-object": { "version": "1.0.1", @@ -1963,6 +2367,33 @@ "integrity": "sha1-mqIOtq7rv/d/vTPnTKAbM1gdOhY=", "dev": true }, + "is-descriptor": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-0.1.6.tgz", + "integrity": "sha512-avDYr0SB3DwO9zsMov0gKCESFYqCnE4hq/4z3TdUlukEy5t9C0YRq7HLrsN52NAcqXKaepeCD0n+B0arnVG3Hg==", + "requires": { + "is-accessor-descriptor": "^0.1.6", + "is-data-descriptor": "^0.1.4", + "kind-of": "^5.0.0" + }, + "dependencies": { + "kind-of": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-5.1.0.tgz", + "integrity": "sha512-NGEErnH6F2vUuXDh+OlbcKW7/wOcfdRHaZ7VWtqCztfHri/++YKmP51OdWeGPuqCOba6kk2OTe5d02VmTB80Pw==" + } + } + }, + "is-extendable": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-0.1.1.tgz", + "integrity": "sha1-YrEQ4omkcUGOPsNqYX1HLjAd/Ik=" + }, + "is-extglob": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", + "integrity": "sha1-qIwCU1eR8C7TfHahueqXc8gz+MI=" + }, "is-fullwidth-code-point": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", @@ -1974,6 +2405,14 @@ "resolved": "https://registry.npmjs.org/is-function/-/is-function-1.0.1.tgz", "integrity": "sha1-Es+5i2W1fdPRk6MSH19uL0N2ArU=" }, + "is-glob": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.0.tgz", + "integrity": "sha1-lSHHaEXMJhCoUgPd8ICpWML/q8A=", + "requires": { + "is-extglob": "^2.1.1" + } + }, "is-hex-prefixed": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/is-hex-prefixed/-/is-hex-prefixed-1.0.0.tgz", @@ -1984,40 +2423,42 @@ "resolved": "https://registry.npmjs.org/is-natural-number/-/is-natural-number-4.0.1.tgz", "integrity": "sha1-q5124dtM7VHjXeDHLr7PCfc0zeg=" }, - "is-object": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-object/-/is-object-1.0.1.tgz", - "integrity": "sha1-iVJojF7C/9awPsyF52ngKQMINHA=" - }, - "is-path-cwd": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-path-cwd/-/is-path-cwd-1.0.0.tgz", - "integrity": "sha1-0iXsIxMuie3Tj9p2dHLmLmXxEG0=", - "dev": true - }, - "is-path-in-cwd": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-path-in-cwd/-/is-path-in-cwd-1.0.1.tgz", - "integrity": "sha512-FjV1RTW48E7CWM7eE/J2NJvAEEVektecDBVBE5Hh3nM1Jd0kvhHtX68Pr3xsDf857xt3Y4AkwVULK1Vku62aaQ==", - "dev": true, + "is-number": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/is-number/-/is-number-3.0.0.tgz", + "integrity": "sha1-JP1iAaR4LPUFYcgQJ2r8fRLXEZU=", "requires": { - "is-path-inside": "^1.0.0" + "kind-of": "^3.0.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "requires": { + "is-buffer": "^1.1.5" + } + } } }, - "is-path-inside": { + "is-object": { "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-path-inside/-/is-path-inside-1.0.1.tgz", - "integrity": "sha1-jvW33lBDej/cprToZe96pVy0gDY=", - "dev": true, - "requires": { - "path-is-inside": "^1.0.1" - } + "resolved": "https://registry.npmjs.org/is-object/-/is-object-1.0.1.tgz", + "integrity": "sha1-iVJojF7C/9awPsyF52ngKQMINHA=" }, "is-plain-obj": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-1.1.0.tgz", "integrity": "sha1-caUMhCnfync8kqOQpKA7OfzVHT4=" }, + "is-plain-object": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/is-plain-object/-/is-plain-object-2.0.4.tgz", + "integrity": "sha512-h5PpgXkWitc38BBMYawTYMWJHFZJVnBquFE57xFpjB8pJFiF6gZ+bU+WyI/yqXiFR5mdLsgYNaPe8uao6Uv9Og==", + "requires": { + "isobject": "^3.0.1" + } + }, "is-promise": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/is-promise/-/is-promise-2.1.0.tgz", @@ -2033,12 +2474,6 @@ "has": "^1.0.1" } }, - "is-resolvable": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/is-resolvable/-/is-resolvable-1.1.0.tgz", - "integrity": "sha512-qgDYXFSR5WvEfuS5dMj6oTMEbrrSaM0CrFk2Yiq/gXnBvD9pMa2jGXxyhGLfvhZpuMZe18CJpFxAt3CRs42NMg==", - "dev": true - }, "is-retry-allowed": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/is-retry-allowed/-/is-retry-allowed-1.1.0.tgz", @@ -2050,16 +2485,24 @@ "integrity": "sha1-EtSj3U5o4Lec6428hBc66A2RykQ=" }, "is-symbol": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-symbol/-/is-symbol-1.0.1.tgz", - "integrity": "sha1-PMWfAAJRlLarLjjbrmaJJWtmBXI=", - "dev": true + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-symbol/-/is-symbol-1.0.2.tgz", + "integrity": "sha512-HS8bZ9ox60yCJLH9snBpIwv9pYUAkcuLhSA1oero1UB5y9aiQpRA8y2ex945AOtCZL1lJDeIk3G5LthswI46Lw==", + "dev": true, + "requires": { + "has-symbols": "^1.0.0" + } }, "is-typedarray": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/is-typedarray/-/is-typedarray-1.0.0.tgz", "integrity": "sha1-5HnICFjfDBsR3dppQPlgEfzaSpo=" }, + "is-windows": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-windows/-/is-windows-1.0.2.tgz", + "integrity": "sha512-eXK1UInq2bPmjyX6e3VHIzMLobc4J94i4AWn+Hpq3OU5KkrRC96OAcR3PRJ/pGu6m8TRnBHP9dkXQVsT/COVIA==" + }, "isarray": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", @@ -2071,6 +2514,11 @@ "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=", "dev": true }, + "isobject": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", + "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=" + }, "isstream": { "version": "0.1.2", "resolved": "https://registry.npmjs.org/isstream/-/isstream-0.1.2.tgz", @@ -2092,9 +2540,9 @@ "dev": true }, "js-sha3": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/js-sha3/-/js-sha3-0.3.1.tgz", - "integrity": "sha1-hhIoAhQvCChQKg0d7h2V4lO7AkM=" + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/js-sha3/-/js-sha3-0.6.1.tgz", + "integrity": "sha1-W4n3enR3Z5h39YxKB1JAk0sflcA=" }, "js-tokens": { "version": "4.0.0", @@ -2103,9 +2551,9 @@ "dev": true }, "js-yaml": { - "version": "3.12.0", - "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.12.0.tgz", - "integrity": "sha512-PIt2cnwmPfL4hKNwqeiuz4bKfnzHTBv6HyVgjahA6mPLwPDzjDWrplJBMjHUFxku/N3FlmrbyPclad+I+4mJ3A==", + "version": "3.12.1", + "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.12.1.tgz", + "integrity": "sha512-um46hB9wNOKlwkHgiuyEVAybXBjwFUV0Z/RaHJblRd9DXltue9FTYvzCr9ErQrK9Adz5MU4gHWVaNUfdmrC8qA==", "dev": true, "requires": { "argparse": "^1.0.7", @@ -2123,8 +2571,7 @@ "jsbn": { "version": "0.1.1", "resolved": "https://registry.npmjs.org/jsbn/-/jsbn-0.1.1.tgz", - "integrity": "sha1-peZUwuWi3rXyAdls77yoDA7y9RM=", - "optional": true + "integrity": "sha1-peZUwuWi3rXyAdls77yoDA7y9RM=" }, "json-schema": { "version": "0.2.3", @@ -2132,17 +2579,9 @@ "integrity": "sha1-tIDIkuWaLwWVTOcnvT8qTogvnhM=" }, "json-schema-traverse": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.3.1.tgz", - "integrity": "sha1-NJptRMU6Ud6JtAgFxdXlm0F9M0A=" - }, - "json-stable-stringify": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/json-stable-stringify/-/json-stable-stringify-1.0.1.tgz", - "integrity": "sha1-mnWdOcXy/1A/1TAGRu1EX4jE+a8=", - "requires": { - "jsonify": "~0.0.0" - } + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", + "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==" }, "json-stable-stringify-without-jsonify": { "version": "1.0.1", @@ -2156,18 +2595,13 @@ "integrity": "sha1-Epai1Y/UXxmg9s4B1lcB4sc1tus=" }, "jsonfile": { - "version": "2.4.0", - "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-2.4.0.tgz", - "integrity": "sha1-NzaitCi4e72gzIO1P6PWM6NcKug=", + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-4.0.0.tgz", + "integrity": "sha1-h3Gq4HmbZAdrdmQPygWPnBDjPss=", "requires": { "graceful-fs": "^4.1.6" } }, - "jsonify": { - "version": "0.0.0", - "resolved": "https://registry.npmjs.org/jsonify/-/jsonify-0.0.0.tgz", - "integrity": "sha1-LHS27kHZPKUbe1qu6PUDYx0lKnM=" - }, "jsprim": { "version": "1.4.1", "resolved": "https://registry.npmjs.org/jsprim/-/jsprim-1.4.1.tgz", @@ -2191,14 +2625,19 @@ } }, "keccakjs": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/keccakjs/-/keccakjs-0.2.1.tgz", - "integrity": "sha1-HWM6+QfvMFu/ny+mFtVsRFYd+k0=", + "version": "0.2.3", + "resolved": "https://registry.npmjs.org/keccakjs/-/keccakjs-0.2.3.tgz", + "integrity": "sha512-BjLkNDcfaZ6l8HBG9tH0tpmDv3sS2mA7FNQxFHpCdzP3Gb2MVruXBSuoM66SnVxKJpAr5dKGdkHD+bDokt8fTg==", "requires": { - "browserify-sha3": "^0.0.1", - "sha3": "^1.1.0" + "browserify-sha3": "^0.0.4", + "sha3": "^1.2.2" } }, + "kind-of": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-6.0.2.tgz", + "integrity": "sha512-s5kLOcnH0XqDO+FvuaLX8DDjZ18CGFk7VygH40QoKPUQhW4e2rvM0rwUq0t8IQDOwYSeLK01U90OjzBTme2QqA==" + }, "levn": { "version": "0.3.0", "resolved": "https://registry.npmjs.org/levn/-/levn-0.3.0.tgz", @@ -2210,7 +2649,7 @@ }, "load-json-file": { "version": "2.0.0", - "resolved": "http://registry.npmjs.org/load-json-file/-/load-json-file-2.0.0.tgz", + "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-2.0.0.tgz", "integrity": "sha1-eUfkIUmvgNaWy/eXvKq8/h/inKg=", "dev": true, "requires": { @@ -2218,6 +2657,14 @@ "parse-json": "^2.2.0", "pify": "^2.0.0", "strip-bom": "^3.0.0" + }, + "dependencies": { + "pify": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", + "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=", + "dev": true + } } }, "locate-path": { @@ -2228,14 +2675,6 @@ "requires": { "p-locate": "^2.0.0", "path-exists": "^3.0.0" - }, - "dependencies": { - "path-exists": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", - "integrity": "sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=", - "dev": true - } } }, "lodash": { @@ -2250,44 +2689,40 @@ "integrity": "sha512-G2Lj61tXDnVFFOi8VZds+SoQjtQC3dgokKdDG2mTm1tx4m50NUHBOZSBwQQHyy0V12A0JTG4icfZQH+xPyh8VA==" }, "make-dir": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-1.2.0.tgz", - "integrity": "sha512-aNUAa4UMg/UougV25bbrU4ZaaKNjJ/3/xnvg/twpmKROPdKZPZ9wGgI0opdZzO8q/zUFawoUuixuOv33eZ61Iw==", + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-1.3.0.tgz", + "integrity": "sha512-2w31R7SJtieJJnQtGc7RVL2StM2vGYVfqUOvUDxH6bC6aJTxPxTF0GnIgCyu7tjockiUWAYQRbxa7vKn34s5sQ==", "requires": { "pify": "^3.0.0" - }, - "dependencies": { - "pify": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", - "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=" - } + } + }, + "map-cache": { + "version": "0.2.2", + "resolved": "https://registry.npmjs.org/map-cache/-/map-cache-0.2.2.tgz", + "integrity": "sha1-wyq9C9ZSXZsFFkW7TyasXcmKDb8=" + }, + "map-visit": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/map-visit/-/map-visit-1.0.0.tgz", + "integrity": "sha1-7Nyo8TFE5mDxtb1B8S80edmN+48=", + "requires": { + "object-visit": "^1.0.0" } }, "md5.js": { - "version": "1.3.4", - "resolved": "https://registry.npmjs.org/md5.js/-/md5.js-1.3.4.tgz", - "integrity": "sha1-6b296UogpawYsENA/Fdk1bCdkB0=", + "version": "1.3.5", + "resolved": "https://registry.npmjs.org/md5.js/-/md5.js-1.3.5.tgz", + "integrity": "sha512-xitP+WxNPcTTOgnTJcrhM0xvdPepipPSf3I8EIpGKeFLjt3PlJLIDG3u8EX53ZIubkb+5U2+3rELYpEhHhzdkg==", "requires": { "hash-base": "^3.0.0", - "inherits": "^2.0.1" - }, - "dependencies": { - "hash-base": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/hash-base/-/hash-base-3.0.4.tgz", - "integrity": "sha1-X8hoaEfs1zSZQDMZprCj8/auSRg=", - "requires": { - "inherits": "^2.0.1", - "safe-buffer": "^5.0.1" - } - } + "inherits": "^2.0.1", + "safe-buffer": "^5.1.2" } }, "meant": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/meant/-/meant-1.0.0.tgz", - "integrity": "sha1-y2KG47evkxXxYRj9wiRybtOAdLs=" + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/meant/-/meant-1.0.1.tgz", + "integrity": "sha512-UakVLFjKkbbUwNWJ2frVLnnAtbb7D7DsloxRd3s/gDpI8rdv8W5Hp3NaDb+POBI1fQdeussER6NB8vpcRURvlg==" }, "media-typer": { "version": "0.3.0", @@ -2299,11 +2734,36 @@ "resolved": "https://registry.npmjs.org/merge-descriptors/-/merge-descriptors-1.0.1.tgz", "integrity": "sha1-sAqqVW3YtEVoFQ7J0blT8/kMu2E=" }, + "merge2": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/merge2/-/merge2-1.2.3.tgz", + "integrity": "sha512-gdUU1Fwj5ep4kplwcmftruWofEFt6lfpkkr3h860CXbAB9c3hGb55EOL2ali0Td5oebvW0E1+3Sr+Ur7XfKpRA==" + }, "methods": { "version": "1.1.2", "resolved": "https://registry.npmjs.org/methods/-/methods-1.1.2.tgz", "integrity": "sha1-VSmk1nZUE07cxSZmVoNbD4Ua/O4=" }, + "micromatch": { + "version": "3.1.10", + "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-3.1.10.tgz", + "integrity": "sha512-MWikgl9n9M3w+bpsY3He8L+w9eF9338xRl8IAO5viDizwSzziFEyUzo2xrrloB64ADbTf8uA8vRqqttDTOmccg==", + "requires": { + "arr-diff": "^4.0.0", + "array-unique": "^0.3.2", + "braces": "^2.3.1", + "define-property": "^2.0.2", + "extend-shallow": "^3.0.2", + "extglob": "^2.0.4", + "fragment-cache": "^0.2.1", + "kind-of": "^6.0.2", + "nanomatch": "^1.2.9", + "object.pick": "^1.3.0", + "regex-not": "^1.0.0", + "snapdragon": "^0.8.1", + "to-regex": "^3.0.2" + } + }, "miller-rabin": { "version": "4.0.1", "resolved": "https://registry.npmjs.org/miller-rabin/-/miller-rabin-4.0.1.tgz", @@ -2319,16 +2779,16 @@ "integrity": "sha512-KI1+qOZu5DcW6wayYHSzR/tXKCDC5Om4s1z2QJjDULzLcmf3DvzS7oluY4HCTrc+9FiKmWUgeNLg7W3uIQvxtQ==" }, "mime-db": { - "version": "1.33.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.33.0.tgz", - "integrity": "sha512-BHJ/EKruNIqJf/QahvxwQZXKygOQ256myeN/Ew+THcAa5q+PjyTTMMeNQC4DZw5AwfvelsUrA6B67NKMqXDbzQ==" + "version": "1.38.0", + "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.38.0.tgz", + "integrity": "sha512-bqVioMFFzc2awcdJZIzR3HjZFX20QhilVS7hytkKrv7xFAn8bM1gzc/FOX2awLISvWe0PV8ptFKcon+wZ5qYkg==" }, "mime-types": { - "version": "2.1.18", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.18.tgz", - "integrity": "sha512-lc/aahn+t4/SWV/qcmumYjymLsWfN3ELhpmVuUFjgsORruuZPVSwAQryq+HHGvO/SI2KVX26bx+En+zhM8g8hQ==", + "version": "2.1.22", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.22.tgz", + "integrity": "sha512-aGl6TZGnhm/li6F7yx82bJiBZwgiEa4Hf6CNr8YO+r5UHr53tSTYZb102zyU50DOWWKeOv0uQLRL0/9EiKWCog==", "requires": { - "mime-db": "~1.33.0" + "mime-db": "~1.38.0" } }, "mimic-fn": { @@ -2338,9 +2798,9 @@ "dev": true }, "mimic-response": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-1.0.0.tgz", - "integrity": "sha1-3z02Uqc/3ta5sLJBRub9BSNTRY4=" + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-1.0.1.tgz", + "integrity": "sha512-j5EctnkH7amfV/q5Hgmoal1g2QHFJRraOtmx0JpIqkxhBhI/lJSl1nMpQ45hVarwNETOoWEimndZ4QK0RHxuxQ==" }, "min-document": { "version": "2.19.0", @@ -2351,9 +2811,9 @@ } }, "minimalistic-assert": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/minimalistic-assert/-/minimalistic-assert-1.0.0.tgz", - "integrity": "sha1-cCvi3aazf0g2vLP121ZkG2Sh09M=" + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/minimalistic-assert/-/minimalistic-assert-1.0.1.tgz", + "integrity": "sha512-UtJcAD4yEaGtjPezWuO9wC4nwUnVH/8/Im3yEHQP4b67cXlD/Qr9hdITCU1xDbSEXg2XKNaP8jsReV7vQd00/A==" }, "minimalistic-crypto-utils": { "version": "1.0.1", @@ -2369,9 +2829,28 @@ } }, "minimist": { - "version": "0.0.8", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-0.0.8.tgz", - "integrity": "sha1-hX/Kv8M5fSYluCKCYuhqp6ARsF0=" + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz", + "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=" + }, + "mixin-deep": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/mixin-deep/-/mixin-deep-1.3.1.tgz", + "integrity": "sha512-8ZItLHeEgaqEvd5lYBXfm4EZSFCX29Jb9K+lAHhDKzReKBQKj3R+7NOF6tjqYi9t4oI8VUfaWITJQm86wnXGNQ==", + "requires": { + "for-in": "^1.0.2", + "is-extendable": "^1.0.1" + }, + "dependencies": { + "is-extendable": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-1.0.1.tgz", + "integrity": "sha512-arnXMxT1hhoKo9k1LZdmlNyJdDDfy2v0fXjFlmok4+i8ul/6WlbVge9bhM74OpNPQPMGUToDtz+KXa1PneJxOA==", + "requires": { + "is-plain-object": "^2.0.4" + } + } + } }, "mkdirp": { "version": "0.5.1", @@ -2379,6 +2858,13 @@ "integrity": "sha1-MAV0OOrGz3+MR2fzhkjWaX11yQM=", "requires": { "minimist": "0.0.8" + }, + "dependencies": { + "minimist": { + "version": "0.0.8", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-0.0.8.tgz", + "integrity": "sha1-hX/Kv8M5fSYluCKCYuhqp6ARsF0=" + } } }, "mkdirp-promise": { @@ -2390,9 +2876,9 @@ } }, "mock-fs": { - "version": "4.4.2", - "resolved": "https://registry.npmjs.org/mock-fs/-/mock-fs-4.4.2.tgz", - "integrity": "sha512-dF+yxZSojSiI8AXGoxj5qdFWpucndc54Ug+TwlpHFaV7j22MGG+OML2+FVa6xAZtjb/OFFQhOC37Jegx2GbEwA==" + "version": "4.8.0", + "resolved": "https://registry.npmjs.org/mock-fs/-/mock-fs-4.8.0.tgz", + "integrity": "sha512-Gwj4KnJOW15YeTJKO5frFd/WDO5Mc0zxXqL9oHx3+e9rBqW8EVARqQHSaIXznUdljrD6pvbNGW2ZGXKPEfYJfw==" }, "mout": { "version": "0.11.1", @@ -2405,9 +2891,9 @@ "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" }, "multistream": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/multistream/-/multistream-2.1.0.tgz", - "integrity": "sha1-YlwmfVxEQkrWKUeItbtNo9yzLx0=", + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/multistream/-/multistream-2.1.1.tgz", + "integrity": "sha512-xasv76hl6nr1dEy3lPvy7Ej7K/Lx3O/FCvwge8PeVJpciPPoNCbaANcNiBug3IpdvTveZUcAV0DJzdnUDMesNQ==", "requires": { "inherits": "^2.0.1", "readable-stream": "^2.0.5" @@ -2430,15 +2916,33 @@ } }, "nan": { - "version": "2.10.0", - "resolved": "https://registry.npmjs.org/nan/-/nan-2.10.0.tgz", - "integrity": "sha512-bAdJv7fBLhWC+/Bls0Oza+mvTaNQtP+1RyhhhvD95pgUJz6XM5IzgmxOkItJ9tkoCiplvAnXI1tNmmUD/eScyA==" + "version": "2.12.1", + "resolved": "https://registry.npmjs.org/nan/-/nan-2.12.1.tgz", + "integrity": "sha512-JY7V6lRkStKcKTvHO5NVSQRv+RV+FIL5pvDoLiAtSL9pKlC5x9PKQcZDsq7m4FO4d57mkhC6Z+QhAh3Jdk5JFw==" }, "nano-json-stream-parser": { "version": "0.1.2", "resolved": "https://registry.npmjs.org/nano-json-stream-parser/-/nano-json-stream-parser-0.1.2.tgz", "integrity": "sha1-DMj20OK2IrR5xA1JnEbWS3Vcb18=" }, + "nanomatch": { + "version": "1.2.13", + "resolved": "https://registry.npmjs.org/nanomatch/-/nanomatch-1.2.13.tgz", + "integrity": "sha512-fpoe2T0RbHwBTBUOftAfBPaDEi06ufaUai0mE6Yn1kacc3SnTErfb/h+X94VXzI64rKFHYImXSvdwGGCmwOqCA==", + "requires": { + "arr-diff": "^4.0.0", + "array-unique": "^0.3.2", + "define-property": "^2.0.2", + "extend-shallow": "^3.0.2", + "fragment-cache": "^0.2.1", + "is-windows": "^1.0.2", + "kind-of": "^6.0.2", + "object.pick": "^1.3.0", + "regex-not": "^1.0.0", + "snapdragon": "^0.8.1", + "to-regex": "^3.0.1" + } + }, "natural-compare": { "version": "1.4.0", "resolved": "https://registry.npmjs.org/natural-compare/-/natural-compare-1.4.0.tgz", @@ -2457,20 +2961,31 @@ "dev": true }, "node-fetch": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.1.2.tgz", - "integrity": "sha1-q4hOjn5X44qUR1POxwb3iNF2i7U=" + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.3.0.tgz", + "integrity": "sha512-MOd8pV3fxENbryESLgVIeaGKrdl+uaYhCSSVkjeOb/31/njTpcis5aWfdqgNlHIrKOLRbMnfPINPOML2CIFeXA==" }, "normalize-package-data": { - "version": "2.4.0", - "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-2.4.0.tgz", - "integrity": "sha512-9jjUFbTPfEy3R/ad/2oNbKtW9Hgovl5O1FvFWKkKblNXoN/Oou6+9+KKohPK13Yc3/TyunyWhJp6gvRNR/PPAw==", + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-2.5.0.tgz", + "integrity": "sha512-/5CMN3T0R4XTj4DcGaexo+roZSdSFW/0AOOTROrjxzCG1wrWXEsGbRKevjlIL+ZDE4sZlJr5ED4YW0yqmkK+eA==", "dev": true, "requires": { "hosted-git-info": "^2.1.4", - "is-builtin-module": "^1.0.0", + "resolve": "^1.10.0", "semver": "2 || 3 || 4 || 5", "validate-npm-package-license": "^3.0.1" + }, + "dependencies": { + "resolve": { + "version": "1.10.0", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.10.0.tgz", + "integrity": "sha512-3sUr9aq5OfSg2S9pNtPA9hL1FVEAjvfOC4leW0SNf/mpnaakz2a9femSd6LqAww2RaFctwyf1lCqnTHuF1rxDg==", + "dev": true, + "requires": { + "path-parse": "^1.0.6" + } + } } }, "number-to-bn": { @@ -2490,21 +3005,57 @@ } }, "oauth-sign": { - "version": "0.8.2", - "resolved": "https://registry.npmjs.org/oauth-sign/-/oauth-sign-0.8.2.tgz", - "integrity": "sha1-Rqarfwrq2N6unsBWV4C31O/rnUM=" + "version": "0.9.0", + "resolved": "https://registry.npmjs.org/oauth-sign/-/oauth-sign-0.9.0.tgz", + "integrity": "sha512-fexhUFFPTGV8ybAtSIGbV6gOkSv8UtRbDBnAyLQw4QPKkgNlsH2ByPGtMUqdWkos6YCRmAqViwgZrJc/mRDzZQ==" }, "object-assign": { "version": "4.1.1", "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", "integrity": "sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM=" }, + "object-copy": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/object-copy/-/object-copy-0.1.0.tgz", + "integrity": "sha1-fn2Fi3gb18mRpBupde04EnVOmYw=", + "requires": { + "copy-descriptor": "^0.1.0", + "define-property": "^0.2.5", + "kind-of": "^3.0.3" + }, + "dependencies": { + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "requires": { + "is-descriptor": "^0.1.0" + } + }, + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "requires": { + "is-buffer": "^1.1.5" + } + } + } + }, "object-keys": { - "version": "1.0.12", - "resolved": "https://registry.npmjs.org/object-keys/-/object-keys-1.0.12.tgz", - "integrity": "sha512-FTMyFUm2wBcGHnH2eXmz7tC6IwlqQZ6mVZ+6dm6vZ4IQIHjs6FdNsQBuKGPuUUUY6NfJw2PshC08Tn6LzLDOag==", + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/object-keys/-/object-keys-1.1.0.tgz", + "integrity": "sha512-6OO5X1+2tYkNyNEx6TsCxEqFfRWaqx6EtMiSbGrw8Ob8v9Ne+Hl8rBAgLBZn5wjEz3s/s6U1WXFUFOcxxAwUpg==", "dev": true }, + "object-visit": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/object-visit/-/object-visit-1.0.1.tgz", + "integrity": "sha1-95xEk68MU3e1n+OdOV5BBC3QRbs=", + "requires": { + "isobject": "^3.0.0" + } + }, "object.assign": { "version": "4.1.0", "resolved": "https://registry.npmjs.org/object.assign/-/object.assign-4.1.0.tgz", @@ -2518,15 +3069,23 @@ } }, "object.entries": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/object.entries/-/object.entries-1.0.4.tgz", - "integrity": "sha1-G/mk3SKI9bM/Opk9JXZh8F0WGl8=", + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/object.entries/-/object.entries-1.1.0.tgz", + "integrity": "sha512-l+H6EQ8qzGRxbkHOd5I/aHRhHDKoQXQ8g0BYt4uSweQU1/J6dZUOyWh9a2Vky35YCKjzmgxOzta2hH6kf9HuXA==", "dev": true, "requires": { - "define-properties": "^1.1.2", - "es-abstract": "^1.6.1", - "function-bind": "^1.1.0", - "has": "^1.0.1" + "define-properties": "^1.1.3", + "es-abstract": "^1.12.0", + "function-bind": "^1.1.1", + "has": "^1.0.3" + } + }, + "object.pick": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/object.pick/-/object.pick-1.3.0.tgz", + "integrity": "sha1-h6EKxMFpS9Lhy/U1kaZhQftd10c=", + "requires": { + "isobject": "^3.0.1" } }, "oboe": { @@ -2590,6 +3149,11 @@ "resolved": "https://registry.npmjs.org/p-finally/-/p-finally-1.0.0.tgz", "integrity": "sha1-P7z7FbiZpEEjs0ttzBi3JDNqLK4=" }, + "p-is-promise": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/p-is-promise/-/p-is-promise-2.0.0.tgz", + "integrity": "sha512-pzQPhYMCAgLAKPWD2jC3Se9fEfrD9npNos0y150EeqZll7akhEgGhTW/slB6lHku8AvYGiJ+YJ5hfHKePPgFWg==" + }, "p-limit": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-1.3.0.tgz", @@ -2622,16 +3186,26 @@ "integrity": "sha1-y8ec26+P1CKOE/Yh8rGiN8GyB7M=", "dev": true }, + "parent-module": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/parent-module/-/parent-module-1.0.0.tgz", + "integrity": "sha512-8Mf5juOMmiE4FcmzYc4IaiS9L3+9paz2KOiXzkRviCP6aDmN49Hz6EMWz0lGNp9pX80GvvAuLADtyGfW/Em3TA==", + "dev": true, + "requires": { + "callsites": "^3.0.0" + } + }, "parse-asn1": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/parse-asn1/-/parse-asn1-5.1.0.tgz", - "integrity": "sha1-N8T5t+06tlx0gXtfJICTf7+XxxI=", + "version": "5.1.4", + "resolved": "https://registry.npmjs.org/parse-asn1/-/parse-asn1-5.1.4.tgz", + "integrity": "sha512-Qs5duJcuvNExRfFZ99HDD3z4mAi3r9Wl/FOjEOijlxwCZs7E7mW2vjTpgQ4J8LpTF8x5v+1Vn5UQFejmWT11aw==", "requires": { "asn1.js": "^4.0.0", "browserify-aes": "^1.0.0", "create-hash": "^1.1.0", "evp_bytestokey": "^1.0.0", - "pbkdf2": "^3.0.3" + "pbkdf2": "^3.0.3", + "safe-buffer": "^5.1.1" } }, "parse-headers": { @@ -2657,14 +3231,21 @@ "resolved": "https://registry.npmjs.org/parseurl/-/parseurl-1.3.2.tgz", "integrity": "sha1-/CidTtiZMRlGDBViUyYs3I3mW/M=" }, + "pascalcase": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/pascalcase/-/pascalcase-0.1.1.tgz", + "integrity": "sha1-s2PlXoAGym/iF4TS2yK9FdeRfxQ=" + }, + "path-dirname": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/path-dirname/-/path-dirname-1.0.2.tgz", + "integrity": "sha1-zDPSTVJeCZpTiMAzbG4yuRYGCeA=" + }, "path-exists": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-2.1.0.tgz", - "integrity": "sha1-D+tsZPD8UY2adU3V77YscCJ2H0s=", - "dev": true, - "requires": { - "pinkie-promise": "^2.0.0" - } + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", + "integrity": "sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=", + "dev": true }, "path-is-absolute": { "version": "1.0.1", @@ -2684,9 +3265,9 @@ "dev": true }, "path-parse": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.5.tgz", - "integrity": "sha1-PBrfhx6pzWyUMbbqK9dKD/BVxME=" + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.6.tgz", + "integrity": "sha512-GSmOT2EbHrINBf9SR7CDELwlJ8AENk3Qn7OikK4nFYAu3Ote2+JYNVvkpAEQm3/TLNEJFD/xZJjzyxg3KBWOzw==" }, "path-to-regexp": { "version": "0.1.7", @@ -2694,18 +3275,17 @@ "integrity": "sha1-32BBeABfUi8V60SQ5yR6G/qmf4w=" }, "path-type": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/path-type/-/path-type-2.0.0.tgz", - "integrity": "sha1-8BLMuEFbcJb8LaoQVMPXI4lZTHM=", - "dev": true, + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/path-type/-/path-type-3.0.0.tgz", + "integrity": "sha512-T2ZUsdZFHgA3u4e5PfPbjd7HDDpxPnQb5jN0SrDsjNSuVXHJqtwTnWqG0B1jZrgmJ/7lj1EmVIByWt1gxGkWvg==", "requires": { - "pify": "^2.0.0" + "pify": "^3.0.0" } }, "pbkdf2": { - "version": "3.0.14", - "resolved": "https://registry.npmjs.org/pbkdf2/-/pbkdf2-3.0.14.tgz", - "integrity": "sha512-gjsZW9O34fm0R7PaLHRJmLLVfSoesxztjPjE9o6R+qtVJij90ltg1joIovN9GKrRW3t1PzhDDG3UMEMFfZ+1wA==", + "version": "3.0.17", + "resolved": "https://registry.npmjs.org/pbkdf2/-/pbkdf2-3.0.17.tgz", + "integrity": "sha512-U/il5MsrZp7mGg3mSQfn742na2T+1/vHDCG5/iTI3X9MKUuYUZVLQhyRsg06mCgDBTd57TxzgZt7P+fYfjRLtA==", "requires": { "create-hash": "^1.1.2", "create-hmac": "^1.1.4", @@ -2725,9 +3305,9 @@ "integrity": "sha1-Ywn04OX6kT7BxpMHrjZLSzd8nns=" }, "pify": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", - "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=" + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", + "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=" }, "pinkie": { "version": "2.0.4", @@ -2743,241 +3323,69 @@ } }, "pkg": { - "version": "4.3.1", - "resolved": "https://registry.npmjs.org/pkg/-/pkg-4.3.1.tgz", - "integrity": "sha512-QaOXdF9doVkrXpeu0D5ODLDLjYE4LE2WAk7/wSgNiCsCajg4ExjApxwkVIanz61tR8oIe+8vkmW0WpAwfV1ExA==", - "requires": { - "acorn": "5.5.3", - "acorn-object-rest-spread": "1.1.0", - "babel-runtime": "6.25.0", - "chalk": "2.1.0", - "escodegen": "1.8.1", - "fs-extra": "4.0.1", - "globby": "6.1.0", + "version": "4.3.7", + "resolved": "https://registry.npmjs.org/pkg/-/pkg-4.3.7.tgz", + "integrity": "sha512-/BvtFft1nKKtnTuOm/0es0sk1cOs7ZtWgJpqdtszJ4348jYJ8owVyCB/iuGhI3YJFX/ZFIv4Rmra9ETUgpnnfA==", + "requires": { + "@babel/parser": "7.2.3", + "babel-runtime": "6.26.0", + "chalk": "2.4.2", + "escodegen": "1.11.0", + "fs-extra": "7.0.1", + "globby": "8.0.2", + "into-stream": "4.0.0", "minimist": "1.2.0", - "multistream": "2.1.0", - "pkg-fetch": "2.5.4", - "progress": "2.0.0", - "resolve": "1.4.0", - "simple-bufferstream": "1.0.0", + "multistream": "2.1.1", + "pkg-fetch": "2.5.7", + "progress": "2.0.3", + "resolve": "1.6.0", "stream-meter": "1.0.4" - }, - "dependencies": { - "fs-extra": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-4.0.1.tgz", - "integrity": "sha1-f8DGyJV/mD9X8waiTlud3Y0N2IA=", - "requires": { - "graceful-fs": "^4.1.2", - "jsonfile": "^3.0.0", - "universalify": "^0.1.0" - } - }, - "jsonfile": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-3.0.1.tgz", - "integrity": "sha1-pezG9l9T9mLEQVx2daAzHQmS7GY=", - "requires": { - "graceful-fs": "^4.1.6" - } - }, - "minimist": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz", - "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=" - } } }, "pkg-dir": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/pkg-dir/-/pkg-dir-1.0.0.tgz", - "integrity": "sha1-ektQio1bstYp1EcFb/TpyTFM89Q=", + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/pkg-dir/-/pkg-dir-2.0.0.tgz", + "integrity": "sha1-9tXREJ4Z1j7fQo4L1X4Sd3YVM0s=", "dev": true, "requires": { - "find-up": "^1.0.0" + "find-up": "^2.1.0" } }, "pkg-fetch": { - "version": "2.5.4", - "resolved": "https://registry.npmjs.org/pkg-fetch/-/pkg-fetch-2.5.4.tgz", - "integrity": "sha512-KASiP5yytve4otDY242Zp3r+e11whyoSl79QmmBS3Qg4rvZsYOC5RE0szM0SZrVxg93sqYcINxHlXmzBTJDOeA==", - "requires": { - "babel-runtime": "6.25.0", - "byline": "5.0.0", - "chalk": "2.1.0", - "expand-template": "1.0.3", - "fs-extra": "4.0.1", - "in-publish": "2.0.0", - "minimist": "1.2.0", - "progress": "2.0.0", - "request": "2.81.0", - "request-progress": "3.0.0", - "semver": "5.4.1", - "unique-temp-dir": "1.0.0" + "version": "2.5.7", + "resolved": "https://registry.npmjs.org/pkg-fetch/-/pkg-fetch-2.5.7.tgz", + "integrity": "sha512-fm9aVV3ZRdFYTyFYcSHuKMuxPCVQ0MD9tbVxbvQzFTg1gwvV0KqWrFoj5enVVha94yP83I50XEBa90X8L9fE8w==", + "requires": { + "babel-runtime": "~6.26.0", + "byline": "~5.0.0", + "chalk": "~2.4.1", + "expand-template": "~1.1.1", + "fs-extra": "~6.0.1", + "in-publish": "~2.0.0", + "minimist": "~1.2.0", + "progress": "~2.0.0", + "request": "~2.88.0", + "request-progress": "~3.0.0", + "semver": "~5.6.0", + "unique-temp-dir": "~1.0.0" }, "dependencies": { - "ajv": { - "version": "4.11.8", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-4.11.8.tgz", - "integrity": "sha1-gv+wKynmYq5TvcIK8VlHcGc5xTY=", - "requires": { - "co": "^4.6.0", - "json-stable-stringify": "^1.0.1" - } - }, - "assert-plus": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-0.2.0.tgz", - "integrity": "sha1-104bh+ev/A24qttwIfP+SBAasjQ=" - }, - "aws-sign2": { - "version": "0.6.0", - "resolved": "https://registry.npmjs.org/aws-sign2/-/aws-sign2-0.6.0.tgz", - "integrity": "sha1-FDQt0428yU0OW4fXY81jYSwOeU8=" - }, - "boom": { - "version": "2.10.1", - "resolved": "https://registry.npmjs.org/boom/-/boom-2.10.1.tgz", - "integrity": "sha1-OciRjO/1eZ+D+UkqhI9iWt0Mdm8=", - "requires": { - "hoek": "2.x.x" - } - }, - "cryptiles": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/cryptiles/-/cryptiles-2.0.5.tgz", - "integrity": "sha1-O9/s3GCBR8HGcgL6KR59ylnqo7g=", - "requires": { - "boom": "2.x.x" - } - }, - "form-data": { - "version": "2.1.4", - "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.1.4.tgz", - "integrity": "sha1-M8GDrPGTJ27KqYFDpp6Uv+4XUNE=", - "requires": { - "asynckit": "^0.4.0", - "combined-stream": "^1.0.5", - "mime-types": "^2.1.12" - } - }, "fs-extra": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-4.0.1.tgz", - "integrity": "sha1-f8DGyJV/mD9X8waiTlud3Y0N2IA=", + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-6.0.1.tgz", + "integrity": "sha512-GnyIkKhhzXZUWFCaJzvyDLEEgDkPfb4/TPvJCJVuS8MWZgoSsErf++QpiAlDnKFcqhRlm+tIOcencCjyJE6ZCA==", "requires": { "graceful-fs": "^4.1.2", - "jsonfile": "^3.0.0", + "jsonfile": "^4.0.0", "universalify": "^0.1.0" } - }, - "har-schema": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/har-schema/-/har-schema-1.0.5.tgz", - "integrity": "sha1-0mMTX0MwfALGAq/I/pWXDAFRNp4=" - }, - "har-validator": { - "version": "4.2.1", - "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-4.2.1.tgz", - "integrity": "sha1-M0gdDxu/9gDdID11gSpqX7oALio=", - "requires": { - "ajv": "^4.9.1", - "har-schema": "^1.0.5" - } - }, - "hawk": { - "version": "3.1.3", - "resolved": "https://registry.npmjs.org/hawk/-/hawk-3.1.3.tgz", - "integrity": "sha1-B4REvXwWQLD+VA0sm3PVlnjo4cQ=", - "requires": { - "boom": "2.x.x", - "cryptiles": "2.x.x", - "hoek": "2.x.x", - "sntp": "1.x.x" - } - }, - "hoek": { - "version": "2.16.3", - "resolved": "https://registry.npmjs.org/hoek/-/hoek-2.16.3.tgz", - "integrity": "sha1-ILt0A9POo5jpHcRxCo/xuCdKJe0=" - }, - "http-signature": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/http-signature/-/http-signature-1.1.1.tgz", - "integrity": "sha1-33LiZwZs0Kxn+3at+OE0qPvPkb8=", - "requires": { - "assert-plus": "^0.2.0", - "jsprim": "^1.2.2", - "sshpk": "^1.7.0" - } - }, - "jsonfile": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-3.0.1.tgz", - "integrity": "sha1-pezG9l9T9mLEQVx2daAzHQmS7GY=", - "requires": { - "graceful-fs": "^4.1.6" - } - }, - "minimist": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz", - "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=" - }, - "performance-now": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/performance-now/-/performance-now-0.2.0.tgz", - "integrity": "sha1-M+8wxcd9TqIcWlOGnZG1bY8lVeU=" - }, - "qs": { - "version": "6.4.0", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.4.0.tgz", - "integrity": "sha1-E+JtKK1rD/qpExLNO/cI7TUecjM=" - }, - "request": { - "version": "2.81.0", - "resolved": "https://registry.npmjs.org/request/-/request-2.81.0.tgz", - "integrity": "sha1-xpKJRqDgbF+Nb4qTM0af/aRimKA=", - "requires": { - "aws-sign2": "~0.6.0", - "aws4": "^1.2.1", - "caseless": "~0.12.0", - "combined-stream": "~1.0.5", - "extend": "~3.0.0", - "forever-agent": "~0.6.1", - "form-data": "~2.1.1", - "har-validator": "~4.2.1", - "hawk": "~3.1.3", - "http-signature": "~1.1.0", - "is-typedarray": "~1.0.0", - "isstream": "~0.1.2", - "json-stringify-safe": "~5.0.1", - "mime-types": "~2.1.7", - "oauth-sign": "~0.8.1", - "performance-now": "^0.2.0", - "qs": "~6.4.0", - "safe-buffer": "^5.0.1", - "stringstream": "~0.0.4", - "tough-cookie": "~2.3.0", - "tunnel-agent": "^0.6.0", - "uuid": "^3.0.0" - } - }, - "sntp": { - "version": "1.0.9", - "resolved": "https://registry.npmjs.org/sntp/-/sntp-1.0.9.tgz", - "integrity": "sha1-ZUEYTMkK7qbG57NeJlkIJEPGYZg=", - "requires": { - "hoek": "2.x.x" - } } } }, - "pluralize": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/pluralize/-/pluralize-7.0.0.tgz", - "integrity": "sha512-ARhBOdzS3e41FbkW/XWrTEtukqqLoK5+Z/4UeDaLuSW+39JPeFgs4gCGqsrJHVZX0fUrx//4OF0K1CUGwlIFow==", - "dev": true + "posix-character-classes": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/posix-character-classes/-/posix-character-classes-0.1.1.tgz", + "integrity": "sha1-AerA/jta9xoqbAL+q7jB/vfgDqs=" }, "prelude-ls": { "version": "1.1.2", @@ -2990,9 +3398,9 @@ "integrity": "sha1-1PRWKwzjaW5BrFLQ4ALlemNdxtw=" }, "prettier": { - "version": "1.14.3", - "resolved": "https://registry.npmjs.org/prettier/-/prettier-1.14.3.tgz", - "integrity": "sha512-qZDVnCrnpsRJJq5nSsiHCE3BYMED2OtsI+cmzIzF1QIfqm5ALf8tEJcO27zV1gKNKRPdhjO0dNWnrzssDQ1tFg==", + "version": "1.16.4", + "resolved": "https://registry.npmjs.org/prettier/-/prettier-1.16.4.tgz", + "integrity": "sha512-ZzWuos7TI5CKUeQAtFd6Zhm2s6EpAD/ZLApIhsF9pRvRtM1RFo61dM/4MSRUA0SuLugA/zgrZD8m0BaY46Og7g==", "dev": true }, "process": { @@ -3006,40 +3414,46 @@ "integrity": "sha512-MtEC1TqN0EU5nephaJ4rAtThHtC86dNN9qCuEhtshvpVBkAW5ZO7BASN9REnF9eoXGcRub+pFuKEpOHE+HbEMw==" }, "progress": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/progress/-/progress-2.0.0.tgz", - "integrity": "sha1-ihvjZr+Pwj2yvSPxDG/pILQ4nR8=" + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/progress/-/progress-2.0.3.tgz", + "integrity": "sha512-7PiHtLll5LdnKIMw100I+8xJXR5gW2QwWYkT6iJva0bXitZKa/XMrSbdmg3r2Xnaidz9Qumd0VPaMrZlF9V9sA==" }, "proxy-addr": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.3.tgz", - "integrity": "sha512-jQTChiCJteusULxjBp8+jftSQE5Obdl3k4cnmLA6WXtK6XFuWRnvVL7aCiBqaLPM8c4ph0S4tKna8XvmIwEnXQ==", + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.4.tgz", + "integrity": "sha512-5erio2h9jp5CHGwcybmxmVqHmnCBZeewlfJ0pex+UW7Qny7OOZXTtH56TGNyBizkgiOwhJtMKrVzDTeKcySZwA==", "requires": { "forwarded": "~0.1.2", - "ipaddr.js": "1.6.0" + "ipaddr.js": "1.8.0" } }, + "psl": { + "version": "1.1.31", + "resolved": "https://registry.npmjs.org/psl/-/psl-1.1.31.tgz", + "integrity": "sha512-/6pt4+C+T+wZUieKR620OpzN/LlnNKuWjy1iFLQ/UG35JqHlR/89MP1d96dUfkf6Dne3TuLQzOYEYshJ+Hx8mw==" + }, "public-encrypt": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/public-encrypt/-/public-encrypt-4.0.0.tgz", - "integrity": "sha1-OfaZ86RlYN1eusvKaTyvfGXBjMY=", + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/public-encrypt/-/public-encrypt-4.0.3.tgz", + "integrity": "sha512-zVpa8oKZSz5bTMTFClc1fQOnyyEzpl5ozpi1B5YcvBrdohMjH2rfsBtyXcuNuwjsDIXmBYlF2N5FlJYhR29t8Q==", "requires": { "bn.js": "^4.1.0", "browserify-rsa": "^4.0.0", "create-hash": "^1.1.0", "parse-asn1": "^5.0.0", - "randombytes": "^2.0.1" + "randombytes": "^2.0.1", + "safe-buffer": "^5.1.2" } }, "punycode": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/punycode/-/punycode-1.4.1.tgz", - "integrity": "sha1-wNWmOycYgArY4esPpSachN1BhF4=" + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.1.1.tgz", + "integrity": "sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A==" }, "qs": { - "version": "6.5.1", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.5.1.tgz", - "integrity": "sha512-eRzhrN1WSINYCDCbrz796z37LOe3m5tmW7RQf6oBntukAG1nmovJvhnwHHRMAfeoItc1m2Hk02WER2aQ/iqs+A==" + "version": "6.5.2", + "resolved": "https://registry.npmjs.org/qs/-/qs-6.5.2.tgz", + "integrity": "sha512-N5ZAX4/LxJmF+7wN74pUD6qAh9/wnvdQcjq9TZjevvXzSUo7bfmw91saqMjzGS2xq91/odN2dW/WOl7qQHNDGA==" }, "query-string": { "version": "5.1.1", @@ -3079,13 +3493,13 @@ "integrity": "sha1-9JvmtIeJTdxA3MlKMi9hEJLgDV4=" }, "raw-body": { - "version": "2.3.2", - "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-2.3.2.tgz", - "integrity": "sha1-vNYMd9Prk83gBQKVw/N5OJvIj4k=", + "version": "2.3.3", + "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-2.3.3.tgz", + "integrity": "sha512-9esiElv1BrZoI3rCDuOuKCBRbuApGGaDPQfjSflGxdy4oyzqghxu6klEkkVIvBje+FF0BX9coEv8KqW6X/7njw==", "requires": { "bytes": "3.0.0", - "http-errors": "1.6.2", - "iconv-lite": "0.4.19", + "http-errors": "1.6.3", + "iconv-lite": "0.4.23", "unpipe": "1.0.0" } }, @@ -3098,6 +3512,23 @@ "load-json-file": "^2.0.0", "normalize-package-data": "^2.3.2", "path-type": "^2.0.0" + }, + "dependencies": { + "path-type": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/path-type/-/path-type-2.0.0.tgz", + "integrity": "sha1-8BLMuEFbcJb8LaoQVMPXI4lZTHM=", + "dev": true, + "requires": { + "pify": "^2.0.0" + } + }, + "pify": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", + "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=", + "dev": true + } } }, "read-pkg-up": { @@ -3108,71 +3539,77 @@ "requires": { "find-up": "^2.0.0", "read-pkg": "^2.0.0" - }, - "dependencies": { - "find-up": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", - "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", - "dev": true, - "requires": { - "locate-path": "^2.0.0" - } - } } }, "readable-stream": { - "version": "2.3.5", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.5.tgz", - "integrity": "sha512-tK0yDhrkygt/knjowCUiWP9YdV7c5R+8cR0r/kt9ZhBU906Fs6RpQJCEilamRJj1Nx2rWI6LkW9gKqjTkshhEw==", + "version": "2.3.6", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.6.tgz", + "integrity": "sha512-tQtKA9WIAhBF3+VLAseyMqZeBjW0AHJoxOtYqSUZNJxauErmLbVm2FW1y+J/YA9dUrAC39ITejlZWhVIwawkKw==", "requires": { "core-util-is": "~1.0.0", "inherits": "~2.0.3", "isarray": "~1.0.0", "process-nextick-args": "~2.0.0", "safe-buffer": "~5.1.1", - "string_decoder": "~1.0.3", + "string_decoder": "~1.1.1", "util-deprecate": "~1.0.1" } }, "regenerator-runtime": { - "version": "0.10.5", - "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.10.5.tgz", - "integrity": "sha1-M2w+/BIgrc7dosn6tntaeVWjNlg=" + "version": "0.11.1", + "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.11.1.tgz", + "integrity": "sha512-MguG95oij0fC3QV3URf4V2SDYGJhJnJGqvIIgdECeODCT98wSWDAJ94SSuVpYQUoTcGUIL6L4yNB7j1DFFHSBg==" + }, + "regex-not": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/regex-not/-/regex-not-1.0.2.tgz", + "integrity": "sha512-J6SDjUgDxQj5NusnOtdFxDwN/+HWykR8GELwctJ7mdqhcyy1xEc4SRFHUXvxTp661YaVKAjfRLZ9cCqS6tn32A==", + "requires": { + "extend-shallow": "^3.0.2", + "safe-regex": "^1.1.0" + } }, "regexpp": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/regexpp/-/regexpp-2.0.0.tgz", - "integrity": "sha512-g2FAVtR8Uh8GO1Nv5wpxW7VFVwHcCEr4wyA8/MHiRkO8uHoR5ntAA8Uq3P1vvMTX/BeQiRVSpDGLd+Wn5HNOTA==", + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/regexpp/-/regexpp-2.0.1.tgz", + "integrity": "sha512-lv0M6+TkDVniA3aD1Eg0DVpfU/booSu7Eev3TDO/mZKHBfVjgCGTV4t4buppESEYDtkArYFOxTJWv6S5C+iaNw==", "dev": true }, + "repeat-element": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/repeat-element/-/repeat-element-1.1.3.tgz", + "integrity": "sha512-ahGq0ZnV5m5XtZLMb+vP76kcAM5nkLqk0lpqAuojSKGgQtn4eRi4ZZGm2olo2zKFH+sMsWaqOCW1dqAnOru72g==" + }, + "repeat-string": { + "version": "1.6.1", + "resolved": "https://registry.npmjs.org/repeat-string/-/repeat-string-1.6.1.tgz", + "integrity": "sha1-jcrkcOHIirwtYA//Sndihtp15jc=" + }, "request": { - "version": "2.85.0", - "resolved": "https://registry.npmjs.org/request/-/request-2.85.0.tgz", - "integrity": "sha512-8H7Ehijd4js+s6wuVPLjwORxD4zeuyjYugprdOXlPSqaApmL/QOy+EB/beICHVCHkGMKNh5rvihb5ov+IDw4mg==", + "version": "2.88.0", + "resolved": "https://registry.npmjs.org/request/-/request-2.88.0.tgz", + "integrity": "sha512-NAqBSrijGLZdM0WZNsInLJpkJokL72XYjUpnB0iwsRgxh7dB6COrHnTBNwN0E+lHDAJzu7kLAkDeY08z2/A0hg==", "requires": { "aws-sign2": "~0.7.0", - "aws4": "^1.6.0", + "aws4": "^1.8.0", "caseless": "~0.12.0", - "combined-stream": "~1.0.5", - "extend": "~3.0.1", + "combined-stream": "~1.0.6", + "extend": "~3.0.2", "forever-agent": "~0.6.1", - "form-data": "~2.3.1", - "har-validator": "~5.0.3", - "hawk": "~6.0.2", + "form-data": "~2.3.2", + "har-validator": "~5.1.0", "http-signature": "~1.2.0", "is-typedarray": "~1.0.0", "isstream": "~0.1.2", "json-stringify-safe": "~5.0.1", - "mime-types": "~2.1.17", - "oauth-sign": "~0.8.2", + "mime-types": "~2.1.19", + "oauth-sign": "~0.9.0", "performance-now": "^2.1.0", - "qs": "~6.5.1", - "safe-buffer": "^5.1.1", - "stringstream": "~0.0.5", - "tough-cookie": "~2.3.3", + "qs": "~6.5.2", + "safe-buffer": "^5.1.2", + "tough-cookie": "~2.4.3", "tunnel-agent": "^0.6.0", - "uuid": "^3.1.0" + "uuid": "^3.3.2" } }, "request-progress": { @@ -3183,30 +3620,25 @@ "throttleit": "^1.0.0" } }, - "require-uncached": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/require-uncached/-/require-uncached-1.0.3.tgz", - "integrity": "sha1-Tg1W1slmL9MeQwEcS5WqSZVUIdM=", - "dev": true, - "requires": { - "caller-path": "^0.1.0", - "resolve-from": "^1.0.0" - } - }, "resolve": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.4.0.tgz", - "integrity": "sha512-aW7sVKPufyHqOmyyLzg/J+8606v5nevBgaliIlV7nUpVMsDnoBGV/cbSLNjZAg9q0Cfd/+easKVKQ8vOu8fn1Q==", + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.6.0.tgz", + "integrity": "sha512-mw7JQNu5ExIkcw4LPih0owX/TZXjD/ZUF/ZQ/pDnkw3ZKhDcZZw5klmBlj6gVMwjQ3Pz5Jgu7F3d0jcDVuEWdw==", "requires": { "path-parse": "^1.0.5" } }, "resolve-from": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-1.0.1.tgz", - "integrity": "sha1-Jsv+k10a7uq7Kbw/5a6wHpPUQiY=", + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-4.0.0.tgz", + "integrity": "sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==", "dev": true }, + "resolve-url": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/resolve-url/-/resolve-url-0.2.1.tgz", + "integrity": "sha1-LGN/53yJOv0qZj/iGqkIAGjiBSo=" + }, "restore-cursor": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-2.0.0.tgz", @@ -3217,27 +3649,36 @@ "signal-exit": "^3.0.2" } }, + "ret": { + "version": "0.1.15", + "resolved": "https://registry.npmjs.org/ret/-/ret-0.1.15.tgz", + "integrity": "sha512-TTlYpa+OL+vMMNG24xSlQGEJ3B/RzEfUlLct7b5G/ytav+wPrplCpVMFuwzXbkecJrb6IYo1iFb0S9v37754mg==" + }, "rimraf": { - "version": "2.6.2", - "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.6.2.tgz", - "integrity": "sha512-lreewLK/BlghmxtfH36YYVg1i8IAce4TI7oao75I1g245+6BctqTVQiBP3YUJ9C6DQOXJmkYR9X9fCLtCOJc5w==", + "version": "2.6.3", + "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.6.3.tgz", + "integrity": "sha512-mwqeW5XsA2qAejG46gYdENaxXjx9onRNCfn7L0duuP4hCuTIi/QO7PDK07KJfp1d+izWPrzEJDcSqBa0OZQriA==", "requires": { - "glob": "^7.0.5" + "glob": "^7.1.3" } }, "ripemd160": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/ripemd160/-/ripemd160-2.0.1.tgz", - "integrity": "sha1-D0WEKVxTo2KK9+bXmsohzlfRxuc=", + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/ripemd160/-/ripemd160-2.0.2.tgz", + "integrity": "sha512-ii4iagi25WusVoiC4B4lq7pbXfAp3D9v5CwfkY33vffw2+pkDjY1D8GaN7spsxvCSx8dkPqOZCEZyfxcmJG2IA==", "requires": { - "hash-base": "^2.0.0", + "hash-base": "^3.0.0", "inherits": "^2.0.1" } }, "rlp": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/rlp/-/rlp-2.0.0.tgz", - "integrity": "sha1-nbOE/0uJqPYVY9kjldhiWxjzr7A=" + "version": "2.2.2", + "resolved": "https://registry.npmjs.org/rlp/-/rlp-2.2.2.tgz", + "integrity": "sha512-Ng2kJEN731Sfv4ZAY2i0ytPMc0BbJKBsVNl0QZY8LxOWSwd+1xpg+fpSRfaMn0heHU447s6Kgy8qfHZR0XTyVw==", + "requires": { + "bn.js": "^4.11.1", + "safe-buffer": "^5.1.1" + } }, "run-async": { "version": "2.3.0", @@ -3249,24 +3690,31 @@ } }, "rxjs": { - "version": "6.3.2", - "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-6.3.2.tgz", - "integrity": "sha512-hV7criqbR0pe7EeL3O66UYVg92IR0XsA97+9y+BWTePK9SKmEI5Qd3Zj6uPnGkNzXsBywBQWTvujPl+1Kn9Zjw==", + "version": "6.4.0", + "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-6.4.0.tgz", + "integrity": "sha512-Z9Yfa11F6B9Sg/BK9MnqnQ+aQYicPLtilXBp2yUtDt2JRCE0h26d33EnfO3ZxoNxG0T92OUucP3Ct7cpfkdFfw==", "dev": true, "requires": { "tslib": "^1.9.0" } }, "safe-buffer": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz", - "integrity": "sha512-kKvNJn6Mm93gAczWVJg7wH+wGYWNrDHdWvpUmHyEsgCtIwwo3bqPtV4tR5tuPaUhTOo/kvhVwd8XwwOllGYkbg==" + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", + "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==" + }, + "safe-regex": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/safe-regex/-/safe-regex-1.1.0.tgz", + "integrity": "sha1-QKNmnzsHfR6UPURinhV91IAjvy4=", + "requires": { + "ret": "~0.1.10" + } }, "safer-buffer": { "version": "2.1.2", "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", - "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==", - "dev": true + "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==" }, "scrypt": { "version": "6.0.3", @@ -3294,9 +3742,9 @@ } }, "secp256k1": { - "version": "3.5.0", - "resolved": "https://registry.npmjs.org/secp256k1/-/secp256k1-3.5.0.tgz", - "integrity": "sha512-e5QIJl8W7Y4tT6LHffVcZAxJjvpgE5Owawv6/XCYPQljE9aP2NFFddQ8OYMKhdLshNu88FfL3qCN3/xYkXGRsA==", + "version": "3.6.2", + "resolved": "https://registry.npmjs.org/secp256k1/-/secp256k1-3.6.2.tgz", + "integrity": "sha512-90nYt7yb0LmI4A2jJs1grglkTAXrBwxYAjP9bpeKjvJKOjG2fOeH/YI/lchDMIvjrOasd5QXwvV2jwN168xNng==", "requires": { "bindings": "^1.2.1", "bip66": "^1.1.3", @@ -3317,9 +3765,9 @@ } }, "semver": { - "version": "5.4.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.4.1.tgz", - "integrity": "sha512-WfG/X9+oATh81XtllIo/I8gOiY9EXRdv1cQdyykeXK17YcUW3EXUAi2To4pcH6nZtJPr7ZOpM5OMyWJZm+8Rsg==" + "version": "5.6.0", + "resolved": "https://registry.npmjs.org/semver/-/semver-5.6.0.tgz", + "integrity": "sha512-RS9R6R35NYgQn++fkDWaOmqGoj4Ek9gGs+DPxNUZKuwE183xjJroKvyo1IzVFeXvUrvmALy6FWD5xrdJT25gMg==" }, "send": { "version": "0.16.2", @@ -3371,15 +3819,36 @@ "xhr": "^2.3.3" } }, + "set-value": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/set-value/-/set-value-2.0.0.tgz", + "integrity": "sha512-hw0yxk9GT/Hr5yJEYnHNKYXkIA8mVJgd9ditYZCe16ZczcaELYYcfvaXesNACk2O8O0nTiPQcQhGUQj8JLzeeg==", + "requires": { + "extend-shallow": "^2.0.1", + "is-extendable": "^0.1.1", + "is-plain-object": "^2.0.3", + "split-string": "^3.0.1" + }, + "dependencies": { + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "requires": { + "is-extendable": "^0.1.0" + } + } + } + }, "setimmediate": { "version": "1.0.5", "resolved": "https://registry.npmjs.org/setimmediate/-/setimmediate-1.0.5.tgz", "integrity": "sha1-KQy7Iy4waULX1+qbg3Mqt4VvgoU=" }, "setprototypeof": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.0.3.tgz", - "integrity": "sha1-ZlZ+NwQ+608E2RvWWMDL77VbjgQ=" + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.1.0.tgz", + "integrity": "sha512-BvE/TwpZX4FXExxOxZyRGQQv651MSwmWKZGqvmPcRIjDqWub67kTKuIMx43cZZrS/cBBzwBcNDWoFxt2XEFIpQ==" }, "sha.js": { "version": "2.4.11", @@ -3391,11 +3860,18 @@ } }, "sha3": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/sha3/-/sha3-1.2.0.tgz", - "integrity": "sha1-aYnxtwpJhwWHajc+LGKs6WqpOZo=", + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/sha3/-/sha3-1.2.2.tgz", + "integrity": "sha1-pmxQmN5MJbyIM27ItIF9AFvKe6k=", "requires": { - "nan": "^2.0.5" + "nan": "2.10.0" + }, + "dependencies": { + "nan": { + "version": "2.10.0", + "resolved": "https://registry.npmjs.org/nan/-/nan-2.10.0.tgz", + "integrity": "sha512-bAdJv7fBLhWC+/Bls0Oza+mvTaNQtP+1RyhhhvD95pgUJz6XM5IzgmxOkItJ9tkoCiplvAnXI1tNmmUD/eScyA==" + } } }, "shebang-command": { @@ -3419,56 +3895,166 @@ "integrity": "sha1-tf3AjxKH6hF4Yo5BXiUTK3NkbG0=", "dev": true }, - "simple-bufferstream": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/simple-bufferstream/-/simple-bufferstream-1.0.0.tgz", - "integrity": "sha1-XKsQ6FGqccZnt3th/hux2QpguqQ=" - }, "simple-concat": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/simple-concat/-/simple-concat-1.0.0.tgz", "integrity": "sha1-c0TLuLbib7J9ZrL8hvn21Zl1IcY=" }, "simple-get": { - "version": "2.7.0", - "resolved": "https://registry.npmjs.org/simple-get/-/simple-get-2.7.0.tgz", - "integrity": "sha512-RkE9rGPHcxYZ/baYmgJtOSM63vH0Vyq+ma5TijBcLla41SWlh8t6XYIGMR/oeZcmr+/G8k+zrClkkVrtnQ0esg==", + "version": "2.8.1", + "resolved": "https://registry.npmjs.org/simple-get/-/simple-get-2.8.1.tgz", + "integrity": "sha512-lSSHRSw3mQNUGPAYRqo7xy9dhKmxFXIjLjp4KHpf99GEH2VH7C3AM+Qfx6du6jhfUi6Vm7XnbEVEf7Wb6N8jRw==", "requires": { "decompress-response": "^3.3.0", "once": "^1.3.1", "simple-concat": "^1.0.0" } }, - "slice-ansi": { + "slash": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/slice-ansi/-/slice-ansi-1.0.0.tgz", - "integrity": "sha512-POqxBK6Lb3q6s047D/XsDVNPnF9Dl8JSaqe9h9lURl0OdNqy/ujDrOiIHtsqXMGbWWTIomRzAMaTyawAU//Reg==", + "resolved": "https://registry.npmjs.org/slash/-/slash-1.0.0.tgz", + "integrity": "sha1-xB8vbDn8FtHNF61LXYlhFK5HDVU=" + }, + "slice-ansi": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/slice-ansi/-/slice-ansi-2.1.0.tgz", + "integrity": "sha512-Qu+VC3EwYLldKa1fCxuuvULvSJOKEgk9pi8dZeCVK7TqBfUNTH4sFkk4joj8afVSfAYgJoSOetjx9QWOJ5mYoQ==", "dev": true, "requires": { + "ansi-styles": "^3.2.0", + "astral-regex": "^1.0.0", "is-fullwidth-code-point": "^2.0.0" } }, - "sntp": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/sntp/-/sntp-2.1.0.tgz", - "integrity": "sha512-FL1b58BDrqS3A11lJ0zEdnJ3UOKqVxawAkF3k7F0CVN7VQ34aZrV+G8BZ1WC9ZL7NyrwsW0oviwsWDgRuVYtJg==", + "snapdragon": { + "version": "0.8.2", + "resolved": "https://registry.npmjs.org/snapdragon/-/snapdragon-0.8.2.tgz", + "integrity": "sha512-FtyOnWN/wCHTVXOMwvSv26d+ko5vWlIDD6zoUJ7LW8vh+ZBC8QdljveRP+crNrtBwioEUWy/4dMtbBjA4ioNlg==", + "requires": { + "base": "^0.11.1", + "debug": "^2.2.0", + "define-property": "^0.2.5", + "extend-shallow": "^2.0.1", + "map-cache": "^0.2.2", + "source-map": "^0.5.6", + "source-map-resolve": "^0.5.0", + "use": "^3.1.0" + }, + "dependencies": { + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "requires": { + "is-descriptor": "^0.1.0" + } + }, + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "requires": { + "is-extendable": "^0.1.0" + } + }, + "source-map": { + "version": "0.5.7", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", + "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=" + } + } + }, + "snapdragon-node": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/snapdragon-node/-/snapdragon-node-2.1.1.tgz", + "integrity": "sha512-O27l4xaMYt/RSQ5TR3vpWCAB5Kb/czIcqUFOM/C4fYcLnbZUc1PkjTAMjof2pBWaSTwOUd6qUHcFGVGj7aIwnw==", + "requires": { + "define-property": "^1.0.0", + "isobject": "^3.0.0", + "snapdragon-util": "^3.0.1" + }, + "dependencies": { + "define-property": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-1.0.0.tgz", + "integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=", + "requires": { + "is-descriptor": "^1.0.0" + } + }, + "is-accessor-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz", + "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-data-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz", + "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-descriptor": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz", + "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", + "requires": { + "is-accessor-descriptor": "^1.0.0", + "is-data-descriptor": "^1.0.0", + "kind-of": "^6.0.2" + } + } + } + }, + "snapdragon-util": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/snapdragon-util/-/snapdragon-util-3.0.1.tgz", + "integrity": "sha512-mbKkMdQKsjX4BAL4bRYTj21edOf8cN7XHdYUJEe+Zn99hVEYcMvKPct1IqNe7+AZPirn8BCDOQBHQZknqmKlZQ==", "requires": { - "hoek": "4.x.x" + "kind-of": "^3.2.0" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "requires": { + "is-buffer": "^1.1.5" + } + } } }, "source-map": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.2.0.tgz", - "integrity": "sha1-2rc/vPwrqBm03gO9b26qSBZLP50=", - "optional": true, + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", + "optional": true + }, + "source-map-resolve": { + "version": "0.5.2", + "resolved": "https://registry.npmjs.org/source-map-resolve/-/source-map-resolve-0.5.2.tgz", + "integrity": "sha512-MjqsvNwyz1s0k81Goz/9vRBe9SZdB09Bdw+/zYyO+3CuPk6fouTaxscHkgtE8jKvf01kVfl8riHzERQ/kefaSA==", "requires": { - "amdefine": ">=0.0.4" + "atob": "^2.1.1", + "decode-uri-component": "^0.2.0", + "resolve-url": "^0.2.1", + "source-map-url": "^0.4.0", + "urix": "^0.1.0" } }, + "source-map-url": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/source-map-url/-/source-map-url-0.4.0.tgz", + "integrity": "sha1-PpNdfd1zYxuXZZlW1VEo6HtQhKM=" + }, "spdx-correct": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/spdx-correct/-/spdx-correct-3.0.0.tgz", - "integrity": "sha512-N19o9z5cEyc8yQQPukRCZ9EUmb4HUpnrmaL/fxS2pBo2jbfcFRVuFZ/oFC+vZz0MNNk0h80iMn5/S6qGZOL5+g==", + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/spdx-correct/-/spdx-correct-3.1.0.tgz", + "integrity": "sha512-lr2EZCctC2BNR7j7WzJ2FpDznxky1sjfxvvYEyzxNyb6lZXHODmEoJeFu4JupYlkfha1KZpJyoqiJ7pgA1qq8Q==", "dev": true, "requires": { "spdx-expression-parse": "^3.0.0", @@ -3476,9 +4062,9 @@ } }, "spdx-exceptions": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/spdx-exceptions/-/spdx-exceptions-2.1.0.tgz", - "integrity": "sha512-4K1NsmrlCU1JJgUrtgEeTVyfx8VaYea9J9LvARxhbHtVtohPs/gFGG5yy49beySjlIMhhXZ4QqujIZEfS4l6Cg==", + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/spdx-exceptions/-/spdx-exceptions-2.2.0.tgz", + "integrity": "sha512-2XQACfElKi9SlVb1CYadKDXvoajPgBVPn/gOQLrTvHdElaVhr7ZEbqJaRnJLVNeaI4cMEAgVCeBMKF6MWRDCRA==", "dev": true }, "spdx-expression-parse": { @@ -3492,11 +4078,19 @@ } }, "spdx-license-ids": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/spdx-license-ids/-/spdx-license-ids-3.0.1.tgz", - "integrity": "sha512-TfOfPcYGBB5sDuPn3deByxPhmfegAhpDYKSOXZQN81Oyrrif8ZCodOLzK3AesELnCx03kikhyDwh0pfvvQvF8w==", + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/spdx-license-ids/-/spdx-license-ids-3.0.3.tgz", + "integrity": "sha512-uBIcIl3Ih6Phe3XHK1NqboJLdGfwr1UN3k6wSD1dZpmPsIkb8AGNbZYJ1fOBk834+Gxy8rpfDxrS6XLEMZMY2g==", "dev": true }, + "split-string": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/split-string/-/split-string-3.1.0.tgz", + "integrity": "sha512-NzNVhJDYpwceVVii8/Hu6DKfD2G+NrQHlS/V/qgv763EYudVwEcMQNxd2lh+0VrUByXN/oJkl5grOhYWvQUYiw==", + "requires": { + "extend-shallow": "^3.0.0" + } + }, "sprintf-js": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz", @@ -3504,9 +4098,9 @@ "dev": true }, "sshpk": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/sshpk/-/sshpk-1.14.1.tgz", - "integrity": "sha1-Ew9Zde3a2WPx1W+SuaxsUfqfg+s=", + "version": "1.16.1", + "resolved": "https://registry.npmjs.org/sshpk/-/sshpk-1.16.1.tgz", + "integrity": "sha512-HXXqVUq7+pcKeLqqZj6mHFUMvXtOJt1uoUx09pFW6011inTMxqI8BA8PM95myrIyyKwdnzjdFjLiE6KBPVtJIg==", "requires": { "asn1": "~0.2.3", "assert-plus": "^1.0.0", @@ -3515,9 +4109,29 @@ "ecc-jsbn": "~0.1.1", "getpass": "^0.1.1", "jsbn": "~0.1.0", + "safer-buffer": "^2.0.2", "tweetnacl": "~0.14.0" } }, + "static-extend": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/static-extend/-/static-extend-0.1.2.tgz", + "integrity": "sha1-YICcOcv/VTNyJv1eC1IPNB8ftcY=", + "requires": { + "define-property": "^0.2.5", + "object-copy": "^0.1.0" + }, + "dependencies": { + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "requires": { + "is-descriptor": "^0.1.0" + } + } + } + }, "statuses": { "version": "1.5.0", "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.5.0.tgz", @@ -3547,18 +4161,13 @@ } }, "string_decoder": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "integrity": "sha512-4AH6Z5fzNNBcH+6XDMfA/BTt87skxqJlO0lAh3Dker5zThcAxG6mKz+iGu308UKoPPQ8Dcqx/4JhujzltRa+hQ==", + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", + "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", "requires": { "safe-buffer": "~5.1.0" } }, - "stringstream": { - "version": "0.0.5", - "resolved": "https://registry.npmjs.org/stringstream/-/stringstream-0.0.5.tgz", - "integrity": "sha1-TkhM1N5aC7vuGORjB3EKioFiGHg=" - }, "strip-ansi": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", @@ -3597,11 +4206,11 @@ "dev": true }, "supports-color": { - "version": "4.5.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-4.5.0.tgz", - "integrity": "sha1-vnoN5ITexcXN34s9WRJQRJEvY1s=", + "version": "5.5.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", + "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", "requires": { - "has-flag": "^2.0.0" + "has-flag": "^3.0.0" } }, "swarm-js": { @@ -3622,45 +4231,64 @@ "setimmediate": "^1.0.5", "tar.gz": "^1.0.5", "xhr-request-promise": "^0.1.2" + }, + "dependencies": { + "fs-extra": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-2.1.2.tgz", + "integrity": "sha1-BGxwFjzvmq1GsOSn+kZ/si1x3jU=", + "requires": { + "graceful-fs": "^4.1.2", + "jsonfile": "^2.1.0" + } + }, + "jsonfile": { + "version": "2.4.0", + "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-2.4.0.tgz", + "integrity": "sha1-NzaitCi4e72gzIO1P6PWM6NcKug=", + "requires": { + "graceful-fs": "^4.1.6" + } + } } }, "table": { - "version": "4.0.3", - "resolved": "http://registry.npmjs.org/table/-/table-4.0.3.tgz", - "integrity": "sha512-S7rnFITmBH1EnyKcvxBh1LjYeQMmnZtCXSEbHcH6S0NoKit24ZuFO/T1vDcLdYsLQkM188PVVhQmzKIuThNkKg==", + "version": "5.2.3", + "resolved": "https://registry.npmjs.org/table/-/table-5.2.3.tgz", + "integrity": "sha512-N2RsDAMvDLvYwFcwbPyF3VmVSSkuF+G1e+8inhBLtHpvwXGw4QRPEZhihQNeEN0i1up6/f6ObCJXNdlRG3YVyQ==", "dev": true, "requires": { - "ajv": "^6.0.1", - "ajv-keywords": "^3.0.0", - "chalk": "^2.1.0", - "lodash": "^4.17.4", - "slice-ansi": "1.0.0", - "string-width": "^2.1.1" + "ajv": "^6.9.1", + "lodash": "^4.17.11", + "slice-ansi": "^2.1.0", + "string-width": "^3.0.0" }, "dependencies": { - "ajv": { - "version": "6.5.3", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.5.3.tgz", - "integrity": "sha512-LqZ9wY+fx3UMiiPd741yB2pj3hhil+hQc8taf4o2QGRFpWgZ2V5C8HA165DY9sS3fJwsk7uT7ZlFEyC3Ig3lLg==", + "ansi-regex": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-4.0.0.tgz", + "integrity": "sha512-iB5Dda8t/UqpPI/IjsejXu5jOGDrzn41wJyljwPH65VCIbk6+1BzFIMJGFwTNrYXT1CrD+B4l19U7awiQ8rk7w==", + "dev": true + }, + "string-width": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-3.0.0.tgz", + "integrity": "sha512-rr8CUxBbvOZDUvc5lNIJ+OC1nPVpz+Siw9VBtUjB9b6jZehZLFt0JMCZzShFHIsI8cbhm0EsNIfWJMFV3cu3Ew==", "dev": true, "requires": { - "fast-deep-equal": "^2.0.1", - "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.4.1", - "uri-js": "^4.2.2" + "emoji-regex": "^7.0.1", + "is-fullwidth-code-point": "^2.0.0", + "strip-ansi": "^5.0.0" } }, - "fast-deep-equal": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-2.0.1.tgz", - "integrity": "sha1-ewUhjd+WZ79/Nwv3/bLLFf3Qqkk=", - "dev": true - }, - "json-schema-traverse": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", - "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", - "dev": true + "strip-ansi": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-5.0.0.tgz", + "integrity": "sha512-Uu7gQyZI7J7gn5qLn1Np3G9vcYGTVqB+lFTytnDJv83dd8T22aGH451P3jueT2/QemInJDfxHB5Tde5OzgG1Ow==", + "dev": true, + "requires": { + "ansi-regex": "^4.0.0" + } } } }, @@ -3675,13 +4303,16 @@ } }, "tar-stream": { - "version": "1.5.5", - "resolved": "https://registry.npmjs.org/tar-stream/-/tar-stream-1.5.5.tgz", - "integrity": "sha512-mQdgLPc/Vjfr3VWqWbfxW8yQNiJCbAZ+Gf6GDu1Cy0bdb33ofyiNGBtAY96jHFhDuivCwgW1H9DgTON+INiXgg==", + "version": "1.6.2", + "resolved": "https://registry.npmjs.org/tar-stream/-/tar-stream-1.6.2.tgz", + "integrity": "sha512-rzS0heiNf8Xn7/mpdSVVSMAWAoy9bfb1WOTYC78Z0UQKeKa/CWS8FOq0lKGNa8DWKAn9gxjCvMLYc5PGXYlK2A==", "requires": { "bl": "^1.0.0", + "buffer-alloc": "^1.2.0", "end-of-stream": "^1.0.0", - "readable-stream": "^2.0.0", + "fs-constants": "^1.0.0", + "readable-stream": "^2.3.0", + "to-buffer": "^1.1.1", "xtend": "^4.0.0" } }, @@ -3750,12 +4381,63 @@ "os-tmpdir": "~1.0.2" } }, + "to-buffer": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/to-buffer/-/to-buffer-1.1.1.tgz", + "integrity": "sha512-lx9B5iv7msuFYE3dytT+KE5tap+rNYw+K4jVkb9R/asAb+pbBSM17jtunHplhBe6RRJdZx3Pn2Jph24O32mOVg==" + }, + "to-object-path": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/to-object-path/-/to-object-path-0.3.0.tgz", + "integrity": "sha1-KXWIt7Dn4KwI4E5nL4XB9JmeF68=", + "requires": { + "kind-of": "^3.0.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "requires": { + "is-buffer": "^1.1.5" + } + } + } + }, + "to-regex": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/to-regex/-/to-regex-3.0.2.tgz", + "integrity": "sha512-FWtleNAtZ/Ki2qtqej2CXTOayOH9bHDQF+Q48VpWyDXjbYxA4Yz8iDB31zXOBUlOHHKidDbqGVrTUvQMPmBGBw==", + "requires": { + "define-property": "^2.0.2", + "extend-shallow": "^3.0.2", + "regex-not": "^1.0.2", + "safe-regex": "^1.1.0" + } + }, + "to-regex-range": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-2.1.1.tgz", + "integrity": "sha1-fIDBe53+vlmeJzZ+DU3VWQFB2zg=", + "requires": { + "is-number": "^3.0.0", + "repeat-string": "^1.6.1" + } + }, "tough-cookie": { - "version": "2.3.4", - "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.3.4.tgz", - "integrity": "sha512-TZ6TTfI5NtZnuyy/Kecv+CnoROnyXn2DN97LontgQpCwsX2XyLYCC0ENhYkehSOwAp8rTQKc/NUIF7BkQ5rKLA==", + "version": "2.4.3", + "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.4.3.tgz", + "integrity": "sha512-Q5srk/4vDM54WJsJio3XNn6K2sCG+CQ8G5Wz6bZhRZoAe/+TxjWB/GlFAnYEbkYVlON9FMk/fE3h2RLpPXo4lQ==", "requires": { + "psl": "^1.1.24", "punycode": "^1.4.1" + }, + "dependencies": { + "punycode": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/punycode/-/punycode-1.4.1.tgz", + "integrity": "sha1-wNWmOycYgArY4esPpSachN1BhF4=" + } } }, "trim": { @@ -3780,8 +4462,7 @@ "tweetnacl": { "version": "0.14.5", "resolved": "https://registry.npmjs.org/tweetnacl/-/tweetnacl-0.14.5.tgz", - "integrity": "sha1-WuaBd/GS1EViadEIr6k/+HQ/T2Q=", - "optional": true + "integrity": "sha1-WuaBd/GS1EViadEIr6k/+HQ/T2Q=" }, "type-check": { "version": "0.3.2", @@ -3819,36 +4500,51 @@ "integrity": "sha512-UIEXBNeYmKptWH6z8ZnqTeS8fV74zG0/eRU9VGkpzz+LIJNs8W/zM/L+7ctCkRrgbNnnR0xxw4bKOr0cW0N0Og==" }, "unbzip2-stream": { - "version": "1.2.5", - "resolved": "https://registry.npmjs.org/unbzip2-stream/-/unbzip2-stream-1.2.5.tgz", - "integrity": "sha512-izD3jxT8xkzwtXRUZjtmRwKnZoeECrfZ8ra/ketwOcusbZEp4mjULMnJOCfTDZBgGQAAY1AJ/IgxcwkavcX9Og==", + "version": "1.3.3", + "resolved": "https://registry.npmjs.org/unbzip2-stream/-/unbzip2-stream-1.3.3.tgz", + "integrity": "sha512-fUlAF7U9Ah1Q6EieQ4x4zLNejrRvDWUYmxXUpN3uziFYCHapjWFaCAnreY9bGgxzaMCFAPPpYNng57CypwJVhg==", "requires": { - "buffer": "^3.0.1", - "through": "^2.3.6" + "buffer": "^5.2.1", + "through": "^2.3.8" + } + }, + "underscore": { + "version": "1.8.3", + "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", + "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=" + }, + "union-value": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/union-value/-/union-value-1.0.0.tgz", + "integrity": "sha1-XHHDTLW61dzr4+oM0IIHulqhrqQ=", + "requires": { + "arr-union": "^3.1.0", + "get-value": "^2.0.6", + "is-extendable": "^0.1.1", + "set-value": "^0.4.3" }, "dependencies": { - "base64-js": { - "version": "0.0.8", - "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-0.0.8.tgz", - "integrity": "sha1-EQHpVE9KdrG8OybUUsqW16NeeXg=" + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "requires": { + "is-extendable": "^0.1.0" + } }, - "buffer": { - "version": "3.6.0", - "resolved": "https://registry.npmjs.org/buffer/-/buffer-3.6.0.tgz", - "integrity": "sha1-pyyTb3e5a/UvX357RnGAYoVR3vs=", + "set-value": { + "version": "0.4.3", + "resolved": "https://registry.npmjs.org/set-value/-/set-value-0.4.3.tgz", + "integrity": "sha1-fbCPnT0i3H945Trzw79GZuzfzPE=", "requires": { - "base64-js": "0.0.8", - "ieee754": "^1.1.4", - "isarray": "^1.0.0" + "extend-shallow": "^2.0.1", + "is-extendable": "^0.1.1", + "is-plain-object": "^2.0.1", + "to-object-path": "^0.3.0" } } } }, - "underscore": { - "version": "1.8.3", - "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", - "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=" - }, "unique-temp-dir": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/unique-temp-dir/-/unique-temp-dir-1.0.0.tgz", @@ -3860,32 +4556,64 @@ } }, "universalify": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/universalify/-/universalify-0.1.1.tgz", - "integrity": "sha1-+nG63UQ3r0wUiEHjs7Fl+enlkLc=" + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/universalify/-/universalify-0.1.2.tgz", + "integrity": "sha512-rBJeI5CXAlmy1pV+617WB9J63U6XcazHHF2f2dbJix4XzpUF0RS3Zbj0FGIOCAva5P/d/GBOYaACQ1w+0azUkg==" }, "unpipe": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/unpipe/-/unpipe-1.0.0.tgz", "integrity": "sha1-sr9O6FFKrmFltIF4KdIbLvSZBOw=" }, + "unset-value": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/unset-value/-/unset-value-1.0.0.tgz", + "integrity": "sha1-g3aHP30jNRef+x5vw6jtDfyKtVk=", + "requires": { + "has-value": "^0.3.1", + "isobject": "^3.0.0" + }, + "dependencies": { + "has-value": { + "version": "0.3.1", + "resolved": "https://registry.npmjs.org/has-value/-/has-value-0.3.1.tgz", + "integrity": "sha1-ex9YutpiyoJ+wKIHgCVlSEWZXh8=", + "requires": { + "get-value": "^2.0.3", + "has-values": "^0.1.4", + "isobject": "^2.0.0" + }, + "dependencies": { + "isobject": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/isobject/-/isobject-2.1.0.tgz", + "integrity": "sha1-8GVWEJaj8dou9GJy+BXIQNh+DIk=", + "requires": { + "isarray": "1.0.0" + } + } + } + }, + "has-values": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/has-values/-/has-values-0.1.4.tgz", + "integrity": "sha1-bWHeldkd/Km5oCCJrThL/49it3E=" + } + } + }, "uri-js": { "version": "4.2.2", "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.2.2.tgz", "integrity": "sha512-KY9Frmirql91X2Qgjry0Wd4Y+YTdrdZheS8TFwvkbLWf/G5KNJDCh6pKL5OZctEW4+0Baa5idK2ZQuELRwPznQ==", - "dev": true, "requires": { "punycode": "^2.1.0" - }, - "dependencies": { - "punycode": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.1.1.tgz", - "integrity": "sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A==", - "dev": true - } } }, + "urix": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/urix/-/urix-0.1.0.tgz", + "integrity": "sha1-2pN/emLiH+wf0Y1Js1wpNQZ6bHI=" + }, "url-parse-lax": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/url-parse-lax/-/url-parse-lax-1.0.0.tgz", @@ -3904,6 +4632,11 @@ "resolved": "https://registry.npmjs.org/url-to-options/-/url-to-options-1.0.1.tgz", "integrity": "sha1-FQWgOiiaSMvXpDTvuu7FBV9WM6k=" }, + "use": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/use/-/use-3.1.1.tgz", + "integrity": "sha512-cwESVXlO3url9YWlFW/TA9cshCEhtu7IKJ/p5soJ/gGpj7vbvFrAY/eIioQ6Dw23KjZhYgiIo8HOs1nQ2vr/oQ==" + }, "utf8": { "version": "2.1.1", "resolved": "https://registry.npmjs.org/utf8/-/utf8-2.1.1.tgz", @@ -3920,9 +4653,9 @@ "integrity": "sha1-n5VxD1CiZ5R7LMwSR0HBAoQn5xM=" }, "uuid": { - "version": "3.2.1", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.2.1.tgz", - "integrity": "sha512-jZnMwlb9Iku/O3smGWvZhauCf6cvvpKi4BKRiliS3cxnI+Gz9j5MEpTz2UFuXiKPJocb7gnsLHwiS05ige5BEA==" + "version": "3.3.2", + "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.3.2.tgz", + "integrity": "sha512-yXJmeNaw3DnnKAOKJE51sL/ZaYfWJRl1pK9dr19YFCu0ObS231AB1/LbqTKRAQ5kw8A90rA6fr4riOUpTZvQZA==" }, "validate-npm-package-license": { "version": "3.0.4", @@ -3935,9 +4668,9 @@ } }, "validator": { - "version": "9.4.1", - "resolved": "http://registry.npmjs.org/validator/-/validator-9.4.1.tgz", - "integrity": "sha512-YV5KjzvRmSyJ1ee/Dm5UED0G+1L4GZnLN3w6/T+zZm8scVua4sOhYKWTUrKa0H/tMiJyO9QLHMPN+9mB/aMunA==" + "version": "10.11.0", + "resolved": "https://registry.npmjs.org/validator/-/validator-10.11.0.tgz", + "integrity": "sha512-X/p3UZerAIsbBfN/IwahhYaBbY68EN/UQBWHtsbXGT5bfrH/p4NQzUCG1kF/rtKaNpnJ7jAu6NGTdSNtyNIXMw==" }, "vary": { "version": "1.1.2", @@ -4192,7 +4925,7 @@ "requires": { "underscore": "1.8.3", "web3-core-helpers": "1.0.0-beta.33", - "websocket": "git://github.com/frozeman/WebSocket-Node.git#7004c39c42ac98875ab61126e5b4a925430f592c" + "websocket": "git://github.com/frozeman/WebSocket-Node.git#6c72925e3f8aaaea8dc8450f97627e85263999f2" } }, "web3-shh": { @@ -4228,8 +4961,8 @@ } }, "websocket": { - "version": "git://github.com/frozeman/WebSocket-Node.git#7004c39c42ac98875ab61126e5b4a925430f592c", - "from": "websocket@git://github.com/frozeman/WebSocket-Node.git#7004c39c42ac98875ab61126e5b4a925430f592c", + "version": "git://github.com/frozeman/WebSocket-Node.git#6c72925e3f8aaaea8dc8450f97627e85263999f2", + "from": "git://github.com/frozeman/WebSocket-Node.git#browserifyCompatible", "requires": { "debug": "^2.2.0", "nan": "^2.3.3", @@ -4257,9 +4990,9 @@ "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=" }, "write": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/write/-/write-0.2.1.tgz", - "integrity": "sha1-X8A4KOJkzqP+kUVUdvejxWbLB1c=", + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/write/-/write-1.0.3.tgz", + "integrity": "sha512-/lg70HAjtkUgWPVZhZcm+T4hkL8Zbtp1nFNOn3lRrxnlv50SRBv7cR7RqR+GMsd3hUXy9hWBo4CHTbFTcOYwig==", "dev": true, "requires": { "mkdirp": "^0.5.1" @@ -4276,9 +5009,9 @@ } }, "xhr": { - "version": "2.4.1", - "resolved": "https://registry.npmjs.org/xhr/-/xhr-2.4.1.tgz", - "integrity": "sha512-pAIU5vBr9Hiy5cpFIbPnwf0C18ZF86DBsZKrlsf87N5De/JbA6RJ83UP/cv+aljl4S40iRVMqP4pr4sF9Dnj0A==", + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/xhr/-/xhr-2.5.0.tgz", + "integrity": "sha512-4nlO/14t3BNUZRXIXfXe+3N6w3s1KoxcJUUURctd64BLRe67E4gRwp4PjywtDY72fXpZ1y6Ch0VZQRY/gMPzzQ==", "requires": { "global": "~4.3.0", "is-function": "^1.0.1", @@ -4324,12 +5057,12 @@ "integrity": "sha1-8m9ITXJoTPQr7ft2lwqhYI+/lXc=" }, "yauzl": { - "version": "2.9.1", - "resolved": "https://registry.npmjs.org/yauzl/-/yauzl-2.9.1.tgz", - "integrity": "sha1-qBmB6nCleUYTOIPwKcWCGok1mn8=", + "version": "2.10.0", + "resolved": "https://registry.npmjs.org/yauzl/-/yauzl-2.10.0.tgz", + "integrity": "sha1-x+sXyT4RLLEIb6bY5R+wZnt5pfk=", "requires": { "buffer-crc32": "~0.2.3", - "fd-slicer": "~1.0.1" + "fd-slicer": "~1.1.0" } } } diff --git a/deploy/package.json b/deploy/package.json index ecace1df5..831552c7e 100644 --- a/deploy/package.json +++ b/deploy/package.json @@ -15,7 +15,7 @@ "ethereumjs-tx": "^1.3.4", "node-fetch": "^2.1.2", "pkg": "^4.3.1", - "web3": "^1.0.0-beta.33" + "web3": "1.0.0-beta.33" }, "devDependencies": { "eslint": "^5.6.0", diff --git a/package-lock.json b/package-lock.json index 37f350ac1..301109f25 100644 --- a/package-lock.json +++ b/package-lock.json @@ -4,14 +4,67 @@ "lockfileVersion": 1, "requires": true, "dependencies": { - "@sindresorhus/is": { - "version": "0.7.0", - "resolved": "https://registry.npmjs.org/@sindresorhus/is/-/is-0.7.0.tgz", - "integrity": "sha512-ONhaKPIufzzrlNbqtWFFd+jlnemX6lJAgq9ZeiZtS7I1PIf/la7CW4m83rTXRnVnsMbW2k56pGYu7AUFJD9Pow==" + "@babel/runtime": { + "version": "7.3.1", + "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.3.1.tgz", + "integrity": "sha512-7jGW8ppV0ant637pIqAcFfQDDH1orEPGJb8aXfUozuCU3QqX7rX4DA8iwrbPrR1hcH0FTTHz47yQnk+bl5xHQA==", + "requires": { + "regenerator-runtime": "^0.12.0" + } + }, + "@resolver-engine/core": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/@resolver-engine/core/-/core-0.2.1.tgz", + "integrity": "sha512-nsLQHmPJ77QuifqsIvqjaF5B9aHnDzJjp73Q1z6apY3e9nqYrx4Dtowhpsf7Jwftg/XzVDEMQC+OzUBNTS+S1A==", + "dev": true, + "requires": { + "debug": "^3.1.0", + "request": "^2.85.0" + } + }, + "@resolver-engine/fs": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/@resolver-engine/fs/-/fs-0.2.1.tgz", + "integrity": "sha512-7kJInM1Qo2LJcKyDhuYzh9ZWd+mal/fynfL9BNjWOiTcOpX+jNfqb/UmGUqros5pceBITlWGqS4lU709yHFUbg==", + "dev": true, + "requires": { + "@resolver-engine/core": "^0.2.1", + "debug": "^3.1.0" + } + }, + "@resolver-engine/imports": { + "version": "0.2.2", + "resolved": "https://registry.npmjs.org/@resolver-engine/imports/-/imports-0.2.2.tgz", + "integrity": "sha512-u5/HUkvo8q34AA+hnxxqqXGfby5swnH0Myw91o3Sm2TETJlNKXibFGSKBavAH+wvWdBi4Z5gS2Odu0PowgVOUg==", + "dev": true, + "requires": { + "@resolver-engine/core": "^0.2.1", + "debug": "^3.1.0", + "hosted-git-info": "^2.6.0" + } + }, + "@resolver-engine/imports-fs": { + "version": "0.2.2", + "resolved": "https://registry.npmjs.org/@resolver-engine/imports-fs/-/imports-fs-0.2.2.tgz", + "integrity": "sha512-gFCgMvCwyppjwq0UzIjde/WI+yDs3oatJhozG9xdjJdewwtd7LiF0T5i9lrHAUtqrQbqoFE4E+ZMRVHWpWHpKQ==", + "dev": true, + "requires": { + "@resolver-engine/fs": "^0.2.1", + "@resolver-engine/imports": "^0.2.2", + "debug": "^3.1.0" + } + }, + "@types/bn.js": { + "version": "4.11.4", + "resolved": "https://registry.npmjs.org/@types/bn.js/-/bn.js-4.11.4.tgz", + "integrity": "sha512-AO8WW+aRcKWKQAYTfKLzwnpL6U+TfPqS+haRrhCy5ff04Da8WZud3ZgVjspQXaEXJDcTlsjUEVvL39wegDek5w==", + "requires": { + "@types/node": "*" + } }, "@types/concat-stream": { "version": "1.6.0", - "resolved": "http://registry.npmjs.org/@types/concat-stream/-/concat-stream-1.6.0.tgz", + "resolved": "https://registry.npmjs.org/@types/concat-stream/-/concat-stream-1.6.0.tgz", "integrity": "sha1-OU2+C7X+5Gs42JZzXoto7yOQ0A0=", "dev": true, "requires": { @@ -20,7 +73,7 @@ }, "@types/form-data": { "version": "0.0.33", - "resolved": "http://registry.npmjs.org/@types/form-data/-/form-data-0.0.33.tgz", + "resolved": "https://registry.npmjs.org/@types/form-data/-/form-data-0.0.33.tgz", "integrity": "sha1-yayFsqX9GENbjIXZ7LUObWyJP/g=", "dev": true, "requires": { @@ -28,10 +81,9 @@ } }, "@types/node": { - "version": "9.6.35", - "resolved": "https://registry.npmjs.org/@types/node/-/node-9.6.35.tgz", - "integrity": "sha512-h5zvHS8wXHGa+Gcqs9K8vqCgOtqjr0+NqG/DDJmQIX1wpR9HivAfgV8bjcD3mGM4bPfQw5Aneb2Pn8355L83jA==", - "dev": true + "version": "10.12.26", + "resolved": "https://registry.npmjs.org/@types/node/-/node-10.12.26.tgz", + "integrity": "sha512-nMRqS+mL1TOnIJrL6LKJcNZPB8V3eTfRo9FQA2b5gDvrHurC8XbSA86KNe0dShlEL7ReWJv/OU9NL7Z0dnqWTg==" }, "@types/qs": { "version": "6.5.1", @@ -52,75 +104,26 @@ "dev": true, "requires": { "web3": "^0.18.4" - }, - "dependencies": { - "bignumber.js": { - "version": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", - "from": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", - "dev": true - }, - "web3": { - "version": "0.18.4", - "resolved": "https://registry.npmjs.org/web3/-/web3-0.18.4.tgz", - "integrity": "sha1-gewXhBRUkfLqqJVbMcBgSeB8Xn0=", - "dev": true, - "requires": { - "bignumber.js": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", - "crypto-js": "^3.1.4", - "utf8": "^2.1.1", - "xhr2": "*", - "xmlhttprequest": "*" - } - } - } - }, - "accepts": { - "version": "1.3.5", - "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.5.tgz", - "integrity": "sha1-63d99gEXI6OxTopywIBcjoZ0a9I=", - "requires": { - "mime-types": "~2.1.18", - "negotiator": "0.6.1" } }, "ajv": { - "version": "5.5.2", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-5.5.2.tgz", - "integrity": "sha1-c7Xuyj+rZT49P5Qis0GtQiBdyWU=", - "requires": { - "co": "^4.6.0", - "fast-deep-equal": "^1.0.0", - "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.3.0" - } - }, - "align-text": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/align-text/-/align-text-0.1.4.tgz", - "integrity": "sha1-DNkKVhCT810KmSVsIrcGlDP60Rc=", + "version": "6.9.1", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.9.1.tgz", + "integrity": "sha512-XDN92U311aINL77ieWHmqCcNlwjoP5cHXDxIxbf2MaPYuCXOHS7gHH8jktxeK5omgd52XbSTX6a4Piwd1pQmzA==", "dev": true, "requires": { - "kind-of": "^3.0.2", - "longest": "^1.0.1", - "repeat-string": "^1.5.2" - }, - "dependencies": { - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", - "dev": true, - "requires": { - "is-buffer": "^1.1.5" - } - } + "fast-deep-equal": "^2.0.1", + "fast-json-stable-stringify": "^2.0.0", + "json-schema-traverse": "^0.4.1", + "uri-js": "^4.2.2" } }, "amdefine": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/amdefine/-/amdefine-1.0.1.tgz", "integrity": "sha1-SlKCrBZHKek2Gbz9OtFR+BfOkfU=", - "dev": true + "dev": true, + "optional": true }, "ansi-align": { "version": "2.0.0", @@ -164,11 +167,6 @@ } } }, - "ansi-escapes": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-3.1.0.tgz", - "integrity": "sha512-UgAb8H9D41AQnu/PbWlCofQVcnV4Gs2bBJi9eZPxfU/hgglFh3SMDMENRIqdr7H6XFnXdoknctFByVsCOotTVw==" - }, "ansi-regex": { "version": "2.1.1", "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz", @@ -178,15 +176,11 @@ "version": "3.2.1", "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz", "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==", + "dev": true, "requires": { "color-convert": "^1.9.0" } }, - "any-observable": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/any-observable/-/any-observable-0.2.0.tgz", - "integrity": "sha1-xnhwBYADV5AJCD9UrAq6+1wz0kI=" - }, "anymatch": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/anymatch/-/anymatch-2.0.0.tgz", @@ -195,6 +189,17 @@ "requires": { "micromatch": "^3.1.4", "normalize-path": "^2.1.1" + }, + "dependencies": { + "normalize-path": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-2.1.1.tgz", + "integrity": "sha1-GrKLVW4Zg2Oowab35vogE3/mrtk=", + "dev": true, + "requires": { + "remove-trailing-separator": "^1.0.1" + } + } } }, "argparse": { @@ -215,7 +220,8 @@ "arr-flatten": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/arr-flatten/-/arr-flatten-1.1.0.tgz", - "integrity": "sha512-L3hKV5R/p5o81R7O02IGnwpDmkp6E982XhtbuwSe3O4qOtMMMtodicASA1Cny2U+aCXcNpml+m4dPsvsJ3jatg==" + "integrity": "sha512-L3hKV5R/p5o81R7O02IGnwpDmkp6E982XhtbuwSe3O4qOtMMMtodicASA1Cny2U+aCXcNpml+m4dPsvsJ3jatg==", + "dev": true }, "arr-union": { "version": "3.1.0", @@ -223,40 +229,12 @@ "integrity": "sha1-45sJrqne+Gao8gbiiK9jkZuuOcQ=", "dev": true }, - "array-differ": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/array-differ/-/array-differ-1.0.0.tgz", - "integrity": "sha1-7/UuN1gknTO+QCuLuOVkuytdQDE=" - }, - "array-flatten": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-1.1.1.tgz", - "integrity": "sha1-ml9pkFGx5wczKPKgCJaLZOopVdI=" - }, - "array-union": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/array-union/-/array-union-1.0.2.tgz", - "integrity": "sha1-mjRBDk9OPaI96jdb5b5w8kd47Dk=", - "requires": { - "array-uniq": "^1.0.1" - } - }, - "array-uniq": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/array-uniq/-/array-uniq-1.0.3.tgz", - "integrity": "sha1-r2rId6Jcx/dOBYiUdThY39sk/bY=" - }, "array-unique": { "version": "0.3.2", "resolved": "https://registry.npmjs.org/array-unique/-/array-unique-0.3.2.tgz", "integrity": "sha1-qJS3XUvE9s1nnvMkSp/Y9Gri1Cg=", "dev": true }, - "arrify": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/arrify/-/arrify-1.0.1.tgz", - "integrity": "sha1-iYUI2iIm84DfkEcoRWhJwVAaSw0=" - }, "asap": { "version": "2.0.6", "resolved": "https://registry.npmjs.org/asap/-/asap-2.0.6.tgz", @@ -264,14 +242,19 @@ "dev": true }, "asn1": { - "version": "0.2.3", - "resolved": "https://registry.npmjs.org/asn1/-/asn1-0.2.3.tgz", - "integrity": "sha1-2sh4dxPJlmhJ/IGAd36+nB3fO4Y=" + "version": "0.2.4", + "resolved": "https://registry.npmjs.org/asn1/-/asn1-0.2.4.tgz", + "integrity": "sha512-jxwzQpLQjSmWXgwaCZE9Nz+glAG01yF1QnWgbhGwHI5A6FRIEY6IVqtHhIepHqI7/kyEyQEagBC5mBEFlIYvdg==", + "dev": true, + "requires": { + "safer-buffer": "~2.1.0" + } }, "assert-plus": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", - "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=" + "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", + "dev": true }, "assertion-error": { "version": "1.1.0", @@ -285,18 +268,11 @@ "integrity": "sha1-WWZ/QfrdTyDMvCu5a41Pf3jsA2c=", "dev": true }, - "ast-types": { - "version": "0.11.3", - "resolved": "https://registry.npmjs.org/ast-types/-/ast-types-0.11.3.tgz", - "integrity": "sha512-XA5o5dsNw8MhyW0Q7MWXJWc4oOzZKbdsEJq45h7c8q/d9DwWZ5F2ugUc1PuMLPGsUnphCt/cNDHu8JeBbxf1qA==" - }, "async": { - "version": "2.6.0", - "resolved": "https://registry.npmjs.org/async/-/async-2.6.0.tgz", - "integrity": "sha512-xAfGg1/NTLBBKlHFmnd7PlmUW9KhVQIUuSrYem9xzFUZy13ScvtyGGejaae9iAVRiRq9+Cx7DPFaAAhCpyxyPw==", - "requires": { - "lodash": "^4.14.0" - } + "version": "1.5.2", + "resolved": "https://registry.npmjs.org/async/-/async-1.5.2.tgz", + "integrity": "sha1-7GphrlZIDAw8skHJVhjiCJL5Zyo=", + "dev": true }, "async-each": { "version": "1.0.1", @@ -304,841 +280,659 @@ "integrity": "sha1-GdOGodntxufByF04iu28xW0zYC0=", "dev": true }, - "async-limiter": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/async-limiter/-/async-limiter-1.0.0.tgz", - "integrity": "sha512-jp/uFnooOiO+L211eZOoSyzpOITMXx1rBITauYykG3BRYPu8h0UcxsPNB04RR5vo4Tyz3+ay17tR6JVf9qzYWg==" - }, "asynckit": { "version": "0.4.0", "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", - "integrity": "sha1-x57Zf380y48robyXkLzDZkdLS3k=" + "integrity": "sha1-x57Zf380y48robyXkLzDZkdLS3k=", + "dev": true }, "atob": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/atob/-/atob-2.1.1.tgz", - "integrity": "sha1-ri1acpR38onWDdf5amMUoi3Wwio=", + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/atob/-/atob-2.1.2.tgz", + "integrity": "sha512-Wm6ukoaOGJi/73p/cl2GvLjTI5JM1k/O14isD73YML8StrH/7/lRFgmg8nICZgD3bZZvjwCGxtMOD3wWNAu8cg==", "dev": true }, "aws-sign2": { "version": "0.7.0", "resolved": "https://registry.npmjs.org/aws-sign2/-/aws-sign2-0.7.0.tgz", - "integrity": "sha1-tG6JCTSpWR8tL2+G1+ap8bP+dqg=" + "integrity": "sha1-tG6JCTSpWR8tL2+G1+ap8bP+dqg=", + "dev": true }, "aws4": { - "version": "1.7.0", - "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.7.0.tgz", - "integrity": "sha512-32NDda82rhwD9/JBCCkB+MRYDp0oSvlo2IL6rQWA10PQi7tDUM3eqMSltXmY+Oyl/7N3P3qNtAlv7X0d9bI28w==" + "version": "1.8.0", + "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.8.0.tgz", + "integrity": "sha512-ReZxvNHIOv88FlT7rxcXIIC0fPt4KZqZbOlivyWtXLt8ESx84zd3kMC6iK5jVeS2qt+g7ftS7ye4fi06X5rtRQ==", + "dev": true + }, + "balanced-match": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz", + "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=" }, - "babel-code-frame": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-code-frame/-/babel-code-frame-6.26.0.tgz", - "integrity": "sha1-Y/1D99weO7fONZR9uP42mj9Yx0s=", + "base": { + "version": "0.11.2", + "resolved": "https://registry.npmjs.org/base/-/base-0.11.2.tgz", + "integrity": "sha512-5T6P4xPgpp0YDFvSWwEZ4NoE3aM4QBQXDzmVbraCkFj8zHM+mba8SyqB5DbZWyR7mYHo6Y7BdQo3MoA4m0TeQg==", + "dev": true, "requires": { - "chalk": "^1.1.3", - "esutils": "^2.0.2", - "js-tokens": "^3.0.2" + "cache-base": "^1.0.1", + "class-utils": "^0.3.5", + "component-emitter": "^1.2.1", + "define-property": "^1.0.0", + "isobject": "^3.0.1", + "mixin-deep": "^1.2.0", + "pascalcase": "^0.1.1" }, "dependencies": { - "ansi-styles": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-2.2.1.tgz", - "integrity": "sha1-tDLdM1i2NM914eRmQ2gkBTPB3b4=" + "define-property": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-1.0.0.tgz", + "integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=", + "dev": true, + "requires": { + "is-descriptor": "^1.0.0" + } }, - "chalk": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz", - "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=", + "is-accessor-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz", + "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", + "dev": true, "requires": { - "ansi-styles": "^2.2.1", - "escape-string-regexp": "^1.0.2", - "has-ansi": "^2.0.0", - "strip-ansi": "^3.0.0", - "supports-color": "^2.0.0" + "kind-of": "^6.0.0" } }, - "supports-color": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz", - "integrity": "sha1-U10EXOa2Nj+kARcIRimZXp3zJMc=" - } - } - }, - "babel-core": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-core/-/babel-core-6.26.0.tgz", - "integrity": "sha1-rzL3izGm/O8RnIew/Y2XU/A6C7g=", - "requires": { - "babel-code-frame": "^6.26.0", - "babel-generator": "^6.26.0", - "babel-helpers": "^6.24.1", - "babel-messages": "^6.23.0", - "babel-register": "^6.26.0", - "babel-runtime": "^6.26.0", - "babel-template": "^6.26.0", - "babel-traverse": "^6.26.0", - "babel-types": "^6.26.0", - "babylon": "^6.18.0", - "convert-source-map": "^1.5.0", - "debug": "^2.6.8", - "json5": "^0.5.1", - "lodash": "^4.17.4", - "minimatch": "^3.0.4", - "path-is-absolute": "^1.0.1", - "private": "^0.1.7", - "slash": "^1.0.0", - "source-map": "^0.5.6" - }, - "dependencies": { - "babylon": { - "version": "6.18.0", - "resolved": "https://registry.npmjs.org/babylon/-/babylon-6.18.0.tgz", - "integrity": "sha512-q/UEjfGJ2Cm3oKV71DJz9d25TPnq5rhBVL2Q4fA5wcC3jcrdn7+SssEybFIxwAvvP+YCsCYNKughoF33GxgycQ==" - } - } - }, - "babel-generator": { - "version": "6.26.1", - "resolved": "https://registry.npmjs.org/babel-generator/-/babel-generator-6.26.1.tgz", - "integrity": "sha512-HyfwY6ApZj7BYTcJURpM5tznulaBvyio7/0d4zFOeMPUmfxkCjHocCuoLa2SAGzBI8AREcH3eP3758F672DppA==", - "requires": { - "babel-messages": "^6.23.0", - "babel-runtime": "^6.26.0", - "babel-types": "^6.26.0", - "detect-indent": "^4.0.0", - "jsesc": "^1.3.0", - "lodash": "^4.17.4", - "source-map": "^0.5.7", - "trim-right": "^1.0.1" - }, - "dependencies": { - "jsesc": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-1.3.0.tgz", - "integrity": "sha1-RsP+yMGJKxKwgz25vHYiF226s0s=" + "is-data-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz", + "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", + "dev": true, + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-descriptor": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz", + "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", + "dev": true, + "requires": { + "is-accessor-descriptor": "^1.0.0", + "is-data-descriptor": "^1.0.0", + "kind-of": "^6.0.2" + } } } }, - "babel-helper-bindify-decorators": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-bindify-decorators/-/babel-helper-bindify-decorators-6.24.1.tgz", - "integrity": "sha1-FMGeXxQte0fxmlJDHlKxzLxAozA=", - "requires": { - "babel-runtime": "^6.22.0", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" - } - }, - "babel-helper-builder-binary-assignment-operator-visitor": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-builder-binary-assignment-operator-visitor/-/babel-helper-builder-binary-assignment-operator-visitor-6.24.1.tgz", - "integrity": "sha1-zORReto1b0IgvK6KAsKzRvmlZmQ=", + "bcrypt-pbkdf": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.2.tgz", + "integrity": "sha1-pDAdOJtqQ/m2f/PKEaP2Y342Dp4=", + "dev": true, "requires": { - "babel-helper-explode-assignable-expression": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" + "tweetnacl": "^0.14.3" } }, - "babel-helper-call-delegate": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-call-delegate/-/babel-helper-call-delegate-6.24.1.tgz", - "integrity": "sha1-7Oaqzdx25Bw0YfiL/Fdb0Nqi340=", - "requires": { - "babel-helper-hoist-variables": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" - } + "bignumber.js": { + "version": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", + "from": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", + "dev": true }, - "babel-helper-define-map": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-helper-define-map/-/babel-helper-define-map-6.26.0.tgz", - "integrity": "sha1-pfVtq0GiX5fstJjH66ypgZ+Vvl8=", - "requires": { - "babel-helper-function-name": "^6.24.1", - "babel-runtime": "^6.26.0", - "babel-types": "^6.26.0", - "lodash": "^4.17.4" - } + "binary-extensions": { + "version": "1.13.0", + "resolved": "https://registry.npmjs.org/binary-extensions/-/binary-extensions-1.13.0.tgz", + "integrity": "sha512-EgmjVLMn22z7eGGv3kcnHwSnJXmFHjISTY9E/S5lIcTD3Oxw05QTcBLNkJFzcb3cNueUdF/IN4U+d78V0zO8Hw==", + "dev": true }, - "babel-helper-explode-assignable-expression": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-explode-assignable-expression/-/babel-helper-explode-assignable-expression-6.24.1.tgz", - "integrity": "sha1-8luCz33BBDPFX3BZLVdGQArCLKo=", - "requires": { - "babel-runtime": "^6.22.0", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" - } + "bn.js": { + "version": "4.11.8", + "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.11.8.tgz", + "integrity": "sha512-ItfYfPLkWHUjckQCk8xC+LwxgK8NYcXywGigJgSwOP8Y2iyWT4f2vsZnoOXTTbo+o5yXmIUJ4gn5538SO5S3gA==" }, - "babel-helper-explode-class": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-explode-class/-/babel-helper-explode-class-6.24.1.tgz", - "integrity": "sha1-fcKjkQ3uAHBW4eMdZAztPVTqqes=", + "boxen": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/boxen/-/boxen-1.3.0.tgz", + "integrity": "sha512-TNPjfTr432qx7yOjQyaXm3dSR0MH9vXp7eT1BFSl/C51g+EFnOR9hTg1IreahGBmDNCehscshe45f+C1TBZbLw==", + "dev": true, "requires": { - "babel-helper-bindify-decorators": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" + "ansi-align": "^2.0.0", + "camelcase": "^4.0.0", + "chalk": "^2.0.1", + "cli-boxes": "^1.0.0", + "string-width": "^2.0.0", + "term-size": "^1.2.0", + "widest-line": "^2.0.0" + }, + "dependencies": { + "ansi-regex": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", + "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=", + "dev": true + }, + "camelcase": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-4.1.0.tgz", + "integrity": "sha1-1UVjW+HjPFQmScaRc+Xeas+uNN0=", + "dev": true + }, + "is-fullwidth-code-point": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", + "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=", + "dev": true + }, + "string-width": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", + "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", + "dev": true, + "requires": { + "is-fullwidth-code-point": "^2.0.0", + "strip-ansi": "^4.0.0" + } + }, + "strip-ansi": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", + "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", + "dev": true, + "requires": { + "ansi-regex": "^3.0.0" + } + } } }, - "babel-helper-function-name": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-function-name/-/babel-helper-function-name-6.24.1.tgz", - "integrity": "sha1-00dbjAPtmCQqJbSDUasYOZ01gKk=", + "brace-expansion": { + "version": "1.1.11", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", + "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", "requires": { - "babel-helper-get-function-arity": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" + "balanced-match": "^1.0.0", + "concat-map": "0.0.1" } }, - "babel-helper-get-function-arity": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-get-function-arity/-/babel-helper-get-function-arity-6.24.1.tgz", - "integrity": "sha1-j3eCqpNAfEHTqlCQj4mwMbG2hT0=", + "braces": { + "version": "2.3.2", + "resolved": "https://registry.npmjs.org/braces/-/braces-2.3.2.tgz", + "integrity": "sha512-aNdbnj9P8PjdXU4ybaWLK2IF3jc/EoDYbC7AazW6to3TRsfXxscC9UXOB5iDiEQrkyIbWp2SLQda4+QAa7nc3w==", + "dev": true, "requires": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } - }, - "babel-helper-hoist-variables": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-hoist-variables/-/babel-helper-hoist-variables-6.24.1.tgz", - "integrity": "sha1-HssnaJydJVE+rbyZFKc/VAi+enY=", - "requires": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } - }, - "babel-helper-optimise-call-expression": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-optimise-call-expression/-/babel-helper-optimise-call-expression-6.24.1.tgz", - "integrity": "sha1-96E0J7qfc/j0+pk8VKl4gtEkQlc=", - "requires": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" + "arr-flatten": "^1.1.0", + "array-unique": "^0.3.2", + "extend-shallow": "^2.0.1", + "fill-range": "^4.0.0", + "isobject": "^3.0.1", + "repeat-element": "^1.1.2", + "snapdragon": "^0.8.1", + "snapdragon-node": "^2.0.1", + "split-string": "^3.0.2", + "to-regex": "^3.0.1" + }, + "dependencies": { + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "dev": true, + "requires": { + "is-extendable": "^0.1.0" + } + } } }, - "babel-helper-regex": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-helper-regex/-/babel-helper-regex-6.26.0.tgz", - "integrity": "sha1-MlxZ+QL4LyS3T6zu0DY5VPZJXnI=", - "requires": { - "babel-runtime": "^6.26.0", - "babel-types": "^6.26.0", - "lodash": "^4.17.4" - } + "brorand": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/brorand/-/brorand-1.1.0.tgz", + "integrity": "sha1-EsJe/kCkXjwyPrhnWgoM5XsiNx8=" }, - "babel-helper-remap-async-to-generator": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-remap-async-to-generator/-/babel-helper-remap-async-to-generator-6.24.1.tgz", - "integrity": "sha1-XsWBgnrXI/7N04HxySg5BnbkVRs=", - "requires": { - "babel-helper-function-name": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" - } + "browser-stdout": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/browser-stdout/-/browser-stdout-1.3.0.tgz", + "integrity": "sha1-81HTKWnTL6XXpVZxVCY9korjvR8=" }, - "babel-helper-replace-supers": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-replace-supers/-/babel-helper-replace-supers-6.24.1.tgz", - "integrity": "sha1-v22/5Dk40XNpohPKiov3S2qQqxo=", + "browserify-sha3": { + "version": "0.0.4", + "resolved": "https://registry.npmjs.org/browserify-sha3/-/browserify-sha3-0.0.4.tgz", + "integrity": "sha1-CGxHuMgjFsnUcCLCYYWVRXbdjiY=", + "dev": true, "requires": { - "babel-helper-optimise-call-expression": "^6.24.1", - "babel-messages": "^6.23.0", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" + "js-sha3": "^0.6.1", + "safe-buffer": "^5.1.1" } }, - "babel-helpers": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helpers/-/babel-helpers-6.24.1.tgz", - "integrity": "sha1-NHHenK7DiOXIUOWX5Yom3fN2ArI=", - "requires": { - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" - } + "buffer-from": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.1.tgz", + "integrity": "sha512-MQcXEUbCKtEo7bhqEs6560Hyd4XaovZlO/k9V3hjVUF/zwW7KBVdSK4gIt/bzwS9MbR5qob+F5jusZsb0YQK2A==", + "dev": true }, - "babel-messages": { - "version": "6.23.0", - "resolved": "https://registry.npmjs.org/babel-messages/-/babel-messages-6.23.0.tgz", - "integrity": "sha1-8830cDhYA1sqKVHG7F7fbGLyYw4=", - "requires": { - "babel-runtime": "^6.22.0" - } + "buffer-to-arraybuffer": { + "version": "0.0.5", + "resolved": "https://registry.npmjs.org/buffer-to-arraybuffer/-/buffer-to-arraybuffer-0.0.5.tgz", + "integrity": "sha1-YGSkD6dutDxyOrqe+PbhIW0QURo=" }, - "babel-plugin-check-es2015-constants": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-check-es2015-constants/-/babel-plugin-check-es2015-constants-6.22.0.tgz", - "integrity": "sha1-NRV7EBQm/S/9PaP3XH0ekYNbv4o=", + "cache-base": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/cache-base/-/cache-base-1.0.1.tgz", + "integrity": "sha512-AKcdTnFSWATd5/GCPRxr2ChwIJ85CeyrEyjRHlKxQ56d4XJMGym0uAiKn0xbLOGOl3+yRpOTi484dVCEc5AUzQ==", + "dev": true, "requires": { - "babel-runtime": "^6.22.0" + "collection-visit": "^1.0.0", + "component-emitter": "^1.2.1", + "get-value": "^2.0.6", + "has-value": "^1.0.0", + "isobject": "^3.0.1", + "set-value": "^2.0.0", + "to-object-path": "^0.3.0", + "union-value": "^1.0.0", + "unset-value": "^1.0.0" } }, - "babel-plugin-syntax-async-functions": { - "version": "6.13.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-async-functions/-/babel-plugin-syntax-async-functions-6.13.0.tgz", - "integrity": "sha1-ytnK0RkbWtY0vzCuCHI5HgZHvpU=" - }, - "babel-plugin-syntax-async-generators": { - "version": "6.13.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-async-generators/-/babel-plugin-syntax-async-generators-6.13.0.tgz", - "integrity": "sha1-a8lj67FuzLrmuStZbrfzXDQqi5o=" - }, - "babel-plugin-syntax-class-constructor-call": { - "version": "6.18.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-class-constructor-call/-/babel-plugin-syntax-class-constructor-call-6.18.0.tgz", - "integrity": "sha1-nLnTn+Q8hgC+yBRkVt3L1OGnZBY=" - }, - "babel-plugin-syntax-class-properties": { - "version": "6.13.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-class-properties/-/babel-plugin-syntax-class-properties-6.13.0.tgz", - "integrity": "sha1-1+sjt5oxf4VDlixQW4J8fWysJ94=" - }, - "babel-plugin-syntax-decorators": { - "version": "6.13.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-decorators/-/babel-plugin-syntax-decorators-6.13.0.tgz", - "integrity": "sha1-MSVjtNvePMgGzuPkFszurd0RrAs=" - }, - "babel-plugin-syntax-dynamic-import": { - "version": "6.18.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-dynamic-import/-/babel-plugin-syntax-dynamic-import-6.18.0.tgz", - "integrity": "sha1-jWomIpyDdFqZgqRBBRVyyqF5sdo=" - }, - "babel-plugin-syntax-exponentiation-operator": { - "version": "6.13.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-exponentiation-operator/-/babel-plugin-syntax-exponentiation-operator-6.13.0.tgz", - "integrity": "sha1-nufoM3KQ2pUoggGmpX9BcDF4MN4=" - }, - "babel-plugin-syntax-export-extensions": { - "version": "6.13.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-export-extensions/-/babel-plugin-syntax-export-extensions-6.13.0.tgz", - "integrity": "sha1-cKFITw+QiaToStRLrDU8lbmxJyE=" - }, - "babel-plugin-syntax-flow": { - "version": "6.18.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-flow/-/babel-plugin-syntax-flow-6.18.0.tgz", - "integrity": "sha1-TDqyCiryaqIM0lmVw5jE63AxDI0=" + "camelcase": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-3.0.0.tgz", + "integrity": "sha1-MvxLn82vhF/N9+c7uXysImHwqwo=" }, - "babel-plugin-syntax-object-rest-spread": { - "version": "6.13.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-object-rest-spread/-/babel-plugin-syntax-object-rest-spread-6.13.0.tgz", - "integrity": "sha1-/WU28rzhODb/o6VFjEkDpZe7O/U=" + "capture-stack-trace": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/capture-stack-trace/-/capture-stack-trace-1.0.1.tgz", + "integrity": "sha512-mYQLZnx5Qt1JgB1WEiMCf2647plpGeQ2NMR/5L0HNZzGQo4fuSPnK+wjfPnKZV0aiJDgzmWqqkV/g7JD+DW0qw==", + "dev": true }, - "babel-plugin-syntax-trailing-function-commas": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-trailing-function-commas/-/babel-plugin-syntax-trailing-function-commas-6.22.0.tgz", - "integrity": "sha1-ugNgk3+NBuQBgKQ/4NVhb/9TLPM=" + "caseless": { + "version": "0.12.0", + "resolved": "https://registry.npmjs.org/caseless/-/caseless-0.12.0.tgz", + "integrity": "sha1-G2gcIf+EAzyCZUMJBolCDRhxUdw=", + "dev": true }, - "babel-plugin-transform-async-generator-functions": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-async-generator-functions/-/babel-plugin-transform-async-generator-functions-6.24.1.tgz", - "integrity": "sha1-8FiQAUX9PpkHpt3yjaWfIVJYpds=", + "chai": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/chai/-/chai-4.2.0.tgz", + "integrity": "sha512-XQU3bhBukrOsQCuwZndwGcCVQHyZi53fQ6Ys1Fym7E4olpIqqZZhhoFJoaKVvV17lWQoXYwgWN2nF5crA8J2jw==", + "dev": true, "requires": { - "babel-helper-remap-async-to-generator": "^6.24.1", - "babel-plugin-syntax-async-generators": "^6.5.0", - "babel-runtime": "^6.22.0" + "assertion-error": "^1.1.0", + "check-error": "^1.0.2", + "deep-eql": "^3.0.1", + "get-func-name": "^2.0.0", + "pathval": "^1.1.0", + "type-detect": "^4.0.5" } }, - "babel-plugin-transform-async-to-generator": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-async-to-generator/-/babel-plugin-transform-async-to-generator-6.24.1.tgz", - "integrity": "sha1-ZTbjeK/2yx1VF6wOQOs+n8jQh2E=", + "chai-as-promised": { + "version": "7.1.1", + "resolved": "https://registry.npmjs.org/chai-as-promised/-/chai-as-promised-7.1.1.tgz", + "integrity": "sha512-azL6xMoi+uxu6z4rhWQ1jbdUhOMhis2PvscD/xjLqNMkv3BPPp2JyyuTHOrf9BOosGpNQ11v6BKv/g57RXbiaA==", + "dev": true, "requires": { - "babel-helper-remap-async-to-generator": "^6.24.1", - "babel-plugin-syntax-async-functions": "^6.8.0", - "babel-runtime": "^6.22.0" + "check-error": "^1.0.2" } }, - "babel-plugin-transform-class-constructor-call": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-class-constructor-call/-/babel-plugin-transform-class-constructor-call-6.24.1.tgz", - "integrity": "sha1-gNwoVQWsBn3LjWxl4vbxGrd2Xvk=", - "requires": { - "babel-plugin-syntax-class-constructor-call": "^6.18.0", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" - } + "chai-bignumber": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/chai-bignumber/-/chai-bignumber-2.0.2.tgz", + "integrity": "sha512-BIdRNjRaoRj4bMsZLKbIZPMNKqmwnzNiyxqBYDSs6dFOCs9w8OHPuUE8e1bH60i1IhOzT0NjLtCD+lKEWB1KTQ==", + "dev": true }, - "babel-plugin-transform-class-properties": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-class-properties/-/babel-plugin-transform-class-properties-6.24.1.tgz", - "integrity": "sha1-anl2PqYdM9NvN7YRqp3vgagbRqw=", + "chalk": { + "version": "2.4.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz", + "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==", + "dev": true, "requires": { - "babel-helper-function-name": "^6.24.1", - "babel-plugin-syntax-class-properties": "^6.8.0", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" + "ansi-styles": "^3.2.1", + "escape-string-regexp": "^1.0.5", + "supports-color": "^5.3.0" + }, + "dependencies": { + "has-flag": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", + "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=", + "dev": true + }, + "supports-color": { + "version": "5.5.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", + "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", + "dev": true, + "requires": { + "has-flag": "^3.0.0" + } + } } }, - "babel-plugin-transform-decorators": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-decorators/-/babel-plugin-transform-decorators-6.24.1.tgz", - "integrity": "sha1-eIAT2PjGtSIr33s0Q5Df13Vp4k0=", - "requires": { - "babel-helper-explode-class": "^6.24.1", - "babel-plugin-syntax-decorators": "^6.13.0", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-types": "^6.24.1" - } + "charenc": { + "version": "0.0.2", + "resolved": "https://registry.npmjs.org/charenc/-/charenc-0.0.2.tgz", + "integrity": "sha1-wKHS86cJLgN3S/qD8UwPxXkKhmc=", + "dev": true }, - "babel-plugin-transform-es2015-arrow-functions": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-arrow-functions/-/babel-plugin-transform-es2015-arrow-functions-6.22.0.tgz", - "integrity": "sha1-RSaSy3EdX3ncf4XkQM5BufJE0iE=", - "requires": { - "babel-runtime": "^6.22.0" - } + "check-error": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/check-error/-/check-error-1.0.2.tgz", + "integrity": "sha1-V00xLt2Iu13YkS6Sht1sCu1KrII=", + "dev": true }, - "babel-plugin-transform-es2015-block-scoped-functions": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-block-scoped-functions/-/babel-plugin-transform-es2015-block-scoped-functions-6.22.0.tgz", - "integrity": "sha1-u8UbSflk1wy42OC5ToICRs46YUE=", + "chokidar": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-2.1.1.tgz", + "integrity": "sha512-gfw3p2oQV2wEt+8VuMlNsPjCxDxvvgnm/kz+uATu805mWVF8IJN7uz9DN7iBz+RMJISmiVbCOBFs9qBGMjtPfQ==", + "dev": true, "requires": { - "babel-runtime": "^6.22.0" + "anymatch": "^2.0.0", + "async-each": "^1.0.1", + "braces": "^2.3.2", + "fsevents": "^1.2.7", + "glob-parent": "^3.1.0", + "inherits": "^2.0.3", + "is-binary-path": "^1.0.0", + "is-glob": "^4.0.0", + "normalize-path": "^3.0.0", + "path-is-absolute": "^1.0.0", + "readdirp": "^2.2.1", + "upath": "^1.1.0" } }, - "babel-plugin-transform-es2015-block-scoping": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-block-scoping/-/babel-plugin-transform-es2015-block-scoping-6.26.0.tgz", - "integrity": "sha1-1w9SmcEwjQXBL0Y4E7CgnnOxiV8=", - "requires": { - "babel-runtime": "^6.26.0", - "babel-template": "^6.26.0", - "babel-traverse": "^6.26.0", - "babel-types": "^6.26.0", - "lodash": "^4.17.4" - } + "ci-info": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/ci-info/-/ci-info-1.6.0.tgz", + "integrity": "sha512-vsGdkwSCDpWmP80ncATX7iea5DWQemg1UgCW5J8tqjU3lYw4FBYuj89J0CTVomA7BEfvSZd84GmHko+MxFQU2A==", + "dev": true }, - "babel-plugin-transform-es2015-classes": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-classes/-/babel-plugin-transform-es2015-classes-6.24.1.tgz", - "integrity": "sha1-WkxYpQyclGHlZLSyo7+ryXolhNs=", + "class-utils": { + "version": "0.3.6", + "resolved": "https://registry.npmjs.org/class-utils/-/class-utils-0.3.6.tgz", + "integrity": "sha512-qOhPa/Fj7s6TY8H8esGu5QNpMMQxz79h+urzrNYN6mn+9BnxlDGf5QZ+XeCDsxSjPqsSR56XOZOJmpeurnLMeg==", + "dev": true, "requires": { - "babel-helper-define-map": "^6.24.1", - "babel-helper-function-name": "^6.24.1", - "babel-helper-optimise-call-expression": "^6.24.1", - "babel-helper-replace-supers": "^6.24.1", - "babel-messages": "^6.23.0", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" + "arr-union": "^3.1.0", + "define-property": "^0.2.5", + "isobject": "^3.0.0", + "static-extend": "^0.1.1" + }, + "dependencies": { + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "dev": true, + "requires": { + "is-descriptor": "^0.1.0" + } + } } }, - "babel-plugin-transform-es2015-computed-properties": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-computed-properties/-/babel-plugin-transform-es2015-computed-properties-6.24.1.tgz", - "integrity": "sha1-b+Ko0WiV1WNPTNmZttNICjCBWbM=", - "requires": { - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" - } + "cli-boxes": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/cli-boxes/-/cli-boxes-1.0.0.tgz", + "integrity": "sha1-T6kXw+WclKAEzWH47lCdplFocUM=", + "dev": true }, - "babel-plugin-transform-es2015-destructuring": { - "version": "6.23.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-destructuring/-/babel-plugin-transform-es2015-destructuring-6.23.0.tgz", - "integrity": "sha1-mXux8auWf2gtKwh2/jWNYOdlxW0=", + "cli-table3": { + "version": "0.5.1", + "resolved": "https://registry.npmjs.org/cli-table3/-/cli-table3-0.5.1.tgz", + "integrity": "sha512-7Qg2Jrep1S/+Q3EceiZtQcDPWxhAvBw+ERf1162v4sikJrvojMHFqXt8QIVha8UlH9rgU0BeWPytZ9/TzYqlUw==", + "dev": true, "requires": { - "babel-runtime": "^6.22.0" + "colors": "^1.1.2", + "object-assign": "^4.1.0", + "string-width": "^2.1.1" + }, + "dependencies": { + "ansi-regex": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", + "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=", + "dev": true + }, + "is-fullwidth-code-point": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", + "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=", + "dev": true + }, + "string-width": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", + "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", + "dev": true, + "requires": { + "is-fullwidth-code-point": "^2.0.0", + "strip-ansi": "^4.0.0" + } + }, + "strip-ansi": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", + "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", + "dev": true, + "requires": { + "ansi-regex": "^3.0.0" + } + } } }, - "babel-plugin-transform-es2015-duplicate-keys": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-duplicate-keys/-/babel-plugin-transform-es2015-duplicate-keys-6.24.1.tgz", - "integrity": "sha1-c+s9MQypaePvnskcU3QabxV2Qj4=", + "cliui": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/cliui/-/cliui-3.2.0.tgz", + "integrity": "sha1-EgYBU3qRbSmUD5NNo7SNWFo5IT0=", "requires": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" + "string-width": "^1.0.1", + "strip-ansi": "^3.0.1", + "wrap-ansi": "^2.0.0" } }, - "babel-plugin-transform-es2015-for-of": { - "version": "6.23.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-for-of/-/babel-plugin-transform-es2015-for-of-6.23.0.tgz", - "integrity": "sha1-9HyVsrYT3x0+zC/bdXNiPHUkhpE=", - "requires": { - "babel-runtime": "^6.22.0" - } + "code-point-at": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/code-point-at/-/code-point-at-1.1.0.tgz", + "integrity": "sha1-DQcLTQQ6W+ozovGkDi7bPZpMz3c=" }, - "babel-plugin-transform-es2015-function-name": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-function-name/-/babel-plugin-transform-es2015-function-name-6.24.1.tgz", - "integrity": "sha1-g0yJhTvDaxrw86TF26qU/Y6sqos=", + "collection-visit": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/collection-visit/-/collection-visit-1.0.0.tgz", + "integrity": "sha1-S8A3PBZLwykbTTaMgpzxqApZ3KA=", + "dev": true, "requires": { - "babel-helper-function-name": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" + "map-visit": "^1.0.0", + "object-visit": "^1.0.0" } }, - "babel-plugin-transform-es2015-literals": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-literals/-/babel-plugin-transform-es2015-literals-6.22.0.tgz", - "integrity": "sha1-T1SgLWzWbPkVKAAZox0xklN3yi4=", + "color-convert": { + "version": "1.9.3", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.3.tgz", + "integrity": "sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==", + "dev": true, "requires": { - "babel-runtime": "^6.22.0" + "color-name": "1.1.3" } }, - "babel-plugin-transform-es2015-modules-amd": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-modules-amd/-/babel-plugin-transform-es2015-modules-amd-6.24.1.tgz", - "integrity": "sha1-Oz5UAXI5hC1tGcMBHEvS8AoA0VQ=", - "requires": { - "babel-plugin-transform-es2015-modules-commonjs": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" - } + "color-name": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz", + "integrity": "sha1-p9BVi9icQveV3UIyj3QIMcpTvCU=", + "dev": true }, - "babel-plugin-transform-es2015-modules-commonjs": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-modules-commonjs/-/babel-plugin-transform-es2015-modules-commonjs-6.26.0.tgz", - "integrity": "sha1-DYOUApt9xqvhqX7xgeAHWN0uXYo=", - "requires": { - "babel-plugin-transform-strict-mode": "^6.24.1", - "babel-runtime": "^6.26.0", - "babel-template": "^6.26.0", - "babel-types": "^6.26.0" - } + "colors": { + "version": "1.3.3", + "resolved": "https://registry.npmjs.org/colors/-/colors-1.3.3.tgz", + "integrity": "sha512-mmGt/1pZqYRjMxB1axhTo16/snVZ5krrKkcmMeVKxzECMMXoCgnvTPp10QgHfcbQZw8Dq2jMNG6je4JlWU0gWg==", + "dev": true }, - "babel-plugin-transform-es2015-modules-systemjs": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-modules-systemjs/-/babel-plugin-transform-es2015-modules-systemjs-6.24.1.tgz", - "integrity": "sha1-/4mhQrkRmpBhlfXxBuzzBdlAfSM=", - "requires": { - "babel-helper-hoist-variables": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" - } - }, - "babel-plugin-transform-es2015-modules-umd": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-modules-umd/-/babel-plugin-transform-es2015-modules-umd-6.24.1.tgz", - "integrity": "sha1-rJl+YoXNGO1hdq22B9YCNErThGg=", - "requires": { - "babel-plugin-transform-es2015-modules-amd": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" - } - }, - "babel-plugin-transform-es2015-object-super": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-object-super/-/babel-plugin-transform-es2015-object-super-6.24.1.tgz", - "integrity": "sha1-JM72muIcuDp/hgPa0CH1cusnj40=", - "requires": { - "babel-helper-replace-supers": "^6.24.1", - "babel-runtime": "^6.22.0" - } - }, - "babel-plugin-transform-es2015-parameters": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-parameters/-/babel-plugin-transform-es2015-parameters-6.24.1.tgz", - "integrity": "sha1-V6w1GrScrxSpfNE7CfZv3wpiXys=", + "combined-stream": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.7.tgz", + "integrity": "sha512-brWl9y6vOB1xYPZcpZde3N9zDByXTosAeMDo4p1wzo6UMOX4vumB+TP1RZ76sfE6Md68Q0NJSrE/gbezd4Ul+w==", + "dev": true, "requires": { - "babel-helper-call-delegate": "^6.24.1", - "babel-helper-get-function-arity": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" + "delayed-stream": "~1.0.0" } }, - "babel-plugin-transform-es2015-shorthand-properties": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-shorthand-properties/-/babel-plugin-transform-es2015-shorthand-properties-6.24.1.tgz", - "integrity": "sha1-JPh11nIch2YbvZmkYi5R8U3jiqA=", - "requires": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } + "commander": { + "version": "2.11.0", + "resolved": "https://registry.npmjs.org/commander/-/commander-2.11.0.tgz", + "integrity": "sha512-b0553uYA5YAEGgyYIGYROzKQ7X5RAqedkfjiZxwi0kL1g3bOaBNNZfYkzt/CL0umgD5wc9Jec2FbB98CjkMRvQ==" }, - "babel-plugin-transform-es2015-spread": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-spread/-/babel-plugin-transform-es2015-spread-6.22.0.tgz", - "integrity": "sha1-1taKmfia7cRTbIGlQujdnxdG+NE=", - "requires": { - "babel-runtime": "^6.22.0" - } + "component-emitter": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/component-emitter/-/component-emitter-1.2.1.tgz", + "integrity": "sha1-E3kY1teCg/ffemt8WmPhQOaUJeY=", + "dev": true }, - "babel-plugin-transform-es2015-sticky-regex": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-sticky-regex/-/babel-plugin-transform-es2015-sticky-regex-6.24.1.tgz", - "integrity": "sha1-AMHNsaynERLN8M9hJsLta0V8zbw=", - "requires": { - "babel-helper-regex": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } + "concat-map": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", + "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=" }, - "babel-plugin-transform-es2015-template-literals": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-template-literals/-/babel-plugin-transform-es2015-template-literals-6.22.0.tgz", - "integrity": "sha1-qEs0UPfp+PH2g51taH2oS7EjbY0=", + "concat-stream": { + "version": "1.6.2", + "resolved": "https://registry.npmjs.org/concat-stream/-/concat-stream-1.6.2.tgz", + "integrity": "sha512-27HBghJxjiZtIk3Ycvn/4kbJk/1uZuJFfuPEns6LaEvpvG1f0hTea8lilrouyo9mVc2GWdcEZ8OLoGmSADlrCw==", + "dev": true, "requires": { - "babel-runtime": "^6.22.0" + "buffer-from": "^1.0.0", + "inherits": "^2.0.3", + "readable-stream": "^2.2.2", + "typedarray": "^0.0.6" } }, - "babel-plugin-transform-es2015-typeof-symbol": { - "version": "6.23.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-typeof-symbol/-/babel-plugin-transform-es2015-typeof-symbol-6.23.0.tgz", - "integrity": "sha1-3sCfHN3/lLUqxz1QXITfWdzOs3I=", + "configstore": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/configstore/-/configstore-3.1.2.tgz", + "integrity": "sha512-vtv5HtGjcYUgFrXc6Kx747B83MRRVS5R1VTEQoXvuP+kMI+if6uywV0nDGoiydJRy4yk7h9od5Og0kxx4zUXmw==", + "dev": true, "requires": { - "babel-runtime": "^6.22.0" + "dot-prop": "^4.1.0", + "graceful-fs": "^4.1.2", + "make-dir": "^1.0.0", + "unique-string": "^1.0.0", + "write-file-atomic": "^2.0.0", + "xdg-basedir": "^3.0.0" } }, - "babel-plugin-transform-es2015-unicode-regex": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-unicode-regex/-/babel-plugin-transform-es2015-unicode-regex-6.24.1.tgz", - "integrity": "sha1-04sS9C6nMj9yk4fxinxa4frrNek=", - "requires": { - "babel-helper-regex": "^6.24.1", - "babel-runtime": "^6.22.0", - "regexpu-core": "^2.0.0" - } + "copy-descriptor": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/copy-descriptor/-/copy-descriptor-0.1.1.tgz", + "integrity": "sha1-Z29us8OZl8LuGsOpJP1hJHSPV40=", + "dev": true }, - "babel-plugin-transform-exponentiation-operator": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-exponentiation-operator/-/babel-plugin-transform-exponentiation-operator-6.24.1.tgz", - "integrity": "sha1-KrDJx/MJj6SJB3cruBP+QejeOg4=", - "requires": { - "babel-helper-builder-binary-assignment-operator-visitor": "^6.24.1", - "babel-plugin-syntax-exponentiation-operator": "^6.8.0", - "babel-runtime": "^6.22.0" - } + "core-util-is": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz", + "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=", + "dev": true }, - "babel-plugin-transform-export-extensions": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-export-extensions/-/babel-plugin-transform-export-extensions-6.22.0.tgz", - "integrity": "sha1-U3OLR+deghhYnuqUbLvTkQm75lM=", + "create-error-class": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/create-error-class/-/create-error-class-3.0.2.tgz", + "integrity": "sha1-Br56vvlHo/FKMP1hBnHUAbyot7Y=", + "dev": true, "requires": { - "babel-plugin-syntax-export-extensions": "^6.8.0", - "babel-runtime": "^6.22.0" + "capture-stack-trace": "^1.0.0" } }, - "babel-plugin-transform-flow-strip-types": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-flow-strip-types/-/babel-plugin-transform-flow-strip-types-6.22.0.tgz", - "integrity": "sha1-hMtnKTXUNxT9wyvOhFaNh0Qc988=", + "cross-spawn": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-5.1.0.tgz", + "integrity": "sha1-6L0O/uWPz/b4+UUQoKVUu/ojVEk=", + "dev": true, "requires": { - "babel-plugin-syntax-flow": "^6.18.0", - "babel-runtime": "^6.22.0" + "lru-cache": "^4.0.1", + "shebang-command": "^1.2.0", + "which": "^1.2.9" } }, - "babel-plugin-transform-object-rest-spread": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-object-rest-spread/-/babel-plugin-transform-object-rest-spread-6.26.0.tgz", - "integrity": "sha1-DzZpLVD+9rfi1LOsFHgTepY7ewY=", - "requires": { - "babel-plugin-syntax-object-rest-spread": "^6.8.0", - "babel-runtime": "^6.26.0" - } + "crypt": { + "version": "0.0.2", + "resolved": "https://registry.npmjs.org/crypt/-/crypt-0.0.2.tgz", + "integrity": "sha1-iNf/fsDfuG9xPch7u0LQRNPmxBs=", + "dev": true }, - "babel-plugin-transform-regenerator": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-regenerator/-/babel-plugin-transform-regenerator-6.26.0.tgz", - "integrity": "sha1-4HA2lvveJ/Cj78rPi03KL3s6jy8=", - "requires": { - "regenerator-transform": "^0.10.0" - } + "crypto-js": { + "version": "3.1.8", + "resolved": "https://registry.npmjs.org/crypto-js/-/crypto-js-3.1.8.tgz", + "integrity": "sha1-cV8HC/YBTyrpkqmLOSkli3E/CNU=", + "dev": true }, - "babel-plugin-transform-strict-mode": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-strict-mode/-/babel-plugin-transform-strict-mode-6.24.1.tgz", - "integrity": "sha1-1fr3qleKZbvlkc9e2uBKDGcCB1g=", - "requires": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } + "crypto-random-string": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/crypto-random-string/-/crypto-random-string-1.0.0.tgz", + "integrity": "sha1-ojD2T1aDEOFJgAmUB5DsmVRbyn4=", + "dev": true }, - "babel-preset-es2015": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-preset-es2015/-/babel-preset-es2015-6.24.1.tgz", - "integrity": "sha1-1EBQ1rwsn+6nAqrzjXJ6AhBTiTk=", + "dashdash": { + "version": "1.14.1", + "resolved": "https://registry.npmjs.org/dashdash/-/dashdash-1.14.1.tgz", + "integrity": "sha1-hTz6D3y+L+1d4gMmuN1YEDX24vA=", + "dev": true, "requires": { - "babel-plugin-check-es2015-constants": "^6.22.0", - "babel-plugin-transform-es2015-arrow-functions": "^6.22.0", - "babel-plugin-transform-es2015-block-scoped-functions": "^6.22.0", - "babel-plugin-transform-es2015-block-scoping": "^6.24.1", - "babel-plugin-transform-es2015-classes": "^6.24.1", - "babel-plugin-transform-es2015-computed-properties": "^6.24.1", - "babel-plugin-transform-es2015-destructuring": "^6.22.0", - "babel-plugin-transform-es2015-duplicate-keys": "^6.24.1", - "babel-plugin-transform-es2015-for-of": "^6.22.0", - "babel-plugin-transform-es2015-function-name": "^6.24.1", - "babel-plugin-transform-es2015-literals": "^6.22.0", - "babel-plugin-transform-es2015-modules-amd": "^6.24.1", - "babel-plugin-transform-es2015-modules-commonjs": "^6.24.1", - "babel-plugin-transform-es2015-modules-systemjs": "^6.24.1", - "babel-plugin-transform-es2015-modules-umd": "^6.24.1", - "babel-plugin-transform-es2015-object-super": "^6.24.1", - "babel-plugin-transform-es2015-parameters": "^6.24.1", - "babel-plugin-transform-es2015-shorthand-properties": "^6.24.1", - "babel-plugin-transform-es2015-spread": "^6.22.0", - "babel-plugin-transform-es2015-sticky-regex": "^6.24.1", - "babel-plugin-transform-es2015-template-literals": "^6.22.0", - "babel-plugin-transform-es2015-typeof-symbol": "^6.22.0", - "babel-plugin-transform-es2015-unicode-regex": "^6.24.1", - "babel-plugin-transform-regenerator": "^6.24.1" + "assert-plus": "^1.0.0" } }, - "babel-preset-stage-1": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-preset-stage-1/-/babel-preset-stage-1-6.24.1.tgz", - "integrity": "sha1-dpLNfc1oSZB+auSgqFWJz7niv7A=", - "requires": { - "babel-plugin-transform-class-constructor-call": "^6.24.1", - "babel-plugin-transform-export-extensions": "^6.22.0", - "babel-preset-stage-2": "^6.24.1" - } + "death": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/death/-/death-1.1.0.tgz", + "integrity": "sha1-AaqcQB7dknUFFEcLgmY5DGbGcxg=", + "dev": true }, - "babel-preset-stage-2": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-preset-stage-2/-/babel-preset-stage-2-6.24.1.tgz", - "integrity": "sha1-2eKWD7PXEYfw5k7sYrwHdnIZvcE=", + "debug": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", + "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", "requires": { - "babel-plugin-syntax-dynamic-import": "^6.18.0", - "babel-plugin-transform-class-properties": "^6.24.1", - "babel-plugin-transform-decorators": "^6.24.1", - "babel-preset-stage-3": "^6.24.1" - } - }, - "babel-preset-stage-3": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-preset-stage-3/-/babel-preset-stage-3-6.24.1.tgz", - "integrity": "sha1-g2raCp56f6N8sTj7kyb4eTSkg5U=", - "requires": { - "babel-plugin-syntax-trailing-function-commas": "^6.22.0", - "babel-plugin-transform-async-generator-functions": "^6.24.1", - "babel-plugin-transform-async-to-generator": "^6.24.1", - "babel-plugin-transform-exponentiation-operator": "^6.24.1", - "babel-plugin-transform-object-rest-spread": "^6.22.0" + "ms": "2.0.0" } }, - "babel-register": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-register/-/babel-register-6.26.0.tgz", - "integrity": "sha1-btAhFz4vy0htestFxgCahW9kcHE=", - "requires": { - "babel-core": "^6.26.0", - "babel-runtime": "^6.26.0", - "core-js": "^2.5.0", - "home-or-tmp": "^2.0.0", - "lodash": "^4.17.4", - "mkdirp": "^0.5.1", - "source-map-support": "^0.4.15" - }, - "dependencies": { - "source-map-support": { - "version": "0.4.18", - "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.4.18.tgz", - "integrity": "sha512-try0/JqxPLF9nOjvSta7tVondkP5dwgyLDjVoyMDlmjugT2lRZ1OfsrYTkCd2hkDnJTKRbO/Rl3orm8vlsUzbA==", - "requires": { - "source-map": "^0.5.6" - } - } - } + "decamelize": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/decamelize/-/decamelize-1.2.0.tgz", + "integrity": "sha1-9lNNFRSCabIDUue+4m9QH5oZEpA=" }, - "babel-runtime": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-runtime/-/babel-runtime-6.26.0.tgz", - "integrity": "sha1-llxwWGaOgrVde/4E/yM3vItWR/4=", - "requires": { - "core-js": "^2.4.0", - "regenerator-runtime": "^0.11.0" - } + "decode-uri-component": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/decode-uri-component/-/decode-uri-component-0.2.0.tgz", + "integrity": "sha1-6zkTMzRYd1y4TNGh+uBiEGu4dUU=" }, - "babel-template": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-template/-/babel-template-6.26.0.tgz", - "integrity": "sha1-3gPi0WOWsGn0bdn/+FIfsaDjXgI=", + "decompress-response": { + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/decompress-response/-/decompress-response-3.3.0.tgz", + "integrity": "sha1-gKTdMjdIOEv6JICDYirt7Jgq3/M=", "requires": { - "babel-runtime": "^6.26.0", - "babel-traverse": "^6.26.0", - "babel-types": "^6.26.0", - "babylon": "^6.18.0", - "lodash": "^4.17.4" - }, - "dependencies": { - "babylon": { - "version": "6.18.0", - "resolved": "https://registry.npmjs.org/babylon/-/babylon-6.18.0.tgz", - "integrity": "sha512-q/UEjfGJ2Cm3oKV71DJz9d25TPnq5rhBVL2Q4fA5wcC3jcrdn7+SssEybFIxwAvvP+YCsCYNKughoF33GxgycQ==" - } - } - }, - "babel-traverse": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-traverse/-/babel-traverse-6.26.0.tgz", - "integrity": "sha1-RqnL1+3MYsjlwGTi0tjQ9ANXZu4=", - "requires": { - "babel-code-frame": "^6.26.0", - "babel-messages": "^6.23.0", - "babel-runtime": "^6.26.0", - "babel-types": "^6.26.0", - "babylon": "^6.18.0", - "debug": "^2.6.8", - "globals": "^9.18.0", - "invariant": "^2.2.2", - "lodash": "^4.17.4" - }, - "dependencies": { - "babylon": { - "version": "6.18.0", - "resolved": "https://registry.npmjs.org/babylon/-/babylon-6.18.0.tgz", - "integrity": "sha512-q/UEjfGJ2Cm3oKV71DJz9d25TPnq5rhBVL2Q4fA5wcC3jcrdn7+SssEybFIxwAvvP+YCsCYNKughoF33GxgycQ==" - } + "mimic-response": "^1.0.0" } }, - "babel-types": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-types/-/babel-types-6.26.0.tgz", - "integrity": "sha1-o7Bz+Uq0nrb6Vc1lInozQ4BjJJc=", + "deep-eql": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/deep-eql/-/deep-eql-3.0.1.tgz", + "integrity": "sha512-+QeIQyN5ZuO+3Uk5DYh6/1eKO0m0YmJFGNmFHGACpf1ClL1nmlV/p4gNgbl2pJGxgXb4faqo6UE+M5ACEMyVcw==", + "dev": true, "requires": { - "babel-runtime": "^6.26.0", - "esutils": "^2.0.2", - "lodash": "^4.17.4", - "to-fast-properties": "^1.0.3" + "type-detect": "^4.0.0" } }, - "babylon": { - "version": "7.0.0-beta.42", - "resolved": "https://registry.npmjs.org/babylon/-/babylon-7.0.0-beta.42.tgz", - "integrity": "sha512-h6E/OkkvcBw/JimbL0p8dIaxrcuQn3QmIYGC/GtJlRYif5LTKBYPHXYwqluJpfS/kOXoz0go+9mkmOVC0M+zWw==" + "deep-extend": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/deep-extend/-/deep-extend-0.6.0.tgz", + "integrity": "sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA==", + "dev": true }, - "balanced-match": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz", - "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=" + "deep-is": { + "version": "0.1.3", + "resolved": "https://registry.npmjs.org/deep-is/-/deep-is-0.1.3.tgz", + "integrity": "sha1-s2nW+128E+7PUk+RsHD+7cNXzzQ=", + "dev": true }, - "base": { - "version": "0.11.2", - "resolved": "https://registry.npmjs.org/base/-/base-0.11.2.tgz", - "integrity": "sha512-5T6P4xPgpp0YDFvSWwEZ4NoE3aM4QBQXDzmVbraCkFj8zHM+mba8SyqB5DbZWyR7mYHo6Y7BdQo3MoA4m0TeQg==", + "define-property": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-2.0.2.tgz", + "integrity": "sha512-jwK2UV4cnPpbcG7+VRARKTZPUWowwXA8bzH5NP6ud0oeAxyYPuGZUAC7hMugpCdz4BeSZl2Dl9k66CHJ/46ZYQ==", "dev": true, "requires": { - "cache-base": "^1.0.1", - "class-utils": "^0.3.5", - "component-emitter": "^1.2.1", - "define-property": "^1.0.0", - "isobject": "^3.0.1", - "mixin-deep": "^1.2.0", - "pascalcase": "^0.1.1" + "is-descriptor": "^1.0.2", + "isobject": "^3.0.1" }, "dependencies": { - "define-property": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/define-property/-/define-property-1.0.0.tgz", - "integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=", - "dev": true, - "requires": { - "is-descriptor": "^1.0.0" - } - }, "is-accessor-descriptor": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz", @@ -1170,381 +964,211 @@ } } }, - "bcrypt-pbkdf": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.1.tgz", - "integrity": "sha1-Y7xdy2EzG5K8Bf1SiVPDNGKgb40=", - "optional": true, - "requires": { - "tweetnacl": "^0.14.3" - } - }, - "big.js": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/big.js/-/big.js-3.2.0.tgz", - "integrity": "sha512-+hN/Zh2D08Mx65pZ/4g5bsmNiZUuChDiQfTUQ7qJr4/kuopCr88xZsAXv6mBoZEsUI4OuGHlX59qE94K2mMW8Q==" - }, - "bignumber.js": { - "version": "git+https://github.com/frozeman/bignumber.js-nolookahead.git#57692b3ecfc98bbdd6b3a516cb2353652ea49934", - "from": "bignumber.js@git+https://github.com/frozeman/bignumber.js-nolookahead.git#57692b3ecfc98bbdd6b3a516cb2353652ea49934", + "delayed-stream": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", + "integrity": "sha1-3zrhmayt+31ECqrgsp4icrJOxhk=", "dev": true }, - "binary-extensions": { - "version": "1.11.0", - "resolved": "https://registry.npmjs.org/binary-extensions/-/binary-extensions-1.11.0.tgz", - "integrity": "sha1-RqoXUftqL5PuXmibsQh9SxTGwgU=", - "dev": true + "diff": { + "version": "3.3.1", + "resolved": "https://registry.npmjs.org/diff/-/diff-3.3.1.tgz", + "integrity": "sha512-MKPHZDMB0o6yHyDryUOScqZibp914ksXwAMYMTHj6KO8UeKsRYNJD3oNCKjTqZon+V488P7N/HzXF8t7ZR95ww==" }, - "binaryextensions": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/binaryextensions/-/binaryextensions-2.1.1.tgz", - "integrity": "sha512-XBaoWE9RW8pPdPQNibZsW2zh8TW6gcarXp1FZPwT8Uop8ScSNldJEWf2k9l3HeTqdrEwsOsFcq74RiJECW34yA==" + "dom-walk": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/dom-walk/-/dom-walk-0.1.1.tgz", + "integrity": "sha1-ZyIm3HTI95mtNTB9+TaroRrNYBg=" }, - "bn.js": { - "version": "4.11.6", - "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.11.6.tgz", - "integrity": "sha1-UzRK2xRhehP26N0s4okF0cC6MhU=" - }, - "body-parser": { - "version": "1.18.2", - "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.18.2.tgz", - "integrity": "sha1-h2eKGdhLR9hZuDGZvVm84iKxBFQ=", - "requires": { - "bytes": "3.0.0", - "content-type": "~1.0.4", - "debug": "2.6.9", - "depd": "~1.1.1", - "http-errors": "~1.6.2", - "iconv-lite": "0.4.19", - "on-finished": "~2.3.0", - "qs": "6.5.1", - "raw-body": "2.3.2", - "type-is": "~1.6.15" - }, - "dependencies": { - "debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "requires": { - "ms": "2.0.0" - } - } + "dot-prop": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/dot-prop/-/dot-prop-4.2.0.tgz", + "integrity": "sha512-tUMXrxlExSW6U2EXiiKGSBVdYgtV8qlHL+C10TsW4PURY/ic+eaysnSkwB4kA/mBlCyy/IKDJ+Lc3wbWeaXtuQ==", + "dev": true, + "requires": { + "is-obj": "^1.0.0" } }, - "boom": { - "version": "4.3.1", - "resolved": "https://registry.npmjs.org/boom/-/boom-4.3.1.tgz", - "integrity": "sha1-T4owBctKfjiJ90kDD9JbluAdLjE=", + "duplexer3": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/duplexer3/-/duplexer3-0.1.4.tgz", + "integrity": "sha1-7gHdHKwO08vH/b6jfcCo8c4ALOI=", + "dev": true + }, + "ecc-jsbn": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/ecc-jsbn/-/ecc-jsbn-0.1.2.tgz", + "integrity": "sha1-OoOpBOVDUyh4dMVkt1SThoSamMk=", + "dev": true, "requires": { - "hoek": "4.x.x" + "jsbn": "~0.1.0", + "safer-buffer": "^2.1.0" } }, - "boxen": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/boxen/-/boxen-1.3.0.tgz", - "integrity": "sha512-TNPjfTr432qx7yOjQyaXm3dSR0MH9vXp7eT1BFSl/C51g+EFnOR9hTg1IreahGBmDNCehscshe45f+C1TBZbLw==", - "dev": true, + "elliptic": { + "version": "6.4.1", + "resolved": "https://registry.npmjs.org/elliptic/-/elliptic-6.4.1.tgz", + "integrity": "sha512-BsXLz5sqX8OHcsh7CqBMztyXARmGQ3LWPtGjJi6DiJHq5C/qvi9P3OqgswKSDftbu8+IoI/QDTAm2fFnQ9SZSQ==", "requires": { - "ansi-align": "^2.0.0", - "camelcase": "^4.0.0", - "chalk": "^2.0.1", - "cli-boxes": "^1.0.0", - "string-width": "^2.0.0", - "term-size": "^1.2.0", - "widest-line": "^2.0.0" - }, - "dependencies": { - "ansi-regex": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", - "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=", - "dev": true - }, - "camelcase": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-4.1.0.tgz", - "integrity": "sha1-1UVjW+HjPFQmScaRc+Xeas+uNN0=", - "dev": true - }, - "is-fullwidth-code-point": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", - "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=", - "dev": true - }, - "string-width": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", - "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", - "dev": true, - "requires": { - "is-fullwidth-code-point": "^2.0.0", - "strip-ansi": "^4.0.0" - } - }, - "strip-ansi": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", - "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", - "dev": true, - "requires": { - "ansi-regex": "^3.0.0" - } - } + "bn.js": "^4.4.0", + "brorand": "^1.0.1", + "hash.js": "^1.0.0", + "hmac-drbg": "^1.0.0", + "inherits": "^2.0.1", + "minimalistic-assert": "^1.0.0", + "minimalistic-crypto-utils": "^1.0.0" } }, - "brace-expansion": { - "version": "1.1.11", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", - "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", + "error-ex": { + "version": "1.3.2", + "resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.2.tgz", + "integrity": "sha512-7dFHNmqeFSEt2ZBsCriorKnn3Z2pj+fd9kmI6QoWw4//DL+icEBfc0U7qJCisqrTsKTjw4fNFy2pW9OqStD84g==", "requires": { - "balanced-match": "^1.0.0", - "concat-map": "0.0.1" + "is-arrayish": "^0.2.1" } }, - "braces": { - "version": "2.3.2", - "resolved": "https://registry.npmjs.org/braces/-/braces-2.3.2.tgz", - "integrity": "sha512-aNdbnj9P8PjdXU4ybaWLK2IF3jc/EoDYbC7AazW6to3TRsfXxscC9UXOB5iDiEQrkyIbWp2SLQda4+QAa7nc3w==", + "escape-string-regexp": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", + "integrity": "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=" + }, + "escodegen": { + "version": "1.8.1", + "resolved": "https://registry.npmjs.org/escodegen/-/escodegen-1.8.1.tgz", + "integrity": "sha1-WltTr0aTEQvrsIZ6o0MN07cKEBg=", "dev": true, "requires": { - "arr-flatten": "^1.1.0", - "array-unique": "^0.3.2", - "extend-shallow": "^2.0.1", - "fill-range": "^4.0.0", - "isobject": "^3.0.1", - "repeat-element": "^1.1.2", - "snapdragon": "^0.8.1", - "snapdragon-node": "^2.0.1", - "split-string": "^3.0.2", - "to-regex": "^3.0.1" + "esprima": "^2.7.1", + "estraverse": "^1.9.1", + "esutils": "^2.0.2", + "optionator": "^0.8.1", + "source-map": "~0.2.0" }, "dependencies": { - "extend-shallow": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", - "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "source-map": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.2.0.tgz", + "integrity": "sha1-2rc/vPwrqBm03gO9b26qSBZLP50=", "dev": true, + "optional": true, "requires": { - "is-extendable": "^0.1.0" + "amdefine": ">=0.0.4" } } } }, - "brorand": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/brorand/-/brorand-1.1.0.tgz", - "integrity": "sha1-EsJe/kCkXjwyPrhnWgoM5XsiNx8=" - }, - "browser-stdout": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/browser-stdout/-/browser-stdout-1.3.0.tgz", - "integrity": "sha1-81HTKWnTL6XXpVZxVCY9korjvR8=" - }, - "browserify-sha3": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/browserify-sha3/-/browserify-sha3-0.0.1.tgz", - "integrity": "sha1-P/NKMAbvFcD7NWflQbkaI0ASPRE=", - "requires": { - "js-sha3": "^0.3.1" - }, - "dependencies": { - "js-sha3": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/js-sha3/-/js-sha3-0.3.1.tgz", - "integrity": "sha1-hhIoAhQvCChQKg0d7h2V4lO7AkM=" - } - } - }, - "buffer-from": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.1.tgz", - "integrity": "sha512-MQcXEUbCKtEo7bhqEs6560Hyd4XaovZlO/k9V3hjVUF/zwW7KBVdSK4gIt/bzwS9MbR5qob+F5jusZsb0YQK2A==", + "esprima": { + "version": "2.7.3", + "resolved": "https://registry.npmjs.org/esprima/-/esprima-2.7.3.tgz", + "integrity": "sha1-luO3DVd59q1JzQMmc9HDEnZ7pYE=", "dev": true }, - "buffer-to-arraybuffer": { - "version": "0.0.5", - "resolved": "https://registry.npmjs.org/buffer-to-arraybuffer/-/buffer-to-arraybuffer-0.0.5.tgz", - "integrity": "sha1-YGSkD6dutDxyOrqe+PbhIW0QURo=" - }, - "builtin-modules": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/builtin-modules/-/builtin-modules-1.1.1.tgz", - "integrity": "sha1-Jw8HbFpywC9bZaR9+Uxf46J4iS8=" + "estraverse": { + "version": "1.9.3", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-1.9.3.tgz", + "integrity": "sha1-r2fy3JIlgkFZUJJgkaQAXSnJu0Q=", + "dev": true }, - "bytes": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.0.0.tgz", - "integrity": "sha1-0ygVQE1olpn4Wk6k+odV3ROpYEg=" + "esutils": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/esutils/-/esutils-2.0.2.tgz", + "integrity": "sha1-Cr9PHKpbyx96nYrMbepPqqBLrJs=", + "dev": true }, - "cache-base": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/cache-base/-/cache-base-1.0.1.tgz", - "integrity": "sha512-AKcdTnFSWATd5/GCPRxr2ChwIJ85CeyrEyjRHlKxQ56d4XJMGym0uAiKn0xbLOGOl3+yRpOTi484dVCEc5AUzQ==", + "eth-gas-reporter": { + "version": "0.1.12", + "resolved": "https://registry.npmjs.org/eth-gas-reporter/-/eth-gas-reporter-0.1.12.tgz", + "integrity": "sha512-Ao5uiXSA5Ep5fi/YvGCsFJMelMKj0fMJkAvWYzPVe1h3Mg9Z7X3Rs51ovG9izFZH7wSqnqydiC6SKDhZWpxK2g==", "dev": true, "requires": { - "collection-visit": "^1.0.0", - "component-emitter": "^1.2.1", - "get-value": "^2.0.6", - "has-value": "^1.0.0", - "isobject": "^3.0.1", - "set-value": "^2.0.0", - "to-object-path": "^0.3.0", - "union-value": "^1.0.0", - "unset-value": "^1.0.0" + "abi-decoder": "^1.0.8", + "cli-table3": "^0.5.0", + "colors": "^1.1.2", + "lodash": "^4.17.4", + "mocha": "^4.1.0", + "req-cwd": "^2.0.0", + "request": "^2.83.0", + "request-promise-native": "^1.0.5", + "sha1": "^1.1.1", + "shelljs": "^0.7.8", + "solidity-parser-antlr": "^0.2.10", + "sync-request": "^6.0.0" } }, - "cacheable-request": { - "version": "2.1.4", - "resolved": "https://registry.npmjs.org/cacheable-request/-/cacheable-request-2.1.4.tgz", - "integrity": "sha1-DYCIAbY0KtM8kd+dC0TcCbkeXD0=", + "eth-lib": { + "version": "0.2.8", + "resolved": "https://registry.npmjs.org/eth-lib/-/eth-lib-0.2.8.tgz", + "integrity": "sha512-ArJ7x1WcWOlSpzdoTBX8vkwlkSQ85CjjifSZtV4co64vWxSV8geWfPI9x4SVYu3DSxnX4yWFVTtGL+j9DUFLNw==", "requires": { - "clone-response": "1.0.2", - "get-stream": "3.0.0", - "http-cache-semantics": "3.8.1", - "keyv": "3.0.0", - "lowercase-keys": "1.0.0", - "normalize-url": "2.0.1", - "responselike": "1.0.2" + "bn.js": "^4.11.6", + "elliptic": "^6.4.0", + "xhr-request-promise": "^0.1.2" } }, - "camelcase": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-3.0.0.tgz", - "integrity": "sha1-MvxLn82vhF/N9+c7uXysImHwqwo=" - }, - "capture-stack-trace": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/capture-stack-trace/-/capture-stack-trace-1.0.0.tgz", - "integrity": "sha1-Sm+gc5nCa7pH8LJJa00PtAjFVQ0=", - "dev": true - }, - "caseless": { - "version": "0.12.0", - "resolved": "https://registry.npmjs.org/caseless/-/caseless-0.12.0.tgz", - "integrity": "sha1-G2gcIf+EAzyCZUMJBolCDRhxUdw=" - }, - "center-align": { - "version": "0.1.3", - "resolved": "https://registry.npmjs.org/center-align/-/center-align-0.1.3.tgz", - "integrity": "sha1-qg0yYptu6XIgBBHL1EYckHvCt60=", + "ethereumjs-testrpc-sc": { + "version": "6.1.6", + "resolved": "https://registry.npmjs.org/ethereumjs-testrpc-sc/-/ethereumjs-testrpc-sc-6.1.6.tgz", + "integrity": "sha512-iv2qiGBFgk9mn5Nq2enX8dG5WQ7Lk+FCqpnxfPfH4Ns8KLPwttmNOy264nh3SXDJJvcQwz/XnlLteDQVILotbg==", "dev": true, - "optional": true, "requires": { - "align-text": "^0.1.3", - "lazy-cache": "^1.0.3" + "source-map-support": "^0.5.3" } }, - "chai": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chai/-/chai-4.1.2.tgz", - "integrity": "sha1-D2RYS6ZC8PKs4oBiefTwbKI61zw=", - "dev": true, + "ethjs-unit": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/ethjs-unit/-/ethjs-unit-0.1.6.tgz", + "integrity": "sha1-xmWSHkduh7ziqdWIpv4EBbLEFpk=", "requires": { - "assertion-error": "^1.0.1", - "check-error": "^1.0.1", - "deep-eql": "^3.0.0", - "get-func-name": "^2.0.0", - "pathval": "^1.0.0", - "type-detect": "^4.0.0" + "bn.js": "4.11.6", + "number-to-bn": "1.7.0" + }, + "dependencies": { + "bn.js": { + "version": "4.11.6", + "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.11.6.tgz", + "integrity": "sha1-UzRK2xRhehP26N0s4okF0cC6MhU=" + } } }, - "chai-as-promised": { - "version": "7.1.1", - "resolved": "https://registry.npmjs.org/chai-as-promised/-/chai-as-promised-7.1.1.tgz", - "integrity": "sha512-azL6xMoi+uxu6z4rhWQ1jbdUhOMhis2PvscD/xjLqNMkv3BPPp2JyyuTHOrf9BOosGpNQ11v6BKv/g57RXbiaA==", + "execa": { + "version": "0.7.0", + "resolved": "https://registry.npmjs.org/execa/-/execa-0.7.0.tgz", + "integrity": "sha1-lEvs00zEHuMqY6n68nrVpl/Fl3c=", "dev": true, "requires": { - "check-error": "^1.0.2" + "cross-spawn": "^5.0.1", + "get-stream": "^3.0.0", + "is-stream": "^1.1.0", + "npm-run-path": "^2.0.0", + "p-finally": "^1.0.0", + "signal-exit": "^3.0.0", + "strip-eof": "^1.0.0" } }, - "chai-bignumber": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/chai-bignumber/-/chai-bignumber-2.0.2.tgz", - "integrity": "sha512-BIdRNjRaoRj4bMsZLKbIZPMNKqmwnzNiyxqBYDSs6dFOCs9w8OHPuUE8e1bH60i1IhOzT0NjLtCD+lKEWB1KTQ==", - "dev": true - }, - "chalk": { - "version": "2.3.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.3.2.tgz", - "integrity": "sha512-ZM4j2/ld/YZDc3Ma8PgN7gyAk+kHMMMyzLNryCPGhWrsfAuDVeuid5bpRFTDgMH9JBK2lA4dyyAkkZYF/WcqDQ==", + "expand-brackets": { + "version": "2.1.4", + "resolved": "https://registry.npmjs.org/expand-brackets/-/expand-brackets-2.1.4.tgz", + "integrity": "sha1-t3c14xXOMPa27/D4OwQVGiJEliI=", + "dev": true, "requires": { - "ansi-styles": "^3.2.1", - "escape-string-regexp": "^1.0.5", - "supports-color": "^5.3.0" + "debug": "^2.3.3", + "define-property": "^0.2.5", + "extend-shallow": "^2.0.1", + "posix-character-classes": "^0.1.0", + "regex-not": "^1.0.0", + "snapdragon": "^0.8.1", + "to-regex": "^3.0.1" }, "dependencies": { - "has-flag": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", - "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=" - }, - "supports-color": { - "version": "5.3.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.3.0.tgz", - "integrity": "sha512-0aP01LLIskjKs3lq52EC0aGBAJhLq7B2Rd8HC/DR/PtNNpcLilNmHC12O+hu0usQpo7wtHNRqtrhBwtDb0+dNg==", + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, "requires": { - "has-flag": "^3.0.0" + "ms": "2.0.0" } - } - } - }, - "chardet": { - "version": "0.4.2", - "resolved": "https://registry.npmjs.org/chardet/-/chardet-0.4.2.tgz", - "integrity": "sha1-tUc7M9yXxCTl2Y3IfVXU2KKci/I=" - }, - "charenc": { - "version": "0.0.2", - "resolved": "https://registry.npmjs.org/charenc/-/charenc-0.0.2.tgz", - "integrity": "sha1-wKHS86cJLgN3S/qD8UwPxXkKhmc=", - "dev": true - }, - "check-error": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/check-error/-/check-error-1.0.2.tgz", - "integrity": "sha1-V00xLt2Iu13YkS6Sht1sCu1KrII=", - "dev": true - }, - "chokidar": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-2.0.3.tgz", - "integrity": "sha512-zW8iXYZtXMx4kux/nuZVXjkLP+CyIK5Al5FHnj1OgTKGZfp4Oy6/ymtMSKFv3GD8DviEmUPmJg9eFdJ/JzudMg==", - "dev": true, - "requires": { - "anymatch": "^2.0.0", - "async-each": "^1.0.0", - "braces": "^2.3.0", - "fsevents": "^1.1.2", - "glob-parent": "^3.1.0", - "inherits": "^2.0.1", - "is-binary-path": "^1.0.0", - "is-glob": "^4.0.0", - "normalize-path": "^2.1.1", - "path-is-absolute": "^1.0.0", - "readdirp": "^2.0.0", - "upath": "^1.0.0" - } - }, - "ci-info": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/ci-info/-/ci-info-1.1.3.tgz", - "integrity": "sha512-SK/846h/Rcy8q9Z9CAwGBLfCJ6EkjJWdpelWDufQpqVDYq2Wnnv8zlSO6AMQap02jvhVruKKpEtQOufo3pFhLg==", - "dev": true - }, - "class-utils": { - "version": "0.3.6", - "resolved": "https://registry.npmjs.org/class-utils/-/class-utils-0.3.6.tgz", - "integrity": "sha512-qOhPa/Fj7s6TY8H8esGu5QNpMMQxz79h+urzrNYN6mn+9BnxlDGf5QZ+XeCDsxSjPqsSR56XOZOJmpeurnLMeg==", - "dev": true, - "requires": { - "arr-union": "^3.1.0", - "define-property": "^0.2.5", - "isobject": "^3.0.0", - "static-extend": "^0.1.1" - }, - "dependencies": { + }, "define-property": { "version": "0.2.5", "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", @@ -1553,6891 +1177,3813 @@ "requires": { "is-descriptor": "^0.1.0" } + }, + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "dev": true, + "requires": { + "is-extendable": "^0.1.0" + } } } }, - "cli-boxes": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/cli-boxes/-/cli-boxes-1.0.0.tgz", - "integrity": "sha1-T6kXw+WclKAEzWH47lCdplFocUM=", + "extend": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz", + "integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==", "dev": true }, - "cli-cursor": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-2.1.0.tgz", - "integrity": "sha1-s12sN2R5+sw+lHR9QdDQ9SOP/LU=", - "requires": { - "restore-cursor": "^2.0.0" - } - }, - "cli-spinners": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/cli-spinners/-/cli-spinners-0.1.2.tgz", - "integrity": "sha1-u3ZNiOGF+54eaiofGXcjGPYF4xw=" - }, - "cli-table": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/cli-table/-/cli-table-0.3.1.tgz", - "integrity": "sha1-9TsFJmqLGguTSz0IIebi3FkUriM=", + "extend-shallow": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-3.0.2.tgz", + "integrity": "sha1-Jqcarwc7OfshJxcnRhMcJwQCjbg=", + "dev": true, "requires": { - "colors": "1.0.3" + "assign-symbols": "^1.0.0", + "is-extendable": "^1.0.1" }, "dependencies": { - "colors": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/colors/-/colors-1.0.3.tgz", - "integrity": "sha1-BDP0TYCWgP3rYO0mDxsMJi6CpAs=" + "is-extendable": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-1.0.1.tgz", + "integrity": "sha512-arnXMxT1hhoKo9k1LZdmlNyJdDDfy2v0fXjFlmok4+i8ul/6WlbVge9bhM74OpNPQPMGUToDtz+KXa1PneJxOA==", + "dev": true, + "requires": { + "is-plain-object": "^2.0.4" + } } } }, - "cli-table3": { - "version": "0.5.1", - "resolved": "https://registry.npmjs.org/cli-table3/-/cli-table3-0.5.1.tgz", - "integrity": "sha512-7Qg2Jrep1S/+Q3EceiZtQcDPWxhAvBw+ERf1162v4sikJrvojMHFqXt8QIVha8UlH9rgU0BeWPytZ9/TzYqlUw==", + "extglob": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/extglob/-/extglob-2.0.4.tgz", + "integrity": "sha512-Nmb6QXkELsuBr24CJSkilo6UHHgbekK5UiZgfE6UHD3Eb27YC6oD+bhcT+tJ6cl8dmsgdQxnWlcry8ksBIBLpw==", "dev": true, "requires": { - "colors": "^1.1.2", - "object-assign": "^4.1.0", - "string-width": "^2.1.1" + "array-unique": "^0.3.2", + "define-property": "^1.0.0", + "expand-brackets": "^2.1.4", + "extend-shallow": "^2.0.1", + "fragment-cache": "^0.2.1", + "regex-not": "^1.0.0", + "snapdragon": "^0.8.1", + "to-regex": "^3.0.1" }, "dependencies": { - "ansi-regex": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", - "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=", - "dev": true + "define-property": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-1.0.0.tgz", + "integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=", + "dev": true, + "requires": { + "is-descriptor": "^1.0.0" + } }, - "is-fullwidth-code-point": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", - "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=", - "dev": true + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "dev": true, + "requires": { + "is-extendable": "^0.1.0" + } }, - "string-width": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", - "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", + "is-accessor-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz", + "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", "dev": true, "requires": { - "is-fullwidth-code-point": "^2.0.0", - "strip-ansi": "^4.0.0" + "kind-of": "^6.0.0" } }, - "strip-ansi": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", - "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", + "is-data-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz", + "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", "dev": true, "requires": { - "ansi-regex": "^3.0.0" + "kind-of": "^6.0.0" + } + }, + "is-descriptor": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz", + "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", + "dev": true, + "requires": { + "is-accessor-descriptor": "^1.0.0", + "is-data-descriptor": "^1.0.0", + "kind-of": "^6.0.2" } } } }, - "cli-truncate": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/cli-truncate/-/cli-truncate-0.2.1.tgz", - "integrity": "sha1-nxXPuwcFAFNpIWxiasfQWrkN1XQ=", - "requires": { - "slice-ansi": "0.0.4", - "string-width": "^1.0.1" - } - }, - "cli-width": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/cli-width/-/cli-width-2.2.0.tgz", - "integrity": "sha1-/xnt6Kml5XkyQUewwR8PvLq+1jk=" + "extsprintf": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/extsprintf/-/extsprintf-1.3.0.tgz", + "integrity": "sha1-lpGEQOMEGnpBT4xS48V06zw+HgU=", + "dev": true }, - "cliui": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/cliui/-/cliui-3.2.0.tgz", - "integrity": "sha1-EgYBU3qRbSmUD5NNo7SNWFo5IT0=", - "requires": { - "string-width": "^1.0.1", - "strip-ansi": "^3.0.1", - "wrap-ansi": "^2.0.0" - } + "fast-deep-equal": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-2.0.1.tgz", + "integrity": "sha1-ewUhjd+WZ79/Nwv3/bLLFf3Qqkk=", + "dev": true }, - "clone": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/clone/-/clone-1.0.4.tgz", - "integrity": "sha1-2jCcwmPfFZlMaIypAheco8fNfH4=" + "fast-json-stable-stringify": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.0.0.tgz", + "integrity": "sha1-1RQsDK7msRifh9OnYREGT4bIu/I=", + "dev": true }, - "clone-buffer": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/clone-buffer/-/clone-buffer-1.0.0.tgz", - "integrity": "sha1-4+JbIHrE5wGvch4staFnksrD3Fg=" + "fast-levenshtein": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz", + "integrity": "sha1-PYpcZog6FqMMqGQ+hR8Zuqd5eRc=", + "dev": true }, - "clone-response": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/clone-response/-/clone-response-1.0.2.tgz", - "integrity": "sha1-0dyXOSAxTfZ/vrlCI7TuNQI56Ws=", + "fill-range": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-4.0.0.tgz", + "integrity": "sha1-1USBHUKPmOsGpj3EAtJAPDKMOPc=", + "dev": true, "requires": { - "mimic-response": "^1.0.0" + "extend-shallow": "^2.0.1", + "is-number": "^3.0.0", + "repeat-string": "^1.6.1", + "to-regex-range": "^2.1.0" + }, + "dependencies": { + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "dev": true, + "requires": { + "is-extendable": "^0.1.0" + } + } } }, - "clone-stats": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/clone-stats/-/clone-stats-0.0.1.tgz", - "integrity": "sha1-uI+UqCzzi4eR1YBG6kAprYjKmdE=" - }, - "cloneable-readable": { + "find-up": { "version": "1.1.2", - "resolved": "https://registry.npmjs.org/cloneable-readable/-/cloneable-readable-1.1.2.tgz", - "integrity": "sha512-Bq6+4t+lbM8vhTs/Bef5c5AdEMtapp/iFb6+s4/Hh9MVTt8OLKH7ZOOZSCT+Ys7hsHvqv0GuMPJ1lnQJVHvxpg==", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-1.1.2.tgz", + "integrity": "sha1-ay6YIrGizgpgq2TWEOzK1TyyTQ8=", "requires": { - "inherits": "^2.0.1", - "process-nextick-args": "^2.0.0", - "readable-stream": "^2.3.5" + "path-exists": "^2.0.0", + "pinkie-promise": "^2.0.0" } }, - "co": { - "version": "4.6.0", - "resolved": "https://registry.npmjs.org/co/-/co-4.6.0.tgz", - "integrity": "sha1-bqa989hTrlTMuOR7+gvz+QMfsYQ=" + "for-each": { + "version": "0.3.3", + "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.3.tgz", + "integrity": "sha512-jqYfLp7mo9vIyQf8ykW2v7A+2N4QjeCeI5+Dz9XraiO1ign81wjiH7Fb9vSOWvQfNtmSa4H2RoQTrrXivdUZmw==", + "requires": { + "is-callable": "^1.1.3" + } }, - "code-point-at": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/code-point-at/-/code-point-at-1.1.0.tgz", - "integrity": "sha1-DQcLTQQ6W+ozovGkDi7bPZpMz3c=" + "for-in": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/for-in/-/for-in-1.0.2.tgz", + "integrity": "sha1-gQaNKVqBQuwKxybG4iAMMPttXoA=", + "dev": true }, - "collection-visit": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/collection-visit/-/collection-visit-1.0.0.tgz", - "integrity": "sha1-S8A3PBZLwykbTTaMgpzxqApZ3KA=", + "forever-agent": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/forever-agent/-/forever-agent-0.6.1.tgz", + "integrity": "sha1-+8cfDEGt6zf5bFd60e1C2P2sypE=", + "dev": true + }, + "form-data": { + "version": "2.3.3", + "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.3.3.tgz", + "integrity": "sha512-1lLKB2Mu3aGP1Q/2eCOx0fNbRMe7XdwktwOruhfqqd0rIJWwN4Dh+E3hrPSlDCXnSR7UtZ1N38rVXm+6+MEhJQ==", "dev": true, "requires": { - "map-visit": "^1.0.0", - "object-visit": "^1.0.0" + "asynckit": "^0.4.0", + "combined-stream": "^1.0.6", + "mime-types": "^2.1.12" } }, - "color-convert": { - "version": "1.9.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.1.tgz", - "integrity": "sha512-mjGanIiwQJskCC18rPR6OmrZ6fm2Lc7PeGFYwCmy5J34wC6F1PzdGL6xeMfmgicfYcNLGuVFA3WzXtIDCQSZxQ==", + "fragment-cache": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/fragment-cache/-/fragment-cache-0.2.1.tgz", + "integrity": "sha1-QpD60n8T6Jvn8zeZxrxaCr//DRk=", + "dev": true, "requires": { - "color-name": "^1.1.1" + "map-cache": "^0.2.2" } }, - "color-name": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz", - "integrity": "sha1-p9BVi9icQveV3UIyj3QIMcpTvCU=" - }, - "colors": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/colors/-/colors-1.2.1.tgz", - "integrity": "sha512-s8+wktIuDSLffCywiwSxQOMqtPxML11a/dtHE17tMn4B1MSWw/C22EKf7M2KGUBcDaVFEGT+S8N02geDXeuNKg==" - }, - "combined-stream": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.6.tgz", - "integrity": "sha1-cj599ugBrFYTETp+RFqbactjKBg=", - "requires": { - "delayed-stream": "~1.0.0" - } - }, - "commander": { - "version": "2.11.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-2.11.0.tgz", - "integrity": "sha512-b0553uYA5YAEGgyYIGYROzKQ7X5RAqedkfjiZxwi0kL1g3bOaBNNZfYkzt/CL0umgD5wc9Jec2FbB98CjkMRvQ==" - }, - "commondir": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/commondir/-/commondir-1.0.1.tgz", - "integrity": "sha1-3dgA2gxmEnOTzKWVDqloo6rxJTs=" - }, - "component-emitter": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/component-emitter/-/component-emitter-1.2.1.tgz", - "integrity": "sha1-E3kY1teCg/ffemt8WmPhQOaUJeY=", - "dev": true - }, - "concat-map": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", - "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=" - }, - "concat-stream": { - "version": "1.6.2", - "resolved": "https://registry.npmjs.org/concat-stream/-/concat-stream-1.6.2.tgz", - "integrity": "sha512-27HBghJxjiZtIk3Ycvn/4kbJk/1uZuJFfuPEns6LaEvpvG1f0hTea8lilrouyo9mVc2GWdcEZ8OLoGmSADlrCw==", - "dev": true, - "requires": { - "buffer-from": "^1.0.0", - "inherits": "^2.0.3", - "readable-stream": "^2.2.2", - "typedarray": "^0.0.6" - } - }, - "configstore": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/configstore/-/configstore-3.1.2.tgz", - "integrity": "sha512-vtv5HtGjcYUgFrXc6Kx747B83MRRVS5R1VTEQoXvuP+kMI+if6uywV0nDGoiydJRy4yk7h9od5Og0kxx4zUXmw==", - "dev": true, + "fs-extra": { + "version": "0.30.0", + "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-0.30.0.tgz", + "integrity": "sha1-8jP/zAjU2n1DLapEl3aYnbHfk/A=", "requires": { - "dot-prop": "^4.1.0", "graceful-fs": "^4.1.2", - "make-dir": "^1.0.0", - "unique-string": "^1.0.0", - "write-file-atomic": "^2.0.0", - "xdg-basedir": "^3.0.0" - } - }, - "content-disposition": { - "version": "0.5.2", - "resolved": "https://registry.npmjs.org/content-disposition/-/content-disposition-0.5.2.tgz", - "integrity": "sha1-DPaLud318r55YcOoUXjLhdunjLQ=" - }, - "content-type": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/content-type/-/content-type-1.0.4.tgz", - "integrity": "sha512-hIP3EEPs8tB9AT1L+NUqtwOAps4mk2Zob89MWXMHjHWg9milF/j4osnnQLXBCBFBk/tvIG/tUc9mOUJiPBhPXA==" - }, - "convert-source-map": { - "version": "1.5.1", - "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-1.5.1.tgz", - "integrity": "sha1-uCeAl7m8IpNl3lxiz1/K7YtVmeU=" - }, - "cookie": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.3.1.tgz", - "integrity": "sha1-5+Ch+e9DtMi6klxcWpboBtFoc7s=" - }, - "cookie-signature": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz", - "integrity": "sha1-4wOogrNCzD7oylE6eZmXNNqzriw=" - }, - "copy-descriptor": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/copy-descriptor/-/copy-descriptor-0.1.1.tgz", - "integrity": "sha1-Z29us8OZl8LuGsOpJP1hJHSPV40=", - "dev": true - }, - "core-js": { - "version": "2.5.3", - "resolved": "https://registry.npmjs.org/core-js/-/core-js-2.5.3.tgz", - "integrity": "sha1-isw4NFgk8W2DZbfJtCWRaOjtYD4=" - }, - "core-util-is": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz", - "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=" - }, - "cors": { - "version": "2.8.4", - "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.4.tgz", - "integrity": "sha1-K9OB8usgECAQXNUOpZ2mMJBpRoY=", - "requires": { - "object-assign": "^4", - "vary": "^1" - } - }, - "create-error-class": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/create-error-class/-/create-error-class-3.0.2.tgz", - "integrity": "sha1-Br56vvlHo/FKMP1hBnHUAbyot7Y=", - "dev": true, - "requires": { - "capture-stack-trace": "^1.0.0" - } - }, - "cross-spawn": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-5.1.0.tgz", - "integrity": "sha1-6L0O/uWPz/b4+UUQoKVUu/ojVEk=", - "requires": { - "lru-cache": "^4.0.1", - "shebang-command": "^1.2.0", - "which": "^1.2.9" - }, - "dependencies": { - "lru-cache": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-4.1.2.tgz", - "integrity": "sha512-wgeVXhrDwAWnIF/yZARsFnMBtdFXOg1b8RIrhilp+0iDYN4mdQcNZElDZ0e4B64BhaxeQ5zN7PMyvu7we1kPeQ==", - "requires": { - "pseudomap": "^1.0.2", - "yallist": "^2.1.2" - } - } - } - }, - "crypt": { - "version": "0.0.2", - "resolved": "https://registry.npmjs.org/crypt/-/crypt-0.0.2.tgz", - "integrity": "sha1-iNf/fsDfuG9xPch7u0LQRNPmxBs=", - "dev": true - }, - "cryptiles": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/cryptiles/-/cryptiles-3.1.2.tgz", - "integrity": "sha1-qJ+7Ig9c4l7FboxKqKT9e1sNKf4=", - "requires": { - "boom": "5.x.x" - }, - "dependencies": { - "boom": { - "version": "5.2.0", - "resolved": "https://registry.npmjs.org/boom/-/boom-5.2.0.tgz", - "integrity": "sha512-Z5BTk6ZRe4tXXQlkqftmsAUANpXmuwlsF5Oov8ThoMbQRzdGTA1ngYRW160GexgOgjsFOKJz0LYhoNi+2AMBUw==", - "requires": { - "hoek": "4.x.x" - } - } + "jsonfile": "^2.1.0", + "klaw": "^1.0.0", + "path-is-absolute": "^1.0.0", + "rimraf": "^2.2.8" } }, - "crypto-js": { - "version": "3.1.8", - "resolved": "https://registry.npmjs.org/crypto-js/-/crypto-js-3.1.8.tgz", - "integrity": "sha1-cV8HC/YBTyrpkqmLOSkli3E/CNU=", - "dev": true - }, - "crypto-random-string": { + "fs.realpath": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/crypto-random-string/-/crypto-random-string-1.0.0.tgz", - "integrity": "sha1-ojD2T1aDEOFJgAmUB5DsmVRbyn4=", - "dev": true - }, - "dargs": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/dargs/-/dargs-5.1.0.tgz", - "integrity": "sha1-7H6lDHhWTNNsnV7Bj2Yyn63ieCk=" - }, - "dashdash": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/dashdash/-/dashdash-1.14.1.tgz", - "integrity": "sha1-hTz6D3y+L+1d4gMmuN1YEDX24vA=", - "requires": { - "assert-plus": "^1.0.0" - } - }, - "date-fns": { - "version": "1.29.0", - "resolved": "https://registry.npmjs.org/date-fns/-/date-fns-1.29.0.tgz", - "integrity": "sha512-lbTXWZ6M20cWH8N9S6afb0SBm6tMk+uUg6z3MqHPKE9atmsY3kJkTm8vKe93izJ2B2+q5MV990sM2CHgtAZaOw==" - }, - "dateformat": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/dateformat/-/dateformat-3.0.3.tgz", - "integrity": "sha512-jyCETtSl3VMZMWeRo7iY1FL19ges1t55hMo5yaam4Jrsm5EPL89UQkoQRyiI+Yf4k8r2ZpdngkV8hr1lIdjb3Q==" - }, - "death": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/death/-/death-1.1.0.tgz", - "integrity": "sha1-AaqcQB7dknUFFEcLgmY5DGbGcxg=", - "dev": true - }, - "debug": { - "version": "2.6.8", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.8.tgz", - "integrity": "sha1-5zFTHKLt4n0YgiJCfaF4IdaP9Pw=", - "requires": { - "ms": "2.0.0" - } - }, - "decamelize": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/decamelize/-/decamelize-1.2.0.tgz", - "integrity": "sha1-9lNNFRSCabIDUue+4m9QH5oZEpA=" - }, - "decode-uri-component": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/decode-uri-component/-/decode-uri-component-0.2.0.tgz", - "integrity": "sha1-6zkTMzRYd1y4TNGh+uBiEGu4dUU=" - }, - "decompress-response": { - "version": "3.3.0", - "resolved": "https://registry.npmjs.org/decompress-response/-/decompress-response-3.3.0.tgz", - "integrity": "sha1-gKTdMjdIOEv6JICDYirt7Jgq3/M=", - "requires": { - "mimic-response": "^1.0.0" - } - }, - "deep-eql": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/deep-eql/-/deep-eql-3.0.1.tgz", - "integrity": "sha512-+QeIQyN5ZuO+3Uk5DYh6/1eKO0m0YmJFGNmFHGACpf1ClL1nmlV/p4gNgbl2pJGxgXb4faqo6UE+M5ACEMyVcw==", - "dev": true, - "requires": { - "type-detect": "^4.0.0" - } - }, - "deep-extend": { - "version": "0.4.2", - "resolved": "https://registry.npmjs.org/deep-extend/-/deep-extend-0.4.2.tgz", - "integrity": "sha1-SLaZwn4zS/ifEIkr5DL25MfTSn8=" - }, - "deep-is": { - "version": "0.1.3", - "resolved": "https://registry.npmjs.org/deep-is/-/deep-is-0.1.3.tgz", - "integrity": "sha1-s2nW+128E+7PUk+RsHD+7cNXzzQ=", - "dev": true + "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", + "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=" }, - "define-property": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/define-property/-/define-property-2.0.2.tgz", - "integrity": "sha512-jwK2UV4cnPpbcG7+VRARKTZPUWowwXA8bzH5NP6ud0oeAxyYPuGZUAC7hMugpCdz4BeSZl2Dl9k66CHJ/46ZYQ==", + "fsevents": { + "version": "1.2.7", + "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-1.2.7.tgz", + "integrity": "sha512-Pxm6sI2MeBD7RdD12RYsqaP0nMiwx8eZBXCa6z2L+mRHm2DYrOYwihmhjpkdjUHwQhslWQjRpEgNq4XvBmaAuw==", "dev": true, + "optional": true, "requires": { - "is-descriptor": "^1.0.2", - "isobject": "^3.0.1" + "nan": "^2.9.2", + "node-pre-gyp": "^0.10.0" }, "dependencies": { - "is-accessor-descriptor": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz", - "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", + "abbrev": { + "version": "1.1.1", + "bundled": true, + "dev": true, + "optional": true + }, + "ansi-regex": { + "version": "2.1.1", + "bundled": true, + "dev": true + }, + "aproba": { + "version": "1.2.0", + "bundled": true, + "dev": true, + "optional": true + }, + "are-we-there-yet": { + "version": "1.1.5", + "bundled": true, "dev": true, + "optional": true, "requires": { - "kind-of": "^6.0.0" + "delegates": "^1.0.0", + "readable-stream": "^2.0.6" } }, - "is-data-descriptor": { + "balanced-match": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz", - "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", + "bundled": true, + "dev": true + }, + "brace-expansion": { + "version": "1.1.11", + "bundled": true, "dev": true, "requires": { - "kind-of": "^6.0.0" + "balanced-match": "^1.0.0", + "concat-map": "0.0.1" } }, - "is-descriptor": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz", - "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", + "chownr": { + "version": "1.1.1", + "bundled": true, "dev": true, - "requires": { - "is-accessor-descriptor": "^1.0.0", - "is-data-descriptor": "^1.0.0", - "kind-of": "^6.0.2" - } - } - } - }, - "delayed-stream": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", - "integrity": "sha1-3zrhmayt+31ECqrgsp4icrJOxhk=" - }, - "depd": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/depd/-/depd-1.1.2.tgz", - "integrity": "sha1-m81S4UwJd2PnSbJ0xDRu0uVgtak=" - }, - "destroy": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/destroy/-/destroy-1.0.4.tgz", - "integrity": "sha1-l4hXRCxEdJ5CBmE+N5RiBYJqvYA=" - }, - "detect-conflict": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/detect-conflict/-/detect-conflict-1.0.1.tgz", - "integrity": "sha1-CIZXpmqWHAUBnbfEIwiDsca0F24=" - }, - "detect-indent": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/detect-indent/-/detect-indent-4.0.0.tgz", - "integrity": "sha1-920GQ1LN9Docts5hnE7jqUdd4gg=", - "requires": { - "repeating": "^2.0.0" - } - }, - "diff": { - "version": "3.3.1", - "resolved": "https://registry.npmjs.org/diff/-/diff-3.3.1.tgz", - "integrity": "sha512-MKPHZDMB0o6yHyDryUOScqZibp914ksXwAMYMTHj6KO8UeKsRYNJD3oNCKjTqZon+V488P7N/HzXF8t7ZR95ww==" - }, - "dom-walk": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/dom-walk/-/dom-walk-0.1.1.tgz", - "integrity": "sha1-ZyIm3HTI95mtNTB9+TaroRrNYBg=" - }, - "dot-prop": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/dot-prop/-/dot-prop-4.2.0.tgz", - "integrity": "sha512-tUMXrxlExSW6U2EXiiKGSBVdYgtV8qlHL+C10TsW4PURY/ic+eaysnSkwB4kA/mBlCyy/IKDJ+Lc3wbWeaXtuQ==", - "dev": true, - "requires": { - "is-obj": "^1.0.0" - } - }, - "duplexer": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/duplexer/-/duplexer-0.1.1.tgz", - "integrity": "sha1-rOb/gIwc5mtX0ev5eXessCM0z8E=", - "dev": true - }, - "duplexer3": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/duplexer3/-/duplexer3-0.1.4.tgz", - "integrity": "sha1-7gHdHKwO08vH/b6jfcCo8c4ALOI=" - }, - "ecc-jsbn": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/ecc-jsbn/-/ecc-jsbn-0.1.1.tgz", - "integrity": "sha1-D8c6ntXw1Tw4GTOYUj735UN3dQU=", - "optional": true, - "requires": { - "jsbn": "~0.1.0" - } - }, - "editions": { - "version": "1.3.4", - "resolved": "https://registry.npmjs.org/editions/-/editions-1.3.4.tgz", - "integrity": "sha512-gzao+mxnYDzIysXKMQi/+M1mjy/rjestjg6OPoYTtI+3Izp23oiGZitsl9lPDPiTGXbcSIk1iJWhliSaglxnUg==" - }, - "ee-first": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/ee-first/-/ee-first-1.1.1.tgz", - "integrity": "sha1-WQxhFWsK4vTwJVcyoViyZrxWsh0=" - }, - "ejs": { - "version": "2.5.8", - "resolved": "https://registry.npmjs.org/ejs/-/ejs-2.5.8.tgz", - "integrity": "sha512-QIDZL54fyV8MDcAsO91BMH1ft2qGGaHIJsJIA/+t+7uvXol1dm413fPcUgUb4k8F/9457rx4/KFE4XfDifrQxQ==" - }, - "elegant-spinner": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/elegant-spinner/-/elegant-spinner-1.0.1.tgz", - "integrity": "sha1-2wQ1IcldfjA/2PNFvtwzSc+wcp4=" - }, - "elliptic": { - "version": "6.4.0", - "resolved": "https://registry.npmjs.org/elliptic/-/elliptic-6.4.0.tgz", - "integrity": "sha1-ysmvh2LIWDYYcAPI3+GT5eLq5d8=", - "requires": { - "bn.js": "^4.4.0", - "brorand": "^1.0.1", - "hash.js": "^1.0.0", - "hmac-drbg": "^1.0.0", - "inherits": "^2.0.1", - "minimalistic-assert": "^1.0.0", - "minimalistic-crypto-utils": "^1.0.0" - } - }, - "emojis-list": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/emojis-list/-/emojis-list-2.1.0.tgz", - "integrity": "sha1-TapNnbAPmBmIDHn6RXrlsJof04k=" - }, - "encodeurl": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-1.0.2.tgz", - "integrity": "sha1-rT/0yG7C0CkyL1oCw6mmBslbP1k=" - }, - "enhanced-resolve": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/enhanced-resolve/-/enhanced-resolve-4.0.0.tgz", - "integrity": "sha512-jox/62b2GofV1qTUQTMPEJSDIGycS43evqYzD/KVtEb9OCoki9cnacUPxCrZa7JfPzZSYOCZhu9O9luaMxAX8g==", - "requires": { - "graceful-fs": "^4.1.2", - "memory-fs": "^0.4.0", - "tapable": "^1.0.0" - } - }, - "errno": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/errno/-/errno-0.1.7.tgz", - "integrity": "sha512-MfrRBDWzIWifgq6tJj60gkAwtLNb6sQPlcFrSOflcP1aFmmruKQ2wRnze/8V6kgyz7H3FF8Npzv78mZ7XLLflg==", - "requires": { - "prr": "~1.0.1" - } - }, - "error": { - "version": "7.0.2", - "resolved": "https://registry.npmjs.org/error/-/error-7.0.2.tgz", - "integrity": "sha1-pfdf/02ZJhJt2sDqXcOOaJFTywI=", - "requires": { - "string-template": "~0.2.1", - "xtend": "~4.0.0" - } - }, - "error-ex": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.1.tgz", - "integrity": "sha1-+FWobOYa3E6GIcPNoh56dhLDqNw=", - "requires": { - "is-arrayish": "^0.2.1" - } - }, - "escape-html": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/escape-html/-/escape-html-1.0.3.tgz", - "integrity": "sha1-Aljq5NPQwJdN4cFpGI7wBR0dGYg=" - }, - "escape-string-regexp": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", - "integrity": "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=" - }, - "escodegen": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/escodegen/-/escodegen-1.8.1.tgz", - "integrity": "sha1-WltTr0aTEQvrsIZ6o0MN07cKEBg=", - "dev": true, - "requires": { - "esprima": "^2.7.1", - "estraverse": "^1.9.1", - "esutils": "^2.0.2", - "optionator": "^0.8.1", - "source-map": "~0.2.0" - }, - "dependencies": { - "esprima": { - "version": "2.7.3", - "resolved": "https://registry.npmjs.org/esprima/-/esprima-2.7.3.tgz", - "integrity": "sha1-luO3DVd59q1JzQMmc9HDEnZ7pYE=", + "optional": true + }, + "code-point-at": { + "version": "1.1.0", + "bundled": true, "dev": true }, - "source-map": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.2.0.tgz", - "integrity": "sha1-2rc/vPwrqBm03gO9b26qSBZLP50=", + "concat-map": { + "version": "0.0.1", + "bundled": true, + "dev": true + }, + "console-control-strings": { + "version": "1.1.0", + "bundled": true, + "dev": true + }, + "core-util-is": { + "version": "1.0.2", + "bundled": true, + "dev": true, + "optional": true + }, + "debug": { + "version": "2.6.9", + "bundled": true, "dev": true, "optional": true, "requires": { - "amdefine": ">=0.0.4" + "ms": "2.0.0" } - } - } - }, - "esprima": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/esprima/-/esprima-4.0.0.tgz", - "integrity": "sha512-oftTcaMu/EGrEIu904mWteKIv8vMuOgGYo7EhVJJN00R/EED9DCua/xxHRdYnKtcECzVg7xOWhflvJMnqcFZjw==" - }, - "estraverse": { - "version": "1.9.3", - "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-1.9.3.tgz", - "integrity": "sha1-r2fy3JIlgkFZUJJgkaQAXSnJu0Q=", - "dev": true - }, - "esutils": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/esutils/-/esutils-2.0.2.tgz", - "integrity": "sha1-Cr9PHKpbyx96nYrMbepPqqBLrJs=" - }, - "etag": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/etag/-/etag-1.8.1.tgz", - "integrity": "sha1-Qa4u62XvpiJorr/qg6x9eSmbCIc=" - }, - "eth-gas-reporter": { - "version": "0.1.12", - "resolved": "https://registry.npmjs.org/eth-gas-reporter/-/eth-gas-reporter-0.1.12.tgz", - "integrity": "sha512-Ao5uiXSA5Ep5fi/YvGCsFJMelMKj0fMJkAvWYzPVe1h3Mg9Z7X3Rs51ovG9izFZH7wSqnqydiC6SKDhZWpxK2g==", - "dev": true, - "requires": { - "abi-decoder": "^1.0.8", - "cli-table3": "^0.5.0", - "colors": "^1.1.2", - "lodash": "^4.17.4", - "mocha": "^4.1.0", - "req-cwd": "^2.0.0", - "request": "^2.83.0", - "request-promise-native": "^1.0.5", - "sha1": "^1.1.1", - "shelljs": "^0.7.8", - "solidity-parser-antlr": "^0.2.10", - "sync-request": "^6.0.0" - }, - "dependencies": { - "req-cwd": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/req-cwd/-/req-cwd-2.0.0.tgz", - "integrity": "sha1-1AgrTURZgDZkD7c93qAe1T20nrw=", + }, + "deep-extend": { + "version": "0.6.0", + "bundled": true, "dev": true, - "requires": { - "req-from": "^2.0.0" - } + "optional": true }, - "req-from": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/req-from/-/req-from-2.0.0.tgz", - "integrity": "sha1-10GI5H+TeW9Kpx327jWuaJ8+DnA=", + "delegates": { + "version": "1.0.0", + "bundled": true, + "dev": true, + "optional": true + }, + "detect-libc": { + "version": "1.0.3", + "bundled": true, + "dev": true, + "optional": true + }, + "fs-minipass": { + "version": "1.2.5", + "bundled": true, "dev": true, + "optional": true, "requires": { - "resolve-from": "^3.0.0" + "minipass": "^2.2.1" } }, - "shelljs": { - "version": "0.7.8", - "resolved": "https://registry.npmjs.org/shelljs/-/shelljs-0.7.8.tgz", - "integrity": "sha1-3svPh0sNHl+3LhSxZKloMEjprLM=", + "fs.realpath": { + "version": "1.0.0", + "bundled": true, + "dev": true, + "optional": true + }, + "gauge": { + "version": "2.7.4", + "bundled": true, "dev": true, + "optional": true, "requires": { - "glob": "^7.0.0", - "interpret": "^1.0.0", - "rechoir": "^0.6.2" + "aproba": "^1.0.3", + "console-control-strings": "^1.0.0", + "has-unicode": "^2.0.0", + "object-assign": "^4.1.0", + "signal-exit": "^3.0.0", + "string-width": "^1.0.1", + "strip-ansi": "^3.0.1", + "wide-align": "^1.1.0" } - } - } - }, - "eth-lib": { - "version": "0.1.27", - "resolved": "https://registry.npmjs.org/eth-lib/-/eth-lib-0.1.27.tgz", - "integrity": "sha512-B8czsfkJYzn2UIEMwjc7Mbj+Cy72V+/OXH/tb44LV8jhrjizQJJ325xMOMyk3+ETa6r6oi0jsUY14+om8mQMWA==", - "requires": { - "bn.js": "^4.11.6", - "elliptic": "^6.4.0", - "keccakjs": "^0.2.1", - "nano-json-stream-parser": "^0.1.2", - "servify": "^0.1.12", - "ws": "^3.0.0", - "xhr-request-promise": "^0.1.2" - } - }, - "ethereumjs-testrpc-sc": { - "version": "6.1.2", - "resolved": "https://registry.npmjs.org/ethereumjs-testrpc-sc/-/ethereumjs-testrpc-sc-6.1.2.tgz", - "integrity": "sha512-dBTav4AZQ7zuajmICv1k7bEesqS+8f0u0wciXNUJZb842RTBi0lgKEDF8WgZshzv4ThI+XVQSRNV/A+seiK4aA==", - "dev": true, - "requires": { - "source-map-support": "^0.5.3", - "webpack-cli": "^2.0.9" - } - }, - "ethjs-unit": { - "version": "0.1.6", - "resolved": "https://registry.npmjs.org/ethjs-unit/-/ethjs-unit-0.1.6.tgz", - "integrity": "sha1-xmWSHkduh7ziqdWIpv4EBbLEFpk=", - "requires": { - "bn.js": "4.11.6", - "number-to-bn": "1.7.0" - } - }, - "event-stream": { - "version": "3.3.4", - "resolved": "http://registry.npmjs.org/event-stream/-/event-stream-3.3.4.tgz", - "integrity": "sha1-SrTJoPWlTbkzi0w02Gv86PSzVXE=", - "dev": true, - "requires": { - "duplexer": "~0.1.1", - "from": "~0", - "map-stream": "~0.1.0", - "pause-stream": "0.0.11", - "split": "0.3", - "stream-combiner": "~0.0.4", - "through": "~2.3.1" - } - }, - "execa": { - "version": "0.7.0", - "resolved": "https://registry.npmjs.org/execa/-/execa-0.7.0.tgz", - "integrity": "sha1-lEvs00zEHuMqY6n68nrVpl/Fl3c=", - "requires": { - "cross-spawn": "^5.0.1", - "get-stream": "^3.0.0", - "is-stream": "^1.1.0", - "npm-run-path": "^2.0.0", - "p-finally": "^1.0.0", - "signal-exit": "^3.0.0", - "strip-eof": "^1.0.0" - } - }, - "exit-hook": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/exit-hook/-/exit-hook-1.1.1.tgz", - "integrity": "sha1-8FyiM7SMBdVP/wd2XfhQfpXAL/g=" - }, - "expand-brackets": { - "version": "2.1.4", - "resolved": "https://registry.npmjs.org/expand-brackets/-/expand-brackets-2.1.4.tgz", - "integrity": "sha1-t3c14xXOMPa27/D4OwQVGiJEliI=", - "dev": true, - "requires": { - "debug": "^2.3.3", - "define-property": "^0.2.5", - "extend-shallow": "^2.0.1", - "posix-character-classes": "^0.1.0", - "regex-not": "^1.0.0", - "snapdragon": "^0.8.1", - "to-regex": "^3.0.1" - }, - "dependencies": { - "define-property": { - "version": "0.2.5", - "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", - "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", - "dev": true, - "requires": { - "is-descriptor": "^0.1.0" - } - }, - "extend-shallow": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", - "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", - "dev": true, - "requires": { - "is-extendable": "^0.1.0" - } - } - } - }, - "expand-range": { - "version": "1.8.2", - "resolved": "https://registry.npmjs.org/expand-range/-/expand-range-1.8.2.tgz", - "integrity": "sha1-opnv/TNf4nIeuujiV+x5ZE/IUzc=", - "requires": { - "fill-range": "^2.1.0" - }, - "dependencies": { - "fill-range": { - "version": "2.2.3", - "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-2.2.3.tgz", - "integrity": "sha1-ULd9/X5Gm8dJJHCWNpn+eoSFpyM=", - "requires": { - "is-number": "^2.1.0", - "isobject": "^2.0.0", - "randomatic": "^1.1.3", - "repeat-element": "^1.1.2", - "repeat-string": "^1.5.2" - } - }, - "is-number": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/is-number/-/is-number-2.1.0.tgz", - "integrity": "sha1-Afy7s5NGOlSPL0ZszhbezknbkI8=", - "requires": { - "kind-of": "^3.0.2" - } - }, - "isobject": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/isobject/-/isobject-2.1.0.tgz", - "integrity": "sha1-8GVWEJaj8dou9GJy+BXIQNh+DIk=", - "requires": { - "isarray": "1.0.0" - } - }, - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", - "requires": { - "is-buffer": "^1.1.5" - } - } - } - }, - "expand-tilde": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/expand-tilde/-/expand-tilde-2.0.2.tgz", - "integrity": "sha1-l+gBqgUt8CRU3kawK/YhZCzchQI=", - "requires": { - "homedir-polyfill": "^1.0.1" - } - }, - "express": { - "version": "4.16.3", - "resolved": "https://registry.npmjs.org/express/-/express-4.16.3.tgz", - "integrity": "sha1-avilAjUNsyRuzEvs9rWjTSL37VM=", - "requires": { - "accepts": "~1.3.5", - "array-flatten": "1.1.1", - "body-parser": "1.18.2", - "content-disposition": "0.5.2", - "content-type": "~1.0.4", - "cookie": "0.3.1", - "cookie-signature": "1.0.6", - "debug": "2.6.9", - "depd": "~1.1.2", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "etag": "~1.8.1", - "finalhandler": "1.1.1", - "fresh": "0.5.2", - "merge-descriptors": "1.0.1", - "methods": "~1.1.2", - "on-finished": "~2.3.0", - "parseurl": "~1.3.2", - "path-to-regexp": "0.1.7", - "proxy-addr": "~2.0.3", - "qs": "6.5.1", - "range-parser": "~1.2.0", - "safe-buffer": "5.1.1", - "send": "0.16.2", - "serve-static": "1.13.2", - "setprototypeof": "1.1.0", - "statuses": "~1.4.0", - "type-is": "~1.6.16", - "utils-merge": "1.0.1", - "vary": "~1.1.2" - }, - "dependencies": { - "debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "requires": { - "ms": "2.0.0" - } - }, - "statuses": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.4.0.tgz", - "integrity": "sha512-zhSCtt8v2NDrRlPQpCNtw/heZLtfUDqxBM1udqikb/Hbk52LK4nQSwr10u77iopCW5LsyHpuXS0GnEc48mLeew==" - } - } - }, - "extend": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.1.tgz", - "integrity": "sha1-p1Xqe8Gt/MWjHOfnYtuq3F5jZEQ=" - }, - "extend-shallow": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-3.0.2.tgz", - "integrity": "sha1-Jqcarwc7OfshJxcnRhMcJwQCjbg=", - "dev": true, - "requires": { - "assign-symbols": "^1.0.0", - "is-extendable": "^1.0.1" - }, - "dependencies": { - "is-extendable": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-1.0.1.tgz", - "integrity": "sha512-arnXMxT1hhoKo9k1LZdmlNyJdDDfy2v0fXjFlmok4+i8ul/6WlbVge9bhM74OpNPQPMGUToDtz+KXa1PneJxOA==", - "dev": true, - "requires": { - "is-plain-object": "^2.0.4" - } - } - } - }, - "external-editor": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/external-editor/-/external-editor-2.1.0.tgz", - "integrity": "sha512-E44iT5QVOUJBKij4IIV3uvxuNlbKS38Tw1HiupxEIHPv9qtC2PrDYohbXV5U+1jnfIXttny8gUhj+oZvflFlzA==", - "requires": { - "chardet": "^0.4.0", - "iconv-lite": "^0.4.17", - "tmp": "^0.0.33" - } - }, - "extglob": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/extglob/-/extglob-2.0.4.tgz", - "integrity": "sha512-Nmb6QXkELsuBr24CJSkilo6UHHgbekK5UiZgfE6UHD3Eb27YC6oD+bhcT+tJ6cl8dmsgdQxnWlcry8ksBIBLpw==", - "dev": true, - "requires": { - "array-unique": "^0.3.2", - "define-property": "^1.0.0", - "expand-brackets": "^2.1.4", - "extend-shallow": "^2.0.1", - "fragment-cache": "^0.2.1", - "regex-not": "^1.0.0", - "snapdragon": "^0.8.1", - "to-regex": "^3.0.1" - }, - "dependencies": { - "define-property": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/define-property/-/define-property-1.0.0.tgz", - "integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=", - "dev": true, - "requires": { - "is-descriptor": "^1.0.0" - } - }, - "extend-shallow": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", - "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", - "dev": true, - "requires": { - "is-extendable": "^0.1.0" - } - }, - "is-accessor-descriptor": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz", - "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", - "dev": true, - "requires": { - "kind-of": "^6.0.0" - } - }, - "is-data-descriptor": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz", - "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", - "dev": true, - "requires": { - "kind-of": "^6.0.0" - } - }, - "is-descriptor": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz", - "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", - "dev": true, - "requires": { - "is-accessor-descriptor": "^1.0.0", - "is-data-descriptor": "^1.0.0", - "kind-of": "^6.0.2" - } - } - } - }, - "extsprintf": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/extsprintf/-/extsprintf-1.3.0.tgz", - "integrity": "sha1-lpGEQOMEGnpBT4xS48V06zw+HgU=" - }, - "fast-deep-equal": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-1.1.0.tgz", - "integrity": "sha1-wFNHeBfIa1HaqFPIHgWbcz0CNhQ=" - }, - "fast-json-stable-stringify": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.0.0.tgz", - "integrity": "sha1-1RQsDK7msRifh9OnYREGT4bIu/I=" - }, - "fast-levenshtein": { - "version": "2.0.6", - "resolved": "https://registry.npmjs.org/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz", - "integrity": "sha1-PYpcZog6FqMMqGQ+hR8Zuqd5eRc=", - "dev": true - }, - "figures": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/figures/-/figures-2.0.0.tgz", - "integrity": "sha1-OrGi0qYsi/tDGgyUy3l6L84nyWI=", - "requires": { - "escape-string-regexp": "^1.0.5" - } - }, - "filename-regex": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/filename-regex/-/filename-regex-2.0.1.tgz", - "integrity": "sha1-wcS5vuPglyXdsQa3XB4wH+LxiyY=" - }, - "fill-range": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-4.0.0.tgz", - "integrity": "sha1-1USBHUKPmOsGpj3EAtJAPDKMOPc=", - "dev": true, - "requires": { - "extend-shallow": "^2.0.1", - "is-number": "^3.0.0", - "repeat-string": "^1.6.1", - "to-regex-range": "^2.1.0" - }, - "dependencies": { - "extend-shallow": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", - "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", - "dev": true, - "requires": { - "is-extendable": "^0.1.0" - } - } - } - }, - "finalhandler": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/finalhandler/-/finalhandler-1.1.1.tgz", - "integrity": "sha512-Y1GUDo39ez4aHAw7MysnUD5JzYX+WaIj8I57kO3aEPT1fFRL4sr7mjei97FgnwhAyyzRYmQZaTHb2+9uZ1dPtg==", - "requires": { - "debug": "2.6.9", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "on-finished": "~2.3.0", - "parseurl": "~1.3.2", - "statuses": "~1.4.0", - "unpipe": "~1.0.0" - }, - "dependencies": { - "debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "requires": { - "ms": "2.0.0" - } - }, - "statuses": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.4.0.tgz", - "integrity": "sha512-zhSCtt8v2NDrRlPQpCNtw/heZLtfUDqxBM1udqikb/Hbk52LK4nQSwr10u77iopCW5LsyHpuXS0GnEc48mLeew==" - } - } - }, - "find-up": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-1.1.2.tgz", - "integrity": "sha1-ay6YIrGizgpgq2TWEOzK1TyyTQ8=", - "requires": { - "path-exists": "^2.0.0", - "pinkie-promise": "^2.0.0" - } - }, - "first-chunk-stream": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/first-chunk-stream/-/first-chunk-stream-2.0.0.tgz", - "integrity": "sha1-G97NuOCDwGZLkZRVgVd6Q6nzHXA=", - "requires": { - "readable-stream": "^2.0.2" - } - }, - "flow-parser": { - "version": "0.68.0", - "resolved": "https://registry.npmjs.org/flow-parser/-/flow-parser-0.68.0.tgz", - "integrity": "sha1-nMlmIKEC4xajFLa81WIFzqzoYtg=" - }, - "for-each": { - "version": "0.3.2", - "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.2.tgz", - "integrity": "sha1-LEBFC5NI6X8oEyJZO6lnBLmr1NQ=", - "requires": { - "is-function": "~1.0.0" - } - }, - "for-in": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/for-in/-/for-in-1.0.2.tgz", - "integrity": "sha1-gQaNKVqBQuwKxybG4iAMMPttXoA=" - }, - "for-own": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/for-own/-/for-own-0.1.5.tgz", - "integrity": "sha1-UmXGgaTylNq78XyVCbZ2OqhFEM4=", - "requires": { - "for-in": "^1.0.1" - } - }, - "forever-agent": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/forever-agent/-/forever-agent-0.6.1.tgz", - "integrity": "sha1-+8cfDEGt6zf5bFd60e1C2P2sypE=" - }, - "form-data": { - "version": "2.3.2", - "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.3.2.tgz", - "integrity": "sha1-SXBJi+YEwgwAXU9cI67NIda0kJk=", - "requires": { - "asynckit": "^0.4.0", - "combined-stream": "1.0.6", - "mime-types": "^2.1.12" - } - }, - "forwarded": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.1.2.tgz", - "integrity": "sha1-mMI9qxF1ZXuMBXPozszZGw/xjIQ=" - }, - "fragment-cache": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/fragment-cache/-/fragment-cache-0.2.1.tgz", - "integrity": "sha1-QpD60n8T6Jvn8zeZxrxaCr//DRk=", - "dev": true, - "requires": { - "map-cache": "^0.2.2" - } - }, - "fresh": { - "version": "0.5.2", - "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.5.2.tgz", - "integrity": "sha1-PYyt2Q2XZWn6g1qx+OSyOhBWBac=" - }, - "from": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/from/-/from-0.1.7.tgz", - "integrity": "sha1-g8YK/Fi5xWmXAH7Rp2izqzA6RP4=", - "dev": true - }, - "from2": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/from2/-/from2-2.3.0.tgz", - "integrity": "sha1-i/tVAr3kpNNs/e6gB/zKIdfjgq8=", - "requires": { - "inherits": "^2.0.1", - "readable-stream": "^2.0.0" - } - }, - "fs-extra": { - "version": "0.30.0", - "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-0.30.0.tgz", - "integrity": "sha1-8jP/zAjU2n1DLapEl3aYnbHfk/A=", - "requires": { - "graceful-fs": "^4.1.2", - "jsonfile": "^2.1.0", - "klaw": "^1.0.0", - "path-is-absolute": "^1.0.0", - "rimraf": "^2.2.8" - } - }, - "fs.realpath": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", - "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=" - }, - "fsevents": { - "version": "1.2.3", - "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-1.2.3.tgz", - "integrity": "sha512-X+57O5YkDTiEQGiw8i7wYc2nQgweIekqkepI8Q3y4wVlurgBt2SuwxTeYUYMZIGpLZH3r/TsMjczCMXE5ZOt7Q==", - "dev": true, - "optional": true, - "requires": { - "nan": "^2.9.2", - "node-pre-gyp": "^0.9.0" - }, - "dependencies": { - "abbrev": { - "version": "1.1.1", - "bundled": true, - "dev": true, - "optional": true - }, - "ansi-regex": { - "version": "2.1.1", - "bundled": true, - "dev": true - }, - "aproba": { - "version": "1.2.0", - "bundled": true, - "dev": true, - "optional": true - }, - "are-we-there-yet": { - "version": "1.1.4", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "delegates": "^1.0.0", - "readable-stream": "^2.0.6" - } - }, - "balanced-match": { - "version": "1.0.0", - "bundled": true, - "dev": true - }, - "brace-expansion": { - "version": "1.1.11", - "bundled": true, - "dev": true, - "requires": { - "balanced-match": "^1.0.0", - "concat-map": "0.0.1" - } - }, - "chownr": { - "version": "1.0.1", - "bundled": true, - "dev": true, - "optional": true - }, - "code-point-at": { - "version": "1.1.0", - "bundled": true, - "dev": true - }, - "concat-map": { - "version": "0.0.1", - "bundled": true, - "dev": true - }, - "console-control-strings": { - "version": "1.1.0", - "bundled": true, - "dev": true - }, - "core-util-is": { - "version": "1.0.2", - "bundled": true, - "dev": true, - "optional": true - }, - "debug": { - "version": "2.6.9", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "ms": "2.0.0" - } - }, - "deep-extend": { - "version": "0.4.2", - "bundled": true, - "dev": true, - "optional": true - }, - "delegates": { - "version": "1.0.0", - "bundled": true, - "dev": true, - "optional": true - }, - "detect-libc": { - "version": "1.0.3", - "bundled": true, - "dev": true, - "optional": true - }, - "fs-minipass": { - "version": "1.2.5", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "minipass": "^2.2.1" - } - }, - "fs.realpath": { - "version": "1.0.0", - "bundled": true, - "dev": true, - "optional": true - }, - "gauge": { - "version": "2.7.4", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "aproba": "^1.0.3", - "console-control-strings": "^1.0.0", - "has-unicode": "^2.0.0", - "object-assign": "^4.1.0", - "signal-exit": "^3.0.0", - "string-width": "^1.0.1", - "strip-ansi": "^3.0.1", - "wide-align": "^1.1.0" - } - }, - "glob": { - "version": "7.1.2", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "fs.realpath": "^1.0.0", - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "^3.0.4", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" - } - }, - "has-unicode": { - "version": "2.0.1", - "bundled": true, - "dev": true, - "optional": true - }, - "iconv-lite": { - "version": "0.4.21", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "safer-buffer": "^2.1.0" - } - }, - "ignore-walk": { - "version": "3.0.1", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "minimatch": "^3.0.4" - } - }, - "inflight": { - "version": "1.0.6", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "once": "^1.3.0", - "wrappy": "1" - } - }, - "inherits": { - "version": "2.0.3", - "bundled": true, - "dev": true - }, - "ini": { - "version": "1.3.5", - "bundled": true, - "dev": true, - "optional": true - }, - "is-fullwidth-code-point": { - "version": "1.0.0", - "bundled": true, - "dev": true, - "requires": { - "number-is-nan": "^1.0.0" - } - }, - "isarray": { - "version": "1.0.0", - "bundled": true, - "dev": true, - "optional": true - }, - "minimatch": { - "version": "3.0.4", - "bundled": true, - "dev": true, - "requires": { - "brace-expansion": "^1.1.7" - } - }, - "minimist": { - "version": "0.0.8", - "bundled": true, - "dev": true - }, - "minipass": { - "version": "2.2.4", - "bundled": true, - "dev": true, - "requires": { - "safe-buffer": "^5.1.1", - "yallist": "^3.0.0" - } - }, - "minizlib": { - "version": "1.1.0", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "minipass": "^2.2.1" - } - }, - "mkdirp": { - "version": "0.5.1", - "bundled": true, - "dev": true, - "requires": { - "minimist": "0.0.8" - } - }, - "ms": { - "version": "2.0.0", - "bundled": true, - "dev": true, - "optional": true - }, - "needle": { - "version": "2.2.0", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "debug": "^2.1.2", - "iconv-lite": "^0.4.4", - "sax": "^1.2.4" - } - }, - "node-pre-gyp": { - "version": "0.9.1", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "detect-libc": "^1.0.2", - "mkdirp": "^0.5.1", - "needle": "^2.2.0", - "nopt": "^4.0.1", - "npm-packlist": "^1.1.6", - "npmlog": "^4.0.2", - "rc": "^1.1.7", - "rimraf": "^2.6.1", - "semver": "^5.3.0", - "tar": "^4" - } - }, - "nopt": { - "version": "4.0.1", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "abbrev": "1", - "osenv": "^0.1.4" - } - }, - "npm-bundled": { - "version": "1.0.3", - "bundled": true, - "dev": true, - "optional": true - }, - "npm-packlist": { - "version": "1.1.10", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "ignore-walk": "^3.0.1", - "npm-bundled": "^1.0.1" - } - }, - "npmlog": { - "version": "4.1.2", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "are-we-there-yet": "~1.1.2", - "console-control-strings": "~1.1.0", - "gauge": "~2.7.3", - "set-blocking": "~2.0.0" - } - }, - "number-is-nan": { - "version": "1.0.1", - "bundled": true, - "dev": true - }, - "object-assign": { - "version": "4.1.1", - "bundled": true, - "dev": true, - "optional": true - }, - "once": { - "version": "1.4.0", - "bundled": true, - "dev": true, - "requires": { - "wrappy": "1" - } - }, - "os-homedir": { - "version": "1.0.2", - "bundled": true, - "dev": true, - "optional": true - }, - "os-tmpdir": { - "version": "1.0.2", - "bundled": true, - "dev": true, - "optional": true - }, - "osenv": { - "version": "0.1.5", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "os-homedir": "^1.0.0", - "os-tmpdir": "^1.0.0" - } - }, - "path-is-absolute": { - "version": "1.0.1", - "bundled": true, - "dev": true, - "optional": true - }, - "process-nextick-args": { - "version": "2.0.0", - "bundled": true, - "dev": true, - "optional": true - }, - "rc": { - "version": "1.2.6", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "deep-extend": "~0.4.0", - "ini": "~1.3.0", - "minimist": "^1.2.0", - "strip-json-comments": "~2.0.1" - }, - "dependencies": { - "minimist": { - "version": "1.2.0", - "bundled": true, - "dev": true, - "optional": true - } - } - }, - "readable-stream": { - "version": "2.3.6", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "core-util-is": "~1.0.0", - "inherits": "~2.0.3", - "isarray": "~1.0.0", - "process-nextick-args": "~2.0.0", - "safe-buffer": "~5.1.1", - "string_decoder": "~1.1.1", - "util-deprecate": "~1.0.1" - } - }, - "rimraf": { - "version": "2.6.2", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "glob": "^7.0.5" - } - }, - "safe-buffer": { - "version": "5.1.1", - "bundled": true, - "dev": true - }, - "safer-buffer": { - "version": "2.1.2", - "bundled": true, - "dev": true, - "optional": true - }, - "sax": { - "version": "1.2.4", - "bundled": true, - "dev": true, - "optional": true - }, - "semver": { - "version": "5.5.0", - "bundled": true, - "dev": true, - "optional": true - }, - "set-blocking": { - "version": "2.0.0", - "bundled": true, - "dev": true, - "optional": true - }, - "signal-exit": { - "version": "3.0.2", - "bundled": true, - "dev": true, - "optional": true - }, - "string-width": { - "version": "1.0.2", - "bundled": true, - "dev": true, - "requires": { - "code-point-at": "^1.0.0", - "is-fullwidth-code-point": "^1.0.0", - "strip-ansi": "^3.0.0" - } - }, - "string_decoder": { - "version": "1.1.1", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "safe-buffer": "~5.1.0" - } - }, - "strip-ansi": { - "version": "3.0.1", - "bundled": true, - "dev": true, - "requires": { - "ansi-regex": "^2.0.0" - } - }, - "strip-json-comments": { - "version": "2.0.1", - "bundled": true, - "dev": true, - "optional": true - }, - "tar": { - "version": "4.4.1", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "chownr": "^1.0.1", - "fs-minipass": "^1.2.5", - "minipass": "^2.2.4", - "minizlib": "^1.1.0", - "mkdirp": "^0.5.0", - "safe-buffer": "^5.1.1", - "yallist": "^3.0.2" - } - }, - "util-deprecate": { - "version": "1.0.2", - "bundled": true, - "dev": true, - "optional": true - }, - "wide-align": { - "version": "1.1.2", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "string-width": "^1.0.2" - } - }, - "wrappy": { - "version": "1.0.2", - "bundled": true, - "dev": true - }, - "yallist": { - "version": "3.0.2", - "bundled": true, - "dev": true - } - } - }, - "ganache-cli": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/ganache-cli/-/ganache-cli-6.1.0.tgz", - "integrity": "sha512-FdTeyk4uLRHGeFiMe+Qnh4Hc5KiTVqvRVVvLDFJEVVKC1P1yHhEgZeh9sp1KhuvxSrxToxgJS25UapYQwH4zHw==", - "requires": { - "source-map-support": "^0.5.3", - "webpack-cli": "^2.0.9" - } - }, - "get-caller-file": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/get-caller-file/-/get-caller-file-1.0.2.tgz", - "integrity": "sha1-9wLmMSfn4jHBYKgMFVSstw1QR+U=" - }, - "get-func-name": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/get-func-name/-/get-func-name-2.0.0.tgz", - "integrity": "sha1-6td0q+5y4gQJQzoGY2YCPdaIekE=", - "dev": true - }, - "get-port": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/get-port/-/get-port-3.2.0.tgz", - "integrity": "sha1-3Xzn3hh8Bsi/NTeWrHHgmfCYDrw=", - "dev": true - }, - "get-stream": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-3.0.0.tgz", - "integrity": "sha1-jpQ9E1jcN1VQVOy+LtsFqhdO3hQ=" - }, - "get-value": { - "version": "2.0.6", - "resolved": "https://registry.npmjs.org/get-value/-/get-value-2.0.6.tgz", - "integrity": "sha1-3BXKHGcjh8p2vTesCjlbogQqLCg=", - "dev": true - }, - "getpass": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/getpass/-/getpass-0.1.7.tgz", - "integrity": "sha1-Xv+OPmhNVprkyysSgmBOi6YhSfo=", - "requires": { - "assert-plus": "^1.0.0" - } - }, - "gh-got": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/gh-got/-/gh-got-6.0.0.tgz", - "integrity": "sha512-F/mS+fsWQMo1zfgG9MD8KWvTWPPzzhuVwY++fhQ5Ggd+0P+CAMHtzMZhNxG+TqGfHDChJKsbh6otfMGqO2AKBw==", - "requires": { - "got": "^7.0.0", - "is-plain-obj": "^1.1.0" - }, - "dependencies": { - "got": { - "version": "7.1.0", - "resolved": "https://registry.npmjs.org/got/-/got-7.1.0.tgz", - "integrity": "sha512-Y5WMo7xKKq1muPsxD+KmrR8DH5auG7fBdDVueZwETwV6VytKyU9OX/ddpq2/1hp1vIPvVb4T81dKQz3BivkNLw==", - "requires": { - "decompress-response": "^3.2.0", - "duplexer3": "^0.1.4", - "get-stream": "^3.0.0", - "is-plain-obj": "^1.1.0", - "is-retry-allowed": "^1.0.0", - "is-stream": "^1.0.0", - "isurl": "^1.0.0-alpha5", - "lowercase-keys": "^1.0.0", - "p-cancelable": "^0.3.0", - "p-timeout": "^1.1.1", - "safe-buffer": "^5.0.1", - "timed-out": "^4.0.0", - "url-parse-lax": "^1.0.0", - "url-to-options": "^1.0.1" - } - }, - "p-cancelable": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/p-cancelable/-/p-cancelable-0.3.0.tgz", - "integrity": "sha512-RVbZPLso8+jFeq1MfNvgXtCRED2raz/dKpacfTNxsx6pLEpEomM7gah6VeHSYV3+vo0OAi4MkArtQcWWXuQoyw==" - }, - "p-timeout": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/p-timeout/-/p-timeout-1.2.1.tgz", - "integrity": "sha1-XrOzU7f86Z8QGhA4iAuwVOu+o4Y=", - "requires": { - "p-finally": "^1.0.0" - } - } - } - }, - "github-username": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/github-username/-/github-username-4.1.0.tgz", - "integrity": "sha1-y+KABBiDIG2kISrp5LXxacML9Bc=", - "requires": { - "gh-got": "^6.0.0" - } - }, - "glob": { - "version": "7.1.1", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.1.tgz", - "integrity": "sha1-gFIR3wT6rxxjo2ADBs31reULLsg=", - "requires": { - "fs.realpath": "^1.0.0", - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "^3.0.2", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" - } - }, - "glob-all": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/glob-all/-/glob-all-3.1.0.tgz", - "integrity": "sha1-iRPd+17hrHgSZWJBsD1SF8ZLAqs=", - "requires": { - "glob": "^7.0.5", - "yargs": "~1.2.6" - }, - "dependencies": { - "minimist": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-0.1.0.tgz", - "integrity": "sha1-md9lelJXTCHJBXSX33QnkLK0wN4=" - }, - "yargs": { - "version": "1.2.6", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-1.2.6.tgz", - "integrity": "sha1-nHtKgv1dWVsr8Xq23MQxNUMv40s=", - "requires": { - "minimist": "^0.1.0" - } - } - } - }, - "glob-base": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/glob-base/-/glob-base-0.3.0.tgz", - "integrity": "sha1-27Fk9iIbHAscz4Kuoyi0l98Oo8Q=", - "requires": { - "glob-parent": "^2.0.0", - "is-glob": "^2.0.0" - }, - "dependencies": { - "glob-parent": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-2.0.0.tgz", - "integrity": "sha1-gTg9ctsFT8zPUzbaqQLxgvbtuyg=", - "requires": { - "is-glob": "^2.0.0" - } - }, - "is-extglob": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-1.0.0.tgz", - "integrity": "sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA=" - }, - "is-glob": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-2.0.1.tgz", - "integrity": "sha1-0Jb5JqPe1WAPP9/ZEZjLCIjC2GM=", - "requires": { - "is-extglob": "^1.0.0" - } - } - } - }, - "glob-parent": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-3.1.0.tgz", - "integrity": "sha1-nmr2KZ2NO9K9QEMIMr0RPfkGxa4=", - "dev": true, - "requires": { - "is-glob": "^3.1.0", - "path-dirname": "^1.0.0" - }, - "dependencies": { - "is-glob": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-3.1.0.tgz", - "integrity": "sha1-e6WuJCF4BKxwcHuWkiVnSGzD6Eo=", - "dev": true, - "requires": { - "is-extglob": "^2.1.0" - } - } - } - }, - "global": { - "version": "4.3.2", - "resolved": "https://registry.npmjs.org/global/-/global-4.3.2.tgz", - "integrity": "sha1-52mJJopsdMOJCLEwWxD8DjlOnQ8=", - "requires": { - "min-document": "^2.19.0", - "process": "~0.5.1" - } - }, - "global-dirs": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/global-dirs/-/global-dirs-0.1.1.tgz", - "integrity": "sha1-sxnA3UYH81PzvpzKTHL8FIxJ9EU=", - "dev": true, - "requires": { - "ini": "^1.3.4" - } - }, - "global-modules": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/global-modules/-/global-modules-1.0.0.tgz", - "integrity": "sha512-sKzpEkf11GpOFuw0Zzjzmt4B4UZwjOcG757PPvrfhxcLFbq0wpsgpOqxpxtxFiCG4DtG93M6XRVbF2oGdev7bg==", - "requires": { - "global-prefix": "^1.0.1", - "is-windows": "^1.0.1", - "resolve-dir": "^1.0.0" - } - }, - "global-prefix": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/global-prefix/-/global-prefix-1.0.2.tgz", - "integrity": "sha1-2/dDxsFJklk8ZVVoy2btMsASLr4=", - "requires": { - "expand-tilde": "^2.0.2", - "homedir-polyfill": "^1.0.1", - "ini": "^1.3.4", - "is-windows": "^1.0.1", - "which": "^1.2.14" - } - }, - "globals": { - "version": "9.18.0", - "resolved": "https://registry.npmjs.org/globals/-/globals-9.18.0.tgz", - "integrity": "sha512-S0nG3CLEQiY/ILxqtztTWH/3iRRdyBLw6KMDxnKMchrtbj2OFmehVh0WUCfW3DUrIgx/qFrJPICrq4Z4sTR9UQ==" - }, - "globby": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/globby/-/globby-6.1.0.tgz", - "integrity": "sha1-9abXDoOV4hyFj7BInWTfAkJNUGw=", - "requires": { - "array-union": "^1.0.1", - "glob": "^7.0.3", - "object-assign": "^4.0.1", - "pify": "^2.0.0", - "pinkie-promise": "^2.0.0" - } - }, - "got": { - "version": "6.7.1", - "resolved": "https://registry.npmjs.org/got/-/got-6.7.1.tgz", - "integrity": "sha1-JAzQV4WpoY5WHcG0S0HHY+8ejbA=", - "dev": true, - "requires": { - "create-error-class": "^3.0.0", - "duplexer3": "^0.1.4", - "get-stream": "^3.0.0", - "is-redirect": "^1.0.0", - "is-retry-allowed": "^1.0.0", - "is-stream": "^1.0.0", - "lowercase-keys": "^1.0.0", - "safe-buffer": "^5.0.1", - "timed-out": "^4.0.0", - "unzip-response": "^2.0.1", - "url-parse-lax": "^1.0.0" - } - }, - "graceful-fs": { - "version": "4.1.11", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.11.tgz", - "integrity": "sha1-Dovf5NHduIVNZOBOp8AOKgJuVlg=" - }, - "grouped-queue": { - "version": "0.3.3", - "resolved": "https://registry.npmjs.org/grouped-queue/-/grouped-queue-0.3.3.tgz", - "integrity": "sha1-wWfSpTGcWg4JZO9qJbfC34mWyFw=", - "requires": { - "lodash": "^4.17.2" - } - }, - "growl": { - "version": "1.9.2", - "resolved": "https://registry.npmjs.org/growl/-/growl-1.9.2.tgz", - "integrity": "sha1-Dqd0NxXbjY3ixe3hd14bRayFwC8=", - "dev": true - }, - "handlebars": { - "version": "4.0.11", - "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.0.11.tgz", - "integrity": "sha1-Ywo13+ApS8KB7a5v/F0yn8eYLcw=", - "dev": true, - "requires": { - "async": "^1.4.0", - "optimist": "^0.6.1", - "source-map": "^0.4.4", - "uglify-js": "^2.6" - }, - "dependencies": { - "async": { - "version": "1.5.2", - "resolved": "https://registry.npmjs.org/async/-/async-1.5.2.tgz", - "integrity": "sha1-7GphrlZIDAw8skHJVhjiCJL5Zyo=", - "dev": true - }, - "source-map": { - "version": "0.4.4", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.4.4.tgz", - "integrity": "sha1-66T12pwNyZneaAMti092FzZSA2s=", - "dev": true, - "requires": { - "amdefine": ">=0.0.4" - } - } - } - }, - "har-schema": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/har-schema/-/har-schema-2.0.0.tgz", - "integrity": "sha1-qUwiJOvKwEeCoNkDVSHyRzW37JI=" - }, - "har-validator": { - "version": "5.0.3", - "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-5.0.3.tgz", - "integrity": "sha1-ukAsJmGU8VlW7xXg/PJCmT9qff0=", - "requires": { - "ajv": "^5.1.0", - "har-schema": "^2.0.0" - } - }, - "has-ansi": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/has-ansi/-/has-ansi-2.0.0.tgz", - "integrity": "sha1-NPUEnOHs3ysGSa8+8k5F7TVBbZE=", - "requires": { - "ansi-regex": "^2.0.0" - } - }, - "has-color": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/has-color/-/has-color-0.1.7.tgz", - "integrity": "sha1-ZxRKUmDDT8PMpnfQQdr1L+e3iy8=" - }, - "has-flag": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-1.0.0.tgz", - "integrity": "sha1-nZ55MWXOAXoA8AQYxD+UKnsdEfo=", - "dev": true - }, - "has-symbol-support-x": { - "version": "1.4.2", - "resolved": "https://registry.npmjs.org/has-symbol-support-x/-/has-symbol-support-x-1.4.2.tgz", - "integrity": "sha512-3ToOva++HaW+eCpgqZrCfN51IPB+7bJNVT6CUATzueB5Heb8o6Nam0V3HG5dlDvZU1Gn5QLcbahiKw/XVk5JJw==" - }, - "has-to-string-tag-x": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/has-to-string-tag-x/-/has-to-string-tag-x-1.4.1.tgz", - "integrity": "sha512-vdbKfmw+3LoOYVr+mtxHaX5a96+0f3DljYd8JOqvOLsf5mw2Otda2qCDT9qRqLAhrjyQ0h7ual5nOiASpsGNFw==", - "requires": { - "has-symbol-support-x": "^1.4.1" - } - }, - "has-value": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/has-value/-/has-value-1.0.0.tgz", - "integrity": "sha1-GLKB2lhbHFxR3vJMkw7SmgvmsXc=", - "dev": true, - "requires": { - "get-value": "^2.0.6", - "has-values": "^1.0.0", - "isobject": "^3.0.0" - } - }, - "has-values": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/has-values/-/has-values-1.0.0.tgz", - "integrity": "sha1-lbC2P+whRmGab+V/51Yo1aOe/k8=", - "dev": true, - "requires": { - "is-number": "^3.0.0", - "kind-of": "^4.0.0" - }, - "dependencies": { - "kind-of": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-4.0.0.tgz", - "integrity": "sha1-IIE989cSkosgc3hpGkUGb65y3Vc=", - "dev": true, - "requires": { - "is-buffer": "^1.1.5" - } - } - } - }, - "hash.js": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/hash.js/-/hash.js-1.1.3.tgz", - "integrity": "sha512-/UETyP0W22QILqS+6HowevwhEFJ3MBJnwTf75Qob9Wz9t0DPuisL8kW8YZMK62dHAKE1c1p+gY1TtOLY+USEHA==", - "requires": { - "inherits": "^2.0.3", - "minimalistic-assert": "^1.0.0" - } - }, - "hawk": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/hawk/-/hawk-6.0.2.tgz", - "integrity": "sha512-miowhl2+U7Qle4vdLqDdPt9m09K6yZhkLDTWGoUiUzrQCn+mHHSmfJgAyGaLRZbPmTqfFFjRV1QWCW0VWUJBbQ==", - "requires": { - "boom": "4.x.x", - "cryptiles": "3.x.x", - "hoek": "4.x.x", - "sntp": "2.x.x" - } - }, - "he": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/he/-/he-1.1.1.tgz", - "integrity": "sha1-k0EP0hsAlzUVH4howvJx80J+I/0=" - }, - "hmac-drbg": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/hmac-drbg/-/hmac-drbg-1.0.1.tgz", - "integrity": "sha1-0nRXAQJabHdabFRXk+1QL8DGSaE=", - "requires": { - "hash.js": "^1.0.3", - "minimalistic-assert": "^1.0.0", - "minimalistic-crypto-utils": "^1.0.1" - } - }, - "hoek": { - "version": "4.2.1", - "resolved": "https://registry.npmjs.org/hoek/-/hoek-4.2.1.tgz", - "integrity": "sha512-QLg82fGkfnJ/4iy1xZ81/9SIJiq1NGFUMGs6ParyjBZr6jW2Ufj/snDqTHixNlHdPNwN2RLVD0Pi3igeK9+JfA==" - }, - "home-or-tmp": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/home-or-tmp/-/home-or-tmp-2.0.0.tgz", - "integrity": "sha1-42w/LSyufXRqhX440Y1fMqeILbg=", - "requires": { - "os-homedir": "^1.0.0", - "os-tmpdir": "^1.0.1" - } - }, - "homedir-polyfill": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/homedir-polyfill/-/homedir-polyfill-1.0.1.tgz", - "integrity": "sha1-TCu8inWJmP7r9e1oWA921GdotLw=", - "requires": { - "parse-passwd": "^1.0.0" - } - }, - "hosted-git-info": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-2.5.0.tgz", - "integrity": "sha512-pNgbURSuab90KbTqvRPsseaTxOJCZBD0a7t+haSN33piP9cCM4l0CqdzAif2hUqm716UovKB2ROmiabGAKVXyg==" - }, - "http-basic": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/http-basic/-/http-basic-7.0.0.tgz", - "integrity": "sha1-gvClBr6UJzLsje6+6A50bvVzbbo=", - "dev": true, - "requires": { - "@types/concat-stream": "^1.6.0", - "@types/node": "^9.4.1", - "caseless": "~0.12.0", - "concat-stream": "^1.4.6", - "http-response-object": "^3.0.1", - "parse-cache-control": "^1.0.1" - } - }, - "http-cache-semantics": { - "version": "3.8.1", - "resolved": "https://registry.npmjs.org/http-cache-semantics/-/http-cache-semantics-3.8.1.tgz", - "integrity": "sha512-5ai2iksyV8ZXmnZhHH4rWPoxxistEexSi5936zIQ1bnNTW5VnA85B6P/VpXiRM017IgRvb2kKo1a//y+0wSp3w==" - }, - "http-errors": { - "version": "1.6.3", - "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.6.3.tgz", - "integrity": "sha1-i1VoC7S+KDoLW/TqLjhYC+HZMg0=", - "requires": { - "depd": "~1.1.2", - "inherits": "2.0.3", - "setprototypeof": "1.1.0", - "statuses": ">= 1.4.0 < 2" - } - }, - "http-response-object": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/http-response-object/-/http-response-object-3.0.1.tgz", - "integrity": "sha512-6L0Fkd6TozA8kFSfh9Widst0wfza3U1Ex2RjJ6zNDK0vR1U1auUR6jY4Nn2Xl7CCy0ikFmxW1XcspVpb9RvwTg==", - "dev": true, - "requires": { - "@types/node": "^9.3.0" - } - }, - "http-signature": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/http-signature/-/http-signature-1.2.0.tgz", - "integrity": "sha1-muzZJRFHcvPZW2WmCruPfBj7rOE=", - "requires": { - "assert-plus": "^1.0.0", - "jsprim": "^1.2.2", - "sshpk": "^1.7.0" - } - }, - "iconv-lite": { - "version": "0.4.19", - "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.19.tgz", - "integrity": "sha512-oTZqweIP51xaGPI4uPa56/Pri/480R+mo7SeU+YETByQNhDG55ycFyNLIgta9vXhILrxXDmF7ZGhqZIcuN0gJQ==" - }, - "ignore-by-default": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/ignore-by-default/-/ignore-by-default-1.0.1.tgz", - "integrity": "sha1-SMptcvbGo68Aqa1K5odr44ieKwk=", - "dev": true - }, - "import-lazy": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/import-lazy/-/import-lazy-2.1.0.tgz", - "integrity": "sha1-BWmOPUXIjo1+nZLLBYTnfwlvPkM=", - "dev": true - }, - "imurmurhash": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/imurmurhash/-/imurmurhash-0.1.4.tgz", - "integrity": "sha1-khi5srkoojixPcT7a21XbyMUU+o=" - }, - "indent-string": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/indent-string/-/indent-string-2.1.0.tgz", - "integrity": "sha1-ji1INIdCEhtKghi3oTfppSBJ3IA=", - "requires": { - "repeating": "^2.0.0" - } - }, - "inflight": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", - "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=", - "requires": { - "once": "^1.3.0", - "wrappy": "1" - } - }, - "inherits": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=" - }, - "ini": { - "version": "1.3.5", - "resolved": "https://registry.npmjs.org/ini/-/ini-1.3.5.tgz", - "integrity": "sha512-RZY5huIKCMRWDUqZlEi72f/lmXKMvuszcMBduliQ3nnWbx9X/ZBQO7DijMEYS9EhHBb2qacRUMtC7svLwe0lcw==" - }, - "inquirer": { - "version": "5.2.0", - "resolved": "https://registry.npmjs.org/inquirer/-/inquirer-5.2.0.tgz", - "integrity": "sha512-E9BmnJbAKLPGonz0HeWHtbKf+EeSP93paWO3ZYoUpq/aowXvYGjjCSuashhXPpzbArIjBbji39THkxTz9ZeEUQ==", - "requires": { - "ansi-escapes": "^3.0.0", - "chalk": "^2.0.0", - "cli-cursor": "^2.1.0", - "cli-width": "^2.0.0", - "external-editor": "^2.1.0", - "figures": "^2.0.0", - "lodash": "^4.3.0", - "mute-stream": "0.0.7", - "run-async": "^2.2.0", - "rxjs": "^5.5.2", - "string-width": "^2.1.0", - "strip-ansi": "^4.0.0", - "through": "^2.3.6" - }, - "dependencies": { - "ansi-regex": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", - "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=" - }, - "is-fullwidth-code-point": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", - "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=" - }, - "string-width": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", - "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", - "requires": { - "is-fullwidth-code-point": "^2.0.0", - "strip-ansi": "^4.0.0" - } - }, - "strip-ansi": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", - "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", - "requires": { - "ansi-regex": "^3.0.0" - } - } - } - }, - "interpret": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/interpret/-/interpret-1.1.0.tgz", - "integrity": "sha1-ftGxQQxqDg94z5XTuEQMY/eLhhQ=" - }, - "into-stream": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/into-stream/-/into-stream-3.1.0.tgz", - "integrity": "sha1-lvsKk2wSur1v8XUqF9BWFqvQlMY=", - "requires": { - "from2": "^2.1.1", - "p-is-promise": "^1.1.0" - } - }, - "invariant": { - "version": "2.2.4", - "resolved": "https://registry.npmjs.org/invariant/-/invariant-2.2.4.tgz", - "integrity": "sha512-phJfQVBuaJM5raOpJjSfkiD6BpbCE4Ns//LaXl6wGYtUBY83nWS6Rf9tXm2e8VaK60JEjYldbPif/A2B1C2gNA==", - "requires": { - "loose-envify": "^1.0.0" - } - }, - "invert-kv": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/invert-kv/-/invert-kv-1.0.0.tgz", - "integrity": "sha1-EEqOSqym09jNFXqO+L+rLXo//bY=" - }, - "ipaddr.js": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.6.0.tgz", - "integrity": "sha1-4/o1e3c9phnybpXwSdBVxyeW+Gs=" - }, - "is-accessor-descriptor": { - "version": "0.1.6", - "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-0.1.6.tgz", - "integrity": "sha1-qeEss66Nh2cn7u84Q/igiXtcmNY=", - "dev": true, - "requires": { - "kind-of": "^3.0.2" - }, - "dependencies": { - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", - "dev": true, - "requires": { - "is-buffer": "^1.1.5" - } - } - } - }, - "is-arrayish": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/is-arrayish/-/is-arrayish-0.2.1.tgz", - "integrity": "sha1-d8mYQFJ6qOyxqLppe4BkWnqSap0=" - }, - "is-binary-path": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-binary-path/-/is-binary-path-1.0.1.tgz", - "integrity": "sha1-dfFmQrSA8YenEcgUFh/TpKdlWJg=", - "dev": true, - "requires": { - "binary-extensions": "^1.0.0" - } - }, - "is-buffer": { - "version": "1.1.6", - "resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-1.1.6.tgz", - "integrity": "sha512-NcdALwpXkTm5Zvvbk7owOUSvVvBKDgKP5/ewfXEznmQFfs4ZRmanOeKBTjRVjka3QFoN6XJ+9F3USqfHqTaU5w==" - }, - "is-builtin-module": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-builtin-module/-/is-builtin-module-1.0.0.tgz", - "integrity": "sha1-VAVy0096wxGfj3bDDLwbHgN6/74=", - "requires": { - "builtin-modules": "^1.0.0" - } - }, - "is-ci": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/is-ci/-/is-ci-1.1.0.tgz", - "integrity": "sha512-c7TnwxLePuqIlxHgr7xtxzycJPegNHFuIrBkwbf8hc58//+Op1CqFkyS+xnIMkwn9UsJIwc174BIjkyBmSpjKg==", - "dev": true, - "requires": { - "ci-info": "^1.0.0" - } - }, - "is-data-descriptor": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-0.1.4.tgz", - "integrity": "sha1-C17mSDiOLIYCgueT8YVv7D8wG1Y=", - "dev": true, - "requires": { - "kind-of": "^3.0.2" - }, - "dependencies": { - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", - "dev": true, - "requires": { - "is-buffer": "^1.1.5" - } - } - } - }, - "is-descriptor": { - "version": "0.1.6", - "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-0.1.6.tgz", - "integrity": "sha512-avDYr0SB3DwO9zsMov0gKCESFYqCnE4hq/4z3TdUlukEy5t9C0YRq7HLrsN52NAcqXKaepeCD0n+B0arnVG3Hg==", - "dev": true, - "requires": { - "is-accessor-descriptor": "^0.1.6", - "is-data-descriptor": "^0.1.4", - "kind-of": "^5.0.0" - }, - "dependencies": { - "kind-of": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-5.1.0.tgz", - "integrity": "sha512-NGEErnH6F2vUuXDh+OlbcKW7/wOcfdRHaZ7VWtqCztfHri/++YKmP51OdWeGPuqCOba6kk2OTe5d02VmTB80Pw==", - "dev": true - } - } - }, - "is-dotfile": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/is-dotfile/-/is-dotfile-1.0.3.tgz", - "integrity": "sha1-pqLzL/0t+wT1yiXs0Pa4PPeYoeE=" - }, - "is-equal-shallow": { - "version": "0.1.3", - "resolved": "https://registry.npmjs.org/is-equal-shallow/-/is-equal-shallow-0.1.3.tgz", - "integrity": "sha1-IjgJj8Ih3gvPpdnqxMRdY4qhxTQ=", - "requires": { - "is-primitive": "^2.0.0" - } - }, - "is-extendable": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-0.1.1.tgz", - "integrity": "sha1-YrEQ4omkcUGOPsNqYX1HLjAd/Ik=" - }, - "is-extglob": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", - "integrity": "sha1-qIwCU1eR8C7TfHahueqXc8gz+MI=", - "dev": true - }, - "is-finite": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/is-finite/-/is-finite-1.0.2.tgz", - "integrity": "sha1-zGZ3aVYCvlUO8R6LSqYwU0K20Ko=", - "requires": { - "number-is-nan": "^1.0.0" - } - }, - "is-fullwidth-code-point": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz", - "integrity": "sha1-754xOG8DGn8NZDr4L95QxFfvAMs=", - "requires": { - "number-is-nan": "^1.0.0" - } - }, - "is-function": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-function/-/is-function-1.0.1.tgz", - "integrity": "sha1-Es+5i2W1fdPRk6MSH19uL0N2ArU=" - }, - "is-glob": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.0.tgz", - "integrity": "sha1-lSHHaEXMJhCoUgPd8ICpWML/q8A=", - "dev": true, - "requires": { - "is-extglob": "^2.1.1" - } - }, - "is-hex-prefixed": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-hex-prefixed/-/is-hex-prefixed-1.0.0.tgz", - "integrity": "sha1-fY035q135dEnFIkTxXPggtd39VQ=" - }, - "is-installed-globally": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/is-installed-globally/-/is-installed-globally-0.1.0.tgz", - "integrity": "sha1-Df2Y9akRFxbdU13aZJL2e/PSWoA=", - "dev": true, - "requires": { - "global-dirs": "^0.1.0", - "is-path-inside": "^1.0.0" - } - }, - "is-npm": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-npm/-/is-npm-1.0.0.tgz", - "integrity": "sha1-8vtjpl5JBbQGyGBydloaTceTufQ=", - "dev": true - }, - "is-number": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/is-number/-/is-number-3.0.0.tgz", - "integrity": "sha1-JP1iAaR4LPUFYcgQJ2r8fRLXEZU=", - "requires": { - "kind-of": "^3.0.2" - }, - "dependencies": { - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", - "requires": { - "is-buffer": "^1.1.5" - } - } - } - }, - "is-obj": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-obj/-/is-obj-1.0.1.tgz", - "integrity": "sha1-PkcprB9f3gJc19g6iW2rn09n2w8=", - "dev": true - }, - "is-object": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-object/-/is-object-1.0.1.tgz", - "integrity": "sha1-iVJojF7C/9awPsyF52ngKQMINHA=" - }, - "is-observable": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/is-observable/-/is-observable-0.2.0.tgz", - "integrity": "sha1-s2ExHYPG5dcmyr9eJQsCNxBvWuI=", - "requires": { - "symbol-observable": "^0.2.2" - }, - "dependencies": { - "symbol-observable": { - "version": "0.2.4", - "resolved": "https://registry.npmjs.org/symbol-observable/-/symbol-observable-0.2.4.tgz", - "integrity": "sha1-lag9smGG1q9+ehjb2XYKL4bQj0A=" - } - } - }, - "is-odd": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-odd/-/is-odd-2.0.0.tgz", - "integrity": "sha512-OTiixgpZAT1M4NHgS5IguFp/Vz2VI3U7Goh4/HA1adtwyLtSBrxYlcSYkhpAE07s4fKEcjrFxyvtQBND4vFQyQ==", - "dev": true, - "requires": { - "is-number": "^4.0.0" - }, - "dependencies": { - "is-number": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/is-number/-/is-number-4.0.0.tgz", - "integrity": "sha512-rSklcAIlf1OmFdyAqbnWTLVelsQ58uvZ66S/ZyawjWqIviTWCjg2PzVGw8WUA+nNuPTqb4wgA+NszrJ+08LlgQ==", - "dev": true - } - } - }, - "is-path-inside": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-path-inside/-/is-path-inside-1.0.1.tgz", - "integrity": "sha1-jvW33lBDej/cprToZe96pVy0gDY=", - "dev": true, - "requires": { - "path-is-inside": "^1.0.1" - } - }, - "is-plain-obj": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-1.1.0.tgz", - "integrity": "sha1-caUMhCnfync8kqOQpKA7OfzVHT4=" - }, - "is-plain-object": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/is-plain-object/-/is-plain-object-2.0.4.tgz", - "integrity": "sha512-h5PpgXkWitc38BBMYawTYMWJHFZJVnBquFE57xFpjB8pJFiF6gZ+bU+WyI/yqXiFR5mdLsgYNaPe8uao6Uv9Og==", - "dev": true, - "requires": { - "isobject": "^3.0.1" - } - }, - "is-posix-bracket": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/is-posix-bracket/-/is-posix-bracket-0.1.1.tgz", - "integrity": "sha1-MzTceXdDaOkvAW5vvAqI9c1ua8Q=" - }, - "is-primitive": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-primitive/-/is-primitive-2.0.0.tgz", - "integrity": "sha1-IHurkWOEmcB7Kt8kCkGochADRXU=" - }, - "is-promise": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/is-promise/-/is-promise-2.1.0.tgz", - "integrity": "sha1-eaKp7OfwlugPNtKy87wWwf9L8/o=" - }, - "is-redirect": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-redirect/-/is-redirect-1.0.0.tgz", - "integrity": "sha1-HQPd7VO9jbDzDCbk+V02/HyH3CQ=", - "dev": true - }, - "is-retry-allowed": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/is-retry-allowed/-/is-retry-allowed-1.1.0.tgz", - "integrity": "sha1-EaBgVotnM5REAz0BJaYaINVk+zQ=" - }, - "is-scoped": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-scoped/-/is-scoped-1.0.0.tgz", - "integrity": "sha1-RJypgpnnEwOCViieyytUDcQ3yzA=", - "requires": { - "scoped-regex": "^1.0.0" - } - }, - "is-stream": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-1.1.0.tgz", - "integrity": "sha1-EtSj3U5o4Lec6428hBc66A2RykQ=" - }, - "is-typedarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-typedarray/-/is-typedarray-1.0.0.tgz", - "integrity": "sha1-5HnICFjfDBsR3dppQPlgEfzaSpo=" - }, - "is-utf8": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/is-utf8/-/is-utf8-0.2.1.tgz", - "integrity": "sha1-Sw2hRCEE0bM2NA6AeX6GXPOffXI=" - }, - "is-windows": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/is-windows/-/is-windows-1.0.2.tgz", - "integrity": "sha512-eXK1UInq2bPmjyX6e3VHIzMLobc4J94i4AWn+Hpq3OU5KkrRC96OAcR3PRJ/pGu6m8TRnBHP9dkXQVsT/COVIA==" - }, - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=" - }, - "isexe": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", - "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=" - }, - "isobject": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", - "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=", - "dev": true - }, - "isstream": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/isstream/-/isstream-0.1.2.tgz", - "integrity": "sha1-R+Y/evVa+m+S4VAOaQ64uFKcCZo=" - }, - "istanbul": { - "version": "0.4.5", - "resolved": "https://registry.npmjs.org/istanbul/-/istanbul-0.4.5.tgz", - "integrity": "sha1-ZcfXPUxNqE1POsMQuRj7C4Azczs=", - "dev": true, - "requires": { - "abbrev": "1.0.x", - "async": "1.x", - "escodegen": "1.8.x", - "esprima": "2.7.x", - "glob": "^5.0.15", - "handlebars": "^4.0.1", - "js-yaml": "3.x", - "mkdirp": "0.5.x", - "nopt": "3.x", - "once": "1.x", - "resolve": "1.1.x", - "supports-color": "^3.1.0", - "which": "^1.1.1", - "wordwrap": "^1.0.0" - }, - "dependencies": { - "abbrev": { - "version": "1.0.9", - "resolved": "https://registry.npmjs.org/abbrev/-/abbrev-1.0.9.tgz", - "integrity": "sha1-kbR5JYinc4wl813W9jdSovh3YTU=", - "dev": true - }, - "async": { - "version": "1.5.2", - "resolved": "https://registry.npmjs.org/async/-/async-1.5.2.tgz", - "integrity": "sha1-7GphrlZIDAw8skHJVhjiCJL5Zyo=", - "dev": true - }, - "esprima": { - "version": "2.7.3", - "resolved": "https://registry.npmjs.org/esprima/-/esprima-2.7.3.tgz", - "integrity": "sha1-luO3DVd59q1JzQMmc9HDEnZ7pYE=", - "dev": true }, "glob": { - "version": "5.0.15", - "resolved": "https://registry.npmjs.org/glob/-/glob-5.0.15.tgz", - "integrity": "sha1-G8k2ueAvSmA/zCIuz3Yz0wuLk7E=", + "version": "7.1.3", + "bundled": true, "dev": true, + "optional": true, "requires": { + "fs.realpath": "^1.0.0", "inflight": "^1.0.4", "inherits": "2", - "minimatch": "2 || 3", + "minimatch": "^3.0.4", "once": "^1.3.0", "path-is-absolute": "^1.0.0" } }, - "nopt": { - "version": "3.0.6", - "resolved": "https://registry.npmjs.org/nopt/-/nopt-3.0.6.tgz", - "integrity": "sha1-xkZdvwirzU2zWTF/eaxopkayj/k=", + "has-unicode": { + "version": "2.0.1", + "bundled": true, + "dev": true, + "optional": true + }, + "iconv-lite": { + "version": "0.4.24", + "bundled": true, + "dev": true, + "optional": true, + "requires": { + "safer-buffer": ">= 2.1.2 < 3" + } + }, + "ignore-walk": { + "version": "3.0.1", + "bundled": true, "dev": true, + "optional": true, "requires": { - "abbrev": "1" + "minimatch": "^3.0.4" } }, - "resolve": { - "version": "1.1.7", - "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.1.7.tgz", - "integrity": "sha1-IDEU2CrSxe2ejgQRs5ModeiJ6Xs=", + "inflight": { + "version": "1.0.6", + "bundled": true, + "dev": true, + "optional": true, + "requires": { + "once": "^1.3.0", + "wrappy": "1" + } + }, + "inherits": { + "version": "2.0.3", + "bundled": true, "dev": true - } - } - }, - "istextorbinary": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/istextorbinary/-/istextorbinary-2.2.1.tgz", - "integrity": "sha512-TS+hoFl8Z5FAFMK38nhBkdLt44CclNRgDHWeMgsV8ko3nDlr/9UI2Sf839sW7enijf8oKsZYXRvM8g0it9Zmcw==", - "requires": { - "binaryextensions": "2", - "editions": "^1.3.3", - "textextensions": "2" - } - }, - "isurl": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isurl/-/isurl-1.0.0.tgz", - "integrity": "sha512-1P/yWsxPlDtn7QeRD+ULKQPaIaN6yF368GZ2vDfv0AL0NwpStafjWCDDdn0k8wgFMWpVAqG7oJhxHnlud42i9w==", - "requires": { - "has-to-string-tag-x": "^1.2.0", - "is-object": "^1.0.1" - } - }, - "jade": { - "version": "0.26.3", - "resolved": "https://registry.npmjs.org/jade/-/jade-0.26.3.tgz", - "integrity": "sha1-jxDXl32NefL2/4YqgbBRPMslaGw=", - "dev": true, - "requires": { - "commander": "0.6.1", - "mkdirp": "0.3.0" - }, - "dependencies": { - "commander": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/commander/-/commander-0.6.1.tgz", - "integrity": "sha1-+mihT2qUXVTbvlDYzbMyDp47GgY=", + }, + "ini": { + "version": "1.3.5", + "bundled": true, + "dev": true, + "optional": true + }, + "is-fullwidth-code-point": { + "version": "1.0.0", + "bundled": true, + "dev": true, + "requires": { + "number-is-nan": "^1.0.0" + } + }, + "isarray": { + "version": "1.0.0", + "bundled": true, + "dev": true, + "optional": true + }, + "minimatch": { + "version": "3.0.4", + "bundled": true, + "dev": true, + "requires": { + "brace-expansion": "^1.1.7" + } + }, + "minimist": { + "version": "0.0.8", + "bundled": true, "dev": true }, + "minipass": { + "version": "2.3.5", + "bundled": true, + "dev": true, + "requires": { + "safe-buffer": "^5.1.2", + "yallist": "^3.0.0" + } + }, + "minizlib": { + "version": "1.2.1", + "bundled": true, + "dev": true, + "optional": true, + "requires": { + "minipass": "^2.2.1" + } + }, "mkdirp": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.3.0.tgz", - "integrity": "sha1-G79asbqCevI1dRQ0kEJkVfSB/h4=", - "dev": true - } - } - }, - "js-sha3": { - "version": "0.5.5", - "resolved": "https://registry.npmjs.org/js-sha3/-/js-sha3-0.5.5.tgz", - "integrity": "sha1-uvDA6MVK1ZA0R9+Wreekobynmko=", - "dev": true - }, - "js-tokens": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-3.0.2.tgz", - "integrity": "sha1-mGbfOVECEw449/mWvOtlRDIJwls=" - }, - "js-yaml": { - "version": "3.11.0", - "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.11.0.tgz", - "integrity": "sha512-saJstZWv7oNeOyBh3+Dx1qWzhW0+e6/8eDzo7p5rDFqxntSztloLtuKu+Ejhtq82jsilwOIZYsCz+lIjthg1Hw==", - "dev": true, - "requires": { - "argparse": "^1.0.7", - "esprima": "^4.0.0" - } - }, - "jsbn": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/jsbn/-/jsbn-0.1.1.tgz", - "integrity": "sha1-peZUwuWi3rXyAdls77yoDA7y9RM=", - "optional": true - }, - "jscodeshift": { - "version": "0.5.0", - "resolved": "https://registry.npmjs.org/jscodeshift/-/jscodeshift-0.5.0.tgz", - "integrity": "sha512-JAcQINNMFpdzzpKJN8k5xXjF3XDuckB1/48uScSzcnNyK199iWEc9AxKL9OoX5144M2w5zEx9Qs4/E/eBZZUlw==", - "requires": { - "babel-plugin-transform-flow-strip-types": "^6.8.0", - "babel-preset-es2015": "^6.9.0", - "babel-preset-stage-1": "^6.5.0", - "babel-register": "^6.9.0", - "babylon": "^7.0.0-beta.30", - "colors": "^1.1.2", - "flow-parser": "^0.*", - "lodash": "^4.13.1", - "micromatch": "^2.3.7", - "neo-async": "^2.5.0", - "node-dir": "0.1.8", - "nomnom": "^1.8.1", - "recast": "^0.14.1", - "temp": "^0.8.1", - "write-file-atomic": "^1.2.0" - }, - "dependencies": { - "arr-diff": { + "version": "0.5.1", + "bundled": true, + "dev": true, + "requires": { + "minimist": "0.0.8" + } + }, + "ms": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/arr-diff/-/arr-diff-2.0.0.tgz", - "integrity": "sha1-jzuCf5Vai9ZpaX5KQlasPOrjVs8=", + "bundled": true, + "dev": true, + "optional": true + }, + "needle": { + "version": "2.2.4", + "bundled": true, + "dev": true, + "optional": true, + "requires": { + "debug": "^2.1.2", + "iconv-lite": "^0.4.4", + "sax": "^1.2.4" + } + }, + "node-pre-gyp": { + "version": "0.10.3", + "bundled": true, + "dev": true, + "optional": true, + "requires": { + "detect-libc": "^1.0.2", + "mkdirp": "^0.5.1", + "needle": "^2.2.1", + "nopt": "^4.0.1", + "npm-packlist": "^1.1.6", + "npmlog": "^4.0.2", + "rc": "^1.2.7", + "rimraf": "^2.6.1", + "semver": "^5.3.0", + "tar": "^4" + } + }, + "nopt": { + "version": "4.0.1", + "bundled": true, + "dev": true, + "optional": true, + "requires": { + "abbrev": "1", + "osenv": "^0.1.4" + } + }, + "npm-bundled": { + "version": "1.0.5", + "bundled": true, + "dev": true, + "optional": true + }, + "npm-packlist": { + "version": "1.2.0", + "bundled": true, + "dev": true, + "optional": true, "requires": { - "arr-flatten": "^1.0.1" + "ignore-walk": "^3.0.1", + "npm-bundled": "^1.0.1" + } + }, + "npmlog": { + "version": "4.1.2", + "bundled": true, + "dev": true, + "optional": true, + "requires": { + "are-we-there-yet": "~1.1.2", + "console-control-strings": "~1.1.0", + "gauge": "~2.7.3", + "set-blocking": "~2.0.0" + } + }, + "number-is-nan": { + "version": "1.0.1", + "bundled": true, + "dev": true + }, + "object-assign": { + "version": "4.1.1", + "bundled": true, + "dev": true, + "optional": true + }, + "once": { + "version": "1.4.0", + "bundled": true, + "dev": true, + "requires": { + "wrappy": "1" + } + }, + "os-homedir": { + "version": "1.0.2", + "bundled": true, + "dev": true, + "optional": true + }, + "os-tmpdir": { + "version": "1.0.2", + "bundled": true, + "dev": true, + "optional": true + }, + "osenv": { + "version": "0.1.5", + "bundled": true, + "dev": true, + "optional": true, + "requires": { + "os-homedir": "^1.0.0", + "os-tmpdir": "^1.0.0" } }, - "array-unique": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/array-unique/-/array-unique-0.2.1.tgz", - "integrity": "sha1-odl8yvy8JiXMcPrc6zalDFiwGlM=" + "path-is-absolute": { + "version": "1.0.1", + "bundled": true, + "dev": true, + "optional": true + }, + "process-nextick-args": { + "version": "2.0.0", + "bundled": true, + "dev": true, + "optional": true }, - "braces": { - "version": "1.8.5", - "resolved": "https://registry.npmjs.org/braces/-/braces-1.8.5.tgz", - "integrity": "sha1-uneWLhLf+WnWt2cR6RS3N4V79qc=", + "rc": { + "version": "1.2.8", + "bundled": true, + "dev": true, + "optional": true, "requires": { - "expand-range": "^1.8.1", - "preserve": "^0.2.0", - "repeat-element": "^1.1.2" + "deep-extend": "^0.6.0", + "ini": "~1.3.0", + "minimist": "^1.2.0", + "strip-json-comments": "~2.0.1" + }, + "dependencies": { + "minimist": { + "version": "1.2.0", + "bundled": true, + "dev": true, + "optional": true + } } }, - "expand-brackets": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/expand-brackets/-/expand-brackets-0.1.5.tgz", - "integrity": "sha1-3wcoTjQqgHzXM6xa9yQR5YHRF3s=", + "readable-stream": { + "version": "2.3.6", + "bundled": true, + "dev": true, + "optional": true, "requires": { - "is-posix-bracket": "^0.1.0" + "core-util-is": "~1.0.0", + "inherits": "~2.0.3", + "isarray": "~1.0.0", + "process-nextick-args": "~2.0.0", + "safe-buffer": "~5.1.1", + "string_decoder": "~1.1.1", + "util-deprecate": "~1.0.1" } }, - "extglob": { - "version": "0.3.2", - "resolved": "https://registry.npmjs.org/extglob/-/extglob-0.3.2.tgz", - "integrity": "sha1-Lhj/PS9JqydlzskCPwEdqo2DSaE=", + "rimraf": { + "version": "2.6.3", + "bundled": true, + "dev": true, + "optional": true, "requires": { - "is-extglob": "^1.0.0" + "glob": "^7.1.3" } }, - "is-extglob": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-1.0.0.tgz", - "integrity": "sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA=" + "safe-buffer": { + "version": "5.1.2", + "bundled": true, + "dev": true }, - "is-glob": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-2.0.1.tgz", - "integrity": "sha1-0Jb5JqPe1WAPP9/ZEZjLCIjC2GM=", - "requires": { - "is-extglob": "^1.0.0" - } + "safer-buffer": { + "version": "2.1.2", + "bundled": true, + "dev": true, + "optional": true }, - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", - "requires": { - "is-buffer": "^1.1.5" - } + "sax": { + "version": "1.2.4", + "bundled": true, + "dev": true, + "optional": true }, - "micromatch": { - "version": "2.3.11", - "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-2.3.11.tgz", - "integrity": "sha1-hmd8l9FyCzY0MdBNDRUpO9OMFWU=", - "requires": { - "arr-diff": "^2.0.0", - "array-unique": "^0.2.1", - "braces": "^1.8.2", - "expand-brackets": "^0.1.4", - "extglob": "^0.3.1", - "filename-regex": "^2.0.0", - "is-extglob": "^1.0.0", - "is-glob": "^2.0.1", - "kind-of": "^3.0.2", - "normalize-path": "^2.0.1", - "object.omit": "^2.0.0", - "parse-glob": "^3.0.4", - "regex-cache": "^0.4.2" - } + "semver": { + "version": "5.6.0", + "bundled": true, + "dev": true, + "optional": true }, - "write-file-atomic": { - "version": "1.3.4", - "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-1.3.4.tgz", - "integrity": "sha1-+Aek8LHZ6ROuekgRLmzDrxmRtF8=", - "requires": { - "graceful-fs": "^4.1.11", - "imurmurhash": "^0.1.4", - "slide": "^1.1.5" - } - } - } - }, - "jsesc": { - "version": "0.5.0", - "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-0.5.0.tgz", - "integrity": "sha1-597mbjXW/Bb3EP6R1c9p9w8IkR0=" - }, - "json-buffer": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/json-buffer/-/json-buffer-3.0.0.tgz", - "integrity": "sha1-Wx85evx11ne96Lz8Dkfh+aPZqJg=" - }, - "json-parse-better-errors": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/json-parse-better-errors/-/json-parse-better-errors-1.0.1.tgz", - "integrity": "sha512-xyQpxeWWMKyJps9CuGJYeng6ssI5bpqS9ltQpdVQ90t4ql6NdnxFKh95JcRt2cun/DjMVNrdjniLPuMA69xmCw==" - }, - "json-schema": { - "version": "0.2.3", - "resolved": "https://registry.npmjs.org/json-schema/-/json-schema-0.2.3.tgz", - "integrity": "sha1-tIDIkuWaLwWVTOcnvT8qTogvnhM=" - }, - "json-schema-traverse": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.3.1.tgz", - "integrity": "sha1-NJptRMU6Ud6JtAgFxdXlm0F9M0A=" - }, - "json-stringify-safe": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/json-stringify-safe/-/json-stringify-safe-5.0.1.tgz", - "integrity": "sha1-Epai1Y/UXxmg9s4B1lcB4sc1tus=" - }, - "json5": { - "version": "0.5.1", - "resolved": "https://registry.npmjs.org/json5/-/json5-0.5.1.tgz", - "integrity": "sha1-Hq3nrMASA0rYTiOWdn6tn6VJWCE=" - }, - "jsonfile": { - "version": "2.4.0", - "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-2.4.0.tgz", - "integrity": "sha1-NzaitCi4e72gzIO1P6PWM6NcKug=", - "requires": { - "graceful-fs": "^4.1.6" - } - }, - "jsprim": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/jsprim/-/jsprim-1.4.1.tgz", - "integrity": "sha1-MT5mvB5cwG5Di8G3SZwuXFastqI=", - "requires": { - "assert-plus": "1.0.0", - "extsprintf": "1.3.0", - "json-schema": "0.2.3", - "verror": "1.10.0" - } - }, - "keccakjs": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/keccakjs/-/keccakjs-0.2.1.tgz", - "integrity": "sha1-HWM6+QfvMFu/ny+mFtVsRFYd+k0=", - "requires": { - "browserify-sha3": "^0.0.1", - "sha3": "^1.1.0" - } - }, - "keyv": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/keyv/-/keyv-3.0.0.tgz", - "integrity": "sha512-eguHnq22OE3uVoSYG0LVWNP+4ppamWr9+zWBe1bsNcovIMy6huUJFPgy4mGwCd/rnl3vOLGW1MTlu4c57CT1xA==", - "requires": { - "json-buffer": "3.0.0" - } - }, - "kind-of": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-6.0.2.tgz", - "integrity": "sha512-s5kLOcnH0XqDO+FvuaLX8DDjZ18CGFk7VygH40QoKPUQhW4e2rvM0rwUq0t8IQDOwYSeLK01U90OjzBTme2QqA==", - "dev": true - }, - "klaw": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/klaw/-/klaw-1.3.1.tgz", - "integrity": "sha1-QIhDO0azsbolnXh4XY6W9zugJDk=", - "requires": { - "graceful-fs": "^4.1.9" - } - }, - "latest-version": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/latest-version/-/latest-version-3.1.0.tgz", - "integrity": "sha1-ogU4P+oyKzO1rjsYq+4NwvNW7hU=", - "dev": true, - "requires": { - "package-json": "^4.0.0" - } - }, - "lazy-cache": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/lazy-cache/-/lazy-cache-1.0.4.tgz", - "integrity": "sha1-odePw6UEdMuAhF07O24dpJpEbo4=", - "dev": true, - "optional": true - }, - "lcid": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/lcid/-/lcid-1.0.0.tgz", - "integrity": "sha1-MIrMr6C8SDo4Z7S28rlQYlHRuDU=", - "requires": { - "invert-kv": "^1.0.0" - } - }, - "levn": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/levn/-/levn-0.3.0.tgz", - "integrity": "sha1-OwmSTt+fCDwEkP3UwLxEIeBHZO4=", - "dev": true, - "requires": { - "prelude-ls": "~1.1.2", - "type-check": "~0.3.2" - } - }, - "listr": { - "version": "0.13.0", - "resolved": "https://registry.npmjs.org/listr/-/listr-0.13.0.tgz", - "integrity": "sha1-ILsLowuuZg7oTMBQPfS+PVYjiH0=", - "requires": { - "chalk": "^1.1.3", - "cli-truncate": "^0.2.1", - "figures": "^1.7.0", - "indent-string": "^2.1.0", - "is-observable": "^0.2.0", - "is-promise": "^2.1.0", - "is-stream": "^1.1.0", - "listr-silent-renderer": "^1.1.1", - "listr-update-renderer": "^0.4.0", - "listr-verbose-renderer": "^0.4.0", - "log-symbols": "^1.0.2", - "log-update": "^1.0.2", - "ora": "^0.2.3", - "p-map": "^1.1.1", - "rxjs": "^5.4.2", - "stream-to-observable": "^0.2.0", - "strip-ansi": "^3.0.1" - }, - "dependencies": { - "ansi-styles": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-2.2.1.tgz", - "integrity": "sha1-tDLdM1i2NM914eRmQ2gkBTPB3b4=" + "set-blocking": { + "version": "2.0.0", + "bundled": true, + "dev": true, + "optional": true }, - "chalk": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz", - "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=", + "signal-exit": { + "version": "3.0.2", + "bundled": true, + "dev": true, + "optional": true + }, + "string-width": { + "version": "1.0.2", + "bundled": true, + "dev": true, "requires": { - "ansi-styles": "^2.2.1", - "escape-string-regexp": "^1.0.2", - "has-ansi": "^2.0.0", - "strip-ansi": "^3.0.0", - "supports-color": "^2.0.0" + "code-point-at": "^1.0.0", + "is-fullwidth-code-point": "^1.0.0", + "strip-ansi": "^3.0.0" } }, - "figures": { - "version": "1.7.0", - "resolved": "https://registry.npmjs.org/figures/-/figures-1.7.0.tgz", - "integrity": "sha1-y+Hjr/zxzUS4DK3+0o3Hk6lwHS4=", + "string_decoder": { + "version": "1.1.1", + "bundled": true, + "dev": true, + "optional": true, "requires": { - "escape-string-regexp": "^1.0.5", - "object-assign": "^4.1.0" + "safe-buffer": "~5.1.0" } }, - "log-symbols": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/log-symbols/-/log-symbols-1.0.2.tgz", - "integrity": "sha1-N2/3tY6jCGoPCfrMdGF+ylAeGhg=", + "strip-ansi": { + "version": "3.0.1", + "bundled": true, + "dev": true, "requires": { - "chalk": "^1.0.0" + "ansi-regex": "^2.0.0" } }, - "supports-color": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz", - "integrity": "sha1-U10EXOa2Nj+kARcIRimZXp3zJMc=" - } - } - }, - "listr-silent-renderer": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/listr-silent-renderer/-/listr-silent-renderer-1.1.1.tgz", - "integrity": "sha1-kktaN1cVN3C/Go4/v3S4u/P5JC4=" - }, - "listr-update-renderer": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/listr-update-renderer/-/listr-update-renderer-0.4.0.tgz", - "integrity": "sha1-NE2YDaLKLosUW6MFkI8yrj9MyKc=", - "requires": { - "chalk": "^1.1.3", - "cli-truncate": "^0.2.1", - "elegant-spinner": "^1.0.1", - "figures": "^1.7.0", - "indent-string": "^3.0.0", - "log-symbols": "^1.0.2", - "log-update": "^1.0.2", - "strip-ansi": "^3.0.1" - }, - "dependencies": { - "ansi-styles": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-2.2.1.tgz", - "integrity": "sha1-tDLdM1i2NM914eRmQ2gkBTPB3b4=" + "strip-json-comments": { + "version": "2.0.1", + "bundled": true, + "dev": true, + "optional": true }, - "chalk": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz", - "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=", + "tar": { + "version": "4.4.8", + "bundled": true, + "dev": true, + "optional": true, "requires": { - "ansi-styles": "^2.2.1", - "escape-string-regexp": "^1.0.2", - "has-ansi": "^2.0.0", - "strip-ansi": "^3.0.0", - "supports-color": "^2.0.0" + "chownr": "^1.1.1", + "fs-minipass": "^1.2.5", + "minipass": "^2.3.4", + "minizlib": "^1.1.1", + "mkdirp": "^0.5.0", + "safe-buffer": "^5.1.2", + "yallist": "^3.0.2" } }, - "figures": { - "version": "1.7.0", - "resolved": "https://registry.npmjs.org/figures/-/figures-1.7.0.tgz", - "integrity": "sha1-y+Hjr/zxzUS4DK3+0o3Hk6lwHS4=", + "util-deprecate": { + "version": "1.0.2", + "bundled": true, + "dev": true, + "optional": true + }, + "wide-align": { + "version": "1.1.3", + "bundled": true, + "dev": true, + "optional": true, "requires": { - "escape-string-regexp": "^1.0.5", - "object-assign": "^4.1.0" + "string-width": "^1.0.2 || 2" } }, - "indent-string": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/indent-string/-/indent-string-3.2.0.tgz", - "integrity": "sha1-Sl/W0nzDMvN+VBmlBNu4NxBckok=" - }, - "log-symbols": { + "wrappy": { "version": "1.0.2", - "resolved": "https://registry.npmjs.org/log-symbols/-/log-symbols-1.0.2.tgz", - "integrity": "sha1-N2/3tY6jCGoPCfrMdGF+ylAeGhg=", - "requires": { - "chalk": "^1.0.0" - } + "bundled": true, + "dev": true }, - "supports-color": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz", - "integrity": "sha1-U10EXOa2Nj+kARcIRimZXp3zJMc=" + "yallist": { + "version": "3.0.3", + "bundled": true, + "dev": true } } }, - "listr-verbose-renderer": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/listr-verbose-renderer/-/listr-verbose-renderer-0.4.1.tgz", - "integrity": "sha1-ggb0z21S3cWCfl/RSYng6WWTOjU=", + "ganache-cli": { + "version": "6.3.0", + "resolved": "https://registry.npmjs.org/ganache-cli/-/ganache-cli-6.3.0.tgz", + "integrity": "sha512-8SyzfX2ipRVBx1fBZLg3j8I3E334U3Vazk5mEpYcWqnIjC2ace6jtOXHG4aTuAvSz3+HzQ8p8pRjOJxdDZ2pnQ==", "requires": { - "chalk": "^1.1.3", - "cli-cursor": "^1.0.2", - "date-fns": "^1.27.2", - "figures": "^1.7.0" + "bn.js": "4.11.8", + "source-map-support": "0.5.9", + "yargs": "11.1.0" }, "dependencies": { - "ansi-styles": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-2.2.1.tgz", - "integrity": "sha1-tDLdM1i2NM914eRmQ2gkBTPB3b4=" + "ansi-regex": { + "version": "3.0.0", + "bundled": true }, - "chalk": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz", - "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=", - "requires": { - "ansi-styles": "^2.2.1", - "escape-string-regexp": "^1.0.2", - "has-ansi": "^2.0.0", - "strip-ansi": "^3.0.0", - "supports-color": "^2.0.0" - } + "bn.js": { + "version": "4.11.8", + "bundled": true }, - "cli-cursor": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-1.0.2.tgz", - "integrity": "sha1-ZNo/fValRBLll5S9Ytw1KV6PKYc=", - "requires": { - "restore-cursor": "^1.0.1" - } + "buffer-from": { + "version": "1.1.1", + "bundled": true + }, + "camelcase": { + "version": "4.1.0", + "bundled": true }, - "figures": { - "version": "1.7.0", - "resolved": "https://registry.npmjs.org/figures/-/figures-1.7.0.tgz", - "integrity": "sha1-y+Hjr/zxzUS4DK3+0o3Hk6lwHS4=", + "cliui": { + "version": "4.1.0", + "bundled": true, "requires": { - "escape-string-regexp": "^1.0.5", - "object-assign": "^4.1.0" + "string-width": "^2.1.1", + "strip-ansi": "^4.0.0", + "wrap-ansi": "^2.0.0" } }, - "onetime": { + "code-point-at": { "version": "1.1.0", - "resolved": "http://registry.npmjs.org/onetime/-/onetime-1.1.0.tgz", - "integrity": "sha1-ofeDj4MUxRbwXs78vEzP4EtO14k=" + "bundled": true }, - "restore-cursor": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-1.0.1.tgz", - "integrity": "sha1-NGYfRohjJ/7SmRR5FSJS35LapUE=", + "cross-spawn": { + "version": "5.1.0", + "bundled": true, "requires": { - "exit-hook": "^1.0.0", - "onetime": "^1.0.0" + "lru-cache": "^4.0.1", + "shebang-command": "^1.2.0", + "which": "^1.2.9" } }, - "supports-color": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz", - "integrity": "sha1-U10EXOa2Nj+kARcIRimZXp3zJMc=" - } - } - }, - "load-json-file": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-1.1.0.tgz", - "integrity": "sha1-lWkFcI1YtLq0wiYbBPWfMcmTdMA=", - "requires": { - "graceful-fs": "^4.1.2", - "parse-json": "^2.2.0", - "pify": "^2.0.0", - "pinkie-promise": "^2.0.0", - "strip-bom": "^2.0.0" - } - }, - "loader-utils": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/loader-utils/-/loader-utils-1.1.0.tgz", - "integrity": "sha1-yYrvSIvM7aL/teLeZG1qdUQp9c0=", - "requires": { - "big.js": "^3.1.3", - "emojis-list": "^2.0.0", - "json5": "^0.5.0" - } - }, - "locate-path": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-2.0.0.tgz", - "integrity": "sha1-K1aLJl7slExtnA3pw9u7ygNUzY4=", - "requires": { - "p-locate": "^2.0.0", - "path-exists": "^3.0.0" - }, - "dependencies": { - "path-exists": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", - "integrity": "sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=" - } - } - }, - "lodash": { - "version": "4.17.5", - "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.5.tgz", - "integrity": "sha512-svL3uiZf1RwhH+cWrfZn3A4+U58wbP0tGVTLQPbjplZxZ8ROD9VLuNgsRniTlLe7OlSqR79RUehXgpBW/s0IQw==" - }, - "lodash.assign": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/lodash.assign/-/lodash.assign-4.2.0.tgz", - "integrity": "sha1-DZnzzNem0mHRm9rrkkUAXShYCOc=" - }, - "log-symbols": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/log-symbols/-/log-symbols-2.2.0.tgz", - "integrity": "sha512-VeIAFslyIerEJLXHziedo2basKbMKtTw3vfn5IzG0XTjhAVEJyNHnL2p7vc+wBDSdQuUpNw3M2u6xb9QsAY5Eg==", - "requires": { - "chalk": "^2.0.1" - } - }, - "log-update": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/log-update/-/log-update-1.0.2.tgz", - "integrity": "sha1-GZKfZMQJPS0ucHWh2tivWcKWuNE=", - "requires": { - "ansi-escapes": "^1.0.0", - "cli-cursor": "^1.0.2" - }, - "dependencies": { - "ansi-escapes": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-1.4.0.tgz", - "integrity": "sha1-06ioOzGapneTZisT52HHkRQiMG4=" + "decamelize": { + "version": "1.2.0", + "bundled": true }, - "cli-cursor": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-1.0.2.tgz", - "integrity": "sha1-ZNo/fValRBLll5S9Ytw1KV6PKYc=", + "execa": { + "version": "0.7.0", + "bundled": true, "requires": { - "restore-cursor": "^1.0.1" + "cross-spawn": "^5.0.1", + "get-stream": "^3.0.0", + "is-stream": "^1.1.0", + "npm-run-path": "^2.0.0", + "p-finally": "^1.0.0", + "signal-exit": "^3.0.0", + "strip-eof": "^1.0.0" } }, - "onetime": { - "version": "1.1.0", - "resolved": "http://registry.npmjs.org/onetime/-/onetime-1.1.0.tgz", - "integrity": "sha1-ofeDj4MUxRbwXs78vEzP4EtO14k=" - }, - "restore-cursor": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-1.0.1.tgz", - "integrity": "sha1-NGYfRohjJ/7SmRR5FSJS35LapUE=", + "find-up": { + "version": "2.1.0", + "bundled": true, "requires": { - "exit-hook": "^1.0.0", - "onetime": "^1.0.0" + "locate-path": "^2.0.0" } - } - } - }, - "longest": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/longest/-/longest-1.0.1.tgz", - "integrity": "sha1-MKCy2jj3N3DoKUoNIuZiXtd9AJc=", - "dev": true - }, - "loose-envify": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/loose-envify/-/loose-envify-1.3.1.tgz", - "integrity": "sha1-0aitM/qc4OcT1l/dCsi3SNR4yEg=", - "requires": { - "js-tokens": "^3.0.0" - } - }, - "lowercase-keys": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/lowercase-keys/-/lowercase-keys-1.0.0.tgz", - "integrity": "sha1-TjNms55/VFfjXxMkvfb4jQv8cwY=" - }, - "lru-cache": { - "version": "2.7.3", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-2.7.3.tgz", - "integrity": "sha1-bUUk6LlV+V1PW1iFHOId1y+06VI=", - "dev": true - }, - "make-dir": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-1.2.0.tgz", - "integrity": "sha512-aNUAa4UMg/UougV25bbrU4ZaaKNjJ/3/xnvg/twpmKROPdKZPZ9wGgI0opdZzO8q/zUFawoUuixuOv33eZ61Iw==", - "requires": { - "pify": "^3.0.0" - }, - "dependencies": { - "pify": { + }, + "get-caller-file": { + "version": "1.0.3", + "bundled": true + }, + "get-stream": { "version": "3.0.0", - "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", - "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=" - } - } - }, - "map-cache": { - "version": "0.2.2", - "resolved": "https://registry.npmjs.org/map-cache/-/map-cache-0.2.2.tgz", - "integrity": "sha1-wyq9C9ZSXZsFFkW7TyasXcmKDb8=", - "dev": true - }, - "map-stream": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/map-stream/-/map-stream-0.1.0.tgz", - "integrity": "sha1-5WqpTEyAVaFkBKBnS3jyFffI4ZQ=", - "dev": true - }, - "map-visit": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/map-visit/-/map-visit-1.0.0.tgz", - "integrity": "sha1-7Nyo8TFE5mDxtb1B8S80edmN+48=", - "dev": true, - "requires": { - "object-visit": "^1.0.0" - } - }, - "media-typer": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/media-typer/-/media-typer-0.3.0.tgz", - "integrity": "sha1-hxDXrwqmJvj/+hzgAWhUUmMlV0g=" - }, - "mem": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/mem/-/mem-1.1.0.tgz", - "integrity": "sha1-Xt1StIXKHZAP5kiVUFOZoN+kX3Y=", - "requires": { - "mimic-fn": "^1.0.0" - } - }, - "mem-fs": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/mem-fs/-/mem-fs-1.1.3.tgz", - "integrity": "sha1-uK6NLj/Lb10/kWXBLUVRoGXZicw=", - "requires": { - "through2": "^2.0.0", - "vinyl": "^1.1.0", - "vinyl-file": "^2.0.0" - } - }, - "mem-fs-editor": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/mem-fs-editor/-/mem-fs-editor-3.0.2.tgz", - "integrity": "sha1-3Qpuryu4prN3QAZ6pUnrUwEFr58=", - "requires": { - "commondir": "^1.0.1", - "deep-extend": "^0.4.0", - "ejs": "^2.3.1", - "glob": "^7.0.3", - "globby": "^6.1.0", - "mkdirp": "^0.5.0", - "multimatch": "^2.0.0", - "rimraf": "^2.2.8", - "through2": "^2.0.0", - "vinyl": "^2.0.1" - }, - "dependencies": { - "clone": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/clone/-/clone-2.1.2.tgz", - "integrity": "sha1-G39Ln1kfHo+DZwQBYANFoCiHQ18=" + "bundled": true }, - "clone-stats": { + "invert-kv": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/clone-stats/-/clone-stats-1.0.0.tgz", - "integrity": "sha1-s3gt/4u1R04Yuba/D9/ngvh3doA=" + "bundled": true + }, + "is-fullwidth-code-point": { + "version": "2.0.0", + "bundled": true }, - "replace-ext": { + "is-stream": { + "version": "1.1.0", + "bundled": true + }, + "isexe": { + "version": "2.0.0", + "bundled": true + }, + "lcid": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/replace-ext/-/replace-ext-1.0.0.tgz", - "integrity": "sha1-3mMSg3P8v3w8z6TeWkgMRaZ5WOs=" + "bundled": true, + "requires": { + "invert-kv": "^1.0.0" + } }, - "vinyl": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-2.1.0.tgz", - "integrity": "sha1-Ah+cLPlR1rk5lDyJ617lrdT9kkw=", + "locate-path": { + "version": "2.0.0", + "bundled": true, "requires": { - "clone": "^2.1.1", - "clone-buffer": "^1.0.0", - "clone-stats": "^1.0.0", - "cloneable-readable": "^1.0.0", - "remove-trailing-separator": "^1.0.1", - "replace-ext": "^1.0.0" + "p-locate": "^2.0.0", + "path-exists": "^3.0.0" } - } - } - }, - "memory-fs": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/memory-fs/-/memory-fs-0.4.1.tgz", - "integrity": "sha1-OpoguEYlI+RHz7x+i7gO1me/xVI=", - "requires": { - "errno": "^0.1.3", - "readable-stream": "^2.0.1" - } - }, - "memorystream": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/memorystream/-/memorystream-0.3.1.tgz", - "integrity": "sha1-htcJCzDORV1j+64S3aUaR93K+bI=" - }, - "merge-descriptors": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/merge-descriptors/-/merge-descriptors-1.0.1.tgz", - "integrity": "sha1-sAqqVW3YtEVoFQ7J0blT8/kMu2E=" - }, - "methods": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/methods/-/methods-1.1.2.tgz", - "integrity": "sha1-VSmk1nZUE07cxSZmVoNbD4Ua/O4=" - }, - "micromatch": { - "version": "3.1.10", - "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-3.1.10.tgz", - "integrity": "sha512-MWikgl9n9M3w+bpsY3He8L+w9eF9338xRl8IAO5viDizwSzziFEyUzo2xrrloB64ADbTf8uA8vRqqttDTOmccg==", - "dev": true, - "requires": { - "arr-diff": "^4.0.0", - "array-unique": "^0.3.2", - "braces": "^2.3.1", - "define-property": "^2.0.2", - "extend-shallow": "^3.0.2", - "extglob": "^2.0.4", - "fragment-cache": "^0.2.1", - "kind-of": "^6.0.2", - "nanomatch": "^1.2.9", - "object.pick": "^1.3.0", - "regex-not": "^1.0.0", - "snapdragon": "^0.8.1", - "to-regex": "^3.0.2" - } - }, - "mime": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/mime/-/mime-1.4.1.tgz", - "integrity": "sha512-KI1+qOZu5DcW6wayYHSzR/tXKCDC5Om4s1z2QJjDULzLcmf3DvzS7oluY4HCTrc+9FiKmWUgeNLg7W3uIQvxtQ==" - }, - "mime-db": { - "version": "1.33.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.33.0.tgz", - "integrity": "sha512-BHJ/EKruNIqJf/QahvxwQZXKygOQ256myeN/Ew+THcAa5q+PjyTTMMeNQC4DZw5AwfvelsUrA6B67NKMqXDbzQ==" - }, - "mime-types": { - "version": "2.1.18", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.18.tgz", - "integrity": "sha512-lc/aahn+t4/SWV/qcmumYjymLsWfN3ELhpmVuUFjgsORruuZPVSwAQryq+HHGvO/SI2KVX26bx+En+zhM8g8hQ==", - "requires": { - "mime-db": "~1.33.0" - } - }, - "mimic-fn": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-1.2.0.tgz", - "integrity": "sha512-jf84uxzwiuiIVKiOLpfYk7N46TSy8ubTonmneY9vrpHNAnp0QBt2BxWV9dO3/j+BoVAb+a5G6YDPW3M5HOdMWQ==" - }, - "mimic-response": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-1.0.0.tgz", - "integrity": "sha1-3z02Uqc/3ta5sLJBRub9BSNTRY4=" - }, - "min-document": { - "version": "2.19.0", - "resolved": "https://registry.npmjs.org/min-document/-/min-document-2.19.0.tgz", - "integrity": "sha1-e9KC4/WELtKVu3SM3Z8f+iyCRoU=", - "requires": { - "dom-walk": "^0.1.0" - } - }, - "minimalistic-assert": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/minimalistic-assert/-/minimalistic-assert-1.0.1.tgz", - "integrity": "sha512-UtJcAD4yEaGtjPezWuO9wC4nwUnVH/8/Im3yEHQP4b67cXlD/Qr9hdITCU1xDbSEXg2XKNaP8jsReV7vQd00/A==" - }, - "minimalistic-crypto-utils": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/minimalistic-crypto-utils/-/minimalistic-crypto-utils-1.0.1.tgz", - "integrity": "sha1-9sAMHAsIIkblxNmd+4x8CDsrWCo=" - }, - "minimatch": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", - "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", - "requires": { - "brace-expansion": "^1.1.7" - } - }, - "minimist": { - "version": "0.0.8", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-0.0.8.tgz", - "integrity": "sha1-hX/Kv8M5fSYluCKCYuhqp6ARsF0=" - }, - "mixin-deep": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/mixin-deep/-/mixin-deep-1.3.1.tgz", - "integrity": "sha512-8ZItLHeEgaqEvd5lYBXfm4EZSFCX29Jb9K+lAHhDKzReKBQKj3R+7NOF6tjqYi9t4oI8VUfaWITJQm86wnXGNQ==", - "dev": true, - "requires": { - "for-in": "^1.0.2", - "is-extendable": "^1.0.1" - }, - "dependencies": { - "is-extendable": { + }, + "lru-cache": { + "version": "4.1.4", + "bundled": true, + "requires": { + "pseudomap": "^1.0.2", + "yallist": "^3.0.2" + } + }, + "mem": { + "version": "1.1.0", + "bundled": true, + "requires": { + "mimic-fn": "^1.0.0" + } + }, + "mimic-fn": { + "version": "1.2.0", + "bundled": true + }, + "npm-run-path": { + "version": "2.0.2", + "bundled": true, + "requires": { + "path-key": "^2.0.0" + } + }, + "number-is-nan": { "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-1.0.1.tgz", - "integrity": "sha512-arnXMxT1hhoKo9k1LZdmlNyJdDDfy2v0fXjFlmok4+i8ul/6WlbVge9bhM74OpNPQPMGUToDtz+KXa1PneJxOA==", - "dev": true, + "bundled": true + }, + "os-locale": { + "version": "2.1.0", + "bundled": true, "requires": { - "is-plain-object": "^2.0.4" + "execa": "^0.7.0", + "lcid": "^1.0.0", + "mem": "^1.1.0" } - } - } - }, - "mkdirp": { - "version": "0.5.1", - "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.1.tgz", - "integrity": "sha1-MAV0OOrGz3+MR2fzhkjWaX11yQM=", - "requires": { - "minimist": "0.0.8" - } - }, - "mocha": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/mocha/-/mocha-4.1.0.tgz", - "integrity": "sha512-0RVnjg1HJsXY2YFDoTNzcc1NKhYuXKRrBAG2gDygmJJA136Cs2QlRliZG1mA0ap7cuaT30mw16luAeln+4RiNA==", - "requires": { - "browser-stdout": "1.3.0", - "commander": "2.11.0", - "debug": "3.1.0", - "diff": "3.3.1", - "escape-string-regexp": "1.0.5", - "glob": "7.1.2", - "growl": "1.10.3", - "he": "1.1.1", - "mkdirp": "0.5.1", - "supports-color": "4.4.0" - }, - "dependencies": { - "debug": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", - "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", + }, + "p-finally": { + "version": "1.0.0", + "bundled": true + }, + "p-limit": { + "version": "1.3.0", + "bundled": true, "requires": { - "ms": "2.0.0" + "p-try": "^1.0.0" } }, - "glob": { - "version": "7.1.2", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz", - "integrity": "sha512-MJTUg1kjuLeQCJ+ccE4Vpa6kKVXkPYJ2mOCQyUuKLcLQsdrMCpBPUi8qVE6+YuaJkozeA9NusTAw3hLr8Xe5EQ==", + "p-locate": { + "version": "2.0.0", + "bundled": true, "requires": { - "fs.realpath": "^1.0.0", - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "^3.0.4", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" + "p-limit": "^1.1.0" } }, - "growl": { - "version": "1.10.3", - "resolved": "https://registry.npmjs.org/growl/-/growl-1.10.3.tgz", - "integrity": "sha512-hKlsbA5Vu3xsh1Cg3J7jSmX/WaW6A5oBeqzM88oNbCRQFz+zUaXm6yxS4RVytp1scBoJzSYl4YAEOQIt6O8V1Q==" + "p-try": { + "version": "1.0.0", + "bundled": true }, - "has-flag": { + "path-exists": { + "version": "3.0.0", + "bundled": true + }, + "path-key": { + "version": "2.0.1", + "bundled": true + }, + "pseudomap": { + "version": "1.0.2", + "bundled": true + }, + "require-directory": { + "version": "2.1.1", + "bundled": true + }, + "require-main-filename": { + "version": "1.0.1", + "bundled": true + }, + "set-blocking": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-2.0.0.tgz", - "integrity": "sha1-6CB68cx7MNRGzHC3NLXovhj4jVE=" + "bundled": true }, - "supports-color": { - "version": "4.4.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-4.4.0.tgz", - "integrity": "sha512-rKC3+DyXWgK0ZLKwmRsrkyHVZAjNkfzeehuFWdGGcqGDTZFH73+RH6S/RDAAxl9GusSjZSUWYLmT9N5pzXFOXQ==", + "shebang-command": { + "version": "1.2.0", + "bundled": true, "requires": { - "has-flag": "^2.0.0" + "shebang-regex": "^1.0.0" } - } - } - }, - "ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" - }, - "multimatch": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/multimatch/-/multimatch-2.1.0.tgz", - "integrity": "sha1-nHkGoi+0wCkZ4vX3UWG0zb1LKis=", - "requires": { - "array-differ": "^1.0.0", - "array-union": "^1.0.1", - "arrify": "^1.0.0", - "minimatch": "^3.0.0" - } - }, - "mute-stream": { - "version": "0.0.7", - "resolved": "https://registry.npmjs.org/mute-stream/-/mute-stream-0.0.7.tgz", - "integrity": "sha1-MHXOk7whuPq0PhvE2n6BFe0ee6s=" - }, - "nan": { - "version": "2.10.0", - "resolved": "https://registry.npmjs.org/nan/-/nan-2.10.0.tgz", - "integrity": "sha512-bAdJv7fBLhWC+/Bls0Oza+mvTaNQtP+1RyhhhvD95pgUJz6XM5IzgmxOkItJ9tkoCiplvAnXI1tNmmUD/eScyA==" - }, - "nano-json-stream-parser": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/nano-json-stream-parser/-/nano-json-stream-parser-0.1.2.tgz", - "integrity": "sha1-DMj20OK2IrR5xA1JnEbWS3Vcb18=" - }, - "nanomatch": { - "version": "1.2.9", - "resolved": "https://registry.npmjs.org/nanomatch/-/nanomatch-1.2.9.tgz", - "integrity": "sha512-n8R9bS8yQ6eSXaV6jHUpKzD8gLsin02w1HSFiegwrs9E098Ylhw5jdyKPaYqvHknHaSCKTPp7C8dGCQ0q9koXA==", - "dev": true, - "requires": { - "arr-diff": "^4.0.0", - "array-unique": "^0.3.2", - "define-property": "^2.0.2", - "extend-shallow": "^3.0.2", - "fragment-cache": "^0.2.1", - "is-odd": "^2.0.0", - "is-windows": "^1.0.2", - "kind-of": "^6.0.2", - "object.pick": "^1.3.0", - "regex-not": "^1.0.0", - "snapdragon": "^0.8.1", - "to-regex": "^3.0.1" - } - }, - "negotiator": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-0.6.1.tgz", - "integrity": "sha1-KzJxhOiZIQEXeyhWP7XnECrNDKk=" - }, - "neo-async": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/neo-async/-/neo-async-2.5.0.tgz", - "integrity": "sha512-nJmSswG4As/MkRq7QZFuH/sf/yuv8ODdMZrY4Bedjp77a5MK4A6s7YbBB64c9u79EBUOfXUXBvArmvzTD0X+6g==" - }, - "nice-try": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/nice-try/-/nice-try-1.0.4.tgz", - "integrity": "sha512-2NpiFHqC87y/zFke0fC0spBXL3bBsoh/p5H1EFhshxjCR5+0g2d6BiXbUFz9v1sAcxsk2htp2eQnNIci2dIYcA==" - }, - "node-dir": { - "version": "0.1.8", - "resolved": "https://registry.npmjs.org/node-dir/-/node-dir-0.1.8.tgz", - "integrity": "sha1-VfuN62mQcHB/tn+RpGDwRIKUx30=" - }, - "nodemon": { - "version": "1.17.3", - "resolved": "https://registry.npmjs.org/nodemon/-/nodemon-1.17.3.tgz", - "integrity": "sha512-8AtS+wA5u6qoE12LONjqOzUzxAI5ObzSw6U5LgqpaO/0y6wwId4l5dN0ZulYyYdpLZD1MbkBp7GjG1hqaoRqYg==", - "dev": true, - "requires": { - "chokidar": "^2.0.2", - "debug": "^3.1.0", - "ignore-by-default": "^1.0.1", - "minimatch": "^3.0.4", - "pstree.remy": "^1.1.0", - "semver": "^5.5.0", - "supports-color": "^5.2.0", - "touch": "^3.1.0", - "undefsafe": "^2.0.2", - "update-notifier": "^2.3.0" - }, - "dependencies": { - "debug": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", - "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", - "dev": true, + }, + "shebang-regex": { + "version": "1.0.0", + "bundled": true + }, + "signal-exit": { + "version": "3.0.2", + "bundled": true + }, + "source-map": { + "version": "0.6.1", + "bundled": true + }, + "source-map-support": { + "version": "0.5.9", + "bundled": true, "requires": { - "ms": "2.0.0" + "buffer-from": "^1.0.0", + "source-map": "^0.6.0" } }, - "has-flag": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", - "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=", - "dev": true + "string-width": { + "version": "2.1.1", + "bundled": true, + "requires": { + "is-fullwidth-code-point": "^2.0.0", + "strip-ansi": "^4.0.0" + } }, - "supports-color": { - "version": "5.4.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.4.0.tgz", - "integrity": "sha512-zjaXglF5nnWpsq470jSv6P9DwPvgLkuapYmfDm3JWOm0vkNTVF2tI4UrN2r6jH1qM/uc/WtxYY1hYoA2dOKj5w==", - "dev": true, + "strip-ansi": { + "version": "4.0.0", + "bundled": true, "requires": { - "has-flag": "^3.0.0" + "ansi-regex": "^3.0.0" } - } - } - }, - "nomnom": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/nomnom/-/nomnom-1.8.1.tgz", - "integrity": "sha1-IVH3Ikcrp55Qp2/BJbuMjy5Nwqc=", - "requires": { - "chalk": "~0.4.0", - "underscore": "~1.6.0" - }, - "dependencies": { - "ansi-styles": { + }, + "strip-eof": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-1.0.0.tgz", - "integrity": "sha1-yxAt8cVvUSPquLZ817mAJ6AnkXg=" + "bundled": true }, - "chalk": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-0.4.0.tgz", - "integrity": "sha1-UZmj3c0MHv4jvAjBsCewYXbgxk8=", + "which": { + "version": "1.3.1", + "bundled": true, "requires": { - "ansi-styles": "~1.0.0", - "has-color": "~0.1.0", - "strip-ansi": "~0.1.0" + "isexe": "^2.0.0" } }, - "strip-ansi": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-0.1.1.tgz", - "integrity": "sha1-OeipjQRNFQZgq+SmgIrPcLt7yZE=" + "which-module": { + "version": "2.0.0", + "bundled": true + }, + "wrap-ansi": { + "version": "2.1.0", + "bundled": true, + "requires": { + "string-width": "^1.0.1", + "strip-ansi": "^3.0.1" + }, + "dependencies": { + "ansi-regex": { + "version": "2.1.1", + "bundled": true + }, + "is-fullwidth-code-point": { + "version": "1.0.0", + "bundled": true, + "requires": { + "number-is-nan": "^1.0.0" + } + }, + "string-width": { + "version": "1.0.2", + "bundled": true, + "requires": { + "code-point-at": "^1.0.0", + "is-fullwidth-code-point": "^1.0.0", + "strip-ansi": "^3.0.0" + } + }, + "strip-ansi": { + "version": "3.0.1", + "bundled": true, + "requires": { + "ansi-regex": "^2.0.0" + } + } + } + }, + "y18n": { + "version": "3.2.1", + "bundled": true + }, + "yallist": { + "version": "3.0.2", + "bundled": true + }, + "yargs": { + "version": "11.1.0", + "bundled": true, + "requires": { + "cliui": "^4.0.0", + "decamelize": "^1.1.1", + "find-up": "^2.1.0", + "get-caller-file": "^1.0.1", + "os-locale": "^2.0.0", + "require-directory": "^2.1.1", + "require-main-filename": "^1.0.1", + "set-blocking": "^2.0.0", + "string-width": "^2.0.0", + "which-module": "^2.0.0", + "y18n": "^3.2.1", + "yargs-parser": "^9.0.2" + } + }, + "yargs-parser": { + "version": "9.0.2", + "bundled": true, + "requires": { + "camelcase": "^4.1.0" + } } } }, - "nopt": { - "version": "1.0.10", - "resolved": "https://registry.npmjs.org/nopt/-/nopt-1.0.10.tgz", - "integrity": "sha1-bd0hvSoxQXuScn3Vhfim83YI6+4=", - "dev": true, - "requires": { - "abbrev": "1" - } + "get-caller-file": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/get-caller-file/-/get-caller-file-1.0.3.tgz", + "integrity": "sha512-3t6rVToeoZfYSGd8YoLFR2DJkiQrIiUrGcjvFX2mDw3bn6k2OtwHN0TNCLbBO+w8qTvimhDkv+LSscbJY1vE6w==" }, - "normalize-package-data": { - "version": "2.4.0", - "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-2.4.0.tgz", - "integrity": "sha512-9jjUFbTPfEy3R/ad/2oNbKtW9Hgovl5O1FvFWKkKblNXoN/Oou6+9+KKohPK13Yc3/TyunyWhJp6gvRNR/PPAw==", - "requires": { - "hosted-git-info": "^2.1.4", - "is-builtin-module": "^1.0.0", - "semver": "2 || 3 || 4 || 5", - "validate-npm-package-license": "^3.0.1" - } + "get-func-name": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/get-func-name/-/get-func-name-2.0.0.tgz", + "integrity": "sha1-6td0q+5y4gQJQzoGY2YCPdaIekE=", + "dev": true + }, + "get-port": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/get-port/-/get-port-3.2.0.tgz", + "integrity": "sha1-3Xzn3hh8Bsi/NTeWrHHgmfCYDrw=", + "dev": true }, - "normalize-path": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-2.1.1.tgz", - "integrity": "sha1-GrKLVW4Zg2Oowab35vogE3/mrtk=", - "requires": { - "remove-trailing-separator": "^1.0.1" - } + "get-stream": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-3.0.0.tgz", + "integrity": "sha1-jpQ9E1jcN1VQVOy+LtsFqhdO3hQ=", + "dev": true }, - "normalize-url": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/normalize-url/-/normalize-url-2.0.1.tgz", - "integrity": "sha512-D6MUW4K/VzoJ4rJ01JFKxDrtY1v9wrgzCX5f2qj/lzH1m/lW6MhUZFKerVsnyjOhOsYzI9Kqqak+10l4LvLpMw==", - "requires": { - "prepend-http": "^2.0.0", - "query-string": "^5.0.1", - "sort-keys": "^2.0.0" - }, - "dependencies": { - "prepend-http": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/prepend-http/-/prepend-http-2.0.0.tgz", - "integrity": "sha1-6SQ0v6XqjBn0HN/UAddBo8gZ2Jc=" - } - } + "get-value": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/get-value/-/get-value-2.0.6.tgz", + "integrity": "sha1-3BXKHGcjh8p2vTesCjlbogQqLCg=", + "dev": true }, - "npm-run-path": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/npm-run-path/-/npm-run-path-2.0.2.tgz", - "integrity": "sha1-NakjLfo11wZ7TLLd8jV7GHFTbF8=", + "getpass": { + "version": "0.1.7", + "resolved": "https://registry.npmjs.org/getpass/-/getpass-0.1.7.tgz", + "integrity": "sha1-Xv+OPmhNVprkyysSgmBOi6YhSfo=", + "dev": true, "requires": { - "path-key": "^2.0.0" + "assert-plus": "^1.0.0" } }, - "number-is-nan": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/number-is-nan/-/number-is-nan-1.0.1.tgz", - "integrity": "sha1-CXtgK1NCKlIsGvuHkDGDNpQaAR0=" - }, - "number-to-bn": { - "version": "1.7.0", - "resolved": "https://registry.npmjs.org/number-to-bn/-/number-to-bn-1.7.0.tgz", - "integrity": "sha1-uzYjWS9+X54AMLGXe9QaDFP+HqA=", + "glob": { + "version": "7.1.2", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz", + "integrity": "sha512-MJTUg1kjuLeQCJ+ccE4Vpa6kKVXkPYJ2mOCQyUuKLcLQsdrMCpBPUi8qVE6+YuaJkozeA9NusTAw3hLr8Xe5EQ==", "requires": { - "bn.js": "4.11.6", - "strip-hex-prefix": "1.0.0" + "fs.realpath": "^1.0.0", + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "^3.0.4", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" } }, - "oauth-sign": { - "version": "0.8.2", - "resolved": "https://registry.npmjs.org/oauth-sign/-/oauth-sign-0.8.2.tgz", - "integrity": "sha1-Rqarfwrq2N6unsBWV4C31O/rnUM=" - }, - "object-assign": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", - "integrity": "sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM=" - }, - "object-copy": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/object-copy/-/object-copy-0.1.0.tgz", - "integrity": "sha1-fn2Fi3gb18mRpBupde04EnVOmYw=", + "glob-parent": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-3.1.0.tgz", + "integrity": "sha1-nmr2KZ2NO9K9QEMIMr0RPfkGxa4=", "dev": true, "requires": { - "copy-descriptor": "^0.1.0", - "define-property": "^0.2.5", - "kind-of": "^3.0.3" + "is-glob": "^3.1.0", + "path-dirname": "^1.0.0" }, "dependencies": { - "define-property": { - "version": "0.2.5", - "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", - "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", - "dev": true, - "requires": { - "is-descriptor": "^0.1.0" - } - }, - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "is-glob": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-3.1.0.tgz", + "integrity": "sha1-e6WuJCF4BKxwcHuWkiVnSGzD6Eo=", "dev": true, "requires": { - "is-buffer": "^1.1.5" + "is-extglob": "^2.1.0" } } } }, - "object-visit": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/object-visit/-/object-visit-1.0.1.tgz", - "integrity": "sha1-95xEk68MU3e1n+OdOV5BBC3QRbs=", - "dev": true, - "requires": { - "isobject": "^3.0.0" - } - }, - "object.omit": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/object.omit/-/object.omit-2.0.1.tgz", - "integrity": "sha1-Gpx0SCnznbuFjHbKNXmuKlTr0fo=", + "global": { + "version": "4.3.2", + "resolved": "https://registry.npmjs.org/global/-/global-4.3.2.tgz", + "integrity": "sha1-52mJJopsdMOJCLEwWxD8DjlOnQ8=", "requires": { - "for-own": "^0.1.4", - "is-extendable": "^0.1.1" + "min-document": "^2.19.0", + "process": "~0.5.1" } }, - "object.pick": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/object.pick/-/object.pick-1.3.0.tgz", - "integrity": "sha1-h6EKxMFpS9Lhy/U1kaZhQftd10c=", + "global-dirs": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/global-dirs/-/global-dirs-0.1.1.tgz", + "integrity": "sha1-sxnA3UYH81PzvpzKTHL8FIxJ9EU=", "dev": true, "requires": { - "isobject": "^3.0.1" - } - }, - "on-finished": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/on-finished/-/on-finished-2.3.0.tgz", - "integrity": "sha1-IPEzZIGwg811M3mSoWlxqi2QaUc=", - "requires": { - "ee-first": "1.1.1" - } - }, - "once": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", - "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", - "requires": { - "wrappy": "1" + "ini": "^1.3.4" } }, - "onetime": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/onetime/-/onetime-2.0.1.tgz", - "integrity": "sha1-BnQoIw/WdEOyeUsiu6UotoZ5YtQ=", + "got": { + "version": "6.7.1", + "resolved": "https://registry.npmjs.org/got/-/got-6.7.1.tgz", + "integrity": "sha1-JAzQV4WpoY5WHcG0S0HHY+8ejbA=", + "dev": true, "requires": { - "mimic-fn": "^1.0.0" + "create-error-class": "^3.0.0", + "duplexer3": "^0.1.4", + "get-stream": "^3.0.0", + "is-redirect": "^1.0.0", + "is-retry-allowed": "^1.0.0", + "is-stream": "^1.0.0", + "lowercase-keys": "^1.0.0", + "safe-buffer": "^5.0.1", + "timed-out": "^4.0.0", + "unzip-response": "^2.0.1", + "url-parse-lax": "^1.0.0" } }, - "openzeppelin-solidity": { - "version": "1.10.0", - "resolved": "https://registry.npmjs.org/openzeppelin-solidity/-/openzeppelin-solidity-1.10.0.tgz", - "integrity": "sha512-igkrumQQ2lrN2zjeQV4Dnb0GpTBj1fzMcd8HPyBUqwI0hhuscX/HzXiqKT6gFQl1j9Wy/ppVVs9fqL/foF7Gmg==" + "graceful-fs": { + "version": "4.1.15", + "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.15.tgz", + "integrity": "sha512-6uHUhOPEBgQ24HM+r6b/QwWfZq+yiFcipKFrOFiBEnWdy5sdzYoi+pJeQaPI5qOLRFqWmAXUPQNsielzdLoecA==" }, - "optimist": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/optimist/-/optimist-0.6.1.tgz", - "integrity": "sha1-2j6nRob6IaGaERwybpDrFaAZZoY=", - "dev": true, - "requires": { - "minimist": "~0.0.1", - "wordwrap": "~0.0.2" - }, - "dependencies": { - "wordwrap": { - "version": "0.0.3", - "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-0.0.3.tgz", - "integrity": "sha1-o9XabNXAvAAI03I0u68b7WMFkQc=", - "dev": true - } - } + "growl": { + "version": "1.10.3", + "resolved": "https://registry.npmjs.org/growl/-/growl-1.10.3.tgz", + "integrity": "sha512-hKlsbA5Vu3xsh1Cg3J7jSmX/WaW6A5oBeqzM88oNbCRQFz+zUaXm6yxS4RVytp1scBoJzSYl4YAEOQIt6O8V1Q==" }, - "optionator": { - "version": "0.8.2", - "resolved": "https://registry.npmjs.org/optionator/-/optionator-0.8.2.tgz", - "integrity": "sha1-NkxeQJ0/TWMB1sC0wFu6UBgK62Q=", + "handlebars": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.1.0.tgz", + "integrity": "sha512-l2jRuU1NAWK6AW5qqcTATWQJvNPEwkM7NEKSiv/gqOsoSQbVoWyqVEY5GS+XPQ88zLNmqASRpzfdm8d79hJS+w==", "dev": true, "requires": { - "deep-is": "~0.1.3", - "fast-levenshtein": "~2.0.4", - "levn": "~0.3.0", - "prelude-ls": "~1.1.2", - "type-check": "~0.3.2", - "wordwrap": "~1.0.0" - } - }, - "ora": { - "version": "0.2.3", - "resolved": "https://registry.npmjs.org/ora/-/ora-0.2.3.tgz", - "integrity": "sha1-N1J9Igrc1Tw5tzVx11QVbV22V6Q=", - "requires": { - "chalk": "^1.1.1", - "cli-cursor": "^1.0.2", - "cli-spinners": "^0.1.2", - "object-assign": "^4.0.1" + "async": "^2.5.0", + "optimist": "^0.6.1", + "source-map": "^0.6.1", + "uglify-js": "^3.1.4" }, "dependencies": { - "ansi-styles": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-2.2.1.tgz", - "integrity": "sha1-tDLdM1i2NM914eRmQ2gkBTPB3b4=" - }, - "chalk": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz", - "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=", - "requires": { - "ansi-styles": "^2.2.1", - "escape-string-regexp": "^1.0.2", - "has-ansi": "^2.0.0", - "strip-ansi": "^3.0.0", - "supports-color": "^2.0.0" - } - }, - "cli-cursor": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-1.0.2.tgz", - "integrity": "sha1-ZNo/fValRBLll5S9Ytw1KV6PKYc=", - "requires": { - "restore-cursor": "^1.0.1" - } - }, - "onetime": { - "version": "1.1.0", - "resolved": "http://registry.npmjs.org/onetime/-/onetime-1.1.0.tgz", - "integrity": "sha1-ofeDj4MUxRbwXs78vEzP4EtO14k=" - }, - "restore-cursor": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-1.0.1.tgz", - "integrity": "sha1-NGYfRohjJ/7SmRR5FSJS35LapUE=", + "async": { + "version": "2.6.2", + "resolved": "https://registry.npmjs.org/async/-/async-2.6.2.tgz", + "integrity": "sha512-H1qVYh1MYhEEFLsP97cVKqCGo7KfCyTt6uEWqsTBr9SO84oK9Uwbyd/yCW+6rKJLHksBNUVWZDAjfS+Ccx0Bbg==", + "dev": true, "requires": { - "exit-hook": "^1.0.0", - "onetime": "^1.0.0" + "lodash": "^4.17.11" } }, - "supports-color": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz", - "integrity": "sha1-U10EXOa2Nj+kARcIRimZXp3zJMc=" + "source-map": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", + "dev": true } } }, - "original-require": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/original-require/-/original-require-1.0.1.tgz", - "integrity": "sha1-DxMEcVhM0zURxew4yNWSE/msXiA=" - }, - "os-homedir": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/os-homedir/-/os-homedir-1.0.2.tgz", - "integrity": "sha1-/7xJiDNuDoM94MFox+8VISGqf7M=" - }, - "os-locale": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/os-locale/-/os-locale-1.4.0.tgz", - "integrity": "sha1-IPnxeuKe00XoveWDsT0gCYA8FNk=", - "requires": { - "lcid": "^1.0.0" - } - }, - "os-tmpdir": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/os-tmpdir/-/os-tmpdir-1.0.2.tgz", - "integrity": "sha1-u+Z0BseaqFxc/sdm/lc0VV36EnQ=" - }, - "p-cancelable": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/p-cancelable/-/p-cancelable-0.4.0.tgz", - "integrity": "sha512-/AodqPe1y/GYbhSlnMjxukLGQfQIgsmjSy2CXCNB96kg4ozKvmlovuHEKICToOO/yS3LLWgrWI1dFtFfrePS1g==" + "har-schema": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/har-schema/-/har-schema-2.0.0.tgz", + "integrity": "sha1-qUwiJOvKwEeCoNkDVSHyRzW37JI=", + "dev": true }, - "p-each-series": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/p-each-series/-/p-each-series-1.0.0.tgz", - "integrity": "sha1-kw89Et0fUOdDRFeiLNbwSsatf3E=", + "har-validator": { + "version": "5.1.3", + "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-5.1.3.tgz", + "integrity": "sha512-sNvOCzEQNr/qrvJgc3UG/kD4QtlHycrzwS+6mfTrrSq97BvaYcPZZI1ZSqGSPR73Cxn4LKTD4PttRwfU7jWq5g==", + "dev": true, "requires": { - "p-reduce": "^1.0.0" + "ajv": "^6.5.5", + "har-schema": "^2.0.0" } }, - "p-finally": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/p-finally/-/p-finally-1.0.0.tgz", - "integrity": "sha1-P7z7FbiZpEEjs0ttzBi3JDNqLK4=" - }, - "p-is-promise": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/p-is-promise/-/p-is-promise-1.1.0.tgz", - "integrity": "sha1-nJRWmJ6fZYgBewQ01WCXZ1w9oF4=" + "has-flag": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-2.0.0.tgz", + "integrity": "sha1-6CB68cx7MNRGzHC3NLXovhj4jVE=" }, - "p-lazy": { + "has-value": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/p-lazy/-/p-lazy-1.0.0.tgz", - "integrity": "sha1-7FPIAvLuOsKPFmzILQsrAt4nqDU=" - }, - "p-limit": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-1.2.0.tgz", - "integrity": "sha512-Y/OtIaXtUPr4/YpMv1pCL5L5ed0rumAaAeBSj12F+bSlMdys7i8oQF/GUJmfpTS/QoaRrS/k6pma29haJpsMng==", - "requires": { - "p-try": "^1.0.0" - } - }, - "p-locate": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-2.0.0.tgz", - "integrity": "sha1-IKAQOyIqcMj9OcwuWAaA893l7EM=", + "resolved": "https://registry.npmjs.org/has-value/-/has-value-1.0.0.tgz", + "integrity": "sha1-GLKB2lhbHFxR3vJMkw7SmgvmsXc=", + "dev": true, "requires": { - "p-limit": "^1.1.0" + "get-value": "^2.0.6", + "has-values": "^1.0.0", + "isobject": "^3.0.0" } }, - "p-map": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/p-map/-/p-map-1.2.0.tgz", - "integrity": "sha512-r6zKACMNhjPJMTl8KcFH4li//gkrXWfbD6feV8l6doRHlzljFWGJ2AP6iKaCJXyZmAUMOPtvbW7EXkbWO/pLEA==" - }, - "p-reduce": { + "has-values": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/p-reduce/-/p-reduce-1.0.0.tgz", - "integrity": "sha1-GMKw3ZNqRpClKfgjH1ig/bakffo=" + "resolved": "https://registry.npmjs.org/has-values/-/has-values-1.0.0.tgz", + "integrity": "sha1-lbC2P+whRmGab+V/51Yo1aOe/k8=", + "dev": true, + "requires": { + "is-number": "^3.0.0", + "kind-of": "^4.0.0" + }, + "dependencies": { + "kind-of": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-4.0.0.tgz", + "integrity": "sha1-IIE989cSkosgc3hpGkUGb65y3Vc=", + "dev": true, + "requires": { + "is-buffer": "^1.1.5" + } + } + } }, - "p-timeout": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/p-timeout/-/p-timeout-2.0.1.tgz", - "integrity": "sha512-88em58dDVB/KzPEx1X0N3LwFfYZPyDc4B6eF38M1rk9VTZMbxXXgjugz8mmwpS9Ox4BDZ+t6t3QP5+/gazweIA==", + "hash.js": { + "version": "1.1.7", + "resolved": "https://registry.npmjs.org/hash.js/-/hash.js-1.1.7.tgz", + "integrity": "sha512-taOaskGt4z4SOANNseOviYDvjEJinIkRgmp7LbKP2YTTmVxWBl87s/uzK9r+44BclBSp2X7K1hqeNfz9JbBeXA==", "requires": { - "p-finally": "^1.0.0" + "inherits": "^2.0.3", + "minimalistic-assert": "^1.0.1" } }, - "p-try": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/p-try/-/p-try-1.0.0.tgz", - "integrity": "sha1-y8ec26+P1CKOE/Yh8rGiN8GyB7M=" + "he": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/he/-/he-1.1.1.tgz", + "integrity": "sha1-k0EP0hsAlzUVH4howvJx80J+I/0=" }, - "package-json": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/package-json/-/package-json-4.0.1.tgz", - "integrity": "sha1-iGmgQBJTZhxMTKPabCEh7VVfXu0=", - "dev": true, + "hmac-drbg": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/hmac-drbg/-/hmac-drbg-1.0.1.tgz", + "integrity": "sha1-0nRXAQJabHdabFRXk+1QL8DGSaE=", "requires": { - "got": "^6.7.1", - "registry-auth-token": "^3.0.1", - "registry-url": "^3.0.3", - "semver": "^5.1.0" + "hash.js": "^1.0.3", + "minimalistic-assert": "^1.0.0", + "minimalistic-crypto-utils": "^1.0.1" } }, - "parse-cache-control": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/parse-cache-control/-/parse-cache-control-1.0.1.tgz", - "integrity": "sha1-juqz5U+laSD+Fro493+iGqzC104=", - "dev": true + "hosted-git-info": { + "version": "2.7.1", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-2.7.1.tgz", + "integrity": "sha512-7T/BxH19zbcCTa8XkMlbK5lTo1WtgkFi3GvdWEyNuc4Vex7/9Dqbnpsf4JMydcfj9HCg4zUWFTL3Za6lapg5/w==" }, - "parse-glob": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/parse-glob/-/parse-glob-3.0.4.tgz", - "integrity": "sha1-ssN2z7EfNVE7rdFz7wu246OIORw=", + "http-basic": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/http-basic/-/http-basic-7.0.0.tgz", + "integrity": "sha1-gvClBr6UJzLsje6+6A50bvVzbbo=", + "dev": true, "requires": { - "glob-base": "^0.3.0", - "is-dotfile": "^1.0.0", - "is-extglob": "^1.0.0", - "is-glob": "^2.0.0" + "@types/concat-stream": "^1.6.0", + "@types/node": "^9.4.1", + "caseless": "~0.12.0", + "concat-stream": "^1.4.6", + "http-response-object": "^3.0.1", + "parse-cache-control": "^1.0.1" }, "dependencies": { - "is-extglob": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-1.0.0.tgz", - "integrity": "sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA=" - }, - "is-glob": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-2.0.1.tgz", - "integrity": "sha1-0Jb5JqPe1WAPP9/ZEZjLCIjC2GM=", - "requires": { - "is-extglob": "^1.0.0" - } + "@types/node": { + "version": "9.6.42", + "resolved": "https://registry.npmjs.org/@types/node/-/node-9.6.42.tgz", + "integrity": "sha512-SpeVQJFekfnEaZZO1yl4je/36upII36L7gOT4DBx51B1GeAB45mmDb3a5OBQB+ZeFxVVOP37r8Owsl940G/fBg==", + "dev": true } } }, - "parse-headers": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/parse-headers/-/parse-headers-2.0.1.tgz", - "integrity": "sha1-aug6eqJanZtwCswoaYzR8e1+lTY=", + "http-response-object": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/http-response-object/-/http-response-object-3.0.1.tgz", + "integrity": "sha512-6L0Fkd6TozA8kFSfh9Widst0wfza3U1Ex2RjJ6zNDK0vR1U1auUR6jY4Nn2Xl7CCy0ikFmxW1XcspVpb9RvwTg==", + "dev": true, "requires": { - "for-each": "^0.3.2", - "trim": "0.0.1" + "@types/node": "^9.3.0" + }, + "dependencies": { + "@types/node": { + "version": "9.6.42", + "resolved": "https://registry.npmjs.org/@types/node/-/node-9.6.42.tgz", + "integrity": "sha512-SpeVQJFekfnEaZZO1yl4je/36upII36L7gOT4DBx51B1GeAB45mmDb3a5OBQB+ZeFxVVOP37r8Owsl940G/fBg==", + "dev": true + } } }, - "parse-json": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-2.2.0.tgz", - "integrity": "sha1-9ID0BDTvgHQfhGkJn43qGPVaTck=", + "http-signature": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/http-signature/-/http-signature-1.2.0.tgz", + "integrity": "sha1-muzZJRFHcvPZW2WmCruPfBj7rOE=", + "dev": true, "requires": { - "error-ex": "^1.2.0" + "assert-plus": "^1.0.0", + "jsprim": "^1.2.2", + "sshpk": "^1.7.0" } }, - "parse-passwd": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/parse-passwd/-/parse-passwd-1.0.0.tgz", - "integrity": "sha1-bVuTSkVpk7I9N/QKOC1vFmao5cY=" - }, - "parseurl": { - "version": "1.3.2", - "resolved": "https://registry.npmjs.org/parseurl/-/parseurl-1.3.2.tgz", - "integrity": "sha1-/CidTtiZMRlGDBViUyYs3I3mW/M=" + "ignore-by-default": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/ignore-by-default/-/ignore-by-default-1.0.1.tgz", + "integrity": "sha1-SMptcvbGo68Aqa1K5odr44ieKwk=", + "dev": true }, - "pascalcase": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/pascalcase/-/pascalcase-0.1.1.tgz", - "integrity": "sha1-s2PlXoAGym/iF4TS2yK9FdeRfxQ=", + "import-lazy": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/import-lazy/-/import-lazy-2.1.0.tgz", + "integrity": "sha1-BWmOPUXIjo1+nZLLBYTnfwlvPkM=", "dev": true }, - "path-dirname": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/path-dirname/-/path-dirname-1.0.2.tgz", - "integrity": "sha1-zDPSTVJeCZpTiMAzbG4yuRYGCeA=", + "imurmurhash": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/imurmurhash/-/imurmurhash-0.1.4.tgz", + "integrity": "sha1-khi5srkoojixPcT7a21XbyMUU+o=", "dev": true }, - "path-exists": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-2.1.0.tgz", - "integrity": "sha1-D+tsZPD8UY2adU3V77YscCJ2H0s=", + "inflight": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", + "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=", "requires": { - "pinkie-promise": "^2.0.0" + "once": "^1.3.0", + "wrappy": "1" } }, - "path-is-absolute": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", - "integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=" + "inherits": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", + "integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=" }, - "path-is-inside": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/path-is-inside/-/path-is-inside-1.0.2.tgz", - "integrity": "sha1-NlQX3t5EQw0cEa9hAn+s8HS9/FM=", + "ini": { + "version": "1.3.5", + "resolved": "https://registry.npmjs.org/ini/-/ini-1.3.5.tgz", + "integrity": "sha512-RZY5huIKCMRWDUqZlEi72f/lmXKMvuszcMBduliQ3nnWbx9X/ZBQO7DijMEYS9EhHBb2qacRUMtC7svLwe0lcw==", "dev": true }, - "path-key": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/path-key/-/path-key-2.0.1.tgz", - "integrity": "sha1-QRyttXTFoUDTpLGRDUDYDMn0C0A=" - }, - "path-parse": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.5.tgz", - "integrity": "sha1-PBrfhx6pzWyUMbbqK9dKD/BVxME=" + "interpret": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/interpret/-/interpret-1.2.0.tgz", + "integrity": "sha512-mT34yGKMNceBQUoVn7iCDKDntA7SC6gycMAWzGx1z/CMCTV7b2AAtXlo3nRyHZ1FelRkQbQjprHSYGwzLtkVbw==", + "dev": true }, - "path-to-regexp": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-0.1.7.tgz", - "integrity": "sha1-32BBeABfUi8V60SQ5yR6G/qmf4w=" + "invert-kv": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/invert-kv/-/invert-kv-1.0.0.tgz", + "integrity": "sha1-EEqOSqym09jNFXqO+L+rLXo//bY=" }, - "path-type": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/path-type/-/path-type-1.1.0.tgz", - "integrity": "sha1-WcRPfuSR2nBNpBXaWkBwuk+P5EE=", + "is-accessor-descriptor": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-0.1.6.tgz", + "integrity": "sha1-qeEss66Nh2cn7u84Q/igiXtcmNY=", + "dev": true, "requires": { - "graceful-fs": "^4.1.2", - "pify": "^2.0.0", - "pinkie-promise": "^2.0.0" + "kind-of": "^3.0.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, + "requires": { + "is-buffer": "^1.1.5" + } + } } }, - "pathval": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/pathval/-/pathval-1.1.0.tgz", - "integrity": "sha1-uULm1L3mUwBe9rcTYd74cn0GReA=", - "dev": true + "is-arrayish": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/is-arrayish/-/is-arrayish-0.2.1.tgz", + "integrity": "sha1-d8mYQFJ6qOyxqLppe4BkWnqSap0=" }, - "pause-stream": { - "version": "0.0.11", - "resolved": "https://registry.npmjs.org/pause-stream/-/pause-stream-0.0.11.tgz", - "integrity": "sha1-/lo0sMvOErWqaitAPuLnO2AvFEU=", + "is-binary-path": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-binary-path/-/is-binary-path-1.0.1.tgz", + "integrity": "sha1-dfFmQrSA8YenEcgUFh/TpKdlWJg=", "dev": true, "requires": { - "through": "~2.3" + "binary-extensions": "^1.0.0" } }, - "pegjs": { - "version": "0.10.0", - "resolved": "https://registry.npmjs.org/pegjs/-/pegjs-0.10.0.tgz", - "integrity": "sha1-z4uvrm7d/0tafvsYUmnqr0YQ3b0=", + "is-buffer": { + "version": "1.1.6", + "resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-1.1.6.tgz", + "integrity": "sha512-NcdALwpXkTm5Zvvbk7owOUSvVvBKDgKP5/ewfXEznmQFfs4ZRmanOeKBTjRVjka3QFoN6XJ+9F3USqfHqTaU5w==", "dev": true }, - "performance-now": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/performance-now/-/performance-now-2.1.0.tgz", - "integrity": "sha1-Ywn04OX6kT7BxpMHrjZLSzd8nns=" + "is-callable": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/is-callable/-/is-callable-1.1.4.tgz", + "integrity": "sha512-r5p9sxJjYnArLjObpjA4xu5EKI3CuKHkJXMhT7kwbpUyIFD1n5PMAsoPvWnvtZiNz7LjkYDRZhd7FlI0eMijEA==" }, - "pify": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", - "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=" + "is-ci": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/is-ci/-/is-ci-1.2.1.tgz", + "integrity": "sha512-s6tfsaQaQi3JNciBH6shVqEDvhGut0SUXr31ag8Pd8BBbVVlcGfWhpPmEOoM6RJ5TFhbypvf5yyRw/VXW1IiWg==", + "dev": true, + "requires": { + "ci-info": "^1.5.0" + } }, - "pinkie": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/pinkie/-/pinkie-2.0.4.tgz", - "integrity": "sha1-clVrgM+g1IqXToDnckjoDtT3+HA=" + "is-data-descriptor": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-0.1.4.tgz", + "integrity": "sha1-C17mSDiOLIYCgueT8YVv7D8wG1Y=", + "dev": true, + "requires": { + "kind-of": "^3.0.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, + "requires": { + "is-buffer": "^1.1.5" + } + } + } }, - "pinkie-promise": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/pinkie-promise/-/pinkie-promise-2.0.1.tgz", - "integrity": "sha1-ITXW36ejWMBprJsXh3YogihFD/o=", + "is-descriptor": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-0.1.6.tgz", + "integrity": "sha512-avDYr0SB3DwO9zsMov0gKCESFYqCnE4hq/4z3TdUlukEy5t9C0YRq7HLrsN52NAcqXKaepeCD0n+B0arnVG3Hg==", + "dev": true, "requires": { - "pinkie": "^2.0.0" + "is-accessor-descriptor": "^0.1.6", + "is-data-descriptor": "^0.1.4", + "kind-of": "^5.0.0" + }, + "dependencies": { + "kind-of": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-5.1.0.tgz", + "integrity": "sha512-NGEErnH6F2vUuXDh+OlbcKW7/wOcfdRHaZ7VWtqCztfHri/++YKmP51OdWeGPuqCOba6kk2OTe5d02VmTB80Pw==", + "dev": true + } } }, - "posix-character-classes": { + "is-extendable": { "version": "0.1.1", - "resolved": "https://registry.npmjs.org/posix-character-classes/-/posix-character-classes-0.1.1.tgz", - "integrity": "sha1-AerA/jta9xoqbAL+q7jB/vfgDqs=", + "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-0.1.1.tgz", + "integrity": "sha1-YrEQ4omkcUGOPsNqYX1HLjAd/Ik=", "dev": true }, - "prelude-ls": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.1.2.tgz", - "integrity": "sha1-IZMqVJ9eUv/ZqCf1cOBL5iqX2lQ=", + "is-extglob": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", + "integrity": "sha1-qIwCU1eR8C7TfHahueqXc8gz+MI=", "dev": true }, - "prepend-http": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/prepend-http/-/prepend-http-1.0.4.tgz", - "integrity": "sha1-1PRWKwzjaW5BrFLQ4ALlemNdxtw=" - }, - "preserve": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/preserve/-/preserve-0.2.0.tgz", - "integrity": "sha1-gV7R9uvGWSb4ZbMQwHE7yzMVzks=" - }, - "prettier": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/prettier/-/prettier-1.11.1.tgz", - "integrity": "sha512-T/KD65Ot0PB97xTrG8afQ46x3oiVhnfGjGESSI9NWYcG92+OUPZKkwHqGWXH2t9jK1crnQjubECW0FuOth+hxw==" - }, - "pretty-bytes": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/pretty-bytes/-/pretty-bytes-4.0.2.tgz", - "integrity": "sha1-sr+C5zUNZcbDOqlaqlpPYyf2HNk=" - }, - "private": { - "version": "0.1.8", - "resolved": "https://registry.npmjs.org/private/-/private-0.1.8.tgz", - "integrity": "sha512-VvivMrbvd2nKkiG38qjULzlc+4Vx4wm/whI9pQD35YrARNnhxeiRktSOhSukRLFNlzg6Br/cJPet5J/u19r/mg==" - }, - "process": { - "version": "0.5.2", - "resolved": "https://registry.npmjs.org/process/-/process-0.5.2.tgz", - "integrity": "sha1-FjjYqONML0QKkduVq5rrZ3/Bhc8=" - }, - "process-nextick-args": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.0.tgz", - "integrity": "sha512-MtEC1TqN0EU5nephaJ4rAtThHtC86dNN9qCuEhtshvpVBkAW5ZO7BASN9REnF9eoXGcRub+pFuKEpOHE+HbEMw==" - }, - "promise": { - "version": "8.0.2", - "resolved": "https://registry.npmjs.org/promise/-/promise-8.0.2.tgz", - "integrity": "sha512-EIyzM39FpVOMbqgzEHhxdrEhtOSDOtjMZQ0M6iVfCE+kWNgCkAyOdnuCWqfmflylftfadU6FkiMgHZA2kUzwRw==", - "dev": true, - "requires": { - "asap": "~2.0.6" - } - }, - "proxy-addr": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.3.tgz", - "integrity": "sha512-jQTChiCJteusULxjBp8+jftSQE5Obdl3k4cnmLA6WXtK6XFuWRnvVL7aCiBqaLPM8c4ph0S4tKna8XvmIwEnXQ==", + "is-fullwidth-code-point": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz", + "integrity": "sha1-754xOG8DGn8NZDr4L95QxFfvAMs=", "requires": { - "forwarded": "~0.1.2", - "ipaddr.js": "1.6.0" + "number-is-nan": "^1.0.0" } }, - "prr": { + "is-function": { "version": "1.0.1", - "resolved": "https://registry.npmjs.org/prr/-/prr-1.0.1.tgz", - "integrity": "sha1-0/wRS6BplaRexok/SEzrHXj19HY=" + "resolved": "https://registry.npmjs.org/is-function/-/is-function-1.0.1.tgz", + "integrity": "sha1-Es+5i2W1fdPRk6MSH19uL0N2ArU=" }, - "ps-tree": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/ps-tree/-/ps-tree-1.1.0.tgz", - "integrity": "sha1-tCGyQUDWID8e08dplrRCewjowBQ=", + "is-glob": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.0.tgz", + "integrity": "sha1-lSHHaEXMJhCoUgPd8ICpWML/q8A=", "dev": true, "requires": { - "event-stream": "~3.3.0" + "is-extglob": "^2.1.1" } }, - "pseudomap": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/pseudomap/-/pseudomap-1.0.2.tgz", - "integrity": "sha1-8FKijacOYYkX7wqKw0wa5aaChrM=" + "is-hex-prefixed": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-hex-prefixed/-/is-hex-prefixed-1.0.0.tgz", + "integrity": "sha1-fY035q135dEnFIkTxXPggtd39VQ=" }, - "pstree.remy": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/pstree.remy/-/pstree.remy-1.1.0.tgz", - "integrity": "sha512-q5I5vLRMVtdWa8n/3UEzZX7Lfghzrg9eG2IKk2ENLSofKRCXVqMvMUHxCKgXNaqH/8ebhBxrqftHWnyTFweJ5Q==", + "is-installed-globally": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/is-installed-globally/-/is-installed-globally-0.1.0.tgz", + "integrity": "sha1-Df2Y9akRFxbdU13aZJL2e/PSWoA=", "dev": true, "requires": { - "ps-tree": "^1.1.0" + "global-dirs": "^0.1.0", + "is-path-inside": "^1.0.0" } }, - "punycode": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/punycode/-/punycode-1.4.1.tgz", - "integrity": "sha1-wNWmOycYgArY4esPpSachN1BhF4=" - }, - "qs": { - "version": "6.5.1", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.5.1.tgz", - "integrity": "sha512-eRzhrN1WSINYCDCbrz796z37LOe3m5tmW7RQf6oBntukAG1nmovJvhnwHHRMAfeoItc1m2Hk02WER2aQ/iqs+A==" - }, - "query-string": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/query-string/-/query-string-5.1.1.tgz", - "integrity": "sha512-gjWOsm2SoGlgLEdAGt7a6slVOk9mGiXmPFMqrEhLQ68rhQuBnpfs3+EmlvqKyxnCo9/PPlF+9MtY02S1aFg+Jw==", - "requires": { - "decode-uri-component": "^0.2.0", - "object-assign": "^4.1.0", - "strict-uri-encode": "^1.0.0" - } + "is-npm": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-npm/-/is-npm-1.0.0.tgz", + "integrity": "sha1-8vtjpl5JBbQGyGBydloaTceTufQ=", + "dev": true }, - "randomatic": { - "version": "1.1.7", - "resolved": "https://registry.npmjs.org/randomatic/-/randomatic-1.1.7.tgz", - "integrity": "sha512-D5JUjPyJbaJDkuAazpVnSfVkLlpeO3wDlPROTMLGKG1zMFNFRgrciKo1ltz/AzNTkqE0HzDx655QOL51N06how==", + "is-number": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/is-number/-/is-number-3.0.0.tgz", + "integrity": "sha1-JP1iAaR4LPUFYcgQJ2r8fRLXEZU=", + "dev": true, "requires": { - "is-number": "^3.0.0", - "kind-of": "^4.0.0" + "kind-of": "^3.0.2" }, "dependencies": { "kind-of": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-4.0.0.tgz", - "integrity": "sha1-IIE989cSkosgc3hpGkUGb65y3Vc=", + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, "requires": { "is-buffer": "^1.1.5" } } } }, - "randomhex": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/randomhex/-/randomhex-0.1.5.tgz", - "integrity": "sha1-us7vmCMpCRQA8qKRLGzQLxCU9YU=" + "is-obj": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-obj/-/is-obj-1.0.1.tgz", + "integrity": "sha1-PkcprB9f3gJc19g6iW2rn09n2w8=", + "dev": true }, - "range-parser": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/range-parser/-/range-parser-1.2.0.tgz", - "integrity": "sha1-9JvmtIeJTdxA3MlKMi9hEJLgDV4=" + "is-path-inside": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-path-inside/-/is-path-inside-1.0.1.tgz", + "integrity": "sha1-jvW33lBDej/cprToZe96pVy0gDY=", + "dev": true, + "requires": { + "path-is-inside": "^1.0.1" + } }, - "raw-body": { - "version": "2.3.2", - "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-2.3.2.tgz", - "integrity": "sha1-vNYMd9Prk83gBQKVw/N5OJvIj4k=", + "is-plain-object": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/is-plain-object/-/is-plain-object-2.0.4.tgz", + "integrity": "sha512-h5PpgXkWitc38BBMYawTYMWJHFZJVnBquFE57xFpjB8pJFiF6gZ+bU+WyI/yqXiFR5mdLsgYNaPe8uao6Uv9Og==", + "dev": true, + "requires": { + "isobject": "^3.0.1" + } + }, + "is-redirect": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-redirect/-/is-redirect-1.0.0.tgz", + "integrity": "sha1-HQPd7VO9jbDzDCbk+V02/HyH3CQ=", + "dev": true + }, + "is-retry-allowed": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/is-retry-allowed/-/is-retry-allowed-1.1.0.tgz", + "integrity": "sha1-EaBgVotnM5REAz0BJaYaINVk+zQ=", + "dev": true + }, + "is-stream": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-1.1.0.tgz", + "integrity": "sha1-EtSj3U5o4Lec6428hBc66A2RykQ=", + "dev": true + }, + "is-typedarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-typedarray/-/is-typedarray-1.0.0.tgz", + "integrity": "sha1-5HnICFjfDBsR3dppQPlgEfzaSpo=", + "dev": true + }, + "is-utf8": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/is-utf8/-/is-utf8-0.2.1.tgz", + "integrity": "sha1-Sw2hRCEE0bM2NA6AeX6GXPOffXI=" + }, + "is-windows": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-windows/-/is-windows-1.0.2.tgz", + "integrity": "sha512-eXK1UInq2bPmjyX6e3VHIzMLobc4J94i4AWn+Hpq3OU5KkrRC96OAcR3PRJ/pGu6m8TRnBHP9dkXQVsT/COVIA==", + "dev": true + }, + "isarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", + "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", + "dev": true + }, + "isexe": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", + "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=", + "dev": true + }, + "isobject": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", + "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=", + "dev": true + }, + "isstream": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/isstream/-/isstream-0.1.2.tgz", + "integrity": "sha1-R+Y/evVa+m+S4VAOaQ64uFKcCZo=", + "dev": true + }, + "istanbul": { + "version": "0.4.5", + "resolved": "https://registry.npmjs.org/istanbul/-/istanbul-0.4.5.tgz", + "integrity": "sha1-ZcfXPUxNqE1POsMQuRj7C4Azczs=", + "dev": true, "requires": { - "bytes": "3.0.0", - "http-errors": "1.6.2", - "iconv-lite": "0.4.19", - "unpipe": "1.0.0" + "abbrev": "1.0.x", + "async": "1.x", + "escodegen": "1.8.x", + "esprima": "2.7.x", + "glob": "^5.0.15", + "handlebars": "^4.0.1", + "js-yaml": "3.x", + "mkdirp": "0.5.x", + "nopt": "3.x", + "once": "1.x", + "resolve": "1.1.x", + "supports-color": "^3.1.0", + "which": "^1.1.1", + "wordwrap": "^1.0.0" }, "dependencies": { - "depd": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/depd/-/depd-1.1.1.tgz", - "integrity": "sha1-V4O04cRZ8G+lyif5kfPQbnoxA1k=" + "abbrev": { + "version": "1.0.9", + "resolved": "https://registry.npmjs.org/abbrev/-/abbrev-1.0.9.tgz", + "integrity": "sha1-kbR5JYinc4wl813W9jdSovh3YTU=", + "dev": true + }, + "glob": { + "version": "5.0.15", + "resolved": "https://registry.npmjs.org/glob/-/glob-5.0.15.tgz", + "integrity": "sha1-G8k2ueAvSmA/zCIuz3Yz0wuLk7E=", + "dev": true, + "requires": { + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "2 || 3", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" + } + }, + "has-flag": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-1.0.0.tgz", + "integrity": "sha1-nZ55MWXOAXoA8AQYxD+UKnsdEfo=", + "dev": true }, - "http-errors": { - "version": "1.6.2", - "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.6.2.tgz", - "integrity": "sha1-CgAsyFcHGSp+eUbO7cERVfYOxzY=", + "nopt": { + "version": "3.0.6", + "resolved": "https://registry.npmjs.org/nopt/-/nopt-3.0.6.tgz", + "integrity": "sha1-xkZdvwirzU2zWTF/eaxopkayj/k=", + "dev": true, "requires": { - "depd": "1.1.1", - "inherits": "2.0.3", - "setprototypeof": "1.0.3", - "statuses": ">= 1.3.1 < 2" + "abbrev": "1" } }, - "setprototypeof": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.0.3.tgz", - "integrity": "sha1-ZlZ+NwQ+608E2RvWWMDL77VbjgQ=" + "resolve": { + "version": "1.1.7", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.1.7.tgz", + "integrity": "sha1-IDEU2CrSxe2ejgQRs5ModeiJ6Xs=", + "dev": true + }, + "supports-color": { + "version": "3.2.3", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-3.2.3.tgz", + "integrity": "sha1-ZawFBLOVQXHYpklGsq48u4pfVPY=", + "dev": true, + "requires": { + "has-flag": "^1.0.0" + } } } }, - "rc": { - "version": "1.2.6", - "resolved": "https://registry.npmjs.org/rc/-/rc-1.2.6.tgz", - "integrity": "sha1-6xiYnG1PTxYsOZ953dKfODVWgJI=", + "js-sha3": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/js-sha3/-/js-sha3-0.6.1.tgz", + "integrity": "sha1-W4n3enR3Z5h39YxKB1JAk0sflcA=", + "dev": true + }, + "js-yaml": { + "version": "3.12.1", + "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.12.1.tgz", + "integrity": "sha512-um46hB9wNOKlwkHgiuyEVAybXBjwFUV0Z/RaHJblRd9DXltue9FTYvzCr9ErQrK9Adz5MU4gHWVaNUfdmrC8qA==", "dev": true, "requires": { - "deep-extend": "~0.4.0", - "ini": "~1.3.0", - "minimist": "^1.2.0", - "strip-json-comments": "~2.0.1" + "argparse": "^1.0.7", + "esprima": "^4.0.0" }, "dependencies": { - "minimist": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz", - "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=", + "esprima": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/esprima/-/esprima-4.0.1.tgz", + "integrity": "sha512-eGuFFw7Upda+g4p+QHvnW0RyTX/SVeJBDM/gCtMARO0cLuT2HcEKnTPvhjV6aGeqrCB/sbNop0Kszm0jsaWU4A==", "dev": true } } }, - "read-chunk": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/read-chunk/-/read-chunk-2.1.0.tgz", - "integrity": "sha1-agTAkoAF7Z1C4aasVgDhnLx/9lU=", - "requires": { - "pify": "^3.0.0", - "safe-buffer": "^5.1.1" - }, - "dependencies": { - "pify": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", - "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=" - } - } + "jsbn": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/jsbn/-/jsbn-0.1.1.tgz", + "integrity": "sha1-peZUwuWi3rXyAdls77yoDA7y9RM=", + "dev": true }, - "read-pkg": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-1.1.0.tgz", - "integrity": "sha1-9f+qXs0pyzHAR0vKfXVra7KePyg=", - "requires": { - "load-json-file": "^1.0.0", - "normalize-package-data": "^2.3.2", - "path-type": "^1.0.0" - } + "json-schema": { + "version": "0.2.3", + "resolved": "https://registry.npmjs.org/json-schema/-/json-schema-0.2.3.tgz", + "integrity": "sha1-tIDIkuWaLwWVTOcnvT8qTogvnhM=", + "dev": true }, - "read-pkg-up": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/read-pkg-up/-/read-pkg-up-1.0.1.tgz", - "integrity": "sha1-nWPBMnbAZZGNV/ACpX9AobZD+wI=", - "requires": { - "find-up": "^1.0.0", - "read-pkg": "^1.0.0" - } + "json-schema-traverse": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", + "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", + "dev": true }, - "readable-stream": { - "version": "2.3.5", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.5.tgz", - "integrity": "sha512-tK0yDhrkygt/knjowCUiWP9YdV7c5R+8cR0r/kt9ZhBU906Fs6RpQJCEilamRJj1Nx2rWI6LkW9gKqjTkshhEw==", + "json-stringify-safe": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/json-stringify-safe/-/json-stringify-safe-5.0.1.tgz", + "integrity": "sha1-Epai1Y/UXxmg9s4B1lcB4sc1tus=", + "dev": true + }, + "jsonfile": { + "version": "2.4.0", + "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-2.4.0.tgz", + "integrity": "sha1-NzaitCi4e72gzIO1P6PWM6NcKug=", "requires": { - "core-util-is": "~1.0.0", - "inherits": "~2.0.3", - "isarray": "~1.0.0", - "process-nextick-args": "~2.0.0", - "safe-buffer": "~5.1.1", - "string_decoder": "~1.0.3", - "util-deprecate": "~1.0.1" + "graceful-fs": "^4.1.6" } }, - "readdirp": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-2.1.0.tgz", - "integrity": "sha1-TtCtBg3zBzMAxIRANz9y0cxkLXg=", + "jsprim": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/jsprim/-/jsprim-1.4.1.tgz", + "integrity": "sha1-MT5mvB5cwG5Di8G3SZwuXFastqI=", "dev": true, "requires": { - "graceful-fs": "^4.1.2", - "minimatch": "^3.0.2", - "readable-stream": "^2.0.2", - "set-immediate-shim": "^1.0.1" + "assert-plus": "1.0.0", + "extsprintf": "1.3.0", + "json-schema": "0.2.3", + "verror": "1.10.0" } }, - "recast": { - "version": "0.14.7", - "resolved": "https://registry.npmjs.org/recast/-/recast-0.14.7.tgz", - "integrity": "sha512-/nwm9pkrcWagN40JeJhkPaRxiHXBRkXyRh/hgU088Z/v+qCy+zIHHY6bC6o7NaKAxPqtE6nD8zBH1LfU0/Wx6A==", + "keccakjs": { + "version": "0.2.3", + "resolved": "https://registry.npmjs.org/keccakjs/-/keccakjs-0.2.3.tgz", + "integrity": "sha512-BjLkNDcfaZ6l8HBG9tH0tpmDv3sS2mA7FNQxFHpCdzP3Gb2MVruXBSuoM66SnVxKJpAr5dKGdkHD+bDokt8fTg==", + "dev": true, "requires": { - "ast-types": "0.11.3", - "esprima": "~4.0.0", - "private": "~0.1.5", - "source-map": "~0.6.1" - }, - "dependencies": { - "source-map": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", - "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==" - } + "browserify-sha3": "^0.0.4", + "sha3": "^1.2.2" } }, - "rechoir": { - "version": "0.6.2", - "resolved": "https://registry.npmjs.org/rechoir/-/rechoir-0.6.2.tgz", - "integrity": "sha1-hSBLVNuoLVdC4oyWdW70OvUOM4Q=", + "kind-of": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-6.0.2.tgz", + "integrity": "sha512-s5kLOcnH0XqDO+FvuaLX8DDjZ18CGFk7VygH40QoKPUQhW4e2rvM0rwUq0t8IQDOwYSeLK01U90OjzBTme2QqA==", + "dev": true + }, + "klaw": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/klaw/-/klaw-1.3.1.tgz", + "integrity": "sha1-QIhDO0azsbolnXh4XY6W9zugJDk=", "requires": { - "resolve": "^1.1.6" + "graceful-fs": "^4.1.9" } }, - "regenerate": { - "version": "1.3.3", - "resolved": "https://registry.npmjs.org/regenerate/-/regenerate-1.3.3.tgz", - "integrity": "sha512-jVpo1GadrDAK59t/0jRx5VxYWQEDkkEKi6+HjE3joFVLfDOh9Xrdh0dF1eSq+BI/SwvTQ44gSscJ8N5zYL61sg==" - }, - "regenerator-runtime": { - "version": "0.11.1", - "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.11.1.tgz", - "integrity": "sha512-MguG95oij0fC3QV3URf4V2SDYGJhJnJGqvIIgdECeODCT98wSWDAJ94SSuVpYQUoTcGUIL6L4yNB7j1DFFHSBg==" - }, - "regenerator-transform": { - "version": "0.10.1", - "resolved": "https://registry.npmjs.org/regenerator-transform/-/regenerator-transform-0.10.1.tgz", - "integrity": "sha512-PJepbvDbuK1xgIgnau7Y90cwaAmO/LCLMI2mPvaXq2heGMR3aWW5/BQvYrhJ8jgmQjXewXvBjzfqKcVOmhjZ6Q==", + "latest-version": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/latest-version/-/latest-version-3.1.0.tgz", + "integrity": "sha1-ogU4P+oyKzO1rjsYq+4NwvNW7hU=", + "dev": true, "requires": { - "babel-runtime": "^6.18.0", - "babel-types": "^6.19.0", - "private": "^0.1.6" + "package-json": "^4.0.0" } }, - "regex-cache": { - "version": "0.4.4", - "resolved": "https://registry.npmjs.org/regex-cache/-/regex-cache-0.4.4.tgz", - "integrity": "sha512-nVIZwtCjkC9YgvWkpM55B5rBhBYRZhAaJbgcFYXXsHnbZ9UZI9nnVWYZpBlCqv9ho2eZryPnWrZGsOdPwVWXWQ==", + "lcid": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/lcid/-/lcid-1.0.0.tgz", + "integrity": "sha1-MIrMr6C8SDo4Z7S28rlQYlHRuDU=", "requires": { - "is-equal-shallow": "^0.1.3" + "invert-kv": "^1.0.0" } }, - "regex-not": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/regex-not/-/regex-not-1.0.2.tgz", - "integrity": "sha512-J6SDjUgDxQj5NusnOtdFxDwN/+HWykR8GELwctJ7mdqhcyy1xEc4SRFHUXvxTp661YaVKAjfRLZ9cCqS6tn32A==", + "levn": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/levn/-/levn-0.3.0.tgz", + "integrity": "sha1-OwmSTt+fCDwEkP3UwLxEIeBHZO4=", "dev": true, "requires": { - "extend-shallow": "^3.0.2", - "safe-regex": "^1.1.0" + "prelude-ls": "~1.1.2", + "type-check": "~0.3.2" } }, - "regexpu-core": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/regexpu-core/-/regexpu-core-2.0.0.tgz", - "integrity": "sha1-SdA4g3uNz4v6W5pCE5k45uoq4kA=", + "load-json-file": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-1.1.0.tgz", + "integrity": "sha1-lWkFcI1YtLq0wiYbBPWfMcmTdMA=", "requires": { - "regenerate": "^1.2.1", - "regjsgen": "^0.2.0", - "regjsparser": "^0.1.4" + "graceful-fs": "^4.1.2", + "parse-json": "^2.2.0", + "pify": "^2.0.0", + "pinkie-promise": "^2.0.0", + "strip-bom": "^2.0.0" } }, - "registry-auth-token": { - "version": "3.3.2", - "resolved": "https://registry.npmjs.org/registry-auth-token/-/registry-auth-token-3.3.2.tgz", - "integrity": "sha512-JL39c60XlzCVgNrO+qq68FoNb56w/m7JYvGR2jT5iR1xBrUA3Mfx5Twk5rqTThPmQKMWydGmq8oFtDlxfrmxnQ==", + "locate-path": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-2.0.0.tgz", + "integrity": "sha1-K1aLJl7slExtnA3pw9u7ygNUzY4=", "dev": true, "requires": { - "rc": "^1.1.6", - "safe-buffer": "^5.0.1" + "p-locate": "^2.0.0", + "path-exists": "^3.0.0" + }, + "dependencies": { + "path-exists": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", + "integrity": "sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=", + "dev": true + } } }, - "registry-url": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/registry-url/-/registry-url-3.1.0.tgz", - "integrity": "sha1-PU74cPc93h138M+aOBQyRE4XSUI=", - "dev": true, - "requires": { - "rc": "^1.0.1" - } + "lodash": { + "version": "4.17.11", + "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.11.tgz", + "integrity": "sha512-cQKh8igo5QUhZ7lg38DYWAxMvjSAKG0A8wGSVimP07SIUEK2UO+arSRKbRZWtelMtN5V0Hkwh5ryOto/SshYIg==" }, - "regjsgen": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/regjsgen/-/regjsgen-0.2.0.tgz", - "integrity": "sha1-bAFq3qxVT3WCP+N6wFuS1aTtsfc=" + "lodash.assign": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/lodash.assign/-/lodash.assign-4.2.0.tgz", + "integrity": "sha1-DZnzzNem0mHRm9rrkkUAXShYCOc=" }, - "regjsparser": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/regjsparser/-/regjsparser-0.1.5.tgz", - "integrity": "sha1-fuj4Tcb6eS0/0K4ijSS9lJ6tIFw=", + "lowercase-keys": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/lowercase-keys/-/lowercase-keys-1.0.1.tgz", + "integrity": "sha512-G2Lj61tXDnVFFOi8VZds+SoQjtQC3dgokKdDG2mTm1tx4m50NUHBOZSBwQQHyy0V12A0JTG4icfZQH+xPyh8VA==", + "dev": true + }, + "lru-cache": { + "version": "4.1.5", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-4.1.5.tgz", + "integrity": "sha512-sWZlbEP2OsHNkXrMl5GYk/jKk70MBng6UU4YI/qGDYbgf6YbP4EvmqISbXCoJiRKs+1bSpFHVgQxvJ17F2li5g==", + "dev": true, "requires": { - "jsesc": "~0.5.0" + "pseudomap": "^1.0.2", + "yallist": "^2.1.2" } }, - "remove-trailing-separator": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/remove-trailing-separator/-/remove-trailing-separator-1.1.0.tgz", - "integrity": "sha1-wkvOKig62tW8P1jg1IJJuSN52O8=" - }, - "repeat-element": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/repeat-element/-/repeat-element-1.1.2.tgz", - "integrity": "sha1-7wiaF40Ug7quTZPrmLT55OEdmQo=" - }, - "repeat-string": { - "version": "1.6.1", - "resolved": "https://registry.npmjs.org/repeat-string/-/repeat-string-1.6.1.tgz", - "integrity": "sha1-jcrkcOHIirwtYA//Sndihtp15jc=" - }, - "repeating": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/repeating/-/repeating-2.0.1.tgz", - "integrity": "sha1-UhTFOpJtNVJwdSf7q0FdvAjQbdo=", + "make-dir": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-1.3.0.tgz", + "integrity": "sha512-2w31R7SJtieJJnQtGc7RVL2StM2vGYVfqUOvUDxH6bC6aJTxPxTF0GnIgCyu7tjockiUWAYQRbxa7vKn34s5sQ==", + "dev": true, "requires": { - "is-finite": "^1.0.0" + "pify": "^3.0.0" + }, + "dependencies": { + "pify": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", + "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=", + "dev": true + } } }, - "replace-ext": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/replace-ext/-/replace-ext-0.0.1.tgz", - "integrity": "sha1-KbvZIHinOfC8zitO5B6DeVNSKSQ=" + "map-cache": { + "version": "0.2.2", + "resolved": "https://registry.npmjs.org/map-cache/-/map-cache-0.2.2.tgz", + "integrity": "sha1-wyq9C9ZSXZsFFkW7TyasXcmKDb8=", + "dev": true }, - "req-cwd": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/req-cwd/-/req-cwd-1.0.1.tgz", - "integrity": "sha1-DXOurpJm5penj3l2AZZ352rPD/8=", + "map-visit": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/map-visit/-/map-visit-1.0.0.tgz", + "integrity": "sha1-7Nyo8TFE5mDxtb1B8S80edmN+48=", "dev": true, "requires": { - "req-from": "^1.0.1" + "object-visit": "^1.0.0" } }, - "req-from": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/req-from/-/req-from-1.0.1.tgz", - "integrity": "sha1-v4HaUUeUfTLRO5R9wSpYrUWHNQ4=", + "memorystream": { + "version": "0.3.1", + "resolved": "https://registry.npmjs.org/memorystream/-/memorystream-0.3.1.tgz", + "integrity": "sha1-htcJCzDORV1j+64S3aUaR93K+bI=" + }, + "micromatch": { + "version": "3.1.10", + "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-3.1.10.tgz", + "integrity": "sha512-MWikgl9n9M3w+bpsY3He8L+w9eF9338xRl8IAO5viDizwSzziFEyUzo2xrrloB64ADbTf8uA8vRqqttDTOmccg==", "dev": true, "requires": { - "resolve-from": "^2.0.0" - }, - "dependencies": { - "resolve-from": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-2.0.0.tgz", - "integrity": "sha1-lICrIOlP+h2egKgEx+oUdhGWa1c=", - "dev": true - } + "arr-diff": "^4.0.0", + "array-unique": "^0.3.2", + "braces": "^2.3.1", + "define-property": "^2.0.2", + "extend-shallow": "^3.0.2", + "extglob": "^2.0.4", + "fragment-cache": "^0.2.1", + "kind-of": "^6.0.2", + "nanomatch": "^1.2.9", + "object.pick": "^1.3.0", + "regex-not": "^1.0.0", + "snapdragon": "^0.8.1", + "to-regex": "^3.0.2" } }, - "request": { - "version": "2.85.0", - "resolved": "https://registry.npmjs.org/request/-/request-2.85.0.tgz", - "integrity": "sha512-8H7Ehijd4js+s6wuVPLjwORxD4zeuyjYugprdOXlPSqaApmL/QOy+EB/beICHVCHkGMKNh5rvihb5ov+IDw4mg==", - "requires": { - "aws-sign2": "~0.7.0", - "aws4": "^1.6.0", - "caseless": "~0.12.0", - "combined-stream": "~1.0.5", - "extend": "~3.0.1", - "forever-agent": "~0.6.1", - "form-data": "~2.3.1", - "har-validator": "~5.0.3", - "hawk": "~6.0.2", - "http-signature": "~1.2.0", - "is-typedarray": "~1.0.0", - "isstream": "~0.1.2", - "json-stringify-safe": "~5.0.1", - "mime-types": "~2.1.17", - "oauth-sign": "~0.8.2", - "performance-now": "^2.1.0", - "qs": "~6.5.1", - "safe-buffer": "^5.1.1", - "stringstream": "~0.0.5", - "tough-cookie": "~2.3.3", - "tunnel-agent": "^0.6.0", - "uuid": "^3.1.0" - } + "mime-db": { + "version": "1.38.0", + "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.38.0.tgz", + "integrity": "sha512-bqVioMFFzc2awcdJZIzR3HjZFX20QhilVS7hytkKrv7xFAn8bM1gzc/FOX2awLISvWe0PV8ptFKcon+wZ5qYkg==", + "dev": true }, - "request-promise-core": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/request-promise-core/-/request-promise-core-1.1.1.tgz", - "integrity": "sha1-Pu4AssWqgyOc+wTFcA2jb4HNCLY=", + "mime-types": { + "version": "2.1.22", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.22.tgz", + "integrity": "sha512-aGl6TZGnhm/li6F7yx82bJiBZwgiEa4Hf6CNr8YO+r5UHr53tSTYZb102zyU50DOWWKeOv0uQLRL0/9EiKWCog==", "dev": true, "requires": { - "lodash": "^4.13.1" + "mime-db": "~1.38.0" } }, - "request-promise-native": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/request-promise-native/-/request-promise-native-1.0.5.tgz", - "integrity": "sha1-UoF3D2jgyXGeUWP9P6tIIhX0/aU=", - "dev": true, + "mimic-response": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-1.0.1.tgz", + "integrity": "sha512-j5EctnkH7amfV/q5Hgmoal1g2QHFJRraOtmx0JpIqkxhBhI/lJSl1nMpQ45hVarwNETOoWEimndZ4QK0RHxuxQ==" + }, + "min-document": { + "version": "2.19.0", + "resolved": "https://registry.npmjs.org/min-document/-/min-document-2.19.0.tgz", + "integrity": "sha1-e9KC4/WELtKVu3SM3Z8f+iyCRoU=", "requires": { - "request-promise-core": "1.1.1", - "stealthy-require": "^1.1.0", - "tough-cookie": ">=2.3.3" + "dom-walk": "^0.1.0" } }, - "require-directory": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/require-directory/-/require-directory-2.1.1.tgz", - "integrity": "sha1-jGStX9MNqxyXbiNE/+f3kqam30I=" - }, - "require-from-string": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/require-from-string/-/require-from-string-1.2.1.tgz", - "integrity": "sha1-UpyczvJzgK3+yaL5ZbZJu+5jZBg=" + "minimalistic-assert": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/minimalistic-assert/-/minimalistic-assert-1.0.1.tgz", + "integrity": "sha512-UtJcAD4yEaGtjPezWuO9wC4nwUnVH/8/Im3yEHQP4b67cXlD/Qr9hdITCU1xDbSEXg2XKNaP8jsReV7vQd00/A==" }, - "require-main-filename": { + "minimalistic-crypto-utils": { "version": "1.0.1", - "resolved": "https://registry.npmjs.org/require-main-filename/-/require-main-filename-1.0.1.tgz", - "integrity": "sha1-l/cXtp1IeE9fUmpsWqj/3aBVpNE=" + "resolved": "https://registry.npmjs.org/minimalistic-crypto-utils/-/minimalistic-crypto-utils-1.0.1.tgz", + "integrity": "sha1-9sAMHAsIIkblxNmd+4x8CDsrWCo=" }, - "resolve": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.6.0.tgz", - "integrity": "sha512-mw7JQNu5ExIkcw4LPih0owX/TZXjD/ZUF/ZQ/pDnkw3ZKhDcZZw5klmBlj6gVMwjQ3Pz5Jgu7F3d0jcDVuEWdw==", + "minimatch": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", + "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", "requires": { - "path-parse": "^1.0.5" + "brace-expansion": "^1.1.7" } }, - "resolve-cwd": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/resolve-cwd/-/resolve-cwd-2.0.0.tgz", - "integrity": "sha1-AKn3OHVW4nA46uIyyqNypqWbZlo=", + "minimist": { + "version": "0.0.8", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-0.0.8.tgz", + "integrity": "sha1-hX/Kv8M5fSYluCKCYuhqp6ARsF0=" + }, + "mixin-deep": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/mixin-deep/-/mixin-deep-1.3.1.tgz", + "integrity": "sha512-8ZItLHeEgaqEvd5lYBXfm4EZSFCX29Jb9K+lAHhDKzReKBQKj3R+7NOF6tjqYi9t4oI8VUfaWITJQm86wnXGNQ==", + "dev": true, "requires": { - "resolve-from": "^3.0.0" + "for-in": "^1.0.2", + "is-extendable": "^1.0.1" + }, + "dependencies": { + "is-extendable": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-1.0.1.tgz", + "integrity": "sha512-arnXMxT1hhoKo9k1LZdmlNyJdDDfy2v0fXjFlmok4+i8ul/6WlbVge9bhM74OpNPQPMGUToDtz+KXa1PneJxOA==", + "dev": true, + "requires": { + "is-plain-object": "^2.0.4" + } + } } }, - "resolve-dir": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/resolve-dir/-/resolve-dir-1.0.1.tgz", - "integrity": "sha1-eaQGRMNivoLybv/nOcm7U4IEb0M=", + "mkdirp": { + "version": "0.5.1", + "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.1.tgz", + "integrity": "sha1-MAV0OOrGz3+MR2fzhkjWaX11yQM=", "requires": { - "expand-tilde": "^2.0.0", - "global-modules": "^1.0.0" + "minimist": "0.0.8" } }, - "resolve-from": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-3.0.0.tgz", - "integrity": "sha1-six699nWiBvItuZTM17rywoYh0g=" - }, - "resolve-url": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/resolve-url/-/resolve-url-0.2.1.tgz", - "integrity": "sha1-LGN/53yJOv0qZj/iGqkIAGjiBSo=", - "dev": true - }, - "responselike": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/responselike/-/responselike-1.0.2.tgz", - "integrity": "sha1-kYcg7ztjHFZCvgaPFa3lpG9Loec=", + "mocha": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/mocha/-/mocha-4.1.0.tgz", + "integrity": "sha512-0RVnjg1HJsXY2YFDoTNzcc1NKhYuXKRrBAG2gDygmJJA136Cs2QlRliZG1mA0ap7cuaT30mw16luAeln+4RiNA==", "requires": { - "lowercase-keys": "^1.0.0" + "browser-stdout": "1.3.0", + "commander": "2.11.0", + "debug": "3.1.0", + "diff": "3.3.1", + "escape-string-regexp": "1.0.5", + "glob": "7.1.2", + "growl": "1.10.3", + "he": "1.1.1", + "mkdirp": "0.5.1", + "supports-color": "4.4.0" } }, - "restore-cursor": { + "ms": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-2.0.0.tgz", - "integrity": "sha1-n37ih/gv0ybU/RYpI9YhKe7g368=", - "requires": { - "onetime": "^2.0.0", - "signal-exit": "^3.0.2" - } + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" }, - "ret": { - "version": "0.1.15", - "resolved": "https://registry.npmjs.org/ret/-/ret-0.1.15.tgz", - "integrity": "sha512-TTlYpa+OL+vMMNG24xSlQGEJ3B/RzEfUlLct7b5G/ytav+wPrplCpVMFuwzXbkecJrb6IYo1iFb0S9v37754mg==", - "dev": true + "nan": { + "version": "2.12.1", + "resolved": "https://registry.npmjs.org/nan/-/nan-2.12.1.tgz", + "integrity": "sha512-JY7V6lRkStKcKTvHO5NVSQRv+RV+FIL5pvDoLiAtSL9pKlC5x9PKQcZDsq7m4FO4d57mkhC6Z+QhAh3Jdk5JFw==", + "dev": true, + "optional": true }, - "right-align": { - "version": "0.1.3", - "resolved": "https://registry.npmjs.org/right-align/-/right-align-0.1.3.tgz", - "integrity": "sha1-YTObci/mo1FWiSENJOFMlhSGE+8=", + "nanomatch": { + "version": "1.2.13", + "resolved": "https://registry.npmjs.org/nanomatch/-/nanomatch-1.2.13.tgz", + "integrity": "sha512-fpoe2T0RbHwBTBUOftAfBPaDEi06ufaUai0mE6Yn1kacc3SnTErfb/h+X94VXzI64rKFHYImXSvdwGGCmwOqCA==", "dev": true, - "optional": true, "requires": { - "align-text": "^0.1.1" + "arr-diff": "^4.0.0", + "array-unique": "^0.3.2", + "define-property": "^2.0.2", + "extend-shallow": "^3.0.2", + "fragment-cache": "^0.2.1", + "is-windows": "^1.0.2", + "kind-of": "^6.0.2", + "object.pick": "^1.3.0", + "regex-not": "^1.0.0", + "snapdragon": "^0.8.1", + "to-regex": "^3.0.1" } }, - "rimraf": { - "version": "2.6.2", - "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.6.2.tgz", - "integrity": "sha512-lreewLK/BlghmxtfH36YYVg1i8IAce4TI7oao75I1g245+6BctqTVQiBP3YUJ9C6DQOXJmkYR9X9fCLtCOJc5w==", + "nodemon": { + "version": "1.18.10", + "resolved": "https://registry.npmjs.org/nodemon/-/nodemon-1.18.10.tgz", + "integrity": "sha512-we51yBb1TfEvZamFchRgcfLbVYgg0xlGbyXmOtbBzDwxwgewYS/YbZ5tnlnsH51+AoSTTsT3A2E/FloUbtH8cQ==", + "dev": true, "requires": { - "glob": "^7.0.5" + "chokidar": "^2.1.0", + "debug": "^3.1.0", + "ignore-by-default": "^1.0.1", + "minimatch": "^3.0.4", + "pstree.remy": "^1.1.6", + "semver": "^5.5.0", + "supports-color": "^5.2.0", + "touch": "^3.1.0", + "undefsafe": "^2.0.2", + "update-notifier": "^2.5.0" + }, + "dependencies": { + "has-flag": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", + "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=", + "dev": true + }, + "supports-color": { + "version": "5.5.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", + "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", + "dev": true, + "requires": { + "has-flag": "^3.0.0" + } + } } }, - "run-async": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/run-async/-/run-async-2.3.0.tgz", - "integrity": "sha1-A3GrSuC91yDUFm19/aZP96RFpsA=", + "nopt": { + "version": "1.0.10", + "resolved": "https://registry.npmjs.org/nopt/-/nopt-1.0.10.tgz", + "integrity": "sha1-bd0hvSoxQXuScn3Vhfim83YI6+4=", + "dev": true, "requires": { - "is-promise": "^2.1.0" + "abbrev": "1" } }, - "rx-lite": { - "version": "4.0.8", - "resolved": "https://registry.npmjs.org/rx-lite/-/rx-lite-4.0.8.tgz", - "integrity": "sha1-Cx4Rr4vESDbwSmQH6S2kJGe3lEQ=" - }, - "rx-lite-aggregates": { - "version": "4.0.8", - "resolved": "https://registry.npmjs.org/rx-lite-aggregates/-/rx-lite-aggregates-4.0.8.tgz", - "integrity": "sha1-dTuHqJoRyVRnxKwWJsTvxOBcZ74=", + "normalize-package-data": { + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-2.5.0.tgz", + "integrity": "sha512-/5CMN3T0R4XTj4DcGaexo+roZSdSFW/0AOOTROrjxzCG1wrWXEsGbRKevjlIL+ZDE4sZlJr5ED4YW0yqmkK+eA==", "requires": { - "rx-lite": "*" + "hosted-git-info": "^2.1.4", + "resolve": "^1.10.0", + "semver": "2 || 3 || 4 || 5", + "validate-npm-package-license": "^3.0.1" } }, - "rxjs": { - "version": "5.5.7", - "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-5.5.7.tgz", - "integrity": "sha512-Hxo2ac8gRQjwjtKgukMIwBRbq5+KAeEV5hXM4obYBOAghev41bDQWgFH4svYiU9UnQ5kNww2LgfyBdevCd2HXA==", + "normalize-path": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-3.0.0.tgz", + "integrity": "sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==", + "dev": true + }, + "npm-run-path": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/npm-run-path/-/npm-run-path-2.0.2.tgz", + "integrity": "sha1-NakjLfo11wZ7TLLd8jV7GHFTbF8=", + "dev": true, "requires": { - "symbol-observable": "1.0.1" + "path-key": "^2.0.0" } }, - "safe-buffer": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz", - "integrity": "sha512-kKvNJn6Mm93gAczWVJg7wH+wGYWNrDHdWvpUmHyEsgCtIwwo3bqPtV4tR5tuPaUhTOo/kvhVwd8XwwOllGYkbg==" + "number-is-nan": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/number-is-nan/-/number-is-nan-1.0.1.tgz", + "integrity": "sha1-CXtgK1NCKlIsGvuHkDGDNpQaAR0=" }, - "safe-regex": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/safe-regex/-/safe-regex-1.1.0.tgz", - "integrity": "sha1-QKNmnzsHfR6UPURinhV91IAjvy4=", - "dev": true, + "number-to-bn": { + "version": "1.7.0", + "resolved": "https://registry.npmjs.org/number-to-bn/-/number-to-bn-1.7.0.tgz", + "integrity": "sha1-uzYjWS9+X54AMLGXe9QaDFP+HqA=", "requires": { - "ret": "~0.1.10" + "bn.js": "4.11.6", + "strip-hex-prefix": "1.0.0" + }, + "dependencies": { + "bn.js": { + "version": "4.11.6", + "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.11.6.tgz", + "integrity": "sha1-UzRK2xRhehP26N0s4okF0cC6MhU=" + } } }, - "scoped-regex": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/scoped-regex/-/scoped-regex-1.0.0.tgz", - "integrity": "sha1-o0a7Gs1CB65wvXwMfKnlZra63bg=" + "oauth-sign": { + "version": "0.9.0", + "resolved": "https://registry.npmjs.org/oauth-sign/-/oauth-sign-0.9.0.tgz", + "integrity": "sha512-fexhUFFPTGV8ybAtSIGbV6gOkSv8UtRbDBnAyLQw4QPKkgNlsH2ByPGtMUqdWkos6YCRmAqViwgZrJc/mRDzZQ==", + "dev": true }, - "semver": { - "version": "5.5.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.5.0.tgz", - "integrity": "sha512-4SJ3dm0WAwWy/NVeioZh5AntkdJoWKxHxcmyP622fOkgHa4z3R0TdBJICINyaSDE6uNwVc8gZr+ZinwZAH4xIA==" + "object-assign": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", + "integrity": "sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM=" }, - "semver-diff": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/semver-diff/-/semver-diff-2.1.0.tgz", - "integrity": "sha1-S7uEN8jTfksM8aaP1ybsbWRdbTY=", + "object-copy": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/object-copy/-/object-copy-0.1.0.tgz", + "integrity": "sha1-fn2Fi3gb18mRpBupde04EnVOmYw=", "dev": true, "requires": { - "semver": "^5.0.3" - } - }, - "send": { - "version": "0.16.2", - "resolved": "https://registry.npmjs.org/send/-/send-0.16.2.tgz", - "integrity": "sha512-E64YFPUssFHEFBvpbbjr44NCLtI1AohxQ8ZSiJjQLskAdKuriYEP6VyGEsRDH8ScozGpkaX1BGvhanqCwkcEZw==", - "requires": { - "debug": "2.6.9", - "depd": "~1.1.2", - "destroy": "~1.0.4", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "etag": "~1.8.1", - "fresh": "0.5.2", - "http-errors": "~1.6.2", - "mime": "1.4.1", - "ms": "2.0.0", - "on-finished": "~2.3.0", - "range-parser": "~1.2.0", - "statuses": "~1.4.0" + "copy-descriptor": "^0.1.0", + "define-property": "^0.2.5", + "kind-of": "^3.0.3" }, "dependencies": { - "debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "dev": true, "requires": { - "ms": "2.0.0" + "is-descriptor": "^0.1.0" } }, - "statuses": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.4.0.tgz", - "integrity": "sha512-zhSCtt8v2NDrRlPQpCNtw/heZLtfUDqxBM1udqikb/Hbk52LK4nQSwr10u77iopCW5LsyHpuXS0GnEc48mLeew==" + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, + "requires": { + "is-buffer": "^1.1.5" + } } } }, - "serve-static": { - "version": "1.13.2", - "resolved": "https://registry.npmjs.org/serve-static/-/serve-static-1.13.2.tgz", - "integrity": "sha512-p/tdJrO4U387R9oMjb1oj7qSMaMfmOyd4j9hOFoxZe2baQszgHcSWjuya/CiT5kgZZKRudHNOA0pYXOl8rQ5nw==", + "object-visit": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/object-visit/-/object-visit-1.0.1.tgz", + "integrity": "sha1-95xEk68MU3e1n+OdOV5BBC3QRbs=", + "dev": true, + "requires": { + "isobject": "^3.0.0" + } + }, + "object.pick": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/object.pick/-/object.pick-1.3.0.tgz", + "integrity": "sha1-h6EKxMFpS9Lhy/U1kaZhQftd10c=", + "dev": true, "requires": { - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "parseurl": "~1.3.2", - "send": "0.16.2" + "isobject": "^3.0.1" } }, - "servify": { - "version": "0.1.12", - "resolved": "https://registry.npmjs.org/servify/-/servify-0.1.12.tgz", - "integrity": "sha512-/xE6GvsKKqyo1BAY+KxOWXcLpPsUUyji7Qg3bVD7hh1eRze5bR1uYiuDA/k3Gof1s9BTzQZEJK8sNcNGFIzeWw==", + "once": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", + "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", "requires": { - "body-parser": "^1.16.0", - "cors": "^2.8.1", - "express": "^4.14.0", - "request": "^2.79.0", - "xhr": "^2.3.3" + "wrappy": "1" } }, - "set-blocking": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/set-blocking/-/set-blocking-2.0.0.tgz", - "integrity": "sha1-BF+XgtARrppoA93TgrJDkrPYkPc=" - }, - "set-immediate-shim": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/set-immediate-shim/-/set-immediate-shim-1.0.1.tgz", - "integrity": "sha1-SysbJ+uAip+NzEgaWOXlb1mfP2E=", - "dev": true + "openzeppelin-solidity": { + "version": "1.12.0", + "resolved": "https://registry.npmjs.org/openzeppelin-solidity/-/openzeppelin-solidity-1.12.0.tgz", + "integrity": "sha512-WlorzMXIIurugiSdw121RVD5qA3EfSI7GybTn+/Du0mPNgairjt29NpVTAaH8eLjAeAwlw46y7uQKy0NYem/gA==" }, - "set-value": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/set-value/-/set-value-2.0.0.tgz", - "integrity": "sha512-hw0yxk9GT/Hr5yJEYnHNKYXkIA8mVJgd9ditYZCe16ZczcaELYYcfvaXesNACk2O8O0nTiPQcQhGUQj8JLzeeg==", + "optimist": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/optimist/-/optimist-0.6.1.tgz", + "integrity": "sha1-2j6nRob6IaGaERwybpDrFaAZZoY=", "dev": true, "requires": { - "extend-shallow": "^2.0.1", - "is-extendable": "^0.1.1", - "is-plain-object": "^2.0.3", - "split-string": "^3.0.1" + "minimist": "~0.0.1", + "wordwrap": "~0.0.2" }, "dependencies": { - "extend-shallow": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", - "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", - "dev": true, - "requires": { - "is-extendable": "^0.1.0" - } + "wordwrap": { + "version": "0.0.3", + "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-0.0.3.tgz", + "integrity": "sha1-o9XabNXAvAAI03I0u68b7WMFkQc=", + "dev": true } } }, - "setprototypeof": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.1.0.tgz", - "integrity": "sha512-BvE/TwpZX4FXExxOxZyRGQQv651MSwmWKZGqvmPcRIjDqWub67kTKuIMx43cZZrS/cBBzwBcNDWoFxt2XEFIpQ==" - }, - "sha1": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/sha1/-/sha1-1.1.1.tgz", - "integrity": "sha1-rdqnqTFo85PxnrKxUJFhjicA+Eg=", + "optionator": { + "version": "0.8.2", + "resolved": "https://registry.npmjs.org/optionator/-/optionator-0.8.2.tgz", + "integrity": "sha1-NkxeQJ0/TWMB1sC0wFu6UBgK62Q=", "dev": true, "requires": { - "charenc": ">= 0.0.1", - "crypt": ">= 0.0.1" + "deep-is": "~0.1.3", + "fast-levenshtein": "~2.0.4", + "levn": "~0.3.0", + "prelude-ls": "~1.1.2", + "type-check": "~0.3.2", + "wordwrap": "~1.0.0" } }, - "sha3": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/sha3/-/sha3-1.2.0.tgz", - "integrity": "sha1-aYnxtwpJhwWHajc+LGKs6WqpOZo=", - "requires": { - "nan": "^2.0.5" - } + "original-require": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/original-require/-/original-require-1.0.1.tgz", + "integrity": "sha1-DxMEcVhM0zURxew4yNWSE/msXiA=" }, - "shebang-command": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-1.2.0.tgz", - "integrity": "sha1-RKrGW2lbAzmJaMOfNj/uXer98eo=", + "os-locale": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/os-locale/-/os-locale-1.4.0.tgz", + "integrity": "sha1-IPnxeuKe00XoveWDsT0gCYA8FNk=", "requires": { - "shebang-regex": "^1.0.0" + "lcid": "^1.0.0" } }, - "shebang-regex": { + "p-finally": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-1.0.0.tgz", - "integrity": "sha1-2kL0l0DAtC2yypcoVxyxkMmO/qM=" + "resolved": "https://registry.npmjs.org/p-finally/-/p-finally-1.0.0.tgz", + "integrity": "sha1-P7z7FbiZpEEjs0ttzBi3JDNqLK4=", + "dev": true }, - "shelljs": { - "version": "0.8.1", - "resolved": "https://registry.npmjs.org/shelljs/-/shelljs-0.8.1.tgz", - "integrity": "sha512-YA/iYtZpzFe5HyWVGrb02FjPxc4EMCfpoU/Phg9fQoyMC72u9598OUBrsU8IrtwAKG0tO8IYaqbaLIw+k3IRGA==", + "p-limit": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-1.3.0.tgz", + "integrity": "sha512-vvcXsLAJ9Dr5rQOPk7toZQZJApBl2K4J6dANSsEuh6QI41JYcsS/qhTGa9ErIUUgK3WNQoJYvylxvjqmiqEA9Q==", + "dev": true, "requires": { - "glob": "^7.0.0", - "interpret": "^1.0.0", - "rechoir": "^0.6.2" + "p-try": "^1.0.0" } }, - "sigmund": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/sigmund/-/sigmund-1.0.1.tgz", - "integrity": "sha1-P/IfGYytIXX587eBhT/ZTQ0ZtZA=", - "dev": true - }, - "signal-exit": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.2.tgz", - "integrity": "sha1-tf3AjxKH6hF4Yo5BXiUTK3NkbG0=" - }, - "simple-concat": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/simple-concat/-/simple-concat-1.0.0.tgz", - "integrity": "sha1-c0TLuLbib7J9ZrL8hvn21Zl1IcY=" - }, - "simple-get": { - "version": "2.7.0", - "resolved": "https://registry.npmjs.org/simple-get/-/simple-get-2.7.0.tgz", - "integrity": "sha512-RkE9rGPHcxYZ/baYmgJtOSM63vH0Vyq+ma5TijBcLla41SWlh8t6XYIGMR/oeZcmr+/G8k+zrClkkVrtnQ0esg==", + "p-locate": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-2.0.0.tgz", + "integrity": "sha1-IKAQOyIqcMj9OcwuWAaA893l7EM=", + "dev": true, "requires": { - "decompress-response": "^3.3.0", - "once": "^1.3.1", - "simple-concat": "^1.0.0" + "p-limit": "^1.1.0" } }, - "slash": { + "p-try": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/slash/-/slash-1.0.0.tgz", - "integrity": "sha1-xB8vbDn8FtHNF61LXYlhFK5HDVU=" - }, - "slice-ansi": { - "version": "0.0.4", - "resolved": "https://registry.npmjs.org/slice-ansi/-/slice-ansi-0.0.4.tgz", - "integrity": "sha1-7b+JA/ZvfOL46v1s7tZeJkyDGzU=" - }, - "slide": { - "version": "1.1.6", - "resolved": "https://registry.npmjs.org/slide/-/slide-1.1.6.tgz", - "integrity": "sha1-VusCfWW00tzmyy4tMsTUr8nh1wc=" + "resolved": "https://registry.npmjs.org/p-try/-/p-try-1.0.0.tgz", + "integrity": "sha1-y8ec26+P1CKOE/Yh8rGiN8GyB7M=", + "dev": true }, - "snapdragon": { - "version": "0.8.2", - "resolved": "https://registry.npmjs.org/snapdragon/-/snapdragon-0.8.2.tgz", - "integrity": "sha512-FtyOnWN/wCHTVXOMwvSv26d+ko5vWlIDD6zoUJ7LW8vh+ZBC8QdljveRP+crNrtBwioEUWy/4dMtbBjA4ioNlg==", + "package-json": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/package-json/-/package-json-4.0.1.tgz", + "integrity": "sha1-iGmgQBJTZhxMTKPabCEh7VVfXu0=", "dev": true, "requires": { - "base": "^0.11.1", - "debug": "^2.2.0", - "define-property": "^0.2.5", - "extend-shallow": "^2.0.1", - "map-cache": "^0.2.2", - "source-map": "^0.5.6", - "source-map-resolve": "^0.5.0", - "use": "^3.1.0" - }, - "dependencies": { - "define-property": { - "version": "0.2.5", - "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", - "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", - "dev": true, - "requires": { - "is-descriptor": "^0.1.0" - } - }, - "extend-shallow": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", - "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", - "dev": true, - "requires": { - "is-extendable": "^0.1.0" - } - } + "got": "^6.7.1", + "registry-auth-token": "^3.0.1", + "registry-url": "^3.0.3", + "semver": "^5.1.0" } }, - "snapdragon-node": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/snapdragon-node/-/snapdragon-node-2.1.1.tgz", - "integrity": "sha512-O27l4xaMYt/RSQ5TR3vpWCAB5Kb/czIcqUFOM/C4fYcLnbZUc1PkjTAMjof2pBWaSTwOUd6qUHcFGVGj7aIwnw==", - "dev": true, + "parse-cache-control": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/parse-cache-control/-/parse-cache-control-1.0.1.tgz", + "integrity": "sha1-juqz5U+laSD+Fro493+iGqzC104=", + "dev": true + }, + "parse-headers": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/parse-headers/-/parse-headers-2.0.1.tgz", + "integrity": "sha1-aug6eqJanZtwCswoaYzR8e1+lTY=", "requires": { - "define-property": "^1.0.0", - "isobject": "^3.0.0", - "snapdragon-util": "^3.0.1" - }, - "dependencies": { - "define-property": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/define-property/-/define-property-1.0.0.tgz", - "integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=", - "dev": true, - "requires": { - "is-descriptor": "^1.0.0" - } - }, - "is-accessor-descriptor": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz", - "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", - "dev": true, - "requires": { - "kind-of": "^6.0.0" - } - }, - "is-data-descriptor": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz", - "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", - "dev": true, - "requires": { - "kind-of": "^6.0.0" - } - }, - "is-descriptor": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz", - "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", - "dev": true, - "requires": { - "is-accessor-descriptor": "^1.0.0", - "is-data-descriptor": "^1.0.0", - "kind-of": "^6.0.2" - } - } + "for-each": "^0.3.2", + "trim": "0.0.1" } }, - "snapdragon-util": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/snapdragon-util/-/snapdragon-util-3.0.1.tgz", - "integrity": "sha512-mbKkMdQKsjX4BAL4bRYTj21edOf8cN7XHdYUJEe+Zn99hVEYcMvKPct1IqNe7+AZPirn8BCDOQBHQZknqmKlZQ==", - "dev": true, + "parse-json": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-2.2.0.tgz", + "integrity": "sha1-9ID0BDTvgHQfhGkJn43qGPVaTck=", "requires": { - "kind-of": "^3.2.0" - }, - "dependencies": { - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", - "dev": true, - "requires": { - "is-buffer": "^1.1.5" - } - } + "error-ex": "^1.2.0" } }, - "sntp": { + "pascalcase": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/pascalcase/-/pascalcase-0.1.1.tgz", + "integrity": "sha1-s2PlXoAGym/iF4TS2yK9FdeRfxQ=", + "dev": true + }, + "path-dirname": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/path-dirname/-/path-dirname-1.0.2.tgz", + "integrity": "sha1-zDPSTVJeCZpTiMAzbG4yuRYGCeA=", + "dev": true + }, + "path-exists": { "version": "2.1.0", - "resolved": "https://registry.npmjs.org/sntp/-/sntp-2.1.0.tgz", - "integrity": "sha512-FL1b58BDrqS3A11lJ0zEdnJ3UOKqVxawAkF3k7F0CVN7VQ34aZrV+G8BZ1WC9ZL7NyrwsW0oviwsWDgRuVYtJg==", + "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-2.1.0.tgz", + "integrity": "sha1-D+tsZPD8UY2adU3V77YscCJ2H0s=", "requires": { - "hoek": "4.x.x" + "pinkie-promise": "^2.0.0" } }, - "sol-explore": { - "version": "1.6.2", - "resolved": "https://registry.npmjs.org/sol-explore/-/sol-explore-1.6.2.tgz", - "integrity": "sha1-Q66MQZ/TrAVqBfip0fsQIs1B7MI=", + "path-is-absolute": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", + "integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=" + }, + "path-is-inside": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/path-is-inside/-/path-is-inside-1.0.2.tgz", + "integrity": "sha1-NlQX3t5EQw0cEa9hAn+s8HS9/FM=", "dev": true }, - "solc": { - "version": "0.4.24", - "resolved": "https://registry.npmjs.org/solc/-/solc-0.4.24.tgz", - "integrity": "sha512-2xd7Cf1HeVwrIb6Bu1cwY2/TaLRodrppCq3l7rhLimFQgmxptXhTC3+/wesVLpB09F1A2kZgvbMOgH7wvhFnBQ==", - "requires": { - "fs-extra": "^0.30.0", - "memorystream": "^0.3.1", - "require-from-string": "^1.1.0", - "semver": "^5.3.0", - "yargs": "^4.7.1" - } + "path-key": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/path-key/-/path-key-2.0.1.tgz", + "integrity": "sha1-QRyttXTFoUDTpLGRDUDYDMn0C0A=", + "dev": true }, - "solidity-coverage": { - "version": "0.4.15", - "resolved": "https://registry.npmjs.org/solidity-coverage/-/solidity-coverage-0.4.15.tgz", - "integrity": "sha512-iA3MT20rh1LllcNwfxAKU3ZBDu8R/4K8jANJAk7BcJU1foOjEh3tYhGqL8w2kRJPIo5XtoW0wxyVt95X2eJk/A==", - "dev": true, + "path-parse": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.6.tgz", + "integrity": "sha512-GSmOT2EbHrINBf9SR7CDELwlJ8AENk3Qn7OikK4nFYAu3Ote2+JYNVvkpAEQm3/TLNEJFD/xZJjzyxg3KBWOzw==" + }, + "path-type": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/path-type/-/path-type-1.1.0.tgz", + "integrity": "sha1-WcRPfuSR2nBNpBXaWkBwuk+P5EE=", "requires": { - "death": "^1.1.0", - "ethereumjs-testrpc-sc": "6.1.2", - "istanbul": "^0.4.5", - "keccakjs": "^0.2.1", - "req-cwd": "^1.0.1", - "shelljs": "^0.7.4", - "sol-explore": "^1.6.2", - "solidity-parser-sc": "0.4.7", - "web3": "^0.18.4" - }, - "dependencies": { - "bignumber.js": { - "version": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", - "from": "bignumber.js@git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", - "dev": true - }, - "commander": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-2.3.0.tgz", - "integrity": "sha1-/UMOiJgy7DU7ms0d4hfBHLPu+HM=", - "dev": true - }, - "debug": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.2.0.tgz", - "integrity": "sha1-+HBX6ZWxofauaklgZkE3vFbwOdo=", - "dev": true, - "requires": { - "ms": "0.7.1" - } - }, - "diff": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/diff/-/diff-1.4.0.tgz", - "integrity": "sha1-fyjS657nsVqX79ic5j3P2qPMur8=", - "dev": true - }, - "escape-string-regexp": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.2.tgz", - "integrity": "sha1-Tbwv5nTnGUnK8/smlc5/LcHZqNE=", - "dev": true - }, - "minimatch": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-0.3.0.tgz", - "integrity": "sha1-J12O2qxPG7MyZHIInnlJyDlGmd0=", - "dev": true, - "requires": { - "lru-cache": "2", - "sigmund": "~1.0.0" - } - }, - "mocha": { - "version": "2.5.3", - "resolved": "https://registry.npmjs.org/mocha/-/mocha-2.5.3.tgz", - "integrity": "sha1-FhvlvetJZ3HrmzV0UFC2IrWu/Fg=", - "dev": true, - "requires": { - "commander": "2.3.0", - "debug": "2.2.0", - "diff": "1.4.0", - "escape-string-regexp": "1.0.2", - "glob": "3.2.11", - "growl": "1.9.2", - "jade": "0.26.3", - "mkdirp": "0.5.1", - "supports-color": "1.2.0", - "to-iso-string": "0.0.2" - }, - "dependencies": { - "glob": { - "version": "3.2.11", - "resolved": "https://registry.npmjs.org/glob/-/glob-3.2.11.tgz", - "integrity": "sha1-Spc/Y1uRkPcV0QmH1cAP0oFevj0=", - "dev": true, - "requires": { - "inherits": "2", - "minimatch": "0.3" - } - } - } - }, - "ms": { - "version": "0.7.1", - "resolved": "https://registry.npmjs.org/ms/-/ms-0.7.1.tgz", - "integrity": "sha1-nNE8A62/8ltl7/3nzoZO6VIBcJg=", - "dev": true - }, - "shelljs": { - "version": "0.7.8", - "resolved": "https://registry.npmjs.org/shelljs/-/shelljs-0.7.8.tgz", - "integrity": "sha1-3svPh0sNHl+3LhSxZKloMEjprLM=", - "dev": true, - "requires": { - "glob": "^7.0.0", - "interpret": "^1.0.0", - "rechoir": "^0.6.2" - } - }, - "solidity-parser-sc": { - "version": "0.4.7", - "resolved": "https://registry.npmjs.org/solidity-parser-sc/-/solidity-parser-sc-0.4.7.tgz", - "integrity": "sha512-wbX2806sm6thZME1aniqLcLH9HYwNwuKke6aw/FEgupCvoT9Iq5PdwuN9OyHWKGBOVeczpM5tCrnRXWNQ04YVw==", - "dev": true, - "requires": { - "mocha": "^2.4.5", - "pegjs": "^0.10.0", - "yargs": "^4.6.0" - } - }, - "supports-color": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-1.2.0.tgz", - "integrity": "sha1-/x7R5hFp0Gs88tWI4YixjYhH4X4=", - "dev": true - }, - "web3": { - "version": "0.18.4", - "resolved": "https://registry.npmjs.org/web3/-/web3-0.18.4.tgz", - "integrity": "sha1-gewXhBRUkfLqqJVbMcBgSeB8Xn0=", - "dev": true, - "requires": { - "bignumber.js": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", - "crypto-js": "^3.1.4", - "utf8": "^2.1.1", - "xhr2": "*", - "xmlhttprequest": "*" - } - } + "graceful-fs": "^4.1.2", + "pify": "^2.0.0", + "pinkie-promise": "^2.0.0" } }, - "solidity-parser": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/solidity-parser/-/solidity-parser-0.4.0.tgz", - "integrity": "sha1-o0PxPac8kWgyeQNGgOgMSR3jQPo=", - "dev": true, + "pathval": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/pathval/-/pathval-1.1.0.tgz", + "integrity": "sha1-uULm1L3mUwBe9rcTYd74cn0GReA=", + "dev": true + }, + "pegjs": { + "version": "0.10.0", + "resolved": "https://registry.npmjs.org/pegjs/-/pegjs-0.10.0.tgz", + "integrity": "sha1-z4uvrm7d/0tafvsYUmnqr0YQ3b0=", + "dev": true + }, + "performance-now": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/performance-now/-/performance-now-2.1.0.tgz", + "integrity": "sha1-Ywn04OX6kT7BxpMHrjZLSzd8nns=", + "dev": true + }, + "pify": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", + "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=" + }, + "pinkie": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/pinkie/-/pinkie-2.0.4.tgz", + "integrity": "sha1-clVrgM+g1IqXToDnckjoDtT3+HA=" + }, + "pinkie-promise": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/pinkie-promise/-/pinkie-promise-2.0.1.tgz", + "integrity": "sha1-ITXW36ejWMBprJsXh3YogihFD/o=", "requires": { - "mocha": "^2.4.5", - "pegjs": "^0.10.0", - "yargs": "^4.6.0" - }, - "dependencies": { - "commander": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-2.3.0.tgz", - "integrity": "sha1-/UMOiJgy7DU7ms0d4hfBHLPu+HM=", - "dev": true - }, - "debug": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.2.0.tgz", - "integrity": "sha1-+HBX6ZWxofauaklgZkE3vFbwOdo=", - "dev": true, - "requires": { - "ms": "0.7.1" - } - }, - "diff": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/diff/-/diff-1.4.0.tgz", - "integrity": "sha1-fyjS657nsVqX79ic5j3P2qPMur8=", - "dev": true - }, - "escape-string-regexp": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.2.tgz", - "integrity": "sha1-Tbwv5nTnGUnK8/smlc5/LcHZqNE=", - "dev": true - }, - "glob": { - "version": "3.2.11", - "resolved": "https://registry.npmjs.org/glob/-/glob-3.2.11.tgz", - "integrity": "sha1-Spc/Y1uRkPcV0QmH1cAP0oFevj0=", - "dev": true, - "requires": { - "inherits": "2", - "minimatch": "0.3" - } - }, - "minimatch": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-0.3.0.tgz", - "integrity": "sha1-J12O2qxPG7MyZHIInnlJyDlGmd0=", - "dev": true, - "requires": { - "lru-cache": "2", - "sigmund": "~1.0.0" - } - }, - "mocha": { - "version": "2.5.3", - "resolved": "https://registry.npmjs.org/mocha/-/mocha-2.5.3.tgz", - "integrity": "sha1-FhvlvetJZ3HrmzV0UFC2IrWu/Fg=", - "dev": true, - "requires": { - "commander": "2.3.0", - "debug": "2.2.0", - "diff": "1.4.0", - "escape-string-regexp": "1.0.2", - "glob": "3.2.11", - "growl": "1.9.2", - "jade": "0.26.3", - "mkdirp": "0.5.1", - "supports-color": "1.2.0", - "to-iso-string": "0.0.2" - } - }, - "ms": { - "version": "0.7.1", - "resolved": "https://registry.npmjs.org/ms/-/ms-0.7.1.tgz", - "integrity": "sha1-nNE8A62/8ltl7/3nzoZO6VIBcJg=", - "dev": true - }, - "supports-color": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-1.2.0.tgz", - "integrity": "sha1-/x7R5hFp0Gs88tWI4YixjYhH4X4=", - "dev": true - } + "pinkie": "^2.0.0" } }, - "solidity-parser-antlr": { - "version": "0.2.15", - "resolved": "https://registry.npmjs.org/solidity-parser-antlr/-/solidity-parser-antlr-0.2.15.tgz", - "integrity": "sha512-EzRI8/TR/ljTXkZAyAjb0w4G20wH2XM7pcNf87ifdV825AbUv7DkY7HmiZCTj6NeKtIx8Y1s0NZWPbj+JTp8Zw==", + "posix-character-classes": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/posix-character-classes/-/posix-character-classes-0.1.1.tgz", + "integrity": "sha1-AerA/jta9xoqbAL+q7jB/vfgDqs=", "dev": true }, - "sort-keys": { + "prelude-ls": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.1.2.tgz", + "integrity": "sha1-IZMqVJ9eUv/ZqCf1cOBL5iqX2lQ=", + "dev": true + }, + "prepend-http": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/prepend-http/-/prepend-http-1.0.4.tgz", + "integrity": "sha1-1PRWKwzjaW5BrFLQ4ALlemNdxtw=", + "dev": true + }, + "process": { + "version": "0.5.2", + "resolved": "https://registry.npmjs.org/process/-/process-0.5.2.tgz", + "integrity": "sha1-FjjYqONML0QKkduVq5rrZ3/Bhc8=" + }, + "process-nextick-args": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/sort-keys/-/sort-keys-2.0.0.tgz", - "integrity": "sha1-ZYU1WEhh7JfXMNbPQYIuH1ZoQSg=", + "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.0.tgz", + "integrity": "sha512-MtEC1TqN0EU5nephaJ4rAtThHtC86dNN9qCuEhtshvpVBkAW5ZO7BASN9REnF9eoXGcRub+pFuKEpOHE+HbEMw==", + "dev": true + }, + "promise": { + "version": "8.0.2", + "resolved": "https://registry.npmjs.org/promise/-/promise-8.0.2.tgz", + "integrity": "sha512-EIyzM39FpVOMbqgzEHhxdrEhtOSDOtjMZQ0M6iVfCE+kWNgCkAyOdnuCWqfmflylftfadU6FkiMgHZA2kUzwRw==", + "dev": true, "requires": { - "is-plain-obj": "^1.0.0" + "asap": "~2.0.6" } }, - "source-map": { - "version": "0.5.7", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", - "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=" + "pseudomap": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/pseudomap/-/pseudomap-1.0.2.tgz", + "integrity": "sha1-8FKijacOYYkX7wqKw0wa5aaChrM=", + "dev": true }, - "source-map-resolve": { - "version": "0.5.1", - "resolved": "https://registry.npmjs.org/source-map-resolve/-/source-map-resolve-0.5.1.tgz", - "integrity": "sha512-0KW2wvzfxm8NCTb30z0LMNyPqWCdDGE2viwzUaucqJdkTRXtZiSY3I+2A6nVAjmdOy0I4gU8DwnVVGsk9jvP2A==", - "dev": true, + "psl": { + "version": "1.1.31", + "resolved": "https://registry.npmjs.org/psl/-/psl-1.1.31.tgz", + "integrity": "sha512-/6pt4+C+T+wZUieKR620OpzN/LlnNKuWjy1iFLQ/UG35JqHlR/89MP1d96dUfkf6Dne3TuLQzOYEYshJ+Hx8mw==", + "dev": true + }, + "pstree.remy": { + "version": "1.1.6", + "resolved": "https://registry.npmjs.org/pstree.remy/-/pstree.remy-1.1.6.tgz", + "integrity": "sha512-NdF35+QsqD7EgNEI5mkI/X+UwaxVEbQaz9f4IooEmMUv6ZPmlTQYGjBPJGgrlzNdjSvIy4MWMg6Q6vCgBO2K+w==", + "dev": true + }, + "punycode": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.1.1.tgz", + "integrity": "sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A==", + "dev": true + }, + "qs": { + "version": "6.5.2", + "resolved": "https://registry.npmjs.org/qs/-/qs-6.5.2.tgz", + "integrity": "sha512-N5ZAX4/LxJmF+7wN74pUD6qAh9/wnvdQcjq9TZjevvXzSUo7bfmw91saqMjzGS2xq91/odN2dW/WOl7qQHNDGA==", + "dev": true + }, + "query-string": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/query-string/-/query-string-5.1.1.tgz", + "integrity": "sha512-gjWOsm2SoGlgLEdAGt7a6slVOk9mGiXmPFMqrEhLQ68rhQuBnpfs3+EmlvqKyxnCo9/PPlF+9MtY02S1aFg+Jw==", "requires": { - "atob": "^2.0.0", "decode-uri-component": "^0.2.0", - "resolve-url": "^0.2.1", - "source-map-url": "^0.4.0", - "urix": "^0.1.0" + "object-assign": "^4.1.0", + "strict-uri-encode": "^1.0.0" } }, - "source-map-support": { - "version": "0.5.4", - "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.4.tgz", - "integrity": "sha512-PETSPG6BjY1AHs2t64vS2aqAgu6dMIMXJULWFBGbh2Gr8nVLbCFDo6i/RMMvviIQ2h1Z8+5gQhVKSn2je9nmdg==", + "randomhex": { + "version": "0.1.5", + "resolved": "https://registry.npmjs.org/randomhex/-/randomhex-0.1.5.tgz", + "integrity": "sha1-us7vmCMpCRQA8qKRLGzQLxCU9YU=" + }, + "rc": { + "version": "1.2.8", + "resolved": "https://registry.npmjs.org/rc/-/rc-1.2.8.tgz", + "integrity": "sha512-y3bGgqKj3QBdxLbLkomlohkvsA8gdAiUQlSBJnBhfn+BPxg4bc62d8TcBW15wavDfgexCgccckhcZvywyQYPOw==", + "dev": true, "requires": { - "source-map": "^0.6.0" + "deep-extend": "^0.6.0", + "ini": "~1.3.0", + "minimist": "^1.2.0", + "strip-json-comments": "~2.0.1" }, "dependencies": { - "source-map": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", - "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==" + "minimist": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz", + "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=", + "dev": true } } }, - "source-map-url": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/source-map-url/-/source-map-url-0.4.0.tgz", - "integrity": "sha1-PpNdfd1zYxuXZZlW1VEo6HtQhKM=", - "dev": true - }, - "spdx-correct": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/spdx-correct/-/spdx-correct-1.0.2.tgz", - "integrity": "sha1-SzBz2TP/UfORLwOsVRlJikFQ20A=", + "read-pkg": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-1.1.0.tgz", + "integrity": "sha1-9f+qXs0pyzHAR0vKfXVra7KePyg=", "requires": { - "spdx-license-ids": "^1.0.2" + "load-json-file": "^1.0.0", + "normalize-package-data": "^2.3.2", + "path-type": "^1.0.0" } }, - "spdx-expression-parse": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/spdx-expression-parse/-/spdx-expression-parse-1.0.4.tgz", - "integrity": "sha1-m98vIOH0DtRH++JzJmGR/O1RYmw=" - }, - "spdx-license-ids": { - "version": "1.2.2", - "resolved": "https://registry.npmjs.org/spdx-license-ids/-/spdx-license-ids-1.2.2.tgz", - "integrity": "sha1-yd96NCRZSt5r0RkA1ZZpbcBrrFc=" - }, - "split": { - "version": "0.3.3", - "resolved": "https://registry.npmjs.org/split/-/split-0.3.3.tgz", - "integrity": "sha1-zQ7qXmOiEd//frDwkcQTPi0N0o8=", - "dev": true, + "read-pkg-up": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/read-pkg-up/-/read-pkg-up-1.0.1.tgz", + "integrity": "sha1-nWPBMnbAZZGNV/ACpX9AobZD+wI=", "requires": { - "through": "2" + "find-up": "^1.0.0", + "read-pkg": "^1.0.0" } }, - "split-string": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/split-string/-/split-string-3.1.0.tgz", - "integrity": "sha512-NzNVhJDYpwceVVii8/Hu6DKfD2G+NrQHlS/V/qgv763EYudVwEcMQNxd2lh+0VrUByXN/oJkl5grOhYWvQUYiw==", + "readable-stream": { + "version": "2.3.6", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.6.tgz", + "integrity": "sha512-tQtKA9WIAhBF3+VLAseyMqZeBjW0AHJoxOtYqSUZNJxauErmLbVm2FW1y+J/YA9dUrAC39ITejlZWhVIwawkKw==", "dev": true, "requires": { - "extend-shallow": "^3.0.0" + "core-util-is": "~1.0.0", + "inherits": "~2.0.3", + "isarray": "~1.0.0", + "process-nextick-args": "~2.0.0", + "safe-buffer": "~5.1.1", + "string_decoder": "~1.1.1", + "util-deprecate": "~1.0.1" } }, - "sprintf-js": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz", - "integrity": "sha1-BOaSb2YolTVPPdAVIDYzuFcpfiw=", - "dev": true - }, - "sshpk": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/sshpk/-/sshpk-1.14.1.tgz", - "integrity": "sha1-Ew9Zde3a2WPx1W+SuaxsUfqfg+s=", + "readdirp": { + "version": "2.2.1", + "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-2.2.1.tgz", + "integrity": "sha512-1JU/8q+VgFZyxwrJ+SVIOsh+KywWGpds3NTqikiKpDMZWScmAYyKIgqkO+ARvNWJfXeXR1zxz7aHF4u4CyH6vQ==", + "dev": true, "requires": { - "asn1": "~0.2.3", - "assert-plus": "^1.0.0", - "bcrypt-pbkdf": "^1.0.0", - "dashdash": "^1.12.0", - "ecc-jsbn": "~0.1.1", - "getpass": "^0.1.1", - "jsbn": "~0.1.0", - "tweetnacl": "~0.14.0" + "graceful-fs": "^4.1.11", + "micromatch": "^3.1.10", + "readable-stream": "^2.0.2" } }, - "static-extend": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/static-extend/-/static-extend-0.1.2.tgz", - "integrity": "sha1-YICcOcv/VTNyJv1eC1IPNB8ftcY=", + "rechoir": { + "version": "0.6.2", + "resolved": "https://registry.npmjs.org/rechoir/-/rechoir-0.6.2.tgz", + "integrity": "sha1-hSBLVNuoLVdC4oyWdW70OvUOM4Q=", "dev": true, "requires": { - "define-property": "^0.2.5", - "object-copy": "^0.1.0" - }, - "dependencies": { - "define-property": { - "version": "0.2.5", - "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", - "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", - "dev": true, - "requires": { - "is-descriptor": "^0.1.0" - } - } + "resolve": "^1.1.6" } }, - "statuses": { - "version": "1.5.0", - "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.5.0.tgz", - "integrity": "sha1-Fhx9rBd2Wf2YEfQ3cfqZOBR4Yow=" - }, - "stealthy-require": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/stealthy-require/-/stealthy-require-1.1.1.tgz", - "integrity": "sha1-NbCYdbT/SfJqd35QmzCQoyJr8ks=", - "dev": true + "regenerator-runtime": { + "version": "0.12.1", + "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.12.1.tgz", + "integrity": "sha512-odxIc1/vDlo4iZcfXqRYFj0vpXFNoGdKMAUieAlFYO6m/nl5e9KR/beGf41z4a1FI+aQgtjhuaSlDxQ0hmkrHg==" }, - "stream-combiner": { - "version": "0.0.4", - "resolved": "https://registry.npmjs.org/stream-combiner/-/stream-combiner-0.0.4.tgz", - "integrity": "sha1-TV5DPBhSYd3mI8o/RMWGvPXErRQ=", + "regex-not": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/regex-not/-/regex-not-1.0.2.tgz", + "integrity": "sha512-J6SDjUgDxQj5NusnOtdFxDwN/+HWykR8GELwctJ7mdqhcyy1xEc4SRFHUXvxTp661YaVKAjfRLZ9cCqS6tn32A==", "dev": true, "requires": { - "duplexer": "~0.1.1" + "extend-shallow": "^3.0.2", + "safe-regex": "^1.1.0" } }, - "stream-to-observable": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/stream-to-observable/-/stream-to-observable-0.2.0.tgz", - "integrity": "sha1-WdbqOT2HwsDdrBCqDVYbxrpvDhA=", + "registry-auth-token": { + "version": "3.3.2", + "resolved": "https://registry.npmjs.org/registry-auth-token/-/registry-auth-token-3.3.2.tgz", + "integrity": "sha512-JL39c60XlzCVgNrO+qq68FoNb56w/m7JYvGR2jT5iR1xBrUA3Mfx5Twk5rqTThPmQKMWydGmq8oFtDlxfrmxnQ==", + "dev": true, "requires": { - "any-observable": "^0.2.0" + "rc": "^1.1.6", + "safe-buffer": "^5.0.1" } }, - "strict-uri-encode": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/strict-uri-encode/-/strict-uri-encode-1.1.0.tgz", - "integrity": "sha1-J5siXfHVgrH1TmWt3UNS4Y+qBxM=" - }, - "string-template": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/string-template/-/string-template-0.2.1.tgz", - "integrity": "sha1-QpMuWYo1LQH8IuwzZ9nYTuxsmt0=" - }, - "string-width": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz", - "integrity": "sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=", + "registry-url": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/registry-url/-/registry-url-3.1.0.tgz", + "integrity": "sha1-PU74cPc93h138M+aOBQyRE4XSUI=", + "dev": true, "requires": { - "code-point-at": "^1.0.0", - "is-fullwidth-code-point": "^1.0.0", - "strip-ansi": "^3.0.0" + "rc": "^1.0.1" } }, - "string_decoder": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "integrity": "sha512-4AH6Z5fzNNBcH+6XDMfA/BTt87skxqJlO0lAh3Dker5zThcAxG6mKz+iGu308UKoPPQ8Dcqx/4JhujzltRa+hQ==", - "requires": { - "safe-buffer": "~5.1.0" - } + "remove-trailing-separator": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/remove-trailing-separator/-/remove-trailing-separator-1.1.0.tgz", + "integrity": "sha1-wkvOKig62tW8P1jg1IJJuSN52O8=", + "dev": true }, - "stringstream": { - "version": "0.0.5", - "resolved": "https://registry.npmjs.org/stringstream/-/stringstream-0.0.5.tgz", - "integrity": "sha1-TkhM1N5aC7vuGORjB3EKioFiGHg=" + "repeat-element": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/repeat-element/-/repeat-element-1.1.3.tgz", + "integrity": "sha512-ahGq0ZnV5m5XtZLMb+vP76kcAM5nkLqk0lpqAuojSKGgQtn4eRi4ZZGm2olo2zKFH+sMsWaqOCW1dqAnOru72g==", + "dev": true }, - "strip-ansi": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", - "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", - "requires": { - "ansi-regex": "^2.0.0" - } + "repeat-string": { + "version": "1.6.1", + "resolved": "https://registry.npmjs.org/repeat-string/-/repeat-string-1.6.1.tgz", + "integrity": "sha1-jcrkcOHIirwtYA//Sndihtp15jc=", + "dev": true }, - "strip-bom": { + "req-cwd": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-2.0.0.tgz", - "integrity": "sha1-YhmoVhZSBJHzV4i9vxRHqZx+aw4=", + "resolved": "https://registry.npmjs.org/req-cwd/-/req-cwd-2.0.0.tgz", + "integrity": "sha1-1AgrTURZgDZkD7c93qAe1T20nrw=", + "dev": true, "requires": { - "is-utf8": "^0.2.0" + "req-from": "^2.0.0" } }, - "strip-bom-stream": { + "req-from": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/strip-bom-stream/-/strip-bom-stream-2.0.0.tgz", - "integrity": "sha1-+H217yYT9paKpUWr/h7HKLaoKco=", - "requires": { - "first-chunk-stream": "^2.0.0", - "strip-bom": "^2.0.0" - } - }, - "strip-eof": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/strip-eof/-/strip-eof-1.0.0.tgz", - "integrity": "sha1-u0P/VZim6wXYm1n80SnJgzE2Br8=" - }, - "strip-hex-prefix": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/strip-hex-prefix/-/strip-hex-prefix-1.0.0.tgz", - "integrity": "sha1-DF8VX+8RUTczd96du1iNoFUA428=", + "resolved": "https://registry.npmjs.org/req-from/-/req-from-2.0.0.tgz", + "integrity": "sha1-10GI5H+TeW9Kpx327jWuaJ8+DnA=", + "dev": true, "requires": { - "is-hex-prefixed": "1.0.0" + "resolve-from": "^3.0.0" } }, - "strip-json-comments": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", - "integrity": "sha1-PFMZQukIwml8DsNEhYwobHygpgo=", - "dev": true - }, - "supports-color": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-3.1.2.tgz", - "integrity": "sha1-cqJiiU2dQIuVbKBf83su2KbiotU=", + "request": { + "version": "2.88.0", + "resolved": "https://registry.npmjs.org/request/-/request-2.88.0.tgz", + "integrity": "sha512-NAqBSrijGLZdM0WZNsInLJpkJokL72XYjUpnB0iwsRgxh7dB6COrHnTBNwN0E+lHDAJzu7kLAkDeY08z2/A0hg==", "dev": true, "requires": { - "has-flag": "^1.0.0" + "aws-sign2": "~0.7.0", + "aws4": "^1.8.0", + "caseless": "~0.12.0", + "combined-stream": "~1.0.6", + "extend": "~3.0.2", + "forever-agent": "~0.6.1", + "form-data": "~2.3.2", + "har-validator": "~5.1.0", + "http-signature": "~1.2.0", + "is-typedarray": "~1.0.0", + "isstream": "~0.1.2", + "json-stringify-safe": "~5.0.1", + "mime-types": "~2.1.19", + "oauth-sign": "~0.9.0", + "performance-now": "^2.1.0", + "qs": "~6.5.2", + "safe-buffer": "^5.1.2", + "tough-cookie": "~2.4.3", + "tunnel-agent": "^0.6.0", + "uuid": "^3.3.2" } }, - "symbol-observable": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/symbol-observable/-/symbol-observable-1.0.1.tgz", - "integrity": "sha1-g0D8RwLDEi310iKI+IKD9RPT/dQ=" - }, - "sync-request": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/sync-request/-/sync-request-6.0.0.tgz", - "integrity": "sha512-jGNIAlCi9iU4X3Dm4oQnNQshDD3h0/1A7r79LyqjbjUnj69sX6mShAXlhRXgImsfVKtTcnra1jfzabdZvp+Lmw==", + "request-promise-core": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/request-promise-core/-/request-promise-core-1.1.2.tgz", + "integrity": "sha512-UHYyq1MO8GsefGEt7EprS8UrXsm1TxEvFUX1IMTuSLU2Rh7fTIdFtl8xD7JiEYiWU2dl+NYAjCTksTehQUxPag==", "dev": true, "requires": { - "http-response-object": "^3.0.1", - "sync-rpc": "^1.2.1", - "then-request": "^6.0.0" + "lodash": "^4.17.11" } }, - "sync-rpc": { - "version": "1.3.4", - "resolved": "https://registry.npmjs.org/sync-rpc/-/sync-rpc-1.3.4.tgz", - "integrity": "sha512-Iug+t1ICVFenUcTnDu8WXFnT+k8IVoLKGh8VA3eXUtl2Rt9SjKX3YEv33OenABqpTPL9QEaHv1+CNn2LK8vMow==", + "request-promise-native": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/request-promise-native/-/request-promise-native-1.0.7.tgz", + "integrity": "sha512-rIMnbBdgNViL37nZ1b3L/VfPOpSi0TqVDQPAvO6U14lMzOLrt5nilxCQqtDKhZeDiW0/hkCXGoQjhgJd/tCh6w==", "dev": true, "requires": { - "get-port": "^3.1.0" + "request-promise-core": "1.1.2", + "stealthy-require": "^1.1.1", + "tough-cookie": "^2.3.3" } }, - "tapable": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/tapable/-/tapable-1.0.0.tgz", - "integrity": "sha512-dQRhbNQkRnaqauC7WqSJ21EEksgT0fYZX2lqXzGkpo8JNig9zGZTYoMGvyI2nWmXlE2VSVXVDu7wLVGu/mQEsg==" + "require-directory": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/require-directory/-/require-directory-2.1.1.tgz", + "integrity": "sha1-jGStX9MNqxyXbiNE/+f3kqam30I=" }, - "temp": { - "version": "0.8.3", - "resolved": "https://registry.npmjs.org/temp/-/temp-0.8.3.tgz", - "integrity": "sha1-4Ma8TSa5AxJEEOT+2BEDAU38H1k=", - "requires": { - "os-tmpdir": "^1.0.0", - "rimraf": "~2.2.6" - }, - "dependencies": { - "rimraf": { - "version": "2.2.8", - "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.2.8.tgz", - "integrity": "sha1-5Dm+Kq7jJzIZUnMPmaiSnk/FBYI=" - } - } + "require-from-string": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/require-from-string/-/require-from-string-1.2.1.tgz", + "integrity": "sha1-UpyczvJzgK3+yaL5ZbZJu+5jZBg=" }, - "term-size": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/term-size/-/term-size-1.2.0.tgz", - "integrity": "sha1-RYuDiH8oj8Vtb/+/rSYuJmOO+mk=", - "dev": true, + "require-main-filename": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/require-main-filename/-/require-main-filename-1.0.1.tgz", + "integrity": "sha1-l/cXtp1IeE9fUmpsWqj/3aBVpNE=" + }, + "resolve": { + "version": "1.10.0", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.10.0.tgz", + "integrity": "sha512-3sUr9aq5OfSg2S9pNtPA9hL1FVEAjvfOC4leW0SNf/mpnaakz2a9femSd6LqAww2RaFctwyf1lCqnTHuF1rxDg==", "requires": { - "execa": "^0.7.0" + "path-parse": "^1.0.6" } }, - "text-table": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/text-table/-/text-table-0.2.0.tgz", - "integrity": "sha1-f17oI66AUgfACvLfSoTsP8+lcLQ=" + "resolve-from": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-3.0.0.tgz", + "integrity": "sha1-six699nWiBvItuZTM17rywoYh0g=", + "dev": true + }, + "resolve-url": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/resolve-url/-/resolve-url-0.2.1.tgz", + "integrity": "sha1-LGN/53yJOv0qZj/iGqkIAGjiBSo=", + "dev": true }, - "textextensions": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/textextensions/-/textextensions-2.2.0.tgz", - "integrity": "sha512-j5EMxnryTvKxwH2Cq+Pb43tsf6sdEgw6Pdwxk83mPaq0ToeFJt6WE4J3s5BqY7vmjlLgkgXvhtXUxo80FyBhCA==" + "ret": { + "version": "0.1.15", + "resolved": "https://registry.npmjs.org/ret/-/ret-0.1.15.tgz", + "integrity": "sha512-TTlYpa+OL+vMMNG24xSlQGEJ3B/RzEfUlLct7b5G/ytav+wPrplCpVMFuwzXbkecJrb6IYo1iFb0S9v37754mg==", + "dev": true }, - "then-request": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/then-request/-/then-request-6.0.0.tgz", - "integrity": "sha512-xA+7uEMc+jsQIoyySJ93Ad08Kuqnik7u6jLS5hR91Z3smAoCfL3M8/MqMlobAa9gzBfO9pA88A/AntfepkkMJQ==", - "dev": true, + "rimraf": { + "version": "2.6.3", + "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.6.3.tgz", + "integrity": "sha512-mwqeW5XsA2qAejG46gYdENaxXjx9onRNCfn7L0duuP4hCuTIi/QO7PDK07KJfp1d+izWPrzEJDcSqBa0OZQriA==", "requires": { - "@types/concat-stream": "^1.6.0", - "@types/form-data": "0.0.33", - "@types/node": "^8.0.0", - "@types/qs": "^6.2.31", - "caseless": "~0.12.0", - "concat-stream": "^1.6.0", - "form-data": "^2.2.0", - "http-basic": "^7.0.0", - "http-response-object": "^3.0.1", - "promise": "^8.0.0", - "qs": "^6.4.0" + "glob": "^7.1.3" }, "dependencies": { - "@types/node": { - "version": "8.10.36", - "resolved": "https://registry.npmjs.org/@types/node/-/node-8.10.36.tgz", - "integrity": "sha512-SL6KhfM7PTqiFmbCW3eVNwVBZ+88Mrzbuvn9olPsfv43mbiWaFY+nRcz/TGGku0/lc2FepdMbImdMY1JrQ+zbw==", - "dev": true + "glob": { + "version": "7.1.3", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.3.tgz", + "integrity": "sha512-vcfuiIxogLV4DlGBHIUOwI0IbrJ8HWPc4MU7HzviGeNho/UJDfi6B5p3sHeWIQ0KGIU0Jpxi5ZHxemQfLkkAwQ==", + "requires": { + "fs.realpath": "^1.0.0", + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "^3.0.4", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" + } } } }, - "through": { - "version": "2.3.8", - "resolved": "https://registry.npmjs.org/through/-/through-2.3.8.tgz", - "integrity": "sha1-DdTJ/6q8NXlgsbckEV1+Doai4fU=" + "safe-buffer": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", + "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", + "dev": true }, - "through2": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/through2/-/through2-2.0.3.tgz", - "integrity": "sha1-AARWmzfHx0ujnEPzzteNGtlBQL4=", + "safe-regex": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/safe-regex/-/safe-regex-1.1.0.tgz", + "integrity": "sha1-QKNmnzsHfR6UPURinhV91IAjvy4=", + "dev": true, "requires": { - "readable-stream": "^2.1.5", - "xtend": "~4.0.1" + "ret": "~0.1.10" } }, - "timed-out": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/timed-out/-/timed-out-4.0.1.tgz", - "integrity": "sha1-8y6srFoXW+ol1/q1Zas+2HQe9W8=" + "safer-buffer": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", + "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==", + "dev": true }, - "tmp": { - "version": "0.0.33", - "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.0.33.tgz", - "integrity": "sha512-jRCJlojKnZ3addtTOjdIqoRuPEKBvNXcGYqzO6zWZX8KfKEpnGY5jfggJQ3EjKuu8D4bJRr0y+cYJFmYbImXGw==", + "semver": { + "version": "5.6.0", + "resolved": "https://registry.npmjs.org/semver/-/semver-5.6.0.tgz", + "integrity": "sha512-RS9R6R35NYgQn++fkDWaOmqGoj4Ek9gGs+DPxNUZKuwE183xjJroKvyo1IzVFeXvUrvmALy6FWD5xrdJT25gMg==" + }, + "semver-diff": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/semver-diff/-/semver-diff-2.1.0.tgz", + "integrity": "sha1-S7uEN8jTfksM8aaP1ybsbWRdbTY=", + "dev": true, "requires": { - "os-tmpdir": "~1.0.2" + "semver": "^5.0.3" } }, - "to-fast-properties": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/to-fast-properties/-/to-fast-properties-1.0.3.tgz", - "integrity": "sha1-uDVx+k2MJbguIxsG46MFXeTKGkc=" - }, - "to-iso-string": { - "version": "0.0.2", - "resolved": "https://registry.npmjs.org/to-iso-string/-/to-iso-string-0.0.2.tgz", - "integrity": "sha1-TcGeZk38y+Jb2NtQiwDG2hWCVdE=", - "dev": true + "set-blocking": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/set-blocking/-/set-blocking-2.0.0.tgz", + "integrity": "sha1-BF+XgtARrppoA93TgrJDkrPYkPc=" }, - "to-object-path": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/to-object-path/-/to-object-path-0.3.0.tgz", - "integrity": "sha1-KXWIt7Dn4KwI4E5nL4XB9JmeF68=", + "set-value": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/set-value/-/set-value-2.0.0.tgz", + "integrity": "sha512-hw0yxk9GT/Hr5yJEYnHNKYXkIA8mVJgd9ditYZCe16ZczcaELYYcfvaXesNACk2O8O0nTiPQcQhGUQj8JLzeeg==", "dev": true, "requires": { - "kind-of": "^3.0.2" + "extend-shallow": "^2.0.1", + "is-extendable": "^0.1.1", + "is-plain-object": "^2.0.3", + "split-string": "^3.0.1" }, "dependencies": { - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", "dev": true, "requires": { - "is-buffer": "^1.1.5" + "is-extendable": "^0.1.0" } } } }, - "to-regex": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/to-regex/-/to-regex-3.0.2.tgz", - "integrity": "sha512-FWtleNAtZ/Ki2qtqej2CXTOayOH9bHDQF+Q48VpWyDXjbYxA4Yz8iDB31zXOBUlOHHKidDbqGVrTUvQMPmBGBw==", + "sha1": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/sha1/-/sha1-1.1.1.tgz", + "integrity": "sha1-rdqnqTFo85PxnrKxUJFhjicA+Eg=", "dev": true, "requires": { - "define-property": "^2.0.2", - "extend-shallow": "^3.0.2", - "regex-not": "^1.0.2", - "safe-regex": "^1.1.0" + "charenc": ">= 0.0.1", + "crypt": ">= 0.0.1" } }, - "to-regex-range": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-2.1.1.tgz", - "integrity": "sha1-fIDBe53+vlmeJzZ+DU3VWQFB2zg=", + "sha3": { + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/sha3/-/sha3-1.2.2.tgz", + "integrity": "sha1-pmxQmN5MJbyIM27ItIF9AFvKe6k=", "dev": true, "requires": { - "is-number": "^3.0.0", - "repeat-string": "^1.6.1" + "nan": "2.10.0" + }, + "dependencies": { + "nan": { + "version": "2.10.0", + "resolved": "https://registry.npmjs.org/nan/-/nan-2.10.0.tgz", + "integrity": "sha512-bAdJv7fBLhWC+/Bls0Oza+mvTaNQtP+1RyhhhvD95pgUJz6XM5IzgmxOkItJ9tkoCiplvAnXI1tNmmUD/eScyA==", + "dev": true + } } }, - "touch": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/touch/-/touch-3.1.0.tgz", - "integrity": "sha512-WBx8Uy5TLtOSRtIq+M03/sKDrXCLHxwDcquSP2c43Le03/9serjQBIztjRz6FkJez9D/hleyAXTBGLwwZUw9lA==", + "shebang-command": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-1.2.0.tgz", + "integrity": "sha1-RKrGW2lbAzmJaMOfNj/uXer98eo=", "dev": true, "requires": { - "nopt": "~1.0.10" + "shebang-regex": "^1.0.0" } }, - "tough-cookie": { - "version": "2.3.4", - "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.3.4.tgz", - "integrity": "sha512-TZ6TTfI5NtZnuyy/Kecv+CnoROnyXn2DN97LontgQpCwsX2XyLYCC0ENhYkehSOwAp8rTQKc/NUIF7BkQ5rKLA==", + "shebang-regex": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-1.0.0.tgz", + "integrity": "sha1-2kL0l0DAtC2yypcoVxyxkMmO/qM=", + "dev": true + }, + "shelljs": { + "version": "0.7.8", + "resolved": "https://registry.npmjs.org/shelljs/-/shelljs-0.7.8.tgz", + "integrity": "sha1-3svPh0sNHl+3LhSxZKloMEjprLM=", + "dev": true, "requires": { - "punycode": "^1.4.1" + "glob": "^7.0.0", + "interpret": "^1.0.0", + "rechoir": "^0.6.2" } }, - "trim": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/trim/-/trim-0.0.1.tgz", - "integrity": "sha1-WFhUf2spB1fulczMZm+1AITEYN0=" + "signal-exit": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.2.tgz", + "integrity": "sha1-tf3AjxKH6hF4Yo5BXiUTK3NkbG0=", + "dev": true }, - "trim-right": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/trim-right/-/trim-right-1.0.1.tgz", - "integrity": "sha1-yy4SAwZ+DI3h9hQJS5/kVwTqYAM=" + "simple-concat": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/simple-concat/-/simple-concat-1.0.0.tgz", + "integrity": "sha1-c0TLuLbib7J9ZrL8hvn21Zl1IcY=" }, - "truffle": { - "version": "4.1.11", - "resolved": "https://registry.npmjs.org/truffle/-/truffle-4.1.11.tgz", - "integrity": "sha512-VNhc6jexZeM92sNJJr4U8ln3uJ/mJEQO/0y9ZLYc4pccyIskPtl+3r4mzymgGM/Mq5v6MpoQVD6NZgHUVKX+Dw==", + "simple-get": { + "version": "2.8.1", + "resolved": "https://registry.npmjs.org/simple-get/-/simple-get-2.8.1.tgz", + "integrity": "sha512-lSSHRSw3mQNUGPAYRqo7xy9dhKmxFXIjLjp4KHpf99GEH2VH7C3AM+Qfx6du6jhfUi6Vm7XnbEVEf7Wb6N8jRw==", "requires": { - "mocha": "^4.1.0", - "original-require": "^1.0.1", - "solc": "0.4.24" + "decompress-response": "^3.3.0", + "once": "^1.3.1", + "simple-concat": "^1.0.0" } }, - "truffle-blockchain-utils": { - "version": "0.0.4", - "resolved": "https://registry.npmjs.org/truffle-blockchain-utils/-/truffle-blockchain-utils-0.0.4.tgz", - "integrity": "sha512-wgRrhwqh0aea08Hz28hUV4tuF2uTVQH/e9kBou+WK04cqrutB5cxQVQ6HGjeZLltxBYOFvhrGOOq4l3WJFnPEA==", - "dev": true + "snapdragon": { + "version": "0.8.2", + "resolved": "https://registry.npmjs.org/snapdragon/-/snapdragon-0.8.2.tgz", + "integrity": "sha512-FtyOnWN/wCHTVXOMwvSv26d+ko5vWlIDD6zoUJ7LW8vh+ZBC8QdljveRP+crNrtBwioEUWy/4dMtbBjA4ioNlg==", + "dev": true, + "requires": { + "base": "^0.11.1", + "debug": "^2.2.0", + "define-property": "^0.2.5", + "extend-shallow": "^2.0.1", + "map-cache": "^0.2.2", + "source-map": "^0.5.6", + "source-map-resolve": "^0.5.0", + "use": "^3.1.0" + }, + "dependencies": { + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, + "requires": { + "ms": "2.0.0" + } + }, + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "dev": true, + "requires": { + "is-descriptor": "^0.1.0" + } + }, + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "dev": true, + "requires": { + "is-extendable": "^0.1.0" + } + } + } }, - "truffle-config": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/truffle-config/-/truffle-config-1.0.4.tgz", - "integrity": "sha512-E8pvJNAIjs7LNsjkYeS2dgoOnLoSBrTwb1xF5lJwfvZmGMFpKvVL1sa5jpFxozpf/WkRn/rfxy8zTdb3pq16jA==", + "snapdragon-node": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/snapdragon-node/-/snapdragon-node-2.1.1.tgz", + "integrity": "sha512-O27l4xaMYt/RSQ5TR3vpWCAB5Kb/czIcqUFOM/C4fYcLnbZUc1PkjTAMjof2pBWaSTwOUd6qUHcFGVGj7aIwnw==", "dev": true, "requires": { - "find-up": "^2.1.0", - "lodash": "^4.17.4", - "original-require": "^1.0.0", - "truffle-error": "^0.0.2", - "truffle-provider": "^0.0.4" + "define-property": "^1.0.0", + "isobject": "^3.0.0", + "snapdragon-util": "^3.0.1" }, "dependencies": { - "find-up": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", - "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", + "define-property": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-1.0.0.tgz", + "integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=", + "dev": true, + "requires": { + "is-descriptor": "^1.0.0" + } + }, + "is-accessor-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz", + "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", + "dev": true, + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-data-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz", + "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", + "dev": true, + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-descriptor": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz", + "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", "dev": true, "requires": { - "locate-path": "^2.0.0" + "is-accessor-descriptor": "^1.0.0", + "is-data-descriptor": "^1.0.0", + "kind-of": "^6.0.2" } } } }, - "truffle-contract": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/truffle-contract/-/truffle-contract-3.0.4.tgz", - "integrity": "sha512-/1LCtJFf5Jvm5Rv88T0d/rZSKvaiW/yO1SHXLGJgKzLsiG1F/2spFs4HrI1mRxP00opfrYXloEmLtkVV/kcndQ==", + "snapdragon-util": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/snapdragon-util/-/snapdragon-util-3.0.1.tgz", + "integrity": "sha512-mbKkMdQKsjX4BAL4bRYTj21edOf8cN7XHdYUJEe+Zn99hVEYcMvKPct1IqNe7+AZPirn8BCDOQBHQZknqmKlZQ==", "dev": true, "requires": { - "ethjs-abi": "0.1.8", - "truffle-blockchain-utils": "^0.0.4", - "truffle-contract-schema": "^2.0.0", - "truffle-error": "0.0.2", - "web3": "^0.20.1" + "kind-of": "^3.2.0" }, "dependencies": { - "ethjs-abi": { - "version": "0.1.8", - "resolved": "https://registry.npmjs.org/ethjs-abi/-/ethjs-abi-0.1.8.tgz", - "integrity": "sha1-zSiFg+1ijN+tr4re+juh28vKbBg=", + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", "dev": true, "requires": { - "bn.js": "4.11.6", - "js-sha3": "0.5.5", - "number-to-bn": "1.7.0" + "is-buffer": "^1.1.5" } } } }, - "truffle-contract-schema": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/truffle-contract-schema/-/truffle-contract-schema-2.0.0.tgz", - "integrity": "sha512-nLlspmu1GKDaluWksBwitHi/7Z3IpRjmBYeO9N+T1nVJD2V4IWJaptCKP1NqnPiJA+FChB7+F7pI6Br51/FtXQ==", + "sol-explore": { + "version": "1.6.2", + "resolved": "https://registry.npmjs.org/sol-explore/-/sol-explore-1.6.2.tgz", + "integrity": "sha1-Q66MQZ/TrAVqBfip0fsQIs1B7MI=", + "dev": true + }, + "solc": { + "version": "0.4.24", + "resolved": "https://registry.npmjs.org/solc/-/solc-0.4.24.tgz", + "integrity": "sha512-2xd7Cf1HeVwrIb6Bu1cwY2/TaLRodrppCq3l7rhLimFQgmxptXhTC3+/wesVLpB09F1A2kZgvbMOgH7wvhFnBQ==", + "requires": { + "fs-extra": "^0.30.0", + "memorystream": "^0.3.1", + "require-from-string": "^1.1.0", + "semver": "^5.3.0", + "yargs": "^4.7.1" + } + }, + "solidity-coverage": { + "version": "0.5.11", + "resolved": "https://registry.npmjs.org/solidity-coverage/-/solidity-coverage-0.5.11.tgz", + "integrity": "sha512-qikdsSi6+9XbfvwA0aI7HUVpF9fIFNqRWTw23M89GMDY+b6Gj0wWU9IngJS0fimoZIAdEp3bfChxvpfVcrUesg==", "dev": true, "requires": { - "ajv": "^5.1.1", - "crypto-js": "^3.1.9-1", - "debug": "^3.1.0" + "death": "^1.1.0", + "ethereumjs-testrpc-sc": "6.1.6", + "istanbul": "^0.4.5", + "keccakjs": "^0.2.1", + "req-cwd": "^1.0.1", + "shelljs": "^0.7.4", + "sol-explore": "^1.6.2", + "solidity-parser-sc": "0.4.11", + "tree-kill": "^1.2.0", + "web3": "^0.18.4" }, "dependencies": { - "crypto-js": { - "version": "3.1.9-1", - "resolved": "https://registry.npmjs.org/crypto-js/-/crypto-js-3.1.9-1.tgz", - "integrity": "sha1-/aGedh/Ad+Af+/3G6f38WeiAbNg=", - "dev": true + "req-cwd": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/req-cwd/-/req-cwd-1.0.1.tgz", + "integrity": "sha1-DXOurpJm5penj3l2AZZ352rPD/8=", + "dev": true, + "requires": { + "req-from": "^1.0.1" + } }, - "debug": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", - "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", + "req-from": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/req-from/-/req-from-1.0.1.tgz", + "integrity": "sha1-v4HaUUeUfTLRO5R9wSpYrUWHNQ4=", "dev": true, "requires": { - "ms": "2.0.0" + "resolve-from": "^2.0.0" } + }, + "resolve-from": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-2.0.0.tgz", + "integrity": "sha1-lICrIOlP+h2egKgEx+oUdhGWa1c=", + "dev": true } } }, - "truffle-error": { - "version": "0.0.2", - "resolved": "https://registry.npmjs.org/truffle-error/-/truffle-error-0.0.2.tgz", - "integrity": "sha1-AbGJt4UFVmrhaJwjnHyi3RIc/kw=", + "solidity-parser-antlr": { + "version": "0.2.15", + "resolved": "https://registry.npmjs.org/solidity-parser-antlr/-/solidity-parser-antlr-0.2.15.tgz", + "integrity": "sha512-EzRI8/TR/ljTXkZAyAjb0w4G20wH2XM7pcNf87ifdV825AbUv7DkY7HmiZCTj6NeKtIx8Y1s0NZWPbj+JTp8Zw==", "dev": true }, - "truffle-expect": { - "version": "0.0.3", - "resolved": "https://registry.npmjs.org/truffle-expect/-/truffle-expect-0.0.3.tgz", - "integrity": "sha1-m3XO80O9WW5+XbyHj18bLjGKlEw=", + "solidity-parser-sc": { + "version": "0.4.11", + "resolved": "https://registry.npmjs.org/solidity-parser-sc/-/solidity-parser-sc-0.4.11.tgz", + "integrity": "sha512-1kV5iC7m3CtMDfmHaVNwz2saSGQVIuF16rIxU417Al38MVCWHMQQ5vT6cmLsNwDe60S74auobWij9vNawSeOyw==", + "dev": true, + "requires": { + "mocha": "^4.1.0", + "pegjs": "^0.10.0", + "yargs": "^4.6.0" + } + }, + "source-map": { + "version": "0.5.7", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", + "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=", "dev": true }, - "truffle-flattener": { - "version": "1.2.3", - "resolved": "https://registry.npmjs.org/truffle-flattener/-/truffle-flattener-1.2.3.tgz", - "integrity": "sha512-DisthKMI1qH+Xbw/S84CLPGeXz/kMkVUxBpz8Elj2kI4paVjEFEFwrq0juQHwxr2w/046r2tUT5usCE38Bw6Qw==", + "source-map-resolve": { + "version": "0.5.2", + "resolved": "https://registry.npmjs.org/source-map-resolve/-/source-map-resolve-0.5.2.tgz", + "integrity": "sha512-MjqsvNwyz1s0k81Goz/9vRBe9SZdB09Bdw+/zYyO+3CuPk6fouTaxscHkgtE8jKvf01kVfl8riHzERQ/kefaSA==", "dev": true, "requires": { - "find-up": "^2.1.0", - "semver": "^5.4.1", - "solidity-parser": "^0.4.0", - "truffle-config": "^1.0.2", - "truffle-resolver": "^4.0.1", - "tsort": "0.0.1" - }, - "dependencies": { - "find-up": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", - "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", - "dev": true, - "requires": { - "locate-path": "^2.0.0" - } - } + "atob": "^2.1.1", + "decode-uri-component": "^0.2.0", + "resolve-url": "^0.2.1", + "source-map-url": "^0.4.0", + "urix": "^0.1.0" } }, - "truffle-provider": { - "version": "0.0.4", - "resolved": "https://registry.npmjs.org/truffle-provider/-/truffle-provider-0.0.4.tgz", - "integrity": "sha512-yVxxjocxnJcFspQ0T4Rjq/1wvvm3iLxidb6oa1EAX5LsnSQLPG8wAM5+JLlJ4FDBsqJdZLGOq1RR5Ln/w7x5JA==", + "source-map-support": { + "version": "0.5.10", + "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.10.tgz", + "integrity": "sha512-YfQ3tQFTK/yzlGJuX8pTwa4tifQj4QS2Mj7UegOu8jAz59MqIiMGPXxQhVQiIMNzayuUSF/jEuVnfFF5JqybmQ==", "dev": true, "requires": { - "truffle-error": "^0.0.2", - "web3": "^0.20.1" + "buffer-from": "^1.0.0", + "source-map": "^0.6.0" + }, + "dependencies": { + "source-map": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", + "dev": true + } } }, - "truffle-provisioner": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/truffle-provisioner/-/truffle-provisioner-0.1.0.tgz", - "integrity": "sha1-Ap5SScEBUwBzhTXgT97ZMaU8T2I=", + "source-map-url": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/source-map-url/-/source-map-url-0.4.0.tgz", + "integrity": "sha1-PpNdfd1zYxuXZZlW1VEo6HtQhKM=", "dev": true }, - "truffle-resolver": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/truffle-resolver/-/truffle-resolver-4.0.2.tgz", - "integrity": "sha512-HKRd45HSfAqb9/BCOgYq4zkyl2lF40MvPDIGhyoPXFj5/9PSFzclyTkkMOdb+Rnm7oC1vY4cE1/k453lgf81Kw==", - "dev": true, + "spdx-correct": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/spdx-correct/-/spdx-correct-3.1.0.tgz", + "integrity": "sha512-lr2EZCctC2BNR7j7WzJ2FpDznxky1sjfxvvYEyzxNyb6lZXHODmEoJeFu4JupYlkfha1KZpJyoqiJ7pgA1qq8Q==", "requires": { - "async": "^2.1.4", - "truffle-contract": "^3.0.4", - "truffle-expect": "0.0.3", - "truffle-provisioner": "^0.1.0" + "spdx-expression-parse": "^3.0.0", + "spdx-license-ids": "^3.0.0" } }, - "tsort": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/tsort/-/tsort-0.0.1.tgz", - "integrity": "sha1-4igPXoF/i/QnVlf9D5rr1E9aJ4Y=", - "dev": true + "spdx-exceptions": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/spdx-exceptions/-/spdx-exceptions-2.2.0.tgz", + "integrity": "sha512-2XQACfElKi9SlVb1CYadKDXvoajPgBVPn/gOQLrTvHdElaVhr7ZEbqJaRnJLVNeaI4cMEAgVCeBMKF6MWRDCRA==" }, - "tunnel-agent": { - "version": "0.6.0", - "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.6.0.tgz", - "integrity": "sha1-J6XeoGs2sEoKmWZ3SykIaPD8QP0=", + "spdx-expression-parse": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/spdx-expression-parse/-/spdx-expression-parse-3.0.0.tgz", + "integrity": "sha512-Yg6D3XpRD4kkOmTpdgbUiEJFKghJH03fiC1OPll5h/0sO6neh2jqRDVHOQ4o/LMea0tgCkbMgea5ip/e+MkWyg==", "requires": { - "safe-buffer": "^5.0.1" + "spdx-exceptions": "^2.1.0", + "spdx-license-ids": "^3.0.0" } }, - "tweetnacl": { - "version": "0.14.5", - "resolved": "https://registry.npmjs.org/tweetnacl/-/tweetnacl-0.14.5.tgz", - "integrity": "sha1-WuaBd/GS1EViadEIr6k/+HQ/T2Q=", - "optional": true + "spdx-license-ids": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/spdx-license-ids/-/spdx-license-ids-3.0.3.tgz", + "integrity": "sha512-uBIcIl3Ih6Phe3XHK1NqboJLdGfwr1UN3k6wSD1dZpmPsIkb8AGNbZYJ1fOBk834+Gxy8rpfDxrS6XLEMZMY2g==" }, - "type-check": { - "version": "0.3.2", - "resolved": "https://registry.npmjs.org/type-check/-/type-check-0.3.2.tgz", - "integrity": "sha1-WITKtRLPHTVeP7eE8wgEsrUg23I=", + "split-string": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/split-string/-/split-string-3.1.0.tgz", + "integrity": "sha512-NzNVhJDYpwceVVii8/Hu6DKfD2G+NrQHlS/V/qgv763EYudVwEcMQNxd2lh+0VrUByXN/oJkl5grOhYWvQUYiw==", "dev": true, "requires": { - "prelude-ls": "~1.1.2" + "extend-shallow": "^3.0.0" } }, - "type-detect": { - "version": "4.0.8", - "resolved": "https://registry.npmjs.org/type-detect/-/type-detect-4.0.8.tgz", - "integrity": "sha512-0fr/mIH1dlO+x7TlcMy+bIDqKPsw/70tVyeHW787goQjhmqaZe10uwLujubK9q9Lg6Fiho1KUKDYz0Z7k7g5/g==", + "sprintf-js": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz", + "integrity": "sha1-BOaSb2YolTVPPdAVIDYzuFcpfiw=", "dev": true }, - "type-is": { - "version": "1.6.16", - "resolved": "https://registry.npmjs.org/type-is/-/type-is-1.6.16.tgz", - "integrity": "sha512-HRkVv/5qY2G6I8iab9cI7v1bOIdhm94dVjQCPFElW9W+3GeDOSHmy2EBYe4VTApuzolPcmgFTN3ftVJRKR2J9Q==", + "sshpk": { + "version": "1.16.1", + "resolved": "https://registry.npmjs.org/sshpk/-/sshpk-1.16.1.tgz", + "integrity": "sha512-HXXqVUq7+pcKeLqqZj6mHFUMvXtOJt1uoUx09pFW6011inTMxqI8BA8PM95myrIyyKwdnzjdFjLiE6KBPVtJIg==", + "dev": true, "requires": { - "media-typer": "0.3.0", - "mime-types": "~2.1.18" + "asn1": "~0.2.3", + "assert-plus": "^1.0.0", + "bcrypt-pbkdf": "^1.0.0", + "dashdash": "^1.12.0", + "ecc-jsbn": "~0.1.1", + "getpass": "^0.1.1", + "jsbn": "~0.1.0", + "safer-buffer": "^2.0.2", + "tweetnacl": "~0.14.0" } }, - "typedarray": { - "version": "0.0.6", - "resolved": "https://registry.npmjs.org/typedarray/-/typedarray-0.0.6.tgz", - "integrity": "sha1-hnrHTjhkGHsdPUfZlqeOxciDB3c=", - "dev": true - }, - "uglify-js": { - "version": "2.8.29", - "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-2.8.29.tgz", - "integrity": "sha1-KcVzMUgFe7Th913zW3qcty5qWd0=", + "static-extend": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/static-extend/-/static-extend-0.1.2.tgz", + "integrity": "sha1-YICcOcv/VTNyJv1eC1IPNB8ftcY=", "dev": true, - "optional": true, "requires": { - "source-map": "~0.5.1", - "uglify-to-browserify": "~1.0.0", - "yargs": "~3.10.0" + "define-property": "^0.2.5", + "object-copy": "^0.1.0" }, "dependencies": { - "camelcase": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-1.2.1.tgz", - "integrity": "sha1-m7UwTS4LVmmLLHWLCKPqqdqlijk=", - "dev": true, - "optional": true - }, - "cliui": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/cliui/-/cliui-2.1.0.tgz", - "integrity": "sha1-S0dXYP+AJkx2LDoXGQMukcf+oNE=", - "dev": true, - "optional": true, - "requires": { - "center-align": "^0.1.1", - "right-align": "^0.1.1", - "wordwrap": "0.0.2" - } - }, - "window-size": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/window-size/-/window-size-0.1.0.tgz", - "integrity": "sha1-VDjNLqk7IC76Ohn+iIeu58lPnJ0=", - "dev": true, - "optional": true - }, - "wordwrap": { - "version": "0.0.2", - "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-0.0.2.tgz", - "integrity": "sha1-t5Zpu0LstAn4PVg8rVLKF+qhZD8=", - "dev": true, - "optional": true - }, - "yargs": { - "version": "3.10.0", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-3.10.0.tgz", - "integrity": "sha1-9+572FfdfB0tOMDnTvvWgdFDH9E=", + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", "dev": true, - "optional": true, "requires": { - "camelcase": "^1.0.2", - "cliui": "^2.1.0", - "decamelize": "^1.0.0", - "window-size": "0.1.0" + "is-descriptor": "^0.1.0" } } } }, - "uglify-to-browserify": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/uglify-to-browserify/-/uglify-to-browserify-1.0.2.tgz", - "integrity": "sha1-bgkk1r2mta/jSeOabWMoUKD4grc=", - "dev": true, - "optional": true + "stealthy-require": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/stealthy-require/-/stealthy-require-1.1.1.tgz", + "integrity": "sha1-NbCYdbT/SfJqd35QmzCQoyJr8ks=", + "dev": true + }, + "strict-uri-encode": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/strict-uri-encode/-/strict-uri-encode-1.1.0.tgz", + "integrity": "sha1-J5siXfHVgrH1TmWt3UNS4Y+qBxM=" + }, + "string-width": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz", + "integrity": "sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=", + "requires": { + "code-point-at": "^1.0.0", + "is-fullwidth-code-point": "^1.0.0", + "strip-ansi": "^3.0.0" + } + }, + "string_decoder": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", + "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", + "dev": true, + "requires": { + "safe-buffer": "~5.1.0" + } + }, + "strip-ansi": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", + "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", + "requires": { + "ansi-regex": "^2.0.0" + } + }, + "strip-bom": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-2.0.0.tgz", + "integrity": "sha1-YhmoVhZSBJHzV4i9vxRHqZx+aw4=", + "requires": { + "is-utf8": "^0.2.0" + } + }, + "strip-eof": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/strip-eof/-/strip-eof-1.0.0.tgz", + "integrity": "sha1-u0P/VZim6wXYm1n80SnJgzE2Br8=", + "dev": true + }, + "strip-hex-prefix": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/strip-hex-prefix/-/strip-hex-prefix-1.0.0.tgz", + "integrity": "sha1-DF8VX+8RUTczd96du1iNoFUA428=", + "requires": { + "is-hex-prefixed": "1.0.0" + } + }, + "strip-json-comments": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", + "integrity": "sha1-PFMZQukIwml8DsNEhYwobHygpgo=", + "dev": true }, - "ultron": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/ultron/-/ultron-1.1.1.tgz", - "integrity": "sha512-UIEXBNeYmKptWH6z8ZnqTeS8fV74zG0/eRU9VGkpzz+LIJNs8W/zM/L+7ctCkRrgbNnnR0xxw4bKOr0cW0N0Og==" + "supports-color": { + "version": "4.4.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-4.4.0.tgz", + "integrity": "sha512-rKC3+DyXWgK0ZLKwmRsrkyHVZAjNkfzeehuFWdGGcqGDTZFH73+RH6S/RDAAxl9GusSjZSUWYLmT9N5pzXFOXQ==", + "requires": { + "has-flag": "^2.0.0" + } }, - "undefsafe": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/undefsafe/-/undefsafe-2.0.2.tgz", - "integrity": "sha1-Il9rngM3Zj4Njnz9aG/Cg2zKznY=", + "sync-request": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/sync-request/-/sync-request-6.0.0.tgz", + "integrity": "sha512-jGNIAlCi9iU4X3Dm4oQnNQshDD3h0/1A7r79LyqjbjUnj69sX6mShAXlhRXgImsfVKtTcnra1jfzabdZvp+Lmw==", "dev": true, "requires": { - "debug": "^2.2.0" + "http-response-object": "^3.0.1", + "sync-rpc": "^1.2.1", + "then-request": "^6.0.0" } }, - "underscore": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.6.0.tgz", - "integrity": "sha1-izixDKze9jM3uLJOT/htRa6lKag=" + "sync-rpc": { + "version": "1.3.4", + "resolved": "https://registry.npmjs.org/sync-rpc/-/sync-rpc-1.3.4.tgz", + "integrity": "sha512-Iug+t1ICVFenUcTnDu8WXFnT+k8IVoLKGh8VA3eXUtl2Rt9SjKX3YEv33OenABqpTPL9QEaHv1+CNn2LK8vMow==", + "dev": true, + "requires": { + "get-port": "^3.1.0" + } }, - "union-value": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/union-value/-/union-value-1.0.0.tgz", - "integrity": "sha1-XHHDTLW61dzr4+oM0IIHulqhrqQ=", + "term-size": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/term-size/-/term-size-1.2.0.tgz", + "integrity": "sha1-RYuDiH8oj8Vtb/+/rSYuJmOO+mk=", "dev": true, "requires": { - "arr-union": "^3.1.0", - "get-value": "^2.0.6", - "is-extendable": "^0.1.1", - "set-value": "^0.4.3" - }, - "dependencies": { - "extend-shallow": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", - "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", - "dev": true, - "requires": { - "is-extendable": "^0.1.0" - } - }, - "set-value": { - "version": "0.4.3", - "resolved": "https://registry.npmjs.org/set-value/-/set-value-0.4.3.tgz", - "integrity": "sha1-fbCPnT0i3H945Trzw79GZuzfzPE=", - "dev": true, - "requires": { - "extend-shallow": "^2.0.1", - "is-extendable": "^0.1.1", - "is-plain-object": "^2.0.1", - "to-object-path": "^0.3.0" - } - } + "execa": "^0.7.0" } }, - "unique-string": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/unique-string/-/unique-string-1.0.0.tgz", - "integrity": "sha1-nhBXzKhRq7kzmPizOuGHuZyuwRo=", + "then-request": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/then-request/-/then-request-6.0.0.tgz", + "integrity": "sha512-xA+7uEMc+jsQIoyySJ93Ad08Kuqnik7u6jLS5hR91Z3smAoCfL3M8/MqMlobAa9gzBfO9pA88A/AntfepkkMJQ==", "dev": true, "requires": { - "crypto-random-string": "^1.0.0" + "@types/concat-stream": "^1.6.0", + "@types/form-data": "0.0.33", + "@types/node": "^8.0.0", + "@types/qs": "^6.2.31", + "caseless": "~0.12.0", + "concat-stream": "^1.6.0", + "form-data": "^2.2.0", + "http-basic": "^7.0.0", + "http-response-object": "^3.0.1", + "promise": "^8.0.0", + "qs": "^6.4.0" + }, + "dependencies": { + "@types/node": { + "version": "8.10.40", + "resolved": "https://registry.npmjs.org/@types/node/-/node-8.10.40.tgz", + "integrity": "sha512-RRSjdwz63kS4u7edIwJUn8NqKLLQ6LyqF/X4+4jp38MBT3Vwetewi2N4dgJEshLbDwNgOJXNYoOwzVZUSSLhkQ==", + "dev": true + } } }, - "unpipe": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/unpipe/-/unpipe-1.0.0.tgz", - "integrity": "sha1-sr9O6FFKrmFltIF4KdIbLvSZBOw=" + "timed-out": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/timed-out/-/timed-out-4.0.1.tgz", + "integrity": "sha1-8y6srFoXW+ol1/q1Zas+2HQe9W8=" }, - "unset-value": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/unset-value/-/unset-value-1.0.0.tgz", - "integrity": "sha1-g3aHP30jNRef+x5vw6jtDfyKtVk=", + "to-object-path": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/to-object-path/-/to-object-path-0.3.0.tgz", + "integrity": "sha1-KXWIt7Dn4KwI4E5nL4XB9JmeF68=", "dev": true, "requires": { - "has-value": "^0.3.1", - "isobject": "^3.0.0" + "kind-of": "^3.0.2" }, "dependencies": { - "has-value": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/has-value/-/has-value-0.3.1.tgz", - "integrity": "sha1-ex9YutpiyoJ+wKIHgCVlSEWZXh8=", + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", "dev": true, "requires": { - "get-value": "^2.0.3", - "has-values": "^0.1.4", - "isobject": "^2.0.0" - }, - "dependencies": { - "isobject": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/isobject/-/isobject-2.1.0.tgz", - "integrity": "sha1-8GVWEJaj8dou9GJy+BXIQNh+DIk=", - "dev": true, - "requires": { - "isarray": "1.0.0" - } - } + "is-buffer": "^1.1.5" } - }, - "has-values": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/has-values/-/has-values-0.1.4.tgz", - "integrity": "sha1-bWHeldkd/Km5oCCJrThL/49it3E=", - "dev": true } } }, - "untildify": { + "to-regex": { "version": "3.0.2", - "resolved": "https://registry.npmjs.org/untildify/-/untildify-3.0.2.tgz", - "integrity": "sha1-fx8wIFWz/qDz6B3HjrNnZstl4/E=" - }, - "unzip-response": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/unzip-response/-/unzip-response-2.0.1.tgz", - "integrity": "sha1-0vD3N9FrBhXnKmk17QQhRXLVb5c=", - "dev": true - }, - "upath": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/upath/-/upath-1.0.5.tgz", - "integrity": "sha512-qbKn90aDQ0YEwvXoLqj0oiuUYroLX2lVHZ+b+xwjozFasAOC4GneDq5+OaIG5Zj+jFmbz/uO+f7a9qxjktJQww==", - "dev": true - }, - "update-notifier": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/update-notifier/-/update-notifier-2.5.0.tgz", - "integrity": "sha512-gwMdhgJHGuj/+wHJJs9e6PcCszpxR1b236igrOkUofGhqJuG+amlIKwApH1IW1WWl7ovZxsX49lMBWLxSdm5Dw==", + "resolved": "https://registry.npmjs.org/to-regex/-/to-regex-3.0.2.tgz", + "integrity": "sha512-FWtleNAtZ/Ki2qtqej2CXTOayOH9bHDQF+Q48VpWyDXjbYxA4Yz8iDB31zXOBUlOHHKidDbqGVrTUvQMPmBGBw==", "dev": true, "requires": { - "boxen": "^1.2.1", - "chalk": "^2.0.1", - "configstore": "^3.0.0", - "import-lazy": "^2.1.0", - "is-ci": "^1.0.10", - "is-installed-globally": "^0.1.0", - "is-npm": "^1.0.0", - "latest-version": "^3.0.0", - "semver-diff": "^2.0.0", - "xdg-basedir": "^3.0.0" + "define-property": "^2.0.2", + "extend-shallow": "^3.0.2", + "regex-not": "^1.0.2", + "safe-regex": "^1.1.0" } }, - "urix": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/urix/-/urix-0.1.0.tgz", - "integrity": "sha1-2pN/emLiH+wf0Y1Js1wpNQZ6bHI=", - "dev": true - }, - "url-parse-lax": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/url-parse-lax/-/url-parse-lax-1.0.0.tgz", - "integrity": "sha1-evjzA2Rem9eaJy56FKxovAYJ2nM=", + "to-regex-range": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-2.1.1.tgz", + "integrity": "sha1-fIDBe53+vlmeJzZ+DU3VWQFB2zg=", + "dev": true, "requires": { - "prepend-http": "^1.0.1" + "is-number": "^3.0.0", + "repeat-string": "^1.6.1" } }, - "url-set-query": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/url-set-query/-/url-set-query-1.0.0.tgz", - "integrity": "sha1-AW6M/Xwg7gXK/neV6JK9BwL6ozk=" - }, - "url-to-options": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/url-to-options/-/url-to-options-1.0.1.tgz", - "integrity": "sha1-FQWgOiiaSMvXpDTvuu7FBV9WM6k=" - }, - "use": { + "touch": { "version": "3.1.0", - "resolved": "https://registry.npmjs.org/use/-/use-3.1.0.tgz", - "integrity": "sha512-6UJEQM/L+mzC3ZJNM56Q4DFGLX/evKGRg15UJHGB9X5j5Z3AFbgZvjUh2yq/UJUY4U5dh7Fal++XbNg1uzpRAw==", + "resolved": "https://registry.npmjs.org/touch/-/touch-3.1.0.tgz", + "integrity": "sha512-WBx8Uy5TLtOSRtIq+M03/sKDrXCLHxwDcquSP2c43Le03/9serjQBIztjRz6FkJez9D/hleyAXTBGLwwZUw9lA==", "dev": true, "requires": { - "kind-of": "^6.0.2" + "nopt": "~1.0.10" } }, - "utf8": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/utf8/-/utf8-2.1.2.tgz", - "integrity": "sha1-H6DZJw6b6FDZsFAn9jUZv0ZFfZY=", + "tough-cookie": { + "version": "2.4.3", + "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.4.3.tgz", + "integrity": "sha512-Q5srk/4vDM54WJsJio3XNn6K2sCG+CQ8G5Wz6bZhRZoAe/+TxjWB/GlFAnYEbkYVlON9FMk/fE3h2RLpPXo4lQ==", + "dev": true, + "requires": { + "psl": "^1.1.24", + "punycode": "^1.4.1" + }, + "dependencies": { + "punycode": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/punycode/-/punycode-1.4.1.tgz", + "integrity": "sha1-wNWmOycYgArY4esPpSachN1BhF4=", + "dev": true + } + } + }, + "tree-kill": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/tree-kill/-/tree-kill-1.2.1.tgz", + "integrity": "sha512-4hjqbObwlh2dLyW4tcz0Ymw0ggoaVDMveUB9w8kFSQScdRLo0gxO9J7WFcUBo+W3C1TLdFIEwNOWebgZZ0RH9Q==", "dev": true }, - "util-deprecate": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", - "integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=" + "trim": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/trim/-/trim-0.0.1.tgz", + "integrity": "sha1-WFhUf2spB1fulczMZm+1AITEYN0=" }, - "utils-merge": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/utils-merge/-/utils-merge-1.0.1.tgz", - "integrity": "sha1-n5VxD1CiZ5R7LMwSR0HBAoQn5xM=" + "truffle": { + "version": "4.1.11", + "resolved": "https://registry.npmjs.org/truffle/-/truffle-4.1.11.tgz", + "integrity": "sha512-VNhc6jexZeM92sNJJr4U8ln3uJ/mJEQO/0y9ZLYc4pccyIskPtl+3r4mzymgGM/Mq5v6MpoQVD6NZgHUVKX+Dw==", + "requires": { + "mocha": "^4.1.0", + "original-require": "^1.0.1", + "solc": "0.4.24" + } }, - "uuid": { - "version": "3.2.1", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.2.1.tgz", - "integrity": "sha512-jZnMwlb9Iku/O3smGWvZhauCf6cvvpKi4BKRiliS3cxnI+Gz9j5MEpTz2UFuXiKPJocb7gnsLHwiS05ige5BEA==" + "truffle-flattener": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/truffle-flattener/-/truffle-flattener-1.3.0.tgz", + "integrity": "sha512-ppJ9xI0tDuvCYjQlcWwMBcOKZph5U4YpG/gChyUVDxOjUIniG5g7y9vZho2PRj1FohPPnOjg1KOAVNlk/bPZrw==", + "dev": true, + "requires": { + "@resolver-engine/imports-fs": "^0.2.2", + "find-up": "^2.1.0", + "mkdirp": "^0.5.1", + "solidity-parser-antlr": "^0.4.0", + "tsort": "0.0.1" + }, + "dependencies": { + "find-up": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", + "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", + "dev": true, + "requires": { + "locate-path": "^2.0.0" + } + }, + "solidity-parser-antlr": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/solidity-parser-antlr/-/solidity-parser-antlr-0.4.0.tgz", + "integrity": "sha512-RrIsh5VoHmrMQia6yLY8u8rx3JPREhSiCFz4Xb0h1Oh0prUYU2ukyWO8gG892V0UMHIXCWqvdZ3wSctNwdWThg==", + "dev": true + } + } }, - "v8-compile-cache": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/v8-compile-cache/-/v8-compile-cache-1.1.2.tgz", - "integrity": "sha512-ejdrifsIydN1XDH7EuR2hn8ZrkRKUYF7tUcBjBy/lhrCvs2K+zRlbW9UHc0IQ9RsYFZJFqJrieoIHfkCa0DBRA==" + "tsort": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/tsort/-/tsort-0.0.1.tgz", + "integrity": "sha1-4igPXoF/i/QnVlf9D5rr1E9aJ4Y=", + "dev": true }, - "validate-npm-package-license": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/validate-npm-package-license/-/validate-npm-package-license-3.0.1.tgz", - "integrity": "sha1-KAS6vnEq0zeUWaz74kdGqywwP7w=", + "tunnel-agent": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.6.0.tgz", + "integrity": "sha1-J6XeoGs2sEoKmWZ3SykIaPD8QP0=", + "dev": true, "requires": { - "spdx-correct": "~1.0.0", - "spdx-expression-parse": "~1.0.0" + "safe-buffer": "^5.0.1" } }, - "vary": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz", - "integrity": "sha1-IpnwLG3tMNSllhsLn3RSShj2NPw=" + "tweetnacl": { + "version": "0.14.5", + "resolved": "https://registry.npmjs.org/tweetnacl/-/tweetnacl-0.14.5.tgz", + "integrity": "sha1-WuaBd/GS1EViadEIr6k/+HQ/T2Q=", + "dev": true }, - "verror": { - "version": "1.10.0", - "resolved": "https://registry.npmjs.org/verror/-/verror-1.10.0.tgz", - "integrity": "sha1-OhBcoXBTr1XW4nDB+CiGguGNpAA=", + "type-check": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/type-check/-/type-check-0.3.2.tgz", + "integrity": "sha1-WITKtRLPHTVeP7eE8wgEsrUg23I=", + "dev": true, "requires": { - "assert-plus": "^1.0.0", - "core-util-is": "1.0.2", - "extsprintf": "^1.2.0" + "prelude-ls": "~1.1.2" } }, - "vinyl": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-1.2.0.tgz", - "integrity": "sha1-XIgDbPVl5d8FVYv8kR+GVt8hiIQ=", - "requires": { - "clone": "^1.0.0", - "clone-stats": "^0.0.1", - "replace-ext": "0.0.1" - } + "type-detect": { + "version": "4.0.8", + "resolved": "https://registry.npmjs.org/type-detect/-/type-detect-4.0.8.tgz", + "integrity": "sha512-0fr/mIH1dlO+x7TlcMy+bIDqKPsw/70tVyeHW787goQjhmqaZe10uwLujubK9q9Lg6Fiho1KUKDYz0Z7k7g5/g==", + "dev": true }, - "vinyl-file": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/vinyl-file/-/vinyl-file-2.0.0.tgz", - "integrity": "sha1-p+v1/779obfRjRQPyweyI++2dRo=", - "requires": { - "graceful-fs": "^4.1.2", - "pify": "^2.3.0", - "pinkie-promise": "^2.0.0", - "strip-bom": "^2.0.0", - "strip-bom-stream": "^2.0.0", - "vinyl": "^1.1.0" - } + "typedarray": { + "version": "0.0.6", + "resolved": "https://registry.npmjs.org/typedarray/-/typedarray-0.0.6.tgz", + "integrity": "sha1-hnrHTjhkGHsdPUfZlqeOxciDB3c=", + "dev": true }, - "web3": { - "version": "0.20.5", - "resolved": "https://registry.npmjs.org/web3/-/web3-0.20.5.tgz", - "integrity": "sha1-xQSNNfe/TixMKAzlH7u8lRKQsWU=", + "uglify-js": { + "version": "3.4.9", + "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-3.4.9.tgz", + "integrity": "sha512-8CJsbKOtEbnJsTyv6LE6m6ZKniqMiFWmm9sRbopbkGs3gMPPfd3Fh8iIA4Ykv5MgaTbqHr4BaoGLJLZNhsrW1Q==", "dev": true, + "optional": true, "requires": { - "bignumber.js": "git+https://github.com/frozeman/bignumber.js-nolookahead.git#57692b3ecfc98bbdd6b3a516cb2353652ea49934", - "crypto-js": "^3.1.4", - "utf8": "^2.1.1", - "xhr2": "*", - "xmlhttprequest": "*" - } - }, - "web3-utils": { - "version": "1.0.0-beta.34", - "resolved": "https://registry.npmjs.org/web3-utils/-/web3-utils-1.0.0-beta.34.tgz", - "integrity": "sha1-lBH8OarvOcpOBhafdiKX2f8CCXA=", - "requires": { - "bn.js": "4.11.6", - "eth-lib": "0.1.27", - "ethjs-unit": "0.1.6", - "number-to-bn": "1.7.0", - "randomhex": "0.1.5", - "underscore": "1.8.3", - "utf8": "2.1.1" + "commander": "~2.17.1", + "source-map": "~0.6.1" }, "dependencies": { - "underscore": { - "version": "1.8.3", - "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", - "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=" + "commander": { + "version": "2.17.1", + "resolved": "https://registry.npmjs.org/commander/-/commander-2.17.1.tgz", + "integrity": "sha512-wPMUt6FnH2yzG95SA6mzjQOEKUU3aLaDEmzs1ti+1E9h+CsrZghRlqEM/EJ4KscsQVG8uNN4uVreUeT8+drlgg==", + "dev": true, + "optional": true }, - "utf8": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/utf8/-/utf8-2.1.1.tgz", - "integrity": "sha1-LgHbAvfY0JRPdxBPFgnrDDBM92g=" + "source-map": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", + "dev": true, + "optional": true } } }, - "webpack-addons": { - "version": "1.1.5", - "resolved": "https://registry.npmjs.org/webpack-addons/-/webpack-addons-1.1.5.tgz", - "integrity": "sha512-MGO0nVniCLFAQz1qv22zM02QPjcpAoJdy7ED0i3Zy7SY1IecgXCm460ib7H/Wq7e9oL5VL6S2BxaObxwIcag0g==", + "undefsafe": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/undefsafe/-/undefsafe-2.0.2.tgz", + "integrity": "sha1-Il9rngM3Zj4Njnz9aG/Cg2zKznY=", + "dev": true, "requires": { - "jscodeshift": "^0.4.0" + "debug": "^2.2.0" }, "dependencies": { - "arr-diff": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/arr-diff/-/arr-diff-2.0.0.tgz", - "integrity": "sha1-jzuCf5Vai9ZpaX5KQlasPOrjVs8=", - "requires": { - "arr-flatten": "^1.0.1" - } - }, - "array-unique": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/array-unique/-/array-unique-0.2.1.tgz", - "integrity": "sha1-odl8yvy8JiXMcPrc6zalDFiwGlM=" - }, - "ast-types": { - "version": "0.10.1", - "resolved": "https://registry.npmjs.org/ast-types/-/ast-types-0.10.1.tgz", - "integrity": "sha512-UY7+9DPzlJ9VM8eY0b2TUZcZvF+1pO0hzMtAyjBYKhOmnvRlqYNYnWdtsMj0V16CGaMlpL0G1jnLbLo4AyotuQ==" - }, - "async": { - "version": "1.5.2", - "resolved": "https://registry.npmjs.org/async/-/async-1.5.2.tgz", - "integrity": "sha1-7GphrlZIDAw8skHJVhjiCJL5Zyo=" - }, - "babylon": { - "version": "6.18.0", - "resolved": "https://registry.npmjs.org/babylon/-/babylon-6.18.0.tgz", - "integrity": "sha512-q/UEjfGJ2Cm3oKV71DJz9d25TPnq5rhBVL2Q4fA5wcC3jcrdn7+SssEybFIxwAvvP+YCsCYNKughoF33GxgycQ==" - }, - "braces": { - "version": "1.8.5", - "resolved": "https://registry.npmjs.org/braces/-/braces-1.8.5.tgz", - "integrity": "sha1-uneWLhLf+WnWt2cR6RS3N4V79qc=", - "requires": { - "expand-range": "^1.8.1", - "preserve": "^0.2.0", - "repeat-element": "^1.1.2" - } - }, - "expand-brackets": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/expand-brackets/-/expand-brackets-0.1.5.tgz", - "integrity": "sha1-3wcoTjQqgHzXM6xa9yQR5YHRF3s=", - "requires": { - "is-posix-bracket": "^0.1.0" - } - }, - "extglob": { - "version": "0.3.2", - "resolved": "https://registry.npmjs.org/extglob/-/extglob-0.3.2.tgz", - "integrity": "sha1-Lhj/PS9JqydlzskCPwEdqo2DSaE=", - "requires": { - "is-extglob": "^1.0.0" - } - }, - "is-extglob": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-1.0.0.tgz", - "integrity": "sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA=" - }, - "is-glob": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-2.0.1.tgz", - "integrity": "sha1-0Jb5JqPe1WAPP9/ZEZjLCIjC2GM=", - "requires": { - "is-extglob": "^1.0.0" - } - }, - "jscodeshift": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/jscodeshift/-/jscodeshift-0.4.1.tgz", - "integrity": "sha512-iOX6If+hsw0q99V3n31t4f5VlD1TQZddH08xbT65ZqA7T4Vkx68emrDZMUOLVvCEAJ6NpAk7DECe3fjC/t52AQ==", - "requires": { - "async": "^1.5.0", - "babel-plugin-transform-flow-strip-types": "^6.8.0", - "babel-preset-es2015": "^6.9.0", - "babel-preset-stage-1": "^6.5.0", - "babel-register": "^6.9.0", - "babylon": "^6.17.3", - "colors": "^1.1.2", - "flow-parser": "^0.*", - "lodash": "^4.13.1", - "micromatch": "^2.3.7", - "node-dir": "0.1.8", - "nomnom": "^1.8.1", - "recast": "^0.12.5", - "temp": "^0.8.1", - "write-file-atomic": "^1.2.0" - } - }, - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", - "requires": { - "is-buffer": "^1.1.5" - } - }, - "micromatch": { - "version": "2.3.11", - "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-2.3.11.tgz", - "integrity": "sha1-hmd8l9FyCzY0MdBNDRUpO9OMFWU=", - "requires": { - "arr-diff": "^2.0.0", - "array-unique": "^0.2.1", - "braces": "^1.8.2", - "expand-brackets": "^0.1.4", - "extglob": "^0.3.1", - "filename-regex": "^2.0.0", - "is-extglob": "^1.0.0", - "is-glob": "^2.0.1", - "kind-of": "^3.0.2", - "normalize-path": "^2.0.1", - "object.omit": "^2.0.0", - "parse-glob": "^3.0.4", - "regex-cache": "^0.4.2" - } - }, - "recast": { - "version": "0.12.9", - "resolved": "https://registry.npmjs.org/recast/-/recast-0.12.9.tgz", - "integrity": "sha512-y7ANxCWmMW8xLOaiopiRDlyjQ9ajKRENBH+2wjntIbk3A6ZR1+BLQttkmSHMY7Arl+AAZFwJ10grg2T6f1WI8A==", - "requires": { - "ast-types": "0.10.1", - "core-js": "^2.4.1", - "esprima": "~4.0.0", - "private": "~0.1.5", - "source-map": "~0.6.1" - } - }, - "source-map": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", - "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==" - }, - "write-file-atomic": { - "version": "1.3.4", - "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-1.3.4.tgz", - "integrity": "sha1-+Aek8LHZ6ROuekgRLmzDrxmRtF8=", + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, "requires": { - "graceful-fs": "^4.1.11", - "imurmurhash": "^0.1.4", - "slide": "^1.1.5" + "ms": "2.0.0" } } } }, - "webpack-cli": { - "version": "2.0.13", - "resolved": "https://registry.npmjs.org/webpack-cli/-/webpack-cli-2.0.13.tgz", - "integrity": "sha512-0lnOi3yla8FsZVuMsbfnNRB/8DlfuDugKdekC+4ykydZG0+UOidMi5J5LLWN4c0VJ8PqC19yMXXkYyCq78OuqA==", - "requires": { - "chalk": "^2.3.2", - "cross-spawn": "^6.0.5", - "diff": "^3.5.0", - "enhanced-resolve": "^4.0.0", - "glob-all": "^3.1.0", - "global-modules": "^1.0.0", - "got": "^8.2.0", - "inquirer": "^5.1.0", - "interpret": "^1.0.4", - "jscodeshift": "^0.5.0", - "listr": "^0.13.0", - "loader-utils": "^1.1.0", - "lodash": "^4.17.5", - "log-symbols": "^2.2.0", - "mkdirp": "^0.5.1", - "p-each-series": "^1.0.0", - "p-lazy": "^1.0.0", - "prettier": "^1.5.3", - "resolve-cwd": "^2.0.0", - "supports-color": "^5.3.0", - "v8-compile-cache": "^1.1.2", - "webpack-addons": "^1.1.5", - "yargs": "^11.0.0", - "yeoman-environment": "^2.0.0", - "yeoman-generator": "^2.0.3" + "union-value": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/union-value/-/union-value-1.0.0.tgz", + "integrity": "sha1-XHHDTLW61dzr4+oM0IIHulqhrqQ=", + "dev": true, + "requires": { + "arr-union": "^3.1.0", + "get-value": "^2.0.6", + "is-extendable": "^0.1.1", + "set-value": "^0.4.3" }, "dependencies": { - "ansi-regex": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", - "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=" - }, - "camelcase": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-4.1.0.tgz", - "integrity": "sha1-1UVjW+HjPFQmScaRc+Xeas+uNN0=" - }, - "cliui": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/cliui/-/cliui-4.0.0.tgz", - "integrity": "sha512-nY3W5Gu2racvdDk//ELReY+dHjb9PlIcVDFXP72nVIhq2Gy3LuVXYwJoPVudwQnv1shtohpgkdCKT2YaKY0CKw==", - "requires": { - "string-width": "^2.1.1", - "strip-ansi": "^4.0.0", - "wrap-ansi": "^2.0.0" - } - }, - "cross-spawn": { - "version": "6.0.5", - "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-6.0.5.tgz", - "integrity": "sha512-eTVLrBSt7fjbDygz805pMnstIs2VTBNkRm0qxZd+M7A5XDdxVRWO5MxGBXZhjY4cqLYLdtrGqRf8mBPmzwSpWQ==", - "requires": { - "nice-try": "^1.0.4", - "path-key": "^2.0.1", - "semver": "^5.5.0", - "shebang-command": "^1.2.0", - "which": "^1.2.9" - } - }, - "diff": { - "version": "3.5.0", - "resolved": "https://registry.npmjs.org/diff/-/diff-3.5.0.tgz", - "integrity": "sha512-A46qtFgd+g7pDZinpnwiRJtxbC1hpgf0uzP3iG89scHk0AUC7A1TGxf5OiiOUv/JMZR8GOt8hL900hV0bOy5xA==" - }, - "find-up": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", - "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", - "requires": { - "locate-path": "^2.0.0" - } - }, - "got": { - "version": "8.3.0", - "resolved": "https://registry.npmjs.org/got/-/got-8.3.0.tgz", - "integrity": "sha512-kBNy/S2CGwrYgDSec5KTWGKUvupwkkTVAjIsVFF2shXO13xpZdFP4d4kxa//CLX2tN/rV0aYwK8vY6UKWGn2vQ==", - "requires": { - "@sindresorhus/is": "^0.7.0", - "cacheable-request": "^2.1.1", - "decompress-response": "^3.3.0", - "duplexer3": "^0.1.4", - "get-stream": "^3.0.0", - "into-stream": "^3.1.0", - "is-retry-allowed": "^1.1.0", - "isurl": "^1.0.0-alpha5", - "lowercase-keys": "^1.0.0", - "mimic-response": "^1.0.0", - "p-cancelable": "^0.4.0", - "p-timeout": "^2.0.1", - "pify": "^3.0.0", - "safe-buffer": "^5.1.1", - "timed-out": "^4.0.1", - "url-parse-lax": "^3.0.0", - "url-to-options": "^1.0.1" - } - }, - "has-flag": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", - "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=" - }, - "is-fullwidth-code-point": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", - "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=" - }, - "os-locale": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/os-locale/-/os-locale-2.1.0.tgz", - "integrity": "sha512-3sslG3zJbEYcaC4YVAvDorjGxc7tv6KVATnLPZONiljsUncvihe9BQoVCEs0RZ1kmf4Hk9OBqlZfJZWI4GanKA==", - "requires": { - "execa": "^0.7.0", - "lcid": "^1.0.0", - "mem": "^1.1.0" - } - }, - "pify": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", - "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=" - }, - "prepend-http": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/prepend-http/-/prepend-http-2.0.0.tgz", - "integrity": "sha1-6SQ0v6XqjBn0HN/UAddBo8gZ2Jc=" - }, - "string-width": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", - "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", - "requires": { - "is-fullwidth-code-point": "^2.0.0", - "strip-ansi": "^4.0.0" - } - }, - "strip-ansi": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", - "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", - "requires": { - "ansi-regex": "^3.0.0" - } - }, - "supports-color": { - "version": "5.3.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.3.0.tgz", - "integrity": "sha512-0aP01LLIskjKs3lq52EC0aGBAJhLq7B2Rd8HC/DR/PtNNpcLilNmHC12O+hu0usQpo7wtHNRqtrhBwtDb0+dNg==", + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "dev": true, "requires": { - "has-flag": "^3.0.0" + "is-extendable": "^0.1.0" } }, - "url-parse-lax": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/url-parse-lax/-/url-parse-lax-3.0.0.tgz", - "integrity": "sha1-FrXK/Afb42dsGxmZF3gj1lA6yww=", + "set-value": { + "version": "0.4.3", + "resolved": "https://registry.npmjs.org/set-value/-/set-value-0.4.3.tgz", + "integrity": "sha1-fbCPnT0i3H945Trzw79GZuzfzPE=", + "dev": true, "requires": { - "prepend-http": "^2.0.0" + "extend-shallow": "^2.0.1", + "is-extendable": "^0.1.1", + "is-plain-object": "^2.0.1", + "to-object-path": "^0.3.0" } - }, - "which-module": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/which-module/-/which-module-2.0.0.tgz", - "integrity": "sha1-2e8H3Od7mQK4o6j6SzHD4/fm6Ho=" - }, - "yargs": { - "version": "11.0.0", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-11.0.0.tgz", - "integrity": "sha512-Rjp+lMYQOWtgqojx1dEWorjCofi1YN7AoFvYV7b1gx/7dAAeuI4kN5SZiEvr0ZmsZTOpDRcCqrpI10L31tFkBw==", + } + } + }, + "unique-string": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/unique-string/-/unique-string-1.0.0.tgz", + "integrity": "sha1-nhBXzKhRq7kzmPizOuGHuZyuwRo=", + "dev": true, + "requires": { + "crypto-random-string": "^1.0.0" + } + }, + "unset-value": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/unset-value/-/unset-value-1.0.0.tgz", + "integrity": "sha1-g3aHP30jNRef+x5vw6jtDfyKtVk=", + "dev": true, + "requires": { + "has-value": "^0.3.1", + "isobject": "^3.0.0" + }, + "dependencies": { + "has-value": { + "version": "0.3.1", + "resolved": "https://registry.npmjs.org/has-value/-/has-value-0.3.1.tgz", + "integrity": "sha1-ex9YutpiyoJ+wKIHgCVlSEWZXh8=", + "dev": true, "requires": { - "cliui": "^4.0.0", - "decamelize": "^1.1.1", - "find-up": "^2.1.0", - "get-caller-file": "^1.0.1", - "os-locale": "^2.0.0", - "require-directory": "^2.1.1", - "require-main-filename": "^1.0.1", - "set-blocking": "^2.0.0", - "string-width": "^2.0.0", - "which-module": "^2.0.0", - "y18n": "^3.2.1", - "yargs-parser": "^9.0.2" + "get-value": "^2.0.3", + "has-values": "^0.1.4", + "isobject": "^2.0.0" + }, + "dependencies": { + "isobject": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/isobject/-/isobject-2.1.0.tgz", + "integrity": "sha1-8GVWEJaj8dou9GJy+BXIQNh+DIk=", + "dev": true, + "requires": { + "isarray": "1.0.0" + } + } } }, - "yargs-parser": { - "version": "9.0.2", - "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-9.0.2.tgz", - "integrity": "sha1-nM9qQ0YP5O1Aqbto9I1DuKaMwHc=", - "requires": { - "camelcase": "^4.1.0" - } + "has-values": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/has-values/-/has-values-0.1.4.tgz", + "integrity": "sha1-bWHeldkd/Km5oCCJrThL/49it3E=", + "dev": true } } }, + "unzip-response": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/unzip-response/-/unzip-response-2.0.1.tgz", + "integrity": "sha1-0vD3N9FrBhXnKmk17QQhRXLVb5c=", + "dev": true + }, + "upath": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/upath/-/upath-1.1.0.tgz", + "integrity": "sha512-bzpH/oBhoS/QI/YtbkqCg6VEiPYjSZtrHQM6/QnJS6OL9pKUFLqb3aFh4Scvwm45+7iAgiMkLhSbaZxUqmrprw==", + "dev": true + }, + "update-notifier": { + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/update-notifier/-/update-notifier-2.5.0.tgz", + "integrity": "sha512-gwMdhgJHGuj/+wHJJs9e6PcCszpxR1b236igrOkUofGhqJuG+amlIKwApH1IW1WWl7ovZxsX49lMBWLxSdm5Dw==", + "dev": true, + "requires": { + "boxen": "^1.2.1", + "chalk": "^2.0.1", + "configstore": "^3.0.0", + "import-lazy": "^2.1.0", + "is-ci": "^1.0.10", + "is-installed-globally": "^0.1.0", + "is-npm": "^1.0.0", + "latest-version": "^3.0.0", + "semver-diff": "^2.0.0", + "xdg-basedir": "^3.0.0" + } + }, + "uri-js": { + "version": "4.2.2", + "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.2.2.tgz", + "integrity": "sha512-KY9Frmirql91X2Qgjry0Wd4Y+YTdrdZheS8TFwvkbLWf/G5KNJDCh6pKL5OZctEW4+0Baa5idK2ZQuELRwPznQ==", + "dev": true, + "requires": { + "punycode": "^2.1.0" + } + }, + "urix": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/urix/-/urix-0.1.0.tgz", + "integrity": "sha1-2pN/emLiH+wf0Y1Js1wpNQZ6bHI=", + "dev": true + }, + "url-parse-lax": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/url-parse-lax/-/url-parse-lax-1.0.0.tgz", + "integrity": "sha1-evjzA2Rem9eaJy56FKxovAYJ2nM=", + "dev": true, + "requires": { + "prepend-http": "^1.0.1" + } + }, + "url-set-query": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/url-set-query/-/url-set-query-1.0.0.tgz", + "integrity": "sha1-AW6M/Xwg7gXK/neV6JK9BwL6ozk=" + }, + "use": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/use/-/use-3.1.1.tgz", + "integrity": "sha512-cwESVXlO3url9YWlFW/TA9cshCEhtu7IKJ/p5soJ/gGpj7vbvFrAY/eIioQ6Dw23KjZhYgiIo8HOs1nQ2vr/oQ==", + "dev": true + }, + "utf8": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/utf8/-/utf8-2.1.1.tgz", + "integrity": "sha1-LgHbAvfY0JRPdxBPFgnrDDBM92g=" + }, + "util-deprecate": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", + "integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=", + "dev": true + }, + "uuid": { + "version": "3.3.2", + "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.3.2.tgz", + "integrity": "sha512-yXJmeNaw3DnnKAOKJE51sL/ZaYfWJRl1pK9dr19YFCu0ObS231AB1/LbqTKRAQ5kw8A90rA6fr4riOUpTZvQZA==", + "dev": true + }, + "validate-npm-package-license": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/validate-npm-package-license/-/validate-npm-package-license-3.0.4.tgz", + "integrity": "sha512-DpKm2Ui/xN7/HQKCtpZxoRWBhZ9Z0kqtygG8XCgNQ8ZlDnxuQmWhj566j8fN4Cu3/JmbhsDo7fcAJq4s9h27Ew==", + "requires": { + "spdx-correct": "^3.0.0", + "spdx-expression-parse": "^3.0.0" + } + }, + "verror": { + "version": "1.10.0", + "resolved": "https://registry.npmjs.org/verror/-/verror-1.10.0.tgz", + "integrity": "sha1-OhBcoXBTr1XW4nDB+CiGguGNpAA=", + "dev": true, + "requires": { + "assert-plus": "^1.0.0", + "core-util-is": "1.0.2", + "extsprintf": "^1.2.0" + } + }, + "web3": { + "version": "0.18.4", + "resolved": "https://registry.npmjs.org/web3/-/web3-0.18.4.tgz", + "integrity": "sha1-gewXhBRUkfLqqJVbMcBgSeB8Xn0=", + "dev": true, + "requires": { + "bignumber.js": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", + "crypto-js": "^3.1.4", + "utf8": "^2.1.1", + "xhr2": "*", + "xmlhttprequest": "*" + } + }, + "web3-utils": { + "version": "1.0.0-beta.46", + "resolved": "https://registry.npmjs.org/web3-utils/-/web3-utils-1.0.0-beta.46.tgz", + "integrity": "sha512-mSz+NrAil2fDZkxTXHPntCclZ8DofMjv8Q+BYR0VAyzTzylpYNXAV0WDdxBp/sXgniWRZXZMF7OkQNWqhZ1J9g==", + "requires": { + "@babel/runtime": "^7.3.1", + "@types/bn.js": "^4.11.4", + "@types/node": "^10.12.18", + "bn.js": "4.11.8", + "eth-lib": "0.2.8", + "ethjs-unit": "^0.1.6", + "lodash": "^4.17.11", + "number-to-bn": "1.7.0", + "randomhex": "0.1.5", + "utf8": "2.1.1" + } + }, "which": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/which/-/which-1.3.0.tgz", - "integrity": "sha512-xcJpopdamTuY5duC/KnTTNBraPK54YwpenP4lzxU8H91GudWpFv38u0CKjclE1Wi2EH2EDz5LRcHcKbCIzqGyg==", + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/which/-/which-1.3.1.tgz", + "integrity": "sha512-HxJdYWq1MTIQbJ3nw0cqssHoTNU267KlrDuGZ1WYlxDStUtKUhOaJmh112/TZmHxxUfuJqPXSOm7tDyas0OSIQ==", + "dev": true, "requires": { "isexe": "^2.0.0" } @@ -8448,9 +4994,9 @@ "integrity": "sha1-u6Y8qGGUiZT/MHc2CJ47lgJsKk8=" }, "widest-line": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/widest-line/-/widest-line-2.0.0.tgz", - "integrity": "sha1-AUKk6KJD+IgsAjOqDgKBqnYVInM=", + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/widest-line/-/widest-line-2.0.1.tgz", + "integrity": "sha512-Ba5m9/Fa4Xt9eb2ELXt77JxVDV8w7qQrH0zS/TWSJdLyAwQjWoOzpzj5lwVftDz6n/EOu3tNACS84v509qwnJA==", "dev": true, "requires": { "string-width": "^2.1.1" @@ -8515,9 +5061,9 @@ "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=" }, "write-file-atomic": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-2.3.0.tgz", - "integrity": "sha512-xuPeK4OdjWqtfi59ylvVL0Yn35SF3zgcAcv7rBPFHVaEapaDr4GdGgm3j7ckTwH9wHL7fGmgfAnb0+THrHb8tA==", + "version": "2.4.2", + "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-2.4.2.tgz", + "integrity": "sha512-s0b6vB3xIVRLWywa6X9TOMA7k9zio0TMOsl9ZnDkliA/cfJlpHXAscj0gbHVJiTdIuAYpIyqS5GW91fqm6gG5g==", "dev": true, "requires": { "graceful-fs": "^4.1.11", @@ -8525,16 +5071,6 @@ "signal-exit": "^3.0.2" } }, - "ws": { - "version": "3.3.3", - "resolved": "https://registry.npmjs.org/ws/-/ws-3.3.3.tgz", - "integrity": "sha512-nnWLa/NwZSt4KQJu51MYlCcSQ5g7INpOrOMt4XV8j4dqTXdmlUmSHQ8/oLC069ckre0fRsgfvsKwbTdtKLCDkA==", - "requires": { - "async-limiter": "~1.0.0", - "safe-buffer": "~5.1.0", - "ultron": "~1.1.0" - } - }, "xdg-basedir": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/xdg-basedir/-/xdg-basedir-3.0.0.tgz", @@ -8542,9 +5078,9 @@ "dev": true }, "xhr": { - "version": "2.4.1", - "resolved": "https://registry.npmjs.org/xhr/-/xhr-2.4.1.tgz", - "integrity": "sha512-pAIU5vBr9Hiy5cpFIbPnwf0C18ZF86DBsZKrlsf87N5De/JbA6RJ83UP/cv+aljl4S40iRVMqP4pr4sF9Dnj0A==", + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/xhr/-/xhr-2.5.0.tgz", + "integrity": "sha512-4nlO/14t3BNUZRXIXfXe+3N6w3s1KoxcJUUURctd64BLRe67E4gRwp4PjywtDY72fXpZ1y6Ch0VZQRY/gMPzzQ==", "requires": { "global": "~4.3.0", "is-function": "^1.0.1", @@ -8599,7 +5135,8 @@ "yallist": { "version": "2.1.2", "resolved": "https://registry.npmjs.org/yallist/-/yallist-2.1.2.tgz", - "integrity": "sha1-HBH5IY8HYImkfdUS+TxmmaaoHVI=" + "integrity": "sha1-HBH5IY8HYImkfdUS+TxmmaaoHVI=", + "dev": true }, "yargs": { "version": "4.8.1", @@ -8630,201 +5167,6 @@ "camelcase": "^3.0.0", "lodash.assign": "^4.0.6" } - }, - "yeoman-environment": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/yeoman-environment/-/yeoman-environment-2.0.5.tgz", - "integrity": "sha512-6/W7/B54OPHJXob0n0+pmkwFsirC8cokuQkPSmT/D0lCcSxkKtg/BA6ZnjUBIwjuGqmw3DTrT4en++htaUju5g==", - "requires": { - "chalk": "^2.1.0", - "debug": "^3.1.0", - "diff": "^3.3.1", - "escape-string-regexp": "^1.0.2", - "globby": "^6.1.0", - "grouped-queue": "^0.3.3", - "inquirer": "^3.3.0", - "is-scoped": "^1.0.0", - "lodash": "^4.17.4", - "log-symbols": "^2.1.0", - "mem-fs": "^1.1.0", - "text-table": "^0.2.0", - "untildify": "^3.0.2" - }, - "dependencies": { - "ansi-regex": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", - "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=" - }, - "debug": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", - "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", - "requires": { - "ms": "2.0.0" - } - }, - "diff": { - "version": "3.5.0", - "resolved": "https://registry.npmjs.org/diff/-/diff-3.5.0.tgz", - "integrity": "sha512-A46qtFgd+g7pDZinpnwiRJtxbC1hpgf0uzP3iG89scHk0AUC7A1TGxf5OiiOUv/JMZR8GOt8hL900hV0bOy5xA==" - }, - "inquirer": { - "version": "3.3.0", - "resolved": "https://registry.npmjs.org/inquirer/-/inquirer-3.3.0.tgz", - "integrity": "sha512-h+xtnyk4EwKvFWHrUYsWErEVR+igKtLdchu+o0Z1RL7VU/jVMFbYir2bp6bAj8efFNxWqHX0dIss6fJQ+/+qeQ==", - "requires": { - "ansi-escapes": "^3.0.0", - "chalk": "^2.0.0", - "cli-cursor": "^2.1.0", - "cli-width": "^2.0.0", - "external-editor": "^2.0.4", - "figures": "^2.0.0", - "lodash": "^4.3.0", - "mute-stream": "0.0.7", - "run-async": "^2.2.0", - "rx-lite": "^4.0.8", - "rx-lite-aggregates": "^4.0.8", - "string-width": "^2.1.0", - "strip-ansi": "^4.0.0", - "through": "^2.3.6" - } - }, - "is-fullwidth-code-point": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", - "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=" - }, - "string-width": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", - "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", - "requires": { - "is-fullwidth-code-point": "^2.0.0", - "strip-ansi": "^4.0.0" - } - }, - "strip-ansi": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", - "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", - "requires": { - "ansi-regex": "^3.0.0" - } - } - } - }, - "yeoman-generator": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/yeoman-generator/-/yeoman-generator-2.0.3.tgz", - "integrity": "sha512-mODmrZ26a94djmGZZuIiomSGlN4wULdou29ZwcySupb2e9FdvoCl7Ps2FqHFjEHio3kOl/iBeaNqrnx3C3NwWg==", - "requires": { - "async": "^2.6.0", - "chalk": "^2.3.0", - "cli-table": "^0.3.1", - "cross-spawn": "^5.1.0", - "dargs": "^5.1.0", - "dateformat": "^3.0.2", - "debug": "^3.1.0", - "detect-conflict": "^1.0.0", - "error": "^7.0.2", - "find-up": "^2.1.0", - "github-username": "^4.0.0", - "istextorbinary": "^2.1.0", - "lodash": "^4.17.4", - "make-dir": "^1.1.0", - "mem-fs-editor": "^3.0.2", - "minimist": "^1.2.0", - "pretty-bytes": "^4.0.2", - "read-chunk": "^2.1.0", - "read-pkg-up": "^3.0.0", - "rimraf": "^2.6.2", - "run-async": "^2.0.0", - "shelljs": "^0.8.0", - "text-table": "^0.2.0", - "through2": "^2.0.0", - "yeoman-environment": "^2.0.5" - }, - "dependencies": { - "debug": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", - "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", - "requires": { - "ms": "2.0.0" - } - }, - "find-up": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", - "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", - "requires": { - "locate-path": "^2.0.0" - } - }, - "load-json-file": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-4.0.0.tgz", - "integrity": "sha1-L19Fq5HjMhYjT9U62rZo607AmTs=", - "requires": { - "graceful-fs": "^4.1.2", - "parse-json": "^4.0.0", - "pify": "^3.0.0", - "strip-bom": "^3.0.0" - } - }, - "minimist": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz", - "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=" - }, - "parse-json": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-4.0.0.tgz", - "integrity": "sha1-vjX1Qlvh9/bHRxhPmKeIy5lHfuA=", - "requires": { - "error-ex": "^1.3.1", - "json-parse-better-errors": "^1.0.1" - } - }, - "path-type": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/path-type/-/path-type-3.0.0.tgz", - "integrity": "sha512-T2ZUsdZFHgA3u4e5PfPbjd7HDDpxPnQb5jN0SrDsjNSuVXHJqtwTnWqG0B1jZrgmJ/7lj1EmVIByWt1gxGkWvg==", - "requires": { - "pify": "^3.0.0" - } - }, - "pify": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", - "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=" - }, - "read-pkg": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-3.0.0.tgz", - "integrity": "sha1-nLxoaXj+5l0WwA4rGcI3/Pbjg4k=", - "requires": { - "load-json-file": "^4.0.0", - "normalize-package-data": "^2.3.2", - "path-type": "^3.0.0" - } - }, - "read-pkg-up": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/read-pkg-up/-/read-pkg-up-3.0.0.tgz", - "integrity": "sha1-PtSWaF26D4/hGNBpHcUfSh/5bwc=", - "requires": { - "find-up": "^2.0.0", - "read-pkg": "^3.0.0" - } - }, - "strip-bom": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-3.0.0.tgz", - "integrity": "sha1-IzTBjpx1n3vdVv3vfprj1YjmjtM=" - } - } } } } diff --git a/package.json b/package.json index 299b5b46e..3dfb3abaf 100644 --- a/package.json +++ b/package.json @@ -15,7 +15,7 @@ "dependencies": { "ganache-cli": "^6.1.0", "openzeppelin-solidity": "^1.10.0", - "truffle": "^4.1.11", + "truffle": "4.1.11", "web3-utils": "^1.0.0-beta.34" }, "devDependencies": { @@ -24,7 +24,7 @@ "chai-bignumber": "^2.0.2", "eth-gas-reporter": "^0.1.12", "nodemon": "^1.17.3", - "solidity-coverage": "^0.4.15", + "solidity-coverage": "^0.5.11", "truffle-flattener": "^1.2.3" } } From e245268d156568891f87b5ce7e0e10c1b6c3adbe Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 19 Feb 2019 16:24:40 -0300 Subject: [PATCH 095/187] Add both-directions fee manager for native-to-erc --- .../upgradeable_contracts/BaseFeeManager.sol | 6 +-- .../native_to_erc20/FeeManagerNativeToErc.sol | 7 ++++ .../FeeManagerNativeToErcBothDirections.sol | 37 +++++++++++++++++++ .../native_to_erc20/HomeBridgeNativeToErc.sol | 21 ++++++++++- .../RewardableHomeBridgeNativeToErc.sol | 25 +++++++++++++ 5 files changed, 92 insertions(+), 4 deletions(-) create mode 100644 contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErcBothDirections.sol diff --git a/contracts/upgradeable_contracts/BaseFeeManager.sol b/contracts/upgradeable_contracts/BaseFeeManager.sol index 52eb98865..379fac11b 100644 --- a/contracts/upgradeable_contracts/BaseFeeManager.sol +++ b/contracts/upgradeable_contracts/BaseFeeManager.sol @@ -16,7 +16,7 @@ contract BaseFeeManager is EternalStorage, FeeTypes { event HomeFeeUpdated(uint256 fee); event ForeignFeeUpdated(uint256 fee); - function calculateFee(uint256 _value, bool _recover, bytes32 _feeType) external view returns(uint256) { + function calculateFee(uint256 _value, bool _recover, bytes32 _feeType) public view returns(uint256) { uint256 fee = _feeType == HOME_FEE ? getHomeFee() : getForeignFee(); uint256 eth = 1 ether; if (!_recover) { @@ -43,11 +43,11 @@ contract BaseFeeManager is EternalStorage, FeeTypes { return uintStorage[keccak256(abi.encodePacked("foreignFee"))]; } - function distributeFeeFromAffirmation(uint256 _fee) external { + function distributeFeeFromAffirmation(uint256 _fee) public { distributeFeeProportionally(_fee, REWARD_FOR_TRANSFERRING_FROM_FOREIGN); } - function distributeFeeFromSignatures(uint256 _fee) external { + function distributeFeeFromSignatures(uint256 _fee) public { distributeFeeProportionally(_fee, REWARD_FOR_TRANSFERRING_FROM_HOME); } diff --git a/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErc.sol index a1f5b4c4e..65905aeda 100644 --- a/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErc.sol +++ b/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErc.sol @@ -7,6 +7,13 @@ import "../Sacrifice.sol"; contract FeeManagerNativeToErc is BaseFeeManager { + function onRequestForSignature(uint256 _value) external view returns(uint256) { + return _value; + } + + function onSignaturesCollected(uint256) external { + } + function getFeeManagerMode() public pure returns(bytes4) { return bytes4(keccak256(abi.encodePacked("manages-one-direction"))); } diff --git a/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErcBothDirections.sol b/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErcBothDirections.sol new file mode 100644 index 000000000..c1aeb5470 --- /dev/null +++ b/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErcBothDirections.sol @@ -0,0 +1,37 @@ +pragma solidity 0.4.24; + +import "../BaseFeeManager.sol"; +import "../../IBurnableMintableERC677Token.sol"; +import "../Sacrifice.sol"; + + +contract FeeManagerNativeToErcBothDirections is BaseFeeManager { + + function onRequestForSignature(uint256 _value) external view returns(uint256) { + uint256 fee = calculateFee(_value, false, HOME_FEE); + return _value.sub(fee); + } + + function onSignaturesCollected(uint256 _value) external { + uint256 fee = calculateFee(_value, true, HOME_FEE); + distributeFeeFromSignatures(fee); + } + + function getFeeManagerMode() public pure returns(bytes4) { + return bytes4(keccak256(abi.encodePacked("manages-both-directions"))); + } + + function onAffirmationFeeDistribution(address _rewardAddress, uint256 _fee) internal { + _sendReward(_rewardAddress, _fee); + } + + function onSignatureFeeDistribution(address _rewardAddress, uint256 _fee) internal { + _sendReward(_rewardAddress, _fee); + } + + function _sendReward(address _rewardAddress, uint256 _fee) internal { + if (!_rewardAddress.send(_fee)) { + (new Sacrifice).value(_fee)(_rewardAddress); + } + } +} diff --git a/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol index 6b225fd56..d8126cc24 100644 --- a/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol +++ b/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol @@ -15,7 +15,12 @@ contract HomeBridgeNativeToErc is EternalStorage, BasicBridge, BasicHomeBridge, require(msg.data.length == 0); require(withinLimit(msg.value)); setTotalSpentPerDay(getCurrentDay(), totalSpentPerDay(getCurrentDay()).add(msg.value)); - emit UserRequestForSignature(msg.sender, msg.value); + uint256 valueToTransfer = msg.value; + address feeManager = feeManagerContract(); + if (feeManager != address(0)) { + valueToTransfer = onRequestForSignature(valueToTransfer, feeManager); + } + emit UserRequestForSignature(msg.sender, valueToTransfer); } function initialize ( @@ -56,6 +61,7 @@ contract HomeBridgeNativeToErc is EternalStorage, BasicBridge, BasicHomeBridge, uint256 _foreignMaxPerTx, address _owner, address _feeManager, + uint256 _homeFee, uint256 _foreignFee ) public returns(bool) { @@ -72,6 +78,7 @@ contract HomeBridgeNativeToErc is EternalStorage, BasicBridge, BasicHomeBridge, ); require(isContract(_feeManager)); addressStorage[keccak256(abi.encodePacked("feeManagerContract"))] = _feeManager; + _setFee(_feeManager, _homeFee, HOME_FEE); _setFee(_feeManager, _foreignFee, FOREIGN_FEE); setInitialize(true); return isInitialized(); @@ -112,6 +119,18 @@ contract HomeBridgeNativeToErc is EternalStorage, BasicBridge, BasicHomeBridge, setOwner(_owner); } + function onSignaturesCollected(bytes _message) internal { + address feeManager = feeManagerContract(); + if (feeManager != address(0)) { + address recipient; + uint256 amount; + bytes32 txHash; + address contractAddress; + (recipient, amount, txHash, contractAddress) = Message.parseMessage(_message); + distributeFeeOnSignaturesCollected(amount, feeManager); + } + } + function onExecuteAffirmation(address _recipient, uint256 _value) internal returns(bool) { setTotalExecutedPerDay(getCurrentDay(), totalExecutedPerDay(getCurrentDay()).add(_value)); uint256 valueToTransfer = _value; diff --git a/contracts/upgradeable_contracts/native_to_erc20/RewardableHomeBridgeNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/RewardableHomeBridgeNativeToErc.sol index f6f9085c0..71f96fc15 100644 --- a/contracts/upgradeable_contracts/native_to_erc20/RewardableHomeBridgeNativeToErc.sol +++ b/contracts/upgradeable_contracts/native_to_erc20/RewardableHomeBridgeNativeToErc.sol @@ -9,7 +9,32 @@ contract RewardableHomeBridgeNativeToErc is RewardableBridge { _setFee(feeManagerContract(), _fee, FOREIGN_FEE); } + function setHomeFee(uint256 _fee) external onlyOwner { + _setFee(feeManagerContract(), _fee, HOME_FEE); + } + function getForeignFee() public view returns(uint256) { return _getFee(FOREIGN_FEE); } + + function getHomeFee() public view returns(uint256) { + return _getFee(HOME_FEE); + } + + function onRequestForSignature(uint256 _value, address _impl) internal view returns(uint256) { + uint256 returnedValue; + bytes memory callData = abi.encodeWithSignature("onRequestForSignature(uint256)", _value); + assembly { + let result := callcode(gas, _impl, 0x0, add(callData, 0x20), mload(callData), 0, 32) + returnedValue := mload(0) + + switch result + case 0 { revert(0, 0) } + } + return returnedValue; + } + + function distributeFeeOnSignaturesCollected(uint256 _fee, address _feeManager) internal { + require(_feeManager.delegatecall(abi.encodeWithSignature("onSignaturesCollected(uint256)", _fee))); + } } From bbbf609089ec6972e7d49dcbe0b1d217518691dd Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 19 Feb 2019 16:25:15 -0300 Subject: [PATCH 096/187] Update tests for native-to-erc --- test/native_to_erc/home_bridge_test.js | 525 ++++++++++++++++++++++++- 1 file changed, 512 insertions(+), 13 deletions(-) diff --git a/test/native_to_erc/home_bridge_test.js b/test/native_to_erc/home_bridge_test.js index 3846e3519..8572af649 100644 --- a/test/native_to_erc/home_bridge_test.js +++ b/test/native_to_erc/home_bridge_test.js @@ -4,6 +4,7 @@ const EternalStorageProxy = artifacts.require("EternalStorageProxy.sol"); const BridgeValidators = artifacts.require("BridgeValidators.sol"); const RevertFallback = artifacts.require("RevertFallback.sol"); const FeeManagerNativeToErc = artifacts.require("FeeManagerNativeToErc.sol"); +const FeeManagerNativeToErcBothDirections = artifacts.require("FeeManagerNativeToErcBothDirections.sol"); const RewardableValidators = artifacts.require("RewardableValidators.sol"); const {ERROR_MSG, ZERO_ADDRESS} = require('../setup'); const {createMessage, sign, signatureToVRS} = require('../helpers/helpers'); @@ -558,7 +559,7 @@ contract('HomeBridge', async (accounts) => { }) describe('#rewardableInitialize', async() => { - let foreignFee, homeBridge, rewardableValidators + let homeFee, foreignFee, homeBridge, rewardableValidators let validators = [accounts[1]] let rewards = [accounts[2]] let requiredSignatures = 1 @@ -566,6 +567,7 @@ contract('HomeBridge', async (accounts) => { rewardableValidators = await RewardableValidators.new() await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled homeBridge = await HomeBridge.new() + homeFee = web3.toBigNumber(web3.toWei(0, "ether")) foreignFee = web3.toBigNumber(web3.toWei(0.002, "ether")) }) it('sets variables', async () => { @@ -576,11 +578,11 @@ contract('HomeBridge', async (accounts) => { '0'.should.be.bignumber.equal(await homeBridge.maxPerTx()) false.should.be.equal(await homeBridge.isInitialized()) - await homeBridge.rewardableInitialize(ZERO_ADDRESS, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, foreignFee).should.be.rejectedWith(ERROR_MSG); - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, 0, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, foreignFee).should.be.rejectedWith(ERROR_MSG); - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, 0, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, foreignFee).should.be.rejectedWith(ERROR_MSG); - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, ZERO_ADDRESS, foreignFee).should.be.rejectedWith(ERROR_MSG); - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, foreignFee).should.be.fulfilled; + await homeBridge.rewardableInitialize(ZERO_ADDRESS, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, 0, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, 0, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, ZERO_ADDRESS, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; true.should.be.equal(await homeBridge.isInitialized()) rewardableValidators.address.should.be.equal(await homeBridge.validatorContract()); @@ -604,7 +606,7 @@ contract('HomeBridge', async (accounts) => { it('can update fee contract', async () => { const feeManager = await FeeManagerNativeToErc.new() - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, foreignFee).should.be.fulfilled; + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; // Given const newFeeManager = await FeeManagerNativeToErc.new() @@ -619,7 +621,7 @@ contract('HomeBridge', async (accounts) => { it('can update fee', async () => { const feeManager = await FeeManagerNativeToErc.new() - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, foreignFee).should.be.fulfilled; + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; // Given const newForeignFee = web3.toBigNumber(web3.toWei(0.2, "ether")) @@ -637,7 +639,7 @@ contract('HomeBridge', async (accounts) => { const oneDirectionsModeHash = '0xf2aed8f7' // When - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, foreignFee).should.be.fulfilled; + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; // Then const feeManagerMode = await homeBridge.getFeeManagerMode() @@ -645,7 +647,91 @@ contract('HomeBridge', async (accounts) => { }) }) - describe('#feeManager_ExecuteAffirmation', async () => { + describe('#feeManager_OneDirection_fallback', () => { + it('should not subtract fee from value', async () => { + // Initialize + const user = accounts[0] + const owner = accounts[9] + const validators = [accounts[1]] + const rewards = [accounts[2]] + const requiredSignatures = 1 + const rewardableValidators = await RewardableValidators.new() + const homeBridge = await HomeBridge.new(); + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + const feeManager = await FeeManagerNativeToErc.new() + + // Given + // 0.1% fee + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const notUsedFee = web3.toBigNumber(web3.toWei(fee, "ether")) + const value = halfEther; + + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, notUsedFee, feeInWei).should.be.fulfilled; + + // When + const { logs } = await homeBridge.sendTransaction({ + from: user, + value: value + }).should.be.fulfilled + + // Then + logs[0].event.should.be.equal('UserRequestForSignature') + logs[0].args.should.be.deep.equal({ + recipient: user, + value: value + }) + }) + }) + + describe('#feeManager_OneDirection_submitSignature', () => { + it('should not distribute fee to validator', async () => { + // Initialize + const user = accounts[0] + const owner = accounts[9] + const validators = [accounts[1]] + const rewards = [accounts[2]] + const requiredSignatures = 1 + const rewardableValidators = await RewardableValidators.new() + const homeBridge = await HomeBridge.new(); + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + const feeManager = await FeeManagerNativeToErc.new() + + // Given + // 0.1% fee + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const notUsedFee = web3.toBigNumber(web3.toWei(fee, "ether")) + const value = halfEther; + + const rewardAddressBalanceBefore = await web3.eth.getBalance(rewards[0]) + + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, notUsedFee, feeInWei).should.be.fulfilled; + + await homeBridge.sendTransaction({ + from: user, + value: value + }).should.be.fulfilled + + // When + const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80" + const message = createMessage(user, value, transactionHash, homeBridge.address) + const signature = await sign(validators[0], message) + const { logs } = await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled + + // Then + logs.length.should.be.equal(2) + logs[1].event.should.be.equal('CollectedSignatures') + + const bridgeBalance = await web3.eth.getBalance(homeBridge.address) + bridgeBalance.should.be.bignumber.equal(value) + + const rewardAddressBalanceAfter = await web3.eth.getBalance(rewards[0]) + rewardAddressBalanceAfter.should.be.bignumber.equal(rewardAddressBalanceBefore) + }) + }) + + describe('#feeManager_OneDirection_ExecuteAffirmation', async () => { it('should distribute fee to validator', async () => { // Initialize const owner = accounts[9] @@ -661,11 +747,12 @@ contract('HomeBridge', async (accounts) => { // 0.1% fee const fee = 0.001 const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const notUsedFee = web3.toBigNumber(web3.toWei(fee, "ether")) const value = halfEther; const finalUserValue = value.mul(web3.toBigNumber(1-fee)); const feeAmount = value.mul(web3.toBigNumber(fee)) - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei).should.be.fulfilled; + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, notUsedFee, feeInWei).should.be.fulfilled; await homeBridge.sendTransaction({ from: accounts[0], value: halfEther @@ -710,6 +797,7 @@ contract('HomeBridge', async (accounts) => { // 0.1% fee const fee = 0.001 const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const notUsedFee = web3.toBigNumber(web3.toWei(fee, "ether")) const feePerValidator = web3.toBigNumber(166666666666666) const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) const finalUserValue = value.mul(web3.toBigNumber(1-fee)); @@ -717,7 +805,7 @@ contract('HomeBridge', async (accounts) => { const homeBridge = await HomeBridge.new() const feeManager = await FeeManagerNativeToErc.new() await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei).should.be.fulfilled; + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, notUsedFee, feeInWei).should.be.fulfilled; await homeBridge.sendTransaction({ from: accounts[0], value: halfEther @@ -781,6 +869,7 @@ contract('HomeBridge', async (accounts) => { // 0.1% fee const fee = 0.001 const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const notUsedFee = web3.toBigNumber(web3.toWei(fee, "ether")) const feeAmount = value.mul(web3.toBigNumber(fee)) const feePerValidator = feeAmount.div(web3.toBigNumber(5)) @@ -788,7 +877,417 @@ contract('HomeBridge', async (accounts) => { const homeBridge = await HomeBridge.new() const feeManager = await FeeManagerNativeToErc.new() await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei).should.be.fulfilled; + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, notUsedFee, feeInWei).should.be.fulfilled; + await homeBridge.sendTransaction({ + from: accounts[0], + value: halfEther + }).should.be.fulfilled + + const recipient = "0xf4bef13f9f4f2b203faf0c3cbbaabe1afe056955"; + const balanceBefore = await web3.eth.getBalance(recipient) + + const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const initialBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const initialBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + const initialBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) + const initialBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) + + + const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + + // When + const { logs: logsValidator1 } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[1]}).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[2]}).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[3]}).should.be.fulfilled + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[4]}).should.be.fulfilled + + // Then + logsValidator1.length.should.be.equals(1) + + logs[0].event.should.be.equal("SignedForAffirmation"); + logs[0].args.should.be.deep.equal({ + signer: validators[4], + transactionHash + }); + logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].args.should.be.deep.equal({ + recipient, + value, + transactionHash + }) + const balanceAfter = await web3.eth.getBalance(recipient) + balanceAfter.should.be.bignumber.equal(balanceBefore.add(value.sub(feeAmount))) + + const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + const updatedBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) + const updatedBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) + + updatedBalanceRewardAddress1.should.be.bignumber.equal(initialBalanceRewardAddress1.add(feePerValidator)) + updatedBalanceRewardAddress2.should.be.bignumber.equal(initialBalanceRewardAddress2.add(feePerValidator)) + updatedBalanceRewardAddress3.should.be.bignumber.equal(initialBalanceRewardAddress3.add(feePerValidator)) + updatedBalanceRewardAddress4.should.be.bignumber.equal(initialBalanceRewardAddress4.add(feePerValidator)) + updatedBalanceRewardAddress5.should.be.bignumber.equal(initialBalanceRewardAddress5.add(feePerValidator)) + }) + }) + + describe('#feeManager_BothDirections_fallback', () => { + it('should subtract fee from value', async () => { + // Initialize + const user = accounts[0] + const owner = accounts[9] + const validators = [accounts[1]] + const rewards = [accounts[2]] + const requiredSignatures = 1 + const rewardableValidators = await RewardableValidators.new() + const homeBridge = await HomeBridge.new(); + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + const feeManager = await FeeManagerNativeToErcBothDirections.new() + + // Given + // 0.1% fee + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const value = halfEther; + + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei, feeInWei).should.be.fulfilled; + + // When + const { logs } = await homeBridge.sendTransaction({ + from: user, + value: value + }).should.be.fulfilled + + // Then + const finalValue = value.mul(web3.toBigNumber(1 - fee)) + logs[0].event.should.be.equal('UserRequestForSignature') + logs[0].args.should.be.deep.equal({ + recipient: user, + value: finalValue + }) + }) + }) + + describe('#feeManager_BothDirections_submitSignature', () => { + it('should distribute fee to validator', async () => { + // Initialize + const user = accounts[0] + const owner = accounts[9] + const validators = [accounts[1]] + const rewards = [accounts[2]] + const requiredSignatures = 1 + const rewardableValidators = await RewardableValidators.new() + const homeBridge = await HomeBridge.new(); + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + const feeManager = await FeeManagerNativeToErcBothDirections.new() + + // Given + // 0.1% fee + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const initialValue = halfEther + const value = initialValue.mul(web3.toBigNumber(1-fee)); + const feeAmount = initialValue.mul(web3.toBigNumber(fee)) + + const rewardAddressBalanceBefore = await web3.eth.getBalance(rewards[0]) + + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei, feeInWei).should.be.fulfilled; + + await homeBridge.sendTransaction({ + from: user, + value: initialValue + }).should.be.fulfilled + + // When + const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80" + const message = createMessage(user, value, transactionHash, homeBridge.address) + const signature = await sign(validators[0], message) + const { logs } = await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled + + // Then + logs.length.should.be.equal(2) + logs[1].event.should.be.equal('CollectedSignatures') + + const bridgeBalance = await web3.eth.getBalance(homeBridge.address) + bridgeBalance.should.be.bignumber.equal(value) + + const rewardAddressBalanceAfter = await web3.eth.getBalance(rewards[0]) + rewardAddressBalanceAfter.should.be.bignumber.equal(rewardAddressBalanceBefore.add(feeAmount)) + }) + it('should distribute fee to 3 validators', async () => { + // Initialize + const user = accounts[0] + const owner = accounts[9] + const validators = [accounts[1], accounts[2], accounts[3]] + const rewards = [accounts[4], accounts[5], accounts[6]] + const requiredSignatures = 3 + const rewardableValidators = await RewardableValidators.new() + const homeBridge = await HomeBridge.new(); + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + const feeManager = await FeeManagerNativeToErcBothDirections.new() + + // Given + // 0.1% fee + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feePerValidator = web3.toBigNumber(166666666666666) + const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) + const initialValue = halfEther + const value = initialValue.mul(web3.toBigNumber(1-fee)); + + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei, feeInWei).should.be.fulfilled; + + await homeBridge.sendTransaction({ + from: user, + value: initialValue + }).should.be.fulfilled + + const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const initialBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const initialBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + + // When + const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80" + const message = createMessage(user, value, transactionHash, homeBridge.address) + const signature = await sign(validators[0], message) + const signature2 = await sign(validators[1], message) + const signature3 = await sign(validators[2], message) + + await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled; + await homeBridge.submitSignature(signature2, message, {from: validators[1]}).should.be.fulfilled; + const { logs } = await homeBridge.submitSignature(signature3, message, {from: validators[2]}).should.be.fulfilled; + + // Then + logs.length.should.be.equal(2) + logs[1].event.should.be.equal('CollectedSignatures') + + const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + + expect( + updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidator)) + || updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidatorPlusDiff))).to.equal(true) + expect( + updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidator)) + || updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidatorPlusDiff))).to.equal(true) + expect( + updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidator)) + || updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidatorPlusDiff))).to.equal(true) + }) + it('should distribute fee to 5 validators', async () => { + // Initialize + const user = accounts[0] + const owner = accounts[9] + const validators = [accounts[0], accounts[1], accounts[2], accounts[3], accounts[4]] + const rewards = [accounts[5], accounts[6], accounts[7], accounts[8], accounts[9]] + const requiredSignatures = 5 + const rewardableValidators = await RewardableValidators.new() + const homeBridge = await HomeBridge.new(); + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + const feeManager = await FeeManagerNativeToErcBothDirections.new() + + // Given + // 0.1% fee + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const initialValue = halfEther + const feeAmount = initialValue.mul(web3.toBigNumber(fee)) + const feePerValidator = feeAmount.div(web3.toBigNumber(5)) + const value = initialValue.mul(web3.toBigNumber(1-fee)); + + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei, feeInWei).should.be.fulfilled; + + await homeBridge.sendTransaction({ + from: user, + value: initialValue + }).should.be.fulfilled + + const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const initialBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const initialBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + const initialBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) + const initialBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) + + // When + const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80" + const message = createMessage(user, value, transactionHash, homeBridge.address) + const signature = await sign(validators[0], message) + const signature2 = await sign(validators[1], message) + const signature3 = await sign(validators[2], message) + const signature4 = await sign(validators[3], message) + const signature5 = await sign(validators[4], message) + + await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled; + await homeBridge.submitSignature(signature2, message, {from: validators[1]}).should.be.fulfilled; + await homeBridge.submitSignature(signature3, message, {from: validators[2]}).should.be.fulfilled; + await homeBridge.submitSignature(signature4, message, {from: validators[3]}).should.be.fulfilled; + const { logs } = await homeBridge.submitSignature(signature5, message, {from: validators[4]}).should.be.fulfilled; + + // Then + logs.length.should.be.equal(2) + logs[1].event.should.be.equal('CollectedSignatures') + + const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + const updatedBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) + const updatedBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) + + updatedBalanceRewardAddress1.should.be.bignumber.equal(initialBalanceRewardAddress1.add(feePerValidator)) + updatedBalanceRewardAddress2.should.be.bignumber.equal(initialBalanceRewardAddress2.add(feePerValidator)) + updatedBalanceRewardAddress3.should.be.bignumber.equal(initialBalanceRewardAddress3.add(feePerValidator)) + updatedBalanceRewardAddress4.should.be.bignumber.equal(initialBalanceRewardAddress4.add(feePerValidator)) + updatedBalanceRewardAddress5.should.be.bignumber.equal(initialBalanceRewardAddress5.add(feePerValidator)) + }) + }) + + describe('#feeManager_BothDirections_ExecuteAffirmation', async () => { + it('should distribute fee to validator', async () => { + // Initialize + const owner = accounts[9] + const validators = [accounts[1]] + const rewards = [accounts[2]] + const requiredSignatures = 1 + const rewardableValidators = await RewardableValidators.new() + const homeBridge = await HomeBridge.new(); + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + const feeManager = await FeeManagerNativeToErcBothDirections.new() + + // Given + // 0.1% fee + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const value = halfEther; + const finalUserValue = value.mul(web3.toBigNumber(1-fee)); + const feeAmount = value.mul(web3.toBigNumber(fee)) + + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei, feeInWei).should.be.fulfilled; + await homeBridge.sendTransaction({ + from: accounts[0], + value: halfEther + }).should.be.fulfilled + + + const recipient = accounts[5]; + const balanceBefore = await web3.eth.getBalance(recipient) + const rewardAddressBalanceBefore = await web3.eth.getBalance(rewards[0]) + const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + + // When + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled + + // Then + logs[0].event.should.be.equal("SignedForAffirmation"); + logs[0].args.should.be.deep.equal({ + signer: validators[0], + transactionHash + }); + logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].args.should.be.deep.equal({ + recipient, + value, + transactionHash + }) + const balanceAfter = await web3.eth.getBalance(recipient) + const rewardAddressBalanceAfter = await web3.eth.getBalance(rewards[0]) + + rewardAddressBalanceAfter.should.be.bignumber.equal(rewardAddressBalanceBefore.add(feeAmount)) + balanceAfter.should.be.bignumber.equal(balanceBefore.add(finalUserValue)) + }) + it('should distribute fee to 3 validators', async () => { + // Given + const owner = accounts[9] + const validators = [accounts[1], accounts[2], accounts[3]] + const rewards = [accounts[4], accounts[5], accounts[6]] + const requiredSignatures = 2 + const rewardableValidators = await RewardableValidators.new() + + const value = halfEther; + // 0.1% fee + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feePerValidator = web3.toBigNumber(166666666666666) + const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) + const finalUserValue = value.mul(web3.toBigNumber(1-fee)); + + const homeBridge = await HomeBridge.new() + const feeManager = await FeeManagerNativeToErcBothDirections.new() + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei, feeInWei).should.be.fulfilled; + await homeBridge.sendTransaction({ + from: accounts[0], + value: halfEther + }).should.be.fulfilled + + const recipient = accounts[8]; + const balanceBefore = await web3.eth.getBalance(recipient) + + const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const initialBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const initialBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + + const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + + // When + const { logs: logsValidator1 } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[1]}).should.be.fulfilled + + // Then + logsValidator1.length.should.be.equals(1) + + logs[0].event.should.be.equal("SignedForAffirmation"); + logs[0].args.should.be.deep.equal({ + signer: validators[1], + transactionHash + }); + logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].args.should.be.deep.equal({ + recipient, + value, + transactionHash + }) + const balanceAfter = await web3.eth.getBalance(recipient) + balanceAfter.should.be.bignumber.equal(balanceBefore.add(finalUserValue)) + + const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + + expect( + updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidator)) + || updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidatorPlusDiff))).to.equal(true) + expect( + updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidator)) + || updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidatorPlusDiff))).to.equal(true) + expect( + updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidator)) + || updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidatorPlusDiff))).to.equal(true) + + const homeBridgeBalance = await web3.eth.getBalance(homeBridge.address) + homeBridgeBalance.should.be.bignumber.equal('0') + }) + it('should distribute fee to 5 validators', async () => { + // Given + const owner = accounts[0] + const validators = [accounts[0], accounts[1], accounts[2], accounts[3], accounts[4]] + const rewards = [accounts[5], accounts[6], accounts[7], accounts[8], accounts[9]] + const requiredSignatures = 5 + + const value = halfEther; + // 0.1% fee + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeAmount = value.mul(web3.toBigNumber(fee)) + const feePerValidator = feeAmount.div(web3.toBigNumber(5)) + + const rewardableValidators = await RewardableValidators.new() + const homeBridge = await HomeBridge.new() + const feeManager = await FeeManagerNativeToErcBothDirections.new() + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei, feeInWei).should.be.fulfilled; await homeBridge.sendTransaction({ from: accounts[0], value: halfEther From f1b8a3061f5e9331f657053f296357c6effd004a Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 20 Feb 2019 14:13:51 -0300 Subject: [PATCH 097/187] Refactor rewardable env variables --- deploy/.env.example | 5 ++--- deploy/README.md | 24 ++++++++++++++---------- 2 files changed, 16 insertions(+), 13 deletions(-) diff --git a/deploy/.env.example b/deploy/.env.example index 62d114a8b..c37d71568 100644 --- a/deploy/.env.example +++ b/deploy/.env.example @@ -39,10 +39,9 @@ REQUIRED_NUMBER_OF_VALIDATORS=1 #If several validators are used, list them separated by space without quotes #E.g. VALIDATORS=0x 0x 0x VALIDATORS=0x -#for erc_to_native mode -#Set to true if fee will be charged on home side +#Set to ONE_DIRECTION or BOTH_DIRECTIONS if fee will be charged on home side, set to false otherwise HOME_REWARDABLE=false -#Set to true if fee will be charged on foreign side +#Set to ONE_DIRECTION or BOTH_DIRECTIONS if fee will be charged on foreign side, set to false otherwise FOREIGN_REWARDABLE=false #If HOME_REWARDABLE or FOREIGN_REWARDABLE set to true, list validators accounts were rewards should be transferred separated by space without quotes #E.g. VALIDATORS_REWARD_ACCOUNTS=0x 0x 0x diff --git a/deploy/README.md b/deploy/README.md index e959e0a3f..413e147de 100644 --- a/deploy/README.md +++ b/deploy/README.md @@ -124,20 +124,22 @@ REQUIRED_NUMBER_OF_VALIDATORS=1 # correctly to the Foreign network. VALIDATORS=0x 0x 0x -# The flag defining whether to use RewardableValidators contract and set a fee manager contract on Home network +# Variable to define whether to use RewardableValidators contract and set a fee manager contract on Home network +# On this bridge mode ONE_DIRECTION and BOTH_DIRECTIONS are supported on Home network HOME_REWARDABLE=false -# The flag defining whether to use RewardableValidators contract and set a fee manager contract on Foreign network +# Variable to define whether to use RewardableValidators contract and set a fee manager contract on Foreign network +# On this bridge mode ONE_DIRECTION is supported on Foreign network FOREIGN_REWARDABLE=false # List validators accounts were rewards should be transferred separated by space without quotes -# Makes sense only when HOME_REWARDABLE=true or FOREIGN_REWARDABLE=true +# Makes sense only when HOME_REWARDABLE!=false or FOREIGN_REWARDABLE!=false VALIDATORS_REWARD_ACCOUNTS=0x 0x 0x # Fee to be taken for every transaction directed from the Home network to the Foreign network -# Makes sense only when FOREIGN_REWARDABLE=true +# Makes sense only when FOREIGN_REWARDABLE=ONE_DIRECTION or HOME_REWARDABLE=BOTH_DIRECTIONS # e.g. 0.1% fee HOME_TRANSACTIONS_FEE=0.001 # Fee to be taken for every transaction directed from the Foreign network to the Home network -# Makes sense only when HOME_REWARDABLE=true +# Makes sense only when HOME_REWARDABLE!=false # e.g. 0.1% fee FOREIGN_TRANSACTIONS_FEE=0.001 @@ -347,20 +349,22 @@ REQUIRED_NUMBER_OF_VALIDATORS=1 VALIDATORS=0x 0x 0x -# The flag defining whether to use RewardableValidators contract and set a fee manager contract on Home network +# Variable to define whether to use RewardableValidators contract and set a fee manager contract on Home network +# On this bridge mode only BOTH_DIRECTIONS is supported on Home network HOME_REWARDABLE=false -# The flag defining whether to use RewardableValidators contract and set a fee manager contract on Foreign network +# Variable to define whether to use RewardableValidators contract and set a fee manager contract on Foreign network +# Collecting fees on Foreign network is not supported on this bridge mode. FOREIGN_REWARDABLE=false # List validators accounts were rewards should be transferred separated by space without quotes -# Makes sense only when HOME_REWARDABLE=true or FOREIGN_REWARDABLE=true +# Makes sense only when HOME_REWARDABLE=BOTH_DIRECTIONS VALIDATORS_REWARD_ACCOUNTS=0x 0x 0x # Fee to be taken for every transaction directed from the Home network to the Foreign network -# Makes sense only when HOME_REWARDABLE=true +# Makes sense only when HOME_REWARDABLE=BOTH_DIRECTIONS # e.g. 0.1% fee HOME_TRANSACTIONS_FEE=0.001 # Fee to be taken for every transaction directed from the Foreign network to the Home network -# Makes sense only when HOME_REWARDABLE=true +# Makes sense only when HOME_REWARDABLE=BOTH_DIRECTIONS # e.g. 0.1% fee FOREIGN_TRANSACTIONS_FEE=0.001 ``` From 94f5d39c3c9d8cf140a0bc92c1df7454ef3ff6c0 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 20 Feb 2019 14:14:45 -0300 Subject: [PATCH 098/187] Update deploy script --- deploy/src/erc_to_native/home.js | 2 +- deploy/src/loadEnv.js | 35 +++++++++++++++++++++++++++-- deploy/src/native_to_erc/foreign.js | 2 +- deploy/src/native_to_erc/home.js | 9 ++++++-- 4 files changed, 42 insertions(+), 6 deletions(-) diff --git a/deploy/src/erc_to_native/home.js b/deploy/src/erc_to_native/home.js index 6a29343a8..4b0fbe8ee 100644 --- a/deploy/src/erc_to_native/home.js +++ b/deploy/src/erc_to_native/home.js @@ -40,7 +40,7 @@ const { const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVATE_KEY) -const isRewardableBridge = HOME_REWARDABLE === 'true' +const isRewardableBridge = HOME_REWARDABLE === 'BOTH_DIRECTIONS' async function deployHome() { let homeNonce = await web3Home.eth.getTransactionCount(DEPLOYMENT_ACCOUNT_ADDRESS) diff --git a/deploy/src/loadEnv.js b/deploy/src/loadEnv.js index d95b86f74..08f859341 100644 --- a/deploy/src/loadEnv.js +++ b/deploy/src/loadEnv.js @@ -8,6 +8,7 @@ const { ZERO_ADDRESS } = require('./constants') // Validations and constants const validBridgeModes = ['NATIVE_TO_ERC', 'ERC_TO_ERC', 'ERC_TO_NATIVE'] +const validRewardModes = ['false', 'ONE_DIRECTION', 'BOTH_DIRECTIONS'] const bigNumValidator = envalid.makeValidator(x => toBN(x)) const validateAddress = address => { if (isAddress(address)) { @@ -44,6 +45,18 @@ if (!validBridgeModes.includes(BRIDGE_MODE)) { throw new Error(`Invalid bridge mode: ${BRIDGE_MODE}`) } +if (!validRewardModes.includes(HOME_REWARDABLE)) { + throw new Error( + `Invalid HOME_REWARDABLE: ${HOME_REWARDABLE}. Supported values are ${validRewardModes}` + ) +} + +if (!validRewardModes.includes(FOREIGN_REWARDABLE)) { + throw new Error( + `Invalid FOREIGN_REWARDABLE: ${FOREIGN_REWARDABLE}. Supported values are ${validRewardModes}` + ) +} + let validations = { DEPLOYMENT_ACCOUNT_PRIVATE_KEY: envalid.str(), DEPLOYMENT_GAS_LIMIT: bigNumValidator(), @@ -88,6 +101,18 @@ if (BRIDGE_MODE === 'NATIVE_TO_ERC') { DPOS_VALIDATOR_SET_ADDRESS: addressValidator() } } + + if (FOREIGN_REWARDABLE === 'BOTH_DIRECTIONS') { + throw new Error( + `FOREIGN_REWARDABLE: ${FOREIGN_REWARDABLE} is not supported on ${BRIDGE_MODE} bridge mode` + ) + } + + if (HOME_REWARDABLE === 'BOTH_DIRECTIONS' && FOREIGN_REWARDABLE === 'ONE_DIRECTION') { + throw new Error( + `Combination of HOME_REWARDABLE: ${HOME_REWARDABLE} and FOREIGN_REWARDABLE: ${FOREIGN_REWARDABLE} should be avoided on ${BRIDGE_MODE} bridge mode.` + ) + } } if (BRIDGE_MODE === 'ERC_TO_ERC') { validations = { @@ -107,14 +132,20 @@ if (BRIDGE_MODE === 'ERC_TO_NATIVE') { }) } - if (FOREIGN_REWARDABLE === 'true') { + if (HOME_REWARDABLE === 'ONE_DIRECTION') { + throw new Error( + `Only BOTH_DIRECTIONS is supported for collecting fees on Home Network on ${BRIDGE_MODE} bridge mode.` + ) + } + + if (FOREIGN_REWARDABLE !== 'false') { throw new Error( `Collecting fees on Foreign Network on ${BRIDGE_MODE} bridge mode is not supported.` ) } } -if (HOME_REWARDABLE === 'true' || FOREIGN_REWARDABLE === 'true') { +if (HOME_REWARDABLE !== 'false' || FOREIGN_REWARDABLE !== 'false') { validateRewardableAddresses(VALIDATORS, VALIDATORS_REWARD_ACCOUNTS) validations = { ...validations, diff --git a/deploy/src/native_to_erc/foreign.js b/deploy/src/native_to_erc/foreign.js index a85ed8289..8cfc3e567 100644 --- a/deploy/src/native_to_erc/foreign.js +++ b/deploy/src/native_to_erc/foreign.js @@ -46,7 +46,7 @@ const { const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVATE_KEY) -const isRewardableBridge = FOREIGN_REWARDABLE === 'true' +const isRewardableBridge = FOREIGN_REWARDABLE === 'ONE_DIRECTION' async function deployForeign() { let foreignNonce = await web3Foreign.eth.getTransactionCount(DEPLOYMENT_ACCOUNT_ADDRESS) diff --git a/deploy/src/native_to_erc/home.js b/deploy/src/native_to_erc/home.js index 0a12024be..3d88d3398 100644 --- a/deploy/src/native_to_erc/home.js +++ b/deploy/src/native_to_erc/home.js @@ -14,6 +14,7 @@ const EternalStorageProxy = require('../../../build/contracts/EternalStorageProx const BridgeValidators = require('../../../build/contracts/BridgeValidators.json') const RewardableValidators = require('../../../build/contracts/RewardableValidators.json') const FeeManagerNativeToErc = require('../../../build/contracts/FeeManagerNativeToErc.json') +const FeeManagerNativeToErcBothDirections = require('../../../build/contracts/FeeManagerNativeToErcBothDirections.json') const HomeBridge = require('../../../build/contracts/HomeBridgeNativeToErc.json') const VALIDATORS = env.VALIDATORS.split(' ') @@ -38,7 +39,8 @@ const { const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVATE_KEY) -const isRewardableBridge = HOME_REWARDABLE === 'true' +const isBothDirectionsFeeManager = HOME_REWARDABLE === 'BOTH_DIRECTIONS' +const isRewardableBridge = HOME_REWARDABLE === 'ONE_DIRECTION' || isBothDirectionsFeeManager async function deployHome() { let homeNonce = await web3Home.eth.getTransactionCount(DEPLOYMENT_ACCOUNT_ADDRESS) @@ -159,7 +161,10 @@ async function deployHome() { if (isRewardableBridge) { console.log('\ndeploying implementation for fee manager') - const feeManager = await deployContract(FeeManagerNativeToErc, [], { + const feeManagerContract = isBothDirectionsFeeManager + ? FeeManagerNativeToErcBothDirections + : FeeManagerNativeToErc + const feeManager = await deployContract(feeManagerContract, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, nonce: homeNonce }) From 289e09f2569ea112102e3873376b413f4e798849 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 20 Feb 2019 15:36:02 -0300 Subject: [PATCH 099/187] Fix native-to-erc deploy script --- deploy/src/native_to_erc/home.js | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/deploy/src/native_to_erc/home.js b/deploy/src/native_to_erc/home.js index 3d88d3398..e09579b4a 100644 --- a/deploy/src/native_to_erc/home.js +++ b/deploy/src/native_to_erc/home.js @@ -34,6 +34,7 @@ const { FOREIGN_DAILY_LIMIT, FOREIGN_MAX_AMOUNT_PER_TX, HOME_REWARDABLE, + HOME_TRANSACTIONS_FEE, FOREIGN_TRANSACTIONS_FEE } = env @@ -171,6 +172,7 @@ async function deployHome() { console.log('[Home] feeManager Implementation: ', feeManager.options.address) homeNonce++ + const homeFeeInWei = Web3Utils.toWei(HOME_TRANSACTIONS_FEE.toString(), 'ether') const foreignFeeInWei = Web3Utils.toWei(FOREIGN_TRANSACTIONS_FEE.toString(), 'ether') console.log('\ninitializing Home Bridge with fee contract:\n') @@ -191,6 +193,7 @@ async function deployHome() { )} in eth, HOME_BRIDGE_OWNER: ${HOME_BRIDGE_OWNER}, Fee Manager: ${feeManager.options.address}, + Home Fee: ${homeFeeInWei} which is ${HOME_TRANSACTIONS_FEE * 100}% Foreign Fee: ${foreignFeeInWei} which is ${FOREIGN_TRANSACTIONS_FEE * 100}%`) homeBridgeImplementation.options.address = homeBridgeStorage.options.address @@ -206,6 +209,7 @@ async function deployHome() { FOREIGN_MAX_AMOUNT_PER_TX, HOME_BRIDGE_OWNER, feeManager.options.address, + homeFeeInWei, foreignFeeInWei ) .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) From 3997423b084d50f59dd29ee0e2f0ba9ee199f0d5 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 20 Feb 2019 16:24:56 -0300 Subject: [PATCH 100/187] Update Reward Management doc --- REWARD_MANAGEMENT.md | 26 ++++++++++++++++++++++++-- 1 file changed, 24 insertions(+), 2 deletions(-) diff --git a/REWARD_MANAGEMENT.md b/REWARD_MANAGEMENT.md index 270655cf1..83c010378 100644 --- a/REWARD_MANAGEMENT.md +++ b/REWARD_MANAGEMENT.md @@ -1,7 +1,11 @@ # Reward Management ## NATIVE-TO-ERC - +Configuration: +``` +HOME_REWARDABLE=ONE_DIRECTION +FOREIGN_REWARDABLE=ONE_DIRECTION +``` ### Home to Foreign transfer Fees are calculated and distributed on Foreign network. Validators will receive ERC20 tokens. ![native-erc-hometoforeign](https://user-images.githubusercontent.com/4614574/51607402-4bda6180-1ef3-11e9-91e3-50fe5d35d296.png) @@ -10,8 +14,26 @@ Fees are calculated and distributed on Foreign network. Validators will receive Fees are calculated and distributed on Home network. Validators will receive native coins. ![native-erc-foreigntohome](https://user-images.githubusercontent.com/4614574/51607428-5d236e00-1ef3-11e9-8083-3669899c7252.png) -## ERC-TO-NATIVE +## NATIVE-TO-ERC - Fees collected on Home network only +Configuration: +``` +HOME_REWARDABLE=BOTH_DIRECTIONS +FOREIGN_REWARDABLE=false +``` +### Home to Foreign transfer +Fees are calculated and distributed on Home network. Validators will receive native coins. +![native-erc-homefee-hometoforeign](https://user-images.githubusercontent.com/4614574/53118155-43456d00-352b-11e9-80db-53e31494e09b.png) +### Foreign to Home transfer +Fees are calculated and distributed on Home network. Validators will receive native coins. +![native-erc-homefee-foreigntohome](https://user-images.githubusercontent.com/4614574/53118176-4b9da800-352b-11e9-8118-123f30e37d61.png) + +## ERC-TO-NATIVE +Configuration: +``` +HOME_REWARDABLE=BOTH_DIRECTIONS +FOREIGN_REWARDABLE=false +``` ### Foreign to Home transfer Fees are calculated and distributed on Home network. Validators will receive native coins. ![erc-native-foreigntohome](https://user-images.githubusercontent.com/4614574/51607498-9065fd00-1ef3-11e9-8212-fc1ba16ae91a.png) From 84dc9ac4d489f92a8116dbcdaf65f1db37ce74ea Mon Sep 17 00:00:00 2001 From: Lior Rabin Date: Thu, 21 Feb 2019 19:32:34 +0200 Subject: [PATCH 101/187] unit tests & gas consumption (#1) * unit tests - factories * unit tests - mapper * added bridge factories and mapper to gas consumption doc * typo * rename event to fix "[ethjs-abi] while decoding address data, invalid address data" in tests --- GAS_CONSUMPTION.md | 63 +++++++ .../upgradeable_contracts/EternalOwnable.sol | 4 +- .../factories/ForeignBridgeFactory.sol | 4 +- .../factories/HomeBridgeFactory.sol | 6 +- test/factories/foreign_factory.test.js | 138 +++++++++++++++ test/factories/home_factory.test.js | 149 ++++++++++++++++ test/helpers/helpers.js | 5 + test/mapper/home_mapper.test.js | 160 ++++++++++++++++++ 8 files changed, 522 insertions(+), 7 deletions(-) create mode 100644 test/factories/foreign_factory.test.js create mode 100644 test/factories/home_factory.test.js create mode 100644 test/mapper/home_mapper.test.js diff --git a/GAS_CONSUMPTION.md b/GAS_CONSUMPTION.md index 88cc9ae49..ab0214adf 100644 --- a/GAS_CONSUMPTION.md +++ b/GAS_CONSUMPTION.md @@ -172,3 +172,66 @@ To request transfer from the Home to the Foreign| HomeBridgeErcToNative|fallback|80174|80174|80174 To request transfer from the Foreign to the Home| ERC677BridgeToken|transfer|37691|86589|55000 + +### Bridge Factories + +#### Deployment +##### Home + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +BridgeValidators|deployment|1144207|1144207|1144207 +EternalStorageProxy|deployment|378510|378510|378510 +EternalStorageProxy|upgradeTo|35871|30924|30913 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +HomeBridgeErcToErc|initialize|212299|213195|213003 +EternalStorageProxy|deployment|378510|378510|378510 +HomeBridgeFactory|deployment|||4337543 +EternalStorageProxy|upgradeTo|35871|30924|30913 +HomeBridgeFactory|initialize|||433239 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +Total| |||7008144 + +##### Foreign + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +BridgeValidators|deployment|1144207|1144207|1144207 +ForeignBridgeErcToErc|deployment|2449436|2449436|2449436 +EternalStorageProxy|deployment|378510|378510|378510 +ForeignBridgeFactory|deployment|||2515108 +EternalStorageProxy|upgradeTo|35871|30924|30913 +ForeignBridgeFactory|initialize|||390192 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +Total| |||6939019 + +#### Usage +##### Users + + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +To deploy Home bridge| +HomeBridgeFactory|deployHomeBridge|2238032|2238672|2238213 +To deploy Foreign bridge| +ForeignBridgeFactory|deployForeignBridge|1056602|1056666|1056655 + +### Mapper + +#### Deployment +##### Home + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +EternalStorageProxy|deployment|378510|378510|378510 +BridgeMapper|deployment|||1107983 +EternalStorageProxy|upgradeTo|35871|30924|30913 +BridgeMapper|initialize|||68122 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +Total| |||1616181 + +#### Usage +##### Users + + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +To add bridge mapping| +BridgeMapper|addBridgeMapping|||136441 +To remove bridge mapping| +BridgeMapper|removeBridgeMapping|||28283 \ No newline at end of file diff --git a/contracts/upgradeable_contracts/EternalOwnable.sol b/contracts/upgradeable_contracts/EternalOwnable.sol index 4a8ddca56..f99a23b3c 100644 --- a/contracts/upgradeable_contracts/EternalOwnable.sol +++ b/contracts/upgradeable_contracts/EternalOwnable.sol @@ -13,7 +13,7 @@ contract EternalOwnable is EternalStorage { * @param previousOwner representing the address of the previous owner * @param newOwner representing the address of the new owner */ - event OwnershipTransferred(address previousOwner, address newOwner); + event EternalOwnershipTransferred(address previousOwner, address newOwner); /** * @dev Throws if called by any account other than the owner. @@ -44,7 +44,7 @@ contract EternalOwnable is EternalStorage { * @dev Sets a new owner address */ function setOwner(address newOwner) internal { - emit OwnershipTransferred(owner(), newOwner); + emit EternalOwnershipTransferred(owner(), newOwner); addressStorage[keccak256(abi.encodePacked("owner"))] = newOwner; } } diff --git a/contracts/upgradeable_contracts/factories/ForeignBridgeFactory.sol b/contracts/upgradeable_contracts/factories/ForeignBridgeFactory.sol index b2f754659..6ba45b053 100644 --- a/contracts/upgradeable_contracts/factories/ForeignBridgeFactory.sol +++ b/contracts/upgradeable_contracts/factories/ForeignBridgeFactory.sol @@ -65,7 +65,7 @@ contract ForeignBridgeFactory is BasicBridgeFactory { IBridgeValidators bridgeValidators = IBridgeValidators(proxy); // initialize bridgeValidators bridgeValidators.initialize(requiredSignatures(), initialValidators(), bridgeValidatorsOwner()); - // transger proxy upgradeability admin + // transfer proxy upgradeability admin proxy.transferProxyOwnership(bridgeValidatorsProxyOwner()); // deploy new EternalStorageProxy proxy = new EternalStorageProxy(); @@ -75,7 +75,7 @@ contract ForeignBridgeFactory is BasicBridgeFactory { IForeignBridge foreignBridge = IForeignBridge(proxy); // initialize foreignBridge foreignBridge.initialize(bridgeValidators, _erc20Token, requiredBlockConfirmations(), gasPrice(), foreignMaxPerTx(), homeDailyLimit(), homeMaxPerTx(), foreignBridgeOwner()); - // transger proxy upgradeability admin + // transfer proxy upgradeability admin proxy.transferProxyOwnership(foreignBridgeProxyOwner()); // emit event emit ForeignBridgeDeployed(foreignBridge, bridgeValidators, block.number); diff --git a/contracts/upgradeable_contracts/factories/HomeBridgeFactory.sol b/contracts/upgradeable_contracts/factories/HomeBridgeFactory.sol index efdeee6ed..5db043e27 100644 --- a/contracts/upgradeable_contracts/factories/HomeBridgeFactory.sol +++ b/contracts/upgradeable_contracts/factories/HomeBridgeFactory.sol @@ -70,7 +70,7 @@ contract HomeBridgeFactory is BasicBridgeFactory { IBridgeValidators bridgeValidators = IBridgeValidators(proxy); // initialize bridgeValidators bridgeValidators.initialize(requiredSignatures(), initialValidators(), bridgeValidatorsOwner()); - // transger proxy upgradeability admin + // transfer proxy upgradeability admin proxy.transferProxyOwnership(bridgeValidatorsProxyOwner()); // deploy new EternalStorageProxy proxy = new EternalStorageProxy(); @@ -80,13 +80,13 @@ contract HomeBridgeFactory is BasicBridgeFactory { ERC677BridgeToken token = new ERC677BridgeToken(_tokenName, _tokenSymbol, _tokenDecimals); // set token bridge contract token.setBridgeContract(proxy); - // transger token ownership to the bridge + // transfer token ownership to the bridge token.transferOwnership(proxy); // cast proxy as IHomeBridge IHomeBridge homeBridge = IHomeBridge(proxy); // initialize homeBridge homeBridge.initialize(bridgeValidators, homeDailyLimit(), homeMaxPerTx(), minPerTx(), gasPrice(), requiredBlockConfirmations(), token, foreignDailyLimit(), foreignMaxPerTx(), homeBridgeOwner()); - // transger proxy upgradeability admin + // transfer proxy upgradeability admin proxy.transferProxyOwnership(homeBridgeProxyOwner()); // emit event emit HomeBridgeDeployed(homeBridge, bridgeValidators, token, block.number); diff --git a/test/factories/foreign_factory.test.js b/test/factories/foreign_factory.test.js new file mode 100644 index 000000000..04e080448 --- /dev/null +++ b/test/factories/foreign_factory.test.js @@ -0,0 +1,138 @@ +const ForeignBridgeFactory = artifacts.require("ForeignBridgeFactory.sol") +const ForeignBridge = artifacts.require("ForeignBridgeErcToErc.sol") +const BridgeValidators = artifacts.require("BridgeValidators.sol") +const ERC677BridgeToken = artifacts.require("ERC677BridgeToken.sol") + +const {ERROR_MSG, ZERO_ADDRESS, INVALID_ARGUMENTS} = require('../setup') +const {getEventFromLogs} = require('../helpers/helpers') +const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")) +const requiredSignatures = 1 +const requiredBlockConfirmations = 8 +const gasPrice = web3.toWei('1', 'gwei') +const oneEther = web3.toBigNumber(web3.toWei(1, "ether")) +const homeDailyLimit = oneEther +const homeMaxPerTx = halfEther +const maxPerTx = halfEther + +contract('ForeignBridgeFactory', async (accounts) => { + let validatorContract, foreignBridgeContract, owner + before(async () => { + validatorContract = await BridgeValidators.new() + foreignBridgeContract = await ForeignBridge.new() + owner = accounts[0] + }) + + describe('#initialize', async () => { + it('should initialize', async () => { + let foreignBridgeFactory = await ForeignBridgeFactory.new() + + false.should.be.equal(await foreignBridgeFactory.isInitialized()) + ZERO_ADDRESS.should.be.equal(await foreignBridgeFactory.bridgeValidatorsImplementation()) + '0'.should.be.bignumber.equal(await foreignBridgeFactory.requiredSignatures()) + ZERO_ADDRESS.should.be.equal(await foreignBridgeFactory.bridgeValidatorsOwner()) + ZERO_ADDRESS.should.be.equal(await foreignBridgeFactory.bridgeValidatorsProxyOwner()) + ZERO_ADDRESS.should.be.equal(await foreignBridgeFactory.foreignBridgeErcToErcImplementation()) + '0'.should.be.bignumber.equal(await foreignBridgeFactory.requiredBlockConfirmations()) + '0'.should.be.bignumber.equal(await foreignBridgeFactory.gasPrice()) + '0'.should.be.bignumber.equal(await foreignBridgeFactory.foreignMaxPerTx()) + '0'.should.be.bignumber.equal(await foreignBridgeFactory.homeDailyLimit()) + '0'.should.be.bignumber.equal(await foreignBridgeFactory.homeMaxPerTx()) + ZERO_ADDRESS.should.be.equal(await foreignBridgeFactory.foreignBridgeOwner()) + ZERO_ADDRESS.should.be.equal(await foreignBridgeFactory.foreignBridgeProxyOwner()) + + await foreignBridgeFactory.initialize().should.be.rejectedWith(INVALID_ARGUMENTS) + await foreignBridgeFactory.initialize(ZERO_ADDRESS, validatorContract.address, requiredSignatures, [owner], owner, foreignBridgeContract.address, requiredBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) + await foreignBridgeFactory.initialize(owner, ZERO_ADDRESS, requiredSignatures, [owner], owner, foreignBridgeContract.address, requiredBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) + await foreignBridgeFactory.initialize(owner, validatorContract.address, 0, [owner], owner, foreignBridgeContract.address, requiredBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) + await foreignBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [], owner, foreignBridgeContract.address, requiredBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) + await foreignBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], ZERO_ADDRESS, foreignBridgeContract.address, requiredBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) + await foreignBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, ZERO_ADDRESS, requiredBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) + await foreignBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, foreignBridgeContract.address, 0, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) + await foreignBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, foreignBridgeContract.address, requiredBlockConfirmations, 0, maxPerTx, homeDailyLimit, homeMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) + await foreignBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, foreignBridgeContract.address, requiredBlockConfirmations, gasPrice, maxPerTx, 0, homeMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) + await foreignBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, foreignBridgeContract.address, requiredBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeDailyLimit, owner, owner).should.be.rejectedWith(ERROR_MSG) + await foreignBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, foreignBridgeContract.address, requiredBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, ZERO_ADDRESS, owner).should.be.rejectedWith(ERROR_MSG) + await foreignBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, foreignBridgeContract.address, requiredBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner, ZERO_ADDRESS).should.be.rejectedWith(ERROR_MSG) + + await foreignBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, foreignBridgeContract.address, requiredBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner, owner) + + true.should.be.equal(await foreignBridgeFactory.isInitialized()) + validatorContract.address.should.be.equal(await foreignBridgeFactory.bridgeValidatorsImplementation()) + requiredSignatures.should.be.bignumber.equal(await foreignBridgeFactory.requiredSignatures()) + owner.should.be.equal(await foreignBridgeFactory.bridgeValidatorsOwner()) + owner.should.be.equal(await foreignBridgeFactory.bridgeValidatorsProxyOwner()) + foreignBridgeContract.address.should.be.equal(await foreignBridgeFactory.foreignBridgeErcToErcImplementation()) + requiredBlockConfirmations.should.be.bignumber.equal(await foreignBridgeFactory.requiredBlockConfirmations()) + gasPrice.should.be.bignumber.equal(await foreignBridgeFactory.gasPrice()) + maxPerTx.should.be.bignumber.equal(await foreignBridgeFactory.foreignMaxPerTx()) + homeDailyLimit.should.be.bignumber.equal(await foreignBridgeFactory.homeDailyLimit()) + homeMaxPerTx.should.be.bignumber.equal(await foreignBridgeFactory.homeMaxPerTx()) + owner.should.be.equal(await foreignBridgeFactory.foreignBridgeOwner()) + owner.should.be.equal(await foreignBridgeFactory.foreignBridgeProxyOwner()) + const [major, minor, patch] = await foreignBridgeFactory.getBridgeFactoryVersion() + major.should.be.bignumber.gte(0) + minor.should.be.bignumber.gte(0) + patch.should.be.bignumber.gte(0) + }) + }) + + describe('#deployForeignBridge', async () => { + let foreignBridgeFactory + before(async () => { + foreignBridgeFactory = await ForeignBridgeFactory.new() + await foreignBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, foreignBridgeContract.address, requiredBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner, owner) + }) + + it('should deploy a foreign bridge', async () => { + let token = await ERC677BridgeToken.new("Some ERC20", "SMT_1", 18) + + const {logs} = await foreignBridgeFactory.deployForeignBridge(token.address) + const {args} = getEventFromLogs(logs, 'ForeignBridgeDeployed') + + ZERO_ADDRESS.should.not.be.equal(args._foreignBridge) + ZERO_ADDRESS.should.not.be.equal(args._foreignValidators) + args._blockNumber.should.be.bignumber.gte(0) + + let foreignBridge = await ForeignBridge.at(args._foreignBridge) + true.should.be.equal(await foreignBridge.isInitialized()) + args._foreignValidators.should.be.equal(await foreignBridge.validatorContract()) + token.address.should.be.equal(await foreignBridge.erc20token()) + const deployedAtBlock = await foreignBridge.deployedAtBlock() + deployedAtBlock.should.be.bignumber.above(0) + requiredBlockConfirmations.should.be.bignumber.equal(await foreignBridge.requiredBlockConfirmations()) + gasPrice.should.be.bignumber.equal(await foreignBridge.gasPrice()) + const bridgeMode = '0xba4690f5' // 4 bytes of keccak256('erc-to-erc-core') + bridgeMode.should.be.equal(await foreignBridge.getBridgeMode()) + const [major, minor, patch] = await foreignBridge.getBridgeInterfacesVersion() + major.should.be.bignumber.gte(0) + minor.should.be.bignumber.gte(0) + patch.should.be.bignumber.gte(0) + }) + + it('should deploy a second foreign bridge using same factory', async () => { + let token = await ERC677BridgeToken.new("Another ERC20", "SMT_2", 18) + + const {logs} = await foreignBridgeFactory.deployForeignBridge(token.address) + const {args} = getEventFromLogs(logs, 'ForeignBridgeDeployed') + + ZERO_ADDRESS.should.not.be.equal(args._foreignBridge) + ZERO_ADDRESS.should.not.be.equal(args._foreignValidators) + args._blockNumber.should.be.bignumber.gte(0) + + let foreignBridge = await ForeignBridge.at(args._foreignBridge) + true.should.be.equal(await foreignBridge.isInitialized()) + args._foreignValidators.should.be.equal(await foreignBridge.validatorContract()) + token.address.should.be.equal(await foreignBridge.erc20token()) + const deployedAtBlock = await foreignBridge.deployedAtBlock() + deployedAtBlock.should.be.bignumber.above(0) + requiredBlockConfirmations.should.be.bignumber.equal(await foreignBridge.requiredBlockConfirmations()) + gasPrice.should.be.bignumber.equal(await foreignBridge.gasPrice()) + const bridgeMode = '0xba4690f5' // 4 bytes of keccak256('erc-to-erc-core') + bridgeMode.should.be.equal(await foreignBridge.getBridgeMode()) + const [major, minor, patch] = await foreignBridge.getBridgeInterfacesVersion() + major.should.be.bignumber.gte(0) + minor.should.be.bignumber.gte(0) + patch.should.be.bignumber.gte(0) + }) + }) +}) diff --git a/test/factories/home_factory.test.js b/test/factories/home_factory.test.js new file mode 100644 index 000000000..2bcbfaf7d --- /dev/null +++ b/test/factories/home_factory.test.js @@ -0,0 +1,149 @@ +const HomeBridgeFactory = artifacts.require("HomeBridgeFactory.sol") +const HomeBridge = artifacts.require("HomeBridgeErcToErc.sol") +const BridgeValidators = artifacts.require("BridgeValidators.sol") + +const {ERROR_MSG, ZERO_ADDRESS, INVALID_ARGUMENTS} = require('../setup') +const {getEventFromLogs} = require('../helpers/helpers') +const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")) +const quarterEther = web3.toBigNumber(web3.toWei(0.25, "ether")) +const requiredSignatures = 1 +const requiredBlockConfirmations = 8 +const gasPrice = web3.toWei('1', 'gwei') +const oneEther = web3.toBigNumber(web3.toWei(1, "ether")) +const homeDailyLimit = oneEther +const homeMaxPerTx = halfEther +const minPerTx = quarterEther +const foreignDailyLimit = oneEther +const foreignMaxPerTx = halfEther + +contract('HomeBridgeFactory', async (accounts) => { + let validatorContract, homeBridgeContract, owner + before(async () => { + validatorContract = await BridgeValidators.new() + homeBridgeContract = await HomeBridge.new() + owner = accounts[0] + }) + + describe('#initialize', async () => { + it('should initialize', async () => { + let homeBridgeFactory = await HomeBridgeFactory.new() + + false.should.be.equal(await homeBridgeFactory.isInitialized()) + ZERO_ADDRESS.should.be.equal(await homeBridgeFactory.bridgeValidatorsImplementation()) + '0'.should.be.bignumber.equal(await homeBridgeFactory.requiredSignatures()) + ZERO_ADDRESS.should.be.equal(await homeBridgeFactory.bridgeValidatorsOwner()) + ZERO_ADDRESS.should.be.equal(await homeBridgeFactory.bridgeValidatorsProxyOwner()) + ZERO_ADDRESS.should.be.equal(await homeBridgeFactory.homeBridgeErcToErcImplementation()) + '0'.should.be.bignumber.equal(await homeBridgeFactory.requiredBlockConfirmations()) + '0'.should.be.bignumber.equal(await homeBridgeFactory.gasPrice()) + '0'.should.be.bignumber.equal(await homeBridgeFactory.homeDailyLimit()) + '0'.should.be.bignumber.equal(await homeBridgeFactory.homeMaxPerTx()) + '0'.should.be.bignumber.equal(await homeBridgeFactory.minPerTx()) + '0'.should.be.bignumber.equal(await homeBridgeFactory.foreignDailyLimit()) + '0'.should.be.bignumber.equal(await homeBridgeFactory.foreignMaxPerTx()) + ZERO_ADDRESS.should.be.equal(await homeBridgeFactory.homeBridgeOwner()) + ZERO_ADDRESS.should.be.equal(await homeBridgeFactory.homeBridgeProxyOwner()) + + await homeBridgeFactory.initialize().should.be.rejectedWith(INVALID_ARGUMENTS) + await homeBridgeFactory.initialize(ZERO_ADDRESS, validatorContract.address, requiredSignatures, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) + await homeBridgeFactory.initialize(owner, ZERO_ADDRESS, requiredSignatures, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) + await homeBridgeFactory.initialize(owner, validatorContract.address, 0, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) + await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) + await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], ZERO_ADDRESS, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) + await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, ZERO_ADDRESS, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) + await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, homeBridgeContract.address, 0, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) + await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, 0, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) + await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, 0, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) + await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, 0, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) + await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, 0, foreignDailyLimit, foreignMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) + await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, 0, foreignMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) + await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignDailyLimit, owner, owner).should.be.rejectedWith(ERROR_MSG) + await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, ZERO_ADDRESS, owner).should.be.rejectedWith(ERROR_MSG) + await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, ZERO_ADDRESS).should.be.rejectedWith(ERROR_MSG) + + await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, owner) + + true.should.be.equal(await homeBridgeFactory.isInitialized()) + validatorContract.address.should.be.equal(await homeBridgeFactory.bridgeValidatorsImplementation()) + requiredSignatures.should.be.bignumber.equal(await homeBridgeFactory.requiredSignatures()) + owner.should.be.equal(await homeBridgeFactory.bridgeValidatorsOwner()) + owner.should.be.equal(await homeBridgeFactory.bridgeValidatorsProxyOwner()) + homeBridgeContract.address.should.be.equal(await homeBridgeFactory.homeBridgeErcToErcImplementation()) + requiredBlockConfirmations.should.be.bignumber.equal(await homeBridgeFactory.requiredBlockConfirmations()) + gasPrice.should.be.bignumber.equal(await homeBridgeFactory.gasPrice()) + homeDailyLimit.should.be.bignumber.equal(await homeBridgeFactory.homeDailyLimit()) + homeMaxPerTx.should.be.bignumber.equal(await homeBridgeFactory.homeMaxPerTx()) + minPerTx.should.be.bignumber.equal(await homeBridgeFactory.minPerTx()) + foreignDailyLimit.should.be.bignumber.equal(await homeBridgeFactory.foreignDailyLimit()) + foreignMaxPerTx.should.be.bignumber.equal(await homeBridgeFactory.foreignMaxPerTx()) + owner.should.be.equal(await homeBridgeFactory.homeBridgeOwner()) + owner.should.be.equal(await homeBridgeFactory.homeBridgeProxyOwner()) + const [major, minor, patch] = await homeBridgeFactory.getBridgeFactoryVersion() + major.should.be.bignumber.gte(0) + minor.should.be.bignumber.gte(0) + patch.should.be.bignumber.gte(0) + }) + }) + + describe('#deployHomeBridge', async () => { + let homeBridgeFactory + before(async () => { + homeBridgeFactory = await HomeBridgeFactory.new() + await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, owner) + }) + + it('should deploy a home bridge', async () => { + let token = { name: "Some ERC20", symbol: "SMT_1", decimals: 18 } + + const {logs} = await homeBridgeFactory.deployHomeBridge(token.name, token.symbol, token.decimals) + const {args} = getEventFromLogs(logs, 'HomeBridgeDeployed') + + ZERO_ADDRESS.should.not.be.equal(args._homeBridge) + ZERO_ADDRESS.should.not.be.equal(args._homeValidators) + ZERO_ADDRESS.should.not.be.equal(args._token) + args._blockNumber.should.be.bignumber.gte(0) + + let homeBridge = await HomeBridge.at(args._homeBridge) + true.should.be.equal(await homeBridge.isInitialized()) + args._homeValidators.should.be.equal(await homeBridge.validatorContract()) + const deployedAtBlock = await homeBridge.deployedAtBlock() + deployedAtBlock.should.be.bignumber.above(0) + requiredBlockConfirmations.should.be.bignumber.equal(await homeBridge.requiredBlockConfirmations()) + gasPrice.should.be.bignumber.equal(await homeBridge.gasPrice()) + const bridgeMode = '0xba4690f5' // 4 bytes of keccak256('erc-to-erc-core') + const mode = await homeBridge.getBridgeMode() + mode.should.be.equal(bridgeMode) + const [major, minor, patch] = await homeBridge.getBridgeInterfacesVersion() + major.should.be.bignumber.gte(0) + minor.should.be.bignumber.gte(0) + patch.should.be.bignumber.gte(0) + }) + + it('should deploy a second home bridge using same factory', async () => { + let token = { name: "Another ERC20", symbol: "SMT_2", decimals: 18 } + + const {logs} = await homeBridgeFactory.deployHomeBridge(token.name, token.symbol, token.decimals) + const {args} = getEventFromLogs(logs, 'HomeBridgeDeployed') + + ZERO_ADDRESS.should.not.be.equal(args._homeBridge) + ZERO_ADDRESS.should.not.be.equal(args._homeValidators) + ZERO_ADDRESS.should.not.be.equal(args._token) + args._blockNumber.should.be.bignumber.gte(0) + + let homeBridge = await HomeBridge.at(args._homeBridge) + true.should.be.equal(await homeBridge.isInitialized()) + args._homeValidators.should.be.equal(await homeBridge.validatorContract()) + const deployedAtBlock = await homeBridge.deployedAtBlock() + deployedAtBlock.should.be.bignumber.above(0) + requiredBlockConfirmations.should.be.bignumber.equal(await homeBridge.requiredBlockConfirmations()) + gasPrice.should.be.bignumber.equal(await homeBridge.gasPrice()) + const bridgeMode = '0xba4690f5' // 4 bytes of keccak256('erc-to-erc-core') + const mode = await homeBridge.getBridgeMode() + mode.should.be.equal(bridgeMode) + const [major, minor, patch] = await homeBridge.getBridgeInterfacesVersion() + major.should.be.bignumber.gte(0) + minor.should.be.bignumber.gte(0) + patch.should.be.bignumber.gte(0) + }) + }) +}) diff --git a/test/helpers/helpers.js b/test/helpers/helpers.js index cb276a2a8..306c40008 100644 --- a/test/helpers/helpers.js +++ b/test/helpers/helpers.js @@ -111,3 +111,8 @@ module.exports.range = range; function ignoreExpectedError() { } module.exports.ignoreExpectedError = ignoreExpectedError; + +function getEventFromLogs(logs, eventName) { + return logs.filter(log => log.event === eventName)[0] +} +module.exports.getEventFromLogs = getEventFromLogs; diff --git a/test/mapper/home_mapper.test.js b/test/mapper/home_mapper.test.js new file mode 100644 index 000000000..c1a6ccca4 --- /dev/null +++ b/test/mapper/home_mapper.test.js @@ -0,0 +1,160 @@ +const BridgeMapper = artifacts.require("BridgeMapper.sol") +const ForeignBridgeFactory = artifacts.require("ForeignBridgeFactory.sol") +const HomeBridgeFactory = artifacts.require("HomeBridgeFactory.sol") +const ForeignBridge = artifacts.require("ForeignBridgeErcToErc.sol") +const HomeBridge = artifacts.require("HomeBridgeErcToErc.sol") +const BridgeValidators = artifacts.require("BridgeValidators.sol") +const ERC677BridgeToken = artifacts.require("ERC677BridgeToken.sol") + +const {ERROR_MSG, ZERO_ADDRESS, INVALID_ARGUMENTS} = require('../setup') +const {getEventFromLogs} = require('../helpers/helpers') +const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")) +const quarterEther = web3.toBigNumber(web3.toWei(0.25, "ether")) +const requiredSignatures = 1 +const requiredBlockConfirmations = 8 +const gasPrice = web3.toWei('1', 'gwei') +const oneEther = web3.toBigNumber(web3.toWei(1, "ether")) +const homeDailyLimit = oneEther +const homeMaxPerTx = halfEther +const maxPerTx = halfEther +const minPerTx = quarterEther +const foreignDailyLimit = oneEther +const foreignMaxPerTx = halfEther + +contract('BridgeMapper', async (accounts) => { + let validatorContract, owner, foreignBridgeContract, homeBridgeContract, homeBridgeFactory, foreignBridgeFactory + before(async () => { + owner = accounts[0] + + validatorContract = await BridgeValidators.new() + foreignBridgeContract = await ForeignBridge.new() + homeBridgeContract = await HomeBridge.new() + foreignBridgeFactory = await ForeignBridgeFactory.new() + homeBridgeFactory = await HomeBridgeFactory.new() + + await foreignBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, foreignBridgeContract.address, requiredBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner, owner) + await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, owner) + }) + + describe('#initialize', async () => { + it('should initialize', async () => { + let bridgeMapper = await BridgeMapper.new() + + false.should.be.equal(await bridgeMapper.isInitialized()) + ZERO_ADDRESS.should.be.equal(await bridgeMapper.owner()) + + await bridgeMapper.initialize().should.be.rejectedWith(INVALID_ARGUMENTS) + + await bridgeMapper.initialize(owner) + + true.should.be.equal(await bridgeMapper.isInitialized()) + owner.should.be.equal(await bridgeMapper.owner()) + }) + }) + + describe('#addBridgeMapping', async () => { + let bridgeMapper + before(async () => { + bridgeMapper = await BridgeMapper.new() + await bridgeMapper.initialize(owner) + }) + + it('should not add mapping if params are wrong/missng', async () => { + let foreignToken = await ERC677BridgeToken.new("Foreign ERC20", "FSMT", 18) + let foreignBridgeDeployedArgs = getEventFromLogs((await foreignBridgeFactory.deployForeignBridge(foreignToken.address)).logs, 'ForeignBridgeDeployed').args + + let homeToken = { name: "Home ERC20", symbol: "HSMT", decimals: 18 } + let homeBridgeDeployedArgs = getEventFromLogs((await homeBridgeFactory.deployHomeBridge(homeToken.name, homeToken.symbol, homeToken.decimals)).logs, 'HomeBridgeDeployed').args + + await bridgeMapper.addBridgeMapping().should.be.rejectedWith(INVALID_ARGUMENTS) + await bridgeMapper.addBridgeMapping(ZERO_ADDRESS, homeBridgeDeployedArgs._token, foreignBridgeDeployedArgs._foreignBridge, homeBridgeDeployedArgs._homeBridge, foreignBridgeDeployedArgs._blockNumber, homeBridgeDeployedArgs._blockNumber).should.be.rejectedWith(ERROR_MSG) + await bridgeMapper.addBridgeMapping(foreignToken.address, ZERO_ADDRESS, foreignBridgeDeployedArgs._foreignBridge, homeBridgeDeployedArgs._homeBridge, foreignBridgeDeployedArgs._blockNumber, homeBridgeDeployedArgs._blockNumber).should.be.rejectedWith(ERROR_MSG) + await bridgeMapper.addBridgeMapping(foreignToken.address, homeBridgeDeployedArgs._token, ZERO_ADDRESS, homeBridgeDeployedArgs._homeBridge, foreignBridgeDeployedArgs._blockNumber, homeBridgeDeployedArgs._blockNumber).should.be.rejectedWith(ERROR_MSG) + await bridgeMapper.addBridgeMapping(foreignToken.address, homeBridgeDeployedArgs._token, foreignBridgeDeployedArgs._foreignBridge, ZERO_ADDRESS, foreignBridgeDeployedArgs._blockNumber, homeBridgeDeployedArgs._blockNumber).should.be.rejectedWith(ERROR_MSG) + await bridgeMapper.addBridgeMapping(foreignToken.address, homeBridgeDeployedArgs._token, foreignBridgeDeployedArgs._foreignBridge, homeBridgeDeployedArgs._homeBridge, 0, homeBridgeDeployedArgs._blockNumber).should.be.rejectedWith(ERROR_MSG) + await bridgeMapper.addBridgeMapping(foreignToken.address, homeBridgeDeployedArgs._token, foreignBridgeDeployedArgs._foreignBridge, homeBridgeDeployedArgs._homeBridge, foreignBridgeDeployedArgs._blockNumber, 0).should.be.rejectedWith(ERROR_MSG) + }) + + it('should add a bridge mapping', async () => { + let foreignToken = await ERC677BridgeToken.new("Foreign ERC20", "FSMT_1", 18) + let foreignBridgeDeployedArgs = getEventFromLogs((await foreignBridgeFactory.deployForeignBridge(foreignToken.address)).logs, 'ForeignBridgeDeployed').args + + let homeToken = { name: "Home ERC20", symbol: "HSMT_1", decimals: 18 } + let homeBridgeDeployedArgs = getEventFromLogs((await homeBridgeFactory.deployHomeBridge(homeToken.name, homeToken.symbol, homeToken.decimals)).logs, 'HomeBridgeDeployed').args + + let {logs} = await bridgeMapper.addBridgeMapping(foreignToken.address, homeBridgeDeployedArgs._token, foreignBridgeDeployedArgs._foreignBridge, homeBridgeDeployedArgs._homeBridge, foreignBridgeDeployedArgs._blockNumber, homeBridgeDeployedArgs._blockNumber) + let {args} = getEventFromLogs(logs, 'BridgeMappingUpdated') + + foreignToken.address.should.be.equal(args.foreignToken) + homeBridgeDeployedArgs._token.should.be.equal(args.homeToken) + foreignBridgeDeployedArgs._foreignBridge.should.be.equal(args.foreignBridge) + homeBridgeDeployedArgs._homeBridge.should.be.equal(args.homeBridge) + foreignBridgeDeployedArgs._blockNumber.should.be.bignumber.equal(args.foreignStartBlock) + homeBridgeDeployedArgs._blockNumber.should.be.bignumber.equal(args.homeStartBlock) + + homeBridgeDeployedArgs._token.should.be.equal(await bridgeMapper.homeTokenByForeignToken(foreignToken.address)) + foreignBridgeDeployedArgs._foreignBridge.should.be.equal(await bridgeMapper.foreignBridgeByForeignToken(foreignToken.address)) + homeBridgeDeployedArgs._homeBridge.should.be.equal(await bridgeMapper.homeBridgeByForeignToken(foreignToken.address)) + foreignBridgeDeployedArgs._blockNumber.should.be.bignumber.equal(await bridgeMapper.foreignStartBlockByForeignToken(foreignToken.address)) + homeBridgeDeployedArgs._blockNumber.should.be.bignumber.equal(await bridgeMapper.homeStartBlockByForeignToken(foreignToken.address)) + }) + + it('should add a second bridge mapping using same mapper', async () => { + let foreignToken = await ERC677BridgeToken.new("Another Foreign ERC20", "FSMT_2", 18) + let foreignBridgeDeployedArgs = getEventFromLogs((await foreignBridgeFactory.deployForeignBridge(foreignToken.address)).logs, 'ForeignBridgeDeployed').args + + let homeToken = { name: "Another Home ERC20", symbol: "HSMT_2", decimals: 18 } + let homeBridgeDeployedArgs = getEventFromLogs((await homeBridgeFactory.deployHomeBridge(homeToken.name, homeToken.symbol, homeToken.decimals)).logs, 'HomeBridgeDeployed').args + + let {logs} = await bridgeMapper.addBridgeMapping(foreignToken.address, homeBridgeDeployedArgs._token, foreignBridgeDeployedArgs._foreignBridge, homeBridgeDeployedArgs._homeBridge, foreignBridgeDeployedArgs._blockNumber, homeBridgeDeployedArgs._blockNumber) + let {args} = getEventFromLogs(logs, 'BridgeMappingUpdated') + + foreignToken.address.should.be.equal(args.foreignToken) + homeBridgeDeployedArgs._token.should.be.equal(args.homeToken) + foreignBridgeDeployedArgs._foreignBridge.should.be.equal(args.foreignBridge) + homeBridgeDeployedArgs._homeBridge.should.be.equal(args.homeBridge) + foreignBridgeDeployedArgs._blockNumber.should.be.bignumber.equal(args.foreignStartBlock) + homeBridgeDeployedArgs._blockNumber.should.be.bignumber.equal(args.homeStartBlock) + + homeBridgeDeployedArgs._token.should.be.equal(await bridgeMapper.homeTokenByForeignToken(foreignToken.address)) + foreignBridgeDeployedArgs._foreignBridge.should.be.equal(await bridgeMapper.foreignBridgeByForeignToken(foreignToken.address)) + homeBridgeDeployedArgs._homeBridge.should.be.equal(await bridgeMapper.homeBridgeByForeignToken(foreignToken.address)) + foreignBridgeDeployedArgs._blockNumber.should.be.bignumber.equal(await bridgeMapper.foreignStartBlockByForeignToken(foreignToken.address)) + homeBridgeDeployedArgs._blockNumber.should.be.bignumber.equal(await bridgeMapper.homeStartBlockByForeignToken(foreignToken.address)) + }) + }) + + describe('#removeBridgeMapping', async () => { + let bridgeMapper + before(async () => { + bridgeMapper = await BridgeMapper.new() + await bridgeMapper.initialize(owner) + }) + + it('should remove a bridge mapping', async () => { + let foreignToken = await ERC677BridgeToken.new("Foreign ERC20", "FSMT", 18) + let foreignBridgeDeployedArgs = getEventFromLogs((await foreignBridgeFactory.deployForeignBridge(foreignToken.address)).logs, 'ForeignBridgeDeployed').args + + let homeToken = { name: "Home ERC20", symbol: "HSMT", decimals: 18 } + let homeBridgeDeployedArgs = getEventFromLogs((await homeBridgeFactory.deployHomeBridge(homeToken.name, homeToken.symbol, homeToken.decimals)).logs, 'HomeBridgeDeployed').args + + await bridgeMapper.addBridgeMapping(foreignToken.address, homeBridgeDeployedArgs._token, foreignBridgeDeployedArgs._foreignBridge, homeBridgeDeployedArgs._homeBridge, foreignBridgeDeployedArgs._blockNumber, homeBridgeDeployedArgs._blockNumber) + + let {logs} = await bridgeMapper.removeBridgeMapping(foreignToken.address) + let {args} = getEventFromLogs(logs, 'BridgeMappingUpdated') + + foreignToken.address.should.be.equal(args.foreignToken) + ZERO_ADDRESS.should.be.equal(args.homeToken) + ZERO_ADDRESS.should.be.equal(args.foreignBridge) + ZERO_ADDRESS.should.be.equal(args.homeBridge) + '0'.should.be.bignumber.equal(args.foreignStartBlock) + '0'.should.be.bignumber.equal(args.homeStartBlock) + + ZERO_ADDRESS.should.be.equal(await bridgeMapper.homeBridgeByForeignToken(foreignToken.address)) + ZERO_ADDRESS.should.be.equal(await bridgeMapper.foreignBridgeByForeignToken(foreignToken.address)) + ZERO_ADDRESS.should.be.equal(await bridgeMapper.homeTokenByForeignToken(foreignToken.address)) + '0'.should.be.bignumber.equal(await bridgeMapper.homeStartBlockByForeignToken(foreignToken.address)) + '0'.should.be.bignumber.equal(await bridgeMapper.foreignStartBlockByForeignToken(foreignToken.address)) + }) + }) +}) From e414d6640a803424549f33b4a9ef756ff3f6d9fc Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 25 Feb 2019 12:36:22 -0300 Subject: [PATCH 102/187] Remove onRequestForSignature and onSignaturesCollected from FeeManager --- .../upgradeable_contracts/BaseFeeManager.sol | 6 +++--- .../native_to_erc20/FeeManagerNativeToErc.sol | 7 ------- .../FeeManagerNativeToErcBothDirections.sol | 10 ---------- .../ForeignBridgeNativeToErc.sol | 6 ++++-- .../native_to_erc20/HomeBridgeNativeToErc.sol | 8 ++++++-- .../RewardableHomeBridgeNativeToErc.sol | 17 ----------------- deploy/src/native_to_erc/home.js | 5 +++-- test/native_to_erc/home_bridge_test.js | 10 +++++----- 8 files changed, 21 insertions(+), 48 deletions(-) diff --git a/contracts/upgradeable_contracts/BaseFeeManager.sol b/contracts/upgradeable_contracts/BaseFeeManager.sol index 379fac11b..52eb98865 100644 --- a/contracts/upgradeable_contracts/BaseFeeManager.sol +++ b/contracts/upgradeable_contracts/BaseFeeManager.sol @@ -16,7 +16,7 @@ contract BaseFeeManager is EternalStorage, FeeTypes { event HomeFeeUpdated(uint256 fee); event ForeignFeeUpdated(uint256 fee); - function calculateFee(uint256 _value, bool _recover, bytes32 _feeType) public view returns(uint256) { + function calculateFee(uint256 _value, bool _recover, bytes32 _feeType) external view returns(uint256) { uint256 fee = _feeType == HOME_FEE ? getHomeFee() : getForeignFee(); uint256 eth = 1 ether; if (!_recover) { @@ -43,11 +43,11 @@ contract BaseFeeManager is EternalStorage, FeeTypes { return uintStorage[keccak256(abi.encodePacked("foreignFee"))]; } - function distributeFeeFromAffirmation(uint256 _fee) public { + function distributeFeeFromAffirmation(uint256 _fee) external { distributeFeeProportionally(_fee, REWARD_FOR_TRANSFERRING_FROM_FOREIGN); } - function distributeFeeFromSignatures(uint256 _fee) public { + function distributeFeeFromSignatures(uint256 _fee) external { distributeFeeProportionally(_fee, REWARD_FOR_TRANSFERRING_FROM_HOME); } diff --git a/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErc.sol index 65905aeda..a1f5b4c4e 100644 --- a/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErc.sol +++ b/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErc.sol @@ -7,13 +7,6 @@ import "../Sacrifice.sol"; contract FeeManagerNativeToErc is BaseFeeManager { - function onRequestForSignature(uint256 _value) external view returns(uint256) { - return _value; - } - - function onSignaturesCollected(uint256) external { - } - function getFeeManagerMode() public pure returns(bytes4) { return bytes4(keccak256(abi.encodePacked("manages-one-direction"))); } diff --git a/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErcBothDirections.sol b/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErcBothDirections.sol index c1aeb5470..e511ecee0 100644 --- a/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErcBothDirections.sol +++ b/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErcBothDirections.sol @@ -7,16 +7,6 @@ import "../Sacrifice.sol"; contract FeeManagerNativeToErcBothDirections is BaseFeeManager { - function onRequestForSignature(uint256 _value) external view returns(uint256) { - uint256 fee = calculateFee(_value, false, HOME_FEE); - return _value.sub(fee); - } - - function onSignaturesCollected(uint256 _value) external { - uint256 fee = calculateFee(_value, true, HOME_FEE); - distributeFeeFromSignatures(fee); - } - function getFeeManagerMode() public pure returns(bytes4) { return bytes4(keccak256(abi.encodePacked("manages-both-directions"))); } diff --git a/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol index 1821b279c..2183741b7 100644 --- a/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol +++ b/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol @@ -120,8 +120,10 @@ contract ForeignBridgeNativeToErc is ERC677Receiver, BasicBridge, BasicForeignBr address feeManager = feeManagerContract(); if (feeManager != address(0)) { uint256 fee = calculateFee(valueToMint, false, feeManager, HOME_FEE); - distributeFeeFromSignatures(fee, feeManager); - valueToMint = valueToMint.sub(fee); + if (fee != 0) { + distributeFeeFromSignatures(fee, feeManager); + valueToMint = valueToMint.sub(fee); + } } return erc677token().mint(_recipient, valueToMint); } diff --git a/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol index d8126cc24..6c94fbff9 100644 --- a/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol +++ b/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol @@ -18,7 +18,8 @@ contract HomeBridgeNativeToErc is EternalStorage, BasicBridge, BasicHomeBridge, uint256 valueToTransfer = msg.value; address feeManager = feeManagerContract(); if (feeManager != address(0)) { - valueToTransfer = onRequestForSignature(valueToTransfer, feeManager); + uint256 fee = calculateFee(valueToTransfer, false, feeManager, HOME_FEE); + valueToTransfer = valueToTransfer.sub(fee); } emit UserRequestForSignature(msg.sender, valueToTransfer); } @@ -127,7 +128,10 @@ contract HomeBridgeNativeToErc is EternalStorage, BasicBridge, BasicHomeBridge, bytes32 txHash; address contractAddress; (recipient, amount, txHash, contractAddress) = Message.parseMessage(_message); - distributeFeeOnSignaturesCollected(amount, feeManager); + uint256 fee = calculateFee(amount, true, feeManager, HOME_FEE); + if (fee != 0) { + distributeFeeFromSignatures(fee, feeManager); + } } } diff --git a/contracts/upgradeable_contracts/native_to_erc20/RewardableHomeBridgeNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/RewardableHomeBridgeNativeToErc.sol index 71f96fc15..71fb926ec 100644 --- a/contracts/upgradeable_contracts/native_to_erc20/RewardableHomeBridgeNativeToErc.sol +++ b/contracts/upgradeable_contracts/native_to_erc20/RewardableHomeBridgeNativeToErc.sol @@ -20,21 +20,4 @@ contract RewardableHomeBridgeNativeToErc is RewardableBridge { function getHomeFee() public view returns(uint256) { return _getFee(HOME_FEE); } - - function onRequestForSignature(uint256 _value, address _impl) internal view returns(uint256) { - uint256 returnedValue; - bytes memory callData = abi.encodeWithSignature("onRequestForSignature(uint256)", _value); - assembly { - let result := callcode(gas, _impl, 0x0, add(callData, 0x20), mload(callData), 0, 32) - returnedValue := mload(0) - - switch result - case 0 { revert(0, 0) } - } - return returnedValue; - } - - function distributeFeeOnSignaturesCollected(uint256 _fee, address _feeManager) internal { - require(_feeManager.delegatecall(abi.encodeWithSignature("onSignaturesCollected(uint256)", _fee))); - } } diff --git a/deploy/src/native_to_erc/home.js b/deploy/src/native_to_erc/home.js index e09579b4a..5e3011c6e 100644 --- a/deploy/src/native_to_erc/home.js +++ b/deploy/src/native_to_erc/home.js @@ -172,7 +172,8 @@ async function deployHome() { console.log('[Home] feeManager Implementation: ', feeManager.options.address) homeNonce++ - const homeFeeInWei = Web3Utils.toWei(HOME_TRANSACTIONS_FEE.toString(), 'ether') + const homeFee = isBothDirectionsFeeManager ? HOME_TRANSACTIONS_FEE.toString() : '0' + const homeFeeInWei = Web3Utils.toWei(homeFee, 'ether') const foreignFeeInWei = Web3Utils.toWei(FOREIGN_TRANSACTIONS_FEE.toString(), 'ether') console.log('\ninitializing Home Bridge with fee contract:\n') @@ -193,7 +194,7 @@ async function deployHome() { )} in eth, HOME_BRIDGE_OWNER: ${HOME_BRIDGE_OWNER}, Fee Manager: ${feeManager.options.address}, - Home Fee: ${homeFeeInWei} which is ${HOME_TRANSACTIONS_FEE * 100}% + Home Fee: ${homeFeeInWei} which is ${homeFee * 100}% Foreign Fee: ${foreignFeeInWei} which is ${FOREIGN_TRANSACTIONS_FEE * 100}%`) homeBridgeImplementation.options.address = homeBridgeStorage.options.address diff --git a/test/native_to_erc/home_bridge_test.js b/test/native_to_erc/home_bridge_test.js index 8572af649..6a52a7991 100644 --- a/test/native_to_erc/home_bridge_test.js +++ b/test/native_to_erc/home_bridge_test.js @@ -664,7 +664,7 @@ contract('HomeBridge', async (accounts) => { // 0.1% fee const fee = 0.001 const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) - const notUsedFee = web3.toBigNumber(web3.toWei(fee, "ether")) + const notUsedFee = web3.toBigNumber(web3.toWei(0, "ether")) const value = halfEther; await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, notUsedFee, feeInWei).should.be.fulfilled; @@ -701,7 +701,7 @@ contract('HomeBridge', async (accounts) => { // 0.1% fee const fee = 0.001 const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) - const notUsedFee = web3.toBigNumber(web3.toWei(fee, "ether")) + const notUsedFee = web3.toBigNumber(web3.toWei(0, "ether")) const value = halfEther; const rewardAddressBalanceBefore = await web3.eth.getBalance(rewards[0]) @@ -747,7 +747,7 @@ contract('HomeBridge', async (accounts) => { // 0.1% fee const fee = 0.001 const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) - const notUsedFee = web3.toBigNumber(web3.toWei(fee, "ether")) + const notUsedFee = web3.toBigNumber(web3.toWei(0, "ether")) const value = halfEther; const finalUserValue = value.mul(web3.toBigNumber(1-fee)); const feeAmount = value.mul(web3.toBigNumber(fee)) @@ -797,7 +797,7 @@ contract('HomeBridge', async (accounts) => { // 0.1% fee const fee = 0.001 const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) - const notUsedFee = web3.toBigNumber(web3.toWei(fee, "ether")) + const notUsedFee = web3.toBigNumber(web3.toWei(0, "ether")) const feePerValidator = web3.toBigNumber(166666666666666) const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) const finalUserValue = value.mul(web3.toBigNumber(1-fee)); @@ -869,7 +869,7 @@ contract('HomeBridge', async (accounts) => { // 0.1% fee const fee = 0.001 const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) - const notUsedFee = web3.toBigNumber(web3.toWei(fee, "ether")) + const notUsedFee = web3.toBigNumber(web3.toWei(0, "ether")) const feeAmount = value.mul(web3.toBigNumber(fee)) const feePerValidator = feeAmount.div(web3.toBigNumber(5)) From 67de488504228db9e8b8a31ebe7a744c694d5d94 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 25 Feb 2019 15:50:08 -0300 Subject: [PATCH 103/187] Update gas consumption docs --- docs/NATIVE-TO-ERC-WITH-REWARD.md | 81 +++++++++++++++++++++++++++---- docs/NATIVE-TO-ERC.md | 16 +++--- 2 files changed, 79 insertions(+), 18 deletions(-) diff --git a/docs/NATIVE-TO-ERC-WITH-REWARD.md b/docs/NATIVE-TO-ERC-WITH-REWARD.md index 7dc969e98..db3f2bf83 100644 --- a/docs/NATIVE-TO-ERC-WITH-REWARD.md +++ b/docs/NATIVE-TO-ERC-WITH-REWARD.md @@ -1,4 +1,4 @@ -## Gas Consumption `NATIVE-TO-ERC` Bridge Mode with Reward contract +## Gas Consumption `NATIVE-TO-ERC` Bridge Mode with Reward contract on Home and Foreign networks #### Deployment ##### Home @@ -10,12 +10,12 @@ EternalStorageProxy|upgradeTo|35871|30924|30913 RewardableValidators|initialize|202711|423292|318008 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 EternalStorageProxy|deployment|378510|378510|378510 -HomeBridgeNativeToErc|deployment|4594464|4594464|4594464 +HomeBridgeNativeToErc|deployment|4841729|4841729|4841729 EternalStorageProxy|upgradeTo|35871|30924|30913 FeeManagerNativeToErc|deployment|1079956|1079956|1079956 -HomeBridgeNativeToErc|rewardableInitialize|306629|306693|306647 +HomeBridgeNativeToErc|rewardableInitialize|315276|315340|315304 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |8689618|8900369|8795017 +Total| |8945530|9156281|9050939 ##### Foreign Contract | Method | Min | Max | Avg @@ -27,14 +27,14 @@ EternalStorageProxy|upgradeTo|35871|30924|30913 RewardableValidators|initialize|202711|423292|318008 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 EternalStorageProxy|deployment|378510|378510|378510 -ForeignBridgeNativeToErc|deployment|3930131|3930131|3930131 +ForeignBridgeNativeToErc|deployment|3931739|3931739|3931739 EternalStorageProxy|upgradeTo|35871|30924|30913 FeeManagerNativeToErc|deployment|1079956|1079956|1079956 ForeignBridgeNativeToErc|rewardableInitialize|329022|329086|329077 ERC677BridgeToken|setBridgeContract|29432|44432|39432 ERC677BridgeToken|transferOwnership|30860|30924|30913 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |9571506|9798345|9687629 +Total| |9573114|9799953|9689237 #### Usage @@ -43,17 +43,78 @@ Total| |9571506|9798345|9687629 Contract | Method | Min | Max | Avg ---- | ---- | ---- | ---- | ---- To sign at the Home (each validator)| -HomeBridgeNativeToErc|submitSignature|159814|275587|220654 +HomeBridgeNativeToErc|submitSignature|159880|287671|227125 To relay signatures from the Home to the Foreign (one validator)| ForeignBridgeNativeToErc|executeSignatures|193143|374488|288553 To sign and relay from the Foreign to the Home (each validator)| -HomeBridgeNativeToErc|executeAffirmation|67290|205460|108687 +HomeBridgeNativeToErc|executeAffirmation|67313|206296|104845 ##### Users Contract | Method | Min | Max | Avg ---- | ---- | ---- | ---- | ---- To request transfer from the Home to the Foreign| -HomeBridgeNativeToErc|fallback|46982|46982|46982 +HomeBridgeNativeToErc|fallback|51199|51199|51199 To request transfer from the Foreign to the Home| -ERC677BridgeToken|transferAndCall|58654|166206|92597 +ERC677BridgeToken|transferAndCall|58676|166206|92613 + + + +## Gas Consumption `NATIVE-TO-ERC` Bridge Mode with Reward contract on Home network + +#### Deployment +##### Home + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +EternalStorageProxy|deployment|378510|378510|378510 +RewardableValidators|deployment|1615790|1615790|1615790 +EternalStorageProxy|upgradeTo|35871|30924|30913 +RewardableValidators|initialize|202711|423292|318008 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +EternalStorageProxy|deployment|378510|378510|378510 +HomeBridgeNativeToErc|deployment|4841729|4841729|4841729 +EternalStorageProxy|upgradeTo|35871|30924|30913 +FeeManagerNativeToErcBothDirections|deployment|1004365|1004365|1004365 +HomeBridgeNativeToErc|rewardableInitialize|315276|330680|325073 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +Total| |8869939|9096030|8985117 + +##### Foreign + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +ERC677BridgeToken|deployment|1463536|1464560|1464170 +EternalStorageProxy|deployment|378510|378510|378510 +BridgeValidators|deployment|1351491|1351491|1351491 +EternalStorageProxy|upgradeTo|35871|30924|30913 +BridgeValidators|initialize|210762|306607|270900 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +EternalStorageProxy|deployment|378510|378510|378510 +ForeignBridgeNativeToErc|deployment|3931739|3931739|3931739 +EternalStorageProxy|upgradeTo|35871|30924|30913 +ForeignBridgeNativeToErc|initialize|281275|281339|281328 +ERC677BridgeToken|setBridgeContract|29432|44432|39432 +ERC677BridgeToken|transferOwnership|30860|30924|30913 +EternalStorageProxy|transferProxyOwnership|30653|30653|30653 +Total| |8189163|8291266|8250125 + +#### Usage + +##### Validators + + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +To sign at the Home (each validator)| +HomeBridgeNativeToErc|submitSignature|159880|308541|219741 +To relay signatures from the Home to the Foreign (one validator)| +ForeignBridgeNativeToErc|executeSignatures|99365|172087|138314 +To sign and relay from the Foreign to the Home (each validator)| +HomeBridgeNativeToErc|executeAffirmation|67313|206445|104857 + +##### Users + + Contract | Method | Min | Max | Avg +---- | ---- | ---- | ---- | ---- +To request transfer from the Home to the Foreign| +HomeBridgeNativeToErc|fallback|51177,|51177,|51177, +To request transfer from the Foreign to the Home| +ERC677BridgeToken|transferAndCall|58676|166206|92613 diff --git a/docs/NATIVE-TO-ERC.md b/docs/NATIVE-TO-ERC.md index de1f8882e..f073fe80e 100644 --- a/docs/NATIVE-TO-ERC.md +++ b/docs/NATIVE-TO-ERC.md @@ -10,11 +10,11 @@ EternalStorageProxy|upgradeTo|35871|30924|30913 BridgeValidators|initialize|210762|306607|270900 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 EternalStorageProxy|deployment|378510|378510|378510 -HomeBridgeNativeToErc|deployment|4594464|4594464|4594464 +HomeBridgeNativeToErc|deployment|4841729|4841729|4841729 EternalStorageProxy|upgradeTo|35871|30924|30913 HomeBridgeNativeToErc|initialize|257416|258312|258003 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |7304201|7391048|7355010 +Total| |7551466|7638313|7602275 ##### Foreign Contract | Method | Min | Max | Avg @@ -26,13 +26,13 @@ EternalStorageProxy|upgradeTo|35871|30924|30913 BridgeValidators|initialize|210762|306607|270900 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 EternalStorageProxy|deployment|378510|378510|378510 -ForeignBridgeNativeToErc|deployment|3930131|3930131|3930131 +ForeignBridgeNativeToErc|deployment|3931739|3931739|3931739 EternalStorageProxy|upgradeTo|35871|30924|30913 ForeignBridgeNativeToErc|initialize|281275|281339|281328 ERC677BridgeToken|setBridgeContract|29432|44432|39432 ERC677BridgeToken|transferOwnership|30860|30924|30913 EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |8187555|8289658|8248517 +Total| |8189163|8291266|8250125 #### Usage @@ -41,17 +41,17 @@ Total| |8187555|8289658|8248517 Contract | Method | Min | Max | Avg ---- | ---- | ---- | ---- | ---- To sign at the Home (each validator)| -HomeBridgeNativeToErc|submitSignature|159814|275587|220654 +HomeBridgeNativeToErc|submitSignature|159816|275743|221116 To relay signatures from the Home to the Foreign (one validator)| ForeignBridgeNativeToErc|executeSignatures|99365|172087|138314 To sign and relay from the Foreign to the Home (each validator)| -HomeBridgeNativeToErc|executeAffirmation|67247|132985|101980 +HomeBridgeNativeToErc|executeAffirmation|67313|133052|102046 ##### Users Contract | Method | Min | Max | Avg ---- | ---- | ---- | ---- | ---- To request transfer from the Home to the Foreign| -HomeBridgeNativeToErc|fallback|46982|46982|46982 +HomeBridgeNativeToErc|fallback|47848|47848|47848 To request transfer from the Foreign to the Home| -ERC677BridgeToken|transferAndCall|58654|166206|92597 +ERC677BridgeToken|transferAndCall|58676|166206|92613 From 06a396bd7e52b590437b66bed3c23f3bcaf97781 Mon Sep 17 00:00:00 2001 From: Lior Rabin Date: Tue, 26 Feb 2019 15:35:59 +0200 Subject: [PATCH 104/187] make the double-proxy work --- contracts/upgradeability/Proxy.sol | 27 +++++++++++++++++-- .../upgradeability/UpgradeabilityStorage.sol | 5 ++++ deploy/deploy.js | 2 +- 3 files changed, 31 insertions(+), 3 deletions(-) diff --git a/contracts/upgradeability/Proxy.sol b/contracts/upgradeability/Proxy.sol index fc58c19b3..c9362b8fe 100644 --- a/contracts/upgradeability/Proxy.sol +++ b/contracts/upgradeability/Proxy.sol @@ -13,6 +13,8 @@ contract Proxy { */ function implementation() public view returns (address); + function setImplementation(address _newImplementation) external; + /** * @dev Fallback function allowing to perform a delegatecall to the given implementation. * This function will return whatever the implementation call returns @@ -20,6 +22,16 @@ contract Proxy { function () payable public { address _impl = implementation(); require(_impl != address(0)); + + address _innerImpl; + bytes4 sig; + address thisAddress = address(this); + if (_impl.call(0x5c60da1b)) { // bytes(keccak256("implementation()")) + _innerImpl = Proxy(_impl).implementation(); + this.setImplementation(_innerImpl); + sig = 0xd784d426; // bytes4(keccak256("setImplementation(address)")) + } + assembly { /* 0x40 is the "free memory slot", meaning a pointer to next slot of empty memory. mload(0x40) @@ -79,14 +91,25 @@ contract Proxy { */ returndatacopy(ptr, 0, returndatasize) + let retdatasize := returndatasize + + switch sig + case 0 {} + default { + let x := mload(0x40) + mstore(x, sig) + mstore(add(x, 0x04), _impl) + let success := call(gas, thisAddress, 0, x, 0x24, x, 0x0) + } + /* if `result` is 0, revert. if `result` is 1, return `size` amount of data from `ptr`. This is the data that was copied to `ptr` from the delegatecall return data */ switch result - case 0 { revert(ptr, returndatasize) } - default { return(ptr, returndatasize) } + case 0 { revert(ptr, retdatasize) } + default { return(ptr, retdatasize) } } } } diff --git a/contracts/upgradeability/UpgradeabilityStorage.sol b/contracts/upgradeability/UpgradeabilityStorage.sol index b3e537790..85f82060f 100644 --- a/contracts/upgradeability/UpgradeabilityStorage.sol +++ b/contracts/upgradeability/UpgradeabilityStorage.sol @@ -27,4 +27,9 @@ contract UpgradeabilityStorage { function implementation() public view returns (address) { return _implementation; } + + function setImplementation(address _newImplementation) external { + require(msg.sender == address(this)); + _implementation = _newImplementation; + } } diff --git a/deploy/deploy.js b/deploy/deploy.js index 2d0a34d7c..f3fbfc3c8 100644 --- a/deploy/deploy.js +++ b/deploy/deploy.js @@ -118,7 +118,7 @@ async function deployFactory() { const { foreignFactory } = await deployForeign() console.log('\nDeployment has been completed.\n\n') console.log(`[ Home ] HomeFactory: ${homeFactory.address} at block ${homeFactory.deployedBlockNumber}`) - console.log(`[ Home ] mapper: ${mapper.address} at block ${mapper.deployedBlockNumber}`) + console.log(`[ Home ] BridgeMapper: ${mapper.address} at block ${mapper.deployedBlockNumber}`) console.log( `[ Foreign ] ForeignFactory: ${foreignFactory.address} at block ${ foreignFactory.deployedBlockNumber From 70cc7351a0ac8a290f820c4415b8042b6058d3c7 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 27 Feb 2019 10:19:29 -0300 Subject: [PATCH 105/187] update home native-to-erc deploy script --- deploy/src/deploymentUtils.js | 84 +++++++++- deploy/src/native_to_erc/home.js | 263 ++++++++++++++----------------- 2 files changed, 201 insertions(+), 146 deletions(-) diff --git a/deploy/src/deploymentUtils.js b/deploy/src/deploymentUtils.js index 82241e470..b484eac7e 100644 --- a/deploy/src/deploymentUtils.js +++ b/deploy/src/deploymentUtils.js @@ -46,7 +46,7 @@ async function deployContract(contractJson, args, { from, network, nonce }) { url, gasPrice }) - if (Web3Utils.hexToNumber(tx.status) !== 1) { + if (Web3Utils.hexToNumber(tx.status) !== 1 && !tx.contractAddress) { throw new Error('Tx failed') } instance.options.address = tx.contractAddress @@ -88,8 +88,7 @@ async function sendRawTx({ data, nonce, to, privateKey, url, gasPrice, value }) `0x${serializedTx.toString('hex')}` ) console.log('pending txHash', txHash) - const receipt = await getReceipt(txHash, url) - return receipt + return await getReceipt(txHash, url) } catch (e) { console.error(e) } @@ -147,6 +146,80 @@ function logValidatorsAndRewardAccounts(validators, rewards) { }) } +async function upgradeProxy({ proxy, implementationAddress, version, nonce, url }) { + const data = await proxy.methods.upgradeTo(version, implementationAddress).encodeABI() + const result = await sendRawTxHome({ + data, + nonce, + to: proxy.options.address, + privateKey: deploymentPrivateKey, + url + }) + if (result.status) { + assert.strictEqual(Web3Utils.hexToNumber(result.status), 1, 'Transaction Failed') + } else { + const implementation = await proxy.methods.implementation().call() + assert.strictEqual(implementation, implementationAddress, 'Transaction Failed') + } +} + +async function transferProxyOwnership({ proxy, newOwner, nonce, url }) { + const data = await proxy.methods.transferProxyOwnership(newOwner).encodeABI() + const result = await sendRawTxHome({ + data, + nonce, + to: proxy.options.address, + privateKey: deploymentPrivateKey, + url + }) + if (result.status) { + assert.strictEqual(Web3Utils.hexToNumber(result.status), 1, 'Transaction Failed') + } else { + const proxyOwner = await proxy.methods.proxyOwner().call() + assert.strictEqual(proxyOwner, newOwner, 'Transaction Failed') + } +} + +async function initializeValidators({ + contract, + isRewardableBridge, + requiredNumber, + validators, + rewardAccounts, + owner, + nonce, + url +}) { + let data + + if (isRewardableBridge) { + console.log(`REQUIRED_NUMBER_OF_VALIDATORS: ${requiredNumber}, HOME_VALIDATORS_OWNER: ${owner}`) + logValidatorsAndRewardAccounts(validators, rewardAccounts) + data = await contract.methods + .initialize(requiredNumber, validators, rewardAccounts, owner) + .encodeABI() + } else { + console.log( + `REQUIRED_NUMBER_OF_VALIDATORS: ${requiredNumber}, VALIDATORS: ${validators}, HOME_VALIDATORS_OWNER: ${owner}` + ) + data = await contract.methods.initialize(requiredNumber, validators, owner).encodeABI() + } + + const result = await sendRawTxHome({ + data, + nonce, + to: contract.options.address, + privateKey: deploymentPrivateKey, + url + }) + if (result.status) { + assert.strictEqual(Web3Utils.hexToNumber(result.status), 1, 'Transaction Failed') + } else { + const isInitialized = await contract.methods.isInitialized().call() + assert.strictEqual(isInitialized, true, 'Transaction Failed') + } +} + module.exports = { deployContract, sendNodeRequest, @@ -155,5 +228,8 @@ module.exports = { sendRawTxHome, sendRawTxForeign, privateKeyToAddress, - logValidatorsAndRewardAccounts + logValidatorsAndRewardAccounts, + upgradeProxy, + initializeValidators, + transferProxyOwnership } diff --git a/deploy/src/native_to_erc/home.js b/deploy/src/native_to_erc/home.js index 5e3011c6e..aff0faedb 100644 --- a/deploy/src/native_to_erc/home.js +++ b/deploy/src/native_to_erc/home.js @@ -6,7 +6,9 @@ const { deployContract, privateKeyToAddress, sendRawTxHome, - logValidatorsAndRewardAccounts + upgradeProxy, + initializeValidators, + transferProxyOwnership } = require('../deploymentUtils') const { web3Home, deploymentPrivateKey, HOME_RPC_URL } = require('../web3') @@ -43,122 +45,9 @@ const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVAT const isBothDirectionsFeeManager = HOME_REWARDABLE === 'BOTH_DIRECTIONS' const isRewardableBridge = HOME_REWARDABLE === 'ONE_DIRECTION' || isBothDirectionsFeeManager -async function deployHome() { - let homeNonce = await web3Home.eth.getTransactionCount(DEPLOYMENT_ACCOUNT_ADDRESS) - console.log('deploying storage for home validators') - const storageValidatorsHome = await deployContract(EternalStorageProxy, [], { - from: DEPLOYMENT_ACCOUNT_ADDRESS, - nonce: homeNonce - }) - console.log('[Home] BridgeValidators Storage: ', storageValidatorsHome.options.address) - homeNonce++ - - console.log('\ndeploying implementation for home validators') - const bridgeValidatorsContract = isRewardableBridge ? RewardableValidators : BridgeValidators - const bridgeValidatorsHome = await deployContract(bridgeValidatorsContract, [], { - from: DEPLOYMENT_ACCOUNT_ADDRESS, - nonce: homeNonce - }) - console.log('[Home] BridgeValidators Implementation: ', bridgeValidatorsHome.options.address) - homeNonce++ - - console.log('\nhooking up eternal storage to BridgeValidators') - const upgradeToBridgeVHomeData = await storageValidatorsHome.methods - .upgradeTo('1', bridgeValidatorsHome.options.address) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txUpgradeToBridgeVHome = await sendRawTxHome({ - data: upgradeToBridgeVHomeData, - nonce: homeNonce, - to: storageValidatorsHome.options.address, - privateKey: deploymentPrivateKey, - url: HOME_RPC_URL - }) - assert.strictEqual(Web3Utils.hexToNumber(txUpgradeToBridgeVHome.status), 1, 'Transaction Failed') - homeNonce++ - - console.log('\ninitializing Home Bridge Validators with following parameters:\n') - bridgeValidatorsHome.options.address = storageValidatorsHome.options.address - - let initializeData - - if (isRewardableBridge) { - console.log( - `REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, HOME_VALIDATORS_OWNER: ${HOME_VALIDATORS_OWNER}` - ) - logValidatorsAndRewardAccounts(VALIDATORS, VALIDATORS_REWARD_ACCOUNTS) - initializeData = await bridgeValidatorsHome.methods - .initialize( - REQUIRED_NUMBER_OF_VALIDATORS, - VALIDATORS, - VALIDATORS_REWARD_ACCOUNTS, - HOME_VALIDATORS_OWNER - ) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - } else { - console.log( - `REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, VALIDATORS: ${VALIDATORS}, HOME_VALIDATORS_OWNER: ${HOME_VALIDATORS_OWNER}` - ) - initializeData = await bridgeValidatorsHome.methods - .initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, HOME_VALIDATORS_OWNER) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - } - - const txInitialize = await sendRawTxHome({ - data: initializeData, - nonce: homeNonce, - to: bridgeValidatorsHome.options.address, - privateKey: deploymentPrivateKey, - url: HOME_RPC_URL - }) - assert.strictEqual(Web3Utils.hexToNumber(txInitialize.status), 1, 'Transaction Failed') - homeNonce++ - - console.log('transferring proxy ownership to multisig for Validators Proxy contract') - const proxyDataTransfer = await storageValidatorsHome.methods - .transferProxyOwnership(HOME_UPGRADEABLE_ADMIN) - .encodeABI() - const txProxyDataTransfer = await sendRawTxHome({ - data: proxyDataTransfer, - nonce: homeNonce, - to: storageValidatorsHome.options.address, - privateKey: deploymentPrivateKey, - url: HOME_RPC_URL - }) - assert.strictEqual(Web3Utils.hexToNumber(txProxyDataTransfer.status), 1, 'Transaction Failed') - homeNonce++ - - console.log('\ndeploying homeBridge storage\n') - const homeBridgeStorage = await deployContract(EternalStorageProxy, [], { - from: DEPLOYMENT_ACCOUNT_ADDRESS, - nonce: homeNonce - }) - homeNonce++ - console.log('[Home] HomeBridge Storage: ', homeBridgeStorage.options.address) - - console.log('\ndeploying homeBridge implementation\n') - const homeBridgeImplementation = await deployContract(HomeBridge, [], { - from: DEPLOYMENT_ACCOUNT_ADDRESS, - nonce: homeNonce - }) - homeNonce++ - console.log('[Home] HomeBridge Implementation: ', homeBridgeImplementation.options.address) - - console.log('\nhooking up HomeBridge storage to HomeBridge implementation') - const upgradeToHomeBridgeData = await homeBridgeStorage.methods - .upgradeTo('1', homeBridgeImplementation.options.address) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txUpgradeToHomeBridge = await sendRawTxHome({ - data: upgradeToHomeBridgeData, - nonce: homeNonce, - to: homeBridgeStorage.options.address, - privateKey: deploymentPrivateKey, - url: HOME_RPC_URL - }) - assert.strictEqual(Web3Utils.hexToNumber(txUpgradeToHomeBridge.status), 1, 'Transaction Failed') - homeNonce++ - +async function initializeBridge({ validatorsBridge, bridge, initialNonce }) { + let nonce = initialNonce let initializeHomeBridgeData - homeBridgeImplementation.options.address = homeBridgeStorage.options.address if (isRewardableBridge) { console.log('\ndeploying implementation for fee manager') @@ -167,17 +56,17 @@ async function deployHome() { : FeeManagerNativeToErc const feeManager = await deployContract(feeManagerContract, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, - nonce: homeNonce + nonce }) console.log('[Home] feeManager Implementation: ', feeManager.options.address) - homeNonce++ + nonce++ const homeFee = isBothDirectionsFeeManager ? HOME_TRANSACTIONS_FEE.toString() : '0' const homeFeeInWei = Web3Utils.toWei(homeFee, 'ether') const foreignFeeInWei = Web3Utils.toWei(FOREIGN_TRANSACTIONS_FEE.toString(), 'ether') console.log('\ninitializing Home Bridge with fee contract:\n') - console.log(`Home Validators: ${storageValidatorsHome.options.address}, + console.log(`Home Validators: ${validatorsBridge.options.address}, HOME_DAILY_LIMIT : ${HOME_DAILY_LIMIT} which is ${Web3Utils.fromWei(HOME_DAILY_LIMIT)} in eth, HOME_MAX_AMOUNT_PER_TX: ${HOME_MAX_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( HOME_MAX_AMOUNT_PER_TX @@ -197,10 +86,9 @@ async function deployHome() { Home Fee: ${homeFeeInWei} which is ${homeFee * 100}% Foreign Fee: ${foreignFeeInWei} which is ${FOREIGN_TRANSACTIONS_FEE * 100}%`) - homeBridgeImplementation.options.address = homeBridgeStorage.options.address - initializeHomeBridgeData = await homeBridgeImplementation.methods + initializeHomeBridgeData = await bridge.methods .rewardableInitialize( - storageValidatorsHome.options.address, + validatorsBridge.options.address, HOME_DAILY_LIMIT, HOME_MAX_AMOUNT_PER_TX, HOME_MIN_AMOUNT_PER_TX, @@ -213,10 +101,10 @@ async function deployHome() { homeFeeInWei, foreignFeeInWei ) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + .encodeABI() } else { console.log('\ninitializing Home Bridge with following parameters:\n') - console.log(`Home Validators: ${storageValidatorsHome.options.address}, + console.log(`Home Validators: ${validatorsBridge.options.address}, HOME_DAILY_LIMIT : ${HOME_DAILY_LIMIT} which is ${Web3Utils.fromWei(HOME_DAILY_LIMIT)} in eth, HOME_MAX_AMOUNT_PER_TX: ${HOME_MAX_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( HOME_MAX_AMOUNT_PER_TX @@ -233,10 +121,9 @@ async function deployHome() { )} in eth, HOME_BRIDGE_OWNER: ${HOME_BRIDGE_OWNER} `) - homeBridgeImplementation.options.address = homeBridgeStorage.options.address - initializeHomeBridgeData = await homeBridgeImplementation.methods + initializeHomeBridgeData = await bridge.methods .initialize( - storageValidatorsHome.options.address, + validatorsBridge.options.address, HOME_DAILY_LIMIT, HOME_MAX_AMOUNT_PER_TX, HOME_MIN_AMOUNT_PER_TX, @@ -246,32 +133,124 @@ async function deployHome() { FOREIGN_MAX_AMOUNT_PER_TX, HOME_BRIDGE_OWNER ) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + .encodeABI() } const txInitializeHomeBridge = await sendRawTxHome({ data: initializeHomeBridgeData, - nonce: homeNonce, - to: homeBridgeStorage.options.address, + nonce, + to: bridge.options.address, privateKey: deploymentPrivateKey, url: HOME_RPC_URL }) - assert.strictEqual(Web3Utils.hexToNumber(txInitializeHomeBridge.status), 1, 'Transaction Failed') - homeNonce++ + if (txInitializeHomeBridge.status) { + assert.strictEqual( + Web3Utils.hexToNumber(txInitializeHomeBridge.status), + 1, + 'Transaction Failed' + ) + } else { + const isInitialized = await bridge.methods.isInitialized().call() + assert.strictEqual(isInitialized, true, 'Transaction Failed') + } + nonce++ + + return nonce +} + +async function deployHome() { + let nonce = await web3Home.eth.getTransactionCount(DEPLOYMENT_ACCOUNT_ADDRESS) + + console.log('deploying storage for home validators') + const storageValidatorsHome = await deployContract(EternalStorageProxy, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + nonce + }) + console.log('[Home] BridgeValidators Storage: ', storageValidatorsHome.options.address) + nonce++ + + console.log('\ndeploying implementation for home validators') + const bridgeValidatorsContract = isRewardableBridge ? RewardableValidators : BridgeValidators + const bridgeValidatorsHome = await deployContract(bridgeValidatorsContract, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + nonce + }) + console.log('[Home] BridgeValidators Implementation: ', bridgeValidatorsHome.options.address) + nonce++ + + console.log('\nhooking up eternal storage to BridgeValidators') + await upgradeProxy({ + proxy: storageValidatorsHome, + implementationAddress: bridgeValidatorsHome.options.address, + version: '1', + nonce, + url: HOME_RPC_URL + }) + nonce++ + + console.log('\ninitializing Home Bridge Validators with following parameters:\n') + bridgeValidatorsHome.options.address = storageValidatorsHome.options.address + await initializeValidators({ + contract: bridgeValidatorsHome, + isRewardableBridge, + requiredNumber: REQUIRED_NUMBER_OF_VALIDATORS, + validators: VALIDATORS, + rewardAccounts: VALIDATORS_REWARD_ACCOUNTS, + owner: HOME_VALIDATORS_OWNER, + nonce, + url: HOME_RPC_URL + }) + nonce++ + + console.log('transferring proxy ownership to multisig for Validators Proxy contract') + await transferProxyOwnership({ + proxy: storageValidatorsHome, + newOwner: HOME_UPGRADEABLE_ADMIN, + nonce, + url: HOME_RPC_URL + }) + nonce++ + + console.log('\ndeploying homeBridge storage\n') + const homeBridgeStorage = await deployContract(EternalStorageProxy, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + nonce + }) + nonce++ + console.log('[Home] HomeBridge Storage: ', homeBridgeStorage.options.address) + + console.log('\ndeploying homeBridge implementation\n') + const homeBridgeImplementation = await deployContract(HomeBridge, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + nonce + }) + nonce++ + console.log('[Home] HomeBridge Implementation: ', homeBridgeImplementation.options.address) + + console.log('\nhooking up HomeBridge storage to HomeBridge implementation') + await upgradeProxy({ + proxy: homeBridgeStorage, + implementationAddress: homeBridgeImplementation.options.address, + version: '1', + nonce, + url: HOME_RPC_URL + }) + nonce++ + + homeBridgeImplementation.options.address = homeBridgeStorage.options.address + nonce = await initializeBridge({ + validatorsBridge: storageValidatorsHome, + bridge: homeBridgeImplementation, + initialNonce: nonce + }) console.log('transferring proxy ownership to multisig for Home bridge Proxy contract') - const homeBridgeProxyData = await homeBridgeStorage.methods - .transferProxyOwnership(HOME_UPGRADEABLE_ADMIN) - .encodeABI() - const txhomeBridgeProxyData = await sendRawTxHome({ - data: homeBridgeProxyData, - nonce: homeNonce, - to: homeBridgeStorage.options.address, - privateKey: deploymentPrivateKey, + await transferProxyOwnership({ + proxy: homeBridgeStorage, + newOwner: HOME_UPGRADEABLE_ADMIN, + nonce, url: HOME_RPC_URL }) - assert.strictEqual(Web3Utils.hexToNumber(txhomeBridgeProxyData.status), 1, 'Transaction Failed') - homeNonce++ console.log('\nHome Deployment Bridge completed\n') return { From f016a25075d0c2ee78170fb6f69e485bf6bd3771 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 27 Feb 2019 12:19:51 -0300 Subject: [PATCH 106/187] update foreign native-to-erc deploy script --- deploy/src/deploymentUtils.js | 41 ++- deploy/src/native_to_erc/foreign.js | 384 +++++++++++++--------------- 2 files changed, 215 insertions(+), 210 deletions(-) diff --git a/deploy/src/deploymentUtils.js b/deploy/src/deploymentUtils.js index b484eac7e..4bc1749df 100644 --- a/deploy/src/deploymentUtils.js +++ b/deploy/src/deploymentUtils.js @@ -180,6 +180,40 @@ async function transferProxyOwnership({ proxy, newOwner, nonce, url }) { } } +async function transferOwnership({ contract, newOwner, nonce, url }) { + const data = await contract.methods.transferOwnership(newOwner).encodeABI() + const result = await sendRawTxForeign({ + data, + nonce, + to: contract.options.address, + privateKey: deploymentPrivateKey, + url + }) + if (result.status) { + assert.strictEqual(Web3Utils.hexToNumber(result.status), 1, 'Transaction Failed') + } else { + const owner = await contract.methods.owner().call() + assert.strictEqual(owner, newOwner, 'Transaction Failed') + } +} + +async function setBridgeContract({ contract, bridgeAddress, nonce }) { + const data = await contract.methods.setBridgeContract(bridgeAddress).encodeABI() + const result = await sendRawTxForeign({ + data, + nonce, + to: contract.options.address, + privateKey: deploymentPrivateKey, + url: FOREIGN_RPC_URL + }) + if (result.status) { + assert.strictEqual(Web3Utils.hexToNumber(result.status), 1, 'Transaction Failed') + } else { + const bridgeContract = await contract.methods.bridgeContract().call() + assert.strictEqual(bridgeContract, bridgeAddress, 'Transaction Failed') + } +} + async function initializeValidators({ contract, isRewardableBridge, @@ -222,14 +256,13 @@ async function initializeValidators({ module.exports = { deployContract, - sendNodeRequest, - getReceipt, - sendRawTx, sendRawTxHome, sendRawTxForeign, privateKeyToAddress, logValidatorsAndRewardAccounts, upgradeProxy, initializeValidators, - transferProxyOwnership + transferProxyOwnership, + transferOwnership, + setBridgeContract } diff --git a/deploy/src/native_to_erc/foreign.js b/deploy/src/native_to_erc/foreign.js index 8cfc3e567..a4a3051b9 100644 --- a/deploy/src/native_to_erc/foreign.js +++ b/deploy/src/native_to_erc/foreign.js @@ -6,7 +6,11 @@ const { deployContract, privateKeyToAddress, sendRawTxForeign, - logValidatorsAndRewardAccounts + upgradeProxy, + initializeValidators, + transferProxyOwnership, + transferOwnership, + setBridgeContract } = require('../deploymentUtils') const { web3Foreign, deploymentPrivateKey, FOREIGN_RPC_URL } = require('../web3') @@ -48,172 +52,24 @@ const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVAT const isRewardableBridge = FOREIGN_REWARDABLE === 'ONE_DIRECTION' -async function deployForeign() { - let foreignNonce = await web3Foreign.eth.getTransactionCount(DEPLOYMENT_ACCOUNT_ADDRESS) - console.log('========================================') - console.log('deploying ForeignBridge') - console.log('========================================\n') - - console.log('\n[Foreign] deploying BRIDGEABLE_TOKEN_SYMBOL token') - const erc677bridgeToken = await deployContract( - DEPLOY_REWARDABLE_TOKEN ? ERC677BridgeTokenRewardable : ERC677BridgeToken, - [BRIDGEABLE_TOKEN_NAME, BRIDGEABLE_TOKEN_SYMBOL, BRIDGEABLE_TOKEN_DECIMALS], - { from: DEPLOYMENT_ACCOUNT_ADDRESS, network: 'foreign', nonce: foreignNonce } - ) - foreignNonce++ - console.log('[Foreign] BRIDGEABLE_TOKEN_SYMBOL: ', erc677bridgeToken.options.address) - - console.log('deploying storage for foreign validators') - const storageValidatorsForeign = await deployContract(EternalStorageProxy, [], { - from: DEPLOYMENT_ACCOUNT_ADDRESS, - network: 'foreign', - nonce: foreignNonce - }) - foreignNonce++ - console.log('[Foreign] BridgeValidators Storage: ', storageValidatorsForeign.options.address) - - console.log('\ndeploying implementation for foreign validators') - const bridgeValidatorsContract = isRewardableBridge ? RewardableValidators : BridgeValidators - const bridgeValidatorsForeign = await deployContract(bridgeValidatorsContract, [], { - from: DEPLOYMENT_ACCOUNT_ADDRESS, - network: 'foreign', - nonce: foreignNonce - }) - foreignNonce++ - console.log( - '[Foreign] BridgeValidators Implementation: ', - bridgeValidatorsForeign.options.address - ) - - console.log('\nhooking up eternal storage to BridgeValidators') - const upgradeToBridgeVForeignData = await storageValidatorsForeign.methods - .upgradeTo('1', bridgeValidatorsForeign.options.address) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txUpgradeToBridgeVForeign = await sendRawTxForeign({ - data: upgradeToBridgeVForeignData, - nonce: foreignNonce, - to: storageValidatorsForeign.options.address, - privateKey: deploymentPrivateKey, - url: FOREIGN_RPC_URL - }) - assert.strictEqual( - Web3Utils.hexToNumber(txUpgradeToBridgeVForeign.status), - 1, - 'Transaction Failed' - ) - foreignNonce++ - - console.log('\ninitializing Foreign Bridge Validators with following parameters:\n') - bridgeValidatorsForeign.options.address = storageValidatorsForeign.options.address - - let initializeForeignData - - if (isRewardableBridge) { - console.log( - `REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, FOREIGN_VALIDATORS_OWNER: ${FOREIGN_VALIDATORS_OWNER}` - ) - logValidatorsAndRewardAccounts(VALIDATORS, VALIDATORS_REWARD_ACCOUNTS) - initializeForeignData = await bridgeValidatorsForeign.methods - .initialize( - REQUIRED_NUMBER_OF_VALIDATORS, - VALIDATORS, - VALIDATORS_REWARD_ACCOUNTS, - FOREIGN_VALIDATORS_OWNER - ) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - } else { - console.log( - `REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, VALIDATORS: ${VALIDATORS}, FOREIGN_VALIDATORS_OWNER: ${FOREIGN_VALIDATORS_OWNER}` - ) - initializeForeignData = await bridgeValidatorsForeign.methods - .initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, FOREIGN_VALIDATORS_OWNER) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - } - - const txInitializeForeign = await sendRawTxForeign({ - data: initializeForeignData, - nonce: foreignNonce, - to: bridgeValidatorsForeign.options.address, - privateKey: deploymentPrivateKey, - url: FOREIGN_RPC_URL - }) - assert.strictEqual(Web3Utils.hexToNumber(txInitializeForeign.status), 1, 'Transaction Failed') - foreignNonce++ - - console.log('\nTransferring ownership of ValidatorsProxy\n') - const validatorsForeignOwnershipData = await storageValidatorsForeign.methods - .transferProxyOwnership(FOREIGN_UPGRADEABLE_ADMIN) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txValidatorsForeignOwnershipData = await sendRawTxForeign({ - data: validatorsForeignOwnershipData, - nonce: foreignNonce, - to: storageValidatorsForeign.options.address, - privateKey: deploymentPrivateKey, - url: FOREIGN_RPC_URL - }) - assert.strictEqual( - Web3Utils.hexToNumber(txValidatorsForeignOwnershipData.status), - 1, - 'Transaction Failed' - ) - foreignNonce++ - - console.log('\ndeploying foreignBridge storage\n') - const foreignBridgeStorage = await deployContract(EternalStorageProxy, [], { - from: DEPLOYMENT_ACCOUNT_ADDRESS, - network: 'foreign', - nonce: foreignNonce - }) - foreignNonce++ - console.log('[Foreign] ForeignBridge Storage: ', foreignBridgeStorage.options.address) - - console.log('\ndeploying foreignBridge implementation\n') - const foreignBridgeImplementation = await deployContract(ForeignBridge, [], { - from: DEPLOYMENT_ACCOUNT_ADDRESS, - network: 'foreign', - nonce: foreignNonce - }) - foreignNonce++ - console.log( - '[Foreign] ForeignBridge Implementation: ', - foreignBridgeImplementation.options.address - ) - - console.log('\nhooking up ForeignBridge storage to ForeignBridge implementation') - const upgradeToForeignBridgeData = await foreignBridgeStorage.methods - .upgradeTo('1', foreignBridgeImplementation.options.address) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txUpgradeToForeignBridge = await sendRawTxForeign({ - data: upgradeToForeignBridgeData, - nonce: foreignNonce, - to: foreignBridgeStorage.options.address, - privateKey: deploymentPrivateKey, - url: FOREIGN_RPC_URL - }) - assert.strictEqual( - Web3Utils.hexToNumber(txUpgradeToForeignBridge.status), - 1, - 'Transaction Failed' - ) - foreignNonce++ - +async function initializeBridge({ validatorsBridge, bridge, erc677bridgeToken, initialNonce }) { + let nonce = initialNonce let initializeFBridgeData - foreignBridgeImplementation.options.address = foreignBridgeStorage.options.address if (isRewardableBridge) { console.log('\ndeploying implementation for fee manager') const feeManager = await deployContract(FeeManagerNativeToErc, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, network: 'foreign', - nonce: foreignNonce + nonce }) console.log('[Foreign] feeManager Implementation: ', feeManager.options.address) - foreignNonce++ + nonce++ const homeFeeInWei = Web3Utils.toWei(HOME_TRANSACTIONS_FEE.toString(), 'ether') console.log('\ninitializing Foreign Bridge with fee contract:\n') - console.log(`Foreign Validators: ${storageValidatorsForeign.options.address}, + console.log(`Foreign Validators: ${validatorsBridge.options.address}, FOREIGN_DAILY_LIMIT : ${FOREIGN_DAILY_LIMIT} which is ${Web3Utils.fromWei( FOREIGN_DAILY_LIMIT )} in eth, @@ -232,9 +88,9 @@ async function deployForeign() { Fee Manager: ${feeManager.options.address}, Home Fee: ${homeFeeInWei} which is ${HOME_TRANSACTIONS_FEE * 100}%`) - initializeFBridgeData = await foreignBridgeImplementation.methods + initializeFBridgeData = await bridge.methods .rewardableInitialize( - storageValidatorsForeign.options.address, + validatorsBridge.options.address, erc677bridgeToken.options.address, FOREIGN_DAILY_LIMIT, FOREIGN_MAX_AMOUNT_PER_TX, @@ -250,7 +106,7 @@ async function deployForeign() { .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) } else { console.log('\ninitializing Foreign Bridge with following parameters:\n') - console.log(`Foreign Validators: ${storageValidatorsForeign.options.address}, + console.log(`Foreign Validators: ${validatorsBridge.options.address}, FOREIGN_DAILY_LIMIT : ${FOREIGN_DAILY_LIMIT} which is ${Web3Utils.fromWei( FOREIGN_DAILY_LIMIT )} in eth, @@ -268,9 +124,9 @@ async function deployForeign() { FOREIGN_BRIDGE_OWNER: ${FOREIGN_BRIDGE_OWNER} `) - initializeFBridgeData = await foreignBridgeImplementation.methods + initializeFBridgeData = await bridge.methods .initialize( - storageValidatorsForeign.options.address, + validatorsBridge.options.address, erc677bridgeToken.options.address, FOREIGN_DAILY_LIMIT, FOREIGN_MAX_AMOUNT_PER_TX, @@ -286,92 +142,208 @@ async function deployForeign() { const txInitializeBridge = await sendRawTxForeign({ data: initializeFBridgeData, - nonce: foreignNonce, - to: foreignBridgeStorage.options.address, + nonce, + to: bridge.options.address, privateKey: deploymentPrivateKey, url: FOREIGN_RPC_URL }) - assert.strictEqual(Web3Utils.hexToNumber(txInitializeBridge.status), 1, 'Transaction Failed') - foreignNonce++ + if (txInitializeBridge.status) { + assert.strictEqual(Web3Utils.hexToNumber(txInitializeBridge.status), 1, 'Transaction Failed') + } else { + const isInitialized = await bridge.methods.isInitialized().call() + assert.strictEqual(isInitialized, true, 'Transaction Failed') + } + nonce++ - console.log('\nset bridge contract on ERC677BridgeToken') - const setBridgeContractData = await erc677bridgeToken.methods - .setBridgeContract(foreignBridgeStorage.options.address) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const setBridgeContract = await sendRawTxForeign({ - data: setBridgeContractData, - nonce: foreignNonce, - to: erc677bridgeToken.options.address, - privateKey: deploymentPrivateKey, + return nonce +} + +async function deployForeign() { + let nonce = await web3Foreign.eth.getTransactionCount(DEPLOYMENT_ACCOUNT_ADDRESS) + console.log('========================================') + console.log('deploying ForeignBridge') + console.log('========================================\n') + + console.log('\n[Foreign] deploying BRIDGEABLE_TOKEN_SYMBOL token') + const erc677bridgeToken = await deployContract( + DEPLOY_REWARDABLE_TOKEN ? ERC677BridgeTokenRewardable : ERC677BridgeToken, + [BRIDGEABLE_TOKEN_NAME, BRIDGEABLE_TOKEN_SYMBOL, BRIDGEABLE_TOKEN_DECIMALS], + { from: DEPLOYMENT_ACCOUNT_ADDRESS, network: 'foreign', nonce } + ) + nonce++ + console.log('[Foreign] BRIDGEABLE_TOKEN_SYMBOL: ', erc677bridgeToken.options.address) + + console.log('\ndeploying storage for foreign validators') + const storageValidatorsForeign = await deployContract(EternalStorageProxy, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + network: 'foreign', + nonce + }) + nonce++ + console.log('[Foreign] BridgeValidators Storage: ', storageValidatorsForeign.options.address) + + console.log('\ndeploying implementation for foreign validators') + const bridgeValidatorsContract = isRewardableBridge ? RewardableValidators : BridgeValidators + const bridgeValidatorsForeign = await deployContract(bridgeValidatorsContract, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + network: 'foreign', + nonce + }) + nonce++ + console.log( + '[Foreign] BridgeValidators Implementation: ', + bridgeValidatorsForeign.options.address + ) + + console.log('\nhooking up eternal storage to BridgeValidators') + await upgradeProxy({ + proxy: storageValidatorsForeign, + implementationAddress: bridgeValidatorsForeign.options.address, + version: '1', + nonce, + url: FOREIGN_RPC_URL + }) + nonce++ + + console.log('\ninitializing Foreign Bridge Validators with following parameters:\n') + bridgeValidatorsForeign.options.address = storageValidatorsForeign.options.address + await initializeValidators({ + contract: bridgeValidatorsForeign, + isRewardableBridge, + requiredNumber: REQUIRED_NUMBER_OF_VALIDATORS, + validators: VALIDATORS, + rewardAccounts: VALIDATORS_REWARD_ACCOUNTS, + owner: FOREIGN_VALIDATORS_OWNER, + nonce, url: FOREIGN_RPC_URL }) - assert.strictEqual(Web3Utils.hexToNumber(setBridgeContract.status), 1, 'Transaction Failed') - foreignNonce++ + nonce++ + + console.log('\nTransferring ownership of ValidatorsProxy\n') + await transferProxyOwnership({ + proxy: storageValidatorsForeign, + newOwner: FOREIGN_UPGRADEABLE_ADMIN, + nonce, + url: FOREIGN_RPC_URL + }) + nonce++ + + console.log('\ndeploying foreignBridge storage\n') + const foreignBridgeStorage = await deployContract(EternalStorageProxy, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + network: 'foreign', + nonce + }) + nonce++ + console.log('[Foreign] ForeignBridge Storage: ', foreignBridgeStorage.options.address) + + console.log('\ndeploying foreignBridge implementation\n') + const foreignBridgeImplementation = await deployContract(ForeignBridge, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + network: 'foreign', + nonce + }) + nonce++ + console.log( + '[Foreign] ForeignBridge Implementation: ', + foreignBridgeImplementation.options.address + ) + + console.log('\nhooking up ForeignBridge storage to ForeignBridge implementation') + await upgradeProxy({ + proxy: foreignBridgeStorage, + implementationAddress: foreignBridgeImplementation.options.address, + version: '1', + nonce, + url: FOREIGN_RPC_URL + }) + nonce++ + + foreignBridgeImplementation.options.address = foreignBridgeStorage.options.address + nonce = await initializeBridge({ + validatorsBridge: storageValidatorsForeign, + bridge: foreignBridgeImplementation, + erc677bridgeToken, + initialNonce: nonce + }) + + console.log('\nset bridge contract on ERC677BridgeToken') + await setBridgeContract({ + contract: erc677bridgeToken, + bridgeAddress: foreignBridgeStorage.options.address, + nonce + }) + nonce++ if (DEPLOY_REWARDABLE_TOKEN) { console.log('\nset BlockReward contract on ERC677BridgeTokenRewardable') const setBlockRewardContractData = await erc677bridgeToken.methods .setBlockRewardContract(BLOCK_REWARD_ADDRESS) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + .encodeABI() const setBlockRewardContract = await sendRawTxForeign({ data: setBlockRewardContractData, - nonce: foreignNonce, + nonce, to: erc677bridgeToken.options.address, privateKey: deploymentPrivateKey, url: FOREIGN_RPC_URL }) - assert.strictEqual( - Web3Utils.hexToNumber(setBlockRewardContract.status), - 1, - 'Transaction Failed' - ) - foreignNonce++ + if (setBlockRewardContract.status) { + assert.strictEqual( + Web3Utils.hexToNumber(setBlockRewardContract.status), + 1, + 'Transaction Failed' + ) + } else { + const blockRewardContract = await erc677bridgeToken.methods.blockRewardContract().call() + assert.strictEqual(blockRewardContract, BLOCK_REWARD_ADDRESS, 'Transaction Failed') + } + nonce++ console.log('\nset ValidatorSet contract on ERC677BridgeTokenRewardable') const setValidatorSetContractData = await erc677bridgeToken.methods .setValidatorSetContract(DPOS_VALIDATOR_SET_ADDRESS) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + .encodeABI() const setValidatorSetContract = await sendRawTxForeign({ data: setValidatorSetContractData, - nonce: foreignNonce, + nonce, to: erc677bridgeToken.options.address, privateKey: deploymentPrivateKey, url: FOREIGN_RPC_URL }) + if (setValidatorSetContract.status) { + assert.strictEqual( + Web3Utils.hexToNumber(setValidatorSetContract.status), + 1, + 'Transaction Failed' + ) + } else { + const validatorSetContract = await erc677bridgeToken.methods.validatorSetContract().call() + assert.strictEqual(validatorSetContract, DPOS_VALIDATOR_SET_ADDRESS, 'Transaction Failed') + } assert.strictEqual( Web3Utils.hexToNumber(setValidatorSetContract.status), 1, 'Transaction Failed' ) - foreignNonce++ + nonce++ } console.log('transferring ownership of ERC677BridgeToken token to foreignBridge contract') - const txOwnershipData = await erc677bridgeToken.methods - .transferOwnership(foreignBridgeStorage.options.address) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txOwnership = await sendRawTxForeign({ - data: txOwnershipData, - nonce: foreignNonce, - to: erc677bridgeToken.options.address, - privateKey: deploymentPrivateKey, + await transferOwnership({ + contract: erc677bridgeToken, + newOwner: foreignBridgeStorage.options.address, + nonce, url: FOREIGN_RPC_URL }) - assert.strictEqual(Web3Utils.hexToNumber(txOwnership.status), 1, 'Transaction Failed') - foreignNonce++ - - const bridgeOwnershipData = await foreignBridgeStorage.methods - .transferProxyOwnership(FOREIGN_UPGRADEABLE_ADMIN) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txBridgeOwnershipData = await sendRawTxForeign({ - data: bridgeOwnershipData, - nonce: foreignNonce, - to: foreignBridgeStorage.options.address, - privateKey: deploymentPrivateKey, + nonce++ + + console.log('transferring proxy ownership to multisig for foreign bridge Proxy contract') + await transferProxyOwnership({ + proxy: foreignBridgeStorage, + newOwner: FOREIGN_UPGRADEABLE_ADMIN, + nonce, url: FOREIGN_RPC_URL }) - assert.strictEqual(Web3Utils.hexToNumber(txBridgeOwnershipData.status), 1, 'Transaction Failed') - foreignNonce++ console.log('\nForeign Deployment Bridge completed\n') return { From b0d2e362d0865faab0b25b650ffac954402eca78 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 27 Feb 2019 12:22:04 -0300 Subject: [PATCH 107/187] add .idea to .gitignore --- .gitignore | 1 + 1 file changed, 1 insertion(+) diff --git a/.gitignore b/.gitignore index de8a6acc7..ef58a67d8 100644 --- a/.gitignore +++ b/.gitignore @@ -2,3 +2,4 @@ node_modules build flats .node* +.idea From afe54073873229da2c38616c55e69b5a0f149e38 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 27 Feb 2019 14:06:12 -0300 Subject: [PATCH 108/187] Update erc-to-erc deploy script --- deploy/src/deploymentUtils.js | 4 +- deploy/src/erc_to_erc/foreign.js | 181 ++++++++++++------------- deploy/src/erc_to_erc/home.js | 225 +++++++++++++++---------------- 3 files changed, 192 insertions(+), 218 deletions(-) diff --git a/deploy/src/deploymentUtils.js b/deploy/src/deploymentUtils.js index 4bc1749df..6328e0a5a 100644 --- a/deploy/src/deploymentUtils.js +++ b/deploy/src/deploymentUtils.js @@ -197,14 +197,14 @@ async function transferOwnership({ contract, newOwner, nonce, url }) { } } -async function setBridgeContract({ contract, bridgeAddress, nonce }) { +async function setBridgeContract({ contract, bridgeAddress, nonce, url }) { const data = await contract.methods.setBridgeContract(bridgeAddress).encodeABI() const result = await sendRawTxForeign({ data, nonce, to: contract.options.address, privateKey: deploymentPrivateKey, - url: FOREIGN_RPC_URL + url }) if (result.status) { assert.strictEqual(Web3Utils.hexToNumber(result.status), 1, 'Transaction Failed') diff --git a/deploy/src/erc_to_erc/foreign.js b/deploy/src/erc_to_erc/foreign.js index 6dc7d81f9..c8a9aea16 100644 --- a/deploy/src/erc_to_erc/foreign.js +++ b/deploy/src/erc_to_erc/foreign.js @@ -2,7 +2,14 @@ const assert = require('assert') const Web3Utils = require('web3-utils') const env = require('../loadEnv') -const { deployContract, privateKeyToAddress, sendRawTxForeign } = require('../deploymentUtils') +const { + deployContract, + privateKeyToAddress, + sendRawTxForeign, + upgradeProxy, + initializeValidators, + transferProxyOwnership +} = require('../deploymentUtils') const { web3Foreign, deploymentPrivateKey, FOREIGN_RPC_URL } = require('../web3') const EternalStorageProxy = require('../../../build/contracts/EternalStorageProxy.json') @@ -27,11 +34,41 @@ const { const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVATE_KEY) +async function initializeBridge({ validatorsBridge, bridge, nonce }) { + console.log(`Foreign Validators: ${validatorsBridge.options.address}, + `) + const initializeFBridgeData = await bridge.methods + .initialize( + validatorsBridge.options.address, + ERC20_TOKEN_ADDRESS, + FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS, + FOREIGN_GAS_PRICE, + FOREIGN_MAX_AMOUNT_PER_TX, + HOME_DAILY_LIMIT, + HOME_MAX_AMOUNT_PER_TX, + FOREIGN_BRIDGE_OWNER + ) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + const txInitializeBridge = await sendRawTxForeign({ + data: initializeFBridgeData, + nonce, + to: bridge.options.address, + privateKey: deploymentPrivateKey, + url: FOREIGN_RPC_URL + }) + if (txInitializeBridge.status) { + assert.strictEqual(Web3Utils.hexToNumber(txInitializeBridge.status), 1, 'Transaction Failed') + } else { + const isInitialized = await bridge.methods.isInitialized().call() + assert.strictEqual(isInitialized, true, 'Transaction Failed') + } +} + async function deployForeign() { if (!Web3Utils.isAddress(ERC20_TOKEN_ADDRESS)) { throw new Error('ERC20_TOKEN_ADDRESS env var is not defined') } - let foreignNonce = await web3Foreign.eth.getTransactionCount(DEPLOYMENT_ACCOUNT_ADDRESS) + let nonce = await web3Foreign.eth.getTransactionCount(DEPLOYMENT_ACCOUNT_ADDRESS) console.log('========================================') console.log('deploying ForeignBridge') console.log('========================================\n') @@ -40,154 +77,102 @@ async function deployForeign() { const storageValidatorsForeign = await deployContract(EternalStorageProxy, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, network: 'foreign', - nonce: foreignNonce + nonce }) - foreignNonce++ + nonce++ console.log('[Foreign] BridgeValidators Storage: ', storageValidatorsForeign.options.address) console.log('\ndeploying implementation for foreign validators') const bridgeValidatorsForeign = await deployContract(BridgeValidators, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, network: 'foreign', - nonce: foreignNonce + nonce }) - foreignNonce++ + nonce++ console.log( '[Foreign] BridgeValidators Implementation: ', bridgeValidatorsForeign.options.address ) console.log('\nhooking up eternal storage to BridgeValidators') - const upgradeToBridgeVForeignData = await storageValidatorsForeign.methods - .upgradeTo('1', bridgeValidatorsForeign.options.address) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txUpgradeToBridgeVForeign = await sendRawTxForeign({ - data: upgradeToBridgeVForeignData, - nonce: foreignNonce, - to: storageValidatorsForeign.options.address, - privateKey: deploymentPrivateKey, + await upgradeProxy({ + proxy: storageValidatorsForeign, + implementationAddress: bridgeValidatorsForeign.options.address, + version: '1', + nonce, url: FOREIGN_RPC_URL }) - assert.strictEqual( - Web3Utils.hexToNumber(txUpgradeToBridgeVForeign.status), - 1, - 'Transaction Failed' - ) - foreignNonce++ + nonce++ console.log('\ninitializing Foreign Bridge Validators with following parameters:\n') - console.log( - `REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, VALIDATORS: ${VALIDATORS}` - ) - bridgeValidatorsForeign.options.address = storageValidatorsForeign.options.address - const initializeForeignData = await bridgeValidatorsForeign.methods - .initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, FOREIGN_VALIDATORS_OWNER) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txInitializeForeign = await sendRawTxForeign({ - data: initializeForeignData, - nonce: foreignNonce, - to: bridgeValidatorsForeign.options.address, - privateKey: deploymentPrivateKey, + await initializeValidators({ + contract: bridgeValidatorsForeign, + isRewardableBridge: false, + requiredNumber: REQUIRED_NUMBER_OF_VALIDATORS, + validators: VALIDATORS, + rewardAccounts: [], + owner: FOREIGN_VALIDATORS_OWNER, + nonce, url: FOREIGN_RPC_URL }) - assert.strictEqual(Web3Utils.hexToNumber(txInitializeForeign.status), 1, 'Transaction Failed') - foreignNonce++ + nonce++ console.log('\nTransferring ownership of ValidatorsProxy\n') - const validatorsForeignOwnershipData = await storageValidatorsForeign.methods - .transferProxyOwnership(FOREIGN_UPGRADEABLE_ADMIN) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txValidatorsForeignOwnershipData = await sendRawTxForeign({ - data: validatorsForeignOwnershipData, - nonce: foreignNonce, - to: storageValidatorsForeign.options.address, - privateKey: deploymentPrivateKey, + await transferProxyOwnership({ + proxy: storageValidatorsForeign, + newOwner: FOREIGN_UPGRADEABLE_ADMIN, + nonce, url: FOREIGN_RPC_URL }) - assert.strictEqual( - Web3Utils.hexToNumber(txValidatorsForeignOwnershipData.status), - 1, - 'Transaction Failed' - ) - foreignNonce++ + nonce++ console.log('\ndeploying foreignBridge storage\n') const foreignBridgeStorage = await deployContract(EternalStorageProxy, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, network: 'foreign', - nonce: foreignNonce + nonce }) - foreignNonce++ + nonce++ console.log('[Foreign] ForeignBridge Storage: ', foreignBridgeStorage.options.address) console.log('\ndeploying foreignBridge implementation\n') const foreignBridgeImplementation = await deployContract(ForeignBridge, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, network: 'foreign', - nonce: foreignNonce + nonce }) - foreignNonce++ + nonce++ console.log( '[Foreign] ForeignBridge Implementation: ', foreignBridgeImplementation.options.address ) console.log('\nhooking up ForeignBridge storage to ForeignBridge implementation') - const upgradeToForeignBridgeData = await foreignBridgeStorage.methods - .upgradeTo('1', foreignBridgeImplementation.options.address) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txUpgradeToForeignBridge = await sendRawTxForeign({ - data: upgradeToForeignBridgeData, - nonce: foreignNonce, - to: foreignBridgeStorage.options.address, - privateKey: deploymentPrivateKey, + await upgradeProxy({ + proxy: foreignBridgeStorage, + implementationAddress: foreignBridgeImplementation.options.address, + version: '1', + nonce, url: FOREIGN_RPC_URL }) - assert.strictEqual( - Web3Utils.hexToNumber(txUpgradeToForeignBridge.status), - 1, - 'Transaction Failed' - ) - foreignNonce++ + nonce++ console.log('\ninitializing Foreign Bridge with following parameters:\n') - console.log(`Foreign Validators: ${storageValidatorsForeign.options.address}, - `) foreignBridgeImplementation.options.address = foreignBridgeStorage.options.address - const initializeFBridgeData = await foreignBridgeImplementation.methods - .initialize( - storageValidatorsForeign.options.address, - ERC20_TOKEN_ADDRESS, - FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS, - FOREIGN_GAS_PRICE, - FOREIGN_MAX_AMOUNT_PER_TX, - HOME_DAILY_LIMIT, - HOME_MAX_AMOUNT_PER_TX, - FOREIGN_BRIDGE_OWNER - ) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txInitializeBridge = await sendRawTxForeign({ - data: initializeFBridgeData, - nonce: foreignNonce, - to: foreignBridgeStorage.options.address, - privateKey: deploymentPrivateKey, - url: FOREIGN_RPC_URL + await initializeBridge({ + validatorsBridge: storageValidatorsForeign, + bridge: foreignBridgeImplementation, + nonce }) - assert.strictEqual(Web3Utils.hexToNumber(txInitializeBridge.status), 1, 'Transaction Failed') - foreignNonce++ + nonce++ - const bridgeOwnershipData = await foreignBridgeStorage.methods - .transferProxyOwnership(FOREIGN_UPGRADEABLE_ADMIN) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txBridgeOwnershipData = await sendRawTxForeign({ - data: bridgeOwnershipData, - nonce: foreignNonce, - to: foreignBridgeStorage.options.address, - privateKey: deploymentPrivateKey, + console.log('transferring proxy ownership to multisig for foreign bridge Proxy contract') + await transferProxyOwnership({ + proxy: foreignBridgeStorage, + newOwner: FOREIGN_UPGRADEABLE_ADMIN, + nonce, url: FOREIGN_RPC_URL }) - assert.strictEqual(Web3Utils.hexToNumber(txBridgeOwnershipData.status), 1, 'Transaction Failed') - foreignNonce++ console.log('\nForeign Deployment Bridge completed\n') return { diff --git a/deploy/src/erc_to_erc/home.js b/deploy/src/erc_to_erc/home.js index d8f238d21..00393bc18 100644 --- a/deploy/src/erc_to_erc/home.js +++ b/deploy/src/erc_to_erc/home.js @@ -2,7 +2,16 @@ const assert = require('assert') const Web3Utils = require('web3-utils') const env = require('../loadEnv') -const { deployContract, privateKeyToAddress, sendRawTxHome } = require('../deploymentUtils') +const { + deployContract, + privateKeyToAddress, + sendRawTxHome, + upgradeProxy, + initializeValidators, + transferProxyOwnership, + setBridgeContract, + transferOwnership +} = require('../deploymentUtils') const { web3Home, deploymentPrivateKey, HOME_RPC_URL } = require('../web3') const EternalStorageProxy = require('../../../build/contracts/EternalStorageProxy.json') @@ -32,186 +41,166 @@ const { const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVATE_KEY) +async function initializeBridge({ validatorsBridge, bridge, erc677token, initialNonce }) { + let nonce = initialNonce + + console.log(`Home Validators: ${validatorsBridge.options.address}, + HOME_DAILY_LIMIT : ${HOME_DAILY_LIMIT} which is ${Web3Utils.fromWei(HOME_DAILY_LIMIT)} in eth, + HOME_MAX_AMOUNT_PER_TX: ${HOME_MAX_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( + HOME_MAX_AMOUNT_PER_TX + )} in eth, + HOME_MIN_AMOUNT_PER_TX: ${HOME_MIN_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( + HOME_MIN_AMOUNT_PER_TX + )} in eth, + HOME_GAS_PRICE: ${HOME_GAS_PRICE}, HOME_REQUIRED_BLOCK_CONFIRMATIONS : ${HOME_REQUIRED_BLOCK_CONFIRMATIONS} + `) + const initializeHomeBridgeData = await bridge.methods + .initialize( + validatorsBridge.options.address, + HOME_DAILY_LIMIT, + HOME_MAX_AMOUNT_PER_TX, + HOME_MIN_AMOUNT_PER_TX, + HOME_GAS_PRICE, + HOME_REQUIRED_BLOCK_CONFIRMATIONS, + erc677token.options.address, + FOREIGN_DAILY_LIMIT, + FOREIGN_MAX_AMOUNT_PER_TX, + HOME_BRIDGE_OWNER + ) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + const txInitializeHomeBridge = await sendRawTxHome({ + data: initializeHomeBridgeData, + nonce, + to: bridge.options.address, + privateKey: deploymentPrivateKey, + url: HOME_RPC_URL + }) + assert.strictEqual(Web3Utils.hexToNumber(txInitializeHomeBridge.status), 1, 'Transaction Failed') + nonce++ + + return nonce +} + async function deployHome() { - let homeNonce = await web3Home.eth.getTransactionCount(DEPLOYMENT_ACCOUNT_ADDRESS) + let nonce = await web3Home.eth.getTransactionCount(DEPLOYMENT_ACCOUNT_ADDRESS) console.log('deploying storage for home validators') const storageValidatorsHome = await deployContract(EternalStorageProxy, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, - nonce: homeNonce + nonce }) console.log('[Home] BridgeValidators Storage: ', storageValidatorsHome.options.address) - homeNonce++ + nonce++ console.log('\ndeploying implementation for home validators') const bridgeValidatorsHome = await deployContract(BridgeValidators, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, - nonce: homeNonce + nonce }) console.log('[Home] BridgeValidators Implementation: ', bridgeValidatorsHome.options.address) - homeNonce++ + nonce++ console.log('\nhooking up eternal storage to BridgeValidators') - const upgradeToBridgeVHomeData = await storageValidatorsHome.methods - .upgradeTo('1', bridgeValidatorsHome.options.address) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txUpgradeToBridgeVHome = await sendRawTxHome({ - data: upgradeToBridgeVHomeData, - nonce: homeNonce, - to: storageValidatorsHome.options.address, - privateKey: deploymentPrivateKey, + await upgradeProxy({ + proxy: storageValidatorsHome, + implementationAddress: bridgeValidatorsHome.options.address, + version: '1', + nonce, url: HOME_RPC_URL }) - assert.strictEqual(Web3Utils.hexToNumber(txUpgradeToBridgeVHome.status), 1, 'Transaction Failed') - homeNonce++ + nonce++ console.log('\ninitializing Home Bridge Validators with following parameters:\n') - console.log( - `REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, VALIDATORS: ${VALIDATORS}` - ) - bridgeValidatorsHome.options.address = storageValidatorsHome.options.address - const initializeData = await bridgeValidatorsHome.methods - .initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, HOME_VALIDATORS_OWNER) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txInitialize = await sendRawTxHome({ - data: initializeData, - nonce: homeNonce, - to: bridgeValidatorsHome.options.address, - privateKey: deploymentPrivateKey, + await initializeValidators({ + contract: bridgeValidatorsHome, + isRewardableBridge: false, + requiredNumber: REQUIRED_NUMBER_OF_VALIDATORS, + validators: VALIDATORS, + rewardAccounts: [], + owner: HOME_VALIDATORS_OWNER, + nonce, url: HOME_RPC_URL }) - assert.strictEqual(Web3Utils.hexToNumber(txInitialize.status), 1, 'Transaction Failed') - homeNonce++ + nonce++ console.log('transferring proxy ownership to multisig for Validators Proxy contract') - const proxyDataTransfer = await storageValidatorsHome.methods - .transferProxyOwnership(HOME_UPGRADEABLE_ADMIN) - .encodeABI() - const txProxyDataTransfer = await sendRawTxHome({ - data: proxyDataTransfer, - nonce: homeNonce, - to: storageValidatorsHome.options.address, - privateKey: deploymentPrivateKey, + await transferProxyOwnership({ + proxy: storageValidatorsHome, + newOwner: HOME_UPGRADEABLE_ADMIN, + nonce, url: HOME_RPC_URL }) - assert.strictEqual(Web3Utils.hexToNumber(txProxyDataTransfer.status), 1, 'Transaction Failed') - homeNonce++ + nonce++ console.log('\ndeploying homeBridge storage\n') const homeBridgeStorage = await deployContract(EternalStorageProxy, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, - nonce: homeNonce + nonce }) - homeNonce++ + nonce++ console.log('[Home] HomeBridge Storage: ', homeBridgeStorage.options.address) console.log('\ndeploying homeBridge implementation\n') const homeBridgeImplementation = await deployContract(HomeBridge, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, - nonce: homeNonce + nonce }) - homeNonce++ + nonce++ console.log('[Home] HomeBridge Implementation: ', homeBridgeImplementation.options.address) console.log('\nhooking up HomeBridge storage to HomeBridge implementation') - const upgradeToHomeBridgeData = await homeBridgeStorage.methods - .upgradeTo('1', homeBridgeImplementation.options.address) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txUpgradeToHomeBridge = await sendRawTxHome({ - data: upgradeToHomeBridgeData, - nonce: homeNonce, - to: homeBridgeStorage.options.address, - privateKey: deploymentPrivateKey, + await upgradeProxy({ + proxy: homeBridgeStorage, + implementationAddress: homeBridgeImplementation.options.address, + version: '1', + nonce, url: HOME_RPC_URL }) - assert.strictEqual(Web3Utils.hexToNumber(txUpgradeToHomeBridge.status), 1, 'Transaction Failed') - homeNonce++ + nonce++ console.log('\n[Home] deploying Bridgeble token') const erc677token = await deployContract( ERC677BridgeToken, [BRIDGEABLE_TOKEN_NAME, BRIDGEABLE_TOKEN_SYMBOL, BRIDGEABLE_TOKEN_DECIMALS], - { from: DEPLOYMENT_ACCOUNT_ADDRESS, network: 'home', nonce: homeNonce } + { from: DEPLOYMENT_ACCOUNT_ADDRESS, network: 'home', nonce } ) - homeNonce++ + nonce++ console.log('[Home] Bridgeble Token: ', erc677token.options.address) console.log('\nset bridge contract on ERC677BridgeToken') - const setBridgeContractData = await erc677token.methods - .setBridgeContract(homeBridgeStorage.options.address) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const setBridgeContract = await sendRawTxHome({ - data: setBridgeContractData, - nonce: homeNonce, - to: erc677token.options.address, - privateKey: deploymentPrivateKey, + await setBridgeContract({ + contract: erc677token, + bridgeAddress: homeBridgeStorage.options.address, + nonce, url: HOME_RPC_URL }) - assert.strictEqual(Web3Utils.hexToNumber(setBridgeContract.status), 1, 'Transaction Failed') - homeNonce++ + nonce++ console.log('transferring ownership of Bridgeble token to homeBridge contract') - const txOwnershipData = await erc677token.methods - .transferOwnership(homeBridgeStorage.options.address) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txOwnership = await sendRawTxHome({ - data: txOwnershipData, - nonce: homeNonce, - to: erc677token.options.address, - privateKey: deploymentPrivateKey, + await transferOwnership({ + contract: erc677token, + newOwner: homeBridgeStorage.options.address, + nonce, url: HOME_RPC_URL }) - assert.strictEqual(Web3Utils.hexToNumber(txOwnership.status), 1, 'Transaction Failed') - homeNonce++ + nonce++ console.log('\ninitializing Home Bridge with following parameters:\n') - console.log(`Home Validators: ${storageValidatorsHome.options.address}, - HOME_DAILY_LIMIT : ${HOME_DAILY_LIMIT} which is ${Web3Utils.fromWei(HOME_DAILY_LIMIT)} in eth, - HOME_MAX_AMOUNT_PER_TX: ${HOME_MAX_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( - HOME_MAX_AMOUNT_PER_TX - )} in eth, - HOME_MIN_AMOUNT_PER_TX: ${HOME_MIN_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( - HOME_MIN_AMOUNT_PER_TX - )} in eth, - HOME_GAS_PRICE: ${HOME_GAS_PRICE}, HOME_REQUIRED_BLOCK_CONFIRMATIONS : ${HOME_REQUIRED_BLOCK_CONFIRMATIONS} - `) homeBridgeImplementation.options.address = homeBridgeStorage.options.address - const initializeHomeBridgeData = await homeBridgeImplementation.methods - .initialize( - storageValidatorsHome.options.address, - HOME_DAILY_LIMIT, - HOME_MAX_AMOUNT_PER_TX, - HOME_MIN_AMOUNT_PER_TX, - HOME_GAS_PRICE, - HOME_REQUIRED_BLOCK_CONFIRMATIONS, - erc677token.options.address, - FOREIGN_DAILY_LIMIT, - FOREIGN_MAX_AMOUNT_PER_TX, - HOME_BRIDGE_OWNER - ) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txInitializeHomeBridge = await sendRawTxHome({ - data: initializeHomeBridgeData, - nonce: homeNonce, - to: homeBridgeStorage.options.address, - privateKey: deploymentPrivateKey, - url: HOME_RPC_URL + + nonce = await initializeBridge({ + validatorsBridge: storageValidatorsHome, + bridge: homeBridgeImplementation, + erc677token, + initialNonce: nonce }) - assert.strictEqual(Web3Utils.hexToNumber(txInitializeHomeBridge.status), 1, 'Transaction Failed') - homeNonce++ console.log('transferring proxy ownership to multisig for Home bridge Proxy contract') - const homeBridgeProxyData = await homeBridgeStorage.methods - .transferProxyOwnership(HOME_UPGRADEABLE_ADMIN) - .encodeABI() - const txhomeBridgeProxyData = await sendRawTxHome({ - data: homeBridgeProxyData, - nonce: homeNonce, - to: homeBridgeStorage.options.address, - privateKey: deploymentPrivateKey, + await transferProxyOwnership({ + proxy: homeBridgeStorage, + newOwner: HOME_UPGRADEABLE_ADMIN, + nonce, url: HOME_RPC_URL }) - assert.strictEqual(Web3Utils.hexToNumber(txhomeBridgeProxyData.status), 1, 'Transaction Failed') - homeNonce++ console.log('\nHome Deployment Bridge completed\n') return { From 4cc175c6b3ad77af7ba5bfbde5e9263e490ed652 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 27 Feb 2019 16:22:26 -0300 Subject: [PATCH 109/187] Update erc-to-native deploy script --- deploy/src/erc_to_erc/foreign.js | 10 ++ deploy/src/erc_to_erc/home.js | 11 +- deploy/src/erc_to_native/foreign.js | 193 ++++++++++----------- deploy/src/erc_to_native/home.js | 260 +++++++++++++--------------- 4 files changed, 234 insertions(+), 240 deletions(-) diff --git a/deploy/src/erc_to_erc/foreign.js b/deploy/src/erc_to_erc/foreign.js index c8a9aea16..3bf2e89ce 100644 --- a/deploy/src/erc_to_erc/foreign.js +++ b/deploy/src/erc_to_erc/foreign.js @@ -36,6 +36,16 @@ const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVAT async function initializeBridge({ validatorsBridge, bridge, nonce }) { console.log(`Foreign Validators: ${validatorsBridge.options.address}, + ERC20_TOKEN_ADDRESS: ${ERC20_TOKEN_ADDRESS}, + FOREIGN_MAX_AMOUNT_PER_TX: ${FOREIGN_MAX_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( + FOREIGN_MAX_AMOUNT_PER_TX + )} in eth, + FOREIGN_GAS_PRICE: ${FOREIGN_GAS_PRICE}, FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS : ${FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS}, + HOME_DAILY_LIMIT: ${HOME_DAILY_LIMIT} which is ${Web3Utils.fromWei(HOME_DAILY_LIMIT)} in eth, + HOME_MAX_AMOUNT_PER_TX: ${HOME_MAX_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( + HOME_MAX_AMOUNT_PER_TX + )} in eth, + FOREIGN_BRIDGE_OWNER: ${FOREIGN_BRIDGE_OWNER} `) const initializeFBridgeData = await bridge.methods .initialize( diff --git a/deploy/src/erc_to_erc/home.js b/deploy/src/erc_to_erc/home.js index 00393bc18..0be6d6e34 100644 --- a/deploy/src/erc_to_erc/home.js +++ b/deploy/src/erc_to_erc/home.js @@ -75,7 +75,16 @@ async function initializeBridge({ validatorsBridge, bridge, erc677token, initial privateKey: deploymentPrivateKey, url: HOME_RPC_URL }) - assert.strictEqual(Web3Utils.hexToNumber(txInitializeHomeBridge.status), 1, 'Transaction Failed') + if (txInitializeHomeBridge.status) { + assert.strictEqual( + Web3Utils.hexToNumber(txInitializeHomeBridge.status), + 1, + 'Transaction Failed' + ) + } else { + const isInitialized = await bridge.methods.isInitialized().call() + assert.strictEqual(isInitialized, true, 'Transaction Failed') + } nonce++ return nonce diff --git a/deploy/src/erc_to_native/foreign.js b/deploy/src/erc_to_native/foreign.js index 7584fa7c5..7df12c831 100644 --- a/deploy/src/erc_to_native/foreign.js +++ b/deploy/src/erc_to_native/foreign.js @@ -2,7 +2,14 @@ const assert = require('assert') const Web3Utils = require('web3-utils') const env = require('../loadEnv') -const { deployContract, privateKeyToAddress, sendRawTxForeign } = require('../deploymentUtils') +const { + deployContract, + privateKeyToAddress, + sendRawTxForeign, + upgradeProxy, + initializeValidators, + transferProxyOwnership +} = require('../deploymentUtils') const { web3Foreign, deploymentPrivateKey, FOREIGN_RPC_URL } = require('../web3') const EternalStorageProxy = require('../../../build/contracts/EternalStorageProxy.json') @@ -27,11 +34,51 @@ const { const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVATE_KEY) +async function initializeBridge({ validatorsBridge, bridge, nonce }) { + console.log(`Foreign Validators: ${validatorsBridge.options.address}, + ERC20_TOKEN_ADDRESS: ${ERC20_TOKEN_ADDRESS}, + FOREIGN_MAX_AMOUNT_PER_TX: ${FOREIGN_MAX_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( + FOREIGN_MAX_AMOUNT_PER_TX + )} in eth, + FOREIGN_GAS_PRICE: ${FOREIGN_GAS_PRICE}, FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS : ${FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS}, + HOME_DAILY_LIMIT: ${HOME_DAILY_LIMIT} which is ${Web3Utils.fromWei(HOME_DAILY_LIMIT)} in eth, + HOME_MAX_AMOUNT_PER_TX: ${HOME_MAX_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( + HOME_MAX_AMOUNT_PER_TX + )} in eth, + FOREIGN_BRIDGE_OWNER: ${FOREIGN_BRIDGE_OWNER} + `) + const initializeFBridgeData = await bridge.methods + .initialize( + validatorsBridge.options.address, + ERC20_TOKEN_ADDRESS, + FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS, + FOREIGN_GAS_PRICE, + FOREIGN_MAX_AMOUNT_PER_TX, + HOME_DAILY_LIMIT, + HOME_MAX_AMOUNT_PER_TX, + FOREIGN_BRIDGE_OWNER + ) + .encodeABI() + const txInitializeBridge = await sendRawTxForeign({ + data: initializeFBridgeData, + nonce, + to: bridge.options.address, + privateKey: deploymentPrivateKey, + url: FOREIGN_RPC_URL + }) + if (txInitializeBridge.status) { + assert.strictEqual(Web3Utils.hexToNumber(txInitializeBridge.status), 1, 'Transaction Failed') + } else { + const isInitialized = await bridge.methods.isInitialized().call() + assert.strictEqual(isInitialized, true, 'Transaction Failed') + } +} + async function deployForeign() { if (!Web3Utils.isAddress(ERC20_TOKEN_ADDRESS)) { throw new Error('ERC20_TOKEN_ADDRESS env var is not defined') } - let foreignNonce = await web3Foreign.eth.getTransactionCount(DEPLOYMENT_ACCOUNT_ADDRESS) + let nonce = await web3Foreign.eth.getTransactionCount(DEPLOYMENT_ACCOUNT_ADDRESS) console.log('========================================') console.log('deploying ForeignBridge') console.log('========================================\n') @@ -40,154 +87,102 @@ async function deployForeign() { const storageValidatorsForeign = await deployContract(EternalStorageProxy, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, network: 'foreign', - nonce: foreignNonce + nonce }) - foreignNonce++ + nonce++ console.log('[Foreign] BridgeValidators Storage: ', storageValidatorsForeign.options.address) console.log('\ndeploying implementation for foreign validators') const bridgeValidatorsForeign = await deployContract(BridgeValidators, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, network: 'foreign', - nonce: foreignNonce + nonce }) - foreignNonce++ + nonce++ console.log( '[Foreign] BridgeValidators Implementation: ', bridgeValidatorsForeign.options.address ) console.log('\nhooking up eternal storage to BridgeValidators') - const upgradeToBridgeVForeignData = await storageValidatorsForeign.methods - .upgradeTo('1', bridgeValidatorsForeign.options.address) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txUpgradeToBridgeVForeign = await sendRawTxForeign({ - data: upgradeToBridgeVForeignData, - nonce: foreignNonce, - to: storageValidatorsForeign.options.address, - privateKey: deploymentPrivateKey, + await upgradeProxy({ + proxy: storageValidatorsForeign, + implementationAddress: bridgeValidatorsForeign.options.address, + version: '1', + nonce, url: FOREIGN_RPC_URL }) - assert.strictEqual( - Web3Utils.hexToNumber(txUpgradeToBridgeVForeign.status), - 1, - 'Transaction Failed' - ) - foreignNonce++ + nonce++ console.log('\ninitializing Foreign Bridge Validators with following parameters:\n') - console.log( - `REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, VALIDATORS: ${VALIDATORS}` - ) - bridgeValidatorsForeign.options.address = storageValidatorsForeign.options.address - const initializeForeignData = await bridgeValidatorsForeign.methods - .initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, FOREIGN_VALIDATORS_OWNER) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txInitializeForeign = await sendRawTxForeign({ - data: initializeForeignData, - nonce: foreignNonce, - to: bridgeValidatorsForeign.options.address, - privateKey: deploymentPrivateKey, + await initializeValidators({ + contract: bridgeValidatorsForeign, + isRewardableBridge: false, + requiredNumber: REQUIRED_NUMBER_OF_VALIDATORS, + validators: VALIDATORS, + rewardAccounts: [], + owner: FOREIGN_VALIDATORS_OWNER, + nonce, url: FOREIGN_RPC_URL }) - assert.strictEqual(Web3Utils.hexToNumber(txInitializeForeign.status), 1, 'Transaction Failed') - foreignNonce++ + nonce++ console.log('\nTransferring ownership of ValidatorsProxy\n') - const validatorsForeignOwnershipData = await storageValidatorsForeign.methods - .transferProxyOwnership(FOREIGN_UPGRADEABLE_ADMIN) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txValidatorsForeignOwnershipData = await sendRawTxForeign({ - data: validatorsForeignOwnershipData, - nonce: foreignNonce, - to: storageValidatorsForeign.options.address, - privateKey: deploymentPrivateKey, + await transferProxyOwnership({ + proxy: storageValidatorsForeign, + newOwner: FOREIGN_UPGRADEABLE_ADMIN, + nonce, url: FOREIGN_RPC_URL }) - assert.strictEqual( - Web3Utils.hexToNumber(txValidatorsForeignOwnershipData.status), - 1, - 'Transaction Failed' - ) - foreignNonce++ + nonce++ console.log('\ndeploying foreignBridge storage\n') const foreignBridgeStorage = await deployContract(EternalStorageProxy, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, network: 'foreign', - nonce: foreignNonce + nonce }) - foreignNonce++ + nonce++ console.log('[Foreign] ForeignBridge Storage: ', foreignBridgeStorage.options.address) console.log('\ndeploying foreignBridge implementation\n') const foreignBridgeImplementation = await deployContract(ForeignBridge, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, network: 'foreign', - nonce: foreignNonce + nonce }) - foreignNonce++ + nonce++ console.log( '[Foreign] ForeignBridge Implementation: ', foreignBridgeImplementation.options.address ) console.log('\nhooking up ForeignBridge storage to ForeignBridge implementation') - const upgradeToForeignBridgeData = await foreignBridgeStorage.methods - .upgradeTo('1', foreignBridgeImplementation.options.address) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txUpgradeToForeignBridge = await sendRawTxForeign({ - data: upgradeToForeignBridgeData, - nonce: foreignNonce, - to: foreignBridgeStorage.options.address, - privateKey: deploymentPrivateKey, + await upgradeProxy({ + proxy: foreignBridgeStorage, + implementationAddress: foreignBridgeImplementation.options.address, + version: '1', + nonce, url: FOREIGN_RPC_URL }) - assert.strictEqual( - Web3Utils.hexToNumber(txUpgradeToForeignBridge.status), - 1, - 'Transaction Failed' - ) - foreignNonce++ + nonce++ console.log('\ninitializing Foreign Bridge with following parameters:\n') - console.log(`Foreign Validators: ${storageValidatorsForeign.options.address}, - `) foreignBridgeImplementation.options.address = foreignBridgeStorage.options.address - const initializeFBridgeData = await foreignBridgeImplementation.methods - .initialize( - storageValidatorsForeign.options.address, - ERC20_TOKEN_ADDRESS, - FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS, - FOREIGN_GAS_PRICE, - FOREIGN_MAX_AMOUNT_PER_TX, - HOME_DAILY_LIMIT, - HOME_MAX_AMOUNT_PER_TX, - FOREIGN_BRIDGE_OWNER - ) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txInitializeBridge = await sendRawTxForeign({ - data: initializeFBridgeData, - nonce: foreignNonce, - to: foreignBridgeStorage.options.address, - privateKey: deploymentPrivateKey, - url: FOREIGN_RPC_URL + await initializeBridge({ + validatorsBridge: storageValidatorsForeign, + bridge: foreignBridgeImplementation, + nonce }) - assert.strictEqual(Web3Utils.hexToNumber(txInitializeBridge.status), 1, 'Transaction Failed') - foreignNonce++ - - const bridgeOwnershipData = await foreignBridgeStorage.methods - .transferProxyOwnership(FOREIGN_UPGRADEABLE_ADMIN) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txBridgeOwnershipData = await sendRawTxForeign({ - data: bridgeOwnershipData, - nonce: foreignNonce, - to: foreignBridgeStorage.options.address, - privateKey: deploymentPrivateKey, + nonce++ + + console.log('transferring proxy ownership to multisig for foreign bridge Proxy contract') + await transferProxyOwnership({ + proxy: foreignBridgeStorage, + newOwner: FOREIGN_UPGRADEABLE_ADMIN, + nonce, url: FOREIGN_RPC_URL }) - assert.strictEqual(Web3Utils.hexToNumber(txBridgeOwnershipData.status), 1, 'Transaction Failed') - foreignNonce++ console.log('\nForeign Deployment Bridge completed\n') return { diff --git a/deploy/src/erc_to_native/home.js b/deploy/src/erc_to_native/home.js index 4b0fbe8ee..f0cef1256 100644 --- a/deploy/src/erc_to_native/home.js +++ b/deploy/src/erc_to_native/home.js @@ -6,7 +6,9 @@ const { deployContract, privateKeyToAddress, sendRawTxHome, - logValidatorsAndRewardAccounts + upgradeProxy, + initializeValidators, + transferProxyOwnership } = require('../deploymentUtils') const { web3Home, deploymentPrivateKey, HOME_RPC_URL } = require('../web3') @@ -42,136 +44,23 @@ const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVAT const isRewardableBridge = HOME_REWARDABLE === 'BOTH_DIRECTIONS' -async function deployHome() { - let homeNonce = await web3Home.eth.getTransactionCount(DEPLOYMENT_ACCOUNT_ADDRESS) - console.log('deploying storage for home validators') - const storageValidatorsHome = await deployContract(EternalStorageProxy, [], { - from: DEPLOYMENT_ACCOUNT_ADDRESS, - nonce: homeNonce - }) - console.log('[Home] BridgeValidators Storage: ', storageValidatorsHome.options.address) - homeNonce++ - - console.log('\ndeploying implementation for home validators') - const bridgeValidatorsContract = isRewardableBridge ? RewardableValidators : BridgeValidators - const bridgeValidatorsHome = await deployContract(bridgeValidatorsContract, [], { - from: DEPLOYMENT_ACCOUNT_ADDRESS, - nonce: homeNonce - }) - console.log('[Home] BridgeValidators Implementation: ', bridgeValidatorsHome.options.address) - homeNonce++ - - console.log('\nhooking up eternal storage to BridgeValidators') - const upgradeToBridgeVHomeData = await storageValidatorsHome.methods - .upgradeTo('1', bridgeValidatorsHome.options.address) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txUpgradeToBridgeVHome = await sendRawTxHome({ - data: upgradeToBridgeVHomeData, - nonce: homeNonce, - to: storageValidatorsHome.options.address, - privateKey: deploymentPrivateKey, - url: HOME_RPC_URL - }) - assert.strictEqual(Web3Utils.hexToNumber(txUpgradeToBridgeVHome.status), 1, 'Transaction Failed') - homeNonce++ - - console.log('\ninitializing Home Bridge Validators with following parameters:\n') - bridgeValidatorsHome.options.address = storageValidatorsHome.options.address - - let initializeData - - if (isRewardableBridge) { - console.log( - `REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, HOME_VALIDATORS_OWNER: ${HOME_VALIDATORS_OWNER}` - ) - logValidatorsAndRewardAccounts(VALIDATORS, VALIDATORS_REWARD_ACCOUNTS) - initializeData = await bridgeValidatorsHome.methods - .initialize( - REQUIRED_NUMBER_OF_VALIDATORS, - VALIDATORS, - VALIDATORS_REWARD_ACCOUNTS, - HOME_VALIDATORS_OWNER - ) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - } else { - console.log( - `REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, VALIDATORS: ${VALIDATORS}` - ) - initializeData = await bridgeValidatorsHome.methods - .initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, HOME_VALIDATORS_OWNER) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - } - - const txInitialize = await sendRawTxHome({ - data: initializeData, - nonce: homeNonce, - to: bridgeValidatorsHome.options.address, - privateKey: deploymentPrivateKey, - url: HOME_RPC_URL - }) - assert.strictEqual(Web3Utils.hexToNumber(txInitialize.status), 1, 'Transaction Failed') - homeNonce++ - - console.log('transferring proxy ownership to multisig for Validators Proxy contract') - const proxyDataTransfer = await storageValidatorsHome.methods - .transferProxyOwnership(HOME_UPGRADEABLE_ADMIN) - .encodeABI() - const txProxyDataTransfer = await sendRawTxHome({ - data: proxyDataTransfer, - nonce: homeNonce, - to: storageValidatorsHome.options.address, - privateKey: deploymentPrivateKey, - url: HOME_RPC_URL - }) - assert.strictEqual(Web3Utils.hexToNumber(txProxyDataTransfer.status), 1, 'Transaction Failed') - homeNonce++ - - console.log('\ndeploying homeBridge storage\n') - const homeBridgeStorage = await deployContract(EternalStorageProxy, [], { - from: DEPLOYMENT_ACCOUNT_ADDRESS, - nonce: homeNonce - }) - homeNonce++ - console.log('[Home] HomeBridge Storage: ', homeBridgeStorage.options.address) - - console.log('\ndeploying homeBridge implementation\n') - const homeBridgeImplementation = await deployContract(HomeBridge, [], { - from: DEPLOYMENT_ACCOUNT_ADDRESS, - nonce: homeNonce - }) - homeNonce++ - console.log('[Home] HomeBridge Implementation: ', homeBridgeImplementation.options.address) - - console.log('\nhooking up HomeBridge storage to HomeBridge implementation') - const upgradeToHomeBridgeData = await homeBridgeStorage.methods - .upgradeTo('1', homeBridgeImplementation.options.address) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txUpgradeToHomeBridge = await sendRawTxHome({ - data: upgradeToHomeBridgeData, - nonce: homeNonce, - to: homeBridgeStorage.options.address, - privateKey: deploymentPrivateKey, - url: HOME_RPC_URL - }) - assert.strictEqual(Web3Utils.hexToNumber(txUpgradeToHomeBridge.status), 1, 'Transaction Failed') - homeNonce++ - +async function initializeBridge({ validatorsBridge, bridge, initialNonce }) { + let nonce = initialNonce let initializeHomeBridgeData - homeBridgeImplementation.options.address = homeBridgeStorage.options.address if (isRewardableBridge) { console.log('\ndeploying implementation for fee manager') const feeManager = await deployContract(FeeManagerErcToNative, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, - nonce: homeNonce + nonce }) console.log('[Home] feeManager Implementation: ', feeManager.options.address) - homeNonce++ + nonce++ const homeFeeInWei = Web3Utils.toWei(HOME_TRANSACTIONS_FEE.toString(), 'ether') const foreignFeeInWei = Web3Utils.toWei(FOREIGN_TRANSACTIONS_FEE.toString(), 'ether') console.log('\ninitializing Home Bridge with fee contract:\n') - console.log(`Home Validators: ${storageValidatorsHome.options.address}, + console.log(`Home Validators: ${validatorsBridge.options.address}, HOME_DAILY_LIMIT : ${HOME_DAILY_LIMIT} which is ${Web3Utils.fromWei(HOME_DAILY_LIMIT)} in eth, HOME_MAX_AMOUNT_PER_TX: ${HOME_MAX_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( HOME_MAX_AMOUNT_PER_TX @@ -191,9 +80,9 @@ async function deployHome() { Fee Manager: ${feeManager.options.address}, Home Fee: ${homeFeeInWei} which is ${HOME_TRANSACTIONS_FEE * 100}% Foreign Fee: ${foreignFeeInWei} which is ${FOREIGN_TRANSACTIONS_FEE * 100}%`) - initializeHomeBridgeData = await homeBridgeImplementation.methods + initializeHomeBridgeData = await bridge.methods .rewardableInitialize( - storageValidatorsHome.options.address, + validatorsBridge.options.address, HOME_DAILY_LIMIT, HOME_MAX_AMOUNT_PER_TX, HOME_MIN_AMOUNT_PER_TX, @@ -207,10 +96,10 @@ async function deployHome() { homeFeeInWei, foreignFeeInWei ) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + .encodeABI() } else { console.log('\ninitializing Home Bridge with following parameters:\n') - console.log(`Home Validators: ${storageValidatorsHome.options.address}, + console.log(`Home Validators: ${validatorsBridge.options.address}, HOME_DAILY_LIMIT : ${HOME_DAILY_LIMIT} which is ${Web3Utils.fromWei(HOME_DAILY_LIMIT)} in eth, HOME_MAX_AMOUNT_PER_TX: ${HOME_MAX_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( HOME_MAX_AMOUNT_PER_TX @@ -228,9 +117,9 @@ async function deployHome() { )} in eth, HOME_BRIDGE_OWNER: ${HOME_BRIDGE_OWNER} `) - initializeHomeBridgeData = await homeBridgeImplementation.methods + initializeHomeBridgeData = await bridge.methods .initialize( - storageValidatorsHome.options.address, + validatorsBridge.options.address, HOME_DAILY_LIMIT, HOME_MAX_AMOUNT_PER_TX, HOME_MIN_AMOUNT_PER_TX, @@ -241,32 +130,123 @@ async function deployHome() { FOREIGN_MAX_AMOUNT_PER_TX, HOME_BRIDGE_OWNER ) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + .encodeABI() } const txInitializeHomeBridge = await sendRawTxHome({ data: initializeHomeBridgeData, - nonce: homeNonce, - to: homeBridgeStorage.options.address, + nonce, + to: bridge.options.address, privateKey: deploymentPrivateKey, url: HOME_RPC_URL }) - assert.strictEqual(Web3Utils.hexToNumber(txInitializeHomeBridge.status), 1, 'Transaction Failed') - homeNonce++ + if (txInitializeHomeBridge.status) { + assert.strictEqual( + Web3Utils.hexToNumber(txInitializeHomeBridge.status), + 1, + 'Transaction Failed' + ) + } else { + const isInitialized = await bridge.methods.isInitialized().call() + assert.strictEqual(isInitialized, true, 'Transaction Failed') + } + nonce++ + + return nonce +} + +async function deployHome() { + let nonce = await web3Home.eth.getTransactionCount(DEPLOYMENT_ACCOUNT_ADDRESS) + console.log('deploying storage for home validators') + const storageValidatorsHome = await deployContract(EternalStorageProxy, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + nonce + }) + console.log('[Home] BridgeValidators Storage: ', storageValidatorsHome.options.address) + nonce++ + + console.log('\ndeploying implementation for home validators') + const bridgeValidatorsContract = isRewardableBridge ? RewardableValidators : BridgeValidators + const bridgeValidatorsHome = await deployContract(bridgeValidatorsContract, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + nonce + }) + console.log('[Home] BridgeValidators Implementation: ', bridgeValidatorsHome.options.address) + nonce++ + + console.log('\nhooking up eternal storage to BridgeValidators') + await upgradeProxy({ + proxy: storageValidatorsHome, + implementationAddress: bridgeValidatorsHome.options.address, + version: '1', + nonce, + url: HOME_RPC_URL + }) + nonce++ + + console.log('\ninitializing Home Bridge Validators with following parameters:\n') + bridgeValidatorsHome.options.address = storageValidatorsHome.options.address + await initializeValidators({ + contract: bridgeValidatorsHome, + isRewardableBridge, + requiredNumber: REQUIRED_NUMBER_OF_VALIDATORS, + validators: VALIDATORS, + rewardAccounts: VALIDATORS_REWARD_ACCOUNTS, + owner: HOME_VALIDATORS_OWNER, + nonce, + url: HOME_RPC_URL + }) + nonce++ + + console.log('transferring proxy ownership to multisig for Validators Proxy contract') + await transferProxyOwnership({ + proxy: storageValidatorsHome, + newOwner: HOME_UPGRADEABLE_ADMIN, + nonce, + url: HOME_RPC_URL + }) + nonce++ + + console.log('\ndeploying homeBridge storage\n') + const homeBridgeStorage = await deployContract(EternalStorageProxy, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + nonce + }) + nonce++ + console.log('[Home] HomeBridge Storage: ', homeBridgeStorage.options.address) + + console.log('\ndeploying homeBridge implementation\n') + const homeBridgeImplementation = await deployContract(HomeBridge, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + nonce + }) + nonce++ + console.log('[Home] HomeBridge Implementation: ', homeBridgeImplementation.options.address) + + console.log('\nhooking up HomeBridge storage to HomeBridge implementation') + await upgradeProxy({ + proxy: homeBridgeStorage, + implementationAddress: homeBridgeImplementation.options.address, + version: '1', + nonce, + url: HOME_RPC_URL + }) + nonce++ + + homeBridgeImplementation.options.address = homeBridgeStorage.options.address + nonce = await initializeBridge({ + validatorsBridge: storageValidatorsHome, + bridge: homeBridgeImplementation, + initialNonce: nonce + }) console.log('transferring proxy ownership to multisig for Home bridge Proxy contract') - const homeBridgeProxyData = await homeBridgeStorage.methods - .transferProxyOwnership(HOME_UPGRADEABLE_ADMIN) - .encodeABI() - const txhomeBridgeProxyData = await sendRawTxHome({ - data: homeBridgeProxyData, - nonce: homeNonce, - to: homeBridgeStorage.options.address, - privateKey: deploymentPrivateKey, + await transferProxyOwnership({ + proxy: homeBridgeStorage, + newOwner: HOME_UPGRADEABLE_ADMIN, + nonce, url: HOME_RPC_URL }) - assert.strictEqual(Web3Utils.hexToNumber(txhomeBridgeProxyData.status), 1, 'Transaction Failed') - homeNonce++ console.log('\nHome Deployment Bridge completed\n') return { From b419821b4b38580d5a090ed4bda1867f9b62dc80 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Thu, 28 Feb 2019 12:14:56 -0300 Subject: [PATCH 110/187] Add promise-retry for state asserts on deploy scripts --- deploy/package-lock.json | 21 ++++++++++++++++++++- deploy/package.json | 1 + deploy/src/deploymentUtils.js | 28 +++++++++++++++++----------- deploy/src/erc_to_erc/foreign.js | 8 ++++---- deploy/src/erc_to_erc/home.js | 8 ++++---- deploy/src/erc_to_native/foreign.js | 6 +++--- deploy/src/erc_to_native/home.js | 6 +++--- deploy/src/native_to_erc/foreign.js | 26 +++++++++++++------------- deploy/src/native_to_erc/home.js | 6 +++--- 9 files changed, 68 insertions(+), 42 deletions(-) diff --git a/deploy/package-lock.json b/deploy/package-lock.json index a63423650..e15f38f6f 100644 --- a/deploy/package-lock.json +++ b/deploy/package-lock.json @@ -909,6 +909,11 @@ } } }, + "err-code": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/err-code/-/err-code-1.1.2.tgz", + "integrity": "sha1-BuARbTAo9q70gGhJ6w6mp0iuaWA=" + }, "error-ex": { "version": "1.3.2", "resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.2.tgz", @@ -3010,6 +3015,15 @@ "resolved": "https://registry.npmjs.org/progress/-/progress-2.0.0.tgz", "integrity": "sha1-ihvjZr+Pwj2yvSPxDG/pILQ4nR8=" }, + "promise-retry": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/promise-retry/-/promise-retry-1.1.1.tgz", + "integrity": "sha1-ZznpaOMFHaIM5kl/srUPaRHfPW0=", + "requires": { + "err-code": "^1.0.0", + "retry": "^0.10.0" + } + }, "proxy-addr": { "version": "2.0.3", "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.3.tgz", @@ -3217,6 +3231,11 @@ "signal-exit": "^3.0.2" } }, + "retry": { + "version": "0.10.1", + "resolved": "https://registry.npmjs.org/retry/-/retry-0.10.1.tgz", + "integrity": "sha1-52OI0heZLCUnUCQdPTlW/tmNj/Q=" + }, "rimraf": { "version": "2.6.2", "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.6.2.tgz", @@ -4192,7 +4211,7 @@ "requires": { "underscore": "1.8.3", "web3-core-helpers": "1.0.0-beta.33", - "websocket": "git://github.com/frozeman/WebSocket-Node.git#7004c39c42ac98875ab61126e5b4a925430f592c" + "websocket": "websocket@git://github.com/frozeman/WebSocket-Node.git#7004c39c42ac98875ab61126e5b4a925430f592c" } }, "web3-shh": { diff --git a/deploy/package.json b/deploy/package.json index ecace1df5..0da41d4c3 100644 --- a/deploy/package.json +++ b/deploy/package.json @@ -15,6 +15,7 @@ "ethereumjs-tx": "^1.3.4", "node-fetch": "^2.1.2", "pkg": "^4.3.1", + "promise-retry": "^1.1.1", "web3": "^1.0.0-beta.33" }, "devDependencies": { diff --git a/deploy/src/deploymentUtils.js b/deploy/src/deploymentUtils.js index 6328e0a5a..583b4bf78 100644 --- a/deploy/src/deploymentUtils.js +++ b/deploy/src/deploymentUtils.js @@ -3,6 +3,7 @@ const Tx = require('ethereumjs-tx') const Web3Utils = require('web3-utils') const fetch = require('node-fetch') const assert = require('assert') +const promiseRetry = require('promise-retry') const { web3Home, web3Foreign, @@ -158,8 +159,7 @@ async function upgradeProxy({ proxy, implementationAddress, version, nonce, url if (result.status) { assert.strictEqual(Web3Utils.hexToNumber(result.status), 1, 'Transaction Failed') } else { - const implementation = await proxy.methods.implementation().call() - assert.strictEqual(implementation, implementationAddress, 'Transaction Failed') + await assertStateWithRetry(proxy.methods.implementation().call, implementationAddress) } } @@ -175,8 +175,7 @@ async function transferProxyOwnership({ proxy, newOwner, nonce, url }) { if (result.status) { assert.strictEqual(Web3Utils.hexToNumber(result.status), 1, 'Transaction Failed') } else { - const proxyOwner = await proxy.methods.proxyOwner().call() - assert.strictEqual(proxyOwner, newOwner, 'Transaction Failed') + await assertStateWithRetry(proxy.methods.proxyOwner().call, newOwner) } } @@ -192,8 +191,7 @@ async function transferOwnership({ contract, newOwner, nonce, url }) { if (result.status) { assert.strictEqual(Web3Utils.hexToNumber(result.status), 1, 'Transaction Failed') } else { - const owner = await contract.methods.owner().call() - assert.strictEqual(owner, newOwner, 'Transaction Failed') + await assertStateWithRetry(contract.methods.owner().call, newOwner) } } @@ -209,8 +207,7 @@ async function setBridgeContract({ contract, bridgeAddress, nonce, url }) { if (result.status) { assert.strictEqual(Web3Utils.hexToNumber(result.status), 1, 'Transaction Failed') } else { - const bridgeContract = await contract.methods.bridgeContract().call() - assert.strictEqual(bridgeContract, bridgeAddress, 'Transaction Failed') + await assertStateWithRetry(contract.methods.bridgeContract().call, bridgeAddress) } } @@ -249,11 +246,19 @@ async function initializeValidators({ if (result.status) { assert.strictEqual(Web3Utils.hexToNumber(result.status), 1, 'Transaction Failed') } else { - const isInitialized = await contract.methods.isInitialized().call() - assert.strictEqual(isInitialized, true, 'Transaction Failed') + await assertStateWithRetry(contract.methods.isInitialized().call, true) } } +async function assertStateWithRetry(fn, expected) { + return promiseRetry(async retry => { + const value = await fn() + if (value !== expected) { + retry(`Transaction Failed. Expected: ${expected} Actual: ${value}`) + } + }) +} + module.exports = { deployContract, sendRawTxHome, @@ -264,5 +269,6 @@ module.exports = { initializeValidators, transferProxyOwnership, transferOwnership, - setBridgeContract + setBridgeContract, + assertStateWithRetry } diff --git a/deploy/src/erc_to_erc/foreign.js b/deploy/src/erc_to_erc/foreign.js index 3bf2e89ce..3b8c20824 100644 --- a/deploy/src/erc_to_erc/foreign.js +++ b/deploy/src/erc_to_erc/foreign.js @@ -8,7 +8,8 @@ const { sendRawTxForeign, upgradeProxy, initializeValidators, - transferProxyOwnership + transferProxyOwnership, + assertStateWithRetry } = require('../deploymentUtils') const { web3Foreign, deploymentPrivateKey, FOREIGN_RPC_URL } = require('../web3') @@ -58,7 +59,7 @@ async function initializeBridge({ validatorsBridge, bridge, nonce }) { HOME_MAX_AMOUNT_PER_TX, FOREIGN_BRIDGE_OWNER ) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + .encodeABI() const txInitializeBridge = await sendRawTxForeign({ data: initializeFBridgeData, nonce, @@ -69,8 +70,7 @@ async function initializeBridge({ validatorsBridge, bridge, nonce }) { if (txInitializeBridge.status) { assert.strictEqual(Web3Utils.hexToNumber(txInitializeBridge.status), 1, 'Transaction Failed') } else { - const isInitialized = await bridge.methods.isInitialized().call() - assert.strictEqual(isInitialized, true, 'Transaction Failed') + await assertStateWithRetry(bridge.methods.isInitialized().call, true) } } diff --git a/deploy/src/erc_to_erc/home.js b/deploy/src/erc_to_erc/home.js index 0be6d6e34..dca5903c2 100644 --- a/deploy/src/erc_to_erc/home.js +++ b/deploy/src/erc_to_erc/home.js @@ -10,7 +10,8 @@ const { initializeValidators, transferProxyOwnership, setBridgeContract, - transferOwnership + transferOwnership, + assertStateWithRetry } = require('../deploymentUtils') const { web3Home, deploymentPrivateKey, HOME_RPC_URL } = require('../web3') @@ -67,7 +68,7 @@ async function initializeBridge({ validatorsBridge, bridge, erc677token, initial FOREIGN_MAX_AMOUNT_PER_TX, HOME_BRIDGE_OWNER ) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + .encodeABI() const txInitializeHomeBridge = await sendRawTxHome({ data: initializeHomeBridgeData, nonce, @@ -82,8 +83,7 @@ async function initializeBridge({ validatorsBridge, bridge, erc677token, initial 'Transaction Failed' ) } else { - const isInitialized = await bridge.methods.isInitialized().call() - assert.strictEqual(isInitialized, true, 'Transaction Failed') + await assertStateWithRetry(bridge.methods.isInitialized().call, true) } nonce++ diff --git a/deploy/src/erc_to_native/foreign.js b/deploy/src/erc_to_native/foreign.js index 7df12c831..b08fc3363 100644 --- a/deploy/src/erc_to_native/foreign.js +++ b/deploy/src/erc_to_native/foreign.js @@ -8,7 +8,8 @@ const { sendRawTxForeign, upgradeProxy, initializeValidators, - transferProxyOwnership + transferProxyOwnership, + assertStateWithRetry } = require('../deploymentUtils') const { web3Foreign, deploymentPrivateKey, FOREIGN_RPC_URL } = require('../web3') @@ -69,8 +70,7 @@ async function initializeBridge({ validatorsBridge, bridge, nonce }) { if (txInitializeBridge.status) { assert.strictEqual(Web3Utils.hexToNumber(txInitializeBridge.status), 1, 'Transaction Failed') } else { - const isInitialized = await bridge.methods.isInitialized().call() - assert.strictEqual(isInitialized, true, 'Transaction Failed') + await assertStateWithRetry(bridge.methods.isInitialized().call, true) } } diff --git a/deploy/src/erc_to_native/home.js b/deploy/src/erc_to_native/home.js index f0cef1256..05cd37f33 100644 --- a/deploy/src/erc_to_native/home.js +++ b/deploy/src/erc_to_native/home.js @@ -8,7 +8,8 @@ const { sendRawTxHome, upgradeProxy, initializeValidators, - transferProxyOwnership + transferProxyOwnership, + assertStateWithRetry } = require('../deploymentUtils') const { web3Home, deploymentPrivateKey, HOME_RPC_URL } = require('../web3') @@ -147,8 +148,7 @@ async function initializeBridge({ validatorsBridge, bridge, initialNonce }) { 'Transaction Failed' ) } else { - const isInitialized = await bridge.methods.isInitialized().call() - assert.strictEqual(isInitialized, true, 'Transaction Failed') + await assertStateWithRetry(bridge.methods.isInitialized().call, true) } nonce++ diff --git a/deploy/src/native_to_erc/foreign.js b/deploy/src/native_to_erc/foreign.js index a4a3051b9..049ca3bbc 100644 --- a/deploy/src/native_to_erc/foreign.js +++ b/deploy/src/native_to_erc/foreign.js @@ -10,7 +10,8 @@ const { initializeValidators, transferProxyOwnership, transferOwnership, - setBridgeContract + setBridgeContract, + assertStateWithRetry } = require('../deploymentUtils') const { web3Foreign, deploymentPrivateKey, FOREIGN_RPC_URL } = require('../web3') @@ -150,8 +151,7 @@ async function initializeBridge({ validatorsBridge, bridge, erc677bridgeToken, i if (txInitializeBridge.status) { assert.strictEqual(Web3Utils.hexToNumber(txInitializeBridge.status), 1, 'Transaction Failed') } else { - const isInitialized = await bridge.methods.isInitialized().call() - assert.strictEqual(isInitialized, true, 'Transaction Failed') + await assertStateWithRetry(bridge.methods.isInitialized().call, true) } nonce++ @@ -271,7 +271,8 @@ async function deployForeign() { await setBridgeContract({ contract: erc677bridgeToken, bridgeAddress: foreignBridgeStorage.options.address, - nonce + nonce, + url: FOREIGN_RPC_URL }) nonce++ @@ -294,8 +295,10 @@ async function deployForeign() { 'Transaction Failed' ) } else { - const blockRewardContract = await erc677bridgeToken.methods.blockRewardContract().call() - assert.strictEqual(blockRewardContract, BLOCK_REWARD_ADDRESS, 'Transaction Failed') + await assertStateWithRetry( + erc677bridgeToken.methods.blockRewardContract().call, + BLOCK_REWARD_ADDRESS + ) } nonce++ @@ -317,14 +320,11 @@ async function deployForeign() { 'Transaction Failed' ) } else { - const validatorSetContract = await erc677bridgeToken.methods.validatorSetContract().call() - assert.strictEqual(validatorSetContract, DPOS_VALIDATOR_SET_ADDRESS, 'Transaction Failed') + await assertStateWithRetry( + erc677bridgeToken.methods.validatorSetContract().call, + DPOS_VALIDATOR_SET_ADDRESS + ) } - assert.strictEqual( - Web3Utils.hexToNumber(setValidatorSetContract.status), - 1, - 'Transaction Failed' - ) nonce++ } diff --git a/deploy/src/native_to_erc/home.js b/deploy/src/native_to_erc/home.js index aff0faedb..414dca095 100644 --- a/deploy/src/native_to_erc/home.js +++ b/deploy/src/native_to_erc/home.js @@ -8,7 +8,8 @@ const { sendRawTxHome, upgradeProxy, initializeValidators, - transferProxyOwnership + transferProxyOwnership, + assertStateWithRetry } = require('../deploymentUtils') const { web3Home, deploymentPrivateKey, HOME_RPC_URL } = require('../web3') @@ -150,8 +151,7 @@ async function initializeBridge({ validatorsBridge, bridge, initialNonce }) { 'Transaction Failed' ) } else { - const isInitialized = await bridge.methods.isInitialized().call() - assert.strictEqual(isInitialized, true, 'Transaction Failed') + await assertStateWithRetry(bridge.methods.isInitialized().call, true) } nonce++ From 4d50918a291260bc9657a2da90a8aaf630dfaef2 Mon Sep 17 00:00:00 2001 From: Vadim Date: Tue, 5 Mar 2019 08:43:21 +0300 Subject: [PATCH 111/187] Rename ValidatorSet contract to Staking contract --- contracts/ERC677BridgeTokenRewardable.sol | 34 ++++---- contracts/test/Staking.sol | 6 ++ contracts/test/ValidatorSet.sol | 6 -- deploy/.env.example | 5 +- deploy/README.md | 14 +++- deploy/src/erc_to_erc/home.js | 38 ++++++++- deploy/src/loadEnv.js | 7 +- deploy/src/native_to_erc/foreign.js | 14 ++-- .../ERC677BridgeTokenRewardableMock.sol | 4 +- test/poa20_test.js | 78 +++++++++---------- 10 files changed, 126 insertions(+), 80 deletions(-) create mode 100644 contracts/test/Staking.sol delete mode 100644 contracts/test/ValidatorSet.sol diff --git a/contracts/ERC677BridgeTokenRewardable.sol b/contracts/ERC677BridgeTokenRewardable.sol index 3caf2ac7d..d12c93482 100644 --- a/contracts/ERC677BridgeTokenRewardable.sol +++ b/contracts/ERC677BridgeTokenRewardable.sol @@ -6,7 +6,7 @@ import "./ERC677BridgeToken.sol"; contract ERC677BridgeTokenRewardable is ERC677BridgeToken { address public blockRewardContract; - address public validatorSetContract; + address public stakingContract; constructor( string _name, @@ -19,9 +19,9 @@ contract ERC677BridgeTokenRewardable is ERC677BridgeToken { blockRewardContract = _blockRewardContract; } - function setValidatorSetContract(address _validatorSetContract) onlyOwner public { - require(_validatorSetContract != address(0) && isContract(_validatorSetContract)); - validatorSetContract = _validatorSetContract; + function setStakingContract(address _stakingContract) onlyOwner public { + require(_stakingContract != address(0) && isContract(_stakingContract)); + stakingContract = _stakingContract; } modifier onlyBlockRewardContract() { @@ -29,8 +29,8 @@ contract ERC677BridgeTokenRewardable is ERC677BridgeToken { _; } - modifier onlyValidatorSetContract() { - require(msg.sender == validatorSetContract); + modifier onlyStakingContract() { + require(msg.sender == stakingContract); _; } @@ -47,29 +47,29 @@ contract ERC677BridgeTokenRewardable is ERC677BridgeToken { } } - function stake(address _staker, uint256 _amount) external onlyValidatorSetContract { - // Transfer `_amount` from `_staker` to `validatorSetContract` + function stake(address _staker, uint256 _amount) external onlyStakingContract { + // Transfer `_amount` from `_staker` to `stakingContract` require(_amount <= balances[_staker]); balances[_staker] = balances[_staker].sub(_amount); - balances[validatorSetContract] = balances[validatorSetContract].add(_amount); - emit Transfer(_staker, validatorSetContract, _amount); + balances[stakingContract] = balances[stakingContract].add(_amount); + emit Transfer(_staker, stakingContract, _amount); } - function withdraw(address _staker, uint256 _amount) external onlyValidatorSetContract { - // Transfer `_amount` from `validatorSetContract` to `_staker` - require(_amount <= balances[validatorSetContract]); - balances[validatorSetContract] = balances[validatorSetContract].sub(_amount); + function withdraw(address _staker, uint256 _amount) external onlyStakingContract { + // Transfer `_amount` from `stakingContract` to `_staker` + require(_amount <= balances[stakingContract]); + balances[stakingContract] = balances[stakingContract].sub(_amount); balances[_staker] = balances[_staker].add(_amount); - emit Transfer(validatorSetContract, _staker, _amount); + emit Transfer(stakingContract, _staker, _amount); } function transfer(address _to, uint256 _value) public returns(bool) { - require(_to != validatorSetContract); + require(_to != stakingContract); return super.transfer(_to, _value); } function transferFrom(address _from, address _to, uint256 _value) public returns(bool) { - require(_to != validatorSetContract); + require(_to != stakingContract); return super.transferFrom(_from, _to, _value); } diff --git a/contracts/test/Staking.sol b/contracts/test/Staking.sol new file mode 100644 index 000000000..b9e39b7ef --- /dev/null +++ b/contracts/test/Staking.sol @@ -0,0 +1,6 @@ +pragma solidity 0.4.24; + + +contract Staking { + constructor() public {} +} diff --git a/contracts/test/ValidatorSet.sol b/contracts/test/ValidatorSet.sol deleted file mode 100644 index d715ffaa8..000000000 --- a/contracts/test/ValidatorSet.sol +++ /dev/null @@ -1,6 +0,0 @@ -pragma solidity 0.4.24; - - -contract ValidatorSet { - constructor() {} -} diff --git a/deploy/.env.example b/deploy/.env.example index 8145284f6..fd30605a8 100644 --- a/deploy/.env.example +++ b/deploy/.env.example @@ -20,7 +20,6 @@ HOME_MIN_AMOUNT_PER_TX=500000000000000000 HOME_REQUIRED_BLOCK_CONFIRMATIONS=1 HOME_GAS_PRICE=1000000000 -#for bridge erc_to_native and native_to_erc mode BLOCK_REWARD_ADDRESS= FOREIGN_RPC_URL=https://sokol.poa.network @@ -40,6 +39,6 @@ REQUIRED_NUMBER_OF_VALIDATORS=1 #E.g. VALIDATORS=0x 0x 0x VALIDATORS=0x -#for bridge native_to_erc mode +#for bridge native_to_erc, erc_to_erc mode DEPLOY_REWARDABLE_TOKEN=false -DPOS_VALIDATOR_SET_ADDRESS= +DPOS_STAKING_ADDRESS= diff --git a/deploy/README.md b/deploy/README.md index 34a280eea..4bb64487a 100644 --- a/deploy/README.md +++ b/deploy/README.md @@ -127,9 +127,9 @@ VALIDATORS=0x 0x 0x # The flag defining whether to use ERC677BridgeTokenRewardable contract instead of # ERC677BridgeToken. DEPLOY_REWARDABLE_TOKEN=false -# The address of ValidatorSet contract used by ERC677BridgeTokenRewardable contract. +# The address of Staking contract used by ERC677BridgeTokenRewardable contract. # Makes sense only when DEPLOY_REWARDABLE_TOKEN=true -DPOS_VALIDATOR_SET_ADDRESS=0x +DPOS_STAKING_ADDRESS=0x # The address of BlockReward contract used by ERC677BridgeTokenRewardable contract. # Makes sense only when DEPLOY_REWARDABLE_TOKEN=true BLOCK_REWARD_ADDRESS=0x @@ -233,6 +233,16 @@ REQUIRED_NUMBER_OF_VALIDATORS=1 # the Foreign network to confirm that the finalized agreement was transferred # correctly to the Foreign network. VALIDATORS=0x 0x 0x + +# The flag defining whether to use ERC677BridgeTokenRewardable contract instead of +# ERC677BridgeToken. +DEPLOY_REWARDABLE_TOKEN=false +# The address of Staking contract used by ERC677BridgeTokenRewardable contract. +# Makes sense only when DEPLOY_REWARDABLE_TOKEN=true +DPOS_STAKING_ADDRESS=0x +# The address of BlockReward contract used by ERC677BridgeTokenRewardable contract. +# Makes sense only when DEPLOY_REWARDABLE_TOKEN=true +BLOCK_REWARD_ADDRESS=0x ``` ## `ERC-TO-NATIVE` Bridge Mode Configuration Example. diff --git a/deploy/src/erc_to_erc/home.js b/deploy/src/erc_to_erc/home.js index d8f238d21..373f8ab01 100644 --- a/deploy/src/erc_to_erc/home.js +++ b/deploy/src/erc_to_erc/home.js @@ -9,6 +9,7 @@ const EternalStorageProxy = require('../../../build/contracts/EternalStorageProx const BridgeValidators = require('../../../build/contracts/BridgeValidators.json') const HomeBridge = require('../../../build/contracts/HomeBridgeErcToErc.json') const ERC677BridgeToken = require('../../../build/contracts/ERC677BridgeToken.json') +const ERC677BridgeTokenRewardable = require('../../../build/contracts/ERC677BridgeTokenRewardable.json') const VALIDATORS = env.VALIDATORS.split(' ') @@ -27,7 +28,10 @@ const { BRIDGEABLE_TOKEN_SYMBOL, BRIDGEABLE_TOKEN_DECIMALS, FOREIGN_DAILY_LIMIT, - FOREIGN_MAX_AMOUNT_PER_TX + FOREIGN_MAX_AMOUNT_PER_TX, + DEPLOY_REWARDABLE_TOKEN, + BLOCK_REWARD_ADDRESS, + DPOS_STAKING_ADDRESS } = env const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVATE_KEY) @@ -128,7 +132,7 @@ async function deployHome() { console.log('\n[Home] deploying Bridgeble token') const erc677token = await deployContract( - ERC677BridgeToken, + EPLOY_REWARDABLE_TOKEN ? ERC677BridgeTokenRewardable : ERC677BridgeToken, [BRIDGEABLE_TOKEN_NAME, BRIDGEABLE_TOKEN_SYMBOL, BRIDGEABLE_TOKEN_DECIMALS], { from: DEPLOYMENT_ACCOUNT_ADDRESS, network: 'home', nonce: homeNonce } ) @@ -149,6 +153,36 @@ async function deployHome() { assert.strictEqual(Web3Utils.hexToNumber(setBridgeContract.status), 1, 'Transaction Failed') homeNonce++ + if (DEPLOY_REWARDABLE_TOKEN) { + console.log('\nset BlockReward contract on ERC677BridgeTokenRewardable') + const setBlockRewardContractData = await erc677token.methods + .setBlockRewardContract(BLOCK_REWARD_ADDRESS) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + const setBlockRewardContract = await sendRawTxHome({ + data: setBlockRewardContractData, + nonce: homeNonce, + to: erc677token.options.address, + privateKey: deploymentPrivateKey, + url: HOME_RPC_URL + }) + assert.strictEqual(Web3Utils.hexToNumber(setBlockRewardContract.status), 1, 'Transaction Failed') + homeNonce++ + + console.log('\nset Staking contract on ERC677BridgeTokenRewardable') + const setStakingContractData = await erc677token.methods + .setStakingContract(DPOS_STAKING_ADDRESS) + .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + const setStakingContract = await sendRawTxHome({ + data: setStakingContractData, + nonce: homeNonce, + to: erc677token.options.address, + privateKey: deploymentPrivateKey, + url: HOME_RPC_URL + }) + assert.strictEqual(Web3Utils.hexToNumber(setStakingContract.status), 1, 'Transaction Failed') + homeNonce++ + } + console.log('transferring ownership of Bridgeble token to homeBridge contract') const txOwnershipData = await erc677token.methods .transferOwnership(homeBridgeStorage.options.address) diff --git a/deploy/src/loadEnv.js b/deploy/src/loadEnv.js index 8b3d9f36e..61733c9fb 100644 --- a/deploy/src/loadEnv.js +++ b/deploy/src/loadEnv.js @@ -63,7 +63,7 @@ if (BRIDGE_MODE === 'NATIVE_TO_ERC') { FOREIGN_MAX_AMOUNT_PER_TX: bigNumValidator(), FOREIGN_MIN_AMOUNT_PER_TX: bigNumValidator(), DEPLOY_REWARDABLE_TOKEN: envalid.bool(), - DPOS_VALIDATOR_SET_ADDRESS: addressValidator(), + DPOS_STAKING_ADDRESS: addressValidator(), BLOCK_REWARD_ADDRESS: addressValidator() } } @@ -73,7 +73,10 @@ if (BRIDGE_MODE === 'ERC_TO_ERC') { ERC20_TOKEN_ADDRESS: addressValidator(), BRIDGEABLE_TOKEN_NAME: envalid.str(), BRIDGEABLE_TOKEN_SYMBOL: envalid.str(), - BRIDGEABLE_TOKEN_DECIMALS: envalid.num() + BRIDGEABLE_TOKEN_DECIMALS: envalid.num(), + DEPLOY_REWARDABLE_TOKEN: envalid.bool(), + DPOS_STAKING_ADDRESS: addressValidator(), + BLOCK_REWARD_ADDRESS: addressValidator() } } if (BRIDGE_MODE === 'ERC_TO_NATIVE') { diff --git a/deploy/src/native_to_erc/foreign.js b/deploy/src/native_to_erc/foreign.js index 0b70c62bf..c23bc1f6b 100644 --- a/deploy/src/native_to_erc/foreign.js +++ b/deploy/src/native_to_erc/foreign.js @@ -31,7 +31,7 @@ const { HOME_MAX_AMOUNT_PER_TX, DEPLOY_REWARDABLE_TOKEN, BLOCK_REWARD_ADDRESS, - DPOS_VALIDATOR_SET_ADDRESS + DPOS_STAKING_ADDRESS } = env const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVATE_KEY) @@ -231,18 +231,18 @@ async function deployForeign() { assert.equal(Web3Utils.hexToNumber(setBlockRewardContract.status), 1, 'Transaction Failed') foreignNonce++ - console.log('\nset ValidatorSet contract on ERC677BridgeTokenRewardable') - const setValidatorSetContractData = await erc677bridgeToken.methods - .setValidatorSetContract(DPOS_VALIDATOR_SET_ADDRESS) + console.log('\nset Staking contract on ERC677BridgeTokenRewardable') + const setStakingContractData = await erc677bridgeToken.methods + .setStakingContract(DPOS_STAKING_ADDRESS) .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const setValidatorSetContract = await sendRawTxForeign({ - data: setValidatorSetContractData, + const setStakingContract = await sendRawTxForeign({ + data: setStakingContractData, nonce: foreignNonce, to: erc677bridgeToken.options.address, privateKey: deploymentPrivateKey, url: FOREIGN_RPC_URL }) - assert.equal(Web3Utils.hexToNumber(setValidatorSetContract.status), 1, 'Transaction Failed') + assert.equal(Web3Utils.hexToNumber(setStakingContract.status), 1, 'Transaction Failed') foreignNonce++ } diff --git a/test/mockContracts/ERC677BridgeTokenRewardableMock.sol b/test/mockContracts/ERC677BridgeTokenRewardableMock.sol index 7edad2fc3..2fd7f0c97 100644 --- a/test/mockContracts/ERC677BridgeTokenRewardableMock.sol +++ b/test/mockContracts/ERC677BridgeTokenRewardableMock.sol @@ -15,8 +15,8 @@ contract ERC677BridgeTokenRewardableMock is ERC677BridgeTokenRewardable { blockRewardContract = _blockRewardContract; } - function setValidatorSetContractMock(address _validatorSetContract) public { - validatorSetContract = _validatorSetContract; + function setStakingContractMock(address _stakingContract) public { + stakingContract = _stakingContract; } } diff --git a/test/poa20_test.js b/test/poa20_test.js index 1df1459c9..95fb49904 100644 --- a/test/poa20_test.js +++ b/test/poa20_test.js @@ -2,7 +2,7 @@ const POA20 = artifacts.require("ERC677BridgeToken.sol"); const POA20RewardableMock = artifacts.require("./mockContracts/ERC677BridgeTokenRewardableMock"); const ERC677ReceiverTest = artifacts.require("ERC677ReceiverTest.sol") const BlockRewardTest = artifacts.require("BlockReward.sol") -const ValidatorSetTest = artifacts.require("ValidatorSet.sol") +const StakingTest = artifacts.require("Staking.sol") const { ERROR_MSG, ZERO_ADDRESS} = require('./setup'); const Web3Utils = require('web3-utils'); const HomeErcToErcBridge = artifacts.require("HomeBridgeErcToErc.sol"); @@ -114,36 +114,36 @@ async function testERC677BridgeToken(accounts, rewardable) { }) }) - describe('#validatorSetContract', async() => { - it('can set ValidatorSet contract', async () => { - const validatorSetContract = await ValidatorSetTest.new(); - (await token.validatorSetContract()).should.be.equal(ZERO_ADDRESS); + describe('#stakingContract', async() => { + it('can set Staking contract', async () => { + const stakingContract = await StakingTest.new(); + (await token.stakingContract()).should.be.equal(ZERO_ADDRESS); - await token.setValidatorSetContract(validatorSetContract.address).should.be.fulfilled; + await token.setStakingContract(stakingContract.address).should.be.fulfilled; - (await token.validatorSetContract()).should.be.equal(validatorSetContract.address); + (await token.stakingContract()).should.be.equal(stakingContract.address); }) - it('only owner can set ValidatorSet contract', async () => { - const validatorSetContract = await ValidatorSetTest.new(); - (await token.validatorSetContract()).should.be.equal(ZERO_ADDRESS); + it('only owner can set Staking contract', async () => { + const stakingContract = await StakingTest.new(); + (await token.stakingContract()).should.be.equal(ZERO_ADDRESS); - await token.setValidatorSetContract(validatorSetContract.address, {from: user }).should.be.rejectedWith(ERROR_MSG); - (await token.validatorSetContract()).should.be.equal(ZERO_ADDRESS); + await token.setStakingContract(stakingContract.address, {from: user }).should.be.rejectedWith(ERROR_MSG); + (await token.stakingContract()).should.be.equal(ZERO_ADDRESS); - await token.setValidatorSetContract(validatorSetContract.address, {from: owner }).should.be.fulfilled; - (await token.validatorSetContract()).should.be.equal(validatorSetContract.address); + await token.setStakingContract(stakingContract.address, {from: owner }).should.be.fulfilled; + (await token.stakingContract()).should.be.equal(stakingContract.address); }) - it('fail to set invalid ValidatorSet contract address', async () => { + it('fail to set invalid Staking contract address', async () => { const invalidContractAddress = '0xaaB52d66283F7A1D5978bcFcB55721ACB467384b'; - (await token.validatorSetContract()).should.be.equal(ZERO_ADDRESS); + (await token.stakingContract()).should.be.equal(ZERO_ADDRESS); - await token.setValidatorSetContract(invalidContractAddress).should.be.rejectedWith(ERROR_MSG); - (await token.validatorSetContract()).should.be.equal(ZERO_ADDRESS); + await token.setStakingContract(invalidContractAddress).should.be.rejectedWith(ERROR_MSG); + (await token.stakingContract()).should.be.equal(ZERO_ADDRESS); - await token.setValidatorSetContract(ZERO_ADDRESS).should.be.rejectedWith(ERROR_MSG); - (await token.validatorSetContract()).should.be.equal(ZERO_ADDRESS); + await token.setStakingContract(ZERO_ADDRESS).should.be.rejectedWith(ERROR_MSG); + (await token.stakingContract()).should.be.equal(ZERO_ADDRESS); }) }) @@ -174,10 +174,10 @@ async function testERC677BridgeToken(accounts, rewardable) { }) describe('#stake', async() => { - it('can only be called by ValidatorSet contract', async () => { + it('can only be called by Staking contract', async () => { await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled; await token.mintReward([user], [100], {from: accounts[2] }).should.be.fulfilled; - await token.setValidatorSetContractMock(accounts[3]).should.be.fulfilled; + await token.setStakingContractMock(accounts[3]).should.be.fulfilled; await token.stake(user, 100, {from: accounts[4] }).should.be.rejectedWith(ERROR_MSG); await token.stake(user, 100, {from: accounts[3] }).should.be.fulfilled; }) @@ -185,15 +185,15 @@ async function testERC677BridgeToken(accounts, rewardable) { await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled; await token.mintReward([user], [99], {from: accounts[2] }).should.be.fulfilled; (await token.balanceOf(user)).should.be.bignumber.equal(99); - await token.setValidatorSetContractMock(accounts[3]).should.be.fulfilled; + await token.setStakingContractMock(accounts[3]).should.be.fulfilled; await token.stake(user, 100, {from: accounts[3] }).should.be.rejectedWith(ERROR_MSG); }) - it('should decrease user\'s balance and increase ValidatorSet\'s balance', async () => { + it('should decrease user\'s balance and increase Staking\'s balance', async () => { await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled; await token.mintReward([user], [100], {from: accounts[2] }).should.be.fulfilled; (await token.balanceOf(user)).should.be.bignumber.equal(100); (await token.balanceOf(accounts[3])).should.be.bignumber.equal(0); - await token.setValidatorSetContractMock(accounts[3]).should.be.fulfilled; + await token.setStakingContractMock(accounts[3]).should.be.fulfilled; await token.stake(user, 100, {from: accounts[3] }).should.be.fulfilled; (await token.balanceOf(user)).should.be.bignumber.equal(0); (await token.balanceOf(accounts[3])).should.be.bignumber.equal(100); @@ -201,29 +201,29 @@ async function testERC677BridgeToken(accounts, rewardable) { }) describe('#withdraw', async() => { - it('can only be called by ValidatorSet contract', async () => { + it('can only be called by Staking contract', async () => { await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled; await token.mintReward([user], [100], {from: accounts[2] }).should.be.fulfilled; - await token.setValidatorSetContractMock(accounts[3]).should.be.fulfilled; + await token.setStakingContractMock(accounts[3]).should.be.fulfilled; await token.stake(user, 100, {from: accounts[3] }).should.be.fulfilled; await token.withdraw(user, 100, {from: accounts[4] }).should.be.rejectedWith(ERROR_MSG); await token.withdraw(user, 100, {from: accounts[3] }).should.be.fulfilled; }) - it('should revert if ValidatorSet doesn\'t have enough balance', async () => { + it('should revert if Staking doesn\'t have enough balance', async () => { await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled; await token.mintReward([user], [100], {from: accounts[2] }).should.be.fulfilled; (await token.balanceOf(user)).should.be.bignumber.equal(100); - await token.setValidatorSetContractMock(accounts[3]).should.be.fulfilled; + await token.setStakingContractMock(accounts[3]).should.be.fulfilled; await token.stake(user, 100, {from: accounts[3] }).should.be.fulfilled; await token.withdraw(user, 101, {from: accounts[3] }).should.be.rejectedWith(ERROR_MSG); await token.withdraw(user, 100, {from: accounts[3] }).should.be.fulfilled; }) - it('should decrease ValidatorSet\'s balance and increase user\'s balance', async () => { + it('should decrease Staking\'s balance and increase user\'s balance', async () => { await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled; await token.mintReward([user], [100], {from: accounts[2] }).should.be.fulfilled; (await token.balanceOf(user)).should.be.bignumber.equal(100); (await token.balanceOf(accounts[3])).should.be.bignumber.equal(0); - await token.setValidatorSetContractMock(accounts[3]).should.be.fulfilled; + await token.setStakingContractMock(accounts[3]).should.be.fulfilled; await token.stake(user, 100, {from: accounts[3] }).should.be.fulfilled; (await token.balanceOf(user)).should.be.bignumber.equal(0); (await token.balanceOf(accounts[3])).should.be.bignumber.equal(100); @@ -332,13 +332,13 @@ async function testERC677BridgeToken(accounts, rewardable) { }) if (rewardable) { - it('fail to send tokens to ValidatorSet contract directly', async () => { + it('fail to send tokens to Staking contract directly', async () => { const amount = web3.toWei(1, "ether"); - const validatorSetContractAddress = accounts[2]; + const stakingContractAddress = accounts[2]; const arbitraryAccountAddress = accounts[3]; - await token.setValidatorSetContractMock(validatorSetContractAddress, {from: owner}).should.be.fulfilled; + await token.setStakingContractMock(stakingContractAddress, {from: owner}).should.be.fulfilled; await token.mint(user, amount, {from: owner}).should.be.fulfilled; - await token.transfer(validatorSetContractAddress, amount, {from: user}).should.be.rejectedWith(ERROR_MSG); + await token.transfer(stakingContractAddress, amount, {from: user}).should.be.rejectedWith(ERROR_MSG); await token.transfer(arbitraryAccountAddress, amount, {from: user}).should.be.fulfilled; }); } @@ -346,15 +346,15 @@ async function testERC677BridgeToken(accounts, rewardable) { if (rewardable) { describe('#transferFrom', async() => { - it('fail to send tokens to ValidatorSet contract directly', async () => { + it('fail to send tokens to Staking contract directly', async () => { const amount = web3.toWei(1, "ether"); const user2 = accounts[2]; - const validatorSetContractAddress = accounts[3]; + const stakingContractAddress = accounts[3]; const arbitraryAccountAddress = accounts[4]; - await token.setValidatorSetContractMock(validatorSetContractAddress, {from: owner}).should.be.fulfilled; + await token.setStakingContractMock(stakingContractAddress, {from: owner}).should.be.fulfilled; await token.mint(user, amount, {from: owner}).should.be.fulfilled; await token.approve(user2, amount, {from: user}).should.be.fulfilled; - await token.transferFrom(user, validatorSetContractAddress, amount, {from: user2}).should.be.rejectedWith(ERROR_MSG); + await token.transferFrom(user, stakingContractAddress, amount, {from: user2}).should.be.rejectedWith(ERROR_MSG); await token.transferFrom(user, arbitraryAccountAddress, amount, {from: user2}).should.be.fulfilled; }); }); From b043eb0df2b2c4579f006782af99418d0042e9ee Mon Sep 17 00:00:00 2001 From: Vadim Date: Tue, 5 Mar 2019 08:52:27 +0300 Subject: [PATCH 112/187] Fix misprint --- deploy/src/erc_to_erc/home.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/deploy/src/erc_to_erc/home.js b/deploy/src/erc_to_erc/home.js index 373f8ab01..fd8655f71 100644 --- a/deploy/src/erc_to_erc/home.js +++ b/deploy/src/erc_to_erc/home.js @@ -132,7 +132,7 @@ async function deployHome() { console.log('\n[Home] deploying Bridgeble token') const erc677token = await deployContract( - EPLOY_REWARDABLE_TOKEN ? ERC677BridgeTokenRewardable : ERC677BridgeToken, + DEPLOY_REWARDABLE_TOKEN ? ERC677BridgeTokenRewardable : ERC677BridgeToken, [BRIDGEABLE_TOKEN_NAME, BRIDGEABLE_TOKEN_SYMBOL, BRIDGEABLE_TOKEN_DECIMALS], { from: DEPLOYMENT_ACCOUNT_ADDRESS, network: 'home', nonce: homeNonce } ) From 30e0ae82c8f9bea4953b271dd403f737c23d5ed7 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 12 Mar 2019 09:45:29 -0300 Subject: [PATCH 113/187] Revert "140-erc-to-erc-multiple" --- .gitignore | 1 - GAS_CONSUMPTION.md | 63 - contracts/IBridgeValidators.sol | 1 - contracts/IForeignBridge.sol | 16 - contracts/IHomeBridge.sol | 18 - contracts/upgradeability/EternalStorage.sol | 8 - contracts/upgradeability/Proxy.sol | 27 +- .../upgradeability/UpgradeabilityStorage.sol | 5 - .../upgradeable_contracts/BasicBridge.sol | 4 +- .../upgradeable_contracts/BridgeMapper.sol | 94 - .../BridgeValidators.sol | 4 +- .../{EternalOwnable.sol => Ownable.sol} | 8 +- .../factories/BasicBridgeFactory.sol | 101 - .../factories/ForeignBridgeFactory.sol | 107 - .../factories/HomeBridgeFactory.sol | 134 - deploy/.env.example | 12 - deploy/README.md | 102 - deploy/deploy.js | 38 +- deploy/package-lock.json | 3087 +++-- deploy/src/factories/foreign.js | 246 - deploy/src/factories/home.js | 318 - deploy/src/loadEnv.js | 10 +- flatten.sh | 5 - package-lock.json | 11268 ++++++---------- package.json | 2 +- test/factories/foreign_factory.test.js | 138 - test/factories/home_factory.test.js | 149 - test/helpers/helpers.js | 5 - test/mapper/home_mapper.test.js | 160 - 29 files changed, 5728 insertions(+), 10403 deletions(-) delete mode 100644 contracts/IForeignBridge.sol delete mode 100644 contracts/IHomeBridge.sol delete mode 100644 contracts/upgradeable_contracts/BridgeMapper.sol rename contracts/upgradeable_contracts/{EternalOwnable.sol => Ownable.sol} (85%) delete mode 100644 contracts/upgradeable_contracts/factories/BasicBridgeFactory.sol delete mode 100644 contracts/upgradeable_contracts/factories/ForeignBridgeFactory.sol delete mode 100644 contracts/upgradeable_contracts/factories/HomeBridgeFactory.sol delete mode 100644 deploy/src/factories/foreign.js delete mode 100644 deploy/src/factories/home.js delete mode 100644 test/factories/foreign_factory.test.js delete mode 100644 test/factories/home_factory.test.js delete mode 100644 test/mapper/home_mapper.test.js diff --git a/.gitignore b/.gitignore index 1bef161d2..de8a6acc7 100644 --- a/.gitignore +++ b/.gitignore @@ -2,4 +2,3 @@ node_modules build flats .node* -deploy/bridgeDeploymentOutput.txt diff --git a/GAS_CONSUMPTION.md b/GAS_CONSUMPTION.md index ab0214adf..88cc9ae49 100644 --- a/GAS_CONSUMPTION.md +++ b/GAS_CONSUMPTION.md @@ -172,66 +172,3 @@ To request transfer from the Home to the Foreign| HomeBridgeErcToNative|fallback|80174|80174|80174 To request transfer from the Foreign to the Home| ERC677BridgeToken|transfer|37691|86589|55000 - -### Bridge Factories - -#### Deployment -##### Home - Contract | Method | Min | Max | Avg ----- | ---- | ---- | ---- | ---- -BridgeValidators|deployment|1144207|1144207|1144207 -EternalStorageProxy|deployment|378510|378510|378510 -EternalStorageProxy|upgradeTo|35871|30924|30913 -EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -HomeBridgeErcToErc|initialize|212299|213195|213003 -EternalStorageProxy|deployment|378510|378510|378510 -HomeBridgeFactory|deployment|||4337543 -EternalStorageProxy|upgradeTo|35871|30924|30913 -HomeBridgeFactory|initialize|||433239 -EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |||7008144 - -##### Foreign - Contract | Method | Min | Max | Avg ----- | ---- | ---- | ---- | ---- -BridgeValidators|deployment|1144207|1144207|1144207 -ForeignBridgeErcToErc|deployment|2449436|2449436|2449436 -EternalStorageProxy|deployment|378510|378510|378510 -ForeignBridgeFactory|deployment|||2515108 -EternalStorageProxy|upgradeTo|35871|30924|30913 -ForeignBridgeFactory|initialize|||390192 -EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |||6939019 - -#### Usage -##### Users - - Contract | Method | Min | Max | Avg ----- | ---- | ---- | ---- | ---- -To deploy Home bridge| -HomeBridgeFactory|deployHomeBridge|2238032|2238672|2238213 -To deploy Foreign bridge| -ForeignBridgeFactory|deployForeignBridge|1056602|1056666|1056655 - -### Mapper - -#### Deployment -##### Home - Contract | Method | Min | Max | Avg ----- | ---- | ---- | ---- | ---- -EternalStorageProxy|deployment|378510|378510|378510 -BridgeMapper|deployment|||1107983 -EternalStorageProxy|upgradeTo|35871|30924|30913 -BridgeMapper|initialize|||68122 -EternalStorageProxy|transferProxyOwnership|30653|30653|30653 -Total| |||1616181 - -#### Usage -##### Users - - Contract | Method | Min | Max | Avg ----- | ---- | ---- | ---- | ---- -To add bridge mapping| -BridgeMapper|addBridgeMapping|||136441 -To remove bridge mapping| -BridgeMapper|removeBridgeMapping|||28283 \ No newline at end of file diff --git a/contracts/IBridgeValidators.sol b/contracts/IBridgeValidators.sol index 775e94194..2732ae41e 100644 --- a/contracts/IBridgeValidators.sol +++ b/contracts/IBridgeValidators.sol @@ -2,7 +2,6 @@ pragma solidity 0.4.24; interface IBridgeValidators { - function initialize(uint256 _requiredSignatures, address[] _initialValidators, address _owner) public returns(bool); function isValidator(address _validator) public view returns(bool); function requiredSignatures() public view returns(uint256); function owner() public view returns(address); diff --git a/contracts/IForeignBridge.sol b/contracts/IForeignBridge.sol deleted file mode 100644 index 7262d9dd5..000000000 --- a/contracts/IForeignBridge.sol +++ /dev/null @@ -1,16 +0,0 @@ -pragma solidity 0.4.24; - -contract IForeignBridge { - - function initialize( - address _validatorContract, - address _erc20token, - uint256 _requiredBlockConfirmations, - uint256 _gasPrice, - uint256 _maxPerTx, - uint256 _homeDailyLimit, - uint256 _homeMaxPerTx, - address _owner - ) public returns(bool); - -} diff --git a/contracts/IHomeBridge.sol b/contracts/IHomeBridge.sol deleted file mode 100644 index 5e047d172..000000000 --- a/contracts/IHomeBridge.sol +++ /dev/null @@ -1,18 +0,0 @@ -pragma solidity 0.4.24; - -contract IHomeBridge { - - function initialize( - address _validatorContract, - uint256 _dailyLimit, - uint256 _maxPerTx, - uint256 _minPerTx, - uint256 _homeGasPrice, - uint256 _requiredBlockConfirmations, - address _erc677token, - uint256 _foreignDailyLimit, - uint256 _foreignMaxPerTx, - address _owner - ) public returns(bool); - -} diff --git a/contracts/upgradeability/EternalStorage.sol b/contracts/upgradeability/EternalStorage.sol index b9d6c0e1f..a8702dcab 100644 --- a/contracts/upgradeability/EternalStorage.sol +++ b/contracts/upgradeability/EternalStorage.sol @@ -14,12 +14,4 @@ contract EternalStorage { mapping(bytes32 => bool) internal boolStorage; mapping(bytes32 => int256) internal intStorage; - - mapping(bytes32 => uint256[]) internal uintArrayStorage; - mapping(bytes32 => string[]) internal stringArrayStorage; - mapping(bytes32 => address[]) internal addressArrayStorage; - //mapping(bytes32 => bytes[]) internal bytesArrayStorage; - mapping(bytes32 => bool[]) internal boolArrayStorage; - mapping(bytes32 => int256[]) internal intArrayStorage; - mapping(bytes32 => bytes32[]) internal bytes32ArrayStorage; } diff --git a/contracts/upgradeability/Proxy.sol b/contracts/upgradeability/Proxy.sol index c9362b8fe..fc58c19b3 100644 --- a/contracts/upgradeability/Proxy.sol +++ b/contracts/upgradeability/Proxy.sol @@ -13,8 +13,6 @@ contract Proxy { */ function implementation() public view returns (address); - function setImplementation(address _newImplementation) external; - /** * @dev Fallback function allowing to perform a delegatecall to the given implementation. * This function will return whatever the implementation call returns @@ -22,16 +20,6 @@ contract Proxy { function () payable public { address _impl = implementation(); require(_impl != address(0)); - - address _innerImpl; - bytes4 sig; - address thisAddress = address(this); - if (_impl.call(0x5c60da1b)) { // bytes(keccak256("implementation()")) - _innerImpl = Proxy(_impl).implementation(); - this.setImplementation(_innerImpl); - sig = 0xd784d426; // bytes4(keccak256("setImplementation(address)")) - } - assembly { /* 0x40 is the "free memory slot", meaning a pointer to next slot of empty memory. mload(0x40) @@ -91,25 +79,14 @@ contract Proxy { */ returndatacopy(ptr, 0, returndatasize) - let retdatasize := returndatasize - - switch sig - case 0 {} - default { - let x := mload(0x40) - mstore(x, sig) - mstore(add(x, 0x04), _impl) - let success := call(gas, thisAddress, 0, x, 0x24, x, 0x0) - } - /* if `result` is 0, revert. if `result` is 1, return `size` amount of data from `ptr`. This is the data that was copied to `ptr` from the delegatecall return data */ switch result - case 0 { revert(ptr, retdatasize) } - default { return(ptr, retdatasize) } + case 0 { revert(ptr, returndatasize) } + default { return(ptr, returndatasize) } } } } diff --git a/contracts/upgradeability/UpgradeabilityStorage.sol b/contracts/upgradeability/UpgradeabilityStorage.sol index 85f82060f..b3e537790 100644 --- a/contracts/upgradeability/UpgradeabilityStorage.sol +++ b/contracts/upgradeability/UpgradeabilityStorage.sol @@ -27,9 +27,4 @@ contract UpgradeabilityStorage { function implementation() public view returns (address) { return _implementation; } - - function setImplementation(address _newImplementation) external { - require(msg.sender == address(this)); - _implementation = _newImplementation; - } } diff --git a/contracts/upgradeable_contracts/BasicBridge.sol b/contracts/upgradeable_contracts/BasicBridge.sol index cbc4cf2b9..f805c6573 100644 --- a/contracts/upgradeable_contracts/BasicBridge.sol +++ b/contracts/upgradeable_contracts/BasicBridge.sol @@ -4,11 +4,11 @@ import "./OwnedUpgradeability.sol"; import "../upgradeability/EternalStorage.sol"; import "../libraries/SafeMath.sol"; import "./Validatable.sol"; -import "./EternalOwnable.sol"; +import "./Ownable.sol"; import "openzeppelin-solidity/contracts/token/ERC20/ERC20Basic.sol"; -contract BasicBridge is EternalStorage, Validatable, EternalOwnable, OwnedUpgradeability { +contract BasicBridge is EternalStorage, Validatable, Ownable, OwnedUpgradeability { using SafeMath for uint256; event GasPriceChanged(uint256 gasPrice); diff --git a/contracts/upgradeable_contracts/BridgeMapper.sol b/contracts/upgradeable_contracts/BridgeMapper.sol deleted file mode 100644 index 61b41d320..000000000 --- a/contracts/upgradeable_contracts/BridgeMapper.sol +++ /dev/null @@ -1,94 +0,0 @@ -pragma solidity 0.4.24; - -import "./EternalOwnable.sol"; -import "../upgradeability/EternalStorage.sol"; - -contract BridgeMapper is EternalStorage, EternalOwnable { - - event BridgeMappingUpdated(address indexed foreignToken, address homeToken, address foreignBridge, address homeBridge, uint256 foreignStartBlock, uint256 homeStartBlock); - - function homeBridgeByForeignToken(address _foreignToken) public view returns(address) { - return addressStorage[keccak256(abi.encodePacked("homeBridgeByForeignToken", _foreignToken))]; - } - - function setHomeBridgeByForeignToken(address _foreignToken, address _homeBridge) internal { - addressStorage[keccak256(abi.encodePacked("homeBridgeByForeignToken", _foreignToken))] = _homeBridge; - } - - function foreignBridgeByForeignToken(address _foreignToken) public view returns(address) { - return addressStorage[keccak256(abi.encodePacked("foreignBridgeByForeignToken", _foreignToken))]; - } - - function setForeignBridgeByForeignToken(address _foreignToken, address _foreignBridge) internal { - addressStorage[keccak256(abi.encodePacked("foreignBridgeByForeignToken", _foreignToken))] = _foreignBridge; - } - - function homeTokenByForeignToken(address _foreignToken) public view returns(address) { - return addressStorage[keccak256(abi.encodePacked("homeTokenByForeignToken", _foreignToken))]; - } - - function setHomeTokenByForeignToken(address _foreignToken, address _homeToken) internal { - addressStorage[keccak256(abi.encodePacked("homeTokenByForeignToken", _foreignToken))] = _homeToken; - } - - function homeStartBlockByForeignToken(address _foreignToken) public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("homeStartBlockByForeignToken", _foreignToken))]; - } - - function setHomeStartBlockByForeignToken(address _foreignToken, uint256 _homeStartBlock) internal { - uintStorage[keccak256(abi.encodePacked("homeStartBlockByForeignToken", _foreignToken))] = _homeStartBlock; - } - - function foreignStartBlockByForeignToken(address _foreignToken) public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("foreignStartBlockByForeignToken", _foreignToken))]; - } - - function setForeignStartBlockByForeignToken(address _foreignToken, uint256 _foreignStartBlock) internal { - uintStorage[keccak256(abi.encodePacked("foreignStartBlockByForeignToken", _foreignToken))] = _foreignStartBlock; - } - - function setInitialize(bool _status) internal { - boolStorage[keccak256(abi.encodePacked("isInitialized"))] = _status; - } - - function isInitialized() public view returns(bool) { - return boolStorage[keccak256(abi.encodePacked("isInitialized"))]; - } - - function addBridgeMapping(address _foreignToken, address _homeToken, address _foreignBridge, address _homeBridge, uint256 _foreignStartBlock, uint256 _homeStartBlock) public onlyOwner { - require(_foreignToken != address(0)); - require(_homeToken != address(0)); - require(_foreignBridge != address(0)); - require(_homeBridge != address(0)); - require(_foreignStartBlock > 0); - require(_homeStartBlock > 0); - setHomeTokenByForeignToken(_foreignToken, _homeToken); - setForeignBridgeByForeignToken(_foreignToken, _foreignBridge); - setHomeBridgeByForeignToken(_foreignToken, _homeBridge); - setForeignStartBlockByForeignToken(_foreignToken, _foreignStartBlock); - setHomeStartBlockByForeignToken(_foreignToken, _homeStartBlock); - emit BridgeMappingUpdated(_foreignToken, _homeToken, _foreignBridge, _homeBridge, _foreignStartBlock, _homeStartBlock); - } - - function removeBridgeMapping(address _foreignToken) public onlyOwner { - require(_foreignToken != address(0)); - setHomeTokenByForeignToken(_foreignToken, address(0)); - setForeignBridgeByForeignToken(_foreignToken, address(0)); - setHomeBridgeByForeignToken(_foreignToken, address(0)); - setForeignStartBlockByForeignToken(_foreignToken, 0); - setHomeStartBlockByForeignToken(_foreignToken, 0); - emit BridgeMappingUpdated(_foreignToken, address(0), address(0), address(0), 0, 0); - } - - function getBridgeMapperVersion() public pure returns(uint64 major, uint64 minor, uint64 patch) { - return (2, 2, 0); - } - - function initialize(address _owner) public returns(bool) { - require(!isInitialized()); - setOwner(_owner); - setInitialize(true); - return isInitialized(); - } - -} \ No newline at end of file diff --git a/contracts/upgradeable_contracts/BridgeValidators.sol b/contracts/upgradeable_contracts/BridgeValidators.sol index 45bc60b90..d3ee1edba 100644 --- a/contracts/upgradeable_contracts/BridgeValidators.sol +++ b/contracts/upgradeable_contracts/BridgeValidators.sol @@ -1,12 +1,12 @@ pragma solidity 0.4.24; -import "./EternalOwnable.sol"; +import "./Ownable.sol"; import "../IBridgeValidators.sol"; import "../libraries/SafeMath.sol"; import "../upgradeability/EternalStorage.sol"; -contract BridgeValidators is IBridgeValidators, EternalStorage, EternalOwnable { +contract BridgeValidators is IBridgeValidators, EternalStorage, Ownable { using SafeMath for uint256; event ValidatorAdded (address indexed validator); diff --git a/contracts/upgradeable_contracts/EternalOwnable.sol b/contracts/upgradeable_contracts/Ownable.sol similarity index 85% rename from contracts/upgradeable_contracts/EternalOwnable.sol rename to contracts/upgradeable_contracts/Ownable.sol index f99a23b3c..35ccf44fb 100644 --- a/contracts/upgradeable_contracts/EternalOwnable.sol +++ b/contracts/upgradeable_contracts/Ownable.sol @@ -4,16 +4,16 @@ import "../upgradeability/EternalStorage.sol"; /** - * @title EternalOwnable + * @title Ownable * @dev This contract has an owner address providing basic authorization control */ -contract EternalOwnable is EternalStorage { +contract Ownable is EternalStorage { /** * @dev Event to show ownership has been transferred * @param previousOwner representing the address of the previous owner * @param newOwner representing the address of the new owner */ - event EternalOwnershipTransferred(address previousOwner, address newOwner); + event OwnershipTransferred(address previousOwner, address newOwner); /** * @dev Throws if called by any account other than the owner. @@ -44,7 +44,7 @@ contract EternalOwnable is EternalStorage { * @dev Sets a new owner address */ function setOwner(address newOwner) internal { - emit EternalOwnershipTransferred(owner(), newOwner); + emit OwnershipTransferred(owner(), newOwner); addressStorage[keccak256(abi.encodePacked("owner"))] = newOwner; } } diff --git a/contracts/upgradeable_contracts/factories/BasicBridgeFactory.sol b/contracts/upgradeable_contracts/factories/BasicBridgeFactory.sol deleted file mode 100644 index f16da02e8..000000000 --- a/contracts/upgradeable_contracts/factories/BasicBridgeFactory.sol +++ /dev/null @@ -1,101 +0,0 @@ -pragma solidity 0.4.24; - -import "../../upgradeability/EternalStorage.sol"; -import "../EternalOwnable.sol"; - -contract BasicBridgeFactory is EternalStorage, EternalOwnable { - - function getBridgeFactoryVersion() public pure returns(uint64 major, uint64 minor, uint64 patch) { - return (2, 2, 0); - } - - function bridgeValidatorsImplementation() public view returns(address) { - return addressStorage[keccak256(abi.encodePacked("bridgeValidatorsImplementation"))]; - } - - function setBridgeValidatorsImplementation(address _bridgeValidatorsImplementation) public onlyOwner { - addressStorage[keccak256(abi.encodePacked("bridgeValidatorsImplementation"))] = _bridgeValidatorsImplementation; - } - - function requiredSignatures() public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("requiredSignatures"))]; - } - - function setRequiredSignatures(uint256 _requiredSignatures) public onlyOwner { - require(initialValidators().length >= _requiredSignatures); - uintStorage[keccak256(abi.encodePacked("requiredSignatures"))] = _requiredSignatures; - } - - function initialValidators() public view returns(address[]) { - return addressArrayStorage[keccak256(abi.encodePacked("initialValidators"))]; - } - - function setInitialValidators(address[] _initialValidators) public onlyOwner { - require(_initialValidators.length >= requiredSignatures()); - addressArrayStorage[keccak256(abi.encodePacked("initialValidators"))] = _initialValidators; - } - - function bridgeValidatorsOwner() public view returns(address) { - return addressStorage[keccak256(abi.encodePacked("bridgeValidatorsOwner"))]; - } - - function setBridgeValidatorsOwner(address _bridgeValidatorsOwner) public onlyOwner { - addressStorage[keccak256(abi.encodePacked("bridgeValidatorsOwner"))] = _bridgeValidatorsOwner; - } - - function bridgeValidatorsProxyOwner() public view returns(address) { - return addressStorage[keccak256(abi.encodePacked("bridgeValidatorsProxyOwner"))]; - } - - function setBridgeValidatorsProxyOwner(address _bridgeValidatorsProxyOwner) public onlyOwner { - addressStorage[keccak256(abi.encodePacked("bridgeValidatorsProxyOwner"))] = _bridgeValidatorsProxyOwner; - } - - function requiredBlockConfirmations() public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("requiredBlockConfirmations"))]; - } - - function setRequiredBlockConfirmations(uint256 _requiredBlockConfirmations) public onlyOwner { - uintStorage[keccak256(abi.encodePacked("requiredBlockConfirmations"))] = _requiredBlockConfirmations; - } - - function gasPrice() public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("gasPrice"))]; - } - - function setGasPrice(uint256 _gasPrice) public onlyOwner { - uintStorage[keccak256(abi.encodePacked("gasPrice"))] = _gasPrice; - } - - function homeDailyLimit() public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("homeDailyLimit"))]; - } - - function setHomeDailyLimit(uint256 _homeDailyLimit) public onlyOwner { - uintStorage[keccak256(abi.encodePacked("homeDailyLimit"))] = _homeDailyLimit; - } - - function homeMaxPerTx() public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("homeMaxPerTx"))]; - } - - function setHomeMaxPerTx(uint256 _homeMaxPerTx) public onlyOwner { - uintStorage[keccak256(abi.encodePacked("homeMaxPerTx"))] = _homeMaxPerTx; - } - - function foreignMaxPerTx() public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("foreignMaxPerTx"))]; - } - - function setForeignMaxPerTx(uint256 _foreignMaxPerTx) public onlyOwner { - uintStorage[keccak256(abi.encodePacked("foreignMaxPerTx"))] = _foreignMaxPerTx; - } - - function setInitialize(bool _status) internal { - boolStorage[keccak256(abi.encodePacked("isInitialized"))] = _status; - } - - function isInitialized() public view returns(bool) { - return boolStorage[keccak256(abi.encodePacked("isInitialized"))]; - } -} \ No newline at end of file diff --git a/contracts/upgradeable_contracts/factories/ForeignBridgeFactory.sol b/contracts/upgradeable_contracts/factories/ForeignBridgeFactory.sol deleted file mode 100644 index 6ba45b053..000000000 --- a/contracts/upgradeable_contracts/factories/ForeignBridgeFactory.sol +++ /dev/null @@ -1,107 +0,0 @@ -pragma solidity 0.4.24; - -import "../../IBridgeValidators.sol"; -import "../../IForeignBridge.sol"; -import "../../upgradeability/EternalStorageProxy.sol"; -import "./BasicBridgeFactory.sol"; - -contract ForeignBridgeFactory is BasicBridgeFactory { - - event ForeignBridgeDeployed(address indexed _foreignBridge, address indexed _foreignValidators, uint256 _blockNumber); - - function initialize(address _owner, - address _bridgeValidatorsImplementation, - uint256 _requiredSignatures, - address[] _initialValidators, - address _bridgeValidatorsOwner, - address _foreignBridgeErcToErcImplementation, - uint256 _requiredBlockConfirmations, - uint256 _gasPrice, - uint256 _foreignMaxPerTx, - uint256 _homeDailyLimit, - uint256 _homeMaxPerTx, - address _foreignBridgeOwner, - address _foreignProxyOwner) public returns(bool) { - - require(!isInitialized()); - require(_owner != address(0)); - require(_bridgeValidatorsImplementation != address(0)); - require(_requiredSignatures >= 1); - require(_bridgeValidatorsOwner != address(0)); - require(_foreignBridgeErcToErcImplementation != address(0)); - require(_requiredBlockConfirmations != 0); - require(_gasPrice > 0); - require(_foreignMaxPerTx >= 0); - require(_homeMaxPerTx < _homeDailyLimit); - require(_foreignBridgeOwner != address(0)); - require(_foreignProxyOwner != address(0)); - require(_initialValidators.length >= _requiredSignatures); - - setOwner(msg.sender); // set just to have access to the setters. - setBridgeValidatorsImplementation(_bridgeValidatorsImplementation); - setInitialValidators(_initialValidators); - setRequiredSignatures(_requiredSignatures); - setBridgeValidatorsOwner(_bridgeValidatorsOwner); - setBridgeValidatorsProxyOwner(_foreignProxyOwner); - setForeignBridgeErcToErcImplementation(_foreignBridgeErcToErcImplementation); - setRequiredBlockConfirmations(_requiredBlockConfirmations); - setGasPrice(_gasPrice); - setForeignMaxPerTx(_foreignMaxPerTx); - setHomeDailyLimit(_homeDailyLimit); - setHomeMaxPerTx(_homeMaxPerTx); - setForeignBridgeOwner(_foreignBridgeOwner); - setForeignBridgeProxyOwner(_foreignProxyOwner); - setInitialize(true); - setOwner(_owner); // set to the real owner. - return isInitialized(); - } - - function deployForeignBridge(address _erc20Token) public onlyOwner { - // deploy new EternalStorageProxy - EternalStorageProxy proxy = new EternalStorageProxy(); - // connect it to the static BridgeValidators implementation - proxy.upgradeTo(1, bridgeValidatorsImplementation()); - // cast proxy as IBridgeValidators - IBridgeValidators bridgeValidators = IBridgeValidators(proxy); - // initialize bridgeValidators - bridgeValidators.initialize(requiredSignatures(), initialValidators(), bridgeValidatorsOwner()); - // transfer proxy upgradeability admin - proxy.transferProxyOwnership(bridgeValidatorsProxyOwner()); - // deploy new EternalStorageProxy - proxy = new EternalStorageProxy(); - // connect it to the static ForeignBridgeErcToErc implementation - proxy.upgradeTo(1, foreignBridgeErcToErcImplementation()); - // cast proxy as IForeignBridge - IForeignBridge foreignBridge = IForeignBridge(proxy); - // initialize foreignBridge - foreignBridge.initialize(bridgeValidators, _erc20Token, requiredBlockConfirmations(), gasPrice(), foreignMaxPerTx(), homeDailyLimit(), homeMaxPerTx(), foreignBridgeOwner()); - // transfer proxy upgradeability admin - proxy.transferProxyOwnership(foreignBridgeProxyOwner()); - // emit event - emit ForeignBridgeDeployed(foreignBridge, bridgeValidators, block.number); - } - - function foreignBridgeErcToErcImplementation() public view returns(address) { - return addressStorage[keccak256(abi.encodePacked("foreignBridgeErcToErcImplementation"))]; - } - - function setForeignBridgeErcToErcImplementation(address _foreignBridgeErcToErcImplementation) public onlyOwner { - addressStorage[keccak256(abi.encodePacked("foreignBridgeErcToErcImplementation"))] = _foreignBridgeErcToErcImplementation; - } - - function foreignBridgeOwner() public view returns(address) { - return addressStorage[keccak256(abi.encodePacked("foreignBridgeOwner"))]; - } - - function setForeignBridgeOwner(address _foreignBridgeOwner) public onlyOwner { - addressStorage[keccak256(abi.encodePacked("foreignBridgeOwner"))] = _foreignBridgeOwner; - } - - function foreignBridgeProxyOwner() public view returns(address) { - return addressStorage[keccak256(abi.encodePacked("foreignBridgeProxyOwner"))]; - } - - function setForeignBridgeProxyOwner(address _foreignBridgeProxyOwner) public onlyOwner { - addressStorage[keccak256(abi.encodePacked("foreignBridgeProxyOwner"))] = _foreignBridgeProxyOwner; - } -} \ No newline at end of file diff --git a/contracts/upgradeable_contracts/factories/HomeBridgeFactory.sol b/contracts/upgradeable_contracts/factories/HomeBridgeFactory.sol deleted file mode 100644 index 5db043e27..000000000 --- a/contracts/upgradeable_contracts/factories/HomeBridgeFactory.sol +++ /dev/null @@ -1,134 +0,0 @@ -pragma solidity 0.4.24; - -import "../../IBridgeValidators.sol"; -import "../../IHomeBridge.sol"; -import "../../upgradeability/EternalStorageProxy.sol"; -import "../../ERC677BridgeToken.sol"; -import "./BasicBridgeFactory.sol"; - -contract HomeBridgeFactory is BasicBridgeFactory { - - event HomeBridgeDeployed(address indexed _homeBridge, address indexed _homeValidators, address indexed _token, uint256 _blockNumber); - - function initialize(address _owner, - address _bridgeValidatorsImplementation, - uint256 _requiredSignatures, - address[] _initialValidators, - address _bridgeValidatorsOwner, - address _homeBridgeErcToErcImplementation, - uint256 _requiredBlockConfirmations, - uint256 _gasPrice, - uint256 _homeDailyLimit, - uint256 _homeMaxPerTx, - uint256 _minPerTx, - uint256 _foreignDailyLimit, - uint256 _foreignMaxPerTx, - address _homeBridgeOwner, - address _homeProxyOwner) public { - - - require(!isInitialized()); - require(_owner != address(0)); - require(_bridgeValidatorsImplementation != address(0)); - require(_requiredSignatures >= 1); - require(_bridgeValidatorsOwner != address(0)); - require(_homeBridgeErcToErcImplementation != address(0)); - require(_gasPrice > 0); - require(_requiredBlockConfirmations > 0); - require(_minPerTx > 0 && _homeMaxPerTx > _minPerTx && _homeDailyLimit > _homeMaxPerTx); - require(_foreignMaxPerTx < _foreignDailyLimit); - require(_homeBridgeOwner != address(0)); - require(_homeProxyOwner != address(0)); - require(_initialValidators.length >= _requiredSignatures); - - setOwner(msg.sender); // set just to have access to the setters. - setBridgeValidatorsImplementation(_bridgeValidatorsImplementation); - setInitialValidators(_initialValidators); - setRequiredSignatures(_requiredSignatures); - setBridgeValidatorsOwner(_bridgeValidatorsOwner); - setBridgeValidatorsProxyOwner(_homeProxyOwner); - setHomeBridgeErcToErcImplementation(_homeBridgeErcToErcImplementation); - setRequiredBlockConfirmations(_requiredBlockConfirmations); - setGasPrice(_gasPrice); - setHomeDailyLimit(_homeDailyLimit); - setHomeMaxPerTx(_homeMaxPerTx); - setMinPerTx(_minPerTx); - setForeignDailyLimit(_foreignDailyLimit); - setForeignMaxPerTx(_foreignMaxPerTx); - setHomeBridgeOwner(_homeBridgeOwner); - setHomeBridgeProxyOwner(_homeProxyOwner); - setInitialize(true); - setOwner(_owner); // set to the real owner. - } - - function deployHomeBridge(string _tokenName, string _tokenSymbol, uint8 _tokenDecimals) public onlyOwner { - // deploy new EternalStorageProxy - EternalStorageProxy proxy = new EternalStorageProxy(); - // connect it to the static BridgeValidators implementation - proxy.upgradeTo(1, bridgeValidatorsImplementation()); - // cast proxy as IBridgeValidators - IBridgeValidators bridgeValidators = IBridgeValidators(proxy); - // initialize bridgeValidators - bridgeValidators.initialize(requiredSignatures(), initialValidators(), bridgeValidatorsOwner()); - // transfer proxy upgradeability admin - proxy.transferProxyOwnership(bridgeValidatorsProxyOwner()); - // deploy new EternalStorageProxy - proxy = new EternalStorageProxy(); - // connect it to the static homeBridgeErcToErc implementation - proxy.upgradeTo(1, homeBridgeErcToErcImplementation()); - // deploy erc677 token bridge token - ERC677BridgeToken token = new ERC677BridgeToken(_tokenName, _tokenSymbol, _tokenDecimals); - // set token bridge contract - token.setBridgeContract(proxy); - // transfer token ownership to the bridge - token.transferOwnership(proxy); - // cast proxy as IHomeBridge - IHomeBridge homeBridge = IHomeBridge(proxy); - // initialize homeBridge - homeBridge.initialize(bridgeValidators, homeDailyLimit(), homeMaxPerTx(), minPerTx(), gasPrice(), requiredBlockConfirmations(), token, foreignDailyLimit(), foreignMaxPerTx(), homeBridgeOwner()); - // transfer proxy upgradeability admin - proxy.transferProxyOwnership(homeBridgeProxyOwner()); - // emit event - emit HomeBridgeDeployed(homeBridge, bridgeValidators, token, block.number); - } - - function homeBridgeErcToErcImplementation() public view returns(address) { - return addressStorage[keccak256(abi.encodePacked("homeBridgeErcToErcImplementation"))]; - } - - function setHomeBridgeErcToErcImplementation(address _homeBridgeErcToErcImplementation) public onlyOwner { - addressStorage[keccak256(abi.encodePacked("homeBridgeErcToErcImplementation"))] = _homeBridgeErcToErcImplementation; - } - - function minPerTx() public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("minPerTx"))]; - } - - function setMinPerTx(uint256 _minPerTx) public onlyOwner { - uintStorage[keccak256(abi.encodePacked("minPerTx"))] = _minPerTx; - } - - function foreignDailyLimit() public view returns(uint256) { - return uintStorage[keccak256(abi.encodePacked("foreignDailyLimit"))]; - } - - function setForeignDailyLimit(uint256 _foreignDailyLimit) public onlyOwner { - uintStorage[keccak256(abi.encodePacked("foreignDailyLimit"))] = _foreignDailyLimit; - } - - function homeBridgeOwner() public view returns(address) { - return addressStorage[keccak256(abi.encodePacked("homeBridgeOwner"))]; - } - - function setHomeBridgeOwner(address _homeBridgeOwner) public onlyOwner { - addressStorage[keccak256(abi.encodePacked("homeBridgeOwner"))] = _homeBridgeOwner; - } - - function homeBridgeProxyOwner() public view returns(address) { - return addressStorage[keccak256(abi.encodePacked("homeBridgeProxyOwner"))]; - } - - function setHomeBridgeProxyOwner(address _homeBridgeProxyOwner) public onlyOwner { - addressStorage[keccak256(abi.encodePacked("homeBridgeProxyOwner"))] = _homeBridgeProxyOwner; - } -} \ No newline at end of file diff --git a/deploy/.env.example b/deploy/.env.example index 91869f282..8145284f6 100644 --- a/deploy/.env.example +++ b/deploy/.env.example @@ -13,8 +13,6 @@ BRIDGEABLE_TOKEN_DECIMALS=18 HOME_RPC_URL=https://sokol.poa.network HOME_BRIDGE_OWNER=0x HOME_VALIDATORS_OWNER=0x -HOME_FACTORY_OWNER=0x -HOME_MAPPER_OWNER=0x HOME_UPGRADEABLE_ADMIN=0x HOME_DAILY_LIMIT=30000000000000000000000000 HOME_MAX_AMOUNT_PER_TX=1500000000000000000000000 @@ -28,7 +26,6 @@ BLOCK_REWARD_ADDRESS= FOREIGN_RPC_URL=https://sokol.poa.network FOREIGN_BRIDGE_OWNER=0x FOREIGN_VALIDATORS_OWNER=0x -FOREIGN_FACTORY_OWNER=0x FOREIGN_UPGRADEABLE_ADMIN=0x FOREIGN_DAILY_LIMIT=15000000000000000000000000 FOREIGN_MAX_AMOUNT_PER_TX=750000000000000000000000 @@ -38,15 +35,6 @@ FOREIGN_GAS_PRICE=10000000000 #for bridge erc_to_erc and erc_to_native mode ERC20_TOKEN_ADDRESS= -#Optional Implemetation addresses for ERC_TO_ERC_MULTIPLE mode -HOME_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS=0x -HOME_BRIDGE_IMPLEMENTATION_ADDRESS=0x -FOREIGN_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS=0x -FOREIGN_BRIDGE_IMPLEMENTATION_ADDRESS=0x - -#encapsulate implementation in double proxy for easier upgrades. -DOUBLE_PROXY_IMPLEMENTATIONS=0x - REQUIRED_NUMBER_OF_VALIDATORS=1 #If several validators are used, list them separated by space without quotes #E.g. VALIDATORS=0x 0x 0x diff --git a/deploy/README.md b/deploy/README.md index 94550e2d4..34a280eea 100644 --- a/deploy/README.md +++ b/deploy/README.md @@ -329,105 +329,3 @@ REQUIRED_NUMBER_OF_VALIDATORS=1 # correctly to the Foreign network. VALIDATORS=0x 0x 0x ``` - -## `ERC_TO_ERC_MULTIPLE` Bridge Mode Configuration Example. - -This example of an `.env` file for the `erc-to-erc-multiple` bridge mode includes comments describing each parameter. - -```bash -# The type of bridge. Defines set of contracts to be deployed. -BRIDGE_MODE=ERC_TO_ERC_MULTIPLE - -# The private key hex value of the account responsible for contracts -# deployments and initial configuration. The account's balance must contain -# funds from both networks. -DEPLOYMENT_ACCOUNT_PRIVATE_KEY=67..14 -# The "gas" parameter set in every deployment/configuration transaction. -DEPLOYMENT_GAS_LIMIT=5000000 -# The "gasPrice" parameter set in every deployment/configuration transaction on -# Home network (in Wei). -HOME_DEPLOYMENT_GAS_PRICE=10000000000 -# The "gasPrice" parameter set in every deployment/configuration transaction on -# Foreign network (in Wei). -FOREIGN_DEPLOYMENT_GAS_PRICE=10000000000 -# The timeout limit to wait for receipt of the deployment/configuration -# transaction. -GET_RECEIPT_INTERVAL_IN_MILLISECONDS=3000 - -# The RPC channel to a Home node able to handle deployment/configuration -# transactions. -HOME_RPC_URL=https://rpc.fuse.io -# The address of an administrator on the Home network who can change bridge -# parameters and a validator's contract. For extra security we recommended using -HOME_BRIDGE_OWNER=0x -HOME_VALIDATORS_OWNER=0x -# the home factory owner -HOME_FACTORY_OWNER=0x -# the home mapper owner -HOME_MAPPER_OWNER=0x -# The address from which upgradable contract can be upgraded on Home. -HOME_UPGRADEABLE_ADMIN=0x -# The daily transaction limit in Wei. As soon as this limit is exceeded, any -# transaction which requests to relay assets will fail. -HOME_DAILY_LIMIT=30000000000000000000000000 -# The maximum limit for one transaction in Wei. If a single transaction tries to -# relay funds exceeding this limit it will fail. -HOME_MAX_AMOUNT_PER_TX=1500000000000000000000000 -# The minimum limit for one transaction in Wei. If a transaction tries to relay -# funds below this limit it will fail. This is required to prevent dryout -# validator accounts. -HOME_MIN_AMOUNT_PER_TX=500000000000000000 -# The finalization threshold. The number of blocks issued after the block with -# the corresponding deposit transaction to guarantee the transaction will not be -# rolled back. -HOME_REQUIRED_BLOCK_CONFIRMATIONS=1 -# The default gas price (in Wei) used to send Home Network signature -# transactions for deposit or withdrawal confirmations. This price is used if -# the Gas price oracle is unreachable. -HOME_GAS_PRICE=1000000000 - -# The RPC channel to a Foreign node able to handle deployment/configuration -# transactions. -FOREIGN_RPC_URL=https://ropsten.infura.io -# The address of an administrator on the Foreign network who can change bridge -# parameters and the validator's contract. For extra security we recommended -# using a multi-sig wallet contract address here. -FOREIGN_BRIDGE_OWNER=0x -FOREIGN_VALIDATORS_OWNER=0x -# the foreign factory owner -FOREIGN_FACTORY_OWNER=0x -# The address from which upgradable contract can be upgraded on Foreign. -FOREIGN_UPGRADEABLE_ADMIN=0x -# These three parameters are not used in this mode, but the deployment script -# requires it to be set to some value. -FOREIGN_DAILY_LIMIT=30000000000000000000000000 -FOREIGN_MAX_AMOUNT_PER_TX=1500000000000000000000000 -FOREIGN_MIN_AMOUNT_PER_TX=500000000000000000 -# The finalization threshold. The number of blocks issued after the block with -# the corresponding deposit transaction to guarantee the transaction will not be -# rolled back. -FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS=8 -# The default gas price (in Wei) used to send Foreign network transactions -# finalizing asset deposits. This price is used if the Gas price oracle is -# unreachable. -FOREIGN_GAS_PRICE=10000000000 -# The address of the existing ERC20 compatible token in the Foreign network to -# be exchanged to the ERC20/ERC677 token deployed on Home. -ERC20_TOKEN_ADDRESS=0x - -# The minimum number of validators required to send their signatures confirming -# the relay of assets. The same number of validators is expected on both sides -# of the bridge. -REQUIRED_NUMBER_OF_VALIDATORS=1 -# The set of validators' addresses. It is assumed that signatures from these -# addresses are collected on the Home side. The same addresses will be used on -# the Foreign network to confirm that the finalized agreement was transferred -# correctly to the Foreign network. -VALIDATORS=0x 0x 0x - -# implementation addresses - optional: -#FOREIGN_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS=0x -#FOREIGN_BRIDGE_IMPLEMENTATION_ADDRESS=0x -#HOME_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS=0x -#HOME_BRIDGE_IMPLEMENTATION_ADDRESS=0x -``` \ No newline at end of file diff --git a/deploy/deploy.js b/deploy/deploy.js index f3fbfc3c8..a727c5d49 100644 --- a/deploy/deploy.js +++ b/deploy/deploy.js @@ -110,39 +110,6 @@ async function deployErcToNative() { console.log('Contracts Deployment have been saved to `bridgeDeploymentResults.json`') } -async function deployFactory() { - const deployHome = require('./src/factories/home') - const deployForeign = require('./src/factories/foreign') - - const { homeFactory, mapper } = await deployHome() - const { foreignFactory } = await deployForeign() - console.log('\nDeployment has been completed.\n\n') - console.log(`[ Home ] HomeFactory: ${homeFactory.address} at block ${homeFactory.deployedBlockNumber}`) - console.log(`[ Home ] BridgeMapper: ${mapper.address} at block ${mapper.deployedBlockNumber}`) - console.log( - `[ Foreign ] ForeignFactory: ${foreignFactory.address} at block ${ - foreignFactory.deployedBlockNumber - }` - ) - fs.writeFileSync( - deployResultsPath, - JSON.stringify( - { - homeFactory: { - ...homeFactory, - mapper - }, - foreignFactory: { - ...foreignFactory - } - }, - null, - 4 - ) - ) - console.log('Contracts Deployment have been saved to `bridgeDeploymentResults.json`') -} - async function main() { console.log(`Bridge mode: ${BRIDGE_MODE}`) switch (BRIDGE_MODE) { @@ -155,12 +122,9 @@ async function main() { case 'ERC_TO_NATIVE': await deployErcToNative() break - case 'ERC_TO_ERC_MULTIPLE': - await deployFactory() - break default: console.log(BRIDGE_MODE) - throw new Error('Please specify BRIDGE_MODE: NATIVE_TO_ERC or ERC_TO_ERC or ERC_TO_NATIVE or ERC_TO_ERC_MULTIPLE') + throw new Error('Please specify BRIDGE_MODE: NATIVE_TO_ERC or ERC_TO_ERC') } } diff --git a/deploy/package-lock.json b/deploy/package-lock.json index 0efc46691..a5b02bbbc 100644 --- a/deploy/package-lock.json +++ b/deploy/package-lock.json @@ -24,6 +24,25 @@ "js-tokens": "^4.0.0" } }, + "@babel/parser": { + "version": "7.2.3", + "resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.2.3.tgz", + "integrity": "sha512-0LyEcVlfCoFmci8mXx8A5oIkpkOgyo8dRHtxBnK9RRBwxO2+JZPNsqtVEZQ7mJFPxnXF9lfmU24mHOPI0qnlkA==" + }, + "@mrmlnc/readdir-enhanced": { + "version": "2.2.1", + "resolved": "https://registry.npmjs.org/@mrmlnc/readdir-enhanced/-/readdir-enhanced-2.2.1.tgz", + "integrity": "sha512-bPHp6Ji8b41szTOcaP63VlnbbO5Ny6dwAATtY6JTjh5N2OLrb5Qk/Th5cRkRQhkWCt+EJsYrNB0MiL+Gpn6e3g==", + "requires": { + "call-me-maybe": "^1.0.1", + "glob-to-regexp": "^0.3.0" + } + }, + "@nodelib/fs.stat": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/@nodelib/fs.stat/-/fs.stat-1.1.3.tgz", + "integrity": "sha512-shAmDyaQC4H92APFoIaVDHCx5bStIocgvbwQyxPRrbUY20V1EYTbSDchWbuwlMG3V17cprZhA6+78JfB+3DTPw==" + }, "accepts": { "version": "1.3.5", "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.5.tgz", @@ -34,54 +53,32 @@ } }, "acorn": { - "version": "5.5.3", - "resolved": "https://registry.npmjs.org/acorn/-/acorn-5.5.3.tgz", - "integrity": "sha512-jd5MkIUlbbmb07nXH0DT3y7rDVtkzDi4XZOUVWAer8ajmF/DTSSbl5oNFyDOl/OXA33Bl79+ypHhl2pN20VeOQ==" + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/acorn/-/acorn-6.1.0.tgz", + "integrity": "sha512-MW/FjM+IvU9CgBzjO3UIPCE2pyEwUsoFl+VGdczOPEdxfGFjuKny/gN54mOuX7Qxmb9Rg9MCn2oKiSUeW+pjrw==", + "dev": true }, "acorn-jsx": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-4.1.1.tgz", - "integrity": "sha512-JY+iV6r+cO21KtntVvFkD+iqjtdpRUpGqKWgfkCdZq1R+kbreEl8EcdcJR4SmiIgsIQT33s6QzheQ9a275Q8xw==", - "dev": true, - "requires": { - "acorn": "^5.0.3" - } - }, - "acorn-object-rest-spread": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/acorn-object-rest-spread/-/acorn-object-rest-spread-1.1.0.tgz", - "integrity": "sha1-eGma790Y7DGCyq2t9S4ml8BI9HY=", - "requires": { - "acorn": "^5.0.3" - } + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-5.0.1.tgz", + "integrity": "sha512-HJ7CfNHrfJLlNTzIEUTj43LNWGkqpRLxm3YjAlcD0ACydk9XynzYsCBHxut+iqt+1aBXkx9UP/w/ZqMr13XIzg==", + "dev": true }, "ajv": { - "version": "5.5.2", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-5.5.2.tgz", - "integrity": "sha1-c7Xuyj+rZT49P5Qis0GtQiBdyWU=", + "version": "6.9.1", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.9.1.tgz", + "integrity": "sha512-XDN92U311aINL77ieWHmqCcNlwjoP5cHXDxIxbf2MaPYuCXOHS7gHH8jktxeK5omgd52XbSTX6a4Piwd1pQmzA==", "requires": { - "co": "^4.6.0", - "fast-deep-equal": "^1.0.0", + "fast-deep-equal": "^2.0.1", "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.3.0" + "json-schema-traverse": "^0.4.1", + "uri-js": "^4.2.2" } }, - "ajv-keywords": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-3.2.0.tgz", - "integrity": "sha1-6GuBnGAs+IIa1jdBNpjx3sAhhHo=", - "dev": true - }, - "amdefine": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/amdefine/-/amdefine-1.0.1.tgz", - "integrity": "sha1-SlKCrBZHKek2Gbz9OtFR+BfOkfU=", - "optional": true - }, "ansi-escapes": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-3.1.0.tgz", - "integrity": "sha512-UgAb8H9D41AQnu/PbWlCofQVcnV4Gs2bBJi9eZPxfU/hgglFh3SMDMENRIqdr7H6XFnXdoknctFByVsCOotTVw==", + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-3.2.0.tgz", + "integrity": "sha512-cBhpre4ma+U0T1oM5fXg7Dy1Jw7zzwv7lt/GoCpr+hDQJoYnKVPLL4dCvSEFMmQurOQvSrwT7SL/DAlhBI97RQ==", "dev": true }, "ansi-regex": { @@ -112,6 +109,21 @@ "sprintf-js": "~1.0.2" } }, + "arr-diff": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/arr-diff/-/arr-diff-4.0.0.tgz", + "integrity": "sha1-1kYQdP6/7HHn4VI1dhoyml3HxSA=" + }, + "arr-flatten": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/arr-flatten/-/arr-flatten-1.1.0.tgz", + "integrity": "sha512-L3hKV5R/p5o81R7O02IGnwpDmkp6E982XhtbuwSe3O4qOtMMMtodicASA1Cny2U+aCXcNpml+m4dPsvsJ3jatg==" + }, + "arr-union": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/arr-union/-/arr-union-3.1.0.tgz", + "integrity": "sha1-45sJrqne+Gao8gbiiK9jkZuuOcQ=" + }, "array-flatten": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-1.1.1.tgz", @@ -130,16 +142,23 @@ "resolved": "https://registry.npmjs.org/array-uniq/-/array-uniq-1.0.3.tgz", "integrity": "sha1-r2rId6Jcx/dOBYiUdThY39sk/bY=" }, + "array-unique": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/array-unique/-/array-unique-0.3.2.tgz", + "integrity": "sha1-qJS3XUvE9s1nnvMkSp/Y9Gri1Cg=" + }, "arrify": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/arrify/-/arrify-1.0.1.tgz", - "integrity": "sha1-iYUI2iIm84DfkEcoRWhJwVAaSw0=", - "dev": true + "integrity": "sha1-iYUI2iIm84DfkEcoRWhJwVAaSw0=" }, "asn1": { - "version": "0.2.3", - "resolved": "https://registry.npmjs.org/asn1/-/asn1-0.2.3.tgz", - "integrity": "sha1-2sh4dxPJlmhJ/IGAd36+nB3fO4Y=" + "version": "0.2.4", + "resolved": "https://registry.npmjs.org/asn1/-/asn1-0.2.4.tgz", + "integrity": "sha512-jxwzQpLQjSmWXgwaCZE9Nz+glAG01yF1QnWgbhGwHI5A6FRIEY6IVqtHhIepHqI7/kyEyQEagBC5mBEFlIYvdg==", + "requires": { + "safer-buffer": "~2.1.0" + } }, "asn1.js": { "version": "4.10.1", @@ -156,6 +175,17 @@ "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=" }, + "assign-symbols": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/assign-symbols/-/assign-symbols-1.0.0.tgz", + "integrity": "sha1-WWZ/QfrdTyDMvCu5a41Pf3jsA2c=" + }, + "astral-regex": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/astral-regex/-/astral-regex-1.0.0.tgz", + "integrity": "sha512-+Ryf6g3BKoRc7jfp7ad8tM4TtMiaWvbF/1/sQcZPkkS7ag3D5nMBCe2UfOTONtAkaG0tO0ij3C5Lwmf1EiyjHg==", + "dev": true + }, "async-limiter": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/async-limiter/-/async-limiter-1.0.0.tgz", @@ -166,23 +196,28 @@ "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", "integrity": "sha1-x57Zf380y48robyXkLzDZkdLS3k=" }, + "atob": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/atob/-/atob-2.1.2.tgz", + "integrity": "sha512-Wm6ukoaOGJi/73p/cl2GvLjTI5JM1k/O14isD73YML8StrH/7/lRFgmg8nICZgD3bZZvjwCGxtMOD3wWNAu8cg==" + }, "aws-sign2": { "version": "0.7.0", "resolved": "https://registry.npmjs.org/aws-sign2/-/aws-sign2-0.7.0.tgz", "integrity": "sha1-tG6JCTSpWR8tL2+G1+ap8bP+dqg=" }, "aws4": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.6.0.tgz", - "integrity": "sha1-g+9cqGCysy5KDe7e6MdxudtXRx4=" + "version": "1.8.0", + "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.8.0.tgz", + "integrity": "sha512-ReZxvNHIOv88FlT7rxcXIIC0fPt4KZqZbOlivyWtXLt8ESx84zd3kMC6iK5jVeS2qt+g7ftS7ye4fi06X5rtRQ==" }, "babel-runtime": { - "version": "6.25.0", - "resolved": "https://registry.npmjs.org/babel-runtime/-/babel-runtime-6.25.0.tgz", - "integrity": "sha1-M7mOql1IK7AajRqmtDetKwGuxBw=", + "version": "6.26.0", + "resolved": "https://registry.npmjs.org/babel-runtime/-/babel-runtime-6.26.0.tgz", + "integrity": "sha1-llxwWGaOgrVde/4E/yM3vItWR/4=", "requires": { "core-js": "^2.4.0", - "regenerator-runtime": "^0.10.0" + "regenerator-runtime": "^0.11.0" } }, "balanced-match": { @@ -190,24 +225,76 @@ "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz", "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=" }, + "base": { + "version": "0.11.2", + "resolved": "https://registry.npmjs.org/base/-/base-0.11.2.tgz", + "integrity": "sha512-5T6P4xPgpp0YDFvSWwEZ4NoE3aM4QBQXDzmVbraCkFj8zHM+mba8SyqB5DbZWyR7mYHo6Y7BdQo3MoA4m0TeQg==", + "requires": { + "cache-base": "^1.0.1", + "class-utils": "^0.3.5", + "component-emitter": "^1.2.1", + "define-property": "^1.0.0", + "isobject": "^3.0.1", + "mixin-deep": "^1.2.0", + "pascalcase": "^0.1.1" + }, + "dependencies": { + "define-property": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-1.0.0.tgz", + "integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=", + "requires": { + "is-descriptor": "^1.0.0" + } + }, + "is-accessor-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz", + "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-data-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz", + "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-descriptor": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz", + "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", + "requires": { + "is-accessor-descriptor": "^1.0.0", + "is-data-descriptor": "^1.0.0", + "kind-of": "^6.0.2" + } + } + } + }, "base64-js": { - "version": "1.2.3", - "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-1.2.3.tgz", - "integrity": "sha512-MsAhsUW1GxCdgYSO6tAfZrNapmUKk7mWx/k5mFY/A1gBtkaCaNapTg+FExCw1r9yeaZhqx/xPg43xgTFH6KL5w==" + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-1.3.0.tgz", + "integrity": "sha512-ccav/yGvoa80BQDljCxsmmQ3Xvx60/UpBIij5QN21W3wBi/hhIC9OoO+KLpu9IJTS9j4DRVJ3aDDF9cMSoa2lw==" }, "bcrypt-pbkdf": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.1.tgz", - "integrity": "sha1-Y7xdy2EzG5K8Bf1SiVPDNGKgb40=", - "optional": true, + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.2.tgz", + "integrity": "sha1-pDAdOJtqQ/m2f/PKEaP2Y342Dp4=", "requires": { "tweetnacl": "^0.14.3" } }, "bindings": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/bindings/-/bindings-1.3.0.tgz", - "integrity": "sha512-DpLh5EzMR2kzvX1KIlVC0VkC3iZtHKTgdtZ0a3pglBZdaQFjt5S9g9xd1lE+YvXyfd6mtCeRnrUfOLYiTMlNSw==" + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/bindings/-/bindings-1.4.0.tgz", + "integrity": "sha512-7znEVX22Djn+nYjxCWKDne0RRloa9XfYa84yk3s+HkE3LpDYZmhArYr9O9huBoHY3/oXispx5LorIX7Sl2CgSQ==", + "requires": { + "file-uri-to-path": "1.0.0" + } }, "bip66": { "version": "1.1.5", @@ -235,9 +322,9 @@ } }, "bluebird": { - "version": "3.5.1", - "resolved": "https://registry.npmjs.org/bluebird/-/bluebird-3.5.1.tgz", - "integrity": "sha512-MKiLiV+I1AA596t9w1sQJ8jkiSr5+ZKi0WKrYGUn6d1Fx+Ij4tIj+m2WMQSGczs5jZVxV339chE8iwk6F64wjA==" + "version": "3.5.3", + "resolved": "https://registry.npmjs.org/bluebird/-/bluebird-3.5.3.tgz", + "integrity": "sha512-/qKPUQlaW1OyR51WeCPBvRnAlnZFUJkCSG5HzGnuIqhgyJtF+T94lFnn33eiazjRm2LAHVy2guNnaq48X9SJuw==" }, "bn.js": { "version": "4.11.8", @@ -245,28 +332,20 @@ "integrity": "sha512-ItfYfPLkWHUjckQCk8xC+LwxgK8NYcXywGigJgSwOP8Y2iyWT4f2vsZnoOXTTbo+o5yXmIUJ4gn5538SO5S3gA==" }, "body-parser": { - "version": "1.18.2", - "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.18.2.tgz", - "integrity": "sha1-h2eKGdhLR9hZuDGZvVm84iKxBFQ=", + "version": "1.18.3", + "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.18.3.tgz", + "integrity": "sha1-WykhmP/dVTs6DyDe0FkrlWlVyLQ=", "requires": { "bytes": "3.0.0", "content-type": "~1.0.4", "debug": "2.6.9", - "depd": "~1.1.1", - "http-errors": "~1.6.2", - "iconv-lite": "0.4.19", + "depd": "~1.1.2", + "http-errors": "~1.6.3", + "iconv-lite": "0.4.23", "on-finished": "~2.3.0", - "qs": "6.5.1", - "raw-body": "2.3.2", - "type-is": "~1.6.15" - } - }, - "boom": { - "version": "4.3.1", - "resolved": "https://registry.npmjs.org/boom/-/boom-4.3.1.tgz", - "integrity": "sha1-T4owBctKfjiJ90kDD9JbluAdLjE=", - "requires": { - "hoek": "4.x.x" + "qs": "6.5.2", + "raw-body": "2.3.3", + "type-is": "~1.6.16" } }, "brace-expansion": { @@ -278,15 +357,42 @@ "concat-map": "0.0.1" } }, + "braces": { + "version": "2.3.2", + "resolved": "https://registry.npmjs.org/braces/-/braces-2.3.2.tgz", + "integrity": "sha512-aNdbnj9P8PjdXU4ybaWLK2IF3jc/EoDYbC7AazW6to3TRsfXxscC9UXOB5iDiEQrkyIbWp2SLQda4+QAa7nc3w==", + "requires": { + "arr-flatten": "^1.1.0", + "array-unique": "^0.3.2", + "extend-shallow": "^2.0.1", + "fill-range": "^4.0.0", + "isobject": "^3.0.1", + "repeat-element": "^1.1.2", + "snapdragon": "^0.8.1", + "snapdragon-node": "^2.0.1", + "split-string": "^3.0.2", + "to-regex": "^3.0.1" + }, + "dependencies": { + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "requires": { + "is-extendable": "^0.1.0" + } + } + } + }, "brorand": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/brorand/-/brorand-1.1.0.tgz", "integrity": "sha1-EsJe/kCkXjwyPrhnWgoM5XsiNx8=" }, "browserify-aes": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/browserify-aes/-/browserify-aes-1.1.1.tgz", - "integrity": "sha512-UGnTYAnB2a3YuYKIRy1/4FB2HdM866E0qC46JXvVTYKlBlZlnvfpSfY6OKfXZAkv70eJ2a1SqzpAo5CRhZGDFg==", + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/browserify-aes/-/browserify-aes-1.2.0.tgz", + "integrity": "sha512-+7CHXqGuspUn/Sl5aO7Ea0xWGAtETPXNSAjHo48JfLdPWcMng33Xe4znFvQweqc/uzk5zSOI3H52CYnjCfb5hA==", "requires": { "buffer-xor": "^1.0.3", "cipher-base": "^1.0.0", @@ -297,9 +403,9 @@ } }, "browserify-cipher": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/browserify-cipher/-/browserify-cipher-1.0.0.tgz", - "integrity": "sha1-mYgkSHS/XtTijalWZtzWasj8Njo=", + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/browserify-cipher/-/browserify-cipher-1.0.1.tgz", + "integrity": "sha512-sPhkz0ARKbf4rRQt2hTpAHqn47X3llLkUGn+xEJzLjwY8LRs2p0v7ljvI5EyoRO/mexrNunNECisZs+gw2zz1w==", "requires": { "browserify-aes": "^1.0.4", "browserify-des": "^1.0.0", @@ -307,13 +413,14 @@ } }, "browserify-des": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/browserify-des/-/browserify-des-1.0.0.tgz", - "integrity": "sha1-2qJ3cXRwki7S/hhZQRihdUOXId0=", + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/browserify-des/-/browserify-des-1.0.2.tgz", + "integrity": "sha512-BioO1xf3hFwz4kc6iBhI3ieDFompMhrMlnDFC4/0/vd5MokpuAc3R+LYbwTA9A5Yc9pq9UYPqffKpW2ObuwX5A==", "requires": { "cipher-base": "^1.0.1", "des.js": "^1.0.0", - "inherits": "^2.0.1" + "inherits": "^2.0.1", + "safe-buffer": "^5.1.2" } }, "browserify-rsa": { @@ -326,11 +433,12 @@ } }, "browserify-sha3": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/browserify-sha3/-/browserify-sha3-0.0.1.tgz", - "integrity": "sha1-P/NKMAbvFcD7NWflQbkaI0ASPRE=", + "version": "0.0.4", + "resolved": "https://registry.npmjs.org/browserify-sha3/-/browserify-sha3-0.0.4.tgz", + "integrity": "sha1-CGxHuMgjFsnUcCLCYYWVRXbdjiY=", "requires": { - "js-sha3": "^0.3.1" + "js-sha3": "^0.6.1", + "safe-buffer": "^5.1.1" } }, "browserify-sign": { @@ -348,19 +456,38 @@ } }, "buffer": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/buffer/-/buffer-5.1.0.tgz", - "integrity": "sha512-YkIRgwsZwJWTnyQrsBTWefizHh+8GYj3kbL1BTiAQ/9pwpino0G7B2gp5tx/FUBqUlvtxV85KNR3mwfAtv15Yw==", + "version": "5.2.1", + "resolved": "https://registry.npmjs.org/buffer/-/buffer-5.2.1.tgz", + "integrity": "sha512-c+Ko0loDaFfuPWiL02ls9Xd3GO3cPVmUobQ6t3rXNUk304u6hGq+8N/kFi+QEIKhzK3uwolVhLzszmfLmMLnqg==", "requires": { "base64-js": "^1.0.2", "ieee754": "^1.1.4" } }, + "buffer-alloc": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/buffer-alloc/-/buffer-alloc-1.2.0.tgz", + "integrity": "sha512-CFsHQgjtW1UChdXgbyJGtnm+O/uLQeZdtbDo8mfUgYXCHSM1wgrVxXm6bSyrUuErEb+4sYVGCzASBRot7zyrow==", + "requires": { + "buffer-alloc-unsafe": "^1.1.0", + "buffer-fill": "^1.0.0" + } + }, + "buffer-alloc-unsafe": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/buffer-alloc-unsafe/-/buffer-alloc-unsafe-1.1.0.tgz", + "integrity": "sha512-TEM2iMIEQdJ2yjPJoSIsldnleVaAk1oW3DBVUykyOLsEsFmEc9kn+SFFPz+gl54KQNxlDnAwCXosOS9Okx2xAg==" + }, "buffer-crc32": { "version": "0.2.13", "resolved": "https://registry.npmjs.org/buffer-crc32/-/buffer-crc32-0.2.13.tgz", "integrity": "sha1-DTM+PwDqxQqhRUq9MO+MKl2ackI=" }, + "buffer-fill": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/buffer-fill/-/buffer-fill-1.0.0.tgz", + "integrity": "sha1-+PeLdniYiO858gXNY39o5wISKyw=" + }, "buffer-to-arraybuffer": { "version": "0.0.5", "resolved": "https://registry.npmjs.org/buffer-to-arraybuffer/-/buffer-to-arraybuffer-0.0.5.tgz", @@ -371,12 +498,6 @@ "resolved": "https://registry.npmjs.org/buffer-xor/-/buffer-xor-1.0.3.tgz", "integrity": "sha1-JuYe0UIvtw3ULm42cp7VHYVf6Nk=" }, - "builtin-modules": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/builtin-modules/-/builtin-modules-1.1.1.tgz", - "integrity": "sha1-Jw8HbFpywC9bZaR9+Uxf46J4iS8=", - "dev": true - }, "byline": { "version": "5.0.0", "resolved": "https://registry.npmjs.org/byline/-/byline-5.0.0.tgz", @@ -387,19 +508,31 @@ "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.0.0.tgz", "integrity": "sha1-0ygVQE1olpn4Wk6k+odV3ROpYEg=" }, - "caller-path": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/caller-path/-/caller-path-0.1.0.tgz", - "integrity": "sha1-lAhe9jWB7NPaqSREqP6U6CV3dR8=", - "dev": true, + "cache-base": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/cache-base/-/cache-base-1.0.1.tgz", + "integrity": "sha512-AKcdTnFSWATd5/GCPRxr2ChwIJ85CeyrEyjRHlKxQ56d4XJMGym0uAiKn0xbLOGOl3+yRpOTi484dVCEc5AUzQ==", "requires": { - "callsites": "^0.2.0" + "collection-visit": "^1.0.0", + "component-emitter": "^1.2.1", + "get-value": "^2.0.6", + "has-value": "^1.0.0", + "isobject": "^3.0.1", + "set-value": "^2.0.0", + "to-object-path": "^0.3.0", + "union-value": "^1.0.0", + "unset-value": "^1.0.0" } }, + "call-me-maybe": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/call-me-maybe/-/call-me-maybe-1.0.1.tgz", + "integrity": "sha1-JtII6onje1y95gJQoV8DHBak1ms=" + }, "callsites": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/callsites/-/callsites-0.2.0.tgz", - "integrity": "sha1-r6uWJikQp/M8GaV3WCXGnzTjUMo=", + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/callsites/-/callsites-3.0.0.tgz", + "integrity": "sha512-tWnkwu9YEq2uzlBDI4RcLn8jrFvF9AOi8PxDNU3hZZjJcjkcRAq3vCI+vZcg1SuxISDYe86k9VZFwAxDiJGoAw==", "dev": true }, "caseless": { @@ -408,13 +541,13 @@ "integrity": "sha1-G2gcIf+EAzyCZUMJBolCDRhxUdw=" }, "chalk": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.1.0.tgz", - "integrity": "sha512-LUHGS/dge4ujbXMJrnihYMcL4AoOweGnw9Tp3kQuqy1Kx5c1qKjqvMJZ6nVJPMWJtKCTN72ZogH3oeSO9g9rXQ==", + "version": "2.4.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz", + "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==", "requires": { - "ansi-styles": "^3.1.0", + "ansi-styles": "^3.2.1", "escape-string-regexp": "^1.0.5", - "supports-color": "^4.0.0" + "supports-color": "^5.3.0" } }, "chardet": { @@ -432,11 +565,26 @@ "safe-buffer": "^5.0.1" } }, - "circular-json": { - "version": "0.3.3", - "resolved": "https://registry.npmjs.org/circular-json/-/circular-json-0.3.3.tgz", - "integrity": "sha512-UZK3NBx2Mca+b5LsG7bY183pHWt5Y1xts4P3Pz7ENTwGVnJOUWbRb3ocjvX7hx9tq/yTAdclXm9sZ38gNuem4A==", - "dev": true + "class-utils": { + "version": "0.3.6", + "resolved": "https://registry.npmjs.org/class-utils/-/class-utils-0.3.6.tgz", + "integrity": "sha512-qOhPa/Fj7s6TY8H8esGu5QNpMMQxz79h+urzrNYN6mn+9BnxlDGf5QZ+XeCDsxSjPqsSR56XOZOJmpeurnLMeg==", + "requires": { + "arr-union": "^3.1.0", + "define-property": "^0.2.5", + "isobject": "^3.0.0", + "static-extend": "^0.1.1" + }, + "dependencies": { + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "requires": { + "is-descriptor": "^0.1.0" + } + } + } }, "cli-cursor": { "version": "2.1.0", @@ -453,17 +601,21 @@ "integrity": "sha1-/xnt6Kml5XkyQUewwR8PvLq+1jk=", "dev": true }, - "co": { - "version": "4.6.0", - "resolved": "https://registry.npmjs.org/co/-/co-4.6.0.tgz", - "integrity": "sha1-bqa989hTrlTMuOR7+gvz+QMfsYQ=" + "collection-visit": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/collection-visit/-/collection-visit-1.0.0.tgz", + "integrity": "sha1-S8A3PBZLwykbTTaMgpzxqApZ3KA=", + "requires": { + "map-visit": "^1.0.0", + "object-visit": "^1.0.0" + } }, "color-convert": { - "version": "1.9.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.1.tgz", - "integrity": "sha512-mjGanIiwQJskCC18rPR6OmrZ6fm2Lc7PeGFYwCmy5J34wC6F1PzdGL6xeMfmgicfYcNLGuVFA3WzXtIDCQSZxQ==", + "version": "1.9.3", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.3.tgz", + "integrity": "sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==", "requires": { - "color-name": "^1.1.1" + "color-name": "1.1.3" } }, "color-name": { @@ -472,9 +624,9 @@ "integrity": "sha1-p9BVi9icQveV3UIyj3QIMcpTvCU=" }, "combined-stream": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.6.tgz", - "integrity": "sha1-cj599ugBrFYTETp+RFqbactjKBg=", + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.7.tgz", + "integrity": "sha512-brWl9y6vOB1xYPZcpZde3N9zDByXTosAeMDo4p1wzo6UMOX4vumB+TP1RZ76sfE6Md68Q0NJSrE/gbezd4Ul+w==", "requires": { "delayed-stream": "~1.0.0" } @@ -487,6 +639,11 @@ "graceful-readlink": ">= 1.0.0" } }, + "component-emitter": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/component-emitter/-/component-emitter-1.2.1.tgz", + "integrity": "sha1-E3kY1teCg/ffemt8WmPhQOaUJeY=" + }, "concat-map": { "version": "0.0.1", "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", @@ -518,10 +675,15 @@ "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz", "integrity": "sha1-4wOogrNCzD7oylE6eZmXNNqzriw=" }, + "copy-descriptor": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/copy-descriptor/-/copy-descriptor-0.1.1.tgz", + "integrity": "sha1-Z29us8OZl8LuGsOpJP1hJHSPV40=" + }, "core-js": { - "version": "2.5.4", - "resolved": "https://registry.npmjs.org/core-js/-/core-js-2.5.4.tgz", - "integrity": "sha1-8si/GB8qgLkvNgEhQpzmOi8K6uA=" + "version": "2.6.5", + "resolved": "https://registry.npmjs.org/core-js/-/core-js-2.6.5.tgz", + "integrity": "sha512-klh/kDpwX8hryYL14M9w/xei6vrv6sE8gTHDG7/T/+SEovB/G4ejwcfE/CBzO6Edsu+OETZMZ3wcX/EjUkrl5A==" }, "core-util-is": { "version": "1.0.2", @@ -529,38 +691,39 @@ "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=" }, "cors": { - "version": "2.8.4", - "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.4.tgz", - "integrity": "sha1-K9OB8usgECAQXNUOpZ2mMJBpRoY=", + "version": "2.8.5", + "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.5.tgz", + "integrity": "sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==", "requires": { "object-assign": "^4", "vary": "^1" } }, "create-ecdh": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/create-ecdh/-/create-ecdh-4.0.0.tgz", - "integrity": "sha1-iIxyNZbN92EvZJgjPuvXo1MBc30=", + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/create-ecdh/-/create-ecdh-4.0.3.tgz", + "integrity": "sha512-GbEHQPMOswGpKXM9kCWVrremUcBmjteUaQ01T9rkKCPDXfUHX0IoP9LpHYo2NPFampa4e+/pFDc3jQdxrxQLaw==", "requires": { "bn.js": "^4.1.0", "elliptic": "^6.0.0" } }, "create-hash": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/create-hash/-/create-hash-1.1.3.tgz", - "integrity": "sha1-YGBCrIuSYnUPSDyt2rD1gZFy2P0=", + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/create-hash/-/create-hash-1.2.0.tgz", + "integrity": "sha512-z00bCGNHDG8mHAkP7CtT1qVu+bFQUPjYq/4Iv3C3kWjTFV10zIjfSoeqXo9Asws8gwSHDGj/hl2u4OGIjapeCg==", "requires": { "cipher-base": "^1.0.1", "inherits": "^2.0.1", - "ripemd160": "^2.0.0", + "md5.js": "^1.3.4", + "ripemd160": "^2.0.1", "sha.js": "^2.4.0" } }, "create-hmac": { - "version": "1.1.6", - "resolved": "https://registry.npmjs.org/create-hmac/-/create-hmac-1.1.6.tgz", - "integrity": "sha1-rLniIaThe9sHbpBlfEK5PjcmzwY=", + "version": "1.1.7", + "resolved": "https://registry.npmjs.org/create-hmac/-/create-hmac-1.1.7.tgz", + "integrity": "sha512-MJG9liiZ+ogc4TzUwuvbER1JRdgvUFSB5+VR/g5h82fGaIRWMWddtKBHi7/sVhfjQZ6SehlyhvQYrcYkaUIpLg==", "requires": { "cipher-base": "^1.0.3", "create-hash": "^1.1.0", @@ -581,32 +744,6 @@ "semver": "^5.5.0", "shebang-command": "^1.2.0", "which": "^1.2.9" - }, - "dependencies": { - "semver": { - "version": "5.5.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.5.1.tgz", - "integrity": "sha512-PqpAxfrEhlSUWge8dwIp4tZnQ25DIOthpiaHNIthsjEFQD6EvqUKUDM7L8O2rShkFccYo1VjJR0coWfNkCubRw==", - "dev": true - } - } - }, - "cryptiles": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/cryptiles/-/cryptiles-3.1.2.tgz", - "integrity": "sha1-qJ+7Ig9c4l7FboxKqKT9e1sNKf4=", - "requires": { - "boom": "5.x.x" - }, - "dependencies": { - "boom": { - "version": "5.2.0", - "resolved": "https://registry.npmjs.org/boom/-/boom-5.2.0.tgz", - "integrity": "sha512-Z5BTk6ZRe4tXXQlkqftmsAUANpXmuwlsF5Oov8ThoMbQRzdGTA1ngYRW160GexgOgjsFOKJz0LYhoNi+2AMBUw==", - "requires": { - "hoek": "4.x.x" - } - } } }, "crypto-browserify": { @@ -661,6 +798,13 @@ "make-dir": "^1.0.0", "pify": "^2.3.0", "strip-dirs": "^2.0.0" + }, + "dependencies": { + "pify": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", + "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=" + } } }, "decompress-response": { @@ -734,6 +878,11 @@ "object-assign": "^4.0.1", "pinkie-promise": "^2.0.0" } + }, + "pify": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", + "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=" } } }, @@ -751,33 +900,39 @@ "object-keys": "^1.0.12" } }, - "del": { - "version": "2.2.2", - "resolved": "https://registry.npmjs.org/del/-/del-2.2.2.tgz", - "integrity": "sha1-wSyYHQZ4RshLyvhiz/kw2Qf/0ag=", - "dev": true, + "define-property": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-2.0.2.tgz", + "integrity": "sha512-jwK2UV4cnPpbcG7+VRARKTZPUWowwXA8bzH5NP6ud0oeAxyYPuGZUAC7hMugpCdz4BeSZl2Dl9k66CHJ/46ZYQ==", "requires": { - "globby": "^5.0.0", - "is-path-cwd": "^1.0.0", - "is-path-in-cwd": "^1.0.0", - "object-assign": "^4.0.1", - "pify": "^2.0.0", - "pinkie-promise": "^2.0.0", - "rimraf": "^2.2.8" + "is-descriptor": "^1.0.2", + "isobject": "^3.0.1" }, "dependencies": { - "globby": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/globby/-/globby-5.0.0.tgz", - "integrity": "sha1-69hGZ8oNuzMLmbz8aOrCvFQ3Dg0=", - "dev": true, + "is-accessor-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz", + "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", "requires": { - "array-union": "^1.0.1", - "arrify": "^1.0.0", - "glob": "^7.0.3", - "object-assign": "^4.0.1", - "pify": "^2.0.0", - "pinkie-promise": "^2.0.0" + "kind-of": "^6.0.0" + } + }, + "is-data-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz", + "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-descriptor": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz", + "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", + "requires": { + "is-accessor-descriptor": "^1.0.0", + "is-data-descriptor": "^1.0.0", + "kind-of": "^6.0.2" } } } @@ -807,19 +962,28 @@ "integrity": "sha1-l4hXRCxEdJ5CBmE+N5RiBYJqvYA=" }, "diffie-hellman": { - "version": "5.0.2", - "resolved": "https://registry.npmjs.org/diffie-hellman/-/diffie-hellman-5.0.2.tgz", - "integrity": "sha1-tYNXOScM/ias9jIJn97SoH8gnl4=", + "version": "5.0.3", + "resolved": "https://registry.npmjs.org/diffie-hellman/-/diffie-hellman-5.0.3.tgz", + "integrity": "sha512-kqag/Nl+f3GwyK25fhUMYj81BUOrZ9IuJsjIcDE5icNM9FJHAVm3VcUDxdLPoQtTuUylWm6ZIknYJwwaPxsUzg==", "requires": { "bn.js": "^4.1.0", "miller-rabin": "^4.0.0", "randombytes": "^2.0.0" } }, + "dir-glob": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/dir-glob/-/dir-glob-2.0.0.tgz", + "integrity": "sha512-37qirFDz8cA5fimp9feo43fSuRo2gHwaIn6dXL8Ber1dGwUosDrGZeCCXq57WnIqE4aQ+u3eQZzsk1yOzhdwag==", + "requires": { + "arrify": "^1.0.1", + "path-type": "^3.0.0" + } + }, "doctrine": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-2.1.0.tgz", - "integrity": "sha512-35mSku4ZXK0vfCuHEDAwt55dg2jNajHZ1odvF+8SSr82EsZY4QmXfuWso8oEd8zRhVObSN18aM0CjSdoBX7zIw==", + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-3.0.0.tgz", + "integrity": "sha512-yS+Q5i3hBf7GBkd4KG8a7eBNNWNGLTaEwwYWUijIYM7zrlYDM0BFXHjjPWlWZ1Rg7UaddZeIDmi9jF3HmqiQ2w==", "dev": true, "requires": { "esutils": "^2.0.2" @@ -851,12 +1015,12 @@ "integrity": "sha1-7gHdHKwO08vH/b6jfcCo8c4ALOI=" }, "ecc-jsbn": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/ecc-jsbn/-/ecc-jsbn-0.1.1.tgz", - "integrity": "sha1-D8c6ntXw1Tw4GTOYUj735UN3dQU=", - "optional": true, + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/ecc-jsbn/-/ecc-jsbn-0.1.2.tgz", + "integrity": "sha1-OoOpBOVDUyh4dMVkt1SThoSamMk=", "requires": { - "jsbn": "~0.1.0" + "jsbn": "~0.1.0", + "safer-buffer": "^2.1.0" } }, "ee-first": { @@ -865,9 +1029,9 @@ "integrity": "sha1-WQxhFWsK4vTwJVcyoViyZrxWsh0=" }, "elliptic": { - "version": "6.4.0", - "resolved": "https://registry.npmjs.org/elliptic/-/elliptic-6.4.0.tgz", - "integrity": "sha1-ysmvh2LIWDYYcAPI3+GT5eLq5d8=", + "version": "6.4.1", + "resolved": "https://registry.npmjs.org/elliptic/-/elliptic-6.4.1.tgz", + "integrity": "sha512-BsXLz5sqX8OHcsh7CqBMztyXARmGQ3LWPtGjJi6DiJHq5C/qvi9P3OqgswKSDftbu8+IoI/QDTAm2fFnQ9SZSQ==", "requires": { "bn.js": "^4.4.0", "brorand": "^1.0.1", @@ -878,6 +1042,12 @@ "minimalistic-crypto-utils": "^1.0.0" } }, + "emoji-regex": { + "version": "7.0.3", + "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-7.0.3.tgz", + "integrity": "sha512-CwBLREIQ7LvYFB0WyRvwhq5N5qPhc6PMjD6bYggFlI5YyDgl+0vxq5VHbMOFqLg7hfWzmu8T5Z1QofhmTIhItA==", + "dev": true + }, "encodeurl": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-1.0.2.tgz", @@ -892,20 +1062,20 @@ } }, "envalid": { - "version": "4.1.4", - "resolved": "https://registry.npmjs.org/envalid/-/envalid-4.1.4.tgz", - "integrity": "sha512-Xz1fNmcAFLQsUcYgoN2YmXkl9hGfLFXpvTHJKEBW/Nsqj+/4WoFnGf6wbdxJXIx5aKpdapf8XJCGrCRfrk2OZg==", - "requires": { - "chalk": "2.1.0", - "dotenv": "4.0.0", - "meant": "1.0.0", - "validator": "9.4.1" + "version": "4.2.2", + "resolved": "https://registry.npmjs.org/envalid/-/envalid-4.2.2.tgz", + "integrity": "sha512-D6RV00pb4c/eKzslI8bwCeLhBrD9GzNrAa2QRoSto9LdwEQXhsHUKfI61areFi6LvLDVFmlHnrk/SD34UJiMpg==", + "requires": { + "chalk": "^2.4.1", + "dotenv": "^6.2.0", + "meant": "^1.0.1", + "validator": "^10.11.0" }, "dependencies": { "dotenv": { - "version": "4.0.0", - "resolved": "http://registry.npmjs.org/dotenv/-/dotenv-4.0.0.tgz", - "integrity": "sha1-hk7xN5rO1Vzm+V3r7NzhefegzR0=" + "version": "6.2.0", + "resolved": "https://registry.npmjs.org/dotenv/-/dotenv-6.2.0.tgz", + "integrity": "sha512-HygQCKUBSFl8wKQZBSemMywRWcEDNidvNbjGVyZu3nbZ8qq9ubiPoGLMdRDpfSrpkkm9BXYFkpKxxFX38o/76w==" } } }, @@ -919,27 +1089,28 @@ } }, "es-abstract": { - "version": "1.12.0", - "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.12.0.tgz", - "integrity": "sha512-C8Fx/0jFmV5IPoMOFPA9P9G5NtqW+4cOPit3MIuvR2t7Ag2K15EJTpxnHAYTzL+aYQJIESYeXZmDBfOBE1HcpA==", + "version": "1.13.0", + "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.13.0.tgz", + "integrity": "sha512-vDZfg/ykNxQVwup/8E1BZhVzFfBxs9NqMzGcvIJrqg5k2/5Za2bWo40dK2J1pgLngZ7c+Shh8lwYtLGyrwPutg==", "dev": true, "requires": { - "es-to-primitive": "^1.1.1", + "es-to-primitive": "^1.2.0", "function-bind": "^1.1.1", - "has": "^1.0.1", - "is-callable": "^1.1.3", - "is-regex": "^1.0.4" + "has": "^1.0.3", + "is-callable": "^1.1.4", + "is-regex": "^1.0.4", + "object-keys": "^1.0.12" } }, "es-to-primitive": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/es-to-primitive/-/es-to-primitive-1.1.1.tgz", - "integrity": "sha1-RTVSSKiJeQNLZ5Lhm7gfK3l13Q0=", + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/es-to-primitive/-/es-to-primitive-1.2.0.tgz", + "integrity": "sha512-qZryBOJjV//LaxLTV6UC//WewneB3LcXOL9NP++ozKVXsIIIpm/2c13UDiD9Jp2eThsecw9m3jPqDwTyobcdbg==", "dev": true, "requires": { - "is-callable": "^1.1.1", + "is-callable": "^1.1.4", "is-date-object": "^1.0.1", - "is-symbol": "^1.0.1" + "is-symbol": "^1.0.2" } }, "escape-html": { @@ -953,94 +1124,74 @@ "integrity": "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=" }, "escodegen": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/escodegen/-/escodegen-1.8.1.tgz", - "integrity": "sha1-WltTr0aTEQvrsIZ6o0MN07cKEBg=", + "version": "1.11.0", + "resolved": "https://registry.npmjs.org/escodegen/-/escodegen-1.11.0.tgz", + "integrity": "sha512-IeMV45ReixHS53K/OmfKAIztN/igDHzTJUhZM3k1jMhIZWjk45SMwAtBsEXiJp3vSPmTcu6CXn7mDvFHRN66fw==", "requires": { - "esprima": "^2.7.1", - "estraverse": "^1.9.1", + "esprima": "^3.1.3", + "estraverse": "^4.2.0", "esutils": "^2.0.2", "optionator": "^0.8.1", - "source-map": "~0.2.0" + "source-map": "~0.6.1" } }, "eslint": { - "version": "5.6.0", - "resolved": "https://registry.npmjs.org/eslint/-/eslint-5.6.0.tgz", - "integrity": "sha512-/eVYs9VVVboX286mBK7bbKnO1yamUy2UCRjiY6MryhQL2PaaXCExsCQ2aO83OeYRhU2eCU/FMFP+tVMoOrzNrA==", + "version": "5.14.1", + "resolved": "https://registry.npmjs.org/eslint/-/eslint-5.14.1.tgz", + "integrity": "sha512-CyUMbmsjxedx8B0mr79mNOqetvkbij/zrXnFeK2zc3pGRn3/tibjiNAv/3UxFEyfMDjh+ZqTrJrEGBFiGfD5Og==", "dev": true, "requires": { "@babel/code-frame": "^7.0.0", - "ajv": "^6.5.3", + "ajv": "^6.9.1", "chalk": "^2.1.0", "cross-spawn": "^6.0.5", - "debug": "^3.1.0", - "doctrine": "^2.1.0", + "debug": "^4.0.1", + "doctrine": "^3.0.0", "eslint-scope": "^4.0.0", "eslint-utils": "^1.3.1", "eslint-visitor-keys": "^1.0.0", - "espree": "^4.0.0", + "espree": "^5.0.1", "esquery": "^1.0.1", "esutils": "^2.0.2", - "file-entry-cache": "^2.0.0", + "file-entry-cache": "^5.0.1", "functional-red-black-tree": "^1.0.1", "glob": "^7.1.2", "globals": "^11.7.0", "ignore": "^4.0.6", + "import-fresh": "^3.0.0", "imurmurhash": "^0.1.4", - "inquirer": "^6.1.0", - "is-resolvable": "^1.1.0", + "inquirer": "^6.2.2", "js-yaml": "^3.12.0", "json-stable-stringify-without-jsonify": "^1.0.1", "levn": "^0.3.0", - "lodash": "^4.17.5", + "lodash": "^4.17.11", "minimatch": "^3.0.4", "mkdirp": "^0.5.1", "natural-compare": "^1.4.0", "optionator": "^0.8.2", "path-is-inside": "^1.0.2", - "pluralize": "^7.0.0", "progress": "^2.0.0", - "regexpp": "^2.0.0", - "require-uncached": "^1.0.3", + "regexpp": "^2.0.1", "semver": "^5.5.1", "strip-ansi": "^4.0.0", "strip-json-comments": "^2.0.1", - "table": "^4.0.3", + "table": "^5.2.3", "text-table": "^0.2.0" }, "dependencies": { - "ajv": { - "version": "6.5.3", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.5.3.tgz", - "integrity": "sha512-LqZ9wY+fx3UMiiPd741yB2pj3hhil+hQc8taf4o2QGRFpWgZ2V5C8HA165DY9sS3fJwsk7uT7ZlFEyC3Ig3lLg==", - "dev": true, - "requires": { - "fast-deep-equal": "^2.0.1", - "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.4.1", - "uri-js": "^4.2.2" - } - }, "debug": { - "version": "3.2.5", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.2.5.tgz", - "integrity": "sha512-D61LaDQPQkxJ5AUM2mbSJRbPkNs/TmdmOeLAi1hgDkpDfIfetSrjmWhccwtuResSwMbACjx/xXQofvM9CE/aeg==", + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.1.1.tgz", + "integrity": "sha512-pYAIzeRo8J6KPEaJ0VWOh5Pzkbw/RetuzehGM7QRRX5he4fPHx2rdKMB256ehJCkX+XRQm16eZLqLNS8RSZXZw==", "dev": true, "requires": { "ms": "^2.1.1" } }, - "fast-deep-equal": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-2.0.1.tgz", - "integrity": "sha1-ewUhjd+WZ79/Nwv3/bLLFf3Qqkk=", - "dev": true - }, - "json-schema-traverse": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", - "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", + "ignore": { + "version": "4.0.6", + "resolved": "https://registry.npmjs.org/ignore/-/ignore-4.0.6.tgz", + "integrity": "sha512-cyFDKrqc/YdcWFniJhzI42+AzS+gNwmUzOSFcRCQYwySuBBBy/KjuxWLZ/FHEH6Moq1NizMOBWyTcv8O4OZIMg==", "dev": true }, "ms": { @@ -1048,12 +1199,6 @@ "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.1.tgz", "integrity": "sha512-tgp+dl5cGk28utYktBsrFqA7HKgrhgPsg6Z/EfhWI4gl1Hwq8B/GmY/0oXZ6nF8hDVesS/FpnYaD/kOWhYQvyg==", "dev": true - }, - "semver": { - "version": "5.5.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.5.1.tgz", - "integrity": "sha512-PqpAxfrEhlSUWge8dwIp4tZnQ25DIOthpiaHNIthsjEFQD6EvqUKUDM7L8O2rShkFccYo1VjJR0coWfNkCubRw==", - "dev": true } } }, @@ -1069,9 +1214,9 @@ } }, "eslint-config-prettier": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/eslint-config-prettier/-/eslint-config-prettier-3.0.1.tgz", - "integrity": "sha512-vA0TB8HCx/idHXfKHYcg9J98p0Q8nkfNwNAoP7e+ywUidn6ScaFS5iqncZAHPz+/a0A/tp657ulFHFx/2JDP4Q==", + "version": "3.6.0", + "resolved": "https://registry.npmjs.org/eslint-config-prettier/-/eslint-config-prettier-3.6.0.tgz", + "integrity": "sha512-ixJ4U3uTLXwJts4rmSVW/lMXjlGwCijhBJHk8iVqKKSifeI0qgFEfWl8L63isfc8Od7EiBALF6BX3jKLluf/jQ==", "dev": true, "requires": { "get-stdin": "^6.0.0" @@ -1085,55 +1230,44 @@ "requires": { "debug": "^2.6.9", "resolve": "^1.5.0" - }, - "dependencies": { - "resolve": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.8.1.tgz", - "integrity": "sha512-AicPrAC7Qu1JxPCZ9ZgCZlY35QgFnNqc+0LtbRNxnVw4TXvjQ72wnuL9JQcEBgXkI9JM8MsT9kaQoHcpCRJOYA==", - "dev": true, - "requires": { - "path-parse": "^1.0.5" - } - } } }, "eslint-module-utils": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/eslint-module-utils/-/eslint-module-utils-2.2.0.tgz", - "integrity": "sha1-snA2LNiLGkitMIl2zn+lTphBF0Y=", + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/eslint-module-utils/-/eslint-module-utils-2.3.0.tgz", + "integrity": "sha512-lmDJgeOOjk8hObTysjqH7wyMi+nsHwwvfBykwfhjR1LNdd7C2uFJBvx4OpWYpXOw4df1yE1cDEVd1yLHitk34w==", "dev": true, "requires": { "debug": "^2.6.8", - "pkg-dir": "^1.0.0" + "pkg-dir": "^2.0.0" } }, "eslint-plugin-es": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/eslint-plugin-es/-/eslint-plugin-es-1.3.1.tgz", - "integrity": "sha512-9XcVyZiQRVeFjqHw8qHNDAZcQLqaHlOGGpeYqzYh8S4JYCWTCO3yzyen8yVmA5PratfzTRWDwCOFphtDEG+w/w==", + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/eslint-plugin-es/-/eslint-plugin-es-1.4.0.tgz", + "integrity": "sha512-XfFmgFdIUDgvaRAlaXUkxrRg5JSADoRC8IkKLc/cISeR3yHVMefFHQZpcyXXEUUPHfy5DwviBcrfqlyqEwlQVw==", "dev": true, "requires": { "eslint-utils": "^1.3.0", - "regexpp": "^2.0.0" + "regexpp": "^2.0.1" } }, "eslint-plugin-import": { - "version": "2.14.0", - "resolved": "https://registry.npmjs.org/eslint-plugin-import/-/eslint-plugin-import-2.14.0.tgz", - "integrity": "sha512-FpuRtniD/AY6sXByma2Wr0TXvXJ4nA/2/04VPlfpmUDPOpOY264x+ILiwnrk/k4RINgDAyFZByxqPUbSQ5YE7g==", + "version": "2.16.0", + "resolved": "https://registry.npmjs.org/eslint-plugin-import/-/eslint-plugin-import-2.16.0.tgz", + "integrity": "sha512-z6oqWlf1x5GkHIFgrSvtmudnqM6Q60KM4KvpWi5ubonMjycLjndvd5+8VAZIsTlHC03djdgJuyKG6XO577px6A==", "dev": true, "requires": { "contains-path": "^0.1.0", - "debug": "^2.6.8", + "debug": "^2.6.9", "doctrine": "1.5.0", - "eslint-import-resolver-node": "^0.3.1", - "eslint-module-utils": "^2.2.0", - "has": "^1.0.1", - "lodash": "^4.17.4", - "minimatch": "^3.0.3", + "eslint-import-resolver-node": "^0.3.2", + "eslint-module-utils": "^2.3.0", + "has": "^1.0.3", + "lodash": "^4.17.11", + "minimatch": "^3.0.4", "read-pkg-up": "^2.0.0", - "resolve": "^1.6.0" + "resolve": "^1.9.0" }, "dependencies": { "doctrine": { @@ -1147,12 +1281,12 @@ } }, "resolve": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.8.1.tgz", - "integrity": "sha512-AicPrAC7Qu1JxPCZ9ZgCZlY35QgFnNqc+0LtbRNxnVw4TXvjQ72wnuL9JQcEBgXkI9JM8MsT9kaQoHcpCRJOYA==", + "version": "1.10.0", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.10.0.tgz", + "integrity": "sha512-3sUr9aq5OfSg2S9pNtPA9hL1FVEAjvfOC4leW0SNf/mpnaakz2a9femSd6LqAww2RaFctwyf1lCqnTHuF1rxDg==", "dev": true, "requires": { - "path-parse": "^1.0.5" + "path-parse": "^1.0.6" } } } @@ -1171,27 +1305,27 @@ "semver": "^5.5.0" }, "dependencies": { + "ignore": { + "version": "4.0.6", + "resolved": "https://registry.npmjs.org/ignore/-/ignore-4.0.6.tgz", + "integrity": "sha512-cyFDKrqc/YdcWFniJhzI42+AzS+gNwmUzOSFcRCQYwySuBBBy/KjuxWLZ/FHEH6Moq1NizMOBWyTcv8O4OZIMg==", + "dev": true + }, "resolve": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.8.1.tgz", - "integrity": "sha512-AicPrAC7Qu1JxPCZ9ZgCZlY35QgFnNqc+0LtbRNxnVw4TXvjQ72wnuL9JQcEBgXkI9JM8MsT9kaQoHcpCRJOYA==", + "version": "1.10.0", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.10.0.tgz", + "integrity": "sha512-3sUr9aq5OfSg2S9pNtPA9hL1FVEAjvfOC4leW0SNf/mpnaakz2a9femSd6LqAww2RaFctwyf1lCqnTHuF1rxDg==", "dev": true, "requires": { - "path-parse": "^1.0.5" + "path-parse": "^1.0.6" } - }, - "semver": { - "version": "5.5.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.5.1.tgz", - "integrity": "sha512-PqpAxfrEhlSUWge8dwIp4tZnQ25DIOthpiaHNIthsjEFQD6EvqUKUDM7L8O2rShkFccYo1VjJR0coWfNkCubRw==", - "dev": true } } }, "eslint-plugin-prettier": { - "version": "2.6.2", - "resolved": "https://registry.npmjs.org/eslint-plugin-prettier/-/eslint-plugin-prettier-2.6.2.tgz", - "integrity": "sha512-tGek5clmW5swrAx1mdPYM8oThrBE83ePh7LeseZHBWfHVGrHPhKn7Y5zgRMbU/9D5Td9K4CEmUPjGxA7iw98Og==", + "version": "2.7.0", + "resolved": "https://registry.npmjs.org/eslint-plugin-prettier/-/eslint-plugin-prettier-2.7.0.tgz", + "integrity": "sha512-CStQYJgALoQBw3FsBzH0VOVDRnJ/ZimUlpLm226U8qgqYJfPOY/CPK6wyRInMxh73HSKg5wyRwdS4BVYYHwokA==", "dev": true, "requires": { "fast-diff": "^1.1.1", @@ -1212,14 +1346,6 @@ "requires": { "esrecurse": "^4.1.0", "estraverse": "^4.1.1" - }, - "dependencies": { - "estraverse": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-4.2.0.tgz", - "integrity": "sha1-De4/7TH81GlhjOc0IJn8GvoL2xM=", - "dev": true - } } }, "eslint-utils": { @@ -1235,27 +1361,20 @@ "dev": true }, "espree": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/espree/-/espree-4.0.0.tgz", - "integrity": "sha512-kapdTCt1bjmspxStVKX6huolXVV5ZfyZguY1lcfhVVZstce3bqxH9mcLzNn3/mlgW6wQ732+0fuG9v7h0ZQoKg==", + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/espree/-/espree-5.0.1.tgz", + "integrity": "sha512-qWAZcWh4XE/RwzLJejfcofscgMc9CamR6Tn1+XRXNzrvUSSbiAjGOI/fggztjIi7y9VLPqnICMIPiGyr8JaZ0A==", "dev": true, "requires": { - "acorn": "^5.6.0", - "acorn-jsx": "^4.1.1" - }, - "dependencies": { - "acorn": { - "version": "5.7.3", - "resolved": "https://registry.npmjs.org/acorn/-/acorn-5.7.3.tgz", - "integrity": "sha512-T/zvzYRfbVojPWahDsE5evJdHb3oJoQfFbsrKM7w5Zcs++Tr257tia3BmMP8XYVjp1S9RZXQMh7gao96BlqZOw==", - "dev": true - } + "acorn": "^6.0.7", + "acorn-jsx": "^5.0.0", + "eslint-visitor-keys": "^1.0.0" } }, "esprima": { - "version": "2.7.3", - "resolved": "https://registry.npmjs.org/esprima/-/esprima-2.7.3.tgz", - "integrity": "sha1-luO3DVd59q1JzQMmc9HDEnZ7pYE=" + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/esprima/-/esprima-3.1.3.tgz", + "integrity": "sha1-/cpRzuYTOJXjyI1TXOSdv/YqRjM=" }, "esquery": { "version": "1.0.1", @@ -1264,14 +1383,6 @@ "dev": true, "requires": { "estraverse": "^4.0.0" - }, - "dependencies": { - "estraverse": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-4.2.0.tgz", - "integrity": "sha1-De4/7TH81GlhjOc0IJn8GvoL2xM=", - "dev": true - } } }, "esrecurse": { @@ -1281,20 +1392,12 @@ "dev": true, "requires": { "estraverse": "^4.1.0" - }, - "dependencies": { - "estraverse": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-4.2.0.tgz", - "integrity": "sha1-De4/7TH81GlhjOc0IJn8GvoL2xM=", - "dev": true - } } }, "estraverse": { - "version": "1.9.3", - "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-1.9.3.tgz", - "integrity": "sha1-r2fy3JIlgkFZUJJgkaQAXSnJu0Q=" + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-4.2.0.tgz", + "integrity": "sha1-De4/7TH81GlhjOc0IJn8GvoL2xM=" }, "esutils": { "version": "2.0.2", @@ -1326,18 +1429,18 @@ "integrity": "sha1-L9w1dvIykDNYl26znaeDIT/5Uj8=" }, "ethereumjs-tx": { - "version": "1.3.4", - "resolved": "https://registry.npmjs.org/ethereumjs-tx/-/ethereumjs-tx-1.3.4.tgz", - "integrity": "sha512-kOgUd5jC+0tgV7t52UDECMMz9Uf+Lro+6fSpCvzWemtXfMEcwI3EOxf5mVPMRbTFkMMhuERokNNVF3jItAjidg==", + "version": "1.3.7", + "resolved": "https://registry.npmjs.org/ethereumjs-tx/-/ethereumjs-tx-1.3.7.tgz", + "integrity": "sha512-wvLMxzt1RPhAQ9Yi3/HKZTn0FZYpnsmQdbKYfUUpi4j1SEIcbkd9tndVjcPrufY3V7j2IebOpC00Zp2P/Ay2kA==", "requires": { "ethereum-common": "^0.0.18", "ethereumjs-util": "^5.0.0" } }, "ethereumjs-util": { - "version": "5.1.5", - "resolved": "https://registry.npmjs.org/ethereumjs-util/-/ethereumjs-util-5.1.5.tgz", - "integrity": "sha512-xPaSEATYJpMTCGowIt0oMZwFP4R1bxd6QsWgkcDvFL0JtXsr39p32WEcD14RscCjfP41YXZPCVWA4yAg0nrJmw==", + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/ethereumjs-util/-/ethereumjs-util-5.2.0.tgz", + "integrity": "sha512-CJAKdI0wgMbQFLlLRtZKGcy/L6pzVRgelIZqRqNbuVFM3K9VEnyfbcvz0ncWMRNCe4kaHWjwRYQcYMucmwsnWA==", "requires": { "bn.js": "^4.11.0", "create-hash": "^1.1.2", @@ -1365,9 +1468,9 @@ } }, "ethjs-util": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/ethjs-util/-/ethjs-util-0.1.4.tgz", - "integrity": "sha1-HItoeSV0RO9NPz+7rC3tEs2ZfZM=", + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/ethjs-util/-/ethjs-util-0.1.6.tgz", + "integrity": "sha512-CUnVOQq7gSpDHZVVrQW8ExxUETWrnrvXYvYz55wOU8Uj4VCgw56XC2B/fVqQN+f7gmrnRHSLVnFAwsCuNwji8w==", "requires": { "is-hex-prefixed": "1.0.0", "strip-hex-prefix": "1.0.0" @@ -1387,21 +1490,53 @@ "safe-buffer": "^5.1.1" } }, - "expand-template": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/expand-template/-/expand-template-1.0.3.tgz", - "integrity": "sha1-bDAzIxd6YrGyLAcCefeGEoe2mxo=" - }, - "express": { - "version": "4.16.3", - "resolved": "https://registry.npmjs.org/express/-/express-4.16.3.tgz", - "integrity": "sha1-avilAjUNsyRuzEvs9rWjTSL37VM=", + "expand-brackets": { + "version": "2.1.4", + "resolved": "https://registry.npmjs.org/expand-brackets/-/expand-brackets-2.1.4.tgz", + "integrity": "sha1-t3c14xXOMPa27/D4OwQVGiJEliI=", "requires": { - "accepts": "~1.3.5", - "array-flatten": "1.1.1", - "body-parser": "1.18.2", - "content-disposition": "0.5.2", - "content-type": "~1.0.4", + "debug": "^2.3.3", + "define-property": "^0.2.5", + "extend-shallow": "^2.0.1", + "posix-character-classes": "^0.1.0", + "regex-not": "^1.0.0", + "snapdragon": "^0.8.1", + "to-regex": "^3.0.1" + }, + "dependencies": { + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "requires": { + "is-descriptor": "^0.1.0" + } + }, + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "requires": { + "is-extendable": "^0.1.0" + } + } + } + }, + "expand-template": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/expand-template/-/expand-template-1.1.1.tgz", + "integrity": "sha512-cebqLtV8KOZfw0UI8TEFWxtczxxC1jvyUvx6H4fyp1K1FN7A4Q+uggVUlOsI1K8AGU0rwOGqP8nCapdrw8CYQg==" + }, + "express": { + "version": "4.16.4", + "resolved": "https://registry.npmjs.org/express/-/express-4.16.4.tgz", + "integrity": "sha512-j12Uuyb4FMrd/qQAm6uCHAkPtO8FDTRJZBDd5D2KOL2eLaz1yUNdUB/NOIyq0iU4q4cFarsUCrnFDPBcnksuOg==", + "requires": { + "accepts": "~1.3.5", + "array-flatten": "1.1.1", + "body-parser": "1.18.3", + "content-disposition": "0.5.2", + "content-type": "~1.0.4", "cookie": "0.3.1", "cookie-signature": "1.0.6", "debug": "2.6.9", @@ -1416,10 +1551,10 @@ "on-finished": "~2.3.0", "parseurl": "~1.3.2", "path-to-regexp": "0.1.7", - "proxy-addr": "~2.0.3", - "qs": "6.5.1", + "proxy-addr": "~2.0.4", + "qs": "6.5.2", "range-parser": "~1.2.0", - "safe-buffer": "5.1.1", + "safe-buffer": "5.1.2", "send": "0.16.2", "serve-static": "1.13.2", "setprototypeof": "1.1.0", @@ -1429,11 +1564,6 @@ "vary": "~1.1.2" }, "dependencies": { - "setprototypeof": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.1.0.tgz", - "integrity": "sha512-BvE/TwpZX4FXExxOxZyRGQQv651MSwmWKZGqvmPcRIjDqWub67kTKuIMx43cZZrS/cBBzwBcNDWoFxt2XEFIpQ==" - }, "statuses": { "version": "1.4.0", "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.4.0.tgz", @@ -1442,9 +1572,28 @@ } }, "extend": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.1.tgz", - "integrity": "sha1-p1Xqe8Gt/MWjHOfnYtuq3F5jZEQ=" + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz", + "integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==" + }, + "extend-shallow": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-3.0.2.tgz", + "integrity": "sha1-Jqcarwc7OfshJxcnRhMcJwQCjbg=", + "requires": { + "assign-symbols": "^1.0.0", + "is-extendable": "^1.0.1" + }, + "dependencies": { + "is-extendable": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-1.0.1.tgz", + "integrity": "sha512-arnXMxT1hhoKo9k1LZdmlNyJdDDfy2v0fXjFlmok4+i8ul/6WlbVge9bhM74OpNPQPMGUToDtz+KXa1PneJxOA==", + "requires": { + "is-plain-object": "^2.0.4" + } + } + } }, "external-editor": { "version": "3.0.3", @@ -1468,22 +1617,94 @@ } } }, + "extglob": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/extglob/-/extglob-2.0.4.tgz", + "integrity": "sha512-Nmb6QXkELsuBr24CJSkilo6UHHgbekK5UiZgfE6UHD3Eb27YC6oD+bhcT+tJ6cl8dmsgdQxnWlcry8ksBIBLpw==", + "requires": { + "array-unique": "^0.3.2", + "define-property": "^1.0.0", + "expand-brackets": "^2.1.4", + "extend-shallow": "^2.0.1", + "fragment-cache": "^0.2.1", + "regex-not": "^1.0.0", + "snapdragon": "^0.8.1", + "to-regex": "^3.0.1" + }, + "dependencies": { + "define-property": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-1.0.0.tgz", + "integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=", + "requires": { + "is-descriptor": "^1.0.0" + } + }, + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "requires": { + "is-extendable": "^0.1.0" + } + }, + "is-accessor-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz", + "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-data-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz", + "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-descriptor": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz", + "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", + "requires": { + "is-accessor-descriptor": "^1.0.0", + "is-data-descriptor": "^1.0.0", + "kind-of": "^6.0.2" + } + } + } + }, "extsprintf": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/extsprintf/-/extsprintf-1.3.0.tgz", "integrity": "sha1-lpGEQOMEGnpBT4xS48V06zw+HgU=" }, "fast-deep-equal": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-1.1.0.tgz", - "integrity": "sha1-wFNHeBfIa1HaqFPIHgWbcz0CNhQ=" + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-2.0.1.tgz", + "integrity": "sha1-ewUhjd+WZ79/Nwv3/bLLFf3Qqkk=" }, "fast-diff": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/fast-diff/-/fast-diff-1.1.2.tgz", - "integrity": "sha512-KaJUt+M9t1qaIteSvjc6P3RbMdXsNhK61GRftR6SNxqmhthcd9MGIi4T+o0jD8LUSpSnSKXE20nLtJ3fOHxQig==", + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/fast-diff/-/fast-diff-1.2.0.tgz", + "integrity": "sha512-xJuoT5+L99XlZ8twedaRf6Ax2TgQVxvgZOYoPKqZufmJib0tL2tegPBOZb1pVNgIhlqDlA0eO0c3wBvQcmzx4w==", "dev": true }, + "fast-glob": { + "version": "2.2.6", + "resolved": "https://registry.npmjs.org/fast-glob/-/fast-glob-2.2.6.tgz", + "integrity": "sha512-0BvMaZc1k9F+MeWWMe8pL6YltFzZYcJsYU7D4JyDA6PAczaXvxqQQ/z+mDF7/4Mw01DeUc+i3CTKajnkANkV4w==", + "requires": { + "@mrmlnc/readdir-enhanced": "^2.2.1", + "@nodelib/fs.stat": "^1.1.2", + "glob-parent": "^3.1.0", + "is-glob": "^4.0.0", + "merge2": "^1.2.3", + "micromatch": "^3.1.10" + } + }, "fast-json-stable-stringify": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.0.0.tgz", @@ -1495,9 +1716,9 @@ "integrity": "sha1-PYpcZog6FqMMqGQ+hR8Zuqd5eRc=" }, "fd-slicer": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/fd-slicer/-/fd-slicer-1.0.1.tgz", - "integrity": "sha1-i1vL2ewyfFBBv5qwI/1nUPEXfmU=", + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/fd-slicer/-/fd-slicer-1.1.0.tgz", + "integrity": "sha1-JcfInLH5B3+IkbvmHY85Dq4lbx4=", "requires": { "pend": "~1.2.0" } @@ -1512,13 +1733,12 @@ } }, "file-entry-cache": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/file-entry-cache/-/file-entry-cache-2.0.0.tgz", - "integrity": "sha1-w5KZDD5oR4PYOLjISkXYoEhFg2E=", + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/file-entry-cache/-/file-entry-cache-5.0.1.tgz", + "integrity": "sha512-bCg29ictuBaKUwwArK4ouCaqDgLZcysCFLmM/Yn/FDoqndh/9vNuQfXRDvTuXKLxfD/JtZQGKFT8MGcJBK644g==", "dev": true, "requires": { - "flat-cache": "^1.2.1", - "object-assign": "^4.0.1" + "flat-cache": "^2.0.1" } }, "file-type": { @@ -1526,6 +1746,32 @@ "resolved": "https://registry.npmjs.org/file-type/-/file-type-5.2.0.tgz", "integrity": "sha1-LdvqfHP/42No365J3DOMBYwritY=" }, + "file-uri-to-path": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/file-uri-to-path/-/file-uri-to-path-1.0.0.tgz", + "integrity": "sha512-0Zt+s3L7Vf1biwWZ29aARiVYLx7iMGnEUl9x33fbB/j3jR81u/O2LbqK+Bm1CDSNDKVtJ/YjwY7TUd5SkeLQLw==" + }, + "fill-range": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-4.0.0.tgz", + "integrity": "sha1-1USBHUKPmOsGpj3EAtJAPDKMOPc=", + "requires": { + "extend-shallow": "^2.0.1", + "is-number": "^3.0.0", + "repeat-string": "^1.6.1", + "to-regex-range": "^2.1.0" + }, + "dependencies": { + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "requires": { + "is-extendable": "^0.1.0" + } + } + } + }, "finalhandler": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/finalhandler/-/finalhandler-1.1.1.tgz", @@ -1548,47 +1794,56 @@ } }, "find-up": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-1.1.2.tgz", - "integrity": "sha1-ay6YIrGizgpgq2TWEOzK1TyyTQ8=", + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", + "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", "dev": true, "requires": { - "path-exists": "^2.0.0", - "pinkie-promise": "^2.0.0" + "locate-path": "^2.0.0" } }, "flat-cache": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/flat-cache/-/flat-cache-1.3.0.tgz", - "integrity": "sha1-0wMLMrOBVPTjt+nHCfSQ9++XxIE=", + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/flat-cache/-/flat-cache-2.0.1.tgz", + "integrity": "sha512-LoQe6yDuUMDzQAEH8sgmh4Md6oZnc/7PjtwjNFSzveXqSHt6ka9fPBuso7IGf9Rz4uqnSnWiFH2B/zj24a5ReA==", "dev": true, "requires": { - "circular-json": "^0.3.1", - "del": "^2.0.2", - "graceful-fs": "^4.1.2", - "write": "^0.2.1" + "flatted": "^2.0.0", + "rimraf": "2.6.3", + "write": "1.0.3" } }, + "flatted": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/flatted/-/flatted-2.0.0.tgz", + "integrity": "sha512-R+H8IZclI8AAkSBRQJLVOsxwAoHd6WC40b4QTNWIjzAa6BXOBfQcM587MXDTVPeYaopFNWHUFLx7eNmHDSxMWg==", + "dev": true + }, "for-each": { - "version": "0.3.2", - "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.2.tgz", - "integrity": "sha1-LEBFC5NI6X8oEyJZO6lnBLmr1NQ=", + "version": "0.3.3", + "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.3.tgz", + "integrity": "sha512-jqYfLp7mo9vIyQf8ykW2v7A+2N4QjeCeI5+Dz9XraiO1ign81wjiH7Fb9vSOWvQfNtmSa4H2RoQTrrXivdUZmw==", "requires": { - "is-function": "~1.0.0" + "is-callable": "^1.1.3" } }, + "for-in": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/for-in/-/for-in-1.0.2.tgz", + "integrity": "sha1-gQaNKVqBQuwKxybG4iAMMPttXoA=" + }, "forever-agent": { "version": "0.6.1", "resolved": "https://registry.npmjs.org/forever-agent/-/forever-agent-0.6.1.tgz", "integrity": "sha1-+8cfDEGt6zf5bFd60e1C2P2sypE=" }, "form-data": { - "version": "2.3.2", - "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.3.2.tgz", - "integrity": "sha1-SXBJi+YEwgwAXU9cI67NIda0kJk=", + "version": "2.3.3", + "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.3.3.tgz", + "integrity": "sha512-1lLKB2Mu3aGP1Q/2eCOx0fNbRMe7XdwktwOruhfqqd0rIJWwN4Dh+E3hrPSlDCXnSR7UtZ1N38rVXm+6+MEhJQ==", "requires": { "asynckit": "^0.4.0", - "combined-stream": "1.0.6", + "combined-stream": "^1.0.6", "mime-types": "^2.1.12" } }, @@ -1597,18 +1852,41 @@ "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.1.2.tgz", "integrity": "sha1-mMI9qxF1ZXuMBXPozszZGw/xjIQ=" }, + "fragment-cache": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/fragment-cache/-/fragment-cache-0.2.1.tgz", + "integrity": "sha1-QpD60n8T6Jvn8zeZxrxaCr//DRk=", + "requires": { + "map-cache": "^0.2.2" + } + }, "fresh": { "version": "0.5.2", "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.5.2.tgz", "integrity": "sha1-PYyt2Q2XZWn6g1qx+OSyOhBWBac=" }, + "from2": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/from2/-/from2-2.3.0.tgz", + "integrity": "sha1-i/tVAr3kpNNs/e6gB/zKIdfjgq8=", + "requires": { + "inherits": "^2.0.1", + "readable-stream": "^2.0.0" + } + }, + "fs-constants": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/fs-constants/-/fs-constants-1.0.0.tgz", + "integrity": "sha512-y6OAwoSIf7FyjMIv94u+b5rdheZEjzR63GTyZJm5qh4Bi+2YgwLCcI/fPFZkL5PSixOt6ZNKm+w+Hfp/Bciwow==" + }, "fs-extra": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-2.1.2.tgz", - "integrity": "sha1-BGxwFjzvmq1GsOSn+kZ/si1x3jU=", + "version": "7.0.1", + "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-7.0.1.tgz", + "integrity": "sha512-YJDaCJZEnBmcbw13fvdAM9AwNOJwOzrE4pqMqBq5nFiEqXUqHwlK4B+3pUw6JNvfSPtX05xFHtYy/1ni01eGCw==", "requires": { "graceful-fs": "^4.1.2", - "jsonfile": "^2.1.0" + "jsonfile": "^4.0.0", + "universalify": "^0.1.0" } }, "fs-promise": { @@ -1620,6 +1898,25 @@ "fs-extra": "^2.0.0", "mz": "^2.6.0", "thenify-all": "^1.6.0" + }, + "dependencies": { + "fs-extra": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-2.1.2.tgz", + "integrity": "sha1-BGxwFjzvmq1GsOSn+kZ/si1x3jU=", + "requires": { + "graceful-fs": "^4.1.2", + "jsonfile": "^2.1.0" + } + }, + "jsonfile": { + "version": "2.4.0", + "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-2.4.0.tgz", + "integrity": "sha1-NzaitCi4e72gzIO1P6PWM6NcKug=", + "requires": { + "graceful-fs": "^4.1.6" + } + } } }, "fs.realpath": { @@ -1661,6 +1958,11 @@ "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-3.0.0.tgz", "integrity": "sha1-jpQ9E1jcN1VQVOy+LtsFqhdO3hQ=" }, + "get-value": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/get-value/-/get-value-2.0.6.tgz", + "integrity": "sha1-3BXKHGcjh8p2vTesCjlbogQqLCg=" + }, "getpass": { "version": "0.1.7", "resolved": "https://registry.npmjs.org/getpass/-/getpass-0.1.7.tgz", @@ -1670,9 +1972,9 @@ } }, "glob": { - "version": "7.1.2", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz", - "integrity": "sha512-MJTUg1kjuLeQCJ+ccE4Vpa6kKVXkPYJ2mOCQyUuKLcLQsdrMCpBPUi8qVE6+YuaJkozeA9NusTAw3hLr8Xe5EQ==", + "version": "7.1.3", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.3.tgz", + "integrity": "sha512-vcfuiIxogLV4DlGBHIUOwI0IbrJ8HWPc4MU7HzviGeNho/UJDfi6B5p3sHeWIQ0KGIU0Jpxi5ZHxemQfLkkAwQ==", "requires": { "fs.realpath": "^1.0.0", "inflight": "^1.0.4", @@ -1682,6 +1984,30 @@ "path-is-absolute": "^1.0.0" } }, + "glob-parent": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-3.1.0.tgz", + "integrity": "sha1-nmr2KZ2NO9K9QEMIMr0RPfkGxa4=", + "requires": { + "is-glob": "^3.1.0", + "path-dirname": "^1.0.0" + }, + "dependencies": { + "is-glob": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-3.1.0.tgz", + "integrity": "sha1-e6WuJCF4BKxwcHuWkiVnSGzD6Eo=", + "requires": { + "is-extglob": "^2.1.0" + } + } + } + }, + "glob-to-regexp": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/glob-to-regexp/-/glob-to-regexp-0.3.0.tgz", + "integrity": "sha1-jFoUlNIGbFcMw7/kSWF1rMTVAqs=" + }, "global": { "version": "4.3.2", "resolved": "https://registry.npmjs.org/global/-/global-4.3.2.tgz", @@ -1692,21 +2018,23 @@ } }, "globals": { - "version": "11.7.0", - "resolved": "https://registry.npmjs.org/globals/-/globals-11.7.0.tgz", - "integrity": "sha512-K8BNSPySfeShBQXsahYB/AbbWruVOTyVpgoIDnl8odPpeSfP2J5QO2oLFFdl2j7GfDCtZj2bMKar2T49itTPCg==", + "version": "11.11.0", + "resolved": "https://registry.npmjs.org/globals/-/globals-11.11.0.tgz", + "integrity": "sha512-WHq43gS+6ufNOEqlrDBxVEbb8ntfXrfAUU2ZOpCxrBdGKW3gyv8mCxAfIBD0DroPKGrJ2eSsXsLtY9MPntsyTw==", "dev": true }, "globby": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/globby/-/globby-6.1.0.tgz", - "integrity": "sha1-9abXDoOV4hyFj7BInWTfAkJNUGw=", + "version": "8.0.2", + "resolved": "https://registry.npmjs.org/globby/-/globby-8.0.2.tgz", + "integrity": "sha512-yTzMmKygLp8RUpG1Ymu2VXPSJQZjNAZPD4ywgYEaG7e4tBJeUQBO8OpXrf1RCNcEs5alsoJYPAMiIHP0cmeC7w==", "requires": { "array-union": "^1.0.1", - "glob": "^7.0.3", - "object-assign": "^4.0.1", - "pify": "^2.0.0", - "pinkie-promise": "^2.0.0" + "dir-glob": "2.0.0", + "fast-glob": "^2.0.2", + "glob": "^7.1.2", + "ignore": "^3.3.5", + "pify": "^3.0.0", + "slash": "^1.0.0" } }, "got": { @@ -1731,9 +2059,9 @@ } }, "graceful-fs": { - "version": "4.1.11", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.11.tgz", - "integrity": "sha1-Dovf5NHduIVNZOBOp8AOKgJuVlg=" + "version": "4.1.15", + "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.15.tgz", + "integrity": "sha512-6uHUhOPEBgQ24HM+r6b/QwWfZq+yiFcipKFrOFiBEnWdy5sdzYoi+pJeQaPI5qOLRFqWmAXUPQNsielzdLoecA==" }, "graceful-readlink": { "version": "1.0.1", @@ -1746,11 +2074,11 @@ "integrity": "sha1-qUwiJOvKwEeCoNkDVSHyRzW37JI=" }, "har-validator": { - "version": "5.0.3", - "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-5.0.3.tgz", - "integrity": "sha1-ukAsJmGU8VlW7xXg/PJCmT9qff0=", + "version": "5.1.3", + "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-5.1.3.tgz", + "integrity": "sha512-sNvOCzEQNr/qrvJgc3UG/kD4QtlHycrzwS+6mfTrrSq97BvaYcPZZI1ZSqGSPR73Cxn4LKTD4PttRwfU7jWq5g==", "requires": { - "ajv": "^5.1.0", + "ajv": "^6.5.5", "har-schema": "^2.0.0" } }, @@ -1764,9 +2092,9 @@ } }, "has-flag": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-2.0.0.tgz", - "integrity": "sha1-6CB68cx7MNRGzHC3NLXovhj4jVE=" + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", + "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=" }, "has-symbol-support-x": { "version": "1.4.2", @@ -1787,32 +2115,51 @@ "has-symbol-support-x": "^1.4.1" } }, - "hash-base": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/hash-base/-/hash-base-2.0.2.tgz", - "integrity": "sha1-ZuodhW206KVHDK32/OI65SRO8uE=", + "has-value": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/has-value/-/has-value-1.0.0.tgz", + "integrity": "sha1-GLKB2lhbHFxR3vJMkw7SmgvmsXc=", "requires": { - "inherits": "^2.0.1" + "get-value": "^2.0.6", + "has-values": "^1.0.0", + "isobject": "^3.0.0" } }, - "hash.js": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/hash.js/-/hash.js-1.1.3.tgz", - "integrity": "sha512-/UETyP0W22QILqS+6HowevwhEFJ3MBJnwTf75Qob9Wz9t0DPuisL8kW8YZMK62dHAKE1c1p+gY1TtOLY+USEHA==", + "has-values": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/has-values/-/has-values-1.0.0.tgz", + "integrity": "sha1-lbC2P+whRmGab+V/51Yo1aOe/k8=", "requires": { - "inherits": "^2.0.3", - "minimalistic-assert": "^1.0.0" + "is-number": "^3.0.0", + "kind-of": "^4.0.0" + }, + "dependencies": { + "kind-of": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-4.0.0.tgz", + "integrity": "sha1-IIE989cSkosgc3hpGkUGb65y3Vc=", + "requires": { + "is-buffer": "^1.1.5" + } + } } }, - "hawk": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/hawk/-/hawk-6.0.2.tgz", - "integrity": "sha512-miowhl2+U7Qle4vdLqDdPt9m09K6yZhkLDTWGoUiUzrQCn+mHHSmfJgAyGaLRZbPmTqfFFjRV1QWCW0VWUJBbQ==", + "hash-base": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/hash-base/-/hash-base-3.0.4.tgz", + "integrity": "sha1-X8hoaEfs1zSZQDMZprCj8/auSRg=", "requires": { - "boom": "4.x.x", - "cryptiles": "3.x.x", - "hoek": "4.x.x", - "sntp": "2.x.x" + "inherits": "^2.0.1", + "safe-buffer": "^5.0.1" + } + }, + "hash.js": { + "version": "1.1.7", + "resolved": "https://registry.npmjs.org/hash.js/-/hash.js-1.1.7.tgz", + "integrity": "sha512-taOaskGt4z4SOANNseOviYDvjEJinIkRgmp7LbKP2YTTmVxWBl87s/uzK9r+44BclBSp2X7K1hqeNfz9JbBeXA==", + "requires": { + "inherits": "^2.0.3", + "minimalistic-assert": "^1.0.1" } }, "hmac-drbg": { @@ -1825,11 +2172,6 @@ "minimalistic-crypto-utils": "^1.0.1" } }, - "hoek": { - "version": "4.2.1", - "resolved": "https://registry.npmjs.org/hoek/-/hoek-4.2.1.tgz", - "integrity": "sha512-QLg82fGkfnJ/4iy1xZ81/9SIJiq1NGFUMGs6ParyjBZr6jW2Ufj/snDqTHixNlHdPNwN2RLVD0Pi3igeK9+JfA==" - }, "hosted-git-info": { "version": "2.7.1", "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-2.7.1.tgz", @@ -1837,21 +2179,14 @@ "dev": true }, "http-errors": { - "version": "1.6.2", - "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.6.2.tgz", - "integrity": "sha1-CgAsyFcHGSp+eUbO7cERVfYOxzY=", + "version": "1.6.3", + "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.6.3.tgz", + "integrity": "sha1-i1VoC7S+KDoLW/TqLjhYC+HZMg0=", "requires": { - "depd": "1.1.1", + "depd": "~1.1.2", "inherits": "2.0.3", - "setprototypeof": "1.0.3", - "statuses": ">= 1.3.1 < 2" - }, - "dependencies": { - "depd": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/depd/-/depd-1.1.1.tgz", - "integrity": "sha1-V4O04cRZ8G+lyif5kfPQbnoxA1k=" - } + "setprototypeof": "1.1.0", + "statuses": ">= 1.4.0 < 2" } }, "http-https": { @@ -1870,20 +2205,32 @@ } }, "iconv-lite": { - "version": "0.4.19", - "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.19.tgz", - "integrity": "sha512-oTZqweIP51xaGPI4uPa56/Pri/480R+mo7SeU+YETByQNhDG55ycFyNLIgta9vXhILrxXDmF7ZGhqZIcuN0gJQ==" + "version": "0.4.23", + "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.23.tgz", + "integrity": "sha512-neyTUVFtahjf0mB3dZT77u+8O0QB89jFdnBkd5P1JgYPbPaia3gXXOVL2fq8VyU2gMMD7SaN7QukTB/pmXYvDA==", + "requires": { + "safer-buffer": ">= 2.1.2 < 3" + } }, "ieee754": { - "version": "1.1.11", - "resolved": "https://registry.npmjs.org/ieee754/-/ieee754-1.1.11.tgz", - "integrity": "sha512-VhDzCKN7K8ufStx/CLj5/PDTMgph+qwN5Pkd5i0sGnVwk56zJ0lkT8Qzi1xqWLS0Wp29DgDtNeS7v8/wMoZeHg==" + "version": "1.1.12", + "resolved": "https://registry.npmjs.org/ieee754/-/ieee754-1.1.12.tgz", + "integrity": "sha512-GguP+DRY+pJ3soyIiGPTvdiVXjZ+DbXOxGpXn3eMvNW4x4irjqXm4wHKscC+TfxSJ0yw/S1F24tqdMNsMZTiLA==" }, "ignore": { - "version": "4.0.6", - "resolved": "https://registry.npmjs.org/ignore/-/ignore-4.0.6.tgz", - "integrity": "sha512-cyFDKrqc/YdcWFniJhzI42+AzS+gNwmUzOSFcRCQYwySuBBBy/KjuxWLZ/FHEH6Moq1NizMOBWyTcv8O4OZIMg==", - "dev": true + "version": "3.3.10", + "resolved": "https://registry.npmjs.org/ignore/-/ignore-3.3.10.tgz", + "integrity": "sha512-Pgs951kaMm5GXP7MOvxERINe3gsaVjUWFm+UZPSq9xYriQAksyhg0csnS0KXSNRD5NmNdapXEpjxG49+AKh/ug==" + }, + "import-fresh": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/import-fresh/-/import-fresh-3.0.0.tgz", + "integrity": "sha512-pOnA9tfM3Uwics+SaBLCNyZZZbK+4PTu0OPZtLlMIrv17EdBoC15S9Kn8ckJ9TZTyKb3ywNE5y1yeDxxGA7nTQ==", + "dev": true, + "requires": { + "parent-module": "^1.0.0", + "resolve-from": "^4.0.0" + } }, "imurmurhash": { "version": "0.1.4", @@ -1911,30 +2258,74 @@ "integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=" }, "inquirer": { - "version": "6.2.0", - "resolved": "https://registry.npmjs.org/inquirer/-/inquirer-6.2.0.tgz", - "integrity": "sha512-QIEQG4YyQ2UYZGDC4srMZ7BjHOmNk1lR2JQj5UknBapklm6WHA+VVH7N+sUdX3A7NeCfGF8o4X1S3Ao7nAcIeg==", + "version": "6.2.2", + "resolved": "https://registry.npmjs.org/inquirer/-/inquirer-6.2.2.tgz", + "integrity": "sha512-Z2rREiXA6cHRR9KBOarR3WuLlFzlIfAEIiB45ll5SSadMg7WqOh1MKEjjndfuH5ewXdixWCxqnVfGOQzPeiztA==", "dev": true, "requires": { - "ansi-escapes": "^3.0.0", - "chalk": "^2.0.0", + "ansi-escapes": "^3.2.0", + "chalk": "^2.4.2", "cli-cursor": "^2.1.0", "cli-width": "^2.0.0", - "external-editor": "^3.0.0", + "external-editor": "^3.0.3", "figures": "^2.0.0", - "lodash": "^4.17.10", + "lodash": "^4.17.11", "mute-stream": "0.0.7", "run-async": "^2.2.0", - "rxjs": "^6.1.0", + "rxjs": "^6.4.0", "string-width": "^2.1.0", - "strip-ansi": "^4.0.0", + "strip-ansi": "^5.0.0", "through": "^2.3.6" + }, + "dependencies": { + "ansi-regex": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-4.0.0.tgz", + "integrity": "sha512-iB5Dda8t/UqpPI/IjsejXu5jOGDrzn41wJyljwPH65VCIbk6+1BzFIMJGFwTNrYXT1CrD+B4l19U7awiQ8rk7w==", + "dev": true + }, + "strip-ansi": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-5.0.0.tgz", + "integrity": "sha512-Uu7gQyZI7J7gn5qLn1Np3G9vcYGTVqB+lFTytnDJv83dd8T22aGH451P3jueT2/QemInJDfxHB5Tde5OzgG1Ow==", + "dev": true, + "requires": { + "ansi-regex": "^4.0.0" + } + } + } + }, + "into-stream": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/into-stream/-/into-stream-4.0.0.tgz", + "integrity": "sha512-i29KNyE5r0Y/UQzcQ0IbZO1MYJ53Jn0EcFRZPj5FzWKYH17kDFEOwuA+3jroymOI06SW1dEDnly9A1CAreC5dg==", + "requires": { + "from2": "^2.1.1", + "p-is-promise": "^2.0.0" } }, "ipaddr.js": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.6.0.tgz", - "integrity": "sha1-4/o1e3c9phnybpXwSdBVxyeW+Gs=" + "version": "1.8.0", + "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.8.0.tgz", + "integrity": "sha1-6qM9bd16zo9/b+DJygRA5wZzix4=" + }, + "is-accessor-descriptor": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-0.1.6.tgz", + "integrity": "sha1-qeEss66Nh2cn7u84Q/igiXtcmNY=", + "requires": { + "kind-of": "^3.0.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "requires": { + "is-buffer": "^1.1.5" + } + } + } }, "is-arrayish": { "version": "0.2.1", @@ -1942,20 +2333,33 @@ "integrity": "sha1-d8mYQFJ6qOyxqLppe4BkWnqSap0=", "dev": true }, - "is-builtin-module": { - "version": "1.0.0", - "resolved": "http://registry.npmjs.org/is-builtin-module/-/is-builtin-module-1.0.0.tgz", - "integrity": "sha1-VAVy0096wxGfj3bDDLwbHgN6/74=", - "dev": true, - "requires": { - "builtin-modules": "^1.0.0" - } + "is-buffer": { + "version": "1.1.6", + "resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-1.1.6.tgz", + "integrity": "sha512-NcdALwpXkTm5Zvvbk7owOUSvVvBKDgKP5/ewfXEznmQFfs4ZRmanOeKBTjRVjka3QFoN6XJ+9F3USqfHqTaU5w==" }, "is-callable": { "version": "1.1.4", "resolved": "https://registry.npmjs.org/is-callable/-/is-callable-1.1.4.tgz", - "integrity": "sha512-r5p9sxJjYnArLjObpjA4xu5EKI3CuKHkJXMhT7kwbpUyIFD1n5PMAsoPvWnvtZiNz7LjkYDRZhd7FlI0eMijEA==", - "dev": true + "integrity": "sha512-r5p9sxJjYnArLjObpjA4xu5EKI3CuKHkJXMhT7kwbpUyIFD1n5PMAsoPvWnvtZiNz7LjkYDRZhd7FlI0eMijEA==" + }, + "is-data-descriptor": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-0.1.4.tgz", + "integrity": "sha1-C17mSDiOLIYCgueT8YVv7D8wG1Y=", + "requires": { + "kind-of": "^3.0.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "requires": { + "is-buffer": "^1.1.5" + } + } + } }, "is-date-object": { "version": "1.0.1", @@ -1963,6 +2367,33 @@ "integrity": "sha1-mqIOtq7rv/d/vTPnTKAbM1gdOhY=", "dev": true }, + "is-descriptor": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-0.1.6.tgz", + "integrity": "sha512-avDYr0SB3DwO9zsMov0gKCESFYqCnE4hq/4z3TdUlukEy5t9C0YRq7HLrsN52NAcqXKaepeCD0n+B0arnVG3Hg==", + "requires": { + "is-accessor-descriptor": "^0.1.6", + "is-data-descriptor": "^0.1.4", + "kind-of": "^5.0.0" + }, + "dependencies": { + "kind-of": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-5.1.0.tgz", + "integrity": "sha512-NGEErnH6F2vUuXDh+OlbcKW7/wOcfdRHaZ7VWtqCztfHri/++YKmP51OdWeGPuqCOba6kk2OTe5d02VmTB80Pw==" + } + } + }, + "is-extendable": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-0.1.1.tgz", + "integrity": "sha1-YrEQ4omkcUGOPsNqYX1HLjAd/Ik=" + }, + "is-extglob": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", + "integrity": "sha1-qIwCU1eR8C7TfHahueqXc8gz+MI=" + }, "is-fullwidth-code-point": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", @@ -1974,6 +2405,14 @@ "resolved": "https://registry.npmjs.org/is-function/-/is-function-1.0.1.tgz", "integrity": "sha1-Es+5i2W1fdPRk6MSH19uL0N2ArU=" }, + "is-glob": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.0.tgz", + "integrity": "sha1-lSHHaEXMJhCoUgPd8ICpWML/q8A=", + "requires": { + "is-extglob": "^2.1.1" + } + }, "is-hex-prefixed": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/is-hex-prefixed/-/is-hex-prefixed-1.0.0.tgz", @@ -1984,40 +2423,42 @@ "resolved": "https://registry.npmjs.org/is-natural-number/-/is-natural-number-4.0.1.tgz", "integrity": "sha1-q5124dtM7VHjXeDHLr7PCfc0zeg=" }, - "is-object": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-object/-/is-object-1.0.1.tgz", - "integrity": "sha1-iVJojF7C/9awPsyF52ngKQMINHA=" - }, - "is-path-cwd": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-path-cwd/-/is-path-cwd-1.0.0.tgz", - "integrity": "sha1-0iXsIxMuie3Tj9p2dHLmLmXxEG0=", - "dev": true - }, - "is-path-in-cwd": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-path-in-cwd/-/is-path-in-cwd-1.0.1.tgz", - "integrity": "sha512-FjV1RTW48E7CWM7eE/J2NJvAEEVektecDBVBE5Hh3nM1Jd0kvhHtX68Pr3xsDf857xt3Y4AkwVULK1Vku62aaQ==", - "dev": true, + "is-number": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/is-number/-/is-number-3.0.0.tgz", + "integrity": "sha1-JP1iAaR4LPUFYcgQJ2r8fRLXEZU=", "requires": { - "is-path-inside": "^1.0.0" + "kind-of": "^3.0.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "requires": { + "is-buffer": "^1.1.5" + } + } } }, - "is-path-inside": { + "is-object": { "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-path-inside/-/is-path-inside-1.0.1.tgz", - "integrity": "sha1-jvW33lBDej/cprToZe96pVy0gDY=", - "dev": true, - "requires": { - "path-is-inside": "^1.0.1" - } + "resolved": "https://registry.npmjs.org/is-object/-/is-object-1.0.1.tgz", + "integrity": "sha1-iVJojF7C/9awPsyF52ngKQMINHA=" }, "is-plain-obj": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-1.1.0.tgz", "integrity": "sha1-caUMhCnfync8kqOQpKA7OfzVHT4=" }, + "is-plain-object": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/is-plain-object/-/is-plain-object-2.0.4.tgz", + "integrity": "sha512-h5PpgXkWitc38BBMYawTYMWJHFZJVnBquFE57xFpjB8pJFiF6gZ+bU+WyI/yqXiFR5mdLsgYNaPe8uao6Uv9Og==", + "requires": { + "isobject": "^3.0.1" + } + }, "is-promise": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/is-promise/-/is-promise-2.1.0.tgz", @@ -2033,12 +2474,6 @@ "has": "^1.0.1" } }, - "is-resolvable": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/is-resolvable/-/is-resolvable-1.1.0.tgz", - "integrity": "sha512-qgDYXFSR5WvEfuS5dMj6oTMEbrrSaM0CrFk2Yiq/gXnBvD9pMa2jGXxyhGLfvhZpuMZe18CJpFxAt3CRs42NMg==", - "dev": true - }, "is-retry-allowed": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/is-retry-allowed/-/is-retry-allowed-1.1.0.tgz", @@ -2050,16 +2485,24 @@ "integrity": "sha1-EtSj3U5o4Lec6428hBc66A2RykQ=" }, "is-symbol": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-symbol/-/is-symbol-1.0.1.tgz", - "integrity": "sha1-PMWfAAJRlLarLjjbrmaJJWtmBXI=", - "dev": true + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-symbol/-/is-symbol-1.0.2.tgz", + "integrity": "sha512-HS8bZ9ox60yCJLH9snBpIwv9pYUAkcuLhSA1oero1UB5y9aiQpRA8y2ex945AOtCZL1lJDeIk3G5LthswI46Lw==", + "dev": true, + "requires": { + "has-symbols": "^1.0.0" + } }, "is-typedarray": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/is-typedarray/-/is-typedarray-1.0.0.tgz", "integrity": "sha1-5HnICFjfDBsR3dppQPlgEfzaSpo=" }, + "is-windows": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-windows/-/is-windows-1.0.2.tgz", + "integrity": "sha512-eXK1UInq2bPmjyX6e3VHIzMLobc4J94i4AWn+Hpq3OU5KkrRC96OAcR3PRJ/pGu6m8TRnBHP9dkXQVsT/COVIA==" + }, "isarray": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", @@ -2071,6 +2514,11 @@ "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=", "dev": true }, + "isobject": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", + "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=" + }, "isstream": { "version": "0.1.2", "resolved": "https://registry.npmjs.org/isstream/-/isstream-0.1.2.tgz", @@ -2092,9 +2540,9 @@ "dev": true }, "js-sha3": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/js-sha3/-/js-sha3-0.3.1.tgz", - "integrity": "sha1-hhIoAhQvCChQKg0d7h2V4lO7AkM=" + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/js-sha3/-/js-sha3-0.6.1.tgz", + "integrity": "sha1-W4n3enR3Z5h39YxKB1JAk0sflcA=" }, "js-tokens": { "version": "4.0.0", @@ -2103,9 +2551,9 @@ "dev": true }, "js-yaml": { - "version": "3.12.0", - "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.12.0.tgz", - "integrity": "sha512-PIt2cnwmPfL4hKNwqeiuz4bKfnzHTBv6HyVgjahA6mPLwPDzjDWrplJBMjHUFxku/N3FlmrbyPclad+I+4mJ3A==", + "version": "3.12.1", + "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.12.1.tgz", + "integrity": "sha512-um46hB9wNOKlwkHgiuyEVAybXBjwFUV0Z/RaHJblRd9DXltue9FTYvzCr9ErQrK9Adz5MU4gHWVaNUfdmrC8qA==", "dev": true, "requires": { "argparse": "^1.0.7", @@ -2123,8 +2571,7 @@ "jsbn": { "version": "0.1.1", "resolved": "https://registry.npmjs.org/jsbn/-/jsbn-0.1.1.tgz", - "integrity": "sha1-peZUwuWi3rXyAdls77yoDA7y9RM=", - "optional": true + "integrity": "sha1-peZUwuWi3rXyAdls77yoDA7y9RM=" }, "json-schema": { "version": "0.2.3", @@ -2132,17 +2579,9 @@ "integrity": "sha1-tIDIkuWaLwWVTOcnvT8qTogvnhM=" }, "json-schema-traverse": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.3.1.tgz", - "integrity": "sha1-NJptRMU6Ud6JtAgFxdXlm0F9M0A=" - }, - "json-stable-stringify": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/json-stable-stringify/-/json-stable-stringify-1.0.1.tgz", - "integrity": "sha1-mnWdOcXy/1A/1TAGRu1EX4jE+a8=", - "requires": { - "jsonify": "~0.0.0" - } + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", + "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==" }, "json-stable-stringify-without-jsonify": { "version": "1.0.1", @@ -2156,18 +2595,13 @@ "integrity": "sha1-Epai1Y/UXxmg9s4B1lcB4sc1tus=" }, "jsonfile": { - "version": "2.4.0", - "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-2.4.0.tgz", - "integrity": "sha1-NzaitCi4e72gzIO1P6PWM6NcKug=", + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-4.0.0.tgz", + "integrity": "sha1-h3Gq4HmbZAdrdmQPygWPnBDjPss=", "requires": { "graceful-fs": "^4.1.6" } }, - "jsonify": { - "version": "0.0.0", - "resolved": "https://registry.npmjs.org/jsonify/-/jsonify-0.0.0.tgz", - "integrity": "sha1-LHS27kHZPKUbe1qu6PUDYx0lKnM=" - }, "jsprim": { "version": "1.4.1", "resolved": "https://registry.npmjs.org/jsprim/-/jsprim-1.4.1.tgz", @@ -2191,14 +2625,19 @@ } }, "keccakjs": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/keccakjs/-/keccakjs-0.2.1.tgz", - "integrity": "sha1-HWM6+QfvMFu/ny+mFtVsRFYd+k0=", + "version": "0.2.3", + "resolved": "https://registry.npmjs.org/keccakjs/-/keccakjs-0.2.3.tgz", + "integrity": "sha512-BjLkNDcfaZ6l8HBG9tH0tpmDv3sS2mA7FNQxFHpCdzP3Gb2MVruXBSuoM66SnVxKJpAr5dKGdkHD+bDokt8fTg==", "requires": { - "browserify-sha3": "^0.0.1", - "sha3": "^1.1.0" + "browserify-sha3": "^0.0.4", + "sha3": "^1.2.2" } }, + "kind-of": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-6.0.2.tgz", + "integrity": "sha512-s5kLOcnH0XqDO+FvuaLX8DDjZ18CGFk7VygH40QoKPUQhW4e2rvM0rwUq0t8IQDOwYSeLK01U90OjzBTme2QqA==" + }, "levn": { "version": "0.3.0", "resolved": "https://registry.npmjs.org/levn/-/levn-0.3.0.tgz", @@ -2210,7 +2649,7 @@ }, "load-json-file": { "version": "2.0.0", - "resolved": "http://registry.npmjs.org/load-json-file/-/load-json-file-2.0.0.tgz", + "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-2.0.0.tgz", "integrity": "sha1-eUfkIUmvgNaWy/eXvKq8/h/inKg=", "dev": true, "requires": { @@ -2218,6 +2657,14 @@ "parse-json": "^2.2.0", "pify": "^2.0.0", "strip-bom": "^3.0.0" + }, + "dependencies": { + "pify": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", + "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=", + "dev": true + } } }, "locate-path": { @@ -2228,14 +2675,6 @@ "requires": { "p-locate": "^2.0.0", "path-exists": "^3.0.0" - }, - "dependencies": { - "path-exists": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", - "integrity": "sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=", - "dev": true - } } }, "lodash": { @@ -2250,44 +2689,40 @@ "integrity": "sha512-G2Lj61tXDnVFFOi8VZds+SoQjtQC3dgokKdDG2mTm1tx4m50NUHBOZSBwQQHyy0V12A0JTG4icfZQH+xPyh8VA==" }, "make-dir": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-1.2.0.tgz", - "integrity": "sha512-aNUAa4UMg/UougV25bbrU4ZaaKNjJ/3/xnvg/twpmKROPdKZPZ9wGgI0opdZzO8q/zUFawoUuixuOv33eZ61Iw==", + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-1.3.0.tgz", + "integrity": "sha512-2w31R7SJtieJJnQtGc7RVL2StM2vGYVfqUOvUDxH6bC6aJTxPxTF0GnIgCyu7tjockiUWAYQRbxa7vKn34s5sQ==", "requires": { "pify": "^3.0.0" - }, - "dependencies": { - "pify": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", - "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=" - } + } + }, + "map-cache": { + "version": "0.2.2", + "resolved": "https://registry.npmjs.org/map-cache/-/map-cache-0.2.2.tgz", + "integrity": "sha1-wyq9C9ZSXZsFFkW7TyasXcmKDb8=" + }, + "map-visit": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/map-visit/-/map-visit-1.0.0.tgz", + "integrity": "sha1-7Nyo8TFE5mDxtb1B8S80edmN+48=", + "requires": { + "object-visit": "^1.0.0" } }, "md5.js": { - "version": "1.3.4", - "resolved": "https://registry.npmjs.org/md5.js/-/md5.js-1.3.4.tgz", - "integrity": "sha1-6b296UogpawYsENA/Fdk1bCdkB0=", + "version": "1.3.5", + "resolved": "https://registry.npmjs.org/md5.js/-/md5.js-1.3.5.tgz", + "integrity": "sha512-xitP+WxNPcTTOgnTJcrhM0xvdPepipPSf3I8EIpGKeFLjt3PlJLIDG3u8EX53ZIubkb+5U2+3rELYpEhHhzdkg==", "requires": { "hash-base": "^3.0.0", - "inherits": "^2.0.1" - }, - "dependencies": { - "hash-base": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/hash-base/-/hash-base-3.0.4.tgz", - "integrity": "sha1-X8hoaEfs1zSZQDMZprCj8/auSRg=", - "requires": { - "inherits": "^2.0.1", - "safe-buffer": "^5.0.1" - } - } + "inherits": "^2.0.1", + "safe-buffer": "^5.1.2" } }, "meant": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/meant/-/meant-1.0.0.tgz", - "integrity": "sha1-y2KG47evkxXxYRj9wiRybtOAdLs=" + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/meant/-/meant-1.0.1.tgz", + "integrity": "sha512-UakVLFjKkbbUwNWJ2frVLnnAtbb7D7DsloxRd3s/gDpI8rdv8W5Hp3NaDb+POBI1fQdeussER6NB8vpcRURvlg==" }, "media-typer": { "version": "0.3.0", @@ -2299,11 +2734,36 @@ "resolved": "https://registry.npmjs.org/merge-descriptors/-/merge-descriptors-1.0.1.tgz", "integrity": "sha1-sAqqVW3YtEVoFQ7J0blT8/kMu2E=" }, + "merge2": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/merge2/-/merge2-1.2.3.tgz", + "integrity": "sha512-gdUU1Fwj5ep4kplwcmftruWofEFt6lfpkkr3h860CXbAB9c3hGb55EOL2ali0Td5oebvW0E1+3Sr+Ur7XfKpRA==" + }, "methods": { "version": "1.1.2", "resolved": "https://registry.npmjs.org/methods/-/methods-1.1.2.tgz", "integrity": "sha1-VSmk1nZUE07cxSZmVoNbD4Ua/O4=" }, + "micromatch": { + "version": "3.1.10", + "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-3.1.10.tgz", + "integrity": "sha512-MWikgl9n9M3w+bpsY3He8L+w9eF9338xRl8IAO5viDizwSzziFEyUzo2xrrloB64ADbTf8uA8vRqqttDTOmccg==", + "requires": { + "arr-diff": "^4.0.0", + "array-unique": "^0.3.2", + "braces": "^2.3.1", + "define-property": "^2.0.2", + "extend-shallow": "^3.0.2", + "extglob": "^2.0.4", + "fragment-cache": "^0.2.1", + "kind-of": "^6.0.2", + "nanomatch": "^1.2.9", + "object.pick": "^1.3.0", + "regex-not": "^1.0.0", + "snapdragon": "^0.8.1", + "to-regex": "^3.0.2" + } + }, "miller-rabin": { "version": "4.0.1", "resolved": "https://registry.npmjs.org/miller-rabin/-/miller-rabin-4.0.1.tgz", @@ -2319,16 +2779,16 @@ "integrity": "sha512-KI1+qOZu5DcW6wayYHSzR/tXKCDC5Om4s1z2QJjDULzLcmf3DvzS7oluY4HCTrc+9FiKmWUgeNLg7W3uIQvxtQ==" }, "mime-db": { - "version": "1.33.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.33.0.tgz", - "integrity": "sha512-BHJ/EKruNIqJf/QahvxwQZXKygOQ256myeN/Ew+THcAa5q+PjyTTMMeNQC4DZw5AwfvelsUrA6B67NKMqXDbzQ==" + "version": "1.38.0", + "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.38.0.tgz", + "integrity": "sha512-bqVioMFFzc2awcdJZIzR3HjZFX20QhilVS7hytkKrv7xFAn8bM1gzc/FOX2awLISvWe0PV8ptFKcon+wZ5qYkg==" }, "mime-types": { - "version": "2.1.18", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.18.tgz", - "integrity": "sha512-lc/aahn+t4/SWV/qcmumYjymLsWfN3ELhpmVuUFjgsORruuZPVSwAQryq+HHGvO/SI2KVX26bx+En+zhM8g8hQ==", + "version": "2.1.22", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.22.tgz", + "integrity": "sha512-aGl6TZGnhm/li6F7yx82bJiBZwgiEa4Hf6CNr8YO+r5UHr53tSTYZb102zyU50DOWWKeOv0uQLRL0/9EiKWCog==", "requires": { - "mime-db": "~1.33.0" + "mime-db": "~1.38.0" } }, "mimic-fn": { @@ -2338,9 +2798,9 @@ "dev": true }, "mimic-response": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-1.0.0.tgz", - "integrity": "sha1-3z02Uqc/3ta5sLJBRub9BSNTRY4=" + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-1.0.1.tgz", + "integrity": "sha512-j5EctnkH7amfV/q5Hgmoal1g2QHFJRraOtmx0JpIqkxhBhI/lJSl1nMpQ45hVarwNETOoWEimndZ4QK0RHxuxQ==" }, "min-document": { "version": "2.19.0", @@ -2351,9 +2811,9 @@ } }, "minimalistic-assert": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/minimalistic-assert/-/minimalistic-assert-1.0.0.tgz", - "integrity": "sha1-cCvi3aazf0g2vLP121ZkG2Sh09M=" + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/minimalistic-assert/-/minimalistic-assert-1.0.1.tgz", + "integrity": "sha512-UtJcAD4yEaGtjPezWuO9wC4nwUnVH/8/Im3yEHQP4b67cXlD/Qr9hdITCU1xDbSEXg2XKNaP8jsReV7vQd00/A==" }, "minimalistic-crypto-utils": { "version": "1.0.1", @@ -2369,9 +2829,28 @@ } }, "minimist": { - "version": "0.0.8", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-0.0.8.tgz", - "integrity": "sha1-hX/Kv8M5fSYluCKCYuhqp6ARsF0=" + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz", + "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=" + }, + "mixin-deep": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/mixin-deep/-/mixin-deep-1.3.1.tgz", + "integrity": "sha512-8ZItLHeEgaqEvd5lYBXfm4EZSFCX29Jb9K+lAHhDKzReKBQKj3R+7NOF6tjqYi9t4oI8VUfaWITJQm86wnXGNQ==", + "requires": { + "for-in": "^1.0.2", + "is-extendable": "^1.0.1" + }, + "dependencies": { + "is-extendable": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-1.0.1.tgz", + "integrity": "sha512-arnXMxT1hhoKo9k1LZdmlNyJdDDfy2v0fXjFlmok4+i8ul/6WlbVge9bhM74OpNPQPMGUToDtz+KXa1PneJxOA==", + "requires": { + "is-plain-object": "^2.0.4" + } + } + } }, "mkdirp": { "version": "0.5.1", @@ -2379,6 +2858,13 @@ "integrity": "sha1-MAV0OOrGz3+MR2fzhkjWaX11yQM=", "requires": { "minimist": "0.0.8" + }, + "dependencies": { + "minimist": { + "version": "0.0.8", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-0.0.8.tgz", + "integrity": "sha1-hX/Kv8M5fSYluCKCYuhqp6ARsF0=" + } } }, "mkdirp-promise": { @@ -2390,9 +2876,9 @@ } }, "mock-fs": { - "version": "4.4.2", - "resolved": "https://registry.npmjs.org/mock-fs/-/mock-fs-4.4.2.tgz", - "integrity": "sha512-dF+yxZSojSiI8AXGoxj5qdFWpucndc54Ug+TwlpHFaV7j22MGG+OML2+FVa6xAZtjb/OFFQhOC37Jegx2GbEwA==" + "version": "4.8.0", + "resolved": "https://registry.npmjs.org/mock-fs/-/mock-fs-4.8.0.tgz", + "integrity": "sha512-Gwj4KnJOW15YeTJKO5frFd/WDO5Mc0zxXqL9oHx3+e9rBqW8EVARqQHSaIXznUdljrD6pvbNGW2ZGXKPEfYJfw==" }, "mout": { "version": "0.11.1", @@ -2405,9 +2891,9 @@ "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" }, "multistream": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/multistream/-/multistream-2.1.0.tgz", - "integrity": "sha1-YlwmfVxEQkrWKUeItbtNo9yzLx0=", + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/multistream/-/multistream-2.1.1.tgz", + "integrity": "sha512-xasv76hl6nr1dEy3lPvy7Ej7K/Lx3O/FCvwge8PeVJpciPPoNCbaANcNiBug3IpdvTveZUcAV0DJzdnUDMesNQ==", "requires": { "inherits": "^2.0.1", "readable-stream": "^2.0.5" @@ -2430,15 +2916,33 @@ } }, "nan": { - "version": "2.10.0", - "resolved": "https://registry.npmjs.org/nan/-/nan-2.10.0.tgz", - "integrity": "sha512-bAdJv7fBLhWC+/Bls0Oza+mvTaNQtP+1RyhhhvD95pgUJz6XM5IzgmxOkItJ9tkoCiplvAnXI1tNmmUD/eScyA==" + "version": "2.12.1", + "resolved": "https://registry.npmjs.org/nan/-/nan-2.12.1.tgz", + "integrity": "sha512-JY7V6lRkStKcKTvHO5NVSQRv+RV+FIL5pvDoLiAtSL9pKlC5x9PKQcZDsq7m4FO4d57mkhC6Z+QhAh3Jdk5JFw==" }, "nano-json-stream-parser": { "version": "0.1.2", "resolved": "https://registry.npmjs.org/nano-json-stream-parser/-/nano-json-stream-parser-0.1.2.tgz", "integrity": "sha1-DMj20OK2IrR5xA1JnEbWS3Vcb18=" }, + "nanomatch": { + "version": "1.2.13", + "resolved": "https://registry.npmjs.org/nanomatch/-/nanomatch-1.2.13.tgz", + "integrity": "sha512-fpoe2T0RbHwBTBUOftAfBPaDEi06ufaUai0mE6Yn1kacc3SnTErfb/h+X94VXzI64rKFHYImXSvdwGGCmwOqCA==", + "requires": { + "arr-diff": "^4.0.0", + "array-unique": "^0.3.2", + "define-property": "^2.0.2", + "extend-shallow": "^3.0.2", + "fragment-cache": "^0.2.1", + "is-windows": "^1.0.2", + "kind-of": "^6.0.2", + "object.pick": "^1.3.0", + "regex-not": "^1.0.0", + "snapdragon": "^0.8.1", + "to-regex": "^3.0.1" + } + }, "natural-compare": { "version": "1.4.0", "resolved": "https://registry.npmjs.org/natural-compare/-/natural-compare-1.4.0.tgz", @@ -2457,20 +2961,31 @@ "dev": true }, "node-fetch": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.1.2.tgz", - "integrity": "sha1-q4hOjn5X44qUR1POxwb3iNF2i7U=" + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.3.0.tgz", + "integrity": "sha512-MOd8pV3fxENbryESLgVIeaGKrdl+uaYhCSSVkjeOb/31/njTpcis5aWfdqgNlHIrKOLRbMnfPINPOML2CIFeXA==" }, "normalize-package-data": { - "version": "2.4.0", - "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-2.4.0.tgz", - "integrity": "sha512-9jjUFbTPfEy3R/ad/2oNbKtW9Hgovl5O1FvFWKkKblNXoN/Oou6+9+KKohPK13Yc3/TyunyWhJp6gvRNR/PPAw==", + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-2.5.0.tgz", + "integrity": "sha512-/5CMN3T0R4XTj4DcGaexo+roZSdSFW/0AOOTROrjxzCG1wrWXEsGbRKevjlIL+ZDE4sZlJr5ED4YW0yqmkK+eA==", "dev": true, "requires": { "hosted-git-info": "^2.1.4", - "is-builtin-module": "^1.0.0", + "resolve": "^1.10.0", "semver": "2 || 3 || 4 || 5", "validate-npm-package-license": "^3.0.1" + }, + "dependencies": { + "resolve": { + "version": "1.10.0", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.10.0.tgz", + "integrity": "sha512-3sUr9aq5OfSg2S9pNtPA9hL1FVEAjvfOC4leW0SNf/mpnaakz2a9femSd6LqAww2RaFctwyf1lCqnTHuF1rxDg==", + "dev": true, + "requires": { + "path-parse": "^1.0.6" + } + } } }, "number-to-bn": { @@ -2490,21 +3005,57 @@ } }, "oauth-sign": { - "version": "0.8.2", - "resolved": "https://registry.npmjs.org/oauth-sign/-/oauth-sign-0.8.2.tgz", - "integrity": "sha1-Rqarfwrq2N6unsBWV4C31O/rnUM=" + "version": "0.9.0", + "resolved": "https://registry.npmjs.org/oauth-sign/-/oauth-sign-0.9.0.tgz", + "integrity": "sha512-fexhUFFPTGV8ybAtSIGbV6gOkSv8UtRbDBnAyLQw4QPKkgNlsH2ByPGtMUqdWkos6YCRmAqViwgZrJc/mRDzZQ==" }, "object-assign": { "version": "4.1.1", "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", "integrity": "sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM=" }, + "object-copy": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/object-copy/-/object-copy-0.1.0.tgz", + "integrity": "sha1-fn2Fi3gb18mRpBupde04EnVOmYw=", + "requires": { + "copy-descriptor": "^0.1.0", + "define-property": "^0.2.5", + "kind-of": "^3.0.3" + }, + "dependencies": { + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "requires": { + "is-descriptor": "^0.1.0" + } + }, + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "requires": { + "is-buffer": "^1.1.5" + } + } + } + }, "object-keys": { - "version": "1.0.12", - "resolved": "https://registry.npmjs.org/object-keys/-/object-keys-1.0.12.tgz", - "integrity": "sha512-FTMyFUm2wBcGHnH2eXmz7tC6IwlqQZ6mVZ+6dm6vZ4IQIHjs6FdNsQBuKGPuUUUY6NfJw2PshC08Tn6LzLDOag==", + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/object-keys/-/object-keys-1.1.0.tgz", + "integrity": "sha512-6OO5X1+2tYkNyNEx6TsCxEqFfRWaqx6EtMiSbGrw8Ob8v9Ne+Hl8rBAgLBZn5wjEz3s/s6U1WXFUFOcxxAwUpg==", "dev": true }, + "object-visit": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/object-visit/-/object-visit-1.0.1.tgz", + "integrity": "sha1-95xEk68MU3e1n+OdOV5BBC3QRbs=", + "requires": { + "isobject": "^3.0.0" + } + }, "object.assign": { "version": "4.1.0", "resolved": "https://registry.npmjs.org/object.assign/-/object.assign-4.1.0.tgz", @@ -2518,15 +3069,23 @@ } }, "object.entries": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/object.entries/-/object.entries-1.0.4.tgz", - "integrity": "sha1-G/mk3SKI9bM/Opk9JXZh8F0WGl8=", + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/object.entries/-/object.entries-1.1.0.tgz", + "integrity": "sha512-l+H6EQ8qzGRxbkHOd5I/aHRhHDKoQXQ8g0BYt4uSweQU1/J6dZUOyWh9a2Vky35YCKjzmgxOzta2hH6kf9HuXA==", "dev": true, "requires": { - "define-properties": "^1.1.2", - "es-abstract": "^1.6.1", - "function-bind": "^1.1.0", - "has": "^1.0.1" + "define-properties": "^1.1.3", + "es-abstract": "^1.12.0", + "function-bind": "^1.1.1", + "has": "^1.0.3" + } + }, + "object.pick": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/object.pick/-/object.pick-1.3.0.tgz", + "integrity": "sha1-h6EKxMFpS9Lhy/U1kaZhQftd10c=", + "requires": { + "isobject": "^3.0.1" } }, "oboe": { @@ -2590,6 +3149,11 @@ "resolved": "https://registry.npmjs.org/p-finally/-/p-finally-1.0.0.tgz", "integrity": "sha1-P7z7FbiZpEEjs0ttzBi3JDNqLK4=" }, + "p-is-promise": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/p-is-promise/-/p-is-promise-2.0.0.tgz", + "integrity": "sha512-pzQPhYMCAgLAKPWD2jC3Se9fEfrD9npNos0y150EeqZll7akhEgGhTW/slB6lHku8AvYGiJ+YJ5hfHKePPgFWg==" + }, "p-limit": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-1.3.0.tgz", @@ -2622,16 +3186,26 @@ "integrity": "sha1-y8ec26+P1CKOE/Yh8rGiN8GyB7M=", "dev": true }, + "parent-module": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/parent-module/-/parent-module-1.0.0.tgz", + "integrity": "sha512-8Mf5juOMmiE4FcmzYc4IaiS9L3+9paz2KOiXzkRviCP6aDmN49Hz6EMWz0lGNp9pX80GvvAuLADtyGfW/Em3TA==", + "dev": true, + "requires": { + "callsites": "^3.0.0" + } + }, "parse-asn1": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/parse-asn1/-/parse-asn1-5.1.0.tgz", - "integrity": "sha1-N8T5t+06tlx0gXtfJICTf7+XxxI=", + "version": "5.1.4", + "resolved": "https://registry.npmjs.org/parse-asn1/-/parse-asn1-5.1.4.tgz", + "integrity": "sha512-Qs5duJcuvNExRfFZ99HDD3z4mAi3r9Wl/FOjEOijlxwCZs7E7mW2vjTpgQ4J8LpTF8x5v+1Vn5UQFejmWT11aw==", "requires": { "asn1.js": "^4.0.0", "browserify-aes": "^1.0.0", "create-hash": "^1.1.0", "evp_bytestokey": "^1.0.0", - "pbkdf2": "^3.0.3" + "pbkdf2": "^3.0.3", + "safe-buffer": "^5.1.1" } }, "parse-headers": { @@ -2657,14 +3231,21 @@ "resolved": "https://registry.npmjs.org/parseurl/-/parseurl-1.3.2.tgz", "integrity": "sha1-/CidTtiZMRlGDBViUyYs3I3mW/M=" }, + "pascalcase": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/pascalcase/-/pascalcase-0.1.1.tgz", + "integrity": "sha1-s2PlXoAGym/iF4TS2yK9FdeRfxQ=" + }, + "path-dirname": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/path-dirname/-/path-dirname-1.0.2.tgz", + "integrity": "sha1-zDPSTVJeCZpTiMAzbG4yuRYGCeA=" + }, "path-exists": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-2.1.0.tgz", - "integrity": "sha1-D+tsZPD8UY2adU3V77YscCJ2H0s=", - "dev": true, - "requires": { - "pinkie-promise": "^2.0.0" - } + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", + "integrity": "sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=", + "dev": true }, "path-is-absolute": { "version": "1.0.1", @@ -2684,9 +3265,9 @@ "dev": true }, "path-parse": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.5.tgz", - "integrity": "sha1-PBrfhx6pzWyUMbbqK9dKD/BVxME=" + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.6.tgz", + "integrity": "sha512-GSmOT2EbHrINBf9SR7CDELwlJ8AENk3Qn7OikK4nFYAu3Ote2+JYNVvkpAEQm3/TLNEJFD/xZJjzyxg3KBWOzw==" }, "path-to-regexp": { "version": "0.1.7", @@ -2694,18 +3275,17 @@ "integrity": "sha1-32BBeABfUi8V60SQ5yR6G/qmf4w=" }, "path-type": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/path-type/-/path-type-2.0.0.tgz", - "integrity": "sha1-8BLMuEFbcJb8LaoQVMPXI4lZTHM=", - "dev": true, + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/path-type/-/path-type-3.0.0.tgz", + "integrity": "sha512-T2ZUsdZFHgA3u4e5PfPbjd7HDDpxPnQb5jN0SrDsjNSuVXHJqtwTnWqG0B1jZrgmJ/7lj1EmVIByWt1gxGkWvg==", "requires": { - "pify": "^2.0.0" + "pify": "^3.0.0" } }, "pbkdf2": { - "version": "3.0.14", - "resolved": "https://registry.npmjs.org/pbkdf2/-/pbkdf2-3.0.14.tgz", - "integrity": "sha512-gjsZW9O34fm0R7PaLHRJmLLVfSoesxztjPjE9o6R+qtVJij90ltg1joIovN9GKrRW3t1PzhDDG3UMEMFfZ+1wA==", + "version": "3.0.17", + "resolved": "https://registry.npmjs.org/pbkdf2/-/pbkdf2-3.0.17.tgz", + "integrity": "sha512-U/il5MsrZp7mGg3mSQfn742na2T+1/vHDCG5/iTI3X9MKUuYUZVLQhyRsg06mCgDBTd57TxzgZt7P+fYfjRLtA==", "requires": { "create-hash": "^1.1.2", "create-hmac": "^1.1.4", @@ -2725,9 +3305,9 @@ "integrity": "sha1-Ywn04OX6kT7BxpMHrjZLSzd8nns=" }, "pify": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", - "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=" + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", + "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=" }, "pinkie": { "version": "2.0.4", @@ -2743,241 +3323,69 @@ } }, "pkg": { - "version": "4.3.1", - "resolved": "https://registry.npmjs.org/pkg/-/pkg-4.3.1.tgz", - "integrity": "sha512-QaOXdF9doVkrXpeu0D5ODLDLjYE4LE2WAk7/wSgNiCsCajg4ExjApxwkVIanz61tR8oIe+8vkmW0WpAwfV1ExA==", - "requires": { - "acorn": "5.5.3", - "acorn-object-rest-spread": "1.1.0", - "babel-runtime": "6.25.0", - "chalk": "2.1.0", - "escodegen": "1.8.1", - "fs-extra": "4.0.1", - "globby": "6.1.0", + "version": "4.3.7", + "resolved": "https://registry.npmjs.org/pkg/-/pkg-4.3.7.tgz", + "integrity": "sha512-/BvtFft1nKKtnTuOm/0es0sk1cOs7ZtWgJpqdtszJ4348jYJ8owVyCB/iuGhI3YJFX/ZFIv4Rmra9ETUgpnnfA==", + "requires": { + "@babel/parser": "7.2.3", + "babel-runtime": "6.26.0", + "chalk": "2.4.2", + "escodegen": "1.11.0", + "fs-extra": "7.0.1", + "globby": "8.0.2", + "into-stream": "4.0.0", "minimist": "1.2.0", - "multistream": "2.1.0", - "pkg-fetch": "2.5.4", - "progress": "2.0.0", - "resolve": "1.4.0", - "simple-bufferstream": "1.0.0", + "multistream": "2.1.1", + "pkg-fetch": "2.5.7", + "progress": "2.0.3", + "resolve": "1.6.0", "stream-meter": "1.0.4" - }, - "dependencies": { - "fs-extra": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-4.0.1.tgz", - "integrity": "sha1-f8DGyJV/mD9X8waiTlud3Y0N2IA=", - "requires": { - "graceful-fs": "^4.1.2", - "jsonfile": "^3.0.0", - "universalify": "^0.1.0" - } - }, - "jsonfile": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-3.0.1.tgz", - "integrity": "sha1-pezG9l9T9mLEQVx2daAzHQmS7GY=", - "requires": { - "graceful-fs": "^4.1.6" - } - }, - "minimist": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz", - "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=" - } } }, "pkg-dir": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/pkg-dir/-/pkg-dir-1.0.0.tgz", - "integrity": "sha1-ektQio1bstYp1EcFb/TpyTFM89Q=", + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/pkg-dir/-/pkg-dir-2.0.0.tgz", + "integrity": "sha1-9tXREJ4Z1j7fQo4L1X4Sd3YVM0s=", "dev": true, "requires": { - "find-up": "^1.0.0" + "find-up": "^2.1.0" } }, "pkg-fetch": { - "version": "2.5.4", - "resolved": "https://registry.npmjs.org/pkg-fetch/-/pkg-fetch-2.5.4.tgz", - "integrity": "sha512-KASiP5yytve4otDY242Zp3r+e11whyoSl79QmmBS3Qg4rvZsYOC5RE0szM0SZrVxg93sqYcINxHlXmzBTJDOeA==", - "requires": { - "babel-runtime": "6.25.0", - "byline": "5.0.0", - "chalk": "2.1.0", - "expand-template": "1.0.3", - "fs-extra": "4.0.1", - "in-publish": "2.0.0", - "minimist": "1.2.0", - "progress": "2.0.0", - "request": "2.81.0", - "request-progress": "3.0.0", - "semver": "5.4.1", - "unique-temp-dir": "1.0.0" + "version": "2.5.7", + "resolved": "https://registry.npmjs.org/pkg-fetch/-/pkg-fetch-2.5.7.tgz", + "integrity": "sha512-fm9aVV3ZRdFYTyFYcSHuKMuxPCVQ0MD9tbVxbvQzFTg1gwvV0KqWrFoj5enVVha94yP83I50XEBa90X8L9fE8w==", + "requires": { + "babel-runtime": "~6.26.0", + "byline": "~5.0.0", + "chalk": "~2.4.1", + "expand-template": "~1.1.1", + "fs-extra": "~6.0.1", + "in-publish": "~2.0.0", + "minimist": "~1.2.0", + "progress": "~2.0.0", + "request": "~2.88.0", + "request-progress": "~3.0.0", + "semver": "~5.6.0", + "unique-temp-dir": "~1.0.0" }, "dependencies": { - "ajv": { - "version": "4.11.8", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-4.11.8.tgz", - "integrity": "sha1-gv+wKynmYq5TvcIK8VlHcGc5xTY=", - "requires": { - "co": "^4.6.0", - "json-stable-stringify": "^1.0.1" - } - }, - "assert-plus": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-0.2.0.tgz", - "integrity": "sha1-104bh+ev/A24qttwIfP+SBAasjQ=" - }, - "aws-sign2": { - "version": "0.6.0", - "resolved": "https://registry.npmjs.org/aws-sign2/-/aws-sign2-0.6.0.tgz", - "integrity": "sha1-FDQt0428yU0OW4fXY81jYSwOeU8=" - }, - "boom": { - "version": "2.10.1", - "resolved": "https://registry.npmjs.org/boom/-/boom-2.10.1.tgz", - "integrity": "sha1-OciRjO/1eZ+D+UkqhI9iWt0Mdm8=", - "requires": { - "hoek": "2.x.x" - } - }, - "cryptiles": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/cryptiles/-/cryptiles-2.0.5.tgz", - "integrity": "sha1-O9/s3GCBR8HGcgL6KR59ylnqo7g=", - "requires": { - "boom": "2.x.x" - } - }, - "form-data": { - "version": "2.1.4", - "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.1.4.tgz", - "integrity": "sha1-M8GDrPGTJ27KqYFDpp6Uv+4XUNE=", - "requires": { - "asynckit": "^0.4.0", - "combined-stream": "^1.0.5", - "mime-types": "^2.1.12" - } - }, "fs-extra": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-4.0.1.tgz", - "integrity": "sha1-f8DGyJV/mD9X8waiTlud3Y0N2IA=", + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-6.0.1.tgz", + "integrity": "sha512-GnyIkKhhzXZUWFCaJzvyDLEEgDkPfb4/TPvJCJVuS8MWZgoSsErf++QpiAlDnKFcqhRlm+tIOcencCjyJE6ZCA==", "requires": { "graceful-fs": "^4.1.2", - "jsonfile": "^3.0.0", + "jsonfile": "^4.0.0", "universalify": "^0.1.0" } - }, - "har-schema": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/har-schema/-/har-schema-1.0.5.tgz", - "integrity": "sha1-0mMTX0MwfALGAq/I/pWXDAFRNp4=" - }, - "har-validator": { - "version": "4.2.1", - "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-4.2.1.tgz", - "integrity": "sha1-M0gdDxu/9gDdID11gSpqX7oALio=", - "requires": { - "ajv": "^4.9.1", - "har-schema": "^1.0.5" - } - }, - "hawk": { - "version": "3.1.3", - "resolved": "https://registry.npmjs.org/hawk/-/hawk-3.1.3.tgz", - "integrity": "sha1-B4REvXwWQLD+VA0sm3PVlnjo4cQ=", - "requires": { - "boom": "2.x.x", - "cryptiles": "2.x.x", - "hoek": "2.x.x", - "sntp": "1.x.x" - } - }, - "hoek": { - "version": "2.16.3", - "resolved": "https://registry.npmjs.org/hoek/-/hoek-2.16.3.tgz", - "integrity": "sha1-ILt0A9POo5jpHcRxCo/xuCdKJe0=" - }, - "http-signature": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/http-signature/-/http-signature-1.1.1.tgz", - "integrity": "sha1-33LiZwZs0Kxn+3at+OE0qPvPkb8=", - "requires": { - "assert-plus": "^0.2.0", - "jsprim": "^1.2.2", - "sshpk": "^1.7.0" - } - }, - "jsonfile": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-3.0.1.tgz", - "integrity": "sha1-pezG9l9T9mLEQVx2daAzHQmS7GY=", - "requires": { - "graceful-fs": "^4.1.6" - } - }, - "minimist": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz", - "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=" - }, - "performance-now": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/performance-now/-/performance-now-0.2.0.tgz", - "integrity": "sha1-M+8wxcd9TqIcWlOGnZG1bY8lVeU=" - }, - "qs": { - "version": "6.4.0", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.4.0.tgz", - "integrity": "sha1-E+JtKK1rD/qpExLNO/cI7TUecjM=" - }, - "request": { - "version": "2.81.0", - "resolved": "https://registry.npmjs.org/request/-/request-2.81.0.tgz", - "integrity": "sha1-xpKJRqDgbF+Nb4qTM0af/aRimKA=", - "requires": { - "aws-sign2": "~0.6.0", - "aws4": "^1.2.1", - "caseless": "~0.12.0", - "combined-stream": "~1.0.5", - "extend": "~3.0.0", - "forever-agent": "~0.6.1", - "form-data": "~2.1.1", - "har-validator": "~4.2.1", - "hawk": "~3.1.3", - "http-signature": "~1.1.0", - "is-typedarray": "~1.0.0", - "isstream": "~0.1.2", - "json-stringify-safe": "~5.0.1", - "mime-types": "~2.1.7", - "oauth-sign": "~0.8.1", - "performance-now": "^0.2.0", - "qs": "~6.4.0", - "safe-buffer": "^5.0.1", - "stringstream": "~0.0.4", - "tough-cookie": "~2.3.0", - "tunnel-agent": "^0.6.0", - "uuid": "^3.0.0" - } - }, - "sntp": { - "version": "1.0.9", - "resolved": "https://registry.npmjs.org/sntp/-/sntp-1.0.9.tgz", - "integrity": "sha1-ZUEYTMkK7qbG57NeJlkIJEPGYZg=", - "requires": { - "hoek": "2.x.x" - } } } }, - "pluralize": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/pluralize/-/pluralize-7.0.0.tgz", - "integrity": "sha512-ARhBOdzS3e41FbkW/XWrTEtukqqLoK5+Z/4UeDaLuSW+39JPeFgs4gCGqsrJHVZX0fUrx//4OF0K1CUGwlIFow==", - "dev": true + "posix-character-classes": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/posix-character-classes/-/posix-character-classes-0.1.1.tgz", + "integrity": "sha1-AerA/jta9xoqbAL+q7jB/vfgDqs=" }, "prelude-ls": { "version": "1.1.2", @@ -2990,9 +3398,9 @@ "integrity": "sha1-1PRWKwzjaW5BrFLQ4ALlemNdxtw=" }, "prettier": { - "version": "1.14.3", - "resolved": "https://registry.npmjs.org/prettier/-/prettier-1.14.3.tgz", - "integrity": "sha512-qZDVnCrnpsRJJq5nSsiHCE3BYMED2OtsI+cmzIzF1QIfqm5ALf8tEJcO27zV1gKNKRPdhjO0dNWnrzssDQ1tFg==", + "version": "1.16.4", + "resolved": "https://registry.npmjs.org/prettier/-/prettier-1.16.4.tgz", + "integrity": "sha512-ZzWuos7TI5CKUeQAtFd6Zhm2s6EpAD/ZLApIhsF9pRvRtM1RFo61dM/4MSRUA0SuLugA/zgrZD8m0BaY46Og7g==", "dev": true }, "process": { @@ -3006,40 +3414,46 @@ "integrity": "sha512-MtEC1TqN0EU5nephaJ4rAtThHtC86dNN9qCuEhtshvpVBkAW5ZO7BASN9REnF9eoXGcRub+pFuKEpOHE+HbEMw==" }, "progress": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/progress/-/progress-2.0.0.tgz", - "integrity": "sha1-ihvjZr+Pwj2yvSPxDG/pILQ4nR8=" + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/progress/-/progress-2.0.3.tgz", + "integrity": "sha512-7PiHtLll5LdnKIMw100I+8xJXR5gW2QwWYkT6iJva0bXitZKa/XMrSbdmg3r2Xnaidz9Qumd0VPaMrZlF9V9sA==" }, "proxy-addr": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.3.tgz", - "integrity": "sha512-jQTChiCJteusULxjBp8+jftSQE5Obdl3k4cnmLA6WXtK6XFuWRnvVL7aCiBqaLPM8c4ph0S4tKna8XvmIwEnXQ==", + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.4.tgz", + "integrity": "sha512-5erio2h9jp5CHGwcybmxmVqHmnCBZeewlfJ0pex+UW7Qny7OOZXTtH56TGNyBizkgiOwhJtMKrVzDTeKcySZwA==", "requires": { "forwarded": "~0.1.2", - "ipaddr.js": "1.6.0" + "ipaddr.js": "1.8.0" } }, + "psl": { + "version": "1.1.31", + "resolved": "https://registry.npmjs.org/psl/-/psl-1.1.31.tgz", + "integrity": "sha512-/6pt4+C+T+wZUieKR620OpzN/LlnNKuWjy1iFLQ/UG35JqHlR/89MP1d96dUfkf6Dne3TuLQzOYEYshJ+Hx8mw==" + }, "public-encrypt": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/public-encrypt/-/public-encrypt-4.0.0.tgz", - "integrity": "sha1-OfaZ86RlYN1eusvKaTyvfGXBjMY=", + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/public-encrypt/-/public-encrypt-4.0.3.tgz", + "integrity": "sha512-zVpa8oKZSz5bTMTFClc1fQOnyyEzpl5ozpi1B5YcvBrdohMjH2rfsBtyXcuNuwjsDIXmBYlF2N5FlJYhR29t8Q==", "requires": { "bn.js": "^4.1.0", "browserify-rsa": "^4.0.0", "create-hash": "^1.1.0", "parse-asn1": "^5.0.0", - "randombytes": "^2.0.1" + "randombytes": "^2.0.1", + "safe-buffer": "^5.1.2" } }, "punycode": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/punycode/-/punycode-1.4.1.tgz", - "integrity": "sha1-wNWmOycYgArY4esPpSachN1BhF4=" + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.1.1.tgz", + "integrity": "sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A==" }, "qs": { - "version": "6.5.1", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.5.1.tgz", - "integrity": "sha512-eRzhrN1WSINYCDCbrz796z37LOe3m5tmW7RQf6oBntukAG1nmovJvhnwHHRMAfeoItc1m2Hk02WER2aQ/iqs+A==" + "version": "6.5.2", + "resolved": "https://registry.npmjs.org/qs/-/qs-6.5.2.tgz", + "integrity": "sha512-N5ZAX4/LxJmF+7wN74pUD6qAh9/wnvdQcjq9TZjevvXzSUo7bfmw91saqMjzGS2xq91/odN2dW/WOl7qQHNDGA==" }, "query-string": { "version": "5.1.1", @@ -3079,13 +3493,13 @@ "integrity": "sha1-9JvmtIeJTdxA3MlKMi9hEJLgDV4=" }, "raw-body": { - "version": "2.3.2", - "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-2.3.2.tgz", - "integrity": "sha1-vNYMd9Prk83gBQKVw/N5OJvIj4k=", + "version": "2.3.3", + "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-2.3.3.tgz", + "integrity": "sha512-9esiElv1BrZoI3rCDuOuKCBRbuApGGaDPQfjSflGxdy4oyzqghxu6klEkkVIvBje+FF0BX9coEv8KqW6X/7njw==", "requires": { "bytes": "3.0.0", - "http-errors": "1.6.2", - "iconv-lite": "0.4.19", + "http-errors": "1.6.3", + "iconv-lite": "0.4.23", "unpipe": "1.0.0" } }, @@ -3098,6 +3512,23 @@ "load-json-file": "^2.0.0", "normalize-package-data": "^2.3.2", "path-type": "^2.0.0" + }, + "dependencies": { + "path-type": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/path-type/-/path-type-2.0.0.tgz", + "integrity": "sha1-8BLMuEFbcJb8LaoQVMPXI4lZTHM=", + "dev": true, + "requires": { + "pify": "^2.0.0" + } + }, + "pify": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", + "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=", + "dev": true + } } }, "read-pkg-up": { @@ -3108,71 +3539,77 @@ "requires": { "find-up": "^2.0.0", "read-pkg": "^2.0.0" - }, - "dependencies": { - "find-up": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", - "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", - "dev": true, - "requires": { - "locate-path": "^2.0.0" - } - } } }, "readable-stream": { - "version": "2.3.5", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.5.tgz", - "integrity": "sha512-tK0yDhrkygt/knjowCUiWP9YdV7c5R+8cR0r/kt9ZhBU906Fs6RpQJCEilamRJj1Nx2rWI6LkW9gKqjTkshhEw==", + "version": "2.3.6", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.6.tgz", + "integrity": "sha512-tQtKA9WIAhBF3+VLAseyMqZeBjW0AHJoxOtYqSUZNJxauErmLbVm2FW1y+J/YA9dUrAC39ITejlZWhVIwawkKw==", "requires": { "core-util-is": "~1.0.0", "inherits": "~2.0.3", "isarray": "~1.0.0", "process-nextick-args": "~2.0.0", "safe-buffer": "~5.1.1", - "string_decoder": "~1.0.3", + "string_decoder": "~1.1.1", "util-deprecate": "~1.0.1" } }, "regenerator-runtime": { - "version": "0.10.5", - "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.10.5.tgz", - "integrity": "sha1-M2w+/BIgrc7dosn6tntaeVWjNlg=" + "version": "0.11.1", + "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.11.1.tgz", + "integrity": "sha512-MguG95oij0fC3QV3URf4V2SDYGJhJnJGqvIIgdECeODCT98wSWDAJ94SSuVpYQUoTcGUIL6L4yNB7j1DFFHSBg==" + }, + "regex-not": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/regex-not/-/regex-not-1.0.2.tgz", + "integrity": "sha512-J6SDjUgDxQj5NusnOtdFxDwN/+HWykR8GELwctJ7mdqhcyy1xEc4SRFHUXvxTp661YaVKAjfRLZ9cCqS6tn32A==", + "requires": { + "extend-shallow": "^3.0.2", + "safe-regex": "^1.1.0" + } }, "regexpp": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/regexpp/-/regexpp-2.0.0.tgz", - "integrity": "sha512-g2FAVtR8Uh8GO1Nv5wpxW7VFVwHcCEr4wyA8/MHiRkO8uHoR5ntAA8Uq3P1vvMTX/BeQiRVSpDGLd+Wn5HNOTA==", + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/regexpp/-/regexpp-2.0.1.tgz", + "integrity": "sha512-lv0M6+TkDVniA3aD1Eg0DVpfU/booSu7Eev3TDO/mZKHBfVjgCGTV4t4buppESEYDtkArYFOxTJWv6S5C+iaNw==", "dev": true }, + "repeat-element": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/repeat-element/-/repeat-element-1.1.3.tgz", + "integrity": "sha512-ahGq0ZnV5m5XtZLMb+vP76kcAM5nkLqk0lpqAuojSKGgQtn4eRi4ZZGm2olo2zKFH+sMsWaqOCW1dqAnOru72g==" + }, + "repeat-string": { + "version": "1.6.1", + "resolved": "https://registry.npmjs.org/repeat-string/-/repeat-string-1.6.1.tgz", + "integrity": "sha1-jcrkcOHIirwtYA//Sndihtp15jc=" + }, "request": { - "version": "2.85.0", - "resolved": "https://registry.npmjs.org/request/-/request-2.85.0.tgz", - "integrity": "sha512-8H7Ehijd4js+s6wuVPLjwORxD4zeuyjYugprdOXlPSqaApmL/QOy+EB/beICHVCHkGMKNh5rvihb5ov+IDw4mg==", + "version": "2.88.0", + "resolved": "https://registry.npmjs.org/request/-/request-2.88.0.tgz", + "integrity": "sha512-NAqBSrijGLZdM0WZNsInLJpkJokL72XYjUpnB0iwsRgxh7dB6COrHnTBNwN0E+lHDAJzu7kLAkDeY08z2/A0hg==", "requires": { "aws-sign2": "~0.7.0", - "aws4": "^1.6.0", + "aws4": "^1.8.0", "caseless": "~0.12.0", - "combined-stream": "~1.0.5", - "extend": "~3.0.1", + "combined-stream": "~1.0.6", + "extend": "~3.0.2", "forever-agent": "~0.6.1", - "form-data": "~2.3.1", - "har-validator": "~5.0.3", - "hawk": "~6.0.2", + "form-data": "~2.3.2", + "har-validator": "~5.1.0", "http-signature": "~1.2.0", "is-typedarray": "~1.0.0", "isstream": "~0.1.2", "json-stringify-safe": "~5.0.1", - "mime-types": "~2.1.17", - "oauth-sign": "~0.8.2", + "mime-types": "~2.1.19", + "oauth-sign": "~0.9.0", "performance-now": "^2.1.0", - "qs": "~6.5.1", - "safe-buffer": "^5.1.1", - "stringstream": "~0.0.5", - "tough-cookie": "~2.3.3", + "qs": "~6.5.2", + "safe-buffer": "^5.1.2", + "tough-cookie": "~2.4.3", "tunnel-agent": "^0.6.0", - "uuid": "^3.1.0" + "uuid": "^3.3.2" } }, "request-progress": { @@ -3183,30 +3620,25 @@ "throttleit": "^1.0.0" } }, - "require-uncached": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/require-uncached/-/require-uncached-1.0.3.tgz", - "integrity": "sha1-Tg1W1slmL9MeQwEcS5WqSZVUIdM=", - "dev": true, - "requires": { - "caller-path": "^0.1.0", - "resolve-from": "^1.0.0" - } - }, "resolve": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.4.0.tgz", - "integrity": "sha512-aW7sVKPufyHqOmyyLzg/J+8606v5nevBgaliIlV7nUpVMsDnoBGV/cbSLNjZAg9q0Cfd/+easKVKQ8vOu8fn1Q==", + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.6.0.tgz", + "integrity": "sha512-mw7JQNu5ExIkcw4LPih0owX/TZXjD/ZUF/ZQ/pDnkw3ZKhDcZZw5klmBlj6gVMwjQ3Pz5Jgu7F3d0jcDVuEWdw==", "requires": { "path-parse": "^1.0.5" } }, "resolve-from": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-1.0.1.tgz", - "integrity": "sha1-Jsv+k10a7uq7Kbw/5a6wHpPUQiY=", + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-4.0.0.tgz", + "integrity": "sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==", "dev": true }, + "resolve-url": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/resolve-url/-/resolve-url-0.2.1.tgz", + "integrity": "sha1-LGN/53yJOv0qZj/iGqkIAGjiBSo=" + }, "restore-cursor": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-2.0.0.tgz", @@ -3217,27 +3649,36 @@ "signal-exit": "^3.0.2" } }, + "ret": { + "version": "0.1.15", + "resolved": "https://registry.npmjs.org/ret/-/ret-0.1.15.tgz", + "integrity": "sha512-TTlYpa+OL+vMMNG24xSlQGEJ3B/RzEfUlLct7b5G/ytav+wPrplCpVMFuwzXbkecJrb6IYo1iFb0S9v37754mg==" + }, "rimraf": { - "version": "2.6.2", - "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.6.2.tgz", - "integrity": "sha512-lreewLK/BlghmxtfH36YYVg1i8IAce4TI7oao75I1g245+6BctqTVQiBP3YUJ9C6DQOXJmkYR9X9fCLtCOJc5w==", + "version": "2.6.3", + "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.6.3.tgz", + "integrity": "sha512-mwqeW5XsA2qAejG46gYdENaxXjx9onRNCfn7L0duuP4hCuTIi/QO7PDK07KJfp1d+izWPrzEJDcSqBa0OZQriA==", "requires": { - "glob": "^7.0.5" + "glob": "^7.1.3" } }, "ripemd160": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/ripemd160/-/ripemd160-2.0.1.tgz", - "integrity": "sha1-D0WEKVxTo2KK9+bXmsohzlfRxuc=", + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/ripemd160/-/ripemd160-2.0.2.tgz", + "integrity": "sha512-ii4iagi25WusVoiC4B4lq7pbXfAp3D9v5CwfkY33vffw2+pkDjY1D8GaN7spsxvCSx8dkPqOZCEZyfxcmJG2IA==", "requires": { - "hash-base": "^2.0.0", + "hash-base": "^3.0.0", "inherits": "^2.0.1" } }, "rlp": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/rlp/-/rlp-2.0.0.tgz", - "integrity": "sha1-nbOE/0uJqPYVY9kjldhiWxjzr7A=" + "version": "2.2.2", + "resolved": "https://registry.npmjs.org/rlp/-/rlp-2.2.2.tgz", + "integrity": "sha512-Ng2kJEN731Sfv4ZAY2i0ytPMc0BbJKBsVNl0QZY8LxOWSwd+1xpg+fpSRfaMn0heHU447s6Kgy8qfHZR0XTyVw==", + "requires": { + "bn.js": "^4.11.1", + "safe-buffer": "^5.1.1" + } }, "run-async": { "version": "2.3.0", @@ -3249,24 +3690,31 @@ } }, "rxjs": { - "version": "6.3.2", - "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-6.3.2.tgz", - "integrity": "sha512-hV7criqbR0pe7EeL3O66UYVg92IR0XsA97+9y+BWTePK9SKmEI5Qd3Zj6uPnGkNzXsBywBQWTvujPl+1Kn9Zjw==", + "version": "6.4.0", + "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-6.4.0.tgz", + "integrity": "sha512-Z9Yfa11F6B9Sg/BK9MnqnQ+aQYicPLtilXBp2yUtDt2JRCE0h26d33EnfO3ZxoNxG0T92OUucP3Ct7cpfkdFfw==", "dev": true, "requires": { "tslib": "^1.9.0" } }, "safe-buffer": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz", - "integrity": "sha512-kKvNJn6Mm93gAczWVJg7wH+wGYWNrDHdWvpUmHyEsgCtIwwo3bqPtV4tR5tuPaUhTOo/kvhVwd8XwwOllGYkbg==" + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", + "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==" + }, + "safe-regex": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/safe-regex/-/safe-regex-1.1.0.tgz", + "integrity": "sha1-QKNmnzsHfR6UPURinhV91IAjvy4=", + "requires": { + "ret": "~0.1.10" + } }, "safer-buffer": { "version": "2.1.2", "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", - "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==", - "dev": true + "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==" }, "scrypt": { "version": "6.0.3", @@ -3294,9 +3742,9 @@ } }, "secp256k1": { - "version": "3.5.0", - "resolved": "https://registry.npmjs.org/secp256k1/-/secp256k1-3.5.0.tgz", - "integrity": "sha512-e5QIJl8W7Y4tT6LHffVcZAxJjvpgE5Owawv6/XCYPQljE9aP2NFFddQ8OYMKhdLshNu88FfL3qCN3/xYkXGRsA==", + "version": "3.6.2", + "resolved": "https://registry.npmjs.org/secp256k1/-/secp256k1-3.6.2.tgz", + "integrity": "sha512-90nYt7yb0LmI4A2jJs1grglkTAXrBwxYAjP9bpeKjvJKOjG2fOeH/YI/lchDMIvjrOasd5QXwvV2jwN168xNng==", "requires": { "bindings": "^1.2.1", "bip66": "^1.1.3", @@ -3317,9 +3765,9 @@ } }, "semver": { - "version": "5.4.1", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.4.1.tgz", - "integrity": "sha512-WfG/X9+oATh81XtllIo/I8gOiY9EXRdv1cQdyykeXK17YcUW3EXUAi2To4pcH6nZtJPr7ZOpM5OMyWJZm+8Rsg==" + "version": "5.6.0", + "resolved": "https://registry.npmjs.org/semver/-/semver-5.6.0.tgz", + "integrity": "sha512-RS9R6R35NYgQn++fkDWaOmqGoj4Ek9gGs+DPxNUZKuwE183xjJroKvyo1IzVFeXvUrvmALy6FWD5xrdJT25gMg==" }, "send": { "version": "0.16.2", @@ -3371,15 +3819,36 @@ "xhr": "^2.3.3" } }, + "set-value": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/set-value/-/set-value-2.0.0.tgz", + "integrity": "sha512-hw0yxk9GT/Hr5yJEYnHNKYXkIA8mVJgd9ditYZCe16ZczcaELYYcfvaXesNACk2O8O0nTiPQcQhGUQj8JLzeeg==", + "requires": { + "extend-shallow": "^2.0.1", + "is-extendable": "^0.1.1", + "is-plain-object": "^2.0.3", + "split-string": "^3.0.1" + }, + "dependencies": { + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "requires": { + "is-extendable": "^0.1.0" + } + } + } + }, "setimmediate": { "version": "1.0.5", "resolved": "https://registry.npmjs.org/setimmediate/-/setimmediate-1.0.5.tgz", "integrity": "sha1-KQy7Iy4waULX1+qbg3Mqt4VvgoU=" }, "setprototypeof": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.0.3.tgz", - "integrity": "sha1-ZlZ+NwQ+608E2RvWWMDL77VbjgQ=" + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.1.0.tgz", + "integrity": "sha512-BvE/TwpZX4FXExxOxZyRGQQv651MSwmWKZGqvmPcRIjDqWub67kTKuIMx43cZZrS/cBBzwBcNDWoFxt2XEFIpQ==" }, "sha.js": { "version": "2.4.11", @@ -3391,11 +3860,18 @@ } }, "sha3": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/sha3/-/sha3-1.2.0.tgz", - "integrity": "sha1-aYnxtwpJhwWHajc+LGKs6WqpOZo=", + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/sha3/-/sha3-1.2.2.tgz", + "integrity": "sha1-pmxQmN5MJbyIM27ItIF9AFvKe6k=", "requires": { - "nan": "^2.0.5" + "nan": "2.10.0" + }, + "dependencies": { + "nan": { + "version": "2.10.0", + "resolved": "https://registry.npmjs.org/nan/-/nan-2.10.0.tgz", + "integrity": "sha512-bAdJv7fBLhWC+/Bls0Oza+mvTaNQtP+1RyhhhvD95pgUJz6XM5IzgmxOkItJ9tkoCiplvAnXI1tNmmUD/eScyA==" + } } }, "shebang-command": { @@ -3419,56 +3895,166 @@ "integrity": "sha1-tf3AjxKH6hF4Yo5BXiUTK3NkbG0=", "dev": true }, - "simple-bufferstream": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/simple-bufferstream/-/simple-bufferstream-1.0.0.tgz", - "integrity": "sha1-XKsQ6FGqccZnt3th/hux2QpguqQ=" - }, "simple-concat": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/simple-concat/-/simple-concat-1.0.0.tgz", "integrity": "sha1-c0TLuLbib7J9ZrL8hvn21Zl1IcY=" }, "simple-get": { - "version": "2.7.0", - "resolved": "https://registry.npmjs.org/simple-get/-/simple-get-2.7.0.tgz", - "integrity": "sha512-RkE9rGPHcxYZ/baYmgJtOSM63vH0Vyq+ma5TijBcLla41SWlh8t6XYIGMR/oeZcmr+/G8k+zrClkkVrtnQ0esg==", + "version": "2.8.1", + "resolved": "https://registry.npmjs.org/simple-get/-/simple-get-2.8.1.tgz", + "integrity": "sha512-lSSHRSw3mQNUGPAYRqo7xy9dhKmxFXIjLjp4KHpf99GEH2VH7C3AM+Qfx6du6jhfUi6Vm7XnbEVEf7Wb6N8jRw==", "requires": { "decompress-response": "^3.3.0", "once": "^1.3.1", "simple-concat": "^1.0.0" } }, - "slice-ansi": { + "slash": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/slice-ansi/-/slice-ansi-1.0.0.tgz", - "integrity": "sha512-POqxBK6Lb3q6s047D/XsDVNPnF9Dl8JSaqe9h9lURl0OdNqy/ujDrOiIHtsqXMGbWWTIomRzAMaTyawAU//Reg==", + "resolved": "https://registry.npmjs.org/slash/-/slash-1.0.0.tgz", + "integrity": "sha1-xB8vbDn8FtHNF61LXYlhFK5HDVU=" + }, + "slice-ansi": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/slice-ansi/-/slice-ansi-2.1.0.tgz", + "integrity": "sha512-Qu+VC3EwYLldKa1fCxuuvULvSJOKEgk9pi8dZeCVK7TqBfUNTH4sFkk4joj8afVSfAYgJoSOetjx9QWOJ5mYoQ==", "dev": true, "requires": { + "ansi-styles": "^3.2.0", + "astral-regex": "^1.0.0", "is-fullwidth-code-point": "^2.0.0" } }, - "sntp": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/sntp/-/sntp-2.1.0.tgz", - "integrity": "sha512-FL1b58BDrqS3A11lJ0zEdnJ3UOKqVxawAkF3k7F0CVN7VQ34aZrV+G8BZ1WC9ZL7NyrwsW0oviwsWDgRuVYtJg==", + "snapdragon": { + "version": "0.8.2", + "resolved": "https://registry.npmjs.org/snapdragon/-/snapdragon-0.8.2.tgz", + "integrity": "sha512-FtyOnWN/wCHTVXOMwvSv26d+ko5vWlIDD6zoUJ7LW8vh+ZBC8QdljveRP+crNrtBwioEUWy/4dMtbBjA4ioNlg==", + "requires": { + "base": "^0.11.1", + "debug": "^2.2.0", + "define-property": "^0.2.5", + "extend-shallow": "^2.0.1", + "map-cache": "^0.2.2", + "source-map": "^0.5.6", + "source-map-resolve": "^0.5.0", + "use": "^3.1.0" + }, + "dependencies": { + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "requires": { + "is-descriptor": "^0.1.0" + } + }, + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "requires": { + "is-extendable": "^0.1.0" + } + }, + "source-map": { + "version": "0.5.7", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", + "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=" + } + } + }, + "snapdragon-node": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/snapdragon-node/-/snapdragon-node-2.1.1.tgz", + "integrity": "sha512-O27l4xaMYt/RSQ5TR3vpWCAB5Kb/czIcqUFOM/C4fYcLnbZUc1PkjTAMjof2pBWaSTwOUd6qUHcFGVGj7aIwnw==", + "requires": { + "define-property": "^1.0.0", + "isobject": "^3.0.0", + "snapdragon-util": "^3.0.1" + }, + "dependencies": { + "define-property": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-1.0.0.tgz", + "integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=", + "requires": { + "is-descriptor": "^1.0.0" + } + }, + "is-accessor-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz", + "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-data-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz", + "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-descriptor": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz", + "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", + "requires": { + "is-accessor-descriptor": "^1.0.0", + "is-data-descriptor": "^1.0.0", + "kind-of": "^6.0.2" + } + } + } + }, + "snapdragon-util": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/snapdragon-util/-/snapdragon-util-3.0.1.tgz", + "integrity": "sha512-mbKkMdQKsjX4BAL4bRYTj21edOf8cN7XHdYUJEe+Zn99hVEYcMvKPct1IqNe7+AZPirn8BCDOQBHQZknqmKlZQ==", "requires": { - "hoek": "4.x.x" + "kind-of": "^3.2.0" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "requires": { + "is-buffer": "^1.1.5" + } + } } }, "source-map": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.2.0.tgz", - "integrity": "sha1-2rc/vPwrqBm03gO9b26qSBZLP50=", - "optional": true, + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", + "optional": true + }, + "source-map-resolve": { + "version": "0.5.2", + "resolved": "https://registry.npmjs.org/source-map-resolve/-/source-map-resolve-0.5.2.tgz", + "integrity": "sha512-MjqsvNwyz1s0k81Goz/9vRBe9SZdB09Bdw+/zYyO+3CuPk6fouTaxscHkgtE8jKvf01kVfl8riHzERQ/kefaSA==", "requires": { - "amdefine": ">=0.0.4" + "atob": "^2.1.1", + "decode-uri-component": "^0.2.0", + "resolve-url": "^0.2.1", + "source-map-url": "^0.4.0", + "urix": "^0.1.0" } }, + "source-map-url": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/source-map-url/-/source-map-url-0.4.0.tgz", + "integrity": "sha1-PpNdfd1zYxuXZZlW1VEo6HtQhKM=" + }, "spdx-correct": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/spdx-correct/-/spdx-correct-3.0.0.tgz", - "integrity": "sha512-N19o9z5cEyc8yQQPukRCZ9EUmb4HUpnrmaL/fxS2pBo2jbfcFRVuFZ/oFC+vZz0MNNk0h80iMn5/S6qGZOL5+g==", + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/spdx-correct/-/spdx-correct-3.1.0.tgz", + "integrity": "sha512-lr2EZCctC2BNR7j7WzJ2FpDznxky1sjfxvvYEyzxNyb6lZXHODmEoJeFu4JupYlkfha1KZpJyoqiJ7pgA1qq8Q==", "dev": true, "requires": { "spdx-expression-parse": "^3.0.0", @@ -3476,9 +4062,9 @@ } }, "spdx-exceptions": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/spdx-exceptions/-/spdx-exceptions-2.1.0.tgz", - "integrity": "sha512-4K1NsmrlCU1JJgUrtgEeTVyfx8VaYea9J9LvARxhbHtVtohPs/gFGG5yy49beySjlIMhhXZ4QqujIZEfS4l6Cg==", + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/spdx-exceptions/-/spdx-exceptions-2.2.0.tgz", + "integrity": "sha512-2XQACfElKi9SlVb1CYadKDXvoajPgBVPn/gOQLrTvHdElaVhr7ZEbqJaRnJLVNeaI4cMEAgVCeBMKF6MWRDCRA==", "dev": true }, "spdx-expression-parse": { @@ -3492,11 +4078,19 @@ } }, "spdx-license-ids": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/spdx-license-ids/-/spdx-license-ids-3.0.1.tgz", - "integrity": "sha512-TfOfPcYGBB5sDuPn3deByxPhmfegAhpDYKSOXZQN81Oyrrif8ZCodOLzK3AesELnCx03kikhyDwh0pfvvQvF8w==", + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/spdx-license-ids/-/spdx-license-ids-3.0.3.tgz", + "integrity": "sha512-uBIcIl3Ih6Phe3XHK1NqboJLdGfwr1UN3k6wSD1dZpmPsIkb8AGNbZYJ1fOBk834+Gxy8rpfDxrS6XLEMZMY2g==", "dev": true }, + "split-string": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/split-string/-/split-string-3.1.0.tgz", + "integrity": "sha512-NzNVhJDYpwceVVii8/Hu6DKfD2G+NrQHlS/V/qgv763EYudVwEcMQNxd2lh+0VrUByXN/oJkl5grOhYWvQUYiw==", + "requires": { + "extend-shallow": "^3.0.0" + } + }, "sprintf-js": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz", @@ -3504,9 +4098,9 @@ "dev": true }, "sshpk": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/sshpk/-/sshpk-1.14.1.tgz", - "integrity": "sha1-Ew9Zde3a2WPx1W+SuaxsUfqfg+s=", + "version": "1.16.1", + "resolved": "https://registry.npmjs.org/sshpk/-/sshpk-1.16.1.tgz", + "integrity": "sha512-HXXqVUq7+pcKeLqqZj6mHFUMvXtOJt1uoUx09pFW6011inTMxqI8BA8PM95myrIyyKwdnzjdFjLiE6KBPVtJIg==", "requires": { "asn1": "~0.2.3", "assert-plus": "^1.0.0", @@ -3515,9 +4109,29 @@ "ecc-jsbn": "~0.1.1", "getpass": "^0.1.1", "jsbn": "~0.1.0", + "safer-buffer": "^2.0.2", "tweetnacl": "~0.14.0" } }, + "static-extend": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/static-extend/-/static-extend-0.1.2.tgz", + "integrity": "sha1-YICcOcv/VTNyJv1eC1IPNB8ftcY=", + "requires": { + "define-property": "^0.2.5", + "object-copy": "^0.1.0" + }, + "dependencies": { + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "requires": { + "is-descriptor": "^0.1.0" + } + } + } + }, "statuses": { "version": "1.5.0", "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.5.0.tgz", @@ -3547,18 +4161,13 @@ } }, "string_decoder": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "integrity": "sha512-4AH6Z5fzNNBcH+6XDMfA/BTt87skxqJlO0lAh3Dker5zThcAxG6mKz+iGu308UKoPPQ8Dcqx/4JhujzltRa+hQ==", + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", + "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", "requires": { "safe-buffer": "~5.1.0" } }, - "stringstream": { - "version": "0.0.5", - "resolved": "https://registry.npmjs.org/stringstream/-/stringstream-0.0.5.tgz", - "integrity": "sha1-TkhM1N5aC7vuGORjB3EKioFiGHg=" - }, "strip-ansi": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", @@ -3597,11 +4206,11 @@ "dev": true }, "supports-color": { - "version": "4.5.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-4.5.0.tgz", - "integrity": "sha1-vnoN5ITexcXN34s9WRJQRJEvY1s=", + "version": "5.5.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", + "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", "requires": { - "has-flag": "^2.0.0" + "has-flag": "^3.0.0" } }, "swarm-js": { @@ -3622,45 +4231,64 @@ "setimmediate": "^1.0.5", "tar.gz": "^1.0.5", "xhr-request-promise": "^0.1.2" + }, + "dependencies": { + "fs-extra": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-2.1.2.tgz", + "integrity": "sha1-BGxwFjzvmq1GsOSn+kZ/si1x3jU=", + "requires": { + "graceful-fs": "^4.1.2", + "jsonfile": "^2.1.0" + } + }, + "jsonfile": { + "version": "2.4.0", + "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-2.4.0.tgz", + "integrity": "sha1-NzaitCi4e72gzIO1P6PWM6NcKug=", + "requires": { + "graceful-fs": "^4.1.6" + } + } } }, "table": { - "version": "4.0.3", - "resolved": "http://registry.npmjs.org/table/-/table-4.0.3.tgz", - "integrity": "sha512-S7rnFITmBH1EnyKcvxBh1LjYeQMmnZtCXSEbHcH6S0NoKit24ZuFO/T1vDcLdYsLQkM188PVVhQmzKIuThNkKg==", + "version": "5.2.3", + "resolved": "https://registry.npmjs.org/table/-/table-5.2.3.tgz", + "integrity": "sha512-N2RsDAMvDLvYwFcwbPyF3VmVSSkuF+G1e+8inhBLtHpvwXGw4QRPEZhihQNeEN0i1up6/f6ObCJXNdlRG3YVyQ==", "dev": true, "requires": { - "ajv": "^6.0.1", - "ajv-keywords": "^3.0.0", - "chalk": "^2.1.0", - "lodash": "^4.17.4", - "slice-ansi": "1.0.0", - "string-width": "^2.1.1" + "ajv": "^6.9.1", + "lodash": "^4.17.11", + "slice-ansi": "^2.1.0", + "string-width": "^3.0.0" }, "dependencies": { - "ajv": { - "version": "6.5.3", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.5.3.tgz", - "integrity": "sha512-LqZ9wY+fx3UMiiPd741yB2pj3hhil+hQc8taf4o2QGRFpWgZ2V5C8HA165DY9sS3fJwsk7uT7ZlFEyC3Ig3lLg==", + "ansi-regex": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-4.0.0.tgz", + "integrity": "sha512-iB5Dda8t/UqpPI/IjsejXu5jOGDrzn41wJyljwPH65VCIbk6+1BzFIMJGFwTNrYXT1CrD+B4l19U7awiQ8rk7w==", + "dev": true + }, + "string-width": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-3.0.0.tgz", + "integrity": "sha512-rr8CUxBbvOZDUvc5lNIJ+OC1nPVpz+Siw9VBtUjB9b6jZehZLFt0JMCZzShFHIsI8cbhm0EsNIfWJMFV3cu3Ew==", "dev": true, "requires": { - "fast-deep-equal": "^2.0.1", - "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.4.1", - "uri-js": "^4.2.2" + "emoji-regex": "^7.0.1", + "is-fullwidth-code-point": "^2.0.0", + "strip-ansi": "^5.0.0" } }, - "fast-deep-equal": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-2.0.1.tgz", - "integrity": "sha1-ewUhjd+WZ79/Nwv3/bLLFf3Qqkk=", - "dev": true - }, - "json-schema-traverse": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", - "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", - "dev": true + "strip-ansi": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-5.0.0.tgz", + "integrity": "sha512-Uu7gQyZI7J7gn5qLn1Np3G9vcYGTVqB+lFTytnDJv83dd8T22aGH451P3jueT2/QemInJDfxHB5Tde5OzgG1Ow==", + "dev": true, + "requires": { + "ansi-regex": "^4.0.0" + } } } }, @@ -3675,13 +4303,16 @@ } }, "tar-stream": { - "version": "1.5.5", - "resolved": "https://registry.npmjs.org/tar-stream/-/tar-stream-1.5.5.tgz", - "integrity": "sha512-mQdgLPc/Vjfr3VWqWbfxW8yQNiJCbAZ+Gf6GDu1Cy0bdb33ofyiNGBtAY96jHFhDuivCwgW1H9DgTON+INiXgg==", + "version": "1.6.2", + "resolved": "https://registry.npmjs.org/tar-stream/-/tar-stream-1.6.2.tgz", + "integrity": "sha512-rzS0heiNf8Xn7/mpdSVVSMAWAoy9bfb1WOTYC78Z0UQKeKa/CWS8FOq0lKGNa8DWKAn9gxjCvMLYc5PGXYlK2A==", "requires": { "bl": "^1.0.0", + "buffer-alloc": "^1.2.0", "end-of-stream": "^1.0.0", - "readable-stream": "^2.0.0", + "fs-constants": "^1.0.0", + "readable-stream": "^2.3.0", + "to-buffer": "^1.1.1", "xtend": "^4.0.0" } }, @@ -3750,12 +4381,63 @@ "os-tmpdir": "~1.0.2" } }, + "to-buffer": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/to-buffer/-/to-buffer-1.1.1.tgz", + "integrity": "sha512-lx9B5iv7msuFYE3dytT+KE5tap+rNYw+K4jVkb9R/asAb+pbBSM17jtunHplhBe6RRJdZx3Pn2Jph24O32mOVg==" + }, + "to-object-path": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/to-object-path/-/to-object-path-0.3.0.tgz", + "integrity": "sha1-KXWIt7Dn4KwI4E5nL4XB9JmeF68=", + "requires": { + "kind-of": "^3.0.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "requires": { + "is-buffer": "^1.1.5" + } + } + } + }, + "to-regex": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/to-regex/-/to-regex-3.0.2.tgz", + "integrity": "sha512-FWtleNAtZ/Ki2qtqej2CXTOayOH9bHDQF+Q48VpWyDXjbYxA4Yz8iDB31zXOBUlOHHKidDbqGVrTUvQMPmBGBw==", + "requires": { + "define-property": "^2.0.2", + "extend-shallow": "^3.0.2", + "regex-not": "^1.0.2", + "safe-regex": "^1.1.0" + } + }, + "to-regex-range": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-2.1.1.tgz", + "integrity": "sha1-fIDBe53+vlmeJzZ+DU3VWQFB2zg=", + "requires": { + "is-number": "^3.0.0", + "repeat-string": "^1.6.1" + } + }, "tough-cookie": { - "version": "2.3.4", - "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.3.4.tgz", - "integrity": "sha512-TZ6TTfI5NtZnuyy/Kecv+CnoROnyXn2DN97LontgQpCwsX2XyLYCC0ENhYkehSOwAp8rTQKc/NUIF7BkQ5rKLA==", + "version": "2.4.3", + "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.4.3.tgz", + "integrity": "sha512-Q5srk/4vDM54WJsJio3XNn6K2sCG+CQ8G5Wz6bZhRZoAe/+TxjWB/GlFAnYEbkYVlON9FMk/fE3h2RLpPXo4lQ==", "requires": { + "psl": "^1.1.24", "punycode": "^1.4.1" + }, + "dependencies": { + "punycode": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/punycode/-/punycode-1.4.1.tgz", + "integrity": "sha1-wNWmOycYgArY4esPpSachN1BhF4=" + } } }, "trim": { @@ -3780,8 +4462,7 @@ "tweetnacl": { "version": "0.14.5", "resolved": "https://registry.npmjs.org/tweetnacl/-/tweetnacl-0.14.5.tgz", - "integrity": "sha1-WuaBd/GS1EViadEIr6k/+HQ/T2Q=", - "optional": true + "integrity": "sha1-WuaBd/GS1EViadEIr6k/+HQ/T2Q=" }, "type-check": { "version": "0.3.2", @@ -3819,36 +4500,51 @@ "integrity": "sha512-UIEXBNeYmKptWH6z8ZnqTeS8fV74zG0/eRU9VGkpzz+LIJNs8W/zM/L+7ctCkRrgbNnnR0xxw4bKOr0cW0N0Og==" }, "unbzip2-stream": { - "version": "1.2.5", - "resolved": "https://registry.npmjs.org/unbzip2-stream/-/unbzip2-stream-1.2.5.tgz", - "integrity": "sha512-izD3jxT8xkzwtXRUZjtmRwKnZoeECrfZ8ra/ketwOcusbZEp4mjULMnJOCfTDZBgGQAAY1AJ/IgxcwkavcX9Og==", + "version": "1.3.3", + "resolved": "https://registry.npmjs.org/unbzip2-stream/-/unbzip2-stream-1.3.3.tgz", + "integrity": "sha512-fUlAF7U9Ah1Q6EieQ4x4zLNejrRvDWUYmxXUpN3uziFYCHapjWFaCAnreY9bGgxzaMCFAPPpYNng57CypwJVhg==", "requires": { - "buffer": "^3.0.1", - "through": "^2.3.6" + "buffer": "^5.2.1", + "through": "^2.3.8" + } + }, + "underscore": { + "version": "1.8.3", + "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", + "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=" + }, + "union-value": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/union-value/-/union-value-1.0.0.tgz", + "integrity": "sha1-XHHDTLW61dzr4+oM0IIHulqhrqQ=", + "requires": { + "arr-union": "^3.1.0", + "get-value": "^2.0.6", + "is-extendable": "^0.1.1", + "set-value": "^0.4.3" }, "dependencies": { - "base64-js": { - "version": "0.0.8", - "resolved": "https://registry.npmjs.org/base64-js/-/base64-js-0.0.8.tgz", - "integrity": "sha1-EQHpVE9KdrG8OybUUsqW16NeeXg=" + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "requires": { + "is-extendable": "^0.1.0" + } }, - "buffer": { - "version": "3.6.0", - "resolved": "https://registry.npmjs.org/buffer/-/buffer-3.6.0.tgz", - "integrity": "sha1-pyyTb3e5a/UvX357RnGAYoVR3vs=", + "set-value": { + "version": "0.4.3", + "resolved": "https://registry.npmjs.org/set-value/-/set-value-0.4.3.tgz", + "integrity": "sha1-fbCPnT0i3H945Trzw79GZuzfzPE=", "requires": { - "base64-js": "0.0.8", - "ieee754": "^1.1.4", - "isarray": "^1.0.0" + "extend-shallow": "^2.0.1", + "is-extendable": "^0.1.1", + "is-plain-object": "^2.0.1", + "to-object-path": "^0.3.0" } } } }, - "underscore": { - "version": "1.8.3", - "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", - "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=" - }, "unique-temp-dir": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/unique-temp-dir/-/unique-temp-dir-1.0.0.tgz", @@ -3860,32 +4556,64 @@ } }, "universalify": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/universalify/-/universalify-0.1.1.tgz", - "integrity": "sha1-+nG63UQ3r0wUiEHjs7Fl+enlkLc=" + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/universalify/-/universalify-0.1.2.tgz", + "integrity": "sha512-rBJeI5CXAlmy1pV+617WB9J63U6XcazHHF2f2dbJix4XzpUF0RS3Zbj0FGIOCAva5P/d/GBOYaACQ1w+0azUkg==" }, "unpipe": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/unpipe/-/unpipe-1.0.0.tgz", "integrity": "sha1-sr9O6FFKrmFltIF4KdIbLvSZBOw=" }, + "unset-value": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/unset-value/-/unset-value-1.0.0.tgz", + "integrity": "sha1-g3aHP30jNRef+x5vw6jtDfyKtVk=", + "requires": { + "has-value": "^0.3.1", + "isobject": "^3.0.0" + }, + "dependencies": { + "has-value": { + "version": "0.3.1", + "resolved": "https://registry.npmjs.org/has-value/-/has-value-0.3.1.tgz", + "integrity": "sha1-ex9YutpiyoJ+wKIHgCVlSEWZXh8=", + "requires": { + "get-value": "^2.0.3", + "has-values": "^0.1.4", + "isobject": "^2.0.0" + }, + "dependencies": { + "isobject": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/isobject/-/isobject-2.1.0.tgz", + "integrity": "sha1-8GVWEJaj8dou9GJy+BXIQNh+DIk=", + "requires": { + "isarray": "1.0.0" + } + } + } + }, + "has-values": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/has-values/-/has-values-0.1.4.tgz", + "integrity": "sha1-bWHeldkd/Km5oCCJrThL/49it3E=" + } + } + }, "uri-js": { "version": "4.2.2", "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.2.2.tgz", "integrity": "sha512-KY9Frmirql91X2Qgjry0Wd4Y+YTdrdZheS8TFwvkbLWf/G5KNJDCh6pKL5OZctEW4+0Baa5idK2ZQuELRwPznQ==", - "dev": true, "requires": { "punycode": "^2.1.0" - }, - "dependencies": { - "punycode": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.1.1.tgz", - "integrity": "sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A==", - "dev": true - } } }, + "urix": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/urix/-/urix-0.1.0.tgz", + "integrity": "sha1-2pN/emLiH+wf0Y1Js1wpNQZ6bHI=" + }, "url-parse-lax": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/url-parse-lax/-/url-parse-lax-1.0.0.tgz", @@ -3904,6 +4632,11 @@ "resolved": "https://registry.npmjs.org/url-to-options/-/url-to-options-1.0.1.tgz", "integrity": "sha1-FQWgOiiaSMvXpDTvuu7FBV9WM6k=" }, + "use": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/use/-/use-3.1.1.tgz", + "integrity": "sha512-cwESVXlO3url9YWlFW/TA9cshCEhtu7IKJ/p5soJ/gGpj7vbvFrAY/eIioQ6Dw23KjZhYgiIo8HOs1nQ2vr/oQ==" + }, "utf8": { "version": "2.1.1", "resolved": "https://registry.npmjs.org/utf8/-/utf8-2.1.1.tgz", @@ -3920,9 +4653,9 @@ "integrity": "sha1-n5VxD1CiZ5R7LMwSR0HBAoQn5xM=" }, "uuid": { - "version": "3.2.1", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.2.1.tgz", - "integrity": "sha512-jZnMwlb9Iku/O3smGWvZhauCf6cvvpKi4BKRiliS3cxnI+Gz9j5MEpTz2UFuXiKPJocb7gnsLHwiS05ige5BEA==" + "version": "3.3.2", + "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.3.2.tgz", + "integrity": "sha512-yXJmeNaw3DnnKAOKJE51sL/ZaYfWJRl1pK9dr19YFCu0ObS231AB1/LbqTKRAQ5kw8A90rA6fr4riOUpTZvQZA==" }, "validate-npm-package-license": { "version": "3.0.4", @@ -3935,9 +4668,9 @@ } }, "validator": { - "version": "9.4.1", - "resolved": "http://registry.npmjs.org/validator/-/validator-9.4.1.tgz", - "integrity": "sha512-YV5KjzvRmSyJ1ee/Dm5UED0G+1L4GZnLN3w6/T+zZm8scVua4sOhYKWTUrKa0H/tMiJyO9QLHMPN+9mB/aMunA==" + "version": "10.11.0", + "resolved": "https://registry.npmjs.org/validator/-/validator-10.11.0.tgz", + "integrity": "sha512-X/p3UZerAIsbBfN/IwahhYaBbY68EN/UQBWHtsbXGT5bfrH/p4NQzUCG1kF/rtKaNpnJ7jAu6NGTdSNtyNIXMw==" }, "vary": { "version": "1.1.2", @@ -4192,7 +4925,7 @@ "requires": { "underscore": "1.8.3", "web3-core-helpers": "1.0.0-beta.33", - "websocket": "git://github.com/frozeman/WebSocket-Node.git#7004c39c42ac98875ab61126e5b4a925430f592c" + "websocket": "git://github.com/frozeman/WebSocket-Node.git#6c72925e3f8aaaea8dc8450f97627e85263999f2" } }, "web3-shh": { @@ -4228,8 +4961,8 @@ } }, "websocket": { - "version": "git://github.com/frozeman/WebSocket-Node.git#7004c39c42ac98875ab61126e5b4a925430f592c", - "from": "websocket@git://github.com/frozeman/WebSocket-Node.git#7004c39c42ac98875ab61126e5b4a925430f592c", + "version": "git://github.com/frozeman/WebSocket-Node.git#6c72925e3f8aaaea8dc8450f97627e85263999f2", + "from": "git://github.com/frozeman/WebSocket-Node.git#browserifyCompatible", "requires": { "debug": "^2.2.0", "nan": "^2.3.3", @@ -4257,9 +4990,9 @@ "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=" }, "write": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/write/-/write-0.2.1.tgz", - "integrity": "sha1-X8A4KOJkzqP+kUVUdvejxWbLB1c=", + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/write/-/write-1.0.3.tgz", + "integrity": "sha512-/lg70HAjtkUgWPVZhZcm+T4hkL8Zbtp1nFNOn3lRrxnlv50SRBv7cR7RqR+GMsd3hUXy9hWBo4CHTbFTcOYwig==", "dev": true, "requires": { "mkdirp": "^0.5.1" @@ -4276,9 +5009,9 @@ } }, "xhr": { - "version": "2.4.1", - "resolved": "https://registry.npmjs.org/xhr/-/xhr-2.4.1.tgz", - "integrity": "sha512-pAIU5vBr9Hiy5cpFIbPnwf0C18ZF86DBsZKrlsf87N5De/JbA6RJ83UP/cv+aljl4S40iRVMqP4pr4sF9Dnj0A==", + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/xhr/-/xhr-2.5.0.tgz", + "integrity": "sha512-4nlO/14t3BNUZRXIXfXe+3N6w3s1KoxcJUUURctd64BLRe67E4gRwp4PjywtDY72fXpZ1y6Ch0VZQRY/gMPzzQ==", "requires": { "global": "~4.3.0", "is-function": "^1.0.1", @@ -4324,13 +5057,13 @@ "integrity": "sha1-8m9ITXJoTPQr7ft2lwqhYI+/lXc=" }, "yauzl": { - "version": "2.9.1", - "resolved": "https://registry.npmjs.org/yauzl/-/yauzl-2.9.1.tgz", - "integrity": "sha1-qBmB6nCleUYTOIPwKcWCGok1mn8=", + "version": "2.10.0", + "resolved": "https://registry.npmjs.org/yauzl/-/yauzl-2.10.0.tgz", + "integrity": "sha1-x+sXyT4RLLEIb6bY5R+wZnt5pfk=", "requires": { "buffer-crc32": "~0.2.3", - "fd-slicer": "~1.0.1" + "fd-slicer": "~1.1.0" } } } -} \ No newline at end of file +} diff --git a/deploy/src/factories/foreign.js b/deploy/src/factories/foreign.js deleted file mode 100644 index 1ffc2b771..000000000 --- a/deploy/src/factories/foreign.js +++ /dev/null @@ -1,246 +0,0 @@ -const assert = require('assert') -const Web3Utils = require('web3-utils') -const env = require('../loadEnv') - -const { deployContract, privateKeyToAddress, sendRawTxForeign } = require('../deploymentUtils') -const { web3Foreign, deploymentPrivateKey, FOREIGN_RPC_URL } = require('../web3') - -const EternalStorageProxy = require('../../../build/contracts/EternalStorageProxy.json') -const ForeignBridgeFactory = require('../../../build/contracts/ForeignBridgeFactory.json') -const BridgeValidators = require('../../../build/contracts/BridgeValidators.json') -const ForeignBridge = require('../../../build/contracts/ForeignBridgeErcToErc.json') - -const VALIDATORS = env.VALIDATORS.split(' ') - -const { - DEPLOYMENT_ACCOUNT_PRIVATE_KEY, - REQUIRED_NUMBER_OF_VALIDATORS, - FOREIGN_VALIDATORS_OWNER, - FOREIGN_BRIDGE_OWNER, - FOREIGN_FACTORY_OWNER, - FOREIGN_UPGRADEABLE_ADMIN, - FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS, - FOREIGN_GAS_PRICE, - FOREIGN_MAX_AMOUNT_PER_TX, - HOME_DAILY_LIMIT, - HOME_MAX_AMOUNT_PER_TX, - DOUBLE_PROXY_IMPLEMENTATIONS -} = env - -let { - FOREIGN_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS, - FOREIGN_BRIDGE_IMPLEMENTATION_ADDRESS -} = env - -const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVATE_KEY) - -async function deployForeign() { - let foreignNonce = await web3Foreign.eth.getTransactionCount(DEPLOYMENT_ACCOUNT_ADDRESS) - console.log('========================================') - console.log('deploying ForeignBridgeFactory') - console.log('========================================\n') - - if (!FOREIGN_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS) { - console.log('deploying bridge validators implementation') - const bridgeValidatorsImplementationForeign = await deployContract(BridgeValidators, [], { - from: DEPLOYMENT_ACCOUNT_ADDRESS, - network: 'foreign', - nonce: foreignNonce - }) - foreignNonce++ - FOREIGN_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS = bridgeValidatorsImplementationForeign.options.address - - if (DOUBLE_PROXY_IMPLEMENTATIONS) { - console.log('deploying bridge validators proxy') - const implProxy = await deployContract(EternalStorageProxy, [], { - from: DEPLOYMENT_ACCOUNT_ADDRESS, - network: 'foreign', - nonce: foreignNonce - }) - foreignNonce++ - - console.log('\nhooking up eternal storage to implementation') - const upgradeToImpl = await implProxy.methods - .upgradeTo('1', FOREIGN_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txUpgradeToImpl = await sendRawTxForeign({ - data: upgradeToImpl, - nonce: foreignNonce, - to: implProxy.options.address, - privateKey: deploymentPrivateKey, - url: FOREIGN_RPC_URL - }) - assert.equal(Web3Utils.hexToNumber(txUpgradeToImpl.status), 1, 'Transaction Failed') - foreignNonce++ - FOREIGN_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS = implProxy.options.address - - console.log('\nTransferring ownership of Proxy\n') - const ownershipData = await implProxy.methods - .transferProxyOwnership(FOREIGN_UPGRADEABLE_ADMIN) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txOwnershipData = await sendRawTxForeign({ - data: ownershipData, - nonce: foreignNonce, - to: implProxy.options.address, - privateKey: deploymentPrivateKey, - url: FOREIGN_RPC_URL - }) - assert.equal(Web3Utils.hexToNumber(txOwnershipData.status), 1, 'Transaction Failed') - foreignNonce++ - } - } - console.log('[Foreign] bridge validators implementation address: ', FOREIGN_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS) - - if (!FOREIGN_BRIDGE_IMPLEMENTATION_ADDRESS) { - console.log('deploying foreign bridge implementation') - const foreignBridgeImplementationForeign = await deployContract(ForeignBridge, [], { - from: DEPLOYMENT_ACCOUNT_ADDRESS, - network: 'foreign', - nonce: foreignNonce - }) - foreignNonce++ - FOREIGN_BRIDGE_IMPLEMENTATION_ADDRESS = foreignBridgeImplementationForeign.options.address - - if (DOUBLE_PROXY_IMPLEMENTATIONS) { - console.log('deploying foreign bridge proxy') - const implProxy = await deployContract(EternalStorageProxy, [], { - from: DEPLOYMENT_ACCOUNT_ADDRESS, - network: 'foreign', - nonce: foreignNonce - }) - foreignNonce++ - - console.log('\nhooking up eternal storage to implementation') - const upgradeToImpl = await implProxy.methods - .upgradeTo('1', FOREIGN_BRIDGE_IMPLEMENTATION_ADDRESS) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txUpgradeToImpl = await sendRawTxForeign({ - data: upgradeToImpl, - nonce: foreignNonce, - to: implProxy.options.address, - privateKey: deploymentPrivateKey, - url: FOREIGN_RPC_URL - }) - assert.equal(Web3Utils.hexToNumber(txUpgradeToImpl.status), 1, 'Transaction Failed') - foreignNonce++ - FOREIGN_BRIDGE_IMPLEMENTATION_ADDRESS = implProxy.options.address - - console.log('\nTransferring ownership of Proxy\n') - const ownershipData = await implProxy.methods - .transferProxyOwnership(FOREIGN_UPGRADEABLE_ADMIN) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txOwnershipData = await sendRawTxForeign({ - data: ownershipData, - nonce: foreignNonce, - to: implProxy.options.address, - privateKey: deploymentPrivateKey, - url: FOREIGN_RPC_URL - }) - assert.equal(Web3Utils.hexToNumber(txOwnershipData.status), 1, 'Transaction Failed') - foreignNonce++ - } - } - console.log('[Foreign] foreign bridge implementation address: ', FOREIGN_BRIDGE_IMPLEMENTATION_ADDRESS) - - console.log('deploying storage for foreign bridge factory') - const storageBridgeFactoryForeign = await deployContract(EternalStorageProxy, [], { - from: DEPLOYMENT_ACCOUNT_ADDRESS, - network: 'foreign', - nonce: foreignNonce - }) - foreignNonce++ - console.log('[Foreign] BridgeFactory Storage: ', storageBridgeFactoryForeign.options.address) - - console.log('\ndeploying implementation for foreign bridge factory') - const bridgeFactoryForeign = await deployContract(ForeignBridgeFactory, [], { - from: DEPLOYMENT_ACCOUNT_ADDRESS, - network: 'foreign', - nonce: foreignNonce - }) - foreignNonce++ - console.log( - '[Foreign] BridgeFactory Implementation: ', - bridgeFactoryForeign.options.address - ) - console.log('\nhooking up eternal storage to BridgeFactory') - const upgradeToForeignFactoryData = await storageBridgeFactoryForeign.methods - .upgradeTo('1', bridgeFactoryForeign.options.address) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txUpgradeToForeignFactory = await sendRawTxForeign({ - data: upgradeToForeignFactoryData, - nonce: foreignNonce, - to: storageBridgeFactoryForeign.options.address, - privateKey: deploymentPrivateKey, - url: FOREIGN_RPC_URL - }) - assert.equal(Web3Utils.hexToNumber(txUpgradeToForeignFactory.status), 1, 'Transaction Failed') - foreignNonce++ - - console.log('\ninitializing Foreign Bridge Factory with following parameters:\n') - console.log( - `FOREIGN_FACTORY_OWNER: ${FOREIGN_FACTORY_OWNER}, - FOREIGN_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS: ${FOREIGN_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS}, - REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, - VALIDATORS: ${VALIDATORS}, - FOREIGN_VALIDATORS_OWNER: ${FOREIGN_VALIDATORS_OWNER}, - FOREIGN_BRIDGE_IMPLEMENTATION_ADDRESS: ${FOREIGN_BRIDGE_IMPLEMENTATION_ADDRESS}, - FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS" ${FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS}, - FOREIGN_GAS_PRICE: ${FOREIGN_GAS_PRICE}, - FOREIGN_MAX_AMOUNT_PER_TX: ${FOREIGN_MAX_AMOUNT_PER_TX}, - HOME_DAILY_LIMIT: ${HOME_DAILY_LIMIT}, - HOME_MAX_AMOUNT_PER_TX: ${HOME_MAX_AMOUNT_PER_TX}, - FOREIGN_BRIDGE_OWNER: ${FOREIGN_BRIDGE_OWNER}, - FOREIGN_UPGRADEABLE_ADMIN: ${FOREIGN_UPGRADEABLE_ADMIN}` - ) - bridgeFactoryForeign.options.address = storageBridgeFactoryForeign.options.address - const initializeForeignData = await bridgeFactoryForeign.methods - .initialize( - FOREIGN_FACTORY_OWNER, - FOREIGN_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS, - REQUIRED_NUMBER_OF_VALIDATORS, - VALIDATORS, - FOREIGN_VALIDATORS_OWNER, - FOREIGN_BRIDGE_IMPLEMENTATION_ADDRESS, - FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS, - FOREIGN_GAS_PRICE, - FOREIGN_MAX_AMOUNT_PER_TX, - HOME_DAILY_LIMIT, - HOME_MAX_AMOUNT_PER_TX, - FOREIGN_BRIDGE_OWNER, - FOREIGN_UPGRADEABLE_ADMIN - ) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txInitializeForeign = await sendRawTxForeign({ - data: initializeForeignData, - nonce: foreignNonce, - to: bridgeFactoryForeign.options.address, - privateKey: deploymentPrivateKey, - url: FOREIGN_RPC_URL - }) - assert.equal(Web3Utils.hexToNumber(txInitializeForeign.status), 1, 'Transaction Failed') - foreignNonce++ - - console.log('\nTransferring ownership of FactoryProxy\n') - const factoryForeignOwnershipData = await storageBridgeFactoryForeign.methods - .transferProxyOwnership(FOREIGN_UPGRADEABLE_ADMIN) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txFactoryForeignOwnershipData = await sendRawTxForeign({ - data: factoryForeignOwnershipData, - nonce: foreignNonce, - to: storageBridgeFactoryForeign.options.address, - privateKey: deploymentPrivateKey, - url: FOREIGN_RPC_URL - }) - assert.equal(Web3Utils.hexToNumber(txFactoryForeignOwnershipData.status), 1, 'Transaction Failed') - foreignNonce++ - - console.log('\nForeign Deployment Factory completed\n') - return { - foreignFactory: { - address: storageBridgeFactoryForeign.options.address, - deployedBlockNumber: Web3Utils.hexToNumber(storageBridgeFactoryForeign.deployedBlockNumber) - } - } -} - -module.exports = deployForeign diff --git a/deploy/src/factories/home.js b/deploy/src/factories/home.js deleted file mode 100644 index 0f411de7f..000000000 --- a/deploy/src/factories/home.js +++ /dev/null @@ -1,318 +0,0 @@ -const assert = require('assert') -const Web3Utils = require('web3-utils') -const env = require('../loadEnv') - -const { deployContract, privateKeyToAddress, sendRawTxHome } = require('../deploymentUtils') -const { web3Home, deploymentPrivateKey, HOME_RPC_URL } = require('../web3') - -const EternalStorageProxy = require('../../../build/contracts/EternalStorageProxy.json') -const HomeBridgeFactory = require('../../../build/contracts/HomeBridgeFactory.json') -const BridgeValidators = require('../../../build/contracts/BridgeValidators.json') -const HomeBridge = require('../../../build/contracts/HomeBridgeErcToErc.json') -const BridgeMapper = require('../../../build/contracts/BridgeMapper.json') - -const VALIDATORS = env.VALIDATORS.split(' ') - -const { - DEPLOYMENT_ACCOUNT_PRIVATE_KEY, - REQUIRED_NUMBER_OF_VALIDATORS, - HOME_BRIDGE_OWNER, - HOME_VALIDATORS_OWNER, - HOME_FACTORY_OWNER, - HOME_MAPPER_OWNER, - HOME_UPGRADEABLE_ADMIN, - HOME_DAILY_LIMIT, - HOME_MAX_AMOUNT_PER_TX, - HOME_MIN_AMOUNT_PER_TX, - HOME_REQUIRED_BLOCK_CONFIRMATIONS, - HOME_GAS_PRICE, - FOREIGN_DAILY_LIMIT, - FOREIGN_MAX_AMOUNT_PER_TX, - DOUBLE_PROXY_IMPLEMENTATIONS -} = env - -let { - HOME_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS, - HOME_BRIDGE_IMPLEMENTATION_ADDRESS -} = env - -const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVATE_KEY) - -async function deployHome() { - let homeNonce = await web3Home.eth.getTransactionCount(DEPLOYMENT_ACCOUNT_ADDRESS) - - if (!HOME_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS) { - console.log('deploying bridge validators implementation') - const bridgeValidatorsImplementationHome = await deployContract(BridgeValidators, [], { - from: DEPLOYMENT_ACCOUNT_ADDRESS, - network: 'home', - nonce: homeNonce - }) - homeNonce++ - HOME_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS = bridgeValidatorsImplementationHome.options.address - - if (DOUBLE_PROXY_IMPLEMENTATIONS) { - console.log('deploying bridge validators proxy') - const implProxy = await deployContract(EternalStorageProxy, [], { - from: DEPLOYMENT_ACCOUNT_ADDRESS, - network: 'home', - nonce: homeNonce - }) - homeNonce++ - - console.log('\nhooking up eternal storage to implementation') - const upgradeToImpl = await implProxy.methods - .upgradeTo('1', HOME_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txUpgradeToImpl = await sendRawTxHome({ - data: upgradeToImpl, - nonce: homeNonce, - to: implProxy.options.address, - privateKey: deploymentPrivateKey, - url: HOME_RPC_URL - }) - assert.equal(Web3Utils.hexToNumber(txUpgradeToImpl.status), 1, 'Transaction Failed') - homeNonce++ - HOME_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS = implProxy.options.address - - console.log('\nTransferring ownership of Proxy\n') - const ownershipData = await implProxy.methods - .transferProxyOwnership(HOME_UPGRADEABLE_ADMIN) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txOwnershipData = await sendRawTxHome({ - data: ownershipData, - nonce: homeNonce, - to: implProxy.options.address, - privateKey: deploymentPrivateKey, - url: HOME_RPC_URL - }) - assert.equal(Web3Utils.hexToNumber(txOwnershipData.status), 1, 'Transaction Failed') - homeNonce++ - } - } - console.log('[Home] bridge validators implementation address: ', HOME_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS) - - if (!HOME_BRIDGE_IMPLEMENTATION_ADDRESS) { - console.log('deploying home bridge implementation') - const homeBridgeImplementationHome = await deployContract(HomeBridge, [], { - from: DEPLOYMENT_ACCOUNT_ADDRESS, - network: 'home', - nonce: homeNonce - }) - homeNonce++ - HOME_BRIDGE_IMPLEMENTATION_ADDRESS = homeBridgeImplementationHome.options.address - - if (DOUBLE_PROXY_IMPLEMENTATIONS) { - console.log('deploying home bridge proxy') - const implProxy = await deployContract(EternalStorageProxy, [], { - from: DEPLOYMENT_ACCOUNT_ADDRESS, - network: 'home', - nonce: homeNonce - }) - homeNonce++ - - console.log('\nhooking up eternal storage to implementation') - const upgradeToImpl = await implProxy.methods - .upgradeTo('1', HOME_BRIDGE_IMPLEMENTATION_ADDRESS) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txUpgradeToImpl = await sendRawTxHome({ - data: upgradeToImpl, - nonce: homeNonce, - to: implProxy.options.address, - privateKey: deploymentPrivateKey, - url: HOME_RPC_URL - }) - assert.equal(Web3Utils.hexToNumber(txUpgradeToImpl.status), 1, 'Transaction Failed') - homeNonce++ - HOME_BRIDGE_IMPLEMENTATION_ADDRESS = implProxy.options.address - - console.log('\nTransferring ownership of Proxy\n') - const ownershipData = await implProxy.methods - .transferProxyOwnership(HOME_UPGRADEABLE_ADMIN) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txOwnershipData = await sendRawTxHome({ - data: ownershipData, - nonce: homeNonce, - to: implProxy.options.address, - privateKey: deploymentPrivateKey, - url: HOME_RPC_URL - }) - assert.equal(Web3Utils.hexToNumber(txOwnershipData.status), 1, 'Transaction Failed') - homeNonce++ - } - } - console.log('[Home] home bridge implementation address: ', HOME_BRIDGE_IMPLEMENTATION_ADDRESS) - - console.log('deploying storage for home bridge factory') - const storageBridgeFactoryHome = await deployContract(EternalStorageProxy, [], { - from: DEPLOYMENT_ACCOUNT_ADDRESS, - network: 'home', - nonce: homeNonce - }) - homeNonce++ - console.log('[Home] BridgeFactory Storage: ', storageBridgeFactoryHome.options.address) - - console.log('\ndeploying implementation for home bridge factory') - const bridgeFactoryHome = await deployContract(HomeBridgeFactory, [], { - from: DEPLOYMENT_ACCOUNT_ADDRESS, - network: 'home', - nonce: homeNonce - }) - homeNonce++ - console.log( - '[Home] BridgeFactory Implementation: ', - bridgeFactoryHome.options.address - ) - console.log('\nhooking up eternal storage to BridgeFactory') - const upgradeToHomeFactoryData = await storageBridgeFactoryHome.methods - .upgradeTo('1', bridgeFactoryHome.options.address) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txUpgradeToHomeFactory = await sendRawTxHome({ - data: upgradeToHomeFactoryData, - nonce: homeNonce, - to: storageBridgeFactoryHome.options.address, - privateKey: deploymentPrivateKey, - url: HOME_RPC_URL - }) - assert.equal(Web3Utils.hexToNumber(txUpgradeToHomeFactory.status), 1, 'Transaction Failed') - homeNonce++ - - console.log('\ninitializing Home Bridge Factory with following parameters:\n') - console.log( - `HOME_FACTORY_OWNER: ${HOME_FACTORY_OWNER}, - HOME_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS: ${HOME_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS}, - REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, - VALIDATORS: ${VALIDATORS}, - HOME_VALIDATORS_OWNER: ${HOME_VALIDATORS_OWNER}, - HOME_BRIDGE_IMPLEMENTATION_ADDRESS: ${HOME_BRIDGE_IMPLEMENTATION_ADDRESS}, - HOME_REQUIRED_BLOCK_CONFIRMATIONS: ${HOME_REQUIRED_BLOCK_CONFIRMATIONS}, - HOME_GAS_PRICE: ${HOME_GAS_PRICE}, - HOME_DAILY_LIMIT: ${HOME_DAILY_LIMIT}, - HOME_MAX_AMOUNT_PER_TX: ${HOME_MAX_AMOUNT_PER_TX}, - HOME_MIN_AMOUNT_PER_TX: ${HOME_MIN_AMOUNT_PER_TX}, - FOREIGN_DAILY_LIMIT: ${FOREIGN_DAILY_LIMIT}, - FOREIGN_MAX_AMOUNT_PER_TX: ${FOREIGN_MAX_AMOUNT_PER_TX}, - HOME_BRIDGE_OWNER: ${HOME_BRIDGE_OWNER}, - HOME_UPGRADEABLE_ADMIN: ${HOME_UPGRADEABLE_ADMIN}` - ) - bridgeFactoryHome.options.address = storageBridgeFactoryHome.options.address - const initializeHomeData = await bridgeFactoryHome.methods - .initialize( - HOME_FACTORY_OWNER, - HOME_BRIDGE_VALIDATORS_IMPLEMENTATION_ADDRESS, - REQUIRED_NUMBER_OF_VALIDATORS, - VALIDATORS, - HOME_VALIDATORS_OWNER, - HOME_BRIDGE_IMPLEMENTATION_ADDRESS, - HOME_REQUIRED_BLOCK_CONFIRMATIONS, - HOME_GAS_PRICE, - HOME_DAILY_LIMIT, - HOME_MAX_AMOUNT_PER_TX, - HOME_MIN_AMOUNT_PER_TX, - FOREIGN_DAILY_LIMIT, - FOREIGN_MAX_AMOUNT_PER_TX, - HOME_BRIDGE_OWNER, - HOME_UPGRADEABLE_ADMIN - ) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txInitializeHome = await sendRawTxHome({ - data: initializeHomeData, - nonce: homeNonce, - to: bridgeFactoryHome.options.address, - privateKey: deploymentPrivateKey, - url: HOME_RPC_URL - }) - assert.equal(Web3Utils.hexToNumber(txInitializeHome.status), 1, 'Transaction Failed') - homeNonce++ - - console.log('\nTransferring ownership of FactoryProxy\n') - const factoryHomeOwnershipData = await storageBridgeFactoryHome.methods - .transferProxyOwnership(HOME_UPGRADEABLE_ADMIN) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txFactoryHomeOwnershipData = await sendRawTxHome({ - data: factoryHomeOwnershipData, - nonce: homeNonce, - to: storageBridgeFactoryHome.options.address, - privateKey: deploymentPrivateKey, - url: HOME_RPC_URL - }) - assert.equal(Web3Utils.hexToNumber(txFactoryHomeOwnershipData.status), 1, 'Transaction Failed') - homeNonce++ - - console.log('deploying storage for bridge mapper') - const storageBridgeMapperHome = await deployContract(EternalStorageProxy, [], { - from: DEPLOYMENT_ACCOUNT_ADDRESS, - network: 'home', - nonce: homeNonce - }) - homeNonce++ - console.log('[Home] BridgeMapper Storage: ', storageBridgeMapperHome.options.address) - - console.log('\ndeploying implementation for bridge mapper') - const bridgeMapperHome = await deployContract(BridgeMapper, [], { - from: DEPLOYMENT_ACCOUNT_ADDRESS, - network: 'home', - nonce: homeNonce - }) - homeNonce++ - console.log( - '[Home] BridgeMapper Implementation: ', - bridgeMapperHome.options.address - ) - - console.log('\nhooking up eternal storage to BridgeMapper') - const upgradeToBridgeMapperData = await storageBridgeMapperHome.methods - .upgradeTo('1', bridgeMapperHome.options.address) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txUpgradeToBridgeMapper = await sendRawTxHome({ - data: upgradeToBridgeMapperData, - nonce: homeNonce, - to: storageBridgeMapperHome.options.address, - privateKey: deploymentPrivateKey, - url: HOME_RPC_URL - }) - assert.equal(Web3Utils.hexToNumber(txUpgradeToBridgeMapper.status), 1, 'Transaction Failed') - homeNonce++ - - console.log('\ninitializing BridgeMapper:') - bridgeMapperHome.options.address = storageBridgeMapperHome.options.address - const initializeBridgeMapperData = await bridgeMapperHome.methods - .initialize(HOME_MAPPER_OWNER) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txInitializeBridgeMapper = await sendRawTxHome({ - data: initializeBridgeMapperData, - nonce: homeNonce, - to: bridgeMapperHome.options.address, - privateKey: deploymentPrivateKey, - url: HOME_RPC_URL - }) - assert.equal(Web3Utils.hexToNumber(txInitializeBridgeMapper.status), 1, 'Transaction Failed') - homeNonce++ - - console.log('\nTransferring ownership of MapperProxy\n') - const mapperOwnershipData = await storageBridgeMapperHome.methods - .transferProxyOwnership(HOME_UPGRADEABLE_ADMIN) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) - const txMapperOwnershipData = await sendRawTxHome({ - data: mapperOwnershipData, - nonce: homeNonce, - to: storageBridgeMapperHome.options.address, - privateKey: deploymentPrivateKey, - url: HOME_RPC_URL - }) - assert.equal(Web3Utils.hexToNumber(txMapperOwnershipData.status), 1, 'Transaction Failed') - homeNonce++ - - console.log('\nHome Deployment Factory completed\n') - return { - homeFactory: { - address: storageBridgeFactoryHome.options.address, - deployedBlockNumber: Web3Utils.hexToNumber(storageBridgeFactoryHome.deployedBlockNumber) - }, - mapper: { - address: storageBridgeMapperHome.options.address, - deployedBlockNumber: Web3Utils.hexToNumber(storageBridgeMapperHome.deployedBlockNumber) - } - } -} -module.exports = deployHome diff --git a/deploy/src/loadEnv.js b/deploy/src/loadEnv.js index e2b7bff53..8b3d9f36e 100644 --- a/deploy/src/loadEnv.js +++ b/deploy/src/loadEnv.js @@ -7,7 +7,7 @@ const envalid = require('envalid') const { ZERO_ADDRESS } = require('./constants') // Validations and constants -const validBridgeModes = ['NATIVE_TO_ERC', 'ERC_TO_ERC', 'ERC_TO_NATIVE', 'ERC_TO_ERC_MULTIPLE'] +const validBridgeModes = ['NATIVE_TO_ERC', 'ERC_TO_ERC', 'ERC_TO_NATIVE'] const bigNumValidator = envalid.makeValidator(x => toBN(x)) const validateAddress = address => { if (isAddress(address)) { @@ -85,14 +85,6 @@ if (BRIDGE_MODE === 'ERC_TO_NATIVE') { }) } } -if(BRIDGE_MODE === 'ERC_TO_ERC_MULTIPLE') { - validations = { - ...validations, - HOME_FACTORY_OWNER: addressValidator(), - HOME_MAPPER_OWNER: addressValidator(), - FOREIGN_FACTORY_OWNER: addressValidator(), - } -} const env = envalid.cleanEnv(process.env, validations) diff --git a/flatten.sh b/flatten.sh index 55f847252..1f1fe20da 100755 --- a/flatten.sh +++ b/flatten.sh @@ -7,7 +7,6 @@ fi mkdir -p flats/native_to_erc20 mkdir -p flats/erc20_to_erc20 mkdir -p flats/erc20_to_native -mkdir -p flats/factories ./node_modules/.bin/truffle-flattener contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol > flats/native_to_erc20/ForeignBridgeNativeToErc_flat.sol ./node_modules/.bin/truffle-flattener contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol > flats/native_to_erc20/HomeBridgeNativeToErc_flat.sol @@ -20,8 +19,4 @@ mkdir -p flats/factories ./node_modules/.bin/truffle-flattener contracts/upgradeability/EternalStorageProxy.sol > flats/EternalStorageProxy_flat.sol ./node_modules/.bin/truffle-flattener contracts/upgradeable_contracts/BridgeValidators.sol > flats/BridgeValidators_flat.sol -./node_modules/.bin/truffle-flattener contracts/upgradeable_contracts/BridgeMapper.sol > flats/BridgeMapper_flat.sol ./node_modules/.bin/truffle-flattener contracts/ERC677BridgeToken.sol > flats/ERC677BridgeToken_flat.sol - -./node_modules/.bin/truffle-flattener contracts/upgradeable_contracts/factories/ForeignBridgeFactory.sol > flats/factories/ForeignBridgeFactory_flat.sol -./node_modules/.bin/truffle-flattener contracts/upgradeable_contracts/factories/HomeBridgeFactory.sol > flats/factories/HomeBridgeFactory_flat.sol diff --git a/package-lock.json b/package-lock.json index 69c37130f..301109f25 100644 --- a/package-lock.json +++ b/package-lock.json @@ -4,14 +4,67 @@ "lockfileVersion": 1, "requires": true, "dependencies": { - "@sindresorhus/is": { - "version": "0.7.0", - "resolved": "https://registry.npmjs.org/@sindresorhus/is/-/is-0.7.0.tgz", - "integrity": "sha512-ONhaKPIufzzrlNbqtWFFd+jlnemX6lJAgq9ZeiZtS7I1PIf/la7CW4m83rTXRnVnsMbW2k56pGYu7AUFJD9Pow==" + "@babel/runtime": { + "version": "7.3.1", + "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.3.1.tgz", + "integrity": "sha512-7jGW8ppV0ant637pIqAcFfQDDH1orEPGJb8aXfUozuCU3QqX7rX4DA8iwrbPrR1hcH0FTTHz47yQnk+bl5xHQA==", + "requires": { + "regenerator-runtime": "^0.12.0" + } + }, + "@resolver-engine/core": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/@resolver-engine/core/-/core-0.2.1.tgz", + "integrity": "sha512-nsLQHmPJ77QuifqsIvqjaF5B9aHnDzJjp73Q1z6apY3e9nqYrx4Dtowhpsf7Jwftg/XzVDEMQC+OzUBNTS+S1A==", + "dev": true, + "requires": { + "debug": "^3.1.0", + "request": "^2.85.0" + } + }, + "@resolver-engine/fs": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/@resolver-engine/fs/-/fs-0.2.1.tgz", + "integrity": "sha512-7kJInM1Qo2LJcKyDhuYzh9ZWd+mal/fynfL9BNjWOiTcOpX+jNfqb/UmGUqros5pceBITlWGqS4lU709yHFUbg==", + "dev": true, + "requires": { + "@resolver-engine/core": "^0.2.1", + "debug": "^3.1.0" + } + }, + "@resolver-engine/imports": { + "version": "0.2.2", + "resolved": "https://registry.npmjs.org/@resolver-engine/imports/-/imports-0.2.2.tgz", + "integrity": "sha512-u5/HUkvo8q34AA+hnxxqqXGfby5swnH0Myw91o3Sm2TETJlNKXibFGSKBavAH+wvWdBi4Z5gS2Odu0PowgVOUg==", + "dev": true, + "requires": { + "@resolver-engine/core": "^0.2.1", + "debug": "^3.1.0", + "hosted-git-info": "^2.6.0" + } + }, + "@resolver-engine/imports-fs": { + "version": "0.2.2", + "resolved": "https://registry.npmjs.org/@resolver-engine/imports-fs/-/imports-fs-0.2.2.tgz", + "integrity": "sha512-gFCgMvCwyppjwq0UzIjde/WI+yDs3oatJhozG9xdjJdewwtd7LiF0T5i9lrHAUtqrQbqoFE4E+ZMRVHWpWHpKQ==", + "dev": true, + "requires": { + "@resolver-engine/fs": "^0.2.1", + "@resolver-engine/imports": "^0.2.2", + "debug": "^3.1.0" + } + }, + "@types/bn.js": { + "version": "4.11.4", + "resolved": "https://registry.npmjs.org/@types/bn.js/-/bn.js-4.11.4.tgz", + "integrity": "sha512-AO8WW+aRcKWKQAYTfKLzwnpL6U+TfPqS+haRrhCy5ff04Da8WZud3ZgVjspQXaEXJDcTlsjUEVvL39wegDek5w==", + "requires": { + "@types/node": "*" + } }, "@types/concat-stream": { "version": "1.6.0", - "resolved": "http://registry.npmjs.org/@types/concat-stream/-/concat-stream-1.6.0.tgz", + "resolved": "https://registry.npmjs.org/@types/concat-stream/-/concat-stream-1.6.0.tgz", "integrity": "sha1-OU2+C7X+5Gs42JZzXoto7yOQ0A0=", "dev": true, "requires": { @@ -20,7 +73,7 @@ }, "@types/form-data": { "version": "0.0.33", - "resolved": "http://registry.npmjs.org/@types/form-data/-/form-data-0.0.33.tgz", + "resolved": "https://registry.npmjs.org/@types/form-data/-/form-data-0.0.33.tgz", "integrity": "sha1-yayFsqX9GENbjIXZ7LUObWyJP/g=", "dev": true, "requires": { @@ -28,10 +81,9 @@ } }, "@types/node": { - "version": "9.6.35", - "resolved": "https://registry.npmjs.org/@types/node/-/node-9.6.35.tgz", - "integrity": "sha512-h5zvHS8wXHGa+Gcqs9K8vqCgOtqjr0+NqG/DDJmQIX1wpR9HivAfgV8bjcD3mGM4bPfQw5Aneb2Pn8355L83jA==", - "dev": true + "version": "10.12.26", + "resolved": "https://registry.npmjs.org/@types/node/-/node-10.12.26.tgz", + "integrity": "sha512-nMRqS+mL1TOnIJrL6LKJcNZPB8V3eTfRo9FQA2b5gDvrHurC8XbSA86KNe0dShlEL7ReWJv/OU9NL7Z0dnqWTg==" }, "@types/qs": { "version": "6.5.1", @@ -52,75 +104,26 @@ "dev": true, "requires": { "web3": "^0.18.4" - }, - "dependencies": { - "bignumber.js": { - "version": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", - "from": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", - "dev": true - }, - "web3": { - "version": "0.18.4", - "resolved": "https://registry.npmjs.org/web3/-/web3-0.18.4.tgz", - "integrity": "sha1-gewXhBRUkfLqqJVbMcBgSeB8Xn0=", - "dev": true, - "requires": { - "bignumber.js": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", - "crypto-js": "^3.1.4", - "utf8": "^2.1.1", - "xhr2": "*", - "xmlhttprequest": "*" - } - } - } - }, - "accepts": { - "version": "1.3.5", - "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.5.tgz", - "integrity": "sha1-63d99gEXI6OxTopywIBcjoZ0a9I=", - "requires": { - "mime-types": "~2.1.18", - "negotiator": "0.6.1" } }, "ajv": { - "version": "5.5.2", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-5.5.2.tgz", - "integrity": "sha1-c7Xuyj+rZT49P5Qis0GtQiBdyWU=", - "requires": { - "co": "^4.6.0", - "fast-deep-equal": "^1.0.0", - "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.3.0" - } - }, - "align-text": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/align-text/-/align-text-0.1.4.tgz", - "integrity": "sha1-DNkKVhCT810KmSVsIrcGlDP60Rc=", + "version": "6.9.1", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.9.1.tgz", + "integrity": "sha512-XDN92U311aINL77ieWHmqCcNlwjoP5cHXDxIxbf2MaPYuCXOHS7gHH8jktxeK5omgd52XbSTX6a4Piwd1pQmzA==", "dev": true, "requires": { - "kind-of": "^3.0.2", - "longest": "^1.0.1", - "repeat-string": "^1.5.2" - }, - "dependencies": { - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", - "dev": true, - "requires": { - "is-buffer": "^1.1.5" - } - } + "fast-deep-equal": "^2.0.1", + "fast-json-stable-stringify": "^2.0.0", + "json-schema-traverse": "^0.4.1", + "uri-js": "^4.2.2" } }, "amdefine": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/amdefine/-/amdefine-1.0.1.tgz", "integrity": "sha1-SlKCrBZHKek2Gbz9OtFR+BfOkfU=", - "dev": true + "dev": true, + "optional": true }, "ansi-align": { "version": "2.0.0", @@ -164,11 +167,6 @@ } } }, - "ansi-escapes": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-3.1.0.tgz", - "integrity": "sha512-UgAb8H9D41AQnu/PbWlCofQVcnV4Gs2bBJi9eZPxfU/hgglFh3SMDMENRIqdr7H6XFnXdoknctFByVsCOotTVw==" - }, "ansi-regex": { "version": "2.1.1", "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz", @@ -178,15 +176,11 @@ "version": "3.2.1", "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz", "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==", + "dev": true, "requires": { "color-convert": "^1.9.0" } }, - "any-observable": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/any-observable/-/any-observable-0.2.0.tgz", - "integrity": "sha1-xnhwBYADV5AJCD9UrAq6+1wz0kI=" - }, "anymatch": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/anymatch/-/anymatch-2.0.0.tgz", @@ -195,6 +189,17 @@ "requires": { "micromatch": "^3.1.4", "normalize-path": "^2.1.1" + }, + "dependencies": { + "normalize-path": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-2.1.1.tgz", + "integrity": "sha1-GrKLVW4Zg2Oowab35vogE3/mrtk=", + "dev": true, + "requires": { + "remove-trailing-separator": "^1.0.1" + } + } } }, "argparse": { @@ -215,7 +220,8 @@ "arr-flatten": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/arr-flatten/-/arr-flatten-1.1.0.tgz", - "integrity": "sha512-L3hKV5R/p5o81R7O02IGnwpDmkp6E982XhtbuwSe3O4qOtMMMtodicASA1Cny2U+aCXcNpml+m4dPsvsJ3jatg==" + "integrity": "sha512-L3hKV5R/p5o81R7O02IGnwpDmkp6E982XhtbuwSe3O4qOtMMMtodicASA1Cny2U+aCXcNpml+m4dPsvsJ3jatg==", + "dev": true }, "arr-union": { "version": "3.1.0", @@ -223,40 +229,12 @@ "integrity": "sha1-45sJrqne+Gao8gbiiK9jkZuuOcQ=", "dev": true }, - "array-differ": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/array-differ/-/array-differ-1.0.0.tgz", - "integrity": "sha1-7/UuN1gknTO+QCuLuOVkuytdQDE=" - }, - "array-flatten": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-1.1.1.tgz", - "integrity": "sha1-ml9pkFGx5wczKPKgCJaLZOopVdI=" - }, - "array-union": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/array-union/-/array-union-1.0.2.tgz", - "integrity": "sha1-mjRBDk9OPaI96jdb5b5w8kd47Dk=", - "requires": { - "array-uniq": "^1.0.1" - } - }, - "array-uniq": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/array-uniq/-/array-uniq-1.0.3.tgz", - "integrity": "sha1-r2rId6Jcx/dOBYiUdThY39sk/bY=" - }, "array-unique": { "version": "0.3.2", "resolved": "https://registry.npmjs.org/array-unique/-/array-unique-0.3.2.tgz", "integrity": "sha1-qJS3XUvE9s1nnvMkSp/Y9Gri1Cg=", "dev": true }, - "arrify": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/arrify/-/arrify-1.0.1.tgz", - "integrity": "sha1-iYUI2iIm84DfkEcoRWhJwVAaSw0=" - }, "asap": { "version": "2.0.6", "resolved": "https://registry.npmjs.org/asap/-/asap-2.0.6.tgz", @@ -264,14 +242,19 @@ "dev": true }, "asn1": { - "version": "0.2.3", - "resolved": "https://registry.npmjs.org/asn1/-/asn1-0.2.3.tgz", - "integrity": "sha1-2sh4dxPJlmhJ/IGAd36+nB3fO4Y=" + "version": "0.2.4", + "resolved": "https://registry.npmjs.org/asn1/-/asn1-0.2.4.tgz", + "integrity": "sha512-jxwzQpLQjSmWXgwaCZE9Nz+glAG01yF1QnWgbhGwHI5A6FRIEY6IVqtHhIepHqI7/kyEyQEagBC5mBEFlIYvdg==", + "dev": true, + "requires": { + "safer-buffer": "~2.1.0" + } }, "assert-plus": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", - "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=" + "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", + "dev": true }, "assertion-error": { "version": "1.1.0", @@ -285,18 +268,11 @@ "integrity": "sha1-WWZ/QfrdTyDMvCu5a41Pf3jsA2c=", "dev": true }, - "ast-types": { - "version": "0.11.3", - "resolved": "https://registry.npmjs.org/ast-types/-/ast-types-0.11.3.tgz", - "integrity": "sha512-XA5o5dsNw8MhyW0Q7MWXJWc4oOzZKbdsEJq45h7c8q/d9DwWZ5F2ugUc1PuMLPGsUnphCt/cNDHu8JeBbxf1qA==" - }, "async": { - "version": "2.6.0", - "resolved": "https://registry.npmjs.org/async/-/async-2.6.0.tgz", - "integrity": "sha512-xAfGg1/NTLBBKlHFmnd7PlmUW9KhVQIUuSrYem9xzFUZy13ScvtyGGejaae9iAVRiRq9+Cx7DPFaAAhCpyxyPw==", - "requires": { - "lodash": "^4.14.0" - } + "version": "1.5.2", + "resolved": "https://registry.npmjs.org/async/-/async-1.5.2.tgz", + "integrity": "sha1-7GphrlZIDAw8skHJVhjiCJL5Zyo=", + "dev": true }, "async-each": { "version": "1.0.1", @@ -304,841 +280,659 @@ "integrity": "sha1-GdOGodntxufByF04iu28xW0zYC0=", "dev": true }, - "async-limiter": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/async-limiter/-/async-limiter-1.0.0.tgz", - "integrity": "sha512-jp/uFnooOiO+L211eZOoSyzpOITMXx1rBITauYykG3BRYPu8h0UcxsPNB04RR5vo4Tyz3+ay17tR6JVf9qzYWg==" - }, "asynckit": { "version": "0.4.0", "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", - "integrity": "sha1-x57Zf380y48robyXkLzDZkdLS3k=" + "integrity": "sha1-x57Zf380y48robyXkLzDZkdLS3k=", + "dev": true }, "atob": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/atob/-/atob-2.1.1.tgz", - "integrity": "sha1-ri1acpR38onWDdf5amMUoi3Wwio=", + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/atob/-/atob-2.1.2.tgz", + "integrity": "sha512-Wm6ukoaOGJi/73p/cl2GvLjTI5JM1k/O14isD73YML8StrH/7/lRFgmg8nICZgD3bZZvjwCGxtMOD3wWNAu8cg==", "dev": true }, "aws-sign2": { "version": "0.7.0", "resolved": "https://registry.npmjs.org/aws-sign2/-/aws-sign2-0.7.0.tgz", - "integrity": "sha1-tG6JCTSpWR8tL2+G1+ap8bP+dqg=" + "integrity": "sha1-tG6JCTSpWR8tL2+G1+ap8bP+dqg=", + "dev": true }, "aws4": { - "version": "1.7.0", - "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.7.0.tgz", - "integrity": "sha512-32NDda82rhwD9/JBCCkB+MRYDp0oSvlo2IL6rQWA10PQi7tDUM3eqMSltXmY+Oyl/7N3P3qNtAlv7X0d9bI28w==" + "version": "1.8.0", + "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.8.0.tgz", + "integrity": "sha512-ReZxvNHIOv88FlT7rxcXIIC0fPt4KZqZbOlivyWtXLt8ESx84zd3kMC6iK5jVeS2qt+g7ftS7ye4fi06X5rtRQ==", + "dev": true + }, + "balanced-match": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz", + "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=" }, - "babel-code-frame": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-code-frame/-/babel-code-frame-6.26.0.tgz", - "integrity": "sha1-Y/1D99weO7fONZR9uP42mj9Yx0s=", + "base": { + "version": "0.11.2", + "resolved": "https://registry.npmjs.org/base/-/base-0.11.2.tgz", + "integrity": "sha512-5T6P4xPgpp0YDFvSWwEZ4NoE3aM4QBQXDzmVbraCkFj8zHM+mba8SyqB5DbZWyR7mYHo6Y7BdQo3MoA4m0TeQg==", + "dev": true, "requires": { - "chalk": "^1.1.3", - "esutils": "^2.0.2", - "js-tokens": "^3.0.2" + "cache-base": "^1.0.1", + "class-utils": "^0.3.5", + "component-emitter": "^1.2.1", + "define-property": "^1.0.0", + "isobject": "^3.0.1", + "mixin-deep": "^1.2.0", + "pascalcase": "^0.1.1" }, "dependencies": { - "ansi-styles": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-2.2.1.tgz", - "integrity": "sha1-tDLdM1i2NM914eRmQ2gkBTPB3b4=" + "define-property": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-1.0.0.tgz", + "integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=", + "dev": true, + "requires": { + "is-descriptor": "^1.0.0" + } }, - "chalk": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz", - "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=", + "is-accessor-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz", + "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", + "dev": true, "requires": { - "ansi-styles": "^2.2.1", - "escape-string-regexp": "^1.0.2", - "has-ansi": "^2.0.0", - "strip-ansi": "^3.0.0", - "supports-color": "^2.0.0" + "kind-of": "^6.0.0" } }, - "supports-color": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz", - "integrity": "sha1-U10EXOa2Nj+kARcIRimZXp3zJMc=" - } - } - }, - "babel-core": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-core/-/babel-core-6.26.0.tgz", - "integrity": "sha1-rzL3izGm/O8RnIew/Y2XU/A6C7g=", - "requires": { - "babel-code-frame": "^6.26.0", - "babel-generator": "^6.26.0", - "babel-helpers": "^6.24.1", - "babel-messages": "^6.23.0", - "babel-register": "^6.26.0", - "babel-runtime": "^6.26.0", - "babel-template": "^6.26.0", - "babel-traverse": "^6.26.0", - "babel-types": "^6.26.0", - "babylon": "^6.18.0", - "convert-source-map": "^1.5.0", - "debug": "^2.6.8", - "json5": "^0.5.1", - "lodash": "^4.17.4", - "minimatch": "^3.0.4", - "path-is-absolute": "^1.0.1", - "private": "^0.1.7", - "slash": "^1.0.0", - "source-map": "^0.5.6" - }, - "dependencies": { - "babylon": { - "version": "6.18.0", - "resolved": "https://registry.npmjs.org/babylon/-/babylon-6.18.0.tgz", - "integrity": "sha512-q/UEjfGJ2Cm3oKV71DJz9d25TPnq5rhBVL2Q4fA5wcC3jcrdn7+SssEybFIxwAvvP+YCsCYNKughoF33GxgycQ==" - } - } - }, - "babel-generator": { - "version": "6.26.1", - "resolved": "https://registry.npmjs.org/babel-generator/-/babel-generator-6.26.1.tgz", - "integrity": "sha512-HyfwY6ApZj7BYTcJURpM5tznulaBvyio7/0d4zFOeMPUmfxkCjHocCuoLa2SAGzBI8AREcH3eP3758F672DppA==", - "requires": { - "babel-messages": "^6.23.0", - "babel-runtime": "^6.26.0", - "babel-types": "^6.26.0", - "detect-indent": "^4.0.0", - "jsesc": "^1.3.0", - "lodash": "^4.17.4", - "source-map": "^0.5.7", - "trim-right": "^1.0.1" - }, - "dependencies": { - "jsesc": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-1.3.0.tgz", - "integrity": "sha1-RsP+yMGJKxKwgz25vHYiF226s0s=" + "is-data-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz", + "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", + "dev": true, + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-descriptor": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz", + "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", + "dev": true, + "requires": { + "is-accessor-descriptor": "^1.0.0", + "is-data-descriptor": "^1.0.0", + "kind-of": "^6.0.2" + } } } }, - "babel-helper-bindify-decorators": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-bindify-decorators/-/babel-helper-bindify-decorators-6.24.1.tgz", - "integrity": "sha1-FMGeXxQte0fxmlJDHlKxzLxAozA=", - "requires": { - "babel-runtime": "^6.22.0", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" - } - }, - "babel-helper-builder-binary-assignment-operator-visitor": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-builder-binary-assignment-operator-visitor/-/babel-helper-builder-binary-assignment-operator-visitor-6.24.1.tgz", - "integrity": "sha1-zORReto1b0IgvK6KAsKzRvmlZmQ=", + "bcrypt-pbkdf": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.2.tgz", + "integrity": "sha1-pDAdOJtqQ/m2f/PKEaP2Y342Dp4=", + "dev": true, "requires": { - "babel-helper-explode-assignable-expression": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" + "tweetnacl": "^0.14.3" } }, - "babel-helper-call-delegate": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-call-delegate/-/babel-helper-call-delegate-6.24.1.tgz", - "integrity": "sha1-7Oaqzdx25Bw0YfiL/Fdb0Nqi340=", - "requires": { - "babel-helper-hoist-variables": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" - } + "bignumber.js": { + "version": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", + "from": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", + "dev": true }, - "babel-helper-define-map": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-helper-define-map/-/babel-helper-define-map-6.26.0.tgz", - "integrity": "sha1-pfVtq0GiX5fstJjH66ypgZ+Vvl8=", - "requires": { - "babel-helper-function-name": "^6.24.1", - "babel-runtime": "^6.26.0", - "babel-types": "^6.26.0", - "lodash": "^4.17.4" - } + "binary-extensions": { + "version": "1.13.0", + "resolved": "https://registry.npmjs.org/binary-extensions/-/binary-extensions-1.13.0.tgz", + "integrity": "sha512-EgmjVLMn22z7eGGv3kcnHwSnJXmFHjISTY9E/S5lIcTD3Oxw05QTcBLNkJFzcb3cNueUdF/IN4U+d78V0zO8Hw==", + "dev": true }, - "babel-helper-explode-assignable-expression": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-explode-assignable-expression/-/babel-helper-explode-assignable-expression-6.24.1.tgz", - "integrity": "sha1-8luCz33BBDPFX3BZLVdGQArCLKo=", - "requires": { - "babel-runtime": "^6.22.0", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" - } + "bn.js": { + "version": "4.11.8", + "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.11.8.tgz", + "integrity": "sha512-ItfYfPLkWHUjckQCk8xC+LwxgK8NYcXywGigJgSwOP8Y2iyWT4f2vsZnoOXTTbo+o5yXmIUJ4gn5538SO5S3gA==" }, - "babel-helper-explode-class": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-explode-class/-/babel-helper-explode-class-6.24.1.tgz", - "integrity": "sha1-fcKjkQ3uAHBW4eMdZAztPVTqqes=", + "boxen": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/boxen/-/boxen-1.3.0.tgz", + "integrity": "sha512-TNPjfTr432qx7yOjQyaXm3dSR0MH9vXp7eT1BFSl/C51g+EFnOR9hTg1IreahGBmDNCehscshe45f+C1TBZbLw==", + "dev": true, "requires": { - "babel-helper-bindify-decorators": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" + "ansi-align": "^2.0.0", + "camelcase": "^4.0.0", + "chalk": "^2.0.1", + "cli-boxes": "^1.0.0", + "string-width": "^2.0.0", + "term-size": "^1.2.0", + "widest-line": "^2.0.0" + }, + "dependencies": { + "ansi-regex": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", + "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=", + "dev": true + }, + "camelcase": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-4.1.0.tgz", + "integrity": "sha1-1UVjW+HjPFQmScaRc+Xeas+uNN0=", + "dev": true + }, + "is-fullwidth-code-point": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", + "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=", + "dev": true + }, + "string-width": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", + "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", + "dev": true, + "requires": { + "is-fullwidth-code-point": "^2.0.0", + "strip-ansi": "^4.0.0" + } + }, + "strip-ansi": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", + "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", + "dev": true, + "requires": { + "ansi-regex": "^3.0.0" + } + } } }, - "babel-helper-function-name": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-function-name/-/babel-helper-function-name-6.24.1.tgz", - "integrity": "sha1-00dbjAPtmCQqJbSDUasYOZ01gKk=", + "brace-expansion": { + "version": "1.1.11", + "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", + "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", "requires": { - "babel-helper-get-function-arity": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" + "balanced-match": "^1.0.0", + "concat-map": "0.0.1" } }, - "babel-helper-get-function-arity": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-get-function-arity/-/babel-helper-get-function-arity-6.24.1.tgz", - "integrity": "sha1-j3eCqpNAfEHTqlCQj4mwMbG2hT0=", + "braces": { + "version": "2.3.2", + "resolved": "https://registry.npmjs.org/braces/-/braces-2.3.2.tgz", + "integrity": "sha512-aNdbnj9P8PjdXU4ybaWLK2IF3jc/EoDYbC7AazW6to3TRsfXxscC9UXOB5iDiEQrkyIbWp2SLQda4+QAa7nc3w==", + "dev": true, "requires": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } - }, - "babel-helper-hoist-variables": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-hoist-variables/-/babel-helper-hoist-variables-6.24.1.tgz", - "integrity": "sha1-HssnaJydJVE+rbyZFKc/VAi+enY=", - "requires": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } - }, - "babel-helper-optimise-call-expression": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-optimise-call-expression/-/babel-helper-optimise-call-expression-6.24.1.tgz", - "integrity": "sha1-96E0J7qfc/j0+pk8VKl4gtEkQlc=", - "requires": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" + "arr-flatten": "^1.1.0", + "array-unique": "^0.3.2", + "extend-shallow": "^2.0.1", + "fill-range": "^4.0.0", + "isobject": "^3.0.1", + "repeat-element": "^1.1.2", + "snapdragon": "^0.8.1", + "snapdragon-node": "^2.0.1", + "split-string": "^3.0.2", + "to-regex": "^3.0.1" + }, + "dependencies": { + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "dev": true, + "requires": { + "is-extendable": "^0.1.0" + } + } } }, - "babel-helper-regex": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-helper-regex/-/babel-helper-regex-6.26.0.tgz", - "integrity": "sha1-MlxZ+QL4LyS3T6zu0DY5VPZJXnI=", - "requires": { - "babel-runtime": "^6.26.0", - "babel-types": "^6.26.0", - "lodash": "^4.17.4" - } + "brorand": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/brorand/-/brorand-1.1.0.tgz", + "integrity": "sha1-EsJe/kCkXjwyPrhnWgoM5XsiNx8=" }, - "babel-helper-remap-async-to-generator": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-remap-async-to-generator/-/babel-helper-remap-async-to-generator-6.24.1.tgz", - "integrity": "sha1-XsWBgnrXI/7N04HxySg5BnbkVRs=", - "requires": { - "babel-helper-function-name": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" - } + "browser-stdout": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/browser-stdout/-/browser-stdout-1.3.0.tgz", + "integrity": "sha1-81HTKWnTL6XXpVZxVCY9korjvR8=" }, - "babel-helper-replace-supers": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helper-replace-supers/-/babel-helper-replace-supers-6.24.1.tgz", - "integrity": "sha1-v22/5Dk40XNpohPKiov3S2qQqxo=", + "browserify-sha3": { + "version": "0.0.4", + "resolved": "https://registry.npmjs.org/browserify-sha3/-/browserify-sha3-0.0.4.tgz", + "integrity": "sha1-CGxHuMgjFsnUcCLCYYWVRXbdjiY=", + "dev": true, "requires": { - "babel-helper-optimise-call-expression": "^6.24.1", - "babel-messages": "^6.23.0", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" + "js-sha3": "^0.6.1", + "safe-buffer": "^5.1.1" } }, - "babel-helpers": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-helpers/-/babel-helpers-6.24.1.tgz", - "integrity": "sha1-NHHenK7DiOXIUOWX5Yom3fN2ArI=", - "requires": { - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" - } + "buffer-from": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.1.tgz", + "integrity": "sha512-MQcXEUbCKtEo7bhqEs6560Hyd4XaovZlO/k9V3hjVUF/zwW7KBVdSK4gIt/bzwS9MbR5qob+F5jusZsb0YQK2A==", + "dev": true }, - "babel-messages": { - "version": "6.23.0", - "resolved": "https://registry.npmjs.org/babel-messages/-/babel-messages-6.23.0.tgz", - "integrity": "sha1-8830cDhYA1sqKVHG7F7fbGLyYw4=", - "requires": { - "babel-runtime": "^6.22.0" - } + "buffer-to-arraybuffer": { + "version": "0.0.5", + "resolved": "https://registry.npmjs.org/buffer-to-arraybuffer/-/buffer-to-arraybuffer-0.0.5.tgz", + "integrity": "sha1-YGSkD6dutDxyOrqe+PbhIW0QURo=" }, - "babel-plugin-check-es2015-constants": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-check-es2015-constants/-/babel-plugin-check-es2015-constants-6.22.0.tgz", - "integrity": "sha1-NRV7EBQm/S/9PaP3XH0ekYNbv4o=", + "cache-base": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/cache-base/-/cache-base-1.0.1.tgz", + "integrity": "sha512-AKcdTnFSWATd5/GCPRxr2ChwIJ85CeyrEyjRHlKxQ56d4XJMGym0uAiKn0xbLOGOl3+yRpOTi484dVCEc5AUzQ==", + "dev": true, "requires": { - "babel-runtime": "^6.22.0" + "collection-visit": "^1.0.0", + "component-emitter": "^1.2.1", + "get-value": "^2.0.6", + "has-value": "^1.0.0", + "isobject": "^3.0.1", + "set-value": "^2.0.0", + "to-object-path": "^0.3.0", + "union-value": "^1.0.0", + "unset-value": "^1.0.0" } }, - "babel-plugin-syntax-async-functions": { - "version": "6.13.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-async-functions/-/babel-plugin-syntax-async-functions-6.13.0.tgz", - "integrity": "sha1-ytnK0RkbWtY0vzCuCHI5HgZHvpU=" - }, - "babel-plugin-syntax-async-generators": { - "version": "6.13.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-async-generators/-/babel-plugin-syntax-async-generators-6.13.0.tgz", - "integrity": "sha1-a8lj67FuzLrmuStZbrfzXDQqi5o=" - }, - "babel-plugin-syntax-class-constructor-call": { - "version": "6.18.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-class-constructor-call/-/babel-plugin-syntax-class-constructor-call-6.18.0.tgz", - "integrity": "sha1-nLnTn+Q8hgC+yBRkVt3L1OGnZBY=" - }, - "babel-plugin-syntax-class-properties": { - "version": "6.13.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-class-properties/-/babel-plugin-syntax-class-properties-6.13.0.tgz", - "integrity": "sha1-1+sjt5oxf4VDlixQW4J8fWysJ94=" - }, - "babel-plugin-syntax-decorators": { - "version": "6.13.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-decorators/-/babel-plugin-syntax-decorators-6.13.0.tgz", - "integrity": "sha1-MSVjtNvePMgGzuPkFszurd0RrAs=" - }, - "babel-plugin-syntax-dynamic-import": { - "version": "6.18.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-dynamic-import/-/babel-plugin-syntax-dynamic-import-6.18.0.tgz", - "integrity": "sha1-jWomIpyDdFqZgqRBBRVyyqF5sdo=" - }, - "babel-plugin-syntax-exponentiation-operator": { - "version": "6.13.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-exponentiation-operator/-/babel-plugin-syntax-exponentiation-operator-6.13.0.tgz", - "integrity": "sha1-nufoM3KQ2pUoggGmpX9BcDF4MN4=" - }, - "babel-plugin-syntax-export-extensions": { - "version": "6.13.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-export-extensions/-/babel-plugin-syntax-export-extensions-6.13.0.tgz", - "integrity": "sha1-cKFITw+QiaToStRLrDU8lbmxJyE=" - }, - "babel-plugin-syntax-flow": { - "version": "6.18.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-flow/-/babel-plugin-syntax-flow-6.18.0.tgz", - "integrity": "sha1-TDqyCiryaqIM0lmVw5jE63AxDI0=" + "camelcase": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-3.0.0.tgz", + "integrity": "sha1-MvxLn82vhF/N9+c7uXysImHwqwo=" }, - "babel-plugin-syntax-object-rest-spread": { - "version": "6.13.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-object-rest-spread/-/babel-plugin-syntax-object-rest-spread-6.13.0.tgz", - "integrity": "sha1-/WU28rzhODb/o6VFjEkDpZe7O/U=" + "capture-stack-trace": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/capture-stack-trace/-/capture-stack-trace-1.0.1.tgz", + "integrity": "sha512-mYQLZnx5Qt1JgB1WEiMCf2647plpGeQ2NMR/5L0HNZzGQo4fuSPnK+wjfPnKZV0aiJDgzmWqqkV/g7JD+DW0qw==", + "dev": true }, - "babel-plugin-syntax-trailing-function-commas": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-syntax-trailing-function-commas/-/babel-plugin-syntax-trailing-function-commas-6.22.0.tgz", - "integrity": "sha1-ugNgk3+NBuQBgKQ/4NVhb/9TLPM=" + "caseless": { + "version": "0.12.0", + "resolved": "https://registry.npmjs.org/caseless/-/caseless-0.12.0.tgz", + "integrity": "sha1-G2gcIf+EAzyCZUMJBolCDRhxUdw=", + "dev": true }, - "babel-plugin-transform-async-generator-functions": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-async-generator-functions/-/babel-plugin-transform-async-generator-functions-6.24.1.tgz", - "integrity": "sha1-8FiQAUX9PpkHpt3yjaWfIVJYpds=", + "chai": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/chai/-/chai-4.2.0.tgz", + "integrity": "sha512-XQU3bhBukrOsQCuwZndwGcCVQHyZi53fQ6Ys1Fym7E4olpIqqZZhhoFJoaKVvV17lWQoXYwgWN2nF5crA8J2jw==", + "dev": true, "requires": { - "babel-helper-remap-async-to-generator": "^6.24.1", - "babel-plugin-syntax-async-generators": "^6.5.0", - "babel-runtime": "^6.22.0" + "assertion-error": "^1.1.0", + "check-error": "^1.0.2", + "deep-eql": "^3.0.1", + "get-func-name": "^2.0.0", + "pathval": "^1.1.0", + "type-detect": "^4.0.5" } }, - "babel-plugin-transform-async-to-generator": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-async-to-generator/-/babel-plugin-transform-async-to-generator-6.24.1.tgz", - "integrity": "sha1-ZTbjeK/2yx1VF6wOQOs+n8jQh2E=", + "chai-as-promised": { + "version": "7.1.1", + "resolved": "https://registry.npmjs.org/chai-as-promised/-/chai-as-promised-7.1.1.tgz", + "integrity": "sha512-azL6xMoi+uxu6z4rhWQ1jbdUhOMhis2PvscD/xjLqNMkv3BPPp2JyyuTHOrf9BOosGpNQ11v6BKv/g57RXbiaA==", + "dev": true, "requires": { - "babel-helper-remap-async-to-generator": "^6.24.1", - "babel-plugin-syntax-async-functions": "^6.8.0", - "babel-runtime": "^6.22.0" + "check-error": "^1.0.2" } }, - "babel-plugin-transform-class-constructor-call": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-class-constructor-call/-/babel-plugin-transform-class-constructor-call-6.24.1.tgz", - "integrity": "sha1-gNwoVQWsBn3LjWxl4vbxGrd2Xvk=", - "requires": { - "babel-plugin-syntax-class-constructor-call": "^6.18.0", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" - } + "chai-bignumber": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/chai-bignumber/-/chai-bignumber-2.0.2.tgz", + "integrity": "sha512-BIdRNjRaoRj4bMsZLKbIZPMNKqmwnzNiyxqBYDSs6dFOCs9w8OHPuUE8e1bH60i1IhOzT0NjLtCD+lKEWB1KTQ==", + "dev": true }, - "babel-plugin-transform-class-properties": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-class-properties/-/babel-plugin-transform-class-properties-6.24.1.tgz", - "integrity": "sha1-anl2PqYdM9NvN7YRqp3vgagbRqw=", + "chalk": { + "version": "2.4.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz", + "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==", + "dev": true, "requires": { - "babel-helper-function-name": "^6.24.1", - "babel-plugin-syntax-class-properties": "^6.8.0", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" + "ansi-styles": "^3.2.1", + "escape-string-regexp": "^1.0.5", + "supports-color": "^5.3.0" + }, + "dependencies": { + "has-flag": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", + "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=", + "dev": true + }, + "supports-color": { + "version": "5.5.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", + "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", + "dev": true, + "requires": { + "has-flag": "^3.0.0" + } + } } }, - "babel-plugin-transform-decorators": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-decorators/-/babel-plugin-transform-decorators-6.24.1.tgz", - "integrity": "sha1-eIAT2PjGtSIr33s0Q5Df13Vp4k0=", - "requires": { - "babel-helper-explode-class": "^6.24.1", - "babel-plugin-syntax-decorators": "^6.13.0", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-types": "^6.24.1" - } + "charenc": { + "version": "0.0.2", + "resolved": "https://registry.npmjs.org/charenc/-/charenc-0.0.2.tgz", + "integrity": "sha1-wKHS86cJLgN3S/qD8UwPxXkKhmc=", + "dev": true }, - "babel-plugin-transform-es2015-arrow-functions": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-arrow-functions/-/babel-plugin-transform-es2015-arrow-functions-6.22.0.tgz", - "integrity": "sha1-RSaSy3EdX3ncf4XkQM5BufJE0iE=", - "requires": { - "babel-runtime": "^6.22.0" - } + "check-error": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/check-error/-/check-error-1.0.2.tgz", + "integrity": "sha1-V00xLt2Iu13YkS6Sht1sCu1KrII=", + "dev": true }, - "babel-plugin-transform-es2015-block-scoped-functions": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-block-scoped-functions/-/babel-plugin-transform-es2015-block-scoped-functions-6.22.0.tgz", - "integrity": "sha1-u8UbSflk1wy42OC5ToICRs46YUE=", + "chokidar": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-2.1.1.tgz", + "integrity": "sha512-gfw3p2oQV2wEt+8VuMlNsPjCxDxvvgnm/kz+uATu805mWVF8IJN7uz9DN7iBz+RMJISmiVbCOBFs9qBGMjtPfQ==", + "dev": true, "requires": { - "babel-runtime": "^6.22.0" + "anymatch": "^2.0.0", + "async-each": "^1.0.1", + "braces": "^2.3.2", + "fsevents": "^1.2.7", + "glob-parent": "^3.1.0", + "inherits": "^2.0.3", + "is-binary-path": "^1.0.0", + "is-glob": "^4.0.0", + "normalize-path": "^3.0.0", + "path-is-absolute": "^1.0.0", + "readdirp": "^2.2.1", + "upath": "^1.1.0" } }, - "babel-plugin-transform-es2015-block-scoping": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-block-scoping/-/babel-plugin-transform-es2015-block-scoping-6.26.0.tgz", - "integrity": "sha1-1w9SmcEwjQXBL0Y4E7CgnnOxiV8=", - "requires": { - "babel-runtime": "^6.26.0", - "babel-template": "^6.26.0", - "babel-traverse": "^6.26.0", - "babel-types": "^6.26.0", - "lodash": "^4.17.4" - } + "ci-info": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/ci-info/-/ci-info-1.6.0.tgz", + "integrity": "sha512-vsGdkwSCDpWmP80ncATX7iea5DWQemg1UgCW5J8tqjU3lYw4FBYuj89J0CTVomA7BEfvSZd84GmHko+MxFQU2A==", + "dev": true }, - "babel-plugin-transform-es2015-classes": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-classes/-/babel-plugin-transform-es2015-classes-6.24.1.tgz", - "integrity": "sha1-WkxYpQyclGHlZLSyo7+ryXolhNs=", + "class-utils": { + "version": "0.3.6", + "resolved": "https://registry.npmjs.org/class-utils/-/class-utils-0.3.6.tgz", + "integrity": "sha512-qOhPa/Fj7s6TY8H8esGu5QNpMMQxz79h+urzrNYN6mn+9BnxlDGf5QZ+XeCDsxSjPqsSR56XOZOJmpeurnLMeg==", + "dev": true, "requires": { - "babel-helper-define-map": "^6.24.1", - "babel-helper-function-name": "^6.24.1", - "babel-helper-optimise-call-expression": "^6.24.1", - "babel-helper-replace-supers": "^6.24.1", - "babel-messages": "^6.23.0", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" + "arr-union": "^3.1.0", + "define-property": "^0.2.5", + "isobject": "^3.0.0", + "static-extend": "^0.1.1" + }, + "dependencies": { + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "dev": true, + "requires": { + "is-descriptor": "^0.1.0" + } + } } }, - "babel-plugin-transform-es2015-computed-properties": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-computed-properties/-/babel-plugin-transform-es2015-computed-properties-6.24.1.tgz", - "integrity": "sha1-b+Ko0WiV1WNPTNmZttNICjCBWbM=", - "requires": { - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" - } + "cli-boxes": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/cli-boxes/-/cli-boxes-1.0.0.tgz", + "integrity": "sha1-T6kXw+WclKAEzWH47lCdplFocUM=", + "dev": true }, - "babel-plugin-transform-es2015-destructuring": { - "version": "6.23.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-destructuring/-/babel-plugin-transform-es2015-destructuring-6.23.0.tgz", - "integrity": "sha1-mXux8auWf2gtKwh2/jWNYOdlxW0=", + "cli-table3": { + "version": "0.5.1", + "resolved": "https://registry.npmjs.org/cli-table3/-/cli-table3-0.5.1.tgz", + "integrity": "sha512-7Qg2Jrep1S/+Q3EceiZtQcDPWxhAvBw+ERf1162v4sikJrvojMHFqXt8QIVha8UlH9rgU0BeWPytZ9/TzYqlUw==", + "dev": true, "requires": { - "babel-runtime": "^6.22.0" + "colors": "^1.1.2", + "object-assign": "^4.1.0", + "string-width": "^2.1.1" + }, + "dependencies": { + "ansi-regex": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", + "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=", + "dev": true + }, + "is-fullwidth-code-point": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", + "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=", + "dev": true + }, + "string-width": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", + "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", + "dev": true, + "requires": { + "is-fullwidth-code-point": "^2.0.0", + "strip-ansi": "^4.0.0" + } + }, + "strip-ansi": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", + "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", + "dev": true, + "requires": { + "ansi-regex": "^3.0.0" + } + } } }, - "babel-plugin-transform-es2015-duplicate-keys": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-duplicate-keys/-/babel-plugin-transform-es2015-duplicate-keys-6.24.1.tgz", - "integrity": "sha1-c+s9MQypaePvnskcU3QabxV2Qj4=", + "cliui": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/cliui/-/cliui-3.2.0.tgz", + "integrity": "sha1-EgYBU3qRbSmUD5NNo7SNWFo5IT0=", "requires": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" + "string-width": "^1.0.1", + "strip-ansi": "^3.0.1", + "wrap-ansi": "^2.0.0" } }, - "babel-plugin-transform-es2015-for-of": { - "version": "6.23.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-for-of/-/babel-plugin-transform-es2015-for-of-6.23.0.tgz", - "integrity": "sha1-9HyVsrYT3x0+zC/bdXNiPHUkhpE=", - "requires": { - "babel-runtime": "^6.22.0" - } + "code-point-at": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/code-point-at/-/code-point-at-1.1.0.tgz", + "integrity": "sha1-DQcLTQQ6W+ozovGkDi7bPZpMz3c=" }, - "babel-plugin-transform-es2015-function-name": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-function-name/-/babel-plugin-transform-es2015-function-name-6.24.1.tgz", - "integrity": "sha1-g0yJhTvDaxrw86TF26qU/Y6sqos=", + "collection-visit": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/collection-visit/-/collection-visit-1.0.0.tgz", + "integrity": "sha1-S8A3PBZLwykbTTaMgpzxqApZ3KA=", + "dev": true, "requires": { - "babel-helper-function-name": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" + "map-visit": "^1.0.0", + "object-visit": "^1.0.0" } }, - "babel-plugin-transform-es2015-literals": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-literals/-/babel-plugin-transform-es2015-literals-6.22.0.tgz", - "integrity": "sha1-T1SgLWzWbPkVKAAZox0xklN3yi4=", + "color-convert": { + "version": "1.9.3", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.3.tgz", + "integrity": "sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==", + "dev": true, "requires": { - "babel-runtime": "^6.22.0" + "color-name": "1.1.3" } }, - "babel-plugin-transform-es2015-modules-amd": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-modules-amd/-/babel-plugin-transform-es2015-modules-amd-6.24.1.tgz", - "integrity": "sha1-Oz5UAXI5hC1tGcMBHEvS8AoA0VQ=", - "requires": { - "babel-plugin-transform-es2015-modules-commonjs": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" - } + "color-name": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz", + "integrity": "sha1-p9BVi9icQveV3UIyj3QIMcpTvCU=", + "dev": true }, - "babel-plugin-transform-es2015-modules-commonjs": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-modules-commonjs/-/babel-plugin-transform-es2015-modules-commonjs-6.26.0.tgz", - "integrity": "sha1-DYOUApt9xqvhqX7xgeAHWN0uXYo=", - "requires": { - "babel-plugin-transform-strict-mode": "^6.24.1", - "babel-runtime": "^6.26.0", - "babel-template": "^6.26.0", - "babel-types": "^6.26.0" - } + "colors": { + "version": "1.3.3", + "resolved": "https://registry.npmjs.org/colors/-/colors-1.3.3.tgz", + "integrity": "sha512-mmGt/1pZqYRjMxB1axhTo16/snVZ5krrKkcmMeVKxzECMMXoCgnvTPp10QgHfcbQZw8Dq2jMNG6je4JlWU0gWg==", + "dev": true }, - "babel-plugin-transform-es2015-modules-systemjs": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-modules-systemjs/-/babel-plugin-transform-es2015-modules-systemjs-6.24.1.tgz", - "integrity": "sha1-/4mhQrkRmpBhlfXxBuzzBdlAfSM=", - "requires": { - "babel-helper-hoist-variables": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" - } - }, - "babel-plugin-transform-es2015-modules-umd": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-modules-umd/-/babel-plugin-transform-es2015-modules-umd-6.24.1.tgz", - "integrity": "sha1-rJl+YoXNGO1hdq22B9YCNErThGg=", - "requires": { - "babel-plugin-transform-es2015-modules-amd": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1" - } - }, - "babel-plugin-transform-es2015-object-super": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-object-super/-/babel-plugin-transform-es2015-object-super-6.24.1.tgz", - "integrity": "sha1-JM72muIcuDp/hgPa0CH1cusnj40=", - "requires": { - "babel-helper-replace-supers": "^6.24.1", - "babel-runtime": "^6.22.0" - } - }, - "babel-plugin-transform-es2015-parameters": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-parameters/-/babel-plugin-transform-es2015-parameters-6.24.1.tgz", - "integrity": "sha1-V6w1GrScrxSpfNE7CfZv3wpiXys=", + "combined-stream": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.7.tgz", + "integrity": "sha512-brWl9y6vOB1xYPZcpZde3N9zDByXTosAeMDo4p1wzo6UMOX4vumB+TP1RZ76sfE6Md68Q0NJSrE/gbezd4Ul+w==", + "dev": true, "requires": { - "babel-helper-call-delegate": "^6.24.1", - "babel-helper-get-function-arity": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-template": "^6.24.1", - "babel-traverse": "^6.24.1", - "babel-types": "^6.24.1" + "delayed-stream": "~1.0.0" } }, - "babel-plugin-transform-es2015-shorthand-properties": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-shorthand-properties/-/babel-plugin-transform-es2015-shorthand-properties-6.24.1.tgz", - "integrity": "sha1-JPh11nIch2YbvZmkYi5R8U3jiqA=", - "requires": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } + "commander": { + "version": "2.11.0", + "resolved": "https://registry.npmjs.org/commander/-/commander-2.11.0.tgz", + "integrity": "sha512-b0553uYA5YAEGgyYIGYROzKQ7X5RAqedkfjiZxwi0kL1g3bOaBNNZfYkzt/CL0umgD5wc9Jec2FbB98CjkMRvQ==" }, - "babel-plugin-transform-es2015-spread": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-spread/-/babel-plugin-transform-es2015-spread-6.22.0.tgz", - "integrity": "sha1-1taKmfia7cRTbIGlQujdnxdG+NE=", - "requires": { - "babel-runtime": "^6.22.0" - } + "component-emitter": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/component-emitter/-/component-emitter-1.2.1.tgz", + "integrity": "sha1-E3kY1teCg/ffemt8WmPhQOaUJeY=", + "dev": true }, - "babel-plugin-transform-es2015-sticky-regex": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-sticky-regex/-/babel-plugin-transform-es2015-sticky-regex-6.24.1.tgz", - "integrity": "sha1-AMHNsaynERLN8M9hJsLta0V8zbw=", - "requires": { - "babel-helper-regex": "^6.24.1", - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } + "concat-map": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", + "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=" }, - "babel-plugin-transform-es2015-template-literals": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-template-literals/-/babel-plugin-transform-es2015-template-literals-6.22.0.tgz", - "integrity": "sha1-qEs0UPfp+PH2g51taH2oS7EjbY0=", + "concat-stream": { + "version": "1.6.2", + "resolved": "https://registry.npmjs.org/concat-stream/-/concat-stream-1.6.2.tgz", + "integrity": "sha512-27HBghJxjiZtIk3Ycvn/4kbJk/1uZuJFfuPEns6LaEvpvG1f0hTea8lilrouyo9mVc2GWdcEZ8OLoGmSADlrCw==", + "dev": true, "requires": { - "babel-runtime": "^6.22.0" + "buffer-from": "^1.0.0", + "inherits": "^2.0.3", + "readable-stream": "^2.2.2", + "typedarray": "^0.0.6" } }, - "babel-plugin-transform-es2015-typeof-symbol": { - "version": "6.23.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-typeof-symbol/-/babel-plugin-transform-es2015-typeof-symbol-6.23.0.tgz", - "integrity": "sha1-3sCfHN3/lLUqxz1QXITfWdzOs3I=", + "configstore": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/configstore/-/configstore-3.1.2.tgz", + "integrity": "sha512-vtv5HtGjcYUgFrXc6Kx747B83MRRVS5R1VTEQoXvuP+kMI+if6uywV0nDGoiydJRy4yk7h9od5Og0kxx4zUXmw==", + "dev": true, "requires": { - "babel-runtime": "^6.22.0" + "dot-prop": "^4.1.0", + "graceful-fs": "^4.1.2", + "make-dir": "^1.0.0", + "unique-string": "^1.0.0", + "write-file-atomic": "^2.0.0", + "xdg-basedir": "^3.0.0" } }, - "babel-plugin-transform-es2015-unicode-regex": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-unicode-regex/-/babel-plugin-transform-es2015-unicode-regex-6.24.1.tgz", - "integrity": "sha1-04sS9C6nMj9yk4fxinxa4frrNek=", - "requires": { - "babel-helper-regex": "^6.24.1", - "babel-runtime": "^6.22.0", - "regexpu-core": "^2.0.0" - } + "copy-descriptor": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/copy-descriptor/-/copy-descriptor-0.1.1.tgz", + "integrity": "sha1-Z29us8OZl8LuGsOpJP1hJHSPV40=", + "dev": true }, - "babel-plugin-transform-exponentiation-operator": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-exponentiation-operator/-/babel-plugin-transform-exponentiation-operator-6.24.1.tgz", - "integrity": "sha1-KrDJx/MJj6SJB3cruBP+QejeOg4=", - "requires": { - "babel-helper-builder-binary-assignment-operator-visitor": "^6.24.1", - "babel-plugin-syntax-exponentiation-operator": "^6.8.0", - "babel-runtime": "^6.22.0" - } + "core-util-is": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz", + "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=", + "dev": true }, - "babel-plugin-transform-export-extensions": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-export-extensions/-/babel-plugin-transform-export-extensions-6.22.0.tgz", - "integrity": "sha1-U3OLR+deghhYnuqUbLvTkQm75lM=", + "create-error-class": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/create-error-class/-/create-error-class-3.0.2.tgz", + "integrity": "sha1-Br56vvlHo/FKMP1hBnHUAbyot7Y=", + "dev": true, "requires": { - "babel-plugin-syntax-export-extensions": "^6.8.0", - "babel-runtime": "^6.22.0" + "capture-stack-trace": "^1.0.0" } }, - "babel-plugin-transform-flow-strip-types": { - "version": "6.22.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-flow-strip-types/-/babel-plugin-transform-flow-strip-types-6.22.0.tgz", - "integrity": "sha1-hMtnKTXUNxT9wyvOhFaNh0Qc988=", + "cross-spawn": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-5.1.0.tgz", + "integrity": "sha1-6L0O/uWPz/b4+UUQoKVUu/ojVEk=", + "dev": true, "requires": { - "babel-plugin-syntax-flow": "^6.18.0", - "babel-runtime": "^6.22.0" + "lru-cache": "^4.0.1", + "shebang-command": "^1.2.0", + "which": "^1.2.9" } }, - "babel-plugin-transform-object-rest-spread": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-object-rest-spread/-/babel-plugin-transform-object-rest-spread-6.26.0.tgz", - "integrity": "sha1-DzZpLVD+9rfi1LOsFHgTepY7ewY=", - "requires": { - "babel-plugin-syntax-object-rest-spread": "^6.8.0", - "babel-runtime": "^6.26.0" - } + "crypt": { + "version": "0.0.2", + "resolved": "https://registry.npmjs.org/crypt/-/crypt-0.0.2.tgz", + "integrity": "sha1-iNf/fsDfuG9xPch7u0LQRNPmxBs=", + "dev": true }, - "babel-plugin-transform-regenerator": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-regenerator/-/babel-plugin-transform-regenerator-6.26.0.tgz", - "integrity": "sha1-4HA2lvveJ/Cj78rPi03KL3s6jy8=", - "requires": { - "regenerator-transform": "^0.10.0" - } + "crypto-js": { + "version": "3.1.8", + "resolved": "https://registry.npmjs.org/crypto-js/-/crypto-js-3.1.8.tgz", + "integrity": "sha1-cV8HC/YBTyrpkqmLOSkli3E/CNU=", + "dev": true }, - "babel-plugin-transform-strict-mode": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-strict-mode/-/babel-plugin-transform-strict-mode-6.24.1.tgz", - "integrity": "sha1-1fr3qleKZbvlkc9e2uBKDGcCB1g=", - "requires": { - "babel-runtime": "^6.22.0", - "babel-types": "^6.24.1" - } + "crypto-random-string": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/crypto-random-string/-/crypto-random-string-1.0.0.tgz", + "integrity": "sha1-ojD2T1aDEOFJgAmUB5DsmVRbyn4=", + "dev": true }, - "babel-preset-es2015": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-preset-es2015/-/babel-preset-es2015-6.24.1.tgz", - "integrity": "sha1-1EBQ1rwsn+6nAqrzjXJ6AhBTiTk=", + "dashdash": { + "version": "1.14.1", + "resolved": "https://registry.npmjs.org/dashdash/-/dashdash-1.14.1.tgz", + "integrity": "sha1-hTz6D3y+L+1d4gMmuN1YEDX24vA=", + "dev": true, "requires": { - "babel-plugin-check-es2015-constants": "^6.22.0", - "babel-plugin-transform-es2015-arrow-functions": "^6.22.0", - "babel-plugin-transform-es2015-block-scoped-functions": "^6.22.0", - "babel-plugin-transform-es2015-block-scoping": "^6.24.1", - "babel-plugin-transform-es2015-classes": "^6.24.1", - "babel-plugin-transform-es2015-computed-properties": "^6.24.1", - "babel-plugin-transform-es2015-destructuring": "^6.22.0", - "babel-plugin-transform-es2015-duplicate-keys": "^6.24.1", - "babel-plugin-transform-es2015-for-of": "^6.22.0", - "babel-plugin-transform-es2015-function-name": "^6.24.1", - "babel-plugin-transform-es2015-literals": "^6.22.0", - "babel-plugin-transform-es2015-modules-amd": "^6.24.1", - "babel-plugin-transform-es2015-modules-commonjs": "^6.24.1", - "babel-plugin-transform-es2015-modules-systemjs": "^6.24.1", - "babel-plugin-transform-es2015-modules-umd": "^6.24.1", - "babel-plugin-transform-es2015-object-super": "^6.24.1", - "babel-plugin-transform-es2015-parameters": "^6.24.1", - "babel-plugin-transform-es2015-shorthand-properties": "^6.24.1", - "babel-plugin-transform-es2015-spread": "^6.22.0", - "babel-plugin-transform-es2015-sticky-regex": "^6.24.1", - "babel-plugin-transform-es2015-template-literals": "^6.22.0", - "babel-plugin-transform-es2015-typeof-symbol": "^6.22.0", - "babel-plugin-transform-es2015-unicode-regex": "^6.24.1", - "babel-plugin-transform-regenerator": "^6.24.1" + "assert-plus": "^1.0.0" } }, - "babel-preset-stage-1": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-preset-stage-1/-/babel-preset-stage-1-6.24.1.tgz", - "integrity": "sha1-dpLNfc1oSZB+auSgqFWJz7niv7A=", - "requires": { - "babel-plugin-transform-class-constructor-call": "^6.24.1", - "babel-plugin-transform-export-extensions": "^6.22.0", - "babel-preset-stage-2": "^6.24.1" - } + "death": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/death/-/death-1.1.0.tgz", + "integrity": "sha1-AaqcQB7dknUFFEcLgmY5DGbGcxg=", + "dev": true }, - "babel-preset-stage-2": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-preset-stage-2/-/babel-preset-stage-2-6.24.1.tgz", - "integrity": "sha1-2eKWD7PXEYfw5k7sYrwHdnIZvcE=", + "debug": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", + "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", "requires": { - "babel-plugin-syntax-dynamic-import": "^6.18.0", - "babel-plugin-transform-class-properties": "^6.24.1", - "babel-plugin-transform-decorators": "^6.24.1", - "babel-preset-stage-3": "^6.24.1" - } - }, - "babel-preset-stage-3": { - "version": "6.24.1", - "resolved": "https://registry.npmjs.org/babel-preset-stage-3/-/babel-preset-stage-3-6.24.1.tgz", - "integrity": "sha1-g2raCp56f6N8sTj7kyb4eTSkg5U=", - "requires": { - "babel-plugin-syntax-trailing-function-commas": "^6.22.0", - "babel-plugin-transform-async-generator-functions": "^6.24.1", - "babel-plugin-transform-async-to-generator": "^6.24.1", - "babel-plugin-transform-exponentiation-operator": "^6.24.1", - "babel-plugin-transform-object-rest-spread": "^6.22.0" + "ms": "2.0.0" } }, - "babel-register": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-register/-/babel-register-6.26.0.tgz", - "integrity": "sha1-btAhFz4vy0htestFxgCahW9kcHE=", - "requires": { - "babel-core": "^6.26.0", - "babel-runtime": "^6.26.0", - "core-js": "^2.5.0", - "home-or-tmp": "^2.0.0", - "lodash": "^4.17.4", - "mkdirp": "^0.5.1", - "source-map-support": "^0.4.15" - }, - "dependencies": { - "source-map-support": { - "version": "0.4.18", - "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.4.18.tgz", - "integrity": "sha512-try0/JqxPLF9nOjvSta7tVondkP5dwgyLDjVoyMDlmjugT2lRZ1OfsrYTkCd2hkDnJTKRbO/Rl3orm8vlsUzbA==", - "requires": { - "source-map": "^0.5.6" - } - } - } + "decamelize": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/decamelize/-/decamelize-1.2.0.tgz", + "integrity": "sha1-9lNNFRSCabIDUue+4m9QH5oZEpA=" }, - "babel-runtime": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-runtime/-/babel-runtime-6.26.0.tgz", - "integrity": "sha1-llxwWGaOgrVde/4E/yM3vItWR/4=", - "requires": { - "core-js": "^2.4.0", - "regenerator-runtime": "^0.11.0" - } + "decode-uri-component": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/decode-uri-component/-/decode-uri-component-0.2.0.tgz", + "integrity": "sha1-6zkTMzRYd1y4TNGh+uBiEGu4dUU=" }, - "babel-template": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-template/-/babel-template-6.26.0.tgz", - "integrity": "sha1-3gPi0WOWsGn0bdn/+FIfsaDjXgI=", + "decompress-response": { + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/decompress-response/-/decompress-response-3.3.0.tgz", + "integrity": "sha1-gKTdMjdIOEv6JICDYirt7Jgq3/M=", "requires": { - "babel-runtime": "^6.26.0", - "babel-traverse": "^6.26.0", - "babel-types": "^6.26.0", - "babylon": "^6.18.0", - "lodash": "^4.17.4" - }, - "dependencies": { - "babylon": { - "version": "6.18.0", - "resolved": "https://registry.npmjs.org/babylon/-/babylon-6.18.0.tgz", - "integrity": "sha512-q/UEjfGJ2Cm3oKV71DJz9d25TPnq5rhBVL2Q4fA5wcC3jcrdn7+SssEybFIxwAvvP+YCsCYNKughoF33GxgycQ==" - } - } - }, - "babel-traverse": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-traverse/-/babel-traverse-6.26.0.tgz", - "integrity": "sha1-RqnL1+3MYsjlwGTi0tjQ9ANXZu4=", - "requires": { - "babel-code-frame": "^6.26.0", - "babel-messages": "^6.23.0", - "babel-runtime": "^6.26.0", - "babel-types": "^6.26.0", - "babylon": "^6.18.0", - "debug": "^2.6.8", - "globals": "^9.18.0", - "invariant": "^2.2.2", - "lodash": "^4.17.4" - }, - "dependencies": { - "babylon": { - "version": "6.18.0", - "resolved": "https://registry.npmjs.org/babylon/-/babylon-6.18.0.tgz", - "integrity": "sha512-q/UEjfGJ2Cm3oKV71DJz9d25TPnq5rhBVL2Q4fA5wcC3jcrdn7+SssEybFIxwAvvP+YCsCYNKughoF33GxgycQ==" - } + "mimic-response": "^1.0.0" } }, - "babel-types": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-types/-/babel-types-6.26.0.tgz", - "integrity": "sha1-o7Bz+Uq0nrb6Vc1lInozQ4BjJJc=", + "deep-eql": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/deep-eql/-/deep-eql-3.0.1.tgz", + "integrity": "sha512-+QeIQyN5ZuO+3Uk5DYh6/1eKO0m0YmJFGNmFHGACpf1ClL1nmlV/p4gNgbl2pJGxgXb4faqo6UE+M5ACEMyVcw==", + "dev": true, "requires": { - "babel-runtime": "^6.26.0", - "esutils": "^2.0.2", - "lodash": "^4.17.4", - "to-fast-properties": "^1.0.3" + "type-detect": "^4.0.0" } }, - "babylon": { - "version": "7.0.0-beta.42", - "resolved": "https://registry.npmjs.org/babylon/-/babylon-7.0.0-beta.42.tgz", - "integrity": "sha512-h6E/OkkvcBw/JimbL0p8dIaxrcuQn3QmIYGC/GtJlRYif5LTKBYPHXYwqluJpfS/kOXoz0go+9mkmOVC0M+zWw==" + "deep-extend": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/deep-extend/-/deep-extend-0.6.0.tgz", + "integrity": "sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA==", + "dev": true }, - "balanced-match": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz", - "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=" + "deep-is": { + "version": "0.1.3", + "resolved": "https://registry.npmjs.org/deep-is/-/deep-is-0.1.3.tgz", + "integrity": "sha1-s2nW+128E+7PUk+RsHD+7cNXzzQ=", + "dev": true }, - "base": { - "version": "0.11.2", - "resolved": "https://registry.npmjs.org/base/-/base-0.11.2.tgz", - "integrity": "sha512-5T6P4xPgpp0YDFvSWwEZ4NoE3aM4QBQXDzmVbraCkFj8zHM+mba8SyqB5DbZWyR7mYHo6Y7BdQo3MoA4m0TeQg==", + "define-property": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-2.0.2.tgz", + "integrity": "sha512-jwK2UV4cnPpbcG7+VRARKTZPUWowwXA8bzH5NP6ud0oeAxyYPuGZUAC7hMugpCdz4BeSZl2Dl9k66CHJ/46ZYQ==", "dev": true, "requires": { - "cache-base": "^1.0.1", - "class-utils": "^0.3.5", - "component-emitter": "^1.2.1", - "define-property": "^1.0.0", - "isobject": "^3.0.1", - "mixin-deep": "^1.2.0", - "pascalcase": "^0.1.1" + "is-descriptor": "^1.0.2", + "isobject": "^3.0.1" }, "dependencies": { - "define-property": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/define-property/-/define-property-1.0.0.tgz", - "integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=", - "dev": true, - "requires": { - "is-descriptor": "^1.0.0" - } - }, "is-accessor-descriptor": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz", @@ -1170,381 +964,211 @@ } } }, - "bcrypt-pbkdf": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.1.tgz", - "integrity": "sha1-Y7xdy2EzG5K8Bf1SiVPDNGKgb40=", - "optional": true, - "requires": { - "tweetnacl": "^0.14.3" - } - }, - "big.js": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/big.js/-/big.js-3.2.0.tgz", - "integrity": "sha512-+hN/Zh2D08Mx65pZ/4g5bsmNiZUuChDiQfTUQ7qJr4/kuopCr88xZsAXv6mBoZEsUI4OuGHlX59qE94K2mMW8Q==" - }, - "bignumber.js": { - "version": "git+https://github.com/frozeman/bignumber.js-nolookahead.git#57692b3ecfc98bbdd6b3a516cb2353652ea49934", - "from": "bignumber.js@git+https://github.com/frozeman/bignumber.js-nolookahead.git#57692b3ecfc98bbdd6b3a516cb2353652ea49934", + "delayed-stream": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", + "integrity": "sha1-3zrhmayt+31ECqrgsp4icrJOxhk=", "dev": true }, - "binary-extensions": { - "version": "1.11.0", - "resolved": "https://registry.npmjs.org/binary-extensions/-/binary-extensions-1.11.0.tgz", - "integrity": "sha1-RqoXUftqL5PuXmibsQh9SxTGwgU=", - "dev": true + "diff": { + "version": "3.3.1", + "resolved": "https://registry.npmjs.org/diff/-/diff-3.3.1.tgz", + "integrity": "sha512-MKPHZDMB0o6yHyDryUOScqZibp914ksXwAMYMTHj6KO8UeKsRYNJD3oNCKjTqZon+V488P7N/HzXF8t7ZR95ww==" }, - "binaryextensions": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/binaryextensions/-/binaryextensions-2.1.1.tgz", - "integrity": "sha512-XBaoWE9RW8pPdPQNibZsW2zh8TW6gcarXp1FZPwT8Uop8ScSNldJEWf2k9l3HeTqdrEwsOsFcq74RiJECW34yA==" + "dom-walk": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/dom-walk/-/dom-walk-0.1.1.tgz", + "integrity": "sha1-ZyIm3HTI95mtNTB9+TaroRrNYBg=" }, - "bn.js": { - "version": "4.11.6", - "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.11.6.tgz", - "integrity": "sha1-UzRK2xRhehP26N0s4okF0cC6MhU=" - }, - "body-parser": { - "version": "1.18.2", - "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.18.2.tgz", - "integrity": "sha1-h2eKGdhLR9hZuDGZvVm84iKxBFQ=", - "requires": { - "bytes": "3.0.0", - "content-type": "~1.0.4", - "debug": "2.6.9", - "depd": "~1.1.1", - "http-errors": "~1.6.2", - "iconv-lite": "0.4.19", - "on-finished": "~2.3.0", - "qs": "6.5.1", - "raw-body": "2.3.2", - "type-is": "~1.6.15" - }, - "dependencies": { - "debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "requires": { - "ms": "2.0.0" - } - } + "dot-prop": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/dot-prop/-/dot-prop-4.2.0.tgz", + "integrity": "sha512-tUMXrxlExSW6U2EXiiKGSBVdYgtV8qlHL+C10TsW4PURY/ic+eaysnSkwB4kA/mBlCyy/IKDJ+Lc3wbWeaXtuQ==", + "dev": true, + "requires": { + "is-obj": "^1.0.0" } }, - "boom": { - "version": "4.3.1", - "resolved": "https://registry.npmjs.org/boom/-/boom-4.3.1.tgz", - "integrity": "sha1-T4owBctKfjiJ90kDD9JbluAdLjE=", + "duplexer3": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/duplexer3/-/duplexer3-0.1.4.tgz", + "integrity": "sha1-7gHdHKwO08vH/b6jfcCo8c4ALOI=", + "dev": true + }, + "ecc-jsbn": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/ecc-jsbn/-/ecc-jsbn-0.1.2.tgz", + "integrity": "sha1-OoOpBOVDUyh4dMVkt1SThoSamMk=", + "dev": true, "requires": { - "hoek": "4.x.x" + "jsbn": "~0.1.0", + "safer-buffer": "^2.1.0" } }, - "boxen": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/boxen/-/boxen-1.3.0.tgz", - "integrity": "sha512-TNPjfTr432qx7yOjQyaXm3dSR0MH9vXp7eT1BFSl/C51g+EFnOR9hTg1IreahGBmDNCehscshe45f+C1TBZbLw==", - "dev": true, + "elliptic": { + "version": "6.4.1", + "resolved": "https://registry.npmjs.org/elliptic/-/elliptic-6.4.1.tgz", + "integrity": "sha512-BsXLz5sqX8OHcsh7CqBMztyXARmGQ3LWPtGjJi6DiJHq5C/qvi9P3OqgswKSDftbu8+IoI/QDTAm2fFnQ9SZSQ==", "requires": { - "ansi-align": "^2.0.0", - "camelcase": "^4.0.0", - "chalk": "^2.0.1", - "cli-boxes": "^1.0.0", - "string-width": "^2.0.0", - "term-size": "^1.2.0", - "widest-line": "^2.0.0" - }, - "dependencies": { - "ansi-regex": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", - "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=", - "dev": true - }, - "camelcase": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-4.1.0.tgz", - "integrity": "sha1-1UVjW+HjPFQmScaRc+Xeas+uNN0=", - "dev": true - }, - "is-fullwidth-code-point": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", - "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=", - "dev": true - }, - "string-width": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", - "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", - "dev": true, - "requires": { - "is-fullwidth-code-point": "^2.0.0", - "strip-ansi": "^4.0.0" - } - }, - "strip-ansi": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", - "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", - "dev": true, - "requires": { - "ansi-regex": "^3.0.0" - } - } + "bn.js": "^4.4.0", + "brorand": "^1.0.1", + "hash.js": "^1.0.0", + "hmac-drbg": "^1.0.0", + "inherits": "^2.0.1", + "minimalistic-assert": "^1.0.0", + "minimalistic-crypto-utils": "^1.0.0" } }, - "brace-expansion": { - "version": "1.1.11", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz", - "integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==", + "error-ex": { + "version": "1.3.2", + "resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.2.tgz", + "integrity": "sha512-7dFHNmqeFSEt2ZBsCriorKnn3Z2pj+fd9kmI6QoWw4//DL+icEBfc0U7qJCisqrTsKTjw4fNFy2pW9OqStD84g==", "requires": { - "balanced-match": "^1.0.0", - "concat-map": "0.0.1" + "is-arrayish": "^0.2.1" } }, - "braces": { - "version": "2.3.2", - "resolved": "https://registry.npmjs.org/braces/-/braces-2.3.2.tgz", - "integrity": "sha512-aNdbnj9P8PjdXU4ybaWLK2IF3jc/EoDYbC7AazW6to3TRsfXxscC9UXOB5iDiEQrkyIbWp2SLQda4+QAa7nc3w==", + "escape-string-regexp": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", + "integrity": "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=" + }, + "escodegen": { + "version": "1.8.1", + "resolved": "https://registry.npmjs.org/escodegen/-/escodegen-1.8.1.tgz", + "integrity": "sha1-WltTr0aTEQvrsIZ6o0MN07cKEBg=", "dev": true, "requires": { - "arr-flatten": "^1.1.0", - "array-unique": "^0.3.2", - "extend-shallow": "^2.0.1", - "fill-range": "^4.0.0", - "isobject": "^3.0.1", - "repeat-element": "^1.1.2", - "snapdragon": "^0.8.1", - "snapdragon-node": "^2.0.1", - "split-string": "^3.0.2", - "to-regex": "^3.0.1" + "esprima": "^2.7.1", + "estraverse": "^1.9.1", + "esutils": "^2.0.2", + "optionator": "^0.8.1", + "source-map": "~0.2.0" }, "dependencies": { - "extend-shallow": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", - "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "source-map": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.2.0.tgz", + "integrity": "sha1-2rc/vPwrqBm03gO9b26qSBZLP50=", "dev": true, + "optional": true, "requires": { - "is-extendable": "^0.1.0" + "amdefine": ">=0.0.4" } } } }, - "brorand": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/brorand/-/brorand-1.1.0.tgz", - "integrity": "sha1-EsJe/kCkXjwyPrhnWgoM5XsiNx8=" - }, - "browser-stdout": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/browser-stdout/-/browser-stdout-1.3.0.tgz", - "integrity": "sha1-81HTKWnTL6XXpVZxVCY9korjvR8=" - }, - "browserify-sha3": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/browserify-sha3/-/browserify-sha3-0.0.1.tgz", - "integrity": "sha1-P/NKMAbvFcD7NWflQbkaI0ASPRE=", - "requires": { - "js-sha3": "^0.3.1" - }, - "dependencies": { - "js-sha3": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/js-sha3/-/js-sha3-0.3.1.tgz", - "integrity": "sha1-hhIoAhQvCChQKg0d7h2V4lO7AkM=" - } - } - }, - "buffer-from": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.1.tgz", - "integrity": "sha512-MQcXEUbCKtEo7bhqEs6560Hyd4XaovZlO/k9V3hjVUF/zwW7KBVdSK4gIt/bzwS9MbR5qob+F5jusZsb0YQK2A==", + "esprima": { + "version": "2.7.3", + "resolved": "https://registry.npmjs.org/esprima/-/esprima-2.7.3.tgz", + "integrity": "sha1-luO3DVd59q1JzQMmc9HDEnZ7pYE=", "dev": true }, - "buffer-to-arraybuffer": { - "version": "0.0.5", - "resolved": "https://registry.npmjs.org/buffer-to-arraybuffer/-/buffer-to-arraybuffer-0.0.5.tgz", - "integrity": "sha1-YGSkD6dutDxyOrqe+PbhIW0QURo=" - }, - "builtin-modules": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/builtin-modules/-/builtin-modules-1.1.1.tgz", - "integrity": "sha1-Jw8HbFpywC9bZaR9+Uxf46J4iS8=" + "estraverse": { + "version": "1.9.3", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-1.9.3.tgz", + "integrity": "sha1-r2fy3JIlgkFZUJJgkaQAXSnJu0Q=", + "dev": true }, - "bytes": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.0.0.tgz", - "integrity": "sha1-0ygVQE1olpn4Wk6k+odV3ROpYEg=" + "esutils": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/esutils/-/esutils-2.0.2.tgz", + "integrity": "sha1-Cr9PHKpbyx96nYrMbepPqqBLrJs=", + "dev": true }, - "cache-base": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/cache-base/-/cache-base-1.0.1.tgz", - "integrity": "sha512-AKcdTnFSWATd5/GCPRxr2ChwIJ85CeyrEyjRHlKxQ56d4XJMGym0uAiKn0xbLOGOl3+yRpOTi484dVCEc5AUzQ==", + "eth-gas-reporter": { + "version": "0.1.12", + "resolved": "https://registry.npmjs.org/eth-gas-reporter/-/eth-gas-reporter-0.1.12.tgz", + "integrity": "sha512-Ao5uiXSA5Ep5fi/YvGCsFJMelMKj0fMJkAvWYzPVe1h3Mg9Z7X3Rs51ovG9izFZH7wSqnqydiC6SKDhZWpxK2g==", "dev": true, "requires": { - "collection-visit": "^1.0.0", - "component-emitter": "^1.2.1", - "get-value": "^2.0.6", - "has-value": "^1.0.0", - "isobject": "^3.0.1", - "set-value": "^2.0.0", - "to-object-path": "^0.3.0", - "union-value": "^1.0.0", - "unset-value": "^1.0.0" + "abi-decoder": "^1.0.8", + "cli-table3": "^0.5.0", + "colors": "^1.1.2", + "lodash": "^4.17.4", + "mocha": "^4.1.0", + "req-cwd": "^2.0.0", + "request": "^2.83.0", + "request-promise-native": "^1.0.5", + "sha1": "^1.1.1", + "shelljs": "^0.7.8", + "solidity-parser-antlr": "^0.2.10", + "sync-request": "^6.0.0" } }, - "cacheable-request": { - "version": "2.1.4", - "resolved": "https://registry.npmjs.org/cacheable-request/-/cacheable-request-2.1.4.tgz", - "integrity": "sha1-DYCIAbY0KtM8kd+dC0TcCbkeXD0=", + "eth-lib": { + "version": "0.2.8", + "resolved": "https://registry.npmjs.org/eth-lib/-/eth-lib-0.2.8.tgz", + "integrity": "sha512-ArJ7x1WcWOlSpzdoTBX8vkwlkSQ85CjjifSZtV4co64vWxSV8geWfPI9x4SVYu3DSxnX4yWFVTtGL+j9DUFLNw==", "requires": { - "clone-response": "1.0.2", - "get-stream": "3.0.0", - "http-cache-semantics": "3.8.1", - "keyv": "3.0.0", - "lowercase-keys": "1.0.0", - "normalize-url": "2.0.1", - "responselike": "1.0.2" + "bn.js": "^4.11.6", + "elliptic": "^6.4.0", + "xhr-request-promise": "^0.1.2" } }, - "camelcase": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-3.0.0.tgz", - "integrity": "sha1-MvxLn82vhF/N9+c7uXysImHwqwo=" - }, - "capture-stack-trace": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/capture-stack-trace/-/capture-stack-trace-1.0.0.tgz", - "integrity": "sha1-Sm+gc5nCa7pH8LJJa00PtAjFVQ0=", - "dev": true - }, - "caseless": { - "version": "0.12.0", - "resolved": "https://registry.npmjs.org/caseless/-/caseless-0.12.0.tgz", - "integrity": "sha1-G2gcIf+EAzyCZUMJBolCDRhxUdw=" - }, - "center-align": { - "version": "0.1.3", - "resolved": "https://registry.npmjs.org/center-align/-/center-align-0.1.3.tgz", - "integrity": "sha1-qg0yYptu6XIgBBHL1EYckHvCt60=", + "ethereumjs-testrpc-sc": { + "version": "6.1.6", + "resolved": "https://registry.npmjs.org/ethereumjs-testrpc-sc/-/ethereumjs-testrpc-sc-6.1.6.tgz", + "integrity": "sha512-iv2qiGBFgk9mn5Nq2enX8dG5WQ7Lk+FCqpnxfPfH4Ns8KLPwttmNOy264nh3SXDJJvcQwz/XnlLteDQVILotbg==", "dev": true, - "optional": true, "requires": { - "align-text": "^0.1.3", - "lazy-cache": "^1.0.3" + "source-map-support": "^0.5.3" } }, - "chai": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chai/-/chai-4.1.2.tgz", - "integrity": "sha1-D2RYS6ZC8PKs4oBiefTwbKI61zw=", - "dev": true, + "ethjs-unit": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/ethjs-unit/-/ethjs-unit-0.1.6.tgz", + "integrity": "sha1-xmWSHkduh7ziqdWIpv4EBbLEFpk=", "requires": { - "assertion-error": "^1.0.1", - "check-error": "^1.0.1", - "deep-eql": "^3.0.0", - "get-func-name": "^2.0.0", - "pathval": "^1.0.0", - "type-detect": "^4.0.0" + "bn.js": "4.11.6", + "number-to-bn": "1.7.0" + }, + "dependencies": { + "bn.js": { + "version": "4.11.6", + "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.11.6.tgz", + "integrity": "sha1-UzRK2xRhehP26N0s4okF0cC6MhU=" + } } }, - "chai-as-promised": { - "version": "7.1.1", - "resolved": "https://registry.npmjs.org/chai-as-promised/-/chai-as-promised-7.1.1.tgz", - "integrity": "sha512-azL6xMoi+uxu6z4rhWQ1jbdUhOMhis2PvscD/xjLqNMkv3BPPp2JyyuTHOrf9BOosGpNQ11v6BKv/g57RXbiaA==", + "execa": { + "version": "0.7.0", + "resolved": "https://registry.npmjs.org/execa/-/execa-0.7.0.tgz", + "integrity": "sha1-lEvs00zEHuMqY6n68nrVpl/Fl3c=", "dev": true, "requires": { - "check-error": "^1.0.2" + "cross-spawn": "^5.0.1", + "get-stream": "^3.0.0", + "is-stream": "^1.1.0", + "npm-run-path": "^2.0.0", + "p-finally": "^1.0.0", + "signal-exit": "^3.0.0", + "strip-eof": "^1.0.0" } }, - "chai-bignumber": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/chai-bignumber/-/chai-bignumber-2.0.2.tgz", - "integrity": "sha512-BIdRNjRaoRj4bMsZLKbIZPMNKqmwnzNiyxqBYDSs6dFOCs9w8OHPuUE8e1bH60i1IhOzT0NjLtCD+lKEWB1KTQ==", - "dev": true - }, - "chalk": { - "version": "2.3.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.3.2.tgz", - "integrity": "sha512-ZM4j2/ld/YZDc3Ma8PgN7gyAk+kHMMMyzLNryCPGhWrsfAuDVeuid5bpRFTDgMH9JBK2lA4dyyAkkZYF/WcqDQ==", + "expand-brackets": { + "version": "2.1.4", + "resolved": "https://registry.npmjs.org/expand-brackets/-/expand-brackets-2.1.4.tgz", + "integrity": "sha1-t3c14xXOMPa27/D4OwQVGiJEliI=", + "dev": true, "requires": { - "ansi-styles": "^3.2.1", - "escape-string-regexp": "^1.0.5", - "supports-color": "^5.3.0" + "debug": "^2.3.3", + "define-property": "^0.2.5", + "extend-shallow": "^2.0.1", + "posix-character-classes": "^0.1.0", + "regex-not": "^1.0.0", + "snapdragon": "^0.8.1", + "to-regex": "^3.0.1" }, "dependencies": { - "has-flag": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", - "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=" - }, - "supports-color": { - "version": "5.3.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.3.0.tgz", - "integrity": "sha512-0aP01LLIskjKs3lq52EC0aGBAJhLq7B2Rd8HC/DR/PtNNpcLilNmHC12O+hu0usQpo7wtHNRqtrhBwtDb0+dNg==", + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, "requires": { - "has-flag": "^3.0.0" + "ms": "2.0.0" } - } - } - }, - "chardet": { - "version": "0.4.2", - "resolved": "https://registry.npmjs.org/chardet/-/chardet-0.4.2.tgz", - "integrity": "sha1-tUc7M9yXxCTl2Y3IfVXU2KKci/I=" - }, - "charenc": { - "version": "0.0.2", - "resolved": "https://registry.npmjs.org/charenc/-/charenc-0.0.2.tgz", - "integrity": "sha1-wKHS86cJLgN3S/qD8UwPxXkKhmc=", - "dev": true - }, - "check-error": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/check-error/-/check-error-1.0.2.tgz", - "integrity": "sha1-V00xLt2Iu13YkS6Sht1sCu1KrII=", - "dev": true - }, - "chokidar": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-2.0.3.tgz", - "integrity": "sha512-zW8iXYZtXMx4kux/nuZVXjkLP+CyIK5Al5FHnj1OgTKGZfp4Oy6/ymtMSKFv3GD8DviEmUPmJg9eFdJ/JzudMg==", - "dev": true, - "requires": { - "anymatch": "^2.0.0", - "async-each": "^1.0.0", - "braces": "^2.3.0", - "fsevents": "^1.1.2", - "glob-parent": "^3.1.0", - "inherits": "^2.0.1", - "is-binary-path": "^1.0.0", - "is-glob": "^4.0.0", - "normalize-path": "^2.1.1", - "path-is-absolute": "^1.0.0", - "readdirp": "^2.0.0", - "upath": "^1.0.0" - } - }, - "ci-info": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/ci-info/-/ci-info-1.1.3.tgz", - "integrity": "sha512-SK/846h/Rcy8q9Z9CAwGBLfCJ6EkjJWdpelWDufQpqVDYq2Wnnv8zlSO6AMQap02jvhVruKKpEtQOufo3pFhLg==", - "dev": true - }, - "class-utils": { - "version": "0.3.6", - "resolved": "https://registry.npmjs.org/class-utils/-/class-utils-0.3.6.tgz", - "integrity": "sha512-qOhPa/Fj7s6TY8H8esGu5QNpMMQxz79h+urzrNYN6mn+9BnxlDGf5QZ+XeCDsxSjPqsSR56XOZOJmpeurnLMeg==", - "dev": true, - "requires": { - "arr-union": "^3.1.0", - "define-property": "^0.2.5", - "isobject": "^3.0.0", - "static-extend": "^0.1.1" - }, - "dependencies": { + }, "define-property": { "version": "0.2.5", "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", @@ -1553,6891 +1177,3813 @@ "requires": { "is-descriptor": "^0.1.0" } + }, + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "dev": true, + "requires": { + "is-extendable": "^0.1.0" + } } } }, - "cli-boxes": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/cli-boxes/-/cli-boxes-1.0.0.tgz", - "integrity": "sha1-T6kXw+WclKAEzWH47lCdplFocUM=", + "extend": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz", + "integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==", "dev": true }, - "cli-cursor": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-2.1.0.tgz", - "integrity": "sha1-s12sN2R5+sw+lHR9QdDQ9SOP/LU=", - "requires": { - "restore-cursor": "^2.0.0" - } - }, - "cli-spinners": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/cli-spinners/-/cli-spinners-0.1.2.tgz", - "integrity": "sha1-u3ZNiOGF+54eaiofGXcjGPYF4xw=" - }, - "cli-table": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/cli-table/-/cli-table-0.3.1.tgz", - "integrity": "sha1-9TsFJmqLGguTSz0IIebi3FkUriM=", + "extend-shallow": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-3.0.2.tgz", + "integrity": "sha1-Jqcarwc7OfshJxcnRhMcJwQCjbg=", + "dev": true, "requires": { - "colors": "1.0.3" + "assign-symbols": "^1.0.0", + "is-extendable": "^1.0.1" }, "dependencies": { - "colors": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/colors/-/colors-1.0.3.tgz", - "integrity": "sha1-BDP0TYCWgP3rYO0mDxsMJi6CpAs=" + "is-extendable": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-1.0.1.tgz", + "integrity": "sha512-arnXMxT1hhoKo9k1LZdmlNyJdDDfy2v0fXjFlmok4+i8ul/6WlbVge9bhM74OpNPQPMGUToDtz+KXa1PneJxOA==", + "dev": true, + "requires": { + "is-plain-object": "^2.0.4" + } } } }, - "cli-table3": { - "version": "0.5.1", - "resolved": "https://registry.npmjs.org/cli-table3/-/cli-table3-0.5.1.tgz", - "integrity": "sha512-7Qg2Jrep1S/+Q3EceiZtQcDPWxhAvBw+ERf1162v4sikJrvojMHFqXt8QIVha8UlH9rgU0BeWPytZ9/TzYqlUw==", + "extglob": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/extglob/-/extglob-2.0.4.tgz", + "integrity": "sha512-Nmb6QXkELsuBr24CJSkilo6UHHgbekK5UiZgfE6UHD3Eb27YC6oD+bhcT+tJ6cl8dmsgdQxnWlcry8ksBIBLpw==", "dev": true, "requires": { - "colors": "^1.1.2", - "object-assign": "^4.1.0", - "string-width": "^2.1.1" + "array-unique": "^0.3.2", + "define-property": "^1.0.0", + "expand-brackets": "^2.1.4", + "extend-shallow": "^2.0.1", + "fragment-cache": "^0.2.1", + "regex-not": "^1.0.0", + "snapdragon": "^0.8.1", + "to-regex": "^3.0.1" }, "dependencies": { - "ansi-regex": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", - "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=", - "dev": true + "define-property": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-1.0.0.tgz", + "integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=", + "dev": true, + "requires": { + "is-descriptor": "^1.0.0" + } }, - "is-fullwidth-code-point": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", - "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=", - "dev": true + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "dev": true, + "requires": { + "is-extendable": "^0.1.0" + } }, - "string-width": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", - "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", + "is-accessor-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz", + "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", "dev": true, "requires": { - "is-fullwidth-code-point": "^2.0.0", - "strip-ansi": "^4.0.0" + "kind-of": "^6.0.0" } }, - "strip-ansi": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", - "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", + "is-data-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz", + "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", "dev": true, "requires": { - "ansi-regex": "^3.0.0" + "kind-of": "^6.0.0" + } + }, + "is-descriptor": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz", + "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", + "dev": true, + "requires": { + "is-accessor-descriptor": "^1.0.0", + "is-data-descriptor": "^1.0.0", + "kind-of": "^6.0.2" } } } }, - "cli-truncate": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/cli-truncate/-/cli-truncate-0.2.1.tgz", - "integrity": "sha1-nxXPuwcFAFNpIWxiasfQWrkN1XQ=", - "requires": { - "slice-ansi": "0.0.4", - "string-width": "^1.0.1" - } - }, - "cli-width": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/cli-width/-/cli-width-2.2.0.tgz", - "integrity": "sha1-/xnt6Kml5XkyQUewwR8PvLq+1jk=" + "extsprintf": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/extsprintf/-/extsprintf-1.3.0.tgz", + "integrity": "sha1-lpGEQOMEGnpBT4xS48V06zw+HgU=", + "dev": true }, - "cliui": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/cliui/-/cliui-3.2.0.tgz", - "integrity": "sha1-EgYBU3qRbSmUD5NNo7SNWFo5IT0=", - "requires": { - "string-width": "^1.0.1", - "strip-ansi": "^3.0.1", - "wrap-ansi": "^2.0.0" - } + "fast-deep-equal": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-2.0.1.tgz", + "integrity": "sha1-ewUhjd+WZ79/Nwv3/bLLFf3Qqkk=", + "dev": true }, - "clone": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/clone/-/clone-1.0.4.tgz", - "integrity": "sha1-2jCcwmPfFZlMaIypAheco8fNfH4=" + "fast-json-stable-stringify": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.0.0.tgz", + "integrity": "sha1-1RQsDK7msRifh9OnYREGT4bIu/I=", + "dev": true }, - "clone-buffer": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/clone-buffer/-/clone-buffer-1.0.0.tgz", - "integrity": "sha1-4+JbIHrE5wGvch4staFnksrD3Fg=" + "fast-levenshtein": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz", + "integrity": "sha1-PYpcZog6FqMMqGQ+hR8Zuqd5eRc=", + "dev": true }, - "clone-response": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/clone-response/-/clone-response-1.0.2.tgz", - "integrity": "sha1-0dyXOSAxTfZ/vrlCI7TuNQI56Ws=", + "fill-range": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-4.0.0.tgz", + "integrity": "sha1-1USBHUKPmOsGpj3EAtJAPDKMOPc=", + "dev": true, "requires": { - "mimic-response": "^1.0.0" + "extend-shallow": "^2.0.1", + "is-number": "^3.0.0", + "repeat-string": "^1.6.1", + "to-regex-range": "^2.1.0" + }, + "dependencies": { + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "dev": true, + "requires": { + "is-extendable": "^0.1.0" + } + } } }, - "clone-stats": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/clone-stats/-/clone-stats-0.0.1.tgz", - "integrity": "sha1-uI+UqCzzi4eR1YBG6kAprYjKmdE=" - }, - "cloneable-readable": { + "find-up": { "version": "1.1.2", - "resolved": "https://registry.npmjs.org/cloneable-readable/-/cloneable-readable-1.1.2.tgz", - "integrity": "sha512-Bq6+4t+lbM8vhTs/Bef5c5AdEMtapp/iFb6+s4/Hh9MVTt8OLKH7ZOOZSCT+Ys7hsHvqv0GuMPJ1lnQJVHvxpg==", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-1.1.2.tgz", + "integrity": "sha1-ay6YIrGizgpgq2TWEOzK1TyyTQ8=", "requires": { - "inherits": "^2.0.1", - "process-nextick-args": "^2.0.0", - "readable-stream": "^2.3.5" + "path-exists": "^2.0.0", + "pinkie-promise": "^2.0.0" } }, - "co": { - "version": "4.6.0", - "resolved": "https://registry.npmjs.org/co/-/co-4.6.0.tgz", - "integrity": "sha1-bqa989hTrlTMuOR7+gvz+QMfsYQ=" + "for-each": { + "version": "0.3.3", + "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.3.tgz", + "integrity": "sha512-jqYfLp7mo9vIyQf8ykW2v7A+2N4QjeCeI5+Dz9XraiO1ign81wjiH7Fb9vSOWvQfNtmSa4H2RoQTrrXivdUZmw==", + "requires": { + "is-callable": "^1.1.3" + } }, - "code-point-at": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/code-point-at/-/code-point-at-1.1.0.tgz", - "integrity": "sha1-DQcLTQQ6W+ozovGkDi7bPZpMz3c=" + "for-in": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/for-in/-/for-in-1.0.2.tgz", + "integrity": "sha1-gQaNKVqBQuwKxybG4iAMMPttXoA=", + "dev": true }, - "collection-visit": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/collection-visit/-/collection-visit-1.0.0.tgz", - "integrity": "sha1-S8A3PBZLwykbTTaMgpzxqApZ3KA=", + "forever-agent": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/forever-agent/-/forever-agent-0.6.1.tgz", + "integrity": "sha1-+8cfDEGt6zf5bFd60e1C2P2sypE=", + "dev": true + }, + "form-data": { + "version": "2.3.3", + "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.3.3.tgz", + "integrity": "sha512-1lLKB2Mu3aGP1Q/2eCOx0fNbRMe7XdwktwOruhfqqd0rIJWwN4Dh+E3hrPSlDCXnSR7UtZ1N38rVXm+6+MEhJQ==", "dev": true, "requires": { - "map-visit": "^1.0.0", - "object-visit": "^1.0.0" + "asynckit": "^0.4.0", + "combined-stream": "^1.0.6", + "mime-types": "^2.1.12" } }, - "color-convert": { - "version": "1.9.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.1.tgz", - "integrity": "sha512-mjGanIiwQJskCC18rPR6OmrZ6fm2Lc7PeGFYwCmy5J34wC6F1PzdGL6xeMfmgicfYcNLGuVFA3WzXtIDCQSZxQ==", + "fragment-cache": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/fragment-cache/-/fragment-cache-0.2.1.tgz", + "integrity": "sha1-QpD60n8T6Jvn8zeZxrxaCr//DRk=", + "dev": true, "requires": { - "color-name": "^1.1.1" + "map-cache": "^0.2.2" } }, - "color-name": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz", - "integrity": "sha1-p9BVi9icQveV3UIyj3QIMcpTvCU=" - }, - "colors": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/colors/-/colors-1.2.1.tgz", - "integrity": "sha512-s8+wktIuDSLffCywiwSxQOMqtPxML11a/dtHE17tMn4B1MSWw/C22EKf7M2KGUBcDaVFEGT+S8N02geDXeuNKg==" - }, - "combined-stream": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.6.tgz", - "integrity": "sha1-cj599ugBrFYTETp+RFqbactjKBg=", - "requires": { - "delayed-stream": "~1.0.0" - } - }, - "commander": { - "version": "2.11.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-2.11.0.tgz", - "integrity": "sha512-b0553uYA5YAEGgyYIGYROzKQ7X5RAqedkfjiZxwi0kL1g3bOaBNNZfYkzt/CL0umgD5wc9Jec2FbB98CjkMRvQ==" - }, - "commondir": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/commondir/-/commondir-1.0.1.tgz", - "integrity": "sha1-3dgA2gxmEnOTzKWVDqloo6rxJTs=" - }, - "component-emitter": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/component-emitter/-/component-emitter-1.2.1.tgz", - "integrity": "sha1-E3kY1teCg/ffemt8WmPhQOaUJeY=", - "dev": true - }, - "concat-map": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", - "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=" - }, - "concat-stream": { - "version": "1.6.2", - "resolved": "https://registry.npmjs.org/concat-stream/-/concat-stream-1.6.2.tgz", - "integrity": "sha512-27HBghJxjiZtIk3Ycvn/4kbJk/1uZuJFfuPEns6LaEvpvG1f0hTea8lilrouyo9mVc2GWdcEZ8OLoGmSADlrCw==", - "dev": true, - "requires": { - "buffer-from": "^1.0.0", - "inherits": "^2.0.3", - "readable-stream": "^2.2.2", - "typedarray": "^0.0.6" - } - }, - "configstore": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/configstore/-/configstore-3.1.2.tgz", - "integrity": "sha512-vtv5HtGjcYUgFrXc6Kx747B83MRRVS5R1VTEQoXvuP+kMI+if6uywV0nDGoiydJRy4yk7h9od5Og0kxx4zUXmw==", - "dev": true, + "fs-extra": { + "version": "0.30.0", + "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-0.30.0.tgz", + "integrity": "sha1-8jP/zAjU2n1DLapEl3aYnbHfk/A=", "requires": { - "dot-prop": "^4.1.0", "graceful-fs": "^4.1.2", - "make-dir": "^1.0.0", - "unique-string": "^1.0.0", - "write-file-atomic": "^2.0.0", - "xdg-basedir": "^3.0.0" - } - }, - "content-disposition": { - "version": "0.5.2", - "resolved": "https://registry.npmjs.org/content-disposition/-/content-disposition-0.5.2.tgz", - "integrity": "sha1-DPaLud318r55YcOoUXjLhdunjLQ=" - }, - "content-type": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/content-type/-/content-type-1.0.4.tgz", - "integrity": "sha512-hIP3EEPs8tB9AT1L+NUqtwOAps4mk2Zob89MWXMHjHWg9milF/j4osnnQLXBCBFBk/tvIG/tUc9mOUJiPBhPXA==" - }, - "convert-source-map": { - "version": "1.5.1", - "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-1.5.1.tgz", - "integrity": "sha1-uCeAl7m8IpNl3lxiz1/K7YtVmeU=" - }, - "cookie": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.3.1.tgz", - "integrity": "sha1-5+Ch+e9DtMi6klxcWpboBtFoc7s=" - }, - "cookie-signature": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz", - "integrity": "sha1-4wOogrNCzD7oylE6eZmXNNqzriw=" - }, - "copy-descriptor": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/copy-descriptor/-/copy-descriptor-0.1.1.tgz", - "integrity": "sha1-Z29us8OZl8LuGsOpJP1hJHSPV40=", - "dev": true - }, - "core-js": { - "version": "2.5.3", - "resolved": "https://registry.npmjs.org/core-js/-/core-js-2.5.3.tgz", - "integrity": "sha1-isw4NFgk8W2DZbfJtCWRaOjtYD4=" - }, - "core-util-is": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz", - "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=" - }, - "cors": { - "version": "2.8.4", - "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.4.tgz", - "integrity": "sha1-K9OB8usgECAQXNUOpZ2mMJBpRoY=", - "requires": { - "object-assign": "^4", - "vary": "^1" - } - }, - "create-error-class": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/create-error-class/-/create-error-class-3.0.2.tgz", - "integrity": "sha1-Br56vvlHo/FKMP1hBnHUAbyot7Y=", - "dev": true, - "requires": { - "capture-stack-trace": "^1.0.0" - } - }, - "cross-spawn": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-5.1.0.tgz", - "integrity": "sha1-6L0O/uWPz/b4+UUQoKVUu/ojVEk=", - "requires": { - "lru-cache": "^4.0.1", - "shebang-command": "^1.2.0", - "which": "^1.2.9" - }, - "dependencies": { - "lru-cache": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-4.1.2.tgz", - "integrity": "sha512-wgeVXhrDwAWnIF/yZARsFnMBtdFXOg1b8RIrhilp+0iDYN4mdQcNZElDZ0e4B64BhaxeQ5zN7PMyvu7we1kPeQ==", - "requires": { - "pseudomap": "^1.0.2", - "yallist": "^2.1.2" - } - } - } - }, - "crypt": { - "version": "0.0.2", - "resolved": "https://registry.npmjs.org/crypt/-/crypt-0.0.2.tgz", - "integrity": "sha1-iNf/fsDfuG9xPch7u0LQRNPmxBs=", - "dev": true - }, - "cryptiles": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/cryptiles/-/cryptiles-3.1.2.tgz", - "integrity": "sha1-qJ+7Ig9c4l7FboxKqKT9e1sNKf4=", - "requires": { - "boom": "5.x.x" - }, - "dependencies": { - "boom": { - "version": "5.2.0", - "resolved": "https://registry.npmjs.org/boom/-/boom-5.2.0.tgz", - "integrity": "sha512-Z5BTk6ZRe4tXXQlkqftmsAUANpXmuwlsF5Oov8ThoMbQRzdGTA1ngYRW160GexgOgjsFOKJz0LYhoNi+2AMBUw==", - "requires": { - "hoek": "4.x.x" - } - } + "jsonfile": "^2.1.0", + "klaw": "^1.0.0", + "path-is-absolute": "^1.0.0", + "rimraf": "^2.2.8" } }, - "crypto-js": { - "version": "3.1.8", - "resolved": "https://registry.npmjs.org/crypto-js/-/crypto-js-3.1.8.tgz", - "integrity": "sha1-cV8HC/YBTyrpkqmLOSkli3E/CNU=", - "dev": true - }, - "crypto-random-string": { + "fs.realpath": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/crypto-random-string/-/crypto-random-string-1.0.0.tgz", - "integrity": "sha1-ojD2T1aDEOFJgAmUB5DsmVRbyn4=", - "dev": true - }, - "dargs": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/dargs/-/dargs-5.1.0.tgz", - "integrity": "sha1-7H6lDHhWTNNsnV7Bj2Yyn63ieCk=" - }, - "dashdash": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/dashdash/-/dashdash-1.14.1.tgz", - "integrity": "sha1-hTz6D3y+L+1d4gMmuN1YEDX24vA=", - "requires": { - "assert-plus": "^1.0.0" - } - }, - "date-fns": { - "version": "1.29.0", - "resolved": "https://registry.npmjs.org/date-fns/-/date-fns-1.29.0.tgz", - "integrity": "sha512-lbTXWZ6M20cWH8N9S6afb0SBm6tMk+uUg6z3MqHPKE9atmsY3kJkTm8vKe93izJ2B2+q5MV990sM2CHgtAZaOw==" - }, - "dateformat": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/dateformat/-/dateformat-3.0.3.tgz", - "integrity": "sha512-jyCETtSl3VMZMWeRo7iY1FL19ges1t55hMo5yaam4Jrsm5EPL89UQkoQRyiI+Yf4k8r2ZpdngkV8hr1lIdjb3Q==" - }, - "death": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/death/-/death-1.1.0.tgz", - "integrity": "sha1-AaqcQB7dknUFFEcLgmY5DGbGcxg=", - "dev": true - }, - "debug": { - "version": "2.6.8", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.8.tgz", - "integrity": "sha1-5zFTHKLt4n0YgiJCfaF4IdaP9Pw=", - "requires": { - "ms": "2.0.0" - } - }, - "decamelize": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/decamelize/-/decamelize-1.2.0.tgz", - "integrity": "sha1-9lNNFRSCabIDUue+4m9QH5oZEpA=" - }, - "decode-uri-component": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/decode-uri-component/-/decode-uri-component-0.2.0.tgz", - "integrity": "sha1-6zkTMzRYd1y4TNGh+uBiEGu4dUU=" - }, - "decompress-response": { - "version": "3.3.0", - "resolved": "https://registry.npmjs.org/decompress-response/-/decompress-response-3.3.0.tgz", - "integrity": "sha1-gKTdMjdIOEv6JICDYirt7Jgq3/M=", - "requires": { - "mimic-response": "^1.0.0" - } - }, - "deep-eql": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/deep-eql/-/deep-eql-3.0.1.tgz", - "integrity": "sha512-+QeIQyN5ZuO+3Uk5DYh6/1eKO0m0YmJFGNmFHGACpf1ClL1nmlV/p4gNgbl2pJGxgXb4faqo6UE+M5ACEMyVcw==", - "dev": true, - "requires": { - "type-detect": "^4.0.0" - } - }, - "deep-extend": { - "version": "0.4.2", - "resolved": "https://registry.npmjs.org/deep-extend/-/deep-extend-0.4.2.tgz", - "integrity": "sha1-SLaZwn4zS/ifEIkr5DL25MfTSn8=" - }, - "deep-is": { - "version": "0.1.3", - "resolved": "https://registry.npmjs.org/deep-is/-/deep-is-0.1.3.tgz", - "integrity": "sha1-s2nW+128E+7PUk+RsHD+7cNXzzQ=", - "dev": true + "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", + "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=" }, - "define-property": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/define-property/-/define-property-2.0.2.tgz", - "integrity": "sha512-jwK2UV4cnPpbcG7+VRARKTZPUWowwXA8bzH5NP6ud0oeAxyYPuGZUAC7hMugpCdz4BeSZl2Dl9k66CHJ/46ZYQ==", + "fsevents": { + "version": "1.2.7", + "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-1.2.7.tgz", + "integrity": "sha512-Pxm6sI2MeBD7RdD12RYsqaP0nMiwx8eZBXCa6z2L+mRHm2DYrOYwihmhjpkdjUHwQhslWQjRpEgNq4XvBmaAuw==", "dev": true, + "optional": true, "requires": { - "is-descriptor": "^1.0.2", - "isobject": "^3.0.1" + "nan": "^2.9.2", + "node-pre-gyp": "^0.10.0" }, "dependencies": { - "is-accessor-descriptor": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz", - "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", + "abbrev": { + "version": "1.1.1", + "bundled": true, + "dev": true, + "optional": true + }, + "ansi-regex": { + "version": "2.1.1", + "bundled": true, + "dev": true + }, + "aproba": { + "version": "1.2.0", + "bundled": true, + "dev": true, + "optional": true + }, + "are-we-there-yet": { + "version": "1.1.5", + "bundled": true, "dev": true, + "optional": true, "requires": { - "kind-of": "^6.0.0" + "delegates": "^1.0.0", + "readable-stream": "^2.0.6" } }, - "is-data-descriptor": { + "balanced-match": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz", - "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", + "bundled": true, + "dev": true + }, + "brace-expansion": { + "version": "1.1.11", + "bundled": true, "dev": true, "requires": { - "kind-of": "^6.0.0" + "balanced-match": "^1.0.0", + "concat-map": "0.0.1" } }, - "is-descriptor": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz", - "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", + "chownr": { + "version": "1.1.1", + "bundled": true, "dev": true, - "requires": { - "is-accessor-descriptor": "^1.0.0", - "is-data-descriptor": "^1.0.0", - "kind-of": "^6.0.2" - } - } - } - }, - "delayed-stream": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", - "integrity": "sha1-3zrhmayt+31ECqrgsp4icrJOxhk=" - }, - "depd": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/depd/-/depd-1.1.2.tgz", - "integrity": "sha1-m81S4UwJd2PnSbJ0xDRu0uVgtak=" - }, - "destroy": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/destroy/-/destroy-1.0.4.tgz", - "integrity": "sha1-l4hXRCxEdJ5CBmE+N5RiBYJqvYA=" - }, - "detect-conflict": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/detect-conflict/-/detect-conflict-1.0.1.tgz", - "integrity": "sha1-CIZXpmqWHAUBnbfEIwiDsca0F24=" - }, - "detect-indent": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/detect-indent/-/detect-indent-4.0.0.tgz", - "integrity": "sha1-920GQ1LN9Docts5hnE7jqUdd4gg=", - "requires": { - "repeating": "^2.0.0" - } - }, - "diff": { - "version": "3.3.1", - "resolved": "https://registry.npmjs.org/diff/-/diff-3.3.1.tgz", - "integrity": "sha512-MKPHZDMB0o6yHyDryUOScqZibp914ksXwAMYMTHj6KO8UeKsRYNJD3oNCKjTqZon+V488P7N/HzXF8t7ZR95ww==" - }, - "dom-walk": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/dom-walk/-/dom-walk-0.1.1.tgz", - "integrity": "sha1-ZyIm3HTI95mtNTB9+TaroRrNYBg=" - }, - "dot-prop": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/dot-prop/-/dot-prop-4.2.0.tgz", - "integrity": "sha512-tUMXrxlExSW6U2EXiiKGSBVdYgtV8qlHL+C10TsW4PURY/ic+eaysnSkwB4kA/mBlCyy/IKDJ+Lc3wbWeaXtuQ==", - "dev": true, - "requires": { - "is-obj": "^1.0.0" - } - }, - "duplexer": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/duplexer/-/duplexer-0.1.1.tgz", - "integrity": "sha1-rOb/gIwc5mtX0ev5eXessCM0z8E=", - "dev": true - }, - "duplexer3": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/duplexer3/-/duplexer3-0.1.4.tgz", - "integrity": "sha1-7gHdHKwO08vH/b6jfcCo8c4ALOI=" - }, - "ecc-jsbn": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/ecc-jsbn/-/ecc-jsbn-0.1.1.tgz", - "integrity": "sha1-D8c6ntXw1Tw4GTOYUj735UN3dQU=", - "optional": true, - "requires": { - "jsbn": "~0.1.0" - } - }, - "editions": { - "version": "1.3.4", - "resolved": "https://registry.npmjs.org/editions/-/editions-1.3.4.tgz", - "integrity": "sha512-gzao+mxnYDzIysXKMQi/+M1mjy/rjestjg6OPoYTtI+3Izp23oiGZitsl9lPDPiTGXbcSIk1iJWhliSaglxnUg==" - }, - "ee-first": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/ee-first/-/ee-first-1.1.1.tgz", - "integrity": "sha1-WQxhFWsK4vTwJVcyoViyZrxWsh0=" - }, - "ejs": { - "version": "2.5.8", - "resolved": "https://registry.npmjs.org/ejs/-/ejs-2.5.8.tgz", - "integrity": "sha512-QIDZL54fyV8MDcAsO91BMH1ft2qGGaHIJsJIA/+t+7uvXol1dm413fPcUgUb4k8F/9457rx4/KFE4XfDifrQxQ==" - }, - "elegant-spinner": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/elegant-spinner/-/elegant-spinner-1.0.1.tgz", - "integrity": "sha1-2wQ1IcldfjA/2PNFvtwzSc+wcp4=" - }, - "elliptic": { - "version": "6.4.0", - "resolved": "https://registry.npmjs.org/elliptic/-/elliptic-6.4.0.tgz", - "integrity": "sha1-ysmvh2LIWDYYcAPI3+GT5eLq5d8=", - "requires": { - "bn.js": "^4.4.0", - "brorand": "^1.0.1", - "hash.js": "^1.0.0", - "hmac-drbg": "^1.0.0", - "inherits": "^2.0.1", - "minimalistic-assert": "^1.0.0", - "minimalistic-crypto-utils": "^1.0.0" - } - }, - "emojis-list": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/emojis-list/-/emojis-list-2.1.0.tgz", - "integrity": "sha1-TapNnbAPmBmIDHn6RXrlsJof04k=" - }, - "encodeurl": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-1.0.2.tgz", - "integrity": "sha1-rT/0yG7C0CkyL1oCw6mmBslbP1k=" - }, - "enhanced-resolve": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/enhanced-resolve/-/enhanced-resolve-4.0.0.tgz", - "integrity": "sha512-jox/62b2GofV1qTUQTMPEJSDIGycS43evqYzD/KVtEb9OCoki9cnacUPxCrZa7JfPzZSYOCZhu9O9luaMxAX8g==", - "requires": { - "graceful-fs": "^4.1.2", - "memory-fs": "^0.4.0", - "tapable": "^1.0.0" - } - }, - "errno": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/errno/-/errno-0.1.7.tgz", - "integrity": "sha512-MfrRBDWzIWifgq6tJj60gkAwtLNb6sQPlcFrSOflcP1aFmmruKQ2wRnze/8V6kgyz7H3FF8Npzv78mZ7XLLflg==", - "requires": { - "prr": "~1.0.1" - } - }, - "error": { - "version": "7.0.2", - "resolved": "https://registry.npmjs.org/error/-/error-7.0.2.tgz", - "integrity": "sha1-pfdf/02ZJhJt2sDqXcOOaJFTywI=", - "requires": { - "string-template": "~0.2.1", - "xtend": "~4.0.0" - } - }, - "error-ex": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.1.tgz", - "integrity": "sha1-+FWobOYa3E6GIcPNoh56dhLDqNw=", - "requires": { - "is-arrayish": "^0.2.1" - } - }, - "escape-html": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/escape-html/-/escape-html-1.0.3.tgz", - "integrity": "sha1-Aljq5NPQwJdN4cFpGI7wBR0dGYg=" - }, - "escape-string-regexp": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", - "integrity": "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=" - }, - "escodegen": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/escodegen/-/escodegen-1.8.1.tgz", - "integrity": "sha1-WltTr0aTEQvrsIZ6o0MN07cKEBg=", - "dev": true, - "requires": { - "esprima": "^2.7.1", - "estraverse": "^1.9.1", - "esutils": "^2.0.2", - "optionator": "^0.8.1", - "source-map": "~0.2.0" - }, - "dependencies": { - "esprima": { - "version": "2.7.3", - "resolved": "https://registry.npmjs.org/esprima/-/esprima-2.7.3.tgz", - "integrity": "sha1-luO3DVd59q1JzQMmc9HDEnZ7pYE=", + "optional": true + }, + "code-point-at": { + "version": "1.1.0", + "bundled": true, "dev": true }, - "source-map": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.2.0.tgz", - "integrity": "sha1-2rc/vPwrqBm03gO9b26qSBZLP50=", + "concat-map": { + "version": "0.0.1", + "bundled": true, + "dev": true + }, + "console-control-strings": { + "version": "1.1.0", + "bundled": true, + "dev": true + }, + "core-util-is": { + "version": "1.0.2", + "bundled": true, + "dev": true, + "optional": true + }, + "debug": { + "version": "2.6.9", + "bundled": true, "dev": true, "optional": true, "requires": { - "amdefine": ">=0.0.4" + "ms": "2.0.0" } - } - } - }, - "esprima": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/esprima/-/esprima-4.0.0.tgz", - "integrity": "sha512-oftTcaMu/EGrEIu904mWteKIv8vMuOgGYo7EhVJJN00R/EED9DCua/xxHRdYnKtcECzVg7xOWhflvJMnqcFZjw==" - }, - "estraverse": { - "version": "1.9.3", - "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-1.9.3.tgz", - "integrity": "sha1-r2fy3JIlgkFZUJJgkaQAXSnJu0Q=", - "dev": true - }, - "esutils": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/esutils/-/esutils-2.0.2.tgz", - "integrity": "sha1-Cr9PHKpbyx96nYrMbepPqqBLrJs=" - }, - "etag": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/etag/-/etag-1.8.1.tgz", - "integrity": "sha1-Qa4u62XvpiJorr/qg6x9eSmbCIc=" - }, - "eth-gas-reporter": { - "version": "0.1.12", - "resolved": "https://registry.npmjs.org/eth-gas-reporter/-/eth-gas-reporter-0.1.12.tgz", - "integrity": "sha512-Ao5uiXSA5Ep5fi/YvGCsFJMelMKj0fMJkAvWYzPVe1h3Mg9Z7X3Rs51ovG9izFZH7wSqnqydiC6SKDhZWpxK2g==", - "dev": true, - "requires": { - "abi-decoder": "^1.0.8", - "cli-table3": "^0.5.0", - "colors": "^1.1.2", - "lodash": "^4.17.4", - "mocha": "^4.1.0", - "req-cwd": "^2.0.0", - "request": "^2.83.0", - "request-promise-native": "^1.0.5", - "sha1": "^1.1.1", - "shelljs": "^0.7.8", - "solidity-parser-antlr": "^0.2.10", - "sync-request": "^6.0.0" - }, - "dependencies": { - "req-cwd": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/req-cwd/-/req-cwd-2.0.0.tgz", - "integrity": "sha1-1AgrTURZgDZkD7c93qAe1T20nrw=", + }, + "deep-extend": { + "version": "0.6.0", + "bundled": true, "dev": true, - "requires": { - "req-from": "^2.0.0" - } + "optional": true }, - "req-from": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/req-from/-/req-from-2.0.0.tgz", - "integrity": "sha1-10GI5H+TeW9Kpx327jWuaJ8+DnA=", + "delegates": { + "version": "1.0.0", + "bundled": true, + "dev": true, + "optional": true + }, + "detect-libc": { + "version": "1.0.3", + "bundled": true, + "dev": true, + "optional": true + }, + "fs-minipass": { + "version": "1.2.5", + "bundled": true, "dev": true, + "optional": true, "requires": { - "resolve-from": "^3.0.0" + "minipass": "^2.2.1" } }, - "shelljs": { - "version": "0.7.8", - "resolved": "https://registry.npmjs.org/shelljs/-/shelljs-0.7.8.tgz", - "integrity": "sha1-3svPh0sNHl+3LhSxZKloMEjprLM=", + "fs.realpath": { + "version": "1.0.0", + "bundled": true, + "dev": true, + "optional": true + }, + "gauge": { + "version": "2.7.4", + "bundled": true, "dev": true, + "optional": true, "requires": { - "glob": "^7.0.0", - "interpret": "^1.0.0", - "rechoir": "^0.6.2" + "aproba": "^1.0.3", + "console-control-strings": "^1.0.0", + "has-unicode": "^2.0.0", + "object-assign": "^4.1.0", + "signal-exit": "^3.0.0", + "string-width": "^1.0.1", + "strip-ansi": "^3.0.1", + "wide-align": "^1.1.0" } - } - } - }, - "eth-lib": { - "version": "0.1.27", - "resolved": "https://registry.npmjs.org/eth-lib/-/eth-lib-0.1.27.tgz", - "integrity": "sha512-B8czsfkJYzn2UIEMwjc7Mbj+Cy72V+/OXH/tb44LV8jhrjizQJJ325xMOMyk3+ETa6r6oi0jsUY14+om8mQMWA==", - "requires": { - "bn.js": "^4.11.6", - "elliptic": "^6.4.0", - "keccakjs": "^0.2.1", - "nano-json-stream-parser": "^0.1.2", - "servify": "^0.1.12", - "ws": "^3.0.0", - "xhr-request-promise": "^0.1.2" - } - }, - "ethereumjs-testrpc-sc": { - "version": "6.1.2", - "resolved": "https://registry.npmjs.org/ethereumjs-testrpc-sc/-/ethereumjs-testrpc-sc-6.1.2.tgz", - "integrity": "sha512-dBTav4AZQ7zuajmICv1k7bEesqS+8f0u0wciXNUJZb842RTBi0lgKEDF8WgZshzv4ThI+XVQSRNV/A+seiK4aA==", - "dev": true, - "requires": { - "source-map-support": "^0.5.3", - "webpack-cli": "^2.0.9" - } - }, - "ethjs-unit": { - "version": "0.1.6", - "resolved": "https://registry.npmjs.org/ethjs-unit/-/ethjs-unit-0.1.6.tgz", - "integrity": "sha1-xmWSHkduh7ziqdWIpv4EBbLEFpk=", - "requires": { - "bn.js": "4.11.6", - "number-to-bn": "1.7.0" - } - }, - "event-stream": { - "version": "3.3.4", - "resolved": "http://registry.npmjs.org/event-stream/-/event-stream-3.3.4.tgz", - "integrity": "sha1-SrTJoPWlTbkzi0w02Gv86PSzVXE=", - "dev": true, - "requires": { - "duplexer": "~0.1.1", - "from": "~0", - "map-stream": "~0.1.0", - "pause-stream": "0.0.11", - "split": "0.3", - "stream-combiner": "~0.0.4", - "through": "~2.3.1" - } - }, - "execa": { - "version": "0.7.0", - "resolved": "https://registry.npmjs.org/execa/-/execa-0.7.0.tgz", - "integrity": "sha1-lEvs00zEHuMqY6n68nrVpl/Fl3c=", - "requires": { - "cross-spawn": "^5.0.1", - "get-stream": "^3.0.0", - "is-stream": "^1.1.0", - "npm-run-path": "^2.0.0", - "p-finally": "^1.0.0", - "signal-exit": "^3.0.0", - "strip-eof": "^1.0.0" - } - }, - "exit-hook": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/exit-hook/-/exit-hook-1.1.1.tgz", - "integrity": "sha1-8FyiM7SMBdVP/wd2XfhQfpXAL/g=" - }, - "expand-brackets": { - "version": "2.1.4", - "resolved": "https://registry.npmjs.org/expand-brackets/-/expand-brackets-2.1.4.tgz", - "integrity": "sha1-t3c14xXOMPa27/D4OwQVGiJEliI=", - "dev": true, - "requires": { - "debug": "^2.3.3", - "define-property": "^0.2.5", - "extend-shallow": "^2.0.1", - "posix-character-classes": "^0.1.0", - "regex-not": "^1.0.0", - "snapdragon": "^0.8.1", - "to-regex": "^3.0.1" - }, - "dependencies": { - "define-property": { - "version": "0.2.5", - "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", - "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", - "dev": true, - "requires": { - "is-descriptor": "^0.1.0" - } - }, - "extend-shallow": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", - "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", - "dev": true, - "requires": { - "is-extendable": "^0.1.0" - } - } - } - }, - "expand-range": { - "version": "1.8.2", - "resolved": "https://registry.npmjs.org/expand-range/-/expand-range-1.8.2.tgz", - "integrity": "sha1-opnv/TNf4nIeuujiV+x5ZE/IUzc=", - "requires": { - "fill-range": "^2.1.0" - }, - "dependencies": { - "fill-range": { - "version": "2.2.3", - "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-2.2.3.tgz", - "integrity": "sha1-ULd9/X5Gm8dJJHCWNpn+eoSFpyM=", - "requires": { - "is-number": "^2.1.0", - "isobject": "^2.0.0", - "randomatic": "^1.1.3", - "repeat-element": "^1.1.2", - "repeat-string": "^1.5.2" - } - }, - "is-number": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/is-number/-/is-number-2.1.0.tgz", - "integrity": "sha1-Afy7s5NGOlSPL0ZszhbezknbkI8=", - "requires": { - "kind-of": "^3.0.2" - } - }, - "isobject": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/isobject/-/isobject-2.1.0.tgz", - "integrity": "sha1-8GVWEJaj8dou9GJy+BXIQNh+DIk=", - "requires": { - "isarray": "1.0.0" - } - }, - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", - "requires": { - "is-buffer": "^1.1.5" - } - } - } - }, - "expand-tilde": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/expand-tilde/-/expand-tilde-2.0.2.tgz", - "integrity": "sha1-l+gBqgUt8CRU3kawK/YhZCzchQI=", - "requires": { - "homedir-polyfill": "^1.0.1" - } - }, - "express": { - "version": "4.16.3", - "resolved": "https://registry.npmjs.org/express/-/express-4.16.3.tgz", - "integrity": "sha1-avilAjUNsyRuzEvs9rWjTSL37VM=", - "requires": { - "accepts": "~1.3.5", - "array-flatten": "1.1.1", - "body-parser": "1.18.2", - "content-disposition": "0.5.2", - "content-type": "~1.0.4", - "cookie": "0.3.1", - "cookie-signature": "1.0.6", - "debug": "2.6.9", - "depd": "~1.1.2", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "etag": "~1.8.1", - "finalhandler": "1.1.1", - "fresh": "0.5.2", - "merge-descriptors": "1.0.1", - "methods": "~1.1.2", - "on-finished": "~2.3.0", - "parseurl": "~1.3.2", - "path-to-regexp": "0.1.7", - "proxy-addr": "~2.0.3", - "qs": "6.5.1", - "range-parser": "~1.2.0", - "safe-buffer": "5.1.1", - "send": "0.16.2", - "serve-static": "1.13.2", - "setprototypeof": "1.1.0", - "statuses": "~1.4.0", - "type-is": "~1.6.16", - "utils-merge": "1.0.1", - "vary": "~1.1.2" - }, - "dependencies": { - "debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "requires": { - "ms": "2.0.0" - } - }, - "statuses": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.4.0.tgz", - "integrity": "sha512-zhSCtt8v2NDrRlPQpCNtw/heZLtfUDqxBM1udqikb/Hbk52LK4nQSwr10u77iopCW5LsyHpuXS0GnEc48mLeew==" - } - } - }, - "extend": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.1.tgz", - "integrity": "sha1-p1Xqe8Gt/MWjHOfnYtuq3F5jZEQ=" - }, - "extend-shallow": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-3.0.2.tgz", - "integrity": "sha1-Jqcarwc7OfshJxcnRhMcJwQCjbg=", - "dev": true, - "requires": { - "assign-symbols": "^1.0.0", - "is-extendable": "^1.0.1" - }, - "dependencies": { - "is-extendable": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-1.0.1.tgz", - "integrity": "sha512-arnXMxT1hhoKo9k1LZdmlNyJdDDfy2v0fXjFlmok4+i8ul/6WlbVge9bhM74OpNPQPMGUToDtz+KXa1PneJxOA==", - "dev": true, - "requires": { - "is-plain-object": "^2.0.4" - } - } - } - }, - "external-editor": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/external-editor/-/external-editor-2.1.0.tgz", - "integrity": "sha512-E44iT5QVOUJBKij4IIV3uvxuNlbKS38Tw1HiupxEIHPv9qtC2PrDYohbXV5U+1jnfIXttny8gUhj+oZvflFlzA==", - "requires": { - "chardet": "^0.4.0", - "iconv-lite": "^0.4.17", - "tmp": "^0.0.33" - } - }, - "extglob": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/extglob/-/extglob-2.0.4.tgz", - "integrity": "sha512-Nmb6QXkELsuBr24CJSkilo6UHHgbekK5UiZgfE6UHD3Eb27YC6oD+bhcT+tJ6cl8dmsgdQxnWlcry8ksBIBLpw==", - "dev": true, - "requires": { - "array-unique": "^0.3.2", - "define-property": "^1.0.0", - "expand-brackets": "^2.1.4", - "extend-shallow": "^2.0.1", - "fragment-cache": "^0.2.1", - "regex-not": "^1.0.0", - "snapdragon": "^0.8.1", - "to-regex": "^3.0.1" - }, - "dependencies": { - "define-property": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/define-property/-/define-property-1.0.0.tgz", - "integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=", - "dev": true, - "requires": { - "is-descriptor": "^1.0.0" - } - }, - "extend-shallow": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", - "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", - "dev": true, - "requires": { - "is-extendable": "^0.1.0" - } - }, - "is-accessor-descriptor": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz", - "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", - "dev": true, - "requires": { - "kind-of": "^6.0.0" - } - }, - "is-data-descriptor": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz", - "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", - "dev": true, - "requires": { - "kind-of": "^6.0.0" - } - }, - "is-descriptor": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz", - "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", - "dev": true, - "requires": { - "is-accessor-descriptor": "^1.0.0", - "is-data-descriptor": "^1.0.0", - "kind-of": "^6.0.2" - } - } - } - }, - "extsprintf": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/extsprintf/-/extsprintf-1.3.0.tgz", - "integrity": "sha1-lpGEQOMEGnpBT4xS48V06zw+HgU=" - }, - "fast-deep-equal": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-1.1.0.tgz", - "integrity": "sha1-wFNHeBfIa1HaqFPIHgWbcz0CNhQ=" - }, - "fast-json-stable-stringify": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.0.0.tgz", - "integrity": "sha1-1RQsDK7msRifh9OnYREGT4bIu/I=" - }, - "fast-levenshtein": { - "version": "2.0.6", - "resolved": "https://registry.npmjs.org/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz", - "integrity": "sha1-PYpcZog6FqMMqGQ+hR8Zuqd5eRc=", - "dev": true - }, - "figures": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/figures/-/figures-2.0.0.tgz", - "integrity": "sha1-OrGi0qYsi/tDGgyUy3l6L84nyWI=", - "requires": { - "escape-string-regexp": "^1.0.5" - } - }, - "filename-regex": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/filename-regex/-/filename-regex-2.0.1.tgz", - "integrity": "sha1-wcS5vuPglyXdsQa3XB4wH+LxiyY=" - }, - "fill-range": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-4.0.0.tgz", - "integrity": "sha1-1USBHUKPmOsGpj3EAtJAPDKMOPc=", - "dev": true, - "requires": { - "extend-shallow": "^2.0.1", - "is-number": "^3.0.0", - "repeat-string": "^1.6.1", - "to-regex-range": "^2.1.0" - }, - "dependencies": { - "extend-shallow": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", - "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", - "dev": true, - "requires": { - "is-extendable": "^0.1.0" - } - } - } - }, - "finalhandler": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/finalhandler/-/finalhandler-1.1.1.tgz", - "integrity": "sha512-Y1GUDo39ez4aHAw7MysnUD5JzYX+WaIj8I57kO3aEPT1fFRL4sr7mjei97FgnwhAyyzRYmQZaTHb2+9uZ1dPtg==", - "requires": { - "debug": "2.6.9", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "on-finished": "~2.3.0", - "parseurl": "~1.3.2", - "statuses": "~1.4.0", - "unpipe": "~1.0.0" - }, - "dependencies": { - "debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "requires": { - "ms": "2.0.0" - } - }, - "statuses": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.4.0.tgz", - "integrity": "sha512-zhSCtt8v2NDrRlPQpCNtw/heZLtfUDqxBM1udqikb/Hbk52LK4nQSwr10u77iopCW5LsyHpuXS0GnEc48mLeew==" - } - } - }, - "find-up": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-1.1.2.tgz", - "integrity": "sha1-ay6YIrGizgpgq2TWEOzK1TyyTQ8=", - "requires": { - "path-exists": "^2.0.0", - "pinkie-promise": "^2.0.0" - } - }, - "first-chunk-stream": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/first-chunk-stream/-/first-chunk-stream-2.0.0.tgz", - "integrity": "sha1-G97NuOCDwGZLkZRVgVd6Q6nzHXA=", - "requires": { - "readable-stream": "^2.0.2" - } - }, - "flow-parser": { - "version": "0.68.0", - "resolved": "https://registry.npmjs.org/flow-parser/-/flow-parser-0.68.0.tgz", - "integrity": "sha1-nMlmIKEC4xajFLa81WIFzqzoYtg=" - }, - "for-each": { - "version": "0.3.2", - "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.2.tgz", - "integrity": "sha1-LEBFC5NI6X8oEyJZO6lnBLmr1NQ=", - "requires": { - "is-function": "~1.0.0" - } - }, - "for-in": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/for-in/-/for-in-1.0.2.tgz", - "integrity": "sha1-gQaNKVqBQuwKxybG4iAMMPttXoA=" - }, - "for-own": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/for-own/-/for-own-0.1.5.tgz", - "integrity": "sha1-UmXGgaTylNq78XyVCbZ2OqhFEM4=", - "requires": { - "for-in": "^1.0.1" - } - }, - "forever-agent": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/forever-agent/-/forever-agent-0.6.1.tgz", - "integrity": "sha1-+8cfDEGt6zf5bFd60e1C2P2sypE=" - }, - "form-data": { - "version": "2.3.2", - "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.3.2.tgz", - "integrity": "sha1-SXBJi+YEwgwAXU9cI67NIda0kJk=", - "requires": { - "asynckit": "^0.4.0", - "combined-stream": "1.0.6", - "mime-types": "^2.1.12" - } - }, - "forwarded": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.1.2.tgz", - "integrity": "sha1-mMI9qxF1ZXuMBXPozszZGw/xjIQ=" - }, - "fragment-cache": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/fragment-cache/-/fragment-cache-0.2.1.tgz", - "integrity": "sha1-QpD60n8T6Jvn8zeZxrxaCr//DRk=", - "dev": true, - "requires": { - "map-cache": "^0.2.2" - } - }, - "fresh": { - "version": "0.5.2", - "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.5.2.tgz", - "integrity": "sha1-PYyt2Q2XZWn6g1qx+OSyOhBWBac=" - }, - "from": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/from/-/from-0.1.7.tgz", - "integrity": "sha1-g8YK/Fi5xWmXAH7Rp2izqzA6RP4=", - "dev": true - }, - "from2": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/from2/-/from2-2.3.0.tgz", - "integrity": "sha1-i/tVAr3kpNNs/e6gB/zKIdfjgq8=", - "requires": { - "inherits": "^2.0.1", - "readable-stream": "^2.0.0" - } - }, - "fs-extra": { - "version": "0.30.0", - "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-0.30.0.tgz", - "integrity": "sha1-8jP/zAjU2n1DLapEl3aYnbHfk/A=", - "requires": { - "graceful-fs": "^4.1.2", - "jsonfile": "^2.1.0", - "klaw": "^1.0.0", - "path-is-absolute": "^1.0.0", - "rimraf": "^2.2.8" - } - }, - "fs.realpath": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", - "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=" - }, - "fsevents": { - "version": "1.2.3", - "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-1.2.3.tgz", - "integrity": "sha512-X+57O5YkDTiEQGiw8i7wYc2nQgweIekqkepI8Q3y4wVlurgBt2SuwxTeYUYMZIGpLZH3r/TsMjczCMXE5ZOt7Q==", - "dev": true, - "optional": true, - "requires": { - "nan": "^2.9.2", - "node-pre-gyp": "^0.9.0" - }, - "dependencies": { - "abbrev": { - "version": "1.1.1", - "bundled": true, - "dev": true, - "optional": true - }, - "ansi-regex": { - "version": "2.1.1", - "bundled": true, - "dev": true - }, - "aproba": { - "version": "1.2.0", - "bundled": true, - "dev": true, - "optional": true - }, - "are-we-there-yet": { - "version": "1.1.4", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "delegates": "^1.0.0", - "readable-stream": "^2.0.6" - } - }, - "balanced-match": { - "version": "1.0.0", - "bundled": true, - "dev": true - }, - "brace-expansion": { - "version": "1.1.11", - "bundled": true, - "dev": true, - "requires": { - "balanced-match": "^1.0.0", - "concat-map": "0.0.1" - } - }, - "chownr": { - "version": "1.0.1", - "bundled": true, - "dev": true, - "optional": true - }, - "code-point-at": { - "version": "1.1.0", - "bundled": true, - "dev": true - }, - "concat-map": { - "version": "0.0.1", - "bundled": true, - "dev": true - }, - "console-control-strings": { - "version": "1.1.0", - "bundled": true, - "dev": true - }, - "core-util-is": { - "version": "1.0.2", - "bundled": true, - "dev": true, - "optional": true - }, - "debug": { - "version": "2.6.9", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "ms": "2.0.0" - } - }, - "deep-extend": { - "version": "0.4.2", - "bundled": true, - "dev": true, - "optional": true - }, - "delegates": { - "version": "1.0.0", - "bundled": true, - "dev": true, - "optional": true - }, - "detect-libc": { - "version": "1.0.3", - "bundled": true, - "dev": true, - "optional": true - }, - "fs-minipass": { - "version": "1.2.5", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "minipass": "^2.2.1" - } - }, - "fs.realpath": { - "version": "1.0.0", - "bundled": true, - "dev": true, - "optional": true - }, - "gauge": { - "version": "2.7.4", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "aproba": "^1.0.3", - "console-control-strings": "^1.0.0", - "has-unicode": "^2.0.0", - "object-assign": "^4.1.0", - "signal-exit": "^3.0.0", - "string-width": "^1.0.1", - "strip-ansi": "^3.0.1", - "wide-align": "^1.1.0" - } - }, - "glob": { - "version": "7.1.2", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "fs.realpath": "^1.0.0", - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "^3.0.4", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" - } - }, - "has-unicode": { - "version": "2.0.1", - "bundled": true, - "dev": true, - "optional": true - }, - "iconv-lite": { - "version": "0.4.21", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "safer-buffer": "^2.1.0" - } - }, - "ignore-walk": { - "version": "3.0.1", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "minimatch": "^3.0.4" - } - }, - "inflight": { - "version": "1.0.6", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "once": "^1.3.0", - "wrappy": "1" - } - }, - "inherits": { - "version": "2.0.3", - "bundled": true, - "dev": true - }, - "ini": { - "version": "1.3.5", - "bundled": true, - "dev": true, - "optional": true - }, - "is-fullwidth-code-point": { - "version": "1.0.0", - "bundled": true, - "dev": true, - "requires": { - "number-is-nan": "^1.0.0" - } - }, - "isarray": { - "version": "1.0.0", - "bundled": true, - "dev": true, - "optional": true - }, - "minimatch": { - "version": "3.0.4", - "bundled": true, - "dev": true, - "requires": { - "brace-expansion": "^1.1.7" - } - }, - "minimist": { - "version": "0.0.8", - "bundled": true, - "dev": true - }, - "minipass": { - "version": "2.2.4", - "bundled": true, - "dev": true, - "requires": { - "safe-buffer": "^5.1.1", - "yallist": "^3.0.0" - } - }, - "minizlib": { - "version": "1.1.0", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "minipass": "^2.2.1" - } - }, - "mkdirp": { - "version": "0.5.1", - "bundled": true, - "dev": true, - "requires": { - "minimist": "0.0.8" - } - }, - "ms": { - "version": "2.0.0", - "bundled": true, - "dev": true, - "optional": true - }, - "needle": { - "version": "2.2.0", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "debug": "^2.1.2", - "iconv-lite": "^0.4.4", - "sax": "^1.2.4" - } - }, - "node-pre-gyp": { - "version": "0.9.1", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "detect-libc": "^1.0.2", - "mkdirp": "^0.5.1", - "needle": "^2.2.0", - "nopt": "^4.0.1", - "npm-packlist": "^1.1.6", - "npmlog": "^4.0.2", - "rc": "^1.1.7", - "rimraf": "^2.6.1", - "semver": "^5.3.0", - "tar": "^4" - } - }, - "nopt": { - "version": "4.0.1", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "abbrev": "1", - "osenv": "^0.1.4" - } - }, - "npm-bundled": { - "version": "1.0.3", - "bundled": true, - "dev": true, - "optional": true - }, - "npm-packlist": { - "version": "1.1.10", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "ignore-walk": "^3.0.1", - "npm-bundled": "^1.0.1" - } - }, - "npmlog": { - "version": "4.1.2", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "are-we-there-yet": "~1.1.2", - "console-control-strings": "~1.1.0", - "gauge": "~2.7.3", - "set-blocking": "~2.0.0" - } - }, - "number-is-nan": { - "version": "1.0.1", - "bundled": true, - "dev": true - }, - "object-assign": { - "version": "4.1.1", - "bundled": true, - "dev": true, - "optional": true - }, - "once": { - "version": "1.4.0", - "bundled": true, - "dev": true, - "requires": { - "wrappy": "1" - } - }, - "os-homedir": { - "version": "1.0.2", - "bundled": true, - "dev": true, - "optional": true - }, - "os-tmpdir": { - "version": "1.0.2", - "bundled": true, - "dev": true, - "optional": true - }, - "osenv": { - "version": "0.1.5", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "os-homedir": "^1.0.0", - "os-tmpdir": "^1.0.0" - } - }, - "path-is-absolute": { - "version": "1.0.1", - "bundled": true, - "dev": true, - "optional": true - }, - "process-nextick-args": { - "version": "2.0.0", - "bundled": true, - "dev": true, - "optional": true - }, - "rc": { - "version": "1.2.6", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "deep-extend": "~0.4.0", - "ini": "~1.3.0", - "minimist": "^1.2.0", - "strip-json-comments": "~2.0.1" - }, - "dependencies": { - "minimist": { - "version": "1.2.0", - "bundled": true, - "dev": true, - "optional": true - } - } - }, - "readable-stream": { - "version": "2.3.6", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "core-util-is": "~1.0.0", - "inherits": "~2.0.3", - "isarray": "~1.0.0", - "process-nextick-args": "~2.0.0", - "safe-buffer": "~5.1.1", - "string_decoder": "~1.1.1", - "util-deprecate": "~1.0.1" - } - }, - "rimraf": { - "version": "2.6.2", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "glob": "^7.0.5" - } - }, - "safe-buffer": { - "version": "5.1.1", - "bundled": true, - "dev": true - }, - "safer-buffer": { - "version": "2.1.2", - "bundled": true, - "dev": true, - "optional": true - }, - "sax": { - "version": "1.2.4", - "bundled": true, - "dev": true, - "optional": true - }, - "semver": { - "version": "5.5.0", - "bundled": true, - "dev": true, - "optional": true - }, - "set-blocking": { - "version": "2.0.0", - "bundled": true, - "dev": true, - "optional": true - }, - "signal-exit": { - "version": "3.0.2", - "bundled": true, - "dev": true, - "optional": true - }, - "string-width": { - "version": "1.0.2", - "bundled": true, - "dev": true, - "requires": { - "code-point-at": "^1.0.0", - "is-fullwidth-code-point": "^1.0.0", - "strip-ansi": "^3.0.0" - } - }, - "string_decoder": { - "version": "1.1.1", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "safe-buffer": "~5.1.0" - } - }, - "strip-ansi": { - "version": "3.0.1", - "bundled": true, - "dev": true, - "requires": { - "ansi-regex": "^2.0.0" - } - }, - "strip-json-comments": { - "version": "2.0.1", - "bundled": true, - "dev": true, - "optional": true - }, - "tar": { - "version": "4.4.1", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "chownr": "^1.0.1", - "fs-minipass": "^1.2.5", - "minipass": "^2.2.4", - "minizlib": "^1.1.0", - "mkdirp": "^0.5.0", - "safe-buffer": "^5.1.1", - "yallist": "^3.0.2" - } - }, - "util-deprecate": { - "version": "1.0.2", - "bundled": true, - "dev": true, - "optional": true - }, - "wide-align": { - "version": "1.1.2", - "bundled": true, - "dev": true, - "optional": true, - "requires": { - "string-width": "^1.0.2" - } - }, - "wrappy": { - "version": "1.0.2", - "bundled": true, - "dev": true - }, - "yallist": { - "version": "3.0.2", - "bundled": true, - "dev": true - } - } - }, - "ganache-cli": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/ganache-cli/-/ganache-cli-6.1.0.tgz", - "integrity": "sha512-FdTeyk4uLRHGeFiMe+Qnh4Hc5KiTVqvRVVvLDFJEVVKC1P1yHhEgZeh9sp1KhuvxSrxToxgJS25UapYQwH4zHw==", - "requires": { - "source-map-support": "^0.5.3", - "webpack-cli": "^2.0.9" - } - }, - "get-caller-file": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/get-caller-file/-/get-caller-file-1.0.2.tgz", - "integrity": "sha1-9wLmMSfn4jHBYKgMFVSstw1QR+U=" - }, - "get-func-name": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/get-func-name/-/get-func-name-2.0.0.tgz", - "integrity": "sha1-6td0q+5y4gQJQzoGY2YCPdaIekE=", - "dev": true - }, - "get-port": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/get-port/-/get-port-3.2.0.tgz", - "integrity": "sha1-3Xzn3hh8Bsi/NTeWrHHgmfCYDrw=", - "dev": true - }, - "get-stream": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-3.0.0.tgz", - "integrity": "sha1-jpQ9E1jcN1VQVOy+LtsFqhdO3hQ=" - }, - "get-value": { - "version": "2.0.6", - "resolved": "https://registry.npmjs.org/get-value/-/get-value-2.0.6.tgz", - "integrity": "sha1-3BXKHGcjh8p2vTesCjlbogQqLCg=", - "dev": true - }, - "getpass": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/getpass/-/getpass-0.1.7.tgz", - "integrity": "sha1-Xv+OPmhNVprkyysSgmBOi6YhSfo=", - "requires": { - "assert-plus": "^1.0.0" - } - }, - "gh-got": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/gh-got/-/gh-got-6.0.0.tgz", - "integrity": "sha512-F/mS+fsWQMo1zfgG9MD8KWvTWPPzzhuVwY++fhQ5Ggd+0P+CAMHtzMZhNxG+TqGfHDChJKsbh6otfMGqO2AKBw==", - "requires": { - "got": "^7.0.0", - "is-plain-obj": "^1.1.0" - }, - "dependencies": { - "got": { - "version": "7.1.0", - "resolved": "https://registry.npmjs.org/got/-/got-7.1.0.tgz", - "integrity": "sha512-Y5WMo7xKKq1muPsxD+KmrR8DH5auG7fBdDVueZwETwV6VytKyU9OX/ddpq2/1hp1vIPvVb4T81dKQz3BivkNLw==", - "requires": { - "decompress-response": "^3.2.0", - "duplexer3": "^0.1.4", - "get-stream": "^3.0.0", - "is-plain-obj": "^1.1.0", - "is-retry-allowed": "^1.0.0", - "is-stream": "^1.0.0", - "isurl": "^1.0.0-alpha5", - "lowercase-keys": "^1.0.0", - "p-cancelable": "^0.3.0", - "p-timeout": "^1.1.1", - "safe-buffer": "^5.0.1", - "timed-out": "^4.0.0", - "url-parse-lax": "^1.0.0", - "url-to-options": "^1.0.1" - } - }, - "p-cancelable": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/p-cancelable/-/p-cancelable-0.3.0.tgz", - "integrity": "sha512-RVbZPLso8+jFeq1MfNvgXtCRED2raz/dKpacfTNxsx6pLEpEomM7gah6VeHSYV3+vo0OAi4MkArtQcWWXuQoyw==" - }, - "p-timeout": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/p-timeout/-/p-timeout-1.2.1.tgz", - "integrity": "sha1-XrOzU7f86Z8QGhA4iAuwVOu+o4Y=", - "requires": { - "p-finally": "^1.0.0" - } - } - } - }, - "github-username": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/github-username/-/github-username-4.1.0.tgz", - "integrity": "sha1-y+KABBiDIG2kISrp5LXxacML9Bc=", - "requires": { - "gh-got": "^6.0.0" - } - }, - "glob": { - "version": "7.1.1", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.1.tgz", - "integrity": "sha1-gFIR3wT6rxxjo2ADBs31reULLsg=", - "requires": { - "fs.realpath": "^1.0.0", - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "^3.0.2", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" - } - }, - "glob-all": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/glob-all/-/glob-all-3.1.0.tgz", - "integrity": "sha1-iRPd+17hrHgSZWJBsD1SF8ZLAqs=", - "requires": { - "glob": "^7.0.5", - "yargs": "~1.2.6" - }, - "dependencies": { - "minimist": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-0.1.0.tgz", - "integrity": "sha1-md9lelJXTCHJBXSX33QnkLK0wN4=" - }, - "yargs": { - "version": "1.2.6", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-1.2.6.tgz", - "integrity": "sha1-nHtKgv1dWVsr8Xq23MQxNUMv40s=", - "requires": { - "minimist": "^0.1.0" - } - } - } - }, - "glob-base": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/glob-base/-/glob-base-0.3.0.tgz", - "integrity": "sha1-27Fk9iIbHAscz4Kuoyi0l98Oo8Q=", - "requires": { - "glob-parent": "^2.0.0", - "is-glob": "^2.0.0" - }, - "dependencies": { - "glob-parent": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-2.0.0.tgz", - "integrity": "sha1-gTg9ctsFT8zPUzbaqQLxgvbtuyg=", - "requires": { - "is-glob": "^2.0.0" - } - }, - "is-extglob": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-1.0.0.tgz", - "integrity": "sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA=" - }, - "is-glob": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-2.0.1.tgz", - "integrity": "sha1-0Jb5JqPe1WAPP9/ZEZjLCIjC2GM=", - "requires": { - "is-extglob": "^1.0.0" - } - } - } - }, - "glob-parent": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-3.1.0.tgz", - "integrity": "sha1-nmr2KZ2NO9K9QEMIMr0RPfkGxa4=", - "dev": true, - "requires": { - "is-glob": "^3.1.0", - "path-dirname": "^1.0.0" - }, - "dependencies": { - "is-glob": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-3.1.0.tgz", - "integrity": "sha1-e6WuJCF4BKxwcHuWkiVnSGzD6Eo=", - "dev": true, - "requires": { - "is-extglob": "^2.1.0" - } - } - } - }, - "global": { - "version": "4.3.2", - "resolved": "https://registry.npmjs.org/global/-/global-4.3.2.tgz", - "integrity": "sha1-52mJJopsdMOJCLEwWxD8DjlOnQ8=", - "requires": { - "min-document": "^2.19.0", - "process": "~0.5.1" - } - }, - "global-dirs": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/global-dirs/-/global-dirs-0.1.1.tgz", - "integrity": "sha1-sxnA3UYH81PzvpzKTHL8FIxJ9EU=", - "dev": true, - "requires": { - "ini": "^1.3.4" - } - }, - "global-modules": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/global-modules/-/global-modules-1.0.0.tgz", - "integrity": "sha512-sKzpEkf11GpOFuw0Zzjzmt4B4UZwjOcG757PPvrfhxcLFbq0wpsgpOqxpxtxFiCG4DtG93M6XRVbF2oGdev7bg==", - "requires": { - "global-prefix": "^1.0.1", - "is-windows": "^1.0.1", - "resolve-dir": "^1.0.0" - } - }, - "global-prefix": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/global-prefix/-/global-prefix-1.0.2.tgz", - "integrity": "sha1-2/dDxsFJklk8ZVVoy2btMsASLr4=", - "requires": { - "expand-tilde": "^2.0.2", - "homedir-polyfill": "^1.0.1", - "ini": "^1.3.4", - "is-windows": "^1.0.1", - "which": "^1.2.14" - } - }, - "globals": { - "version": "9.18.0", - "resolved": "https://registry.npmjs.org/globals/-/globals-9.18.0.tgz", - "integrity": "sha512-S0nG3CLEQiY/ILxqtztTWH/3iRRdyBLw6KMDxnKMchrtbj2OFmehVh0WUCfW3DUrIgx/qFrJPICrq4Z4sTR9UQ==" - }, - "globby": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/globby/-/globby-6.1.0.tgz", - "integrity": "sha1-9abXDoOV4hyFj7BInWTfAkJNUGw=", - "requires": { - "array-union": "^1.0.1", - "glob": "^7.0.3", - "object-assign": "^4.0.1", - "pify": "^2.0.0", - "pinkie-promise": "^2.0.0" - } - }, - "got": { - "version": "6.7.1", - "resolved": "https://registry.npmjs.org/got/-/got-6.7.1.tgz", - "integrity": "sha1-JAzQV4WpoY5WHcG0S0HHY+8ejbA=", - "dev": true, - "requires": { - "create-error-class": "^3.0.0", - "duplexer3": "^0.1.4", - "get-stream": "^3.0.0", - "is-redirect": "^1.0.0", - "is-retry-allowed": "^1.0.0", - "is-stream": "^1.0.0", - "lowercase-keys": "^1.0.0", - "safe-buffer": "^5.0.1", - "timed-out": "^4.0.0", - "unzip-response": "^2.0.1", - "url-parse-lax": "^1.0.0" - } - }, - "graceful-fs": { - "version": "4.1.11", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.11.tgz", - "integrity": "sha1-Dovf5NHduIVNZOBOp8AOKgJuVlg=" - }, - "grouped-queue": { - "version": "0.3.3", - "resolved": "https://registry.npmjs.org/grouped-queue/-/grouped-queue-0.3.3.tgz", - "integrity": "sha1-wWfSpTGcWg4JZO9qJbfC34mWyFw=", - "requires": { - "lodash": "^4.17.2" - } - }, - "growl": { - "version": "1.9.2", - "resolved": "https://registry.npmjs.org/growl/-/growl-1.9.2.tgz", - "integrity": "sha1-Dqd0NxXbjY3ixe3hd14bRayFwC8=", - "dev": true - }, - "handlebars": { - "version": "4.0.11", - "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.0.11.tgz", - "integrity": "sha1-Ywo13+ApS8KB7a5v/F0yn8eYLcw=", - "dev": true, - "requires": { - "async": "^1.4.0", - "optimist": "^0.6.1", - "source-map": "^0.4.4", - "uglify-js": "^2.6" - }, - "dependencies": { - "async": { - "version": "1.5.2", - "resolved": "https://registry.npmjs.org/async/-/async-1.5.2.tgz", - "integrity": "sha1-7GphrlZIDAw8skHJVhjiCJL5Zyo=", - "dev": true - }, - "source-map": { - "version": "0.4.4", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.4.4.tgz", - "integrity": "sha1-66T12pwNyZneaAMti092FzZSA2s=", - "dev": true, - "requires": { - "amdefine": ">=0.0.4" - } - } - } - }, - "har-schema": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/har-schema/-/har-schema-2.0.0.tgz", - "integrity": "sha1-qUwiJOvKwEeCoNkDVSHyRzW37JI=" - }, - "har-validator": { - "version": "5.0.3", - "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-5.0.3.tgz", - "integrity": "sha1-ukAsJmGU8VlW7xXg/PJCmT9qff0=", - "requires": { - "ajv": "^5.1.0", - "har-schema": "^2.0.0" - } - }, - "has-ansi": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/has-ansi/-/has-ansi-2.0.0.tgz", - "integrity": "sha1-NPUEnOHs3ysGSa8+8k5F7TVBbZE=", - "requires": { - "ansi-regex": "^2.0.0" - } - }, - "has-color": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/has-color/-/has-color-0.1.7.tgz", - "integrity": "sha1-ZxRKUmDDT8PMpnfQQdr1L+e3iy8=" - }, - "has-flag": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-1.0.0.tgz", - "integrity": "sha1-nZ55MWXOAXoA8AQYxD+UKnsdEfo=", - "dev": true - }, - "has-symbol-support-x": { - "version": "1.4.2", - "resolved": "https://registry.npmjs.org/has-symbol-support-x/-/has-symbol-support-x-1.4.2.tgz", - "integrity": "sha512-3ToOva++HaW+eCpgqZrCfN51IPB+7bJNVT6CUATzueB5Heb8o6Nam0V3HG5dlDvZU1Gn5QLcbahiKw/XVk5JJw==" - }, - "has-to-string-tag-x": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/has-to-string-tag-x/-/has-to-string-tag-x-1.4.1.tgz", - "integrity": "sha512-vdbKfmw+3LoOYVr+mtxHaX5a96+0f3DljYd8JOqvOLsf5mw2Otda2qCDT9qRqLAhrjyQ0h7ual5nOiASpsGNFw==", - "requires": { - "has-symbol-support-x": "^1.4.1" - } - }, - "has-value": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/has-value/-/has-value-1.0.0.tgz", - "integrity": "sha1-GLKB2lhbHFxR3vJMkw7SmgvmsXc=", - "dev": true, - "requires": { - "get-value": "^2.0.6", - "has-values": "^1.0.0", - "isobject": "^3.0.0" - } - }, - "has-values": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/has-values/-/has-values-1.0.0.tgz", - "integrity": "sha1-lbC2P+whRmGab+V/51Yo1aOe/k8=", - "dev": true, - "requires": { - "is-number": "^3.0.0", - "kind-of": "^4.0.0" - }, - "dependencies": { - "kind-of": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-4.0.0.tgz", - "integrity": "sha1-IIE989cSkosgc3hpGkUGb65y3Vc=", - "dev": true, - "requires": { - "is-buffer": "^1.1.5" - } - } - } - }, - "hash.js": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/hash.js/-/hash.js-1.1.3.tgz", - "integrity": "sha512-/UETyP0W22QILqS+6HowevwhEFJ3MBJnwTf75Qob9Wz9t0DPuisL8kW8YZMK62dHAKE1c1p+gY1TtOLY+USEHA==", - "requires": { - "inherits": "^2.0.3", - "minimalistic-assert": "^1.0.0" - } - }, - "hawk": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/hawk/-/hawk-6.0.2.tgz", - "integrity": "sha512-miowhl2+U7Qle4vdLqDdPt9m09K6yZhkLDTWGoUiUzrQCn+mHHSmfJgAyGaLRZbPmTqfFFjRV1QWCW0VWUJBbQ==", - "requires": { - "boom": "4.x.x", - "cryptiles": "3.x.x", - "hoek": "4.x.x", - "sntp": "2.x.x" - } - }, - "he": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/he/-/he-1.1.1.tgz", - "integrity": "sha1-k0EP0hsAlzUVH4howvJx80J+I/0=" - }, - "hmac-drbg": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/hmac-drbg/-/hmac-drbg-1.0.1.tgz", - "integrity": "sha1-0nRXAQJabHdabFRXk+1QL8DGSaE=", - "requires": { - "hash.js": "^1.0.3", - "minimalistic-assert": "^1.0.0", - "minimalistic-crypto-utils": "^1.0.1" - } - }, - "hoek": { - "version": "4.2.1", - "resolved": "https://registry.npmjs.org/hoek/-/hoek-4.2.1.tgz", - "integrity": "sha512-QLg82fGkfnJ/4iy1xZ81/9SIJiq1NGFUMGs6ParyjBZr6jW2Ufj/snDqTHixNlHdPNwN2RLVD0Pi3igeK9+JfA==" - }, - "home-or-tmp": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/home-or-tmp/-/home-or-tmp-2.0.0.tgz", - "integrity": "sha1-42w/LSyufXRqhX440Y1fMqeILbg=", - "requires": { - "os-homedir": "^1.0.0", - "os-tmpdir": "^1.0.1" - } - }, - "homedir-polyfill": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/homedir-polyfill/-/homedir-polyfill-1.0.1.tgz", - "integrity": "sha1-TCu8inWJmP7r9e1oWA921GdotLw=", - "requires": { - "parse-passwd": "^1.0.0" - } - }, - "hosted-git-info": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-2.5.0.tgz", - "integrity": "sha512-pNgbURSuab90KbTqvRPsseaTxOJCZBD0a7t+haSN33piP9cCM4l0CqdzAif2hUqm716UovKB2ROmiabGAKVXyg==" - }, - "http-basic": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/http-basic/-/http-basic-7.0.0.tgz", - "integrity": "sha1-gvClBr6UJzLsje6+6A50bvVzbbo=", - "dev": true, - "requires": { - "@types/concat-stream": "^1.6.0", - "@types/node": "^9.4.1", - "caseless": "~0.12.0", - "concat-stream": "^1.4.6", - "http-response-object": "^3.0.1", - "parse-cache-control": "^1.0.1" - } - }, - "http-cache-semantics": { - "version": "3.8.1", - "resolved": "https://registry.npmjs.org/http-cache-semantics/-/http-cache-semantics-3.8.1.tgz", - "integrity": "sha512-5ai2iksyV8ZXmnZhHH4rWPoxxistEexSi5936zIQ1bnNTW5VnA85B6P/VpXiRM017IgRvb2kKo1a//y+0wSp3w==" - }, - "http-errors": { - "version": "1.6.3", - "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.6.3.tgz", - "integrity": "sha1-i1VoC7S+KDoLW/TqLjhYC+HZMg0=", - "requires": { - "depd": "~1.1.2", - "inherits": "2.0.3", - "setprototypeof": "1.1.0", - "statuses": ">= 1.4.0 < 2" - } - }, - "http-response-object": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/http-response-object/-/http-response-object-3.0.1.tgz", - "integrity": "sha512-6L0Fkd6TozA8kFSfh9Widst0wfza3U1Ex2RjJ6zNDK0vR1U1auUR6jY4Nn2Xl7CCy0ikFmxW1XcspVpb9RvwTg==", - "dev": true, - "requires": { - "@types/node": "^9.3.0" - } - }, - "http-signature": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/http-signature/-/http-signature-1.2.0.tgz", - "integrity": "sha1-muzZJRFHcvPZW2WmCruPfBj7rOE=", - "requires": { - "assert-plus": "^1.0.0", - "jsprim": "^1.2.2", - "sshpk": "^1.7.0" - } - }, - "iconv-lite": { - "version": "0.4.19", - "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.19.tgz", - "integrity": "sha512-oTZqweIP51xaGPI4uPa56/Pri/480R+mo7SeU+YETByQNhDG55ycFyNLIgta9vXhILrxXDmF7ZGhqZIcuN0gJQ==" - }, - "ignore-by-default": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/ignore-by-default/-/ignore-by-default-1.0.1.tgz", - "integrity": "sha1-SMptcvbGo68Aqa1K5odr44ieKwk=", - "dev": true - }, - "import-lazy": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/import-lazy/-/import-lazy-2.1.0.tgz", - "integrity": "sha1-BWmOPUXIjo1+nZLLBYTnfwlvPkM=", - "dev": true - }, - "imurmurhash": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/imurmurhash/-/imurmurhash-0.1.4.tgz", - "integrity": "sha1-khi5srkoojixPcT7a21XbyMUU+o=" - }, - "indent-string": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/indent-string/-/indent-string-2.1.0.tgz", - "integrity": "sha1-ji1INIdCEhtKghi3oTfppSBJ3IA=", - "requires": { - "repeating": "^2.0.0" - } - }, - "inflight": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", - "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=", - "requires": { - "once": "^1.3.0", - "wrappy": "1" - } - }, - "inherits": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=" - }, - "ini": { - "version": "1.3.5", - "resolved": "https://registry.npmjs.org/ini/-/ini-1.3.5.tgz", - "integrity": "sha512-RZY5huIKCMRWDUqZlEi72f/lmXKMvuszcMBduliQ3nnWbx9X/ZBQO7DijMEYS9EhHBb2qacRUMtC7svLwe0lcw==" - }, - "inquirer": { - "version": "5.2.0", - "resolved": "https://registry.npmjs.org/inquirer/-/inquirer-5.2.0.tgz", - "integrity": "sha512-E9BmnJbAKLPGonz0HeWHtbKf+EeSP93paWO3ZYoUpq/aowXvYGjjCSuashhXPpzbArIjBbji39THkxTz9ZeEUQ==", - "requires": { - "ansi-escapes": "^3.0.0", - "chalk": "^2.0.0", - "cli-cursor": "^2.1.0", - "cli-width": "^2.0.0", - "external-editor": "^2.1.0", - "figures": "^2.0.0", - "lodash": "^4.3.0", - "mute-stream": "0.0.7", - "run-async": "^2.2.0", - "rxjs": "^5.5.2", - "string-width": "^2.1.0", - "strip-ansi": "^4.0.0", - "through": "^2.3.6" - }, - "dependencies": { - "ansi-regex": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", - "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=" - }, - "is-fullwidth-code-point": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", - "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=" - }, - "string-width": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", - "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", - "requires": { - "is-fullwidth-code-point": "^2.0.0", - "strip-ansi": "^4.0.0" - } - }, - "strip-ansi": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", - "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", - "requires": { - "ansi-regex": "^3.0.0" - } - } - } - }, - "interpret": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/interpret/-/interpret-1.1.0.tgz", - "integrity": "sha1-ftGxQQxqDg94z5XTuEQMY/eLhhQ=" - }, - "into-stream": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/into-stream/-/into-stream-3.1.0.tgz", - "integrity": "sha1-lvsKk2wSur1v8XUqF9BWFqvQlMY=", - "requires": { - "from2": "^2.1.1", - "p-is-promise": "^1.1.0" - } - }, - "invariant": { - "version": "2.2.4", - "resolved": "https://registry.npmjs.org/invariant/-/invariant-2.2.4.tgz", - "integrity": "sha512-phJfQVBuaJM5raOpJjSfkiD6BpbCE4Ns//LaXl6wGYtUBY83nWS6Rf9tXm2e8VaK60JEjYldbPif/A2B1C2gNA==", - "requires": { - "loose-envify": "^1.0.0" - } - }, - "invert-kv": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/invert-kv/-/invert-kv-1.0.0.tgz", - "integrity": "sha1-EEqOSqym09jNFXqO+L+rLXo//bY=" - }, - "ipaddr.js": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.6.0.tgz", - "integrity": "sha1-4/o1e3c9phnybpXwSdBVxyeW+Gs=" - }, - "is-accessor-descriptor": { - "version": "0.1.6", - "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-0.1.6.tgz", - "integrity": "sha1-qeEss66Nh2cn7u84Q/igiXtcmNY=", - "dev": true, - "requires": { - "kind-of": "^3.0.2" - }, - "dependencies": { - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", - "dev": true, - "requires": { - "is-buffer": "^1.1.5" - } - } - } - }, - "is-arrayish": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/is-arrayish/-/is-arrayish-0.2.1.tgz", - "integrity": "sha1-d8mYQFJ6qOyxqLppe4BkWnqSap0=" - }, - "is-binary-path": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-binary-path/-/is-binary-path-1.0.1.tgz", - "integrity": "sha1-dfFmQrSA8YenEcgUFh/TpKdlWJg=", - "dev": true, - "requires": { - "binary-extensions": "^1.0.0" - } - }, - "is-buffer": { - "version": "1.1.6", - "resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-1.1.6.tgz", - "integrity": "sha512-NcdALwpXkTm5Zvvbk7owOUSvVvBKDgKP5/ewfXEznmQFfs4ZRmanOeKBTjRVjka3QFoN6XJ+9F3USqfHqTaU5w==" - }, - "is-builtin-module": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-builtin-module/-/is-builtin-module-1.0.0.tgz", - "integrity": "sha1-VAVy0096wxGfj3bDDLwbHgN6/74=", - "requires": { - "builtin-modules": "^1.0.0" - } - }, - "is-ci": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/is-ci/-/is-ci-1.1.0.tgz", - "integrity": "sha512-c7TnwxLePuqIlxHgr7xtxzycJPegNHFuIrBkwbf8hc58//+Op1CqFkyS+xnIMkwn9UsJIwc174BIjkyBmSpjKg==", - "dev": true, - "requires": { - "ci-info": "^1.0.0" - } - }, - "is-data-descriptor": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-0.1.4.tgz", - "integrity": "sha1-C17mSDiOLIYCgueT8YVv7D8wG1Y=", - "dev": true, - "requires": { - "kind-of": "^3.0.2" - }, - "dependencies": { - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", - "dev": true, - "requires": { - "is-buffer": "^1.1.5" - } - } - } - }, - "is-descriptor": { - "version": "0.1.6", - "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-0.1.6.tgz", - "integrity": "sha512-avDYr0SB3DwO9zsMov0gKCESFYqCnE4hq/4z3TdUlukEy5t9C0YRq7HLrsN52NAcqXKaepeCD0n+B0arnVG3Hg==", - "dev": true, - "requires": { - "is-accessor-descriptor": "^0.1.6", - "is-data-descriptor": "^0.1.4", - "kind-of": "^5.0.0" - }, - "dependencies": { - "kind-of": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-5.1.0.tgz", - "integrity": "sha512-NGEErnH6F2vUuXDh+OlbcKW7/wOcfdRHaZ7VWtqCztfHri/++YKmP51OdWeGPuqCOba6kk2OTe5d02VmTB80Pw==", - "dev": true - } - } - }, - "is-dotfile": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/is-dotfile/-/is-dotfile-1.0.3.tgz", - "integrity": "sha1-pqLzL/0t+wT1yiXs0Pa4PPeYoeE=" - }, - "is-equal-shallow": { - "version": "0.1.3", - "resolved": "https://registry.npmjs.org/is-equal-shallow/-/is-equal-shallow-0.1.3.tgz", - "integrity": "sha1-IjgJj8Ih3gvPpdnqxMRdY4qhxTQ=", - "requires": { - "is-primitive": "^2.0.0" - } - }, - "is-extendable": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-0.1.1.tgz", - "integrity": "sha1-YrEQ4omkcUGOPsNqYX1HLjAd/Ik=" - }, - "is-extglob": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", - "integrity": "sha1-qIwCU1eR8C7TfHahueqXc8gz+MI=", - "dev": true - }, - "is-finite": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/is-finite/-/is-finite-1.0.2.tgz", - "integrity": "sha1-zGZ3aVYCvlUO8R6LSqYwU0K20Ko=", - "requires": { - "number-is-nan": "^1.0.0" - } - }, - "is-fullwidth-code-point": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz", - "integrity": "sha1-754xOG8DGn8NZDr4L95QxFfvAMs=", - "requires": { - "number-is-nan": "^1.0.0" - } - }, - "is-function": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-function/-/is-function-1.0.1.tgz", - "integrity": "sha1-Es+5i2W1fdPRk6MSH19uL0N2ArU=" - }, - "is-glob": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.0.tgz", - "integrity": "sha1-lSHHaEXMJhCoUgPd8ICpWML/q8A=", - "dev": true, - "requires": { - "is-extglob": "^2.1.1" - } - }, - "is-hex-prefixed": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-hex-prefixed/-/is-hex-prefixed-1.0.0.tgz", - "integrity": "sha1-fY035q135dEnFIkTxXPggtd39VQ=" - }, - "is-installed-globally": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/is-installed-globally/-/is-installed-globally-0.1.0.tgz", - "integrity": "sha1-Df2Y9akRFxbdU13aZJL2e/PSWoA=", - "dev": true, - "requires": { - "global-dirs": "^0.1.0", - "is-path-inside": "^1.0.0" - } - }, - "is-npm": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-npm/-/is-npm-1.0.0.tgz", - "integrity": "sha1-8vtjpl5JBbQGyGBydloaTceTufQ=", - "dev": true - }, - "is-number": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/is-number/-/is-number-3.0.0.tgz", - "integrity": "sha1-JP1iAaR4LPUFYcgQJ2r8fRLXEZU=", - "requires": { - "kind-of": "^3.0.2" - }, - "dependencies": { - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", - "requires": { - "is-buffer": "^1.1.5" - } - } - } - }, - "is-obj": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-obj/-/is-obj-1.0.1.tgz", - "integrity": "sha1-PkcprB9f3gJc19g6iW2rn09n2w8=", - "dev": true - }, - "is-object": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-object/-/is-object-1.0.1.tgz", - "integrity": "sha1-iVJojF7C/9awPsyF52ngKQMINHA=" - }, - "is-observable": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/is-observable/-/is-observable-0.2.0.tgz", - "integrity": "sha1-s2ExHYPG5dcmyr9eJQsCNxBvWuI=", - "requires": { - "symbol-observable": "^0.2.2" - }, - "dependencies": { - "symbol-observable": { - "version": "0.2.4", - "resolved": "https://registry.npmjs.org/symbol-observable/-/symbol-observable-0.2.4.tgz", - "integrity": "sha1-lag9smGG1q9+ehjb2XYKL4bQj0A=" - } - } - }, - "is-odd": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-odd/-/is-odd-2.0.0.tgz", - "integrity": "sha512-OTiixgpZAT1M4NHgS5IguFp/Vz2VI3U7Goh4/HA1adtwyLtSBrxYlcSYkhpAE07s4fKEcjrFxyvtQBND4vFQyQ==", - "dev": true, - "requires": { - "is-number": "^4.0.0" - }, - "dependencies": { - "is-number": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/is-number/-/is-number-4.0.0.tgz", - "integrity": "sha512-rSklcAIlf1OmFdyAqbnWTLVelsQ58uvZ66S/ZyawjWqIviTWCjg2PzVGw8WUA+nNuPTqb4wgA+NszrJ+08LlgQ==", - "dev": true - } - } - }, - "is-path-inside": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-path-inside/-/is-path-inside-1.0.1.tgz", - "integrity": "sha1-jvW33lBDej/cprToZe96pVy0gDY=", - "dev": true, - "requires": { - "path-is-inside": "^1.0.1" - } - }, - "is-plain-obj": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-1.1.0.tgz", - "integrity": "sha1-caUMhCnfync8kqOQpKA7OfzVHT4=" - }, - "is-plain-object": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/is-plain-object/-/is-plain-object-2.0.4.tgz", - "integrity": "sha512-h5PpgXkWitc38BBMYawTYMWJHFZJVnBquFE57xFpjB8pJFiF6gZ+bU+WyI/yqXiFR5mdLsgYNaPe8uao6Uv9Og==", - "dev": true, - "requires": { - "isobject": "^3.0.1" - } - }, - "is-posix-bracket": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/is-posix-bracket/-/is-posix-bracket-0.1.1.tgz", - "integrity": "sha1-MzTceXdDaOkvAW5vvAqI9c1ua8Q=" - }, - "is-primitive": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-primitive/-/is-primitive-2.0.0.tgz", - "integrity": "sha1-IHurkWOEmcB7Kt8kCkGochADRXU=" - }, - "is-promise": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/is-promise/-/is-promise-2.1.0.tgz", - "integrity": "sha1-eaKp7OfwlugPNtKy87wWwf9L8/o=" - }, - "is-redirect": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-redirect/-/is-redirect-1.0.0.tgz", - "integrity": "sha1-HQPd7VO9jbDzDCbk+V02/HyH3CQ=", - "dev": true - }, - "is-retry-allowed": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/is-retry-allowed/-/is-retry-allowed-1.1.0.tgz", - "integrity": "sha1-EaBgVotnM5REAz0BJaYaINVk+zQ=" - }, - "is-scoped": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-scoped/-/is-scoped-1.0.0.tgz", - "integrity": "sha1-RJypgpnnEwOCViieyytUDcQ3yzA=", - "requires": { - "scoped-regex": "^1.0.0" - } - }, - "is-stream": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-1.1.0.tgz", - "integrity": "sha1-EtSj3U5o4Lec6428hBc66A2RykQ=" - }, - "is-typedarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-typedarray/-/is-typedarray-1.0.0.tgz", - "integrity": "sha1-5HnICFjfDBsR3dppQPlgEfzaSpo=" - }, - "is-utf8": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/is-utf8/-/is-utf8-0.2.1.tgz", - "integrity": "sha1-Sw2hRCEE0bM2NA6AeX6GXPOffXI=" - }, - "is-windows": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/is-windows/-/is-windows-1.0.2.tgz", - "integrity": "sha512-eXK1UInq2bPmjyX6e3VHIzMLobc4J94i4AWn+Hpq3OU5KkrRC96OAcR3PRJ/pGu6m8TRnBHP9dkXQVsT/COVIA==" - }, - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=" - }, - "isexe": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", - "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=" - }, - "isobject": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", - "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=", - "dev": true - }, - "isstream": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/isstream/-/isstream-0.1.2.tgz", - "integrity": "sha1-R+Y/evVa+m+S4VAOaQ64uFKcCZo=" - }, - "istanbul": { - "version": "0.4.5", - "resolved": "https://registry.npmjs.org/istanbul/-/istanbul-0.4.5.tgz", - "integrity": "sha1-ZcfXPUxNqE1POsMQuRj7C4Azczs=", - "dev": true, - "requires": { - "abbrev": "1.0.x", - "async": "1.x", - "escodegen": "1.8.x", - "esprima": "2.7.x", - "glob": "^5.0.15", - "handlebars": "^4.0.1", - "js-yaml": "3.x", - "mkdirp": "0.5.x", - "nopt": "3.x", - "once": "1.x", - "resolve": "1.1.x", - "supports-color": "^3.1.0", - "which": "^1.1.1", - "wordwrap": "^1.0.0" - }, - "dependencies": { - "abbrev": { - "version": "1.0.9", - "resolved": "https://registry.npmjs.org/abbrev/-/abbrev-1.0.9.tgz", - "integrity": "sha1-kbR5JYinc4wl813W9jdSovh3YTU=", - "dev": true - }, - "async": { - "version": "1.5.2", - "resolved": "https://registry.npmjs.org/async/-/async-1.5.2.tgz", - "integrity": "sha1-7GphrlZIDAw8skHJVhjiCJL5Zyo=", - "dev": true - }, - "esprima": { - "version": "2.7.3", - "resolved": "https://registry.npmjs.org/esprima/-/esprima-2.7.3.tgz", - "integrity": "sha1-luO3DVd59q1JzQMmc9HDEnZ7pYE=", - "dev": true }, "glob": { - "version": "5.0.15", - "resolved": "https://registry.npmjs.org/glob/-/glob-5.0.15.tgz", - "integrity": "sha1-G8k2ueAvSmA/zCIuz3Yz0wuLk7E=", + "version": "7.1.3", + "bundled": true, "dev": true, + "optional": true, "requires": { + "fs.realpath": "^1.0.0", "inflight": "^1.0.4", "inherits": "2", - "minimatch": "2 || 3", + "minimatch": "^3.0.4", "once": "^1.3.0", "path-is-absolute": "^1.0.0" } }, - "nopt": { - "version": "3.0.6", - "resolved": "https://registry.npmjs.org/nopt/-/nopt-3.0.6.tgz", - "integrity": "sha1-xkZdvwirzU2zWTF/eaxopkayj/k=", + "has-unicode": { + "version": "2.0.1", + "bundled": true, + "dev": true, + "optional": true + }, + "iconv-lite": { + "version": "0.4.24", + "bundled": true, + "dev": true, + "optional": true, + "requires": { + "safer-buffer": ">= 2.1.2 < 3" + } + }, + "ignore-walk": { + "version": "3.0.1", + "bundled": true, "dev": true, + "optional": true, "requires": { - "abbrev": "1" + "minimatch": "^3.0.4" } }, - "resolve": { - "version": "1.1.7", - "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.1.7.tgz", - "integrity": "sha1-IDEU2CrSxe2ejgQRs5ModeiJ6Xs=", + "inflight": { + "version": "1.0.6", + "bundled": true, + "dev": true, + "optional": true, + "requires": { + "once": "^1.3.0", + "wrappy": "1" + } + }, + "inherits": { + "version": "2.0.3", + "bundled": true, "dev": true - } - } - }, - "istextorbinary": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/istextorbinary/-/istextorbinary-2.2.1.tgz", - "integrity": "sha512-TS+hoFl8Z5FAFMK38nhBkdLt44CclNRgDHWeMgsV8ko3nDlr/9UI2Sf839sW7enijf8oKsZYXRvM8g0it9Zmcw==", - "requires": { - "binaryextensions": "2", - "editions": "^1.3.3", - "textextensions": "2" - } - }, - "isurl": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isurl/-/isurl-1.0.0.tgz", - "integrity": "sha512-1P/yWsxPlDtn7QeRD+ULKQPaIaN6yF368GZ2vDfv0AL0NwpStafjWCDDdn0k8wgFMWpVAqG7oJhxHnlud42i9w==", - "requires": { - "has-to-string-tag-x": "^1.2.0", - "is-object": "^1.0.1" - } - }, - "jade": { - "version": "0.26.3", - "resolved": "https://registry.npmjs.org/jade/-/jade-0.26.3.tgz", - "integrity": "sha1-jxDXl32NefL2/4YqgbBRPMslaGw=", - "dev": true, - "requires": { - "commander": "0.6.1", - "mkdirp": "0.3.0" - }, - "dependencies": { - "commander": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/commander/-/commander-0.6.1.tgz", - "integrity": "sha1-+mihT2qUXVTbvlDYzbMyDp47GgY=", + }, + "ini": { + "version": "1.3.5", + "bundled": true, + "dev": true, + "optional": true + }, + "is-fullwidth-code-point": { + "version": "1.0.0", + "bundled": true, + "dev": true, + "requires": { + "number-is-nan": "^1.0.0" + } + }, + "isarray": { + "version": "1.0.0", + "bundled": true, + "dev": true, + "optional": true + }, + "minimatch": { + "version": "3.0.4", + "bundled": true, + "dev": true, + "requires": { + "brace-expansion": "^1.1.7" + } + }, + "minimist": { + "version": "0.0.8", + "bundled": true, "dev": true }, + "minipass": { + "version": "2.3.5", + "bundled": true, + "dev": true, + "requires": { + "safe-buffer": "^5.1.2", + "yallist": "^3.0.0" + } + }, + "minizlib": { + "version": "1.2.1", + "bundled": true, + "dev": true, + "optional": true, + "requires": { + "minipass": "^2.2.1" + } + }, "mkdirp": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.3.0.tgz", - "integrity": "sha1-G79asbqCevI1dRQ0kEJkVfSB/h4=", - "dev": true - } - } - }, - "js-sha3": { - "version": "0.5.5", - "resolved": "https://registry.npmjs.org/js-sha3/-/js-sha3-0.5.5.tgz", - "integrity": "sha1-uvDA6MVK1ZA0R9+Wreekobynmko=", - "dev": true - }, - "js-tokens": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-3.0.2.tgz", - "integrity": "sha1-mGbfOVECEw449/mWvOtlRDIJwls=" - }, - "js-yaml": { - "version": "3.11.0", - "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.11.0.tgz", - "integrity": "sha512-saJstZWv7oNeOyBh3+Dx1qWzhW0+e6/8eDzo7p5rDFqxntSztloLtuKu+Ejhtq82jsilwOIZYsCz+lIjthg1Hw==", - "dev": true, - "requires": { - "argparse": "^1.0.7", - "esprima": "^4.0.0" - } - }, - "jsbn": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/jsbn/-/jsbn-0.1.1.tgz", - "integrity": "sha1-peZUwuWi3rXyAdls77yoDA7y9RM=", - "optional": true - }, - "jscodeshift": { - "version": "0.5.0", - "resolved": "https://registry.npmjs.org/jscodeshift/-/jscodeshift-0.5.0.tgz", - "integrity": "sha512-JAcQINNMFpdzzpKJN8k5xXjF3XDuckB1/48uScSzcnNyK199iWEc9AxKL9OoX5144M2w5zEx9Qs4/E/eBZZUlw==", - "requires": { - "babel-plugin-transform-flow-strip-types": "^6.8.0", - "babel-preset-es2015": "^6.9.0", - "babel-preset-stage-1": "^6.5.0", - "babel-register": "^6.9.0", - "babylon": "^7.0.0-beta.30", - "colors": "^1.1.2", - "flow-parser": "^0.*", - "lodash": "^4.13.1", - "micromatch": "^2.3.7", - "neo-async": "^2.5.0", - "node-dir": "0.1.8", - "nomnom": "^1.8.1", - "recast": "^0.14.1", - "temp": "^0.8.1", - "write-file-atomic": "^1.2.0" - }, - "dependencies": { - "arr-diff": { + "version": "0.5.1", + "bundled": true, + "dev": true, + "requires": { + "minimist": "0.0.8" + } + }, + "ms": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/arr-diff/-/arr-diff-2.0.0.tgz", - "integrity": "sha1-jzuCf5Vai9ZpaX5KQlasPOrjVs8=", + "bundled": true, + "dev": true, + "optional": true + }, + "needle": { + "version": "2.2.4", + "bundled": true, + "dev": true, + "optional": true, + "requires": { + "debug": "^2.1.2", + "iconv-lite": "^0.4.4", + "sax": "^1.2.4" + } + }, + "node-pre-gyp": { + "version": "0.10.3", + "bundled": true, + "dev": true, + "optional": true, + "requires": { + "detect-libc": "^1.0.2", + "mkdirp": "^0.5.1", + "needle": "^2.2.1", + "nopt": "^4.0.1", + "npm-packlist": "^1.1.6", + "npmlog": "^4.0.2", + "rc": "^1.2.7", + "rimraf": "^2.6.1", + "semver": "^5.3.0", + "tar": "^4" + } + }, + "nopt": { + "version": "4.0.1", + "bundled": true, + "dev": true, + "optional": true, + "requires": { + "abbrev": "1", + "osenv": "^0.1.4" + } + }, + "npm-bundled": { + "version": "1.0.5", + "bundled": true, + "dev": true, + "optional": true + }, + "npm-packlist": { + "version": "1.2.0", + "bundled": true, + "dev": true, + "optional": true, "requires": { - "arr-flatten": "^1.0.1" + "ignore-walk": "^3.0.1", + "npm-bundled": "^1.0.1" + } + }, + "npmlog": { + "version": "4.1.2", + "bundled": true, + "dev": true, + "optional": true, + "requires": { + "are-we-there-yet": "~1.1.2", + "console-control-strings": "~1.1.0", + "gauge": "~2.7.3", + "set-blocking": "~2.0.0" + } + }, + "number-is-nan": { + "version": "1.0.1", + "bundled": true, + "dev": true + }, + "object-assign": { + "version": "4.1.1", + "bundled": true, + "dev": true, + "optional": true + }, + "once": { + "version": "1.4.0", + "bundled": true, + "dev": true, + "requires": { + "wrappy": "1" + } + }, + "os-homedir": { + "version": "1.0.2", + "bundled": true, + "dev": true, + "optional": true + }, + "os-tmpdir": { + "version": "1.0.2", + "bundled": true, + "dev": true, + "optional": true + }, + "osenv": { + "version": "0.1.5", + "bundled": true, + "dev": true, + "optional": true, + "requires": { + "os-homedir": "^1.0.0", + "os-tmpdir": "^1.0.0" } }, - "array-unique": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/array-unique/-/array-unique-0.2.1.tgz", - "integrity": "sha1-odl8yvy8JiXMcPrc6zalDFiwGlM=" + "path-is-absolute": { + "version": "1.0.1", + "bundled": true, + "dev": true, + "optional": true + }, + "process-nextick-args": { + "version": "2.0.0", + "bundled": true, + "dev": true, + "optional": true }, - "braces": { - "version": "1.8.5", - "resolved": "https://registry.npmjs.org/braces/-/braces-1.8.5.tgz", - "integrity": "sha1-uneWLhLf+WnWt2cR6RS3N4V79qc=", + "rc": { + "version": "1.2.8", + "bundled": true, + "dev": true, + "optional": true, "requires": { - "expand-range": "^1.8.1", - "preserve": "^0.2.0", - "repeat-element": "^1.1.2" + "deep-extend": "^0.6.0", + "ini": "~1.3.0", + "minimist": "^1.2.0", + "strip-json-comments": "~2.0.1" + }, + "dependencies": { + "minimist": { + "version": "1.2.0", + "bundled": true, + "dev": true, + "optional": true + } } }, - "expand-brackets": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/expand-brackets/-/expand-brackets-0.1.5.tgz", - "integrity": "sha1-3wcoTjQqgHzXM6xa9yQR5YHRF3s=", + "readable-stream": { + "version": "2.3.6", + "bundled": true, + "dev": true, + "optional": true, "requires": { - "is-posix-bracket": "^0.1.0" + "core-util-is": "~1.0.0", + "inherits": "~2.0.3", + "isarray": "~1.0.0", + "process-nextick-args": "~2.0.0", + "safe-buffer": "~5.1.1", + "string_decoder": "~1.1.1", + "util-deprecate": "~1.0.1" } }, - "extglob": { - "version": "0.3.2", - "resolved": "https://registry.npmjs.org/extglob/-/extglob-0.3.2.tgz", - "integrity": "sha1-Lhj/PS9JqydlzskCPwEdqo2DSaE=", + "rimraf": { + "version": "2.6.3", + "bundled": true, + "dev": true, + "optional": true, "requires": { - "is-extglob": "^1.0.0" + "glob": "^7.1.3" } }, - "is-extglob": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-1.0.0.tgz", - "integrity": "sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA=" + "safe-buffer": { + "version": "5.1.2", + "bundled": true, + "dev": true }, - "is-glob": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-2.0.1.tgz", - "integrity": "sha1-0Jb5JqPe1WAPP9/ZEZjLCIjC2GM=", - "requires": { - "is-extglob": "^1.0.0" - } + "safer-buffer": { + "version": "2.1.2", + "bundled": true, + "dev": true, + "optional": true }, - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", - "requires": { - "is-buffer": "^1.1.5" - } + "sax": { + "version": "1.2.4", + "bundled": true, + "dev": true, + "optional": true }, - "micromatch": { - "version": "2.3.11", - "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-2.3.11.tgz", - "integrity": "sha1-hmd8l9FyCzY0MdBNDRUpO9OMFWU=", - "requires": { - "arr-diff": "^2.0.0", - "array-unique": "^0.2.1", - "braces": "^1.8.2", - "expand-brackets": "^0.1.4", - "extglob": "^0.3.1", - "filename-regex": "^2.0.0", - "is-extglob": "^1.0.0", - "is-glob": "^2.0.1", - "kind-of": "^3.0.2", - "normalize-path": "^2.0.1", - "object.omit": "^2.0.0", - "parse-glob": "^3.0.4", - "regex-cache": "^0.4.2" - } + "semver": { + "version": "5.6.0", + "bundled": true, + "dev": true, + "optional": true }, - "write-file-atomic": { - "version": "1.3.4", - "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-1.3.4.tgz", - "integrity": "sha1-+Aek8LHZ6ROuekgRLmzDrxmRtF8=", - "requires": { - "graceful-fs": "^4.1.11", - "imurmurhash": "^0.1.4", - "slide": "^1.1.5" - } - } - } - }, - "jsesc": { - "version": "0.5.0", - "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-0.5.0.tgz", - "integrity": "sha1-597mbjXW/Bb3EP6R1c9p9w8IkR0=" - }, - "json-buffer": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/json-buffer/-/json-buffer-3.0.0.tgz", - "integrity": "sha1-Wx85evx11ne96Lz8Dkfh+aPZqJg=" - }, - "json-parse-better-errors": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/json-parse-better-errors/-/json-parse-better-errors-1.0.1.tgz", - "integrity": "sha512-xyQpxeWWMKyJps9CuGJYeng6ssI5bpqS9ltQpdVQ90t4ql6NdnxFKh95JcRt2cun/DjMVNrdjniLPuMA69xmCw==" - }, - "json-schema": { - "version": "0.2.3", - "resolved": "https://registry.npmjs.org/json-schema/-/json-schema-0.2.3.tgz", - "integrity": "sha1-tIDIkuWaLwWVTOcnvT8qTogvnhM=" - }, - "json-schema-traverse": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.3.1.tgz", - "integrity": "sha1-NJptRMU6Ud6JtAgFxdXlm0F9M0A=" - }, - "json-stringify-safe": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/json-stringify-safe/-/json-stringify-safe-5.0.1.tgz", - "integrity": "sha1-Epai1Y/UXxmg9s4B1lcB4sc1tus=" - }, - "json5": { - "version": "0.5.1", - "resolved": "https://registry.npmjs.org/json5/-/json5-0.5.1.tgz", - "integrity": "sha1-Hq3nrMASA0rYTiOWdn6tn6VJWCE=" - }, - "jsonfile": { - "version": "2.4.0", - "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-2.4.0.tgz", - "integrity": "sha1-NzaitCi4e72gzIO1P6PWM6NcKug=", - "requires": { - "graceful-fs": "^4.1.6" - } - }, - "jsprim": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/jsprim/-/jsprim-1.4.1.tgz", - "integrity": "sha1-MT5mvB5cwG5Di8G3SZwuXFastqI=", - "requires": { - "assert-plus": "1.0.0", - "extsprintf": "1.3.0", - "json-schema": "0.2.3", - "verror": "1.10.0" - } - }, - "keccakjs": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/keccakjs/-/keccakjs-0.2.1.tgz", - "integrity": "sha1-HWM6+QfvMFu/ny+mFtVsRFYd+k0=", - "requires": { - "browserify-sha3": "^0.0.1", - "sha3": "^1.1.0" - } - }, - "keyv": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/keyv/-/keyv-3.0.0.tgz", - "integrity": "sha512-eguHnq22OE3uVoSYG0LVWNP+4ppamWr9+zWBe1bsNcovIMy6huUJFPgy4mGwCd/rnl3vOLGW1MTlu4c57CT1xA==", - "requires": { - "json-buffer": "3.0.0" - } - }, - "kind-of": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-6.0.2.tgz", - "integrity": "sha512-s5kLOcnH0XqDO+FvuaLX8DDjZ18CGFk7VygH40QoKPUQhW4e2rvM0rwUq0t8IQDOwYSeLK01U90OjzBTme2QqA==", - "dev": true - }, - "klaw": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/klaw/-/klaw-1.3.1.tgz", - "integrity": "sha1-QIhDO0azsbolnXh4XY6W9zugJDk=", - "requires": { - "graceful-fs": "^4.1.9" - } - }, - "latest-version": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/latest-version/-/latest-version-3.1.0.tgz", - "integrity": "sha1-ogU4P+oyKzO1rjsYq+4NwvNW7hU=", - "dev": true, - "requires": { - "package-json": "^4.0.0" - } - }, - "lazy-cache": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/lazy-cache/-/lazy-cache-1.0.4.tgz", - "integrity": "sha1-odePw6UEdMuAhF07O24dpJpEbo4=", - "dev": true, - "optional": true - }, - "lcid": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/lcid/-/lcid-1.0.0.tgz", - "integrity": "sha1-MIrMr6C8SDo4Z7S28rlQYlHRuDU=", - "requires": { - "invert-kv": "^1.0.0" - } - }, - "levn": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/levn/-/levn-0.3.0.tgz", - "integrity": "sha1-OwmSTt+fCDwEkP3UwLxEIeBHZO4=", - "dev": true, - "requires": { - "prelude-ls": "~1.1.2", - "type-check": "~0.3.2" - } - }, - "listr": { - "version": "0.13.0", - "resolved": "https://registry.npmjs.org/listr/-/listr-0.13.0.tgz", - "integrity": "sha1-ILsLowuuZg7oTMBQPfS+PVYjiH0=", - "requires": { - "chalk": "^1.1.3", - "cli-truncate": "^0.2.1", - "figures": "^1.7.0", - "indent-string": "^2.1.0", - "is-observable": "^0.2.0", - "is-promise": "^2.1.0", - "is-stream": "^1.1.0", - "listr-silent-renderer": "^1.1.1", - "listr-update-renderer": "^0.4.0", - "listr-verbose-renderer": "^0.4.0", - "log-symbols": "^1.0.2", - "log-update": "^1.0.2", - "ora": "^0.2.3", - "p-map": "^1.1.1", - "rxjs": "^5.4.2", - "stream-to-observable": "^0.2.0", - "strip-ansi": "^3.0.1" - }, - "dependencies": { - "ansi-styles": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-2.2.1.tgz", - "integrity": "sha1-tDLdM1i2NM914eRmQ2gkBTPB3b4=" + "set-blocking": { + "version": "2.0.0", + "bundled": true, + "dev": true, + "optional": true }, - "chalk": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz", - "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=", + "signal-exit": { + "version": "3.0.2", + "bundled": true, + "dev": true, + "optional": true + }, + "string-width": { + "version": "1.0.2", + "bundled": true, + "dev": true, "requires": { - "ansi-styles": "^2.2.1", - "escape-string-regexp": "^1.0.2", - "has-ansi": "^2.0.0", - "strip-ansi": "^3.0.0", - "supports-color": "^2.0.0" + "code-point-at": "^1.0.0", + "is-fullwidth-code-point": "^1.0.0", + "strip-ansi": "^3.0.0" } }, - "figures": { - "version": "1.7.0", - "resolved": "https://registry.npmjs.org/figures/-/figures-1.7.0.tgz", - "integrity": "sha1-y+Hjr/zxzUS4DK3+0o3Hk6lwHS4=", + "string_decoder": { + "version": "1.1.1", + "bundled": true, + "dev": true, + "optional": true, "requires": { - "escape-string-regexp": "^1.0.5", - "object-assign": "^4.1.0" + "safe-buffer": "~5.1.0" } }, - "log-symbols": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/log-symbols/-/log-symbols-1.0.2.tgz", - "integrity": "sha1-N2/3tY6jCGoPCfrMdGF+ylAeGhg=", + "strip-ansi": { + "version": "3.0.1", + "bundled": true, + "dev": true, "requires": { - "chalk": "^1.0.0" + "ansi-regex": "^2.0.0" } }, - "supports-color": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz", - "integrity": "sha1-U10EXOa2Nj+kARcIRimZXp3zJMc=" - } - } - }, - "listr-silent-renderer": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/listr-silent-renderer/-/listr-silent-renderer-1.1.1.tgz", - "integrity": "sha1-kktaN1cVN3C/Go4/v3S4u/P5JC4=" - }, - "listr-update-renderer": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/listr-update-renderer/-/listr-update-renderer-0.4.0.tgz", - "integrity": "sha1-NE2YDaLKLosUW6MFkI8yrj9MyKc=", - "requires": { - "chalk": "^1.1.3", - "cli-truncate": "^0.2.1", - "elegant-spinner": "^1.0.1", - "figures": "^1.7.0", - "indent-string": "^3.0.0", - "log-symbols": "^1.0.2", - "log-update": "^1.0.2", - "strip-ansi": "^3.0.1" - }, - "dependencies": { - "ansi-styles": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-2.2.1.tgz", - "integrity": "sha1-tDLdM1i2NM914eRmQ2gkBTPB3b4=" + "strip-json-comments": { + "version": "2.0.1", + "bundled": true, + "dev": true, + "optional": true }, - "chalk": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz", - "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=", + "tar": { + "version": "4.4.8", + "bundled": true, + "dev": true, + "optional": true, "requires": { - "ansi-styles": "^2.2.1", - "escape-string-regexp": "^1.0.2", - "has-ansi": "^2.0.0", - "strip-ansi": "^3.0.0", - "supports-color": "^2.0.0" + "chownr": "^1.1.1", + "fs-minipass": "^1.2.5", + "minipass": "^2.3.4", + "minizlib": "^1.1.1", + "mkdirp": "^0.5.0", + "safe-buffer": "^5.1.2", + "yallist": "^3.0.2" } }, - "figures": { - "version": "1.7.0", - "resolved": "https://registry.npmjs.org/figures/-/figures-1.7.0.tgz", - "integrity": "sha1-y+Hjr/zxzUS4DK3+0o3Hk6lwHS4=", + "util-deprecate": { + "version": "1.0.2", + "bundled": true, + "dev": true, + "optional": true + }, + "wide-align": { + "version": "1.1.3", + "bundled": true, + "dev": true, + "optional": true, "requires": { - "escape-string-regexp": "^1.0.5", - "object-assign": "^4.1.0" + "string-width": "^1.0.2 || 2" } }, - "indent-string": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/indent-string/-/indent-string-3.2.0.tgz", - "integrity": "sha1-Sl/W0nzDMvN+VBmlBNu4NxBckok=" - }, - "log-symbols": { + "wrappy": { "version": "1.0.2", - "resolved": "https://registry.npmjs.org/log-symbols/-/log-symbols-1.0.2.tgz", - "integrity": "sha1-N2/3tY6jCGoPCfrMdGF+ylAeGhg=", - "requires": { - "chalk": "^1.0.0" - } + "bundled": true, + "dev": true }, - "supports-color": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz", - "integrity": "sha1-U10EXOa2Nj+kARcIRimZXp3zJMc=" + "yallist": { + "version": "3.0.3", + "bundled": true, + "dev": true } } }, - "listr-verbose-renderer": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/listr-verbose-renderer/-/listr-verbose-renderer-0.4.1.tgz", - "integrity": "sha1-ggb0z21S3cWCfl/RSYng6WWTOjU=", + "ganache-cli": { + "version": "6.3.0", + "resolved": "https://registry.npmjs.org/ganache-cli/-/ganache-cli-6.3.0.tgz", + "integrity": "sha512-8SyzfX2ipRVBx1fBZLg3j8I3E334U3Vazk5mEpYcWqnIjC2ace6jtOXHG4aTuAvSz3+HzQ8p8pRjOJxdDZ2pnQ==", "requires": { - "chalk": "^1.1.3", - "cli-cursor": "^1.0.2", - "date-fns": "^1.27.2", - "figures": "^1.7.0" + "bn.js": "4.11.8", + "source-map-support": "0.5.9", + "yargs": "11.1.0" }, "dependencies": { - "ansi-styles": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-2.2.1.tgz", - "integrity": "sha1-tDLdM1i2NM914eRmQ2gkBTPB3b4=" + "ansi-regex": { + "version": "3.0.0", + "bundled": true }, - "chalk": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz", - "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=", - "requires": { - "ansi-styles": "^2.2.1", - "escape-string-regexp": "^1.0.2", - "has-ansi": "^2.0.0", - "strip-ansi": "^3.0.0", - "supports-color": "^2.0.0" - } + "bn.js": { + "version": "4.11.8", + "bundled": true }, - "cli-cursor": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-1.0.2.tgz", - "integrity": "sha1-ZNo/fValRBLll5S9Ytw1KV6PKYc=", - "requires": { - "restore-cursor": "^1.0.1" - } + "buffer-from": { + "version": "1.1.1", + "bundled": true + }, + "camelcase": { + "version": "4.1.0", + "bundled": true }, - "figures": { - "version": "1.7.0", - "resolved": "https://registry.npmjs.org/figures/-/figures-1.7.0.tgz", - "integrity": "sha1-y+Hjr/zxzUS4DK3+0o3Hk6lwHS4=", + "cliui": { + "version": "4.1.0", + "bundled": true, "requires": { - "escape-string-regexp": "^1.0.5", - "object-assign": "^4.1.0" + "string-width": "^2.1.1", + "strip-ansi": "^4.0.0", + "wrap-ansi": "^2.0.0" } }, - "onetime": { + "code-point-at": { "version": "1.1.0", - "resolved": "http://registry.npmjs.org/onetime/-/onetime-1.1.0.tgz", - "integrity": "sha1-ofeDj4MUxRbwXs78vEzP4EtO14k=" + "bundled": true }, - "restore-cursor": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-1.0.1.tgz", - "integrity": "sha1-NGYfRohjJ/7SmRR5FSJS35LapUE=", + "cross-spawn": { + "version": "5.1.0", + "bundled": true, "requires": { - "exit-hook": "^1.0.0", - "onetime": "^1.0.0" + "lru-cache": "^4.0.1", + "shebang-command": "^1.2.0", + "which": "^1.2.9" } }, - "supports-color": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz", - "integrity": "sha1-U10EXOa2Nj+kARcIRimZXp3zJMc=" - } - } - }, - "load-json-file": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-1.1.0.tgz", - "integrity": "sha1-lWkFcI1YtLq0wiYbBPWfMcmTdMA=", - "requires": { - "graceful-fs": "^4.1.2", - "parse-json": "^2.2.0", - "pify": "^2.0.0", - "pinkie-promise": "^2.0.0", - "strip-bom": "^2.0.0" - } - }, - "loader-utils": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/loader-utils/-/loader-utils-1.1.0.tgz", - "integrity": "sha1-yYrvSIvM7aL/teLeZG1qdUQp9c0=", - "requires": { - "big.js": "^3.1.3", - "emojis-list": "^2.0.0", - "json5": "^0.5.0" - } - }, - "locate-path": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-2.0.0.tgz", - "integrity": "sha1-K1aLJl7slExtnA3pw9u7ygNUzY4=", - "requires": { - "p-locate": "^2.0.0", - "path-exists": "^3.0.0" - }, - "dependencies": { - "path-exists": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", - "integrity": "sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=" - } - } - }, - "lodash": { - "version": "4.17.5", - "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.5.tgz", - "integrity": "sha512-svL3uiZf1RwhH+cWrfZn3A4+U58wbP0tGVTLQPbjplZxZ8ROD9VLuNgsRniTlLe7OlSqR79RUehXgpBW/s0IQw==" - }, - "lodash.assign": { - "version": "4.2.0", - "resolved": "https://registry.npmjs.org/lodash.assign/-/lodash.assign-4.2.0.tgz", - "integrity": "sha1-DZnzzNem0mHRm9rrkkUAXShYCOc=" - }, - "log-symbols": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/log-symbols/-/log-symbols-2.2.0.tgz", - "integrity": "sha512-VeIAFslyIerEJLXHziedo2basKbMKtTw3vfn5IzG0XTjhAVEJyNHnL2p7vc+wBDSdQuUpNw3M2u6xb9QsAY5Eg==", - "requires": { - "chalk": "^2.0.1" - } - }, - "log-update": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/log-update/-/log-update-1.0.2.tgz", - "integrity": "sha1-GZKfZMQJPS0ucHWh2tivWcKWuNE=", - "requires": { - "ansi-escapes": "^1.0.0", - "cli-cursor": "^1.0.2" - }, - "dependencies": { - "ansi-escapes": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-1.4.0.tgz", - "integrity": "sha1-06ioOzGapneTZisT52HHkRQiMG4=" + "decamelize": { + "version": "1.2.0", + "bundled": true }, - "cli-cursor": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-1.0.2.tgz", - "integrity": "sha1-ZNo/fValRBLll5S9Ytw1KV6PKYc=", + "execa": { + "version": "0.7.0", + "bundled": true, "requires": { - "restore-cursor": "^1.0.1" + "cross-spawn": "^5.0.1", + "get-stream": "^3.0.0", + "is-stream": "^1.1.0", + "npm-run-path": "^2.0.0", + "p-finally": "^1.0.0", + "signal-exit": "^3.0.0", + "strip-eof": "^1.0.0" } }, - "onetime": { - "version": "1.1.0", - "resolved": "http://registry.npmjs.org/onetime/-/onetime-1.1.0.tgz", - "integrity": "sha1-ofeDj4MUxRbwXs78vEzP4EtO14k=" - }, - "restore-cursor": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-1.0.1.tgz", - "integrity": "sha1-NGYfRohjJ/7SmRR5FSJS35LapUE=", + "find-up": { + "version": "2.1.0", + "bundled": true, "requires": { - "exit-hook": "^1.0.0", - "onetime": "^1.0.0" + "locate-path": "^2.0.0" } - } - } - }, - "longest": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/longest/-/longest-1.0.1.tgz", - "integrity": "sha1-MKCy2jj3N3DoKUoNIuZiXtd9AJc=", - "dev": true - }, - "loose-envify": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/loose-envify/-/loose-envify-1.3.1.tgz", - "integrity": "sha1-0aitM/qc4OcT1l/dCsi3SNR4yEg=", - "requires": { - "js-tokens": "^3.0.0" - } - }, - "lowercase-keys": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/lowercase-keys/-/lowercase-keys-1.0.0.tgz", - "integrity": "sha1-TjNms55/VFfjXxMkvfb4jQv8cwY=" - }, - "lru-cache": { - "version": "2.7.3", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-2.7.3.tgz", - "integrity": "sha1-bUUk6LlV+V1PW1iFHOId1y+06VI=", - "dev": true - }, - "make-dir": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-1.2.0.tgz", - "integrity": "sha512-aNUAa4UMg/UougV25bbrU4ZaaKNjJ/3/xnvg/twpmKROPdKZPZ9wGgI0opdZzO8q/zUFawoUuixuOv33eZ61Iw==", - "requires": { - "pify": "^3.0.0" - }, - "dependencies": { - "pify": { + }, + "get-caller-file": { + "version": "1.0.3", + "bundled": true + }, + "get-stream": { "version": "3.0.0", - "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", - "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=" - } - } - }, - "map-cache": { - "version": "0.2.2", - "resolved": "https://registry.npmjs.org/map-cache/-/map-cache-0.2.2.tgz", - "integrity": "sha1-wyq9C9ZSXZsFFkW7TyasXcmKDb8=", - "dev": true - }, - "map-stream": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/map-stream/-/map-stream-0.1.0.tgz", - "integrity": "sha1-5WqpTEyAVaFkBKBnS3jyFffI4ZQ=", - "dev": true - }, - "map-visit": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/map-visit/-/map-visit-1.0.0.tgz", - "integrity": "sha1-7Nyo8TFE5mDxtb1B8S80edmN+48=", - "dev": true, - "requires": { - "object-visit": "^1.0.0" - } - }, - "media-typer": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/media-typer/-/media-typer-0.3.0.tgz", - "integrity": "sha1-hxDXrwqmJvj/+hzgAWhUUmMlV0g=" - }, - "mem": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/mem/-/mem-1.1.0.tgz", - "integrity": "sha1-Xt1StIXKHZAP5kiVUFOZoN+kX3Y=", - "requires": { - "mimic-fn": "^1.0.0" - } - }, - "mem-fs": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/mem-fs/-/mem-fs-1.1.3.tgz", - "integrity": "sha1-uK6NLj/Lb10/kWXBLUVRoGXZicw=", - "requires": { - "through2": "^2.0.0", - "vinyl": "^1.1.0", - "vinyl-file": "^2.0.0" - } - }, - "mem-fs-editor": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/mem-fs-editor/-/mem-fs-editor-3.0.2.tgz", - "integrity": "sha1-3Qpuryu4prN3QAZ6pUnrUwEFr58=", - "requires": { - "commondir": "^1.0.1", - "deep-extend": "^0.4.0", - "ejs": "^2.3.1", - "glob": "^7.0.3", - "globby": "^6.1.0", - "mkdirp": "^0.5.0", - "multimatch": "^2.0.0", - "rimraf": "^2.2.8", - "through2": "^2.0.0", - "vinyl": "^2.0.1" - }, - "dependencies": { - "clone": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/clone/-/clone-2.1.2.tgz", - "integrity": "sha1-G39Ln1kfHo+DZwQBYANFoCiHQ18=" + "bundled": true }, - "clone-stats": { + "invert-kv": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/clone-stats/-/clone-stats-1.0.0.tgz", - "integrity": "sha1-s3gt/4u1R04Yuba/D9/ngvh3doA=" + "bundled": true + }, + "is-fullwidth-code-point": { + "version": "2.0.0", + "bundled": true }, - "replace-ext": { + "is-stream": { + "version": "1.1.0", + "bundled": true + }, + "isexe": { + "version": "2.0.0", + "bundled": true + }, + "lcid": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/replace-ext/-/replace-ext-1.0.0.tgz", - "integrity": "sha1-3mMSg3P8v3w8z6TeWkgMRaZ5WOs=" + "bundled": true, + "requires": { + "invert-kv": "^1.0.0" + } }, - "vinyl": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-2.1.0.tgz", - "integrity": "sha1-Ah+cLPlR1rk5lDyJ617lrdT9kkw=", + "locate-path": { + "version": "2.0.0", + "bundled": true, "requires": { - "clone": "^2.1.1", - "clone-buffer": "^1.0.0", - "clone-stats": "^1.0.0", - "cloneable-readable": "^1.0.0", - "remove-trailing-separator": "^1.0.1", - "replace-ext": "^1.0.0" + "p-locate": "^2.0.0", + "path-exists": "^3.0.0" } - } - } - }, - "memory-fs": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/memory-fs/-/memory-fs-0.4.1.tgz", - "integrity": "sha1-OpoguEYlI+RHz7x+i7gO1me/xVI=", - "requires": { - "errno": "^0.1.3", - "readable-stream": "^2.0.1" - } - }, - "memorystream": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/memorystream/-/memorystream-0.3.1.tgz", - "integrity": "sha1-htcJCzDORV1j+64S3aUaR93K+bI=" - }, - "merge-descriptors": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/merge-descriptors/-/merge-descriptors-1.0.1.tgz", - "integrity": "sha1-sAqqVW3YtEVoFQ7J0blT8/kMu2E=" - }, - "methods": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/methods/-/methods-1.1.2.tgz", - "integrity": "sha1-VSmk1nZUE07cxSZmVoNbD4Ua/O4=" - }, - "micromatch": { - "version": "3.1.10", - "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-3.1.10.tgz", - "integrity": "sha512-MWikgl9n9M3w+bpsY3He8L+w9eF9338xRl8IAO5viDizwSzziFEyUzo2xrrloB64ADbTf8uA8vRqqttDTOmccg==", - "dev": true, - "requires": { - "arr-diff": "^4.0.0", - "array-unique": "^0.3.2", - "braces": "^2.3.1", - "define-property": "^2.0.2", - "extend-shallow": "^3.0.2", - "extglob": "^2.0.4", - "fragment-cache": "^0.2.1", - "kind-of": "^6.0.2", - "nanomatch": "^1.2.9", - "object.pick": "^1.3.0", - "regex-not": "^1.0.0", - "snapdragon": "^0.8.1", - "to-regex": "^3.0.2" - } - }, - "mime": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/mime/-/mime-1.4.1.tgz", - "integrity": "sha512-KI1+qOZu5DcW6wayYHSzR/tXKCDC5Om4s1z2QJjDULzLcmf3DvzS7oluY4HCTrc+9FiKmWUgeNLg7W3uIQvxtQ==" - }, - "mime-db": { - "version": "1.33.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.33.0.tgz", - "integrity": "sha512-BHJ/EKruNIqJf/QahvxwQZXKygOQ256myeN/Ew+THcAa5q+PjyTTMMeNQC4DZw5AwfvelsUrA6B67NKMqXDbzQ==" - }, - "mime-types": { - "version": "2.1.18", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.18.tgz", - "integrity": "sha512-lc/aahn+t4/SWV/qcmumYjymLsWfN3ELhpmVuUFjgsORruuZPVSwAQryq+HHGvO/SI2KVX26bx+En+zhM8g8hQ==", - "requires": { - "mime-db": "~1.33.0" - } - }, - "mimic-fn": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-1.2.0.tgz", - "integrity": "sha512-jf84uxzwiuiIVKiOLpfYk7N46TSy8ubTonmneY9vrpHNAnp0QBt2BxWV9dO3/j+BoVAb+a5G6YDPW3M5HOdMWQ==" - }, - "mimic-response": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-1.0.0.tgz", - "integrity": "sha1-3z02Uqc/3ta5sLJBRub9BSNTRY4=" - }, - "min-document": { - "version": "2.19.0", - "resolved": "https://registry.npmjs.org/min-document/-/min-document-2.19.0.tgz", - "integrity": "sha1-e9KC4/WELtKVu3SM3Z8f+iyCRoU=", - "requires": { - "dom-walk": "^0.1.0" - } - }, - "minimalistic-assert": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/minimalistic-assert/-/minimalistic-assert-1.0.1.tgz", - "integrity": "sha512-UtJcAD4yEaGtjPezWuO9wC4nwUnVH/8/Im3yEHQP4b67cXlD/Qr9hdITCU1xDbSEXg2XKNaP8jsReV7vQd00/A==" - }, - "minimalistic-crypto-utils": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/minimalistic-crypto-utils/-/minimalistic-crypto-utils-1.0.1.tgz", - "integrity": "sha1-9sAMHAsIIkblxNmd+4x8CDsrWCo=" - }, - "minimatch": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", - "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", - "requires": { - "brace-expansion": "^1.1.7" - } - }, - "minimist": { - "version": "0.0.8", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-0.0.8.tgz", - "integrity": "sha1-hX/Kv8M5fSYluCKCYuhqp6ARsF0=" - }, - "mixin-deep": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/mixin-deep/-/mixin-deep-1.3.1.tgz", - "integrity": "sha512-8ZItLHeEgaqEvd5lYBXfm4EZSFCX29Jb9K+lAHhDKzReKBQKj3R+7NOF6tjqYi9t4oI8VUfaWITJQm86wnXGNQ==", - "dev": true, - "requires": { - "for-in": "^1.0.2", - "is-extendable": "^1.0.1" - }, - "dependencies": { - "is-extendable": { + }, + "lru-cache": { + "version": "4.1.4", + "bundled": true, + "requires": { + "pseudomap": "^1.0.2", + "yallist": "^3.0.2" + } + }, + "mem": { + "version": "1.1.0", + "bundled": true, + "requires": { + "mimic-fn": "^1.0.0" + } + }, + "mimic-fn": { + "version": "1.2.0", + "bundled": true + }, + "npm-run-path": { + "version": "2.0.2", + "bundled": true, + "requires": { + "path-key": "^2.0.0" + } + }, + "number-is-nan": { "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-1.0.1.tgz", - "integrity": "sha512-arnXMxT1hhoKo9k1LZdmlNyJdDDfy2v0fXjFlmok4+i8ul/6WlbVge9bhM74OpNPQPMGUToDtz+KXa1PneJxOA==", - "dev": true, + "bundled": true + }, + "os-locale": { + "version": "2.1.0", + "bundled": true, "requires": { - "is-plain-object": "^2.0.4" + "execa": "^0.7.0", + "lcid": "^1.0.0", + "mem": "^1.1.0" } - } - } - }, - "mkdirp": { - "version": "0.5.1", - "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.1.tgz", - "integrity": "sha1-MAV0OOrGz3+MR2fzhkjWaX11yQM=", - "requires": { - "minimist": "0.0.8" - } - }, - "mocha": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/mocha/-/mocha-4.1.0.tgz", - "integrity": "sha512-0RVnjg1HJsXY2YFDoTNzcc1NKhYuXKRrBAG2gDygmJJA136Cs2QlRliZG1mA0ap7cuaT30mw16luAeln+4RiNA==", - "requires": { - "browser-stdout": "1.3.0", - "commander": "2.11.0", - "debug": "3.1.0", - "diff": "3.3.1", - "escape-string-regexp": "1.0.5", - "glob": "7.1.2", - "growl": "1.10.3", - "he": "1.1.1", - "mkdirp": "0.5.1", - "supports-color": "4.4.0" - }, - "dependencies": { - "debug": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", - "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", + }, + "p-finally": { + "version": "1.0.0", + "bundled": true + }, + "p-limit": { + "version": "1.3.0", + "bundled": true, "requires": { - "ms": "2.0.0" + "p-try": "^1.0.0" } }, - "glob": { - "version": "7.1.2", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz", - "integrity": "sha512-MJTUg1kjuLeQCJ+ccE4Vpa6kKVXkPYJ2mOCQyUuKLcLQsdrMCpBPUi8qVE6+YuaJkozeA9NusTAw3hLr8Xe5EQ==", + "p-locate": { + "version": "2.0.0", + "bundled": true, "requires": { - "fs.realpath": "^1.0.0", - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "^3.0.4", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" + "p-limit": "^1.1.0" } }, - "growl": { - "version": "1.10.3", - "resolved": "https://registry.npmjs.org/growl/-/growl-1.10.3.tgz", - "integrity": "sha512-hKlsbA5Vu3xsh1Cg3J7jSmX/WaW6A5oBeqzM88oNbCRQFz+zUaXm6yxS4RVytp1scBoJzSYl4YAEOQIt6O8V1Q==" + "p-try": { + "version": "1.0.0", + "bundled": true }, - "has-flag": { + "path-exists": { + "version": "3.0.0", + "bundled": true + }, + "path-key": { + "version": "2.0.1", + "bundled": true + }, + "pseudomap": { + "version": "1.0.2", + "bundled": true + }, + "require-directory": { + "version": "2.1.1", + "bundled": true + }, + "require-main-filename": { + "version": "1.0.1", + "bundled": true + }, + "set-blocking": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-2.0.0.tgz", - "integrity": "sha1-6CB68cx7MNRGzHC3NLXovhj4jVE=" + "bundled": true }, - "supports-color": { - "version": "4.4.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-4.4.0.tgz", - "integrity": "sha512-rKC3+DyXWgK0ZLKwmRsrkyHVZAjNkfzeehuFWdGGcqGDTZFH73+RH6S/RDAAxl9GusSjZSUWYLmT9N5pzXFOXQ==", + "shebang-command": { + "version": "1.2.0", + "bundled": true, "requires": { - "has-flag": "^2.0.0" + "shebang-regex": "^1.0.0" } - } - } - }, - "ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" - }, - "multimatch": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/multimatch/-/multimatch-2.1.0.tgz", - "integrity": "sha1-nHkGoi+0wCkZ4vX3UWG0zb1LKis=", - "requires": { - "array-differ": "^1.0.0", - "array-union": "^1.0.1", - "arrify": "^1.0.0", - "minimatch": "^3.0.0" - } - }, - "mute-stream": { - "version": "0.0.7", - "resolved": "https://registry.npmjs.org/mute-stream/-/mute-stream-0.0.7.tgz", - "integrity": "sha1-MHXOk7whuPq0PhvE2n6BFe0ee6s=" - }, - "nan": { - "version": "2.10.0", - "resolved": "https://registry.npmjs.org/nan/-/nan-2.10.0.tgz", - "integrity": "sha512-bAdJv7fBLhWC+/Bls0Oza+mvTaNQtP+1RyhhhvD95pgUJz6XM5IzgmxOkItJ9tkoCiplvAnXI1tNmmUD/eScyA==" - }, - "nano-json-stream-parser": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/nano-json-stream-parser/-/nano-json-stream-parser-0.1.2.tgz", - "integrity": "sha1-DMj20OK2IrR5xA1JnEbWS3Vcb18=" - }, - "nanomatch": { - "version": "1.2.9", - "resolved": "https://registry.npmjs.org/nanomatch/-/nanomatch-1.2.9.tgz", - "integrity": "sha512-n8R9bS8yQ6eSXaV6jHUpKzD8gLsin02w1HSFiegwrs9E098Ylhw5jdyKPaYqvHknHaSCKTPp7C8dGCQ0q9koXA==", - "dev": true, - "requires": { - "arr-diff": "^4.0.0", - "array-unique": "^0.3.2", - "define-property": "^2.0.2", - "extend-shallow": "^3.0.2", - "fragment-cache": "^0.2.1", - "is-odd": "^2.0.0", - "is-windows": "^1.0.2", - "kind-of": "^6.0.2", - "object.pick": "^1.3.0", - "regex-not": "^1.0.0", - "snapdragon": "^0.8.1", - "to-regex": "^3.0.1" - } - }, - "negotiator": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-0.6.1.tgz", - "integrity": "sha1-KzJxhOiZIQEXeyhWP7XnECrNDKk=" - }, - "neo-async": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/neo-async/-/neo-async-2.5.0.tgz", - "integrity": "sha512-nJmSswG4As/MkRq7QZFuH/sf/yuv8ODdMZrY4Bedjp77a5MK4A6s7YbBB64c9u79EBUOfXUXBvArmvzTD0X+6g==" - }, - "nice-try": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/nice-try/-/nice-try-1.0.4.tgz", - "integrity": "sha512-2NpiFHqC87y/zFke0fC0spBXL3bBsoh/p5H1EFhshxjCR5+0g2d6BiXbUFz9v1sAcxsk2htp2eQnNIci2dIYcA==" - }, - "node-dir": { - "version": "0.1.8", - "resolved": "https://registry.npmjs.org/node-dir/-/node-dir-0.1.8.tgz", - "integrity": "sha1-VfuN62mQcHB/tn+RpGDwRIKUx30=" - }, - "nodemon": { - "version": "1.17.3", - "resolved": "https://registry.npmjs.org/nodemon/-/nodemon-1.17.3.tgz", - "integrity": "sha512-8AtS+wA5u6qoE12LONjqOzUzxAI5ObzSw6U5LgqpaO/0y6wwId4l5dN0ZulYyYdpLZD1MbkBp7GjG1hqaoRqYg==", - "dev": true, - "requires": { - "chokidar": "^2.0.2", - "debug": "^3.1.0", - "ignore-by-default": "^1.0.1", - "minimatch": "^3.0.4", - "pstree.remy": "^1.1.0", - "semver": "^5.5.0", - "supports-color": "^5.2.0", - "touch": "^3.1.0", - "undefsafe": "^2.0.2", - "update-notifier": "^2.3.0" - }, - "dependencies": { - "debug": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", - "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", - "dev": true, + }, + "shebang-regex": { + "version": "1.0.0", + "bundled": true + }, + "signal-exit": { + "version": "3.0.2", + "bundled": true + }, + "source-map": { + "version": "0.6.1", + "bundled": true + }, + "source-map-support": { + "version": "0.5.9", + "bundled": true, "requires": { - "ms": "2.0.0" + "buffer-from": "^1.0.0", + "source-map": "^0.6.0" } }, - "has-flag": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", - "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=", - "dev": true + "string-width": { + "version": "2.1.1", + "bundled": true, + "requires": { + "is-fullwidth-code-point": "^2.0.0", + "strip-ansi": "^4.0.0" + } }, - "supports-color": { - "version": "5.4.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.4.0.tgz", - "integrity": "sha512-zjaXglF5nnWpsq470jSv6P9DwPvgLkuapYmfDm3JWOm0vkNTVF2tI4UrN2r6jH1qM/uc/WtxYY1hYoA2dOKj5w==", - "dev": true, + "strip-ansi": { + "version": "4.0.0", + "bundled": true, "requires": { - "has-flag": "^3.0.0" + "ansi-regex": "^3.0.0" } - } - } - }, - "nomnom": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/nomnom/-/nomnom-1.8.1.tgz", - "integrity": "sha1-IVH3Ikcrp55Qp2/BJbuMjy5Nwqc=", - "requires": { - "chalk": "~0.4.0", - "underscore": "~1.6.0" - }, - "dependencies": { - "ansi-styles": { + }, + "strip-eof": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-1.0.0.tgz", - "integrity": "sha1-yxAt8cVvUSPquLZ817mAJ6AnkXg=" + "bundled": true }, - "chalk": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-0.4.0.tgz", - "integrity": "sha1-UZmj3c0MHv4jvAjBsCewYXbgxk8=", + "which": { + "version": "1.3.1", + "bundled": true, "requires": { - "ansi-styles": "~1.0.0", - "has-color": "~0.1.0", - "strip-ansi": "~0.1.0" + "isexe": "^2.0.0" } }, - "strip-ansi": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-0.1.1.tgz", - "integrity": "sha1-OeipjQRNFQZgq+SmgIrPcLt7yZE=" + "which-module": { + "version": "2.0.0", + "bundled": true + }, + "wrap-ansi": { + "version": "2.1.0", + "bundled": true, + "requires": { + "string-width": "^1.0.1", + "strip-ansi": "^3.0.1" + }, + "dependencies": { + "ansi-regex": { + "version": "2.1.1", + "bundled": true + }, + "is-fullwidth-code-point": { + "version": "1.0.0", + "bundled": true, + "requires": { + "number-is-nan": "^1.0.0" + } + }, + "string-width": { + "version": "1.0.2", + "bundled": true, + "requires": { + "code-point-at": "^1.0.0", + "is-fullwidth-code-point": "^1.0.0", + "strip-ansi": "^3.0.0" + } + }, + "strip-ansi": { + "version": "3.0.1", + "bundled": true, + "requires": { + "ansi-regex": "^2.0.0" + } + } + } + }, + "y18n": { + "version": "3.2.1", + "bundled": true + }, + "yallist": { + "version": "3.0.2", + "bundled": true + }, + "yargs": { + "version": "11.1.0", + "bundled": true, + "requires": { + "cliui": "^4.0.0", + "decamelize": "^1.1.1", + "find-up": "^2.1.0", + "get-caller-file": "^1.0.1", + "os-locale": "^2.0.0", + "require-directory": "^2.1.1", + "require-main-filename": "^1.0.1", + "set-blocking": "^2.0.0", + "string-width": "^2.0.0", + "which-module": "^2.0.0", + "y18n": "^3.2.1", + "yargs-parser": "^9.0.2" + } + }, + "yargs-parser": { + "version": "9.0.2", + "bundled": true, + "requires": { + "camelcase": "^4.1.0" + } } } }, - "nopt": { - "version": "1.0.10", - "resolved": "https://registry.npmjs.org/nopt/-/nopt-1.0.10.tgz", - "integrity": "sha1-bd0hvSoxQXuScn3Vhfim83YI6+4=", - "dev": true, - "requires": { - "abbrev": "1" - } + "get-caller-file": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/get-caller-file/-/get-caller-file-1.0.3.tgz", + "integrity": "sha512-3t6rVToeoZfYSGd8YoLFR2DJkiQrIiUrGcjvFX2mDw3bn6k2OtwHN0TNCLbBO+w8qTvimhDkv+LSscbJY1vE6w==" }, - "normalize-package-data": { - "version": "2.4.0", - "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-2.4.0.tgz", - "integrity": "sha512-9jjUFbTPfEy3R/ad/2oNbKtW9Hgovl5O1FvFWKkKblNXoN/Oou6+9+KKohPK13Yc3/TyunyWhJp6gvRNR/PPAw==", - "requires": { - "hosted-git-info": "^2.1.4", - "is-builtin-module": "^1.0.0", - "semver": "2 || 3 || 4 || 5", - "validate-npm-package-license": "^3.0.1" - } + "get-func-name": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/get-func-name/-/get-func-name-2.0.0.tgz", + "integrity": "sha1-6td0q+5y4gQJQzoGY2YCPdaIekE=", + "dev": true + }, + "get-port": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/get-port/-/get-port-3.2.0.tgz", + "integrity": "sha1-3Xzn3hh8Bsi/NTeWrHHgmfCYDrw=", + "dev": true }, - "normalize-path": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-2.1.1.tgz", - "integrity": "sha1-GrKLVW4Zg2Oowab35vogE3/mrtk=", - "requires": { - "remove-trailing-separator": "^1.0.1" - } + "get-stream": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-3.0.0.tgz", + "integrity": "sha1-jpQ9E1jcN1VQVOy+LtsFqhdO3hQ=", + "dev": true }, - "normalize-url": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/normalize-url/-/normalize-url-2.0.1.tgz", - "integrity": "sha512-D6MUW4K/VzoJ4rJ01JFKxDrtY1v9wrgzCX5f2qj/lzH1m/lW6MhUZFKerVsnyjOhOsYzI9Kqqak+10l4LvLpMw==", - "requires": { - "prepend-http": "^2.0.0", - "query-string": "^5.0.1", - "sort-keys": "^2.0.0" - }, - "dependencies": { - "prepend-http": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/prepend-http/-/prepend-http-2.0.0.tgz", - "integrity": "sha1-6SQ0v6XqjBn0HN/UAddBo8gZ2Jc=" - } - } + "get-value": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/get-value/-/get-value-2.0.6.tgz", + "integrity": "sha1-3BXKHGcjh8p2vTesCjlbogQqLCg=", + "dev": true }, - "npm-run-path": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/npm-run-path/-/npm-run-path-2.0.2.tgz", - "integrity": "sha1-NakjLfo11wZ7TLLd8jV7GHFTbF8=", + "getpass": { + "version": "0.1.7", + "resolved": "https://registry.npmjs.org/getpass/-/getpass-0.1.7.tgz", + "integrity": "sha1-Xv+OPmhNVprkyysSgmBOi6YhSfo=", + "dev": true, "requires": { - "path-key": "^2.0.0" + "assert-plus": "^1.0.0" } }, - "number-is-nan": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/number-is-nan/-/number-is-nan-1.0.1.tgz", - "integrity": "sha1-CXtgK1NCKlIsGvuHkDGDNpQaAR0=" - }, - "number-to-bn": { - "version": "1.7.0", - "resolved": "https://registry.npmjs.org/number-to-bn/-/number-to-bn-1.7.0.tgz", - "integrity": "sha1-uzYjWS9+X54AMLGXe9QaDFP+HqA=", + "glob": { + "version": "7.1.2", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz", + "integrity": "sha512-MJTUg1kjuLeQCJ+ccE4Vpa6kKVXkPYJ2mOCQyUuKLcLQsdrMCpBPUi8qVE6+YuaJkozeA9NusTAw3hLr8Xe5EQ==", "requires": { - "bn.js": "4.11.6", - "strip-hex-prefix": "1.0.0" + "fs.realpath": "^1.0.0", + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "^3.0.4", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" } }, - "oauth-sign": { - "version": "0.8.2", - "resolved": "https://registry.npmjs.org/oauth-sign/-/oauth-sign-0.8.2.tgz", - "integrity": "sha1-Rqarfwrq2N6unsBWV4C31O/rnUM=" - }, - "object-assign": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", - "integrity": "sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM=" - }, - "object-copy": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/object-copy/-/object-copy-0.1.0.tgz", - "integrity": "sha1-fn2Fi3gb18mRpBupde04EnVOmYw=", + "glob-parent": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-3.1.0.tgz", + "integrity": "sha1-nmr2KZ2NO9K9QEMIMr0RPfkGxa4=", "dev": true, "requires": { - "copy-descriptor": "^0.1.0", - "define-property": "^0.2.5", - "kind-of": "^3.0.3" + "is-glob": "^3.1.0", + "path-dirname": "^1.0.0" }, "dependencies": { - "define-property": { - "version": "0.2.5", - "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", - "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", - "dev": true, - "requires": { - "is-descriptor": "^0.1.0" - } - }, - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "is-glob": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-3.1.0.tgz", + "integrity": "sha1-e6WuJCF4BKxwcHuWkiVnSGzD6Eo=", "dev": true, "requires": { - "is-buffer": "^1.1.5" + "is-extglob": "^2.1.0" } } } }, - "object-visit": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/object-visit/-/object-visit-1.0.1.tgz", - "integrity": "sha1-95xEk68MU3e1n+OdOV5BBC3QRbs=", - "dev": true, - "requires": { - "isobject": "^3.0.0" - } - }, - "object.omit": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/object.omit/-/object.omit-2.0.1.tgz", - "integrity": "sha1-Gpx0SCnznbuFjHbKNXmuKlTr0fo=", + "global": { + "version": "4.3.2", + "resolved": "https://registry.npmjs.org/global/-/global-4.3.2.tgz", + "integrity": "sha1-52mJJopsdMOJCLEwWxD8DjlOnQ8=", "requires": { - "for-own": "^0.1.4", - "is-extendable": "^0.1.1" + "min-document": "^2.19.0", + "process": "~0.5.1" } }, - "object.pick": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/object.pick/-/object.pick-1.3.0.tgz", - "integrity": "sha1-h6EKxMFpS9Lhy/U1kaZhQftd10c=", + "global-dirs": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/global-dirs/-/global-dirs-0.1.1.tgz", + "integrity": "sha1-sxnA3UYH81PzvpzKTHL8FIxJ9EU=", "dev": true, "requires": { - "isobject": "^3.0.1" - } - }, - "on-finished": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/on-finished/-/on-finished-2.3.0.tgz", - "integrity": "sha1-IPEzZIGwg811M3mSoWlxqi2QaUc=", - "requires": { - "ee-first": "1.1.1" - } - }, - "once": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", - "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", - "requires": { - "wrappy": "1" + "ini": "^1.3.4" } }, - "onetime": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/onetime/-/onetime-2.0.1.tgz", - "integrity": "sha1-BnQoIw/WdEOyeUsiu6UotoZ5YtQ=", + "got": { + "version": "6.7.1", + "resolved": "https://registry.npmjs.org/got/-/got-6.7.1.tgz", + "integrity": "sha1-JAzQV4WpoY5WHcG0S0HHY+8ejbA=", + "dev": true, "requires": { - "mimic-fn": "^1.0.0" + "create-error-class": "^3.0.0", + "duplexer3": "^0.1.4", + "get-stream": "^3.0.0", + "is-redirect": "^1.0.0", + "is-retry-allowed": "^1.0.0", + "is-stream": "^1.0.0", + "lowercase-keys": "^1.0.0", + "safe-buffer": "^5.0.1", + "timed-out": "^4.0.0", + "unzip-response": "^2.0.1", + "url-parse-lax": "^1.0.0" } }, - "openzeppelin-solidity": { - "version": "1.10.0", - "resolved": "https://registry.npmjs.org/openzeppelin-solidity/-/openzeppelin-solidity-1.10.0.tgz", - "integrity": "sha512-igkrumQQ2lrN2zjeQV4Dnb0GpTBj1fzMcd8HPyBUqwI0hhuscX/HzXiqKT6gFQl1j9Wy/ppVVs9fqL/foF7Gmg==" + "graceful-fs": { + "version": "4.1.15", + "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.15.tgz", + "integrity": "sha512-6uHUhOPEBgQ24HM+r6b/QwWfZq+yiFcipKFrOFiBEnWdy5sdzYoi+pJeQaPI5qOLRFqWmAXUPQNsielzdLoecA==" }, - "optimist": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/optimist/-/optimist-0.6.1.tgz", - "integrity": "sha1-2j6nRob6IaGaERwybpDrFaAZZoY=", - "dev": true, - "requires": { - "minimist": "~0.0.1", - "wordwrap": "~0.0.2" - }, - "dependencies": { - "wordwrap": { - "version": "0.0.3", - "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-0.0.3.tgz", - "integrity": "sha1-o9XabNXAvAAI03I0u68b7WMFkQc=", - "dev": true - } - } + "growl": { + "version": "1.10.3", + "resolved": "https://registry.npmjs.org/growl/-/growl-1.10.3.tgz", + "integrity": "sha512-hKlsbA5Vu3xsh1Cg3J7jSmX/WaW6A5oBeqzM88oNbCRQFz+zUaXm6yxS4RVytp1scBoJzSYl4YAEOQIt6O8V1Q==" }, - "optionator": { - "version": "0.8.2", - "resolved": "https://registry.npmjs.org/optionator/-/optionator-0.8.2.tgz", - "integrity": "sha1-NkxeQJ0/TWMB1sC0wFu6UBgK62Q=", + "handlebars": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.1.0.tgz", + "integrity": "sha512-l2jRuU1NAWK6AW5qqcTATWQJvNPEwkM7NEKSiv/gqOsoSQbVoWyqVEY5GS+XPQ88zLNmqASRpzfdm8d79hJS+w==", "dev": true, "requires": { - "deep-is": "~0.1.3", - "fast-levenshtein": "~2.0.4", - "levn": "~0.3.0", - "prelude-ls": "~1.1.2", - "type-check": "~0.3.2", - "wordwrap": "~1.0.0" - } - }, - "ora": { - "version": "0.2.3", - "resolved": "https://registry.npmjs.org/ora/-/ora-0.2.3.tgz", - "integrity": "sha1-N1J9Igrc1Tw5tzVx11QVbV22V6Q=", - "requires": { - "chalk": "^1.1.1", - "cli-cursor": "^1.0.2", - "cli-spinners": "^0.1.2", - "object-assign": "^4.0.1" + "async": "^2.5.0", + "optimist": "^0.6.1", + "source-map": "^0.6.1", + "uglify-js": "^3.1.4" }, "dependencies": { - "ansi-styles": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-2.2.1.tgz", - "integrity": "sha1-tDLdM1i2NM914eRmQ2gkBTPB3b4=" - }, - "chalk": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz", - "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=", - "requires": { - "ansi-styles": "^2.2.1", - "escape-string-regexp": "^1.0.2", - "has-ansi": "^2.0.0", - "strip-ansi": "^3.0.0", - "supports-color": "^2.0.0" - } - }, - "cli-cursor": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-1.0.2.tgz", - "integrity": "sha1-ZNo/fValRBLll5S9Ytw1KV6PKYc=", - "requires": { - "restore-cursor": "^1.0.1" - } - }, - "onetime": { - "version": "1.1.0", - "resolved": "http://registry.npmjs.org/onetime/-/onetime-1.1.0.tgz", - "integrity": "sha1-ofeDj4MUxRbwXs78vEzP4EtO14k=" - }, - "restore-cursor": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-1.0.1.tgz", - "integrity": "sha1-NGYfRohjJ/7SmRR5FSJS35LapUE=", + "async": { + "version": "2.6.2", + "resolved": "https://registry.npmjs.org/async/-/async-2.6.2.tgz", + "integrity": "sha512-H1qVYh1MYhEEFLsP97cVKqCGo7KfCyTt6uEWqsTBr9SO84oK9Uwbyd/yCW+6rKJLHksBNUVWZDAjfS+Ccx0Bbg==", + "dev": true, "requires": { - "exit-hook": "^1.0.0", - "onetime": "^1.0.0" + "lodash": "^4.17.11" } }, - "supports-color": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz", - "integrity": "sha1-U10EXOa2Nj+kARcIRimZXp3zJMc=" + "source-map": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", + "dev": true } } }, - "original-require": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/original-require/-/original-require-1.0.1.tgz", - "integrity": "sha1-DxMEcVhM0zURxew4yNWSE/msXiA=" - }, - "os-homedir": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/os-homedir/-/os-homedir-1.0.2.tgz", - "integrity": "sha1-/7xJiDNuDoM94MFox+8VISGqf7M=" - }, - "os-locale": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/os-locale/-/os-locale-1.4.0.tgz", - "integrity": "sha1-IPnxeuKe00XoveWDsT0gCYA8FNk=", - "requires": { - "lcid": "^1.0.0" - } - }, - "os-tmpdir": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/os-tmpdir/-/os-tmpdir-1.0.2.tgz", - "integrity": "sha1-u+Z0BseaqFxc/sdm/lc0VV36EnQ=" - }, - "p-cancelable": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/p-cancelable/-/p-cancelable-0.4.0.tgz", - "integrity": "sha512-/AodqPe1y/GYbhSlnMjxukLGQfQIgsmjSy2CXCNB96kg4ozKvmlovuHEKICToOO/yS3LLWgrWI1dFtFfrePS1g==" + "har-schema": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/har-schema/-/har-schema-2.0.0.tgz", + "integrity": "sha1-qUwiJOvKwEeCoNkDVSHyRzW37JI=", + "dev": true }, - "p-each-series": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/p-each-series/-/p-each-series-1.0.0.tgz", - "integrity": "sha1-kw89Et0fUOdDRFeiLNbwSsatf3E=", + "har-validator": { + "version": "5.1.3", + "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-5.1.3.tgz", + "integrity": "sha512-sNvOCzEQNr/qrvJgc3UG/kD4QtlHycrzwS+6mfTrrSq97BvaYcPZZI1ZSqGSPR73Cxn4LKTD4PttRwfU7jWq5g==", + "dev": true, "requires": { - "p-reduce": "^1.0.0" + "ajv": "^6.5.5", + "har-schema": "^2.0.0" } }, - "p-finally": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/p-finally/-/p-finally-1.0.0.tgz", - "integrity": "sha1-P7z7FbiZpEEjs0ttzBi3JDNqLK4=" - }, - "p-is-promise": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/p-is-promise/-/p-is-promise-1.1.0.tgz", - "integrity": "sha1-nJRWmJ6fZYgBewQ01WCXZ1w9oF4=" + "has-flag": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-2.0.0.tgz", + "integrity": "sha1-6CB68cx7MNRGzHC3NLXovhj4jVE=" }, - "p-lazy": { + "has-value": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/p-lazy/-/p-lazy-1.0.0.tgz", - "integrity": "sha1-7FPIAvLuOsKPFmzILQsrAt4nqDU=" - }, - "p-limit": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-1.2.0.tgz", - "integrity": "sha512-Y/OtIaXtUPr4/YpMv1pCL5L5ed0rumAaAeBSj12F+bSlMdys7i8oQF/GUJmfpTS/QoaRrS/k6pma29haJpsMng==", - "requires": { - "p-try": "^1.0.0" - } - }, - "p-locate": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-2.0.0.tgz", - "integrity": "sha1-IKAQOyIqcMj9OcwuWAaA893l7EM=", + "resolved": "https://registry.npmjs.org/has-value/-/has-value-1.0.0.tgz", + "integrity": "sha1-GLKB2lhbHFxR3vJMkw7SmgvmsXc=", + "dev": true, "requires": { - "p-limit": "^1.1.0" + "get-value": "^2.0.6", + "has-values": "^1.0.0", + "isobject": "^3.0.0" } }, - "p-map": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/p-map/-/p-map-1.2.0.tgz", - "integrity": "sha512-r6zKACMNhjPJMTl8KcFH4li//gkrXWfbD6feV8l6doRHlzljFWGJ2AP6iKaCJXyZmAUMOPtvbW7EXkbWO/pLEA==" - }, - "p-reduce": { + "has-values": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/p-reduce/-/p-reduce-1.0.0.tgz", - "integrity": "sha1-GMKw3ZNqRpClKfgjH1ig/bakffo=" + "resolved": "https://registry.npmjs.org/has-values/-/has-values-1.0.0.tgz", + "integrity": "sha1-lbC2P+whRmGab+V/51Yo1aOe/k8=", + "dev": true, + "requires": { + "is-number": "^3.0.0", + "kind-of": "^4.0.0" + }, + "dependencies": { + "kind-of": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-4.0.0.tgz", + "integrity": "sha1-IIE989cSkosgc3hpGkUGb65y3Vc=", + "dev": true, + "requires": { + "is-buffer": "^1.1.5" + } + } + } }, - "p-timeout": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/p-timeout/-/p-timeout-2.0.1.tgz", - "integrity": "sha512-88em58dDVB/KzPEx1X0N3LwFfYZPyDc4B6eF38M1rk9VTZMbxXXgjugz8mmwpS9Ox4BDZ+t6t3QP5+/gazweIA==", + "hash.js": { + "version": "1.1.7", + "resolved": "https://registry.npmjs.org/hash.js/-/hash.js-1.1.7.tgz", + "integrity": "sha512-taOaskGt4z4SOANNseOviYDvjEJinIkRgmp7LbKP2YTTmVxWBl87s/uzK9r+44BclBSp2X7K1hqeNfz9JbBeXA==", "requires": { - "p-finally": "^1.0.0" + "inherits": "^2.0.3", + "minimalistic-assert": "^1.0.1" } }, - "p-try": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/p-try/-/p-try-1.0.0.tgz", - "integrity": "sha1-y8ec26+P1CKOE/Yh8rGiN8GyB7M=" + "he": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/he/-/he-1.1.1.tgz", + "integrity": "sha1-k0EP0hsAlzUVH4howvJx80J+I/0=" }, - "package-json": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/package-json/-/package-json-4.0.1.tgz", - "integrity": "sha1-iGmgQBJTZhxMTKPabCEh7VVfXu0=", - "dev": true, + "hmac-drbg": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/hmac-drbg/-/hmac-drbg-1.0.1.tgz", + "integrity": "sha1-0nRXAQJabHdabFRXk+1QL8DGSaE=", "requires": { - "got": "^6.7.1", - "registry-auth-token": "^3.0.1", - "registry-url": "^3.0.3", - "semver": "^5.1.0" + "hash.js": "^1.0.3", + "minimalistic-assert": "^1.0.0", + "minimalistic-crypto-utils": "^1.0.1" } }, - "parse-cache-control": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/parse-cache-control/-/parse-cache-control-1.0.1.tgz", - "integrity": "sha1-juqz5U+laSD+Fro493+iGqzC104=", - "dev": true + "hosted-git-info": { + "version": "2.7.1", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-2.7.1.tgz", + "integrity": "sha512-7T/BxH19zbcCTa8XkMlbK5lTo1WtgkFi3GvdWEyNuc4Vex7/9Dqbnpsf4JMydcfj9HCg4zUWFTL3Za6lapg5/w==" }, - "parse-glob": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/parse-glob/-/parse-glob-3.0.4.tgz", - "integrity": "sha1-ssN2z7EfNVE7rdFz7wu246OIORw=", + "http-basic": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/http-basic/-/http-basic-7.0.0.tgz", + "integrity": "sha1-gvClBr6UJzLsje6+6A50bvVzbbo=", + "dev": true, "requires": { - "glob-base": "^0.3.0", - "is-dotfile": "^1.0.0", - "is-extglob": "^1.0.0", - "is-glob": "^2.0.0" + "@types/concat-stream": "^1.6.0", + "@types/node": "^9.4.1", + "caseless": "~0.12.0", + "concat-stream": "^1.4.6", + "http-response-object": "^3.0.1", + "parse-cache-control": "^1.0.1" }, "dependencies": { - "is-extglob": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-1.0.0.tgz", - "integrity": "sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA=" - }, - "is-glob": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-2.0.1.tgz", - "integrity": "sha1-0Jb5JqPe1WAPP9/ZEZjLCIjC2GM=", - "requires": { - "is-extglob": "^1.0.0" - } + "@types/node": { + "version": "9.6.42", + "resolved": "https://registry.npmjs.org/@types/node/-/node-9.6.42.tgz", + "integrity": "sha512-SpeVQJFekfnEaZZO1yl4je/36upII36L7gOT4DBx51B1GeAB45mmDb3a5OBQB+ZeFxVVOP37r8Owsl940G/fBg==", + "dev": true } } }, - "parse-headers": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/parse-headers/-/parse-headers-2.0.1.tgz", - "integrity": "sha1-aug6eqJanZtwCswoaYzR8e1+lTY=", + "http-response-object": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/http-response-object/-/http-response-object-3.0.1.tgz", + "integrity": "sha512-6L0Fkd6TozA8kFSfh9Widst0wfza3U1Ex2RjJ6zNDK0vR1U1auUR6jY4Nn2Xl7CCy0ikFmxW1XcspVpb9RvwTg==", + "dev": true, "requires": { - "for-each": "^0.3.2", - "trim": "0.0.1" + "@types/node": "^9.3.0" + }, + "dependencies": { + "@types/node": { + "version": "9.6.42", + "resolved": "https://registry.npmjs.org/@types/node/-/node-9.6.42.tgz", + "integrity": "sha512-SpeVQJFekfnEaZZO1yl4je/36upII36L7gOT4DBx51B1GeAB45mmDb3a5OBQB+ZeFxVVOP37r8Owsl940G/fBg==", + "dev": true + } } }, - "parse-json": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-2.2.0.tgz", - "integrity": "sha1-9ID0BDTvgHQfhGkJn43qGPVaTck=", + "http-signature": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/http-signature/-/http-signature-1.2.0.tgz", + "integrity": "sha1-muzZJRFHcvPZW2WmCruPfBj7rOE=", + "dev": true, "requires": { - "error-ex": "^1.2.0" + "assert-plus": "^1.0.0", + "jsprim": "^1.2.2", + "sshpk": "^1.7.0" } }, - "parse-passwd": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/parse-passwd/-/parse-passwd-1.0.0.tgz", - "integrity": "sha1-bVuTSkVpk7I9N/QKOC1vFmao5cY=" - }, - "parseurl": { - "version": "1.3.2", - "resolved": "https://registry.npmjs.org/parseurl/-/parseurl-1.3.2.tgz", - "integrity": "sha1-/CidTtiZMRlGDBViUyYs3I3mW/M=" + "ignore-by-default": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/ignore-by-default/-/ignore-by-default-1.0.1.tgz", + "integrity": "sha1-SMptcvbGo68Aqa1K5odr44ieKwk=", + "dev": true }, - "pascalcase": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/pascalcase/-/pascalcase-0.1.1.tgz", - "integrity": "sha1-s2PlXoAGym/iF4TS2yK9FdeRfxQ=", + "import-lazy": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/import-lazy/-/import-lazy-2.1.0.tgz", + "integrity": "sha1-BWmOPUXIjo1+nZLLBYTnfwlvPkM=", "dev": true }, - "path-dirname": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/path-dirname/-/path-dirname-1.0.2.tgz", - "integrity": "sha1-zDPSTVJeCZpTiMAzbG4yuRYGCeA=", + "imurmurhash": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/imurmurhash/-/imurmurhash-0.1.4.tgz", + "integrity": "sha1-khi5srkoojixPcT7a21XbyMUU+o=", "dev": true }, - "path-exists": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-2.1.0.tgz", - "integrity": "sha1-D+tsZPD8UY2adU3V77YscCJ2H0s=", + "inflight": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", + "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=", "requires": { - "pinkie-promise": "^2.0.0" + "once": "^1.3.0", + "wrappy": "1" } }, - "path-is-absolute": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", - "integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=" + "inherits": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", + "integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=" }, - "path-is-inside": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/path-is-inside/-/path-is-inside-1.0.2.tgz", - "integrity": "sha1-NlQX3t5EQw0cEa9hAn+s8HS9/FM=", + "ini": { + "version": "1.3.5", + "resolved": "https://registry.npmjs.org/ini/-/ini-1.3.5.tgz", + "integrity": "sha512-RZY5huIKCMRWDUqZlEi72f/lmXKMvuszcMBduliQ3nnWbx9X/ZBQO7DijMEYS9EhHBb2qacRUMtC7svLwe0lcw==", "dev": true }, - "path-key": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/path-key/-/path-key-2.0.1.tgz", - "integrity": "sha1-QRyttXTFoUDTpLGRDUDYDMn0C0A=" - }, - "path-parse": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.5.tgz", - "integrity": "sha1-PBrfhx6pzWyUMbbqK9dKD/BVxME=" + "interpret": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/interpret/-/interpret-1.2.0.tgz", + "integrity": "sha512-mT34yGKMNceBQUoVn7iCDKDntA7SC6gycMAWzGx1z/CMCTV7b2AAtXlo3nRyHZ1FelRkQbQjprHSYGwzLtkVbw==", + "dev": true }, - "path-to-regexp": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-0.1.7.tgz", - "integrity": "sha1-32BBeABfUi8V60SQ5yR6G/qmf4w=" + "invert-kv": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/invert-kv/-/invert-kv-1.0.0.tgz", + "integrity": "sha1-EEqOSqym09jNFXqO+L+rLXo//bY=" }, - "path-type": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/path-type/-/path-type-1.1.0.tgz", - "integrity": "sha1-WcRPfuSR2nBNpBXaWkBwuk+P5EE=", + "is-accessor-descriptor": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-0.1.6.tgz", + "integrity": "sha1-qeEss66Nh2cn7u84Q/igiXtcmNY=", + "dev": true, "requires": { - "graceful-fs": "^4.1.2", - "pify": "^2.0.0", - "pinkie-promise": "^2.0.0" + "kind-of": "^3.0.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, + "requires": { + "is-buffer": "^1.1.5" + } + } } }, - "pathval": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/pathval/-/pathval-1.1.0.tgz", - "integrity": "sha1-uULm1L3mUwBe9rcTYd74cn0GReA=", - "dev": true + "is-arrayish": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/is-arrayish/-/is-arrayish-0.2.1.tgz", + "integrity": "sha1-d8mYQFJ6qOyxqLppe4BkWnqSap0=" }, - "pause-stream": { - "version": "0.0.11", - "resolved": "https://registry.npmjs.org/pause-stream/-/pause-stream-0.0.11.tgz", - "integrity": "sha1-/lo0sMvOErWqaitAPuLnO2AvFEU=", + "is-binary-path": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-binary-path/-/is-binary-path-1.0.1.tgz", + "integrity": "sha1-dfFmQrSA8YenEcgUFh/TpKdlWJg=", "dev": true, "requires": { - "through": "~2.3" + "binary-extensions": "^1.0.0" } }, - "pegjs": { - "version": "0.10.0", - "resolved": "https://registry.npmjs.org/pegjs/-/pegjs-0.10.0.tgz", - "integrity": "sha1-z4uvrm7d/0tafvsYUmnqr0YQ3b0=", + "is-buffer": { + "version": "1.1.6", + "resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-1.1.6.tgz", + "integrity": "sha512-NcdALwpXkTm5Zvvbk7owOUSvVvBKDgKP5/ewfXEznmQFfs4ZRmanOeKBTjRVjka3QFoN6XJ+9F3USqfHqTaU5w==", "dev": true }, - "performance-now": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/performance-now/-/performance-now-2.1.0.tgz", - "integrity": "sha1-Ywn04OX6kT7BxpMHrjZLSzd8nns=" + "is-callable": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/is-callable/-/is-callable-1.1.4.tgz", + "integrity": "sha512-r5p9sxJjYnArLjObpjA4xu5EKI3CuKHkJXMhT7kwbpUyIFD1n5PMAsoPvWnvtZiNz7LjkYDRZhd7FlI0eMijEA==" }, - "pify": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", - "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=" + "is-ci": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/is-ci/-/is-ci-1.2.1.tgz", + "integrity": "sha512-s6tfsaQaQi3JNciBH6shVqEDvhGut0SUXr31ag8Pd8BBbVVlcGfWhpPmEOoM6RJ5TFhbypvf5yyRw/VXW1IiWg==", + "dev": true, + "requires": { + "ci-info": "^1.5.0" + } }, - "pinkie": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/pinkie/-/pinkie-2.0.4.tgz", - "integrity": "sha1-clVrgM+g1IqXToDnckjoDtT3+HA=" + "is-data-descriptor": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-0.1.4.tgz", + "integrity": "sha1-C17mSDiOLIYCgueT8YVv7D8wG1Y=", + "dev": true, + "requires": { + "kind-of": "^3.0.2" + }, + "dependencies": { + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, + "requires": { + "is-buffer": "^1.1.5" + } + } + } }, - "pinkie-promise": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/pinkie-promise/-/pinkie-promise-2.0.1.tgz", - "integrity": "sha1-ITXW36ejWMBprJsXh3YogihFD/o=", + "is-descriptor": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-0.1.6.tgz", + "integrity": "sha512-avDYr0SB3DwO9zsMov0gKCESFYqCnE4hq/4z3TdUlukEy5t9C0YRq7HLrsN52NAcqXKaepeCD0n+B0arnVG3Hg==", + "dev": true, "requires": { - "pinkie": "^2.0.0" + "is-accessor-descriptor": "^0.1.6", + "is-data-descriptor": "^0.1.4", + "kind-of": "^5.0.0" + }, + "dependencies": { + "kind-of": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-5.1.0.tgz", + "integrity": "sha512-NGEErnH6F2vUuXDh+OlbcKW7/wOcfdRHaZ7VWtqCztfHri/++YKmP51OdWeGPuqCOba6kk2OTe5d02VmTB80Pw==", + "dev": true + } } }, - "posix-character-classes": { + "is-extendable": { "version": "0.1.1", - "resolved": "https://registry.npmjs.org/posix-character-classes/-/posix-character-classes-0.1.1.tgz", - "integrity": "sha1-AerA/jta9xoqbAL+q7jB/vfgDqs=", + "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-0.1.1.tgz", + "integrity": "sha1-YrEQ4omkcUGOPsNqYX1HLjAd/Ik=", "dev": true }, - "prelude-ls": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.1.2.tgz", - "integrity": "sha1-IZMqVJ9eUv/ZqCf1cOBL5iqX2lQ=", + "is-extglob": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-2.1.1.tgz", + "integrity": "sha1-qIwCU1eR8C7TfHahueqXc8gz+MI=", "dev": true }, - "prepend-http": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/prepend-http/-/prepend-http-1.0.4.tgz", - "integrity": "sha1-1PRWKwzjaW5BrFLQ4ALlemNdxtw=" - }, - "preserve": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/preserve/-/preserve-0.2.0.tgz", - "integrity": "sha1-gV7R9uvGWSb4ZbMQwHE7yzMVzks=" - }, - "prettier": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/prettier/-/prettier-1.11.1.tgz", - "integrity": "sha512-T/KD65Ot0PB97xTrG8afQ46x3oiVhnfGjGESSI9NWYcG92+OUPZKkwHqGWXH2t9jK1crnQjubECW0FuOth+hxw==" - }, - "pretty-bytes": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/pretty-bytes/-/pretty-bytes-4.0.2.tgz", - "integrity": "sha1-sr+C5zUNZcbDOqlaqlpPYyf2HNk=" - }, - "private": { - "version": "0.1.8", - "resolved": "https://registry.npmjs.org/private/-/private-0.1.8.tgz", - "integrity": "sha512-VvivMrbvd2nKkiG38qjULzlc+4Vx4wm/whI9pQD35YrARNnhxeiRktSOhSukRLFNlzg6Br/cJPet5J/u19r/mg==" - }, - "process": { - "version": "0.5.2", - "resolved": "https://registry.npmjs.org/process/-/process-0.5.2.tgz", - "integrity": "sha1-FjjYqONML0QKkduVq5rrZ3/Bhc8=" - }, - "process-nextick-args": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.0.tgz", - "integrity": "sha512-MtEC1TqN0EU5nephaJ4rAtThHtC86dNN9qCuEhtshvpVBkAW5ZO7BASN9REnF9eoXGcRub+pFuKEpOHE+HbEMw==" - }, - "promise": { - "version": "8.0.2", - "resolved": "https://registry.npmjs.org/promise/-/promise-8.0.2.tgz", - "integrity": "sha512-EIyzM39FpVOMbqgzEHhxdrEhtOSDOtjMZQ0M6iVfCE+kWNgCkAyOdnuCWqfmflylftfadU6FkiMgHZA2kUzwRw==", - "dev": true, - "requires": { - "asap": "~2.0.6" - } - }, - "proxy-addr": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.3.tgz", - "integrity": "sha512-jQTChiCJteusULxjBp8+jftSQE5Obdl3k4cnmLA6WXtK6XFuWRnvVL7aCiBqaLPM8c4ph0S4tKna8XvmIwEnXQ==", + "is-fullwidth-code-point": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz", + "integrity": "sha1-754xOG8DGn8NZDr4L95QxFfvAMs=", "requires": { - "forwarded": "~0.1.2", - "ipaddr.js": "1.6.0" + "number-is-nan": "^1.0.0" } }, - "prr": { + "is-function": { "version": "1.0.1", - "resolved": "https://registry.npmjs.org/prr/-/prr-1.0.1.tgz", - "integrity": "sha1-0/wRS6BplaRexok/SEzrHXj19HY=" + "resolved": "https://registry.npmjs.org/is-function/-/is-function-1.0.1.tgz", + "integrity": "sha1-Es+5i2W1fdPRk6MSH19uL0N2ArU=" }, - "ps-tree": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/ps-tree/-/ps-tree-1.1.0.tgz", - "integrity": "sha1-tCGyQUDWID8e08dplrRCewjowBQ=", + "is-glob": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.0.tgz", + "integrity": "sha1-lSHHaEXMJhCoUgPd8ICpWML/q8A=", "dev": true, "requires": { - "event-stream": "~3.3.0" + "is-extglob": "^2.1.1" } }, - "pseudomap": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/pseudomap/-/pseudomap-1.0.2.tgz", - "integrity": "sha1-8FKijacOYYkX7wqKw0wa5aaChrM=" + "is-hex-prefixed": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-hex-prefixed/-/is-hex-prefixed-1.0.0.tgz", + "integrity": "sha1-fY035q135dEnFIkTxXPggtd39VQ=" }, - "pstree.remy": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/pstree.remy/-/pstree.remy-1.1.0.tgz", - "integrity": "sha512-q5I5vLRMVtdWa8n/3UEzZX7Lfghzrg9eG2IKk2ENLSofKRCXVqMvMUHxCKgXNaqH/8ebhBxrqftHWnyTFweJ5Q==", + "is-installed-globally": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/is-installed-globally/-/is-installed-globally-0.1.0.tgz", + "integrity": "sha1-Df2Y9akRFxbdU13aZJL2e/PSWoA=", "dev": true, "requires": { - "ps-tree": "^1.1.0" + "global-dirs": "^0.1.0", + "is-path-inside": "^1.0.0" } }, - "punycode": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/punycode/-/punycode-1.4.1.tgz", - "integrity": "sha1-wNWmOycYgArY4esPpSachN1BhF4=" - }, - "qs": { - "version": "6.5.1", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.5.1.tgz", - "integrity": "sha512-eRzhrN1WSINYCDCbrz796z37LOe3m5tmW7RQf6oBntukAG1nmovJvhnwHHRMAfeoItc1m2Hk02WER2aQ/iqs+A==" - }, - "query-string": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/query-string/-/query-string-5.1.1.tgz", - "integrity": "sha512-gjWOsm2SoGlgLEdAGt7a6slVOk9mGiXmPFMqrEhLQ68rhQuBnpfs3+EmlvqKyxnCo9/PPlF+9MtY02S1aFg+Jw==", - "requires": { - "decode-uri-component": "^0.2.0", - "object-assign": "^4.1.0", - "strict-uri-encode": "^1.0.0" - } + "is-npm": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-npm/-/is-npm-1.0.0.tgz", + "integrity": "sha1-8vtjpl5JBbQGyGBydloaTceTufQ=", + "dev": true }, - "randomatic": { - "version": "1.1.7", - "resolved": "https://registry.npmjs.org/randomatic/-/randomatic-1.1.7.tgz", - "integrity": "sha512-D5JUjPyJbaJDkuAazpVnSfVkLlpeO3wDlPROTMLGKG1zMFNFRgrciKo1ltz/AzNTkqE0HzDx655QOL51N06how==", + "is-number": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/is-number/-/is-number-3.0.0.tgz", + "integrity": "sha1-JP1iAaR4LPUFYcgQJ2r8fRLXEZU=", + "dev": true, "requires": { - "is-number": "^3.0.0", - "kind-of": "^4.0.0" + "kind-of": "^3.0.2" }, "dependencies": { "kind-of": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-4.0.0.tgz", - "integrity": "sha1-IIE989cSkosgc3hpGkUGb65y3Vc=", + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, "requires": { "is-buffer": "^1.1.5" } } } }, - "randomhex": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/randomhex/-/randomhex-0.1.5.tgz", - "integrity": "sha1-us7vmCMpCRQA8qKRLGzQLxCU9YU=" + "is-obj": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-obj/-/is-obj-1.0.1.tgz", + "integrity": "sha1-PkcprB9f3gJc19g6iW2rn09n2w8=", + "dev": true }, - "range-parser": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/range-parser/-/range-parser-1.2.0.tgz", - "integrity": "sha1-9JvmtIeJTdxA3MlKMi9hEJLgDV4=" + "is-path-inside": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-path-inside/-/is-path-inside-1.0.1.tgz", + "integrity": "sha1-jvW33lBDej/cprToZe96pVy0gDY=", + "dev": true, + "requires": { + "path-is-inside": "^1.0.1" + } }, - "raw-body": { - "version": "2.3.2", - "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-2.3.2.tgz", - "integrity": "sha1-vNYMd9Prk83gBQKVw/N5OJvIj4k=", + "is-plain-object": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/is-plain-object/-/is-plain-object-2.0.4.tgz", + "integrity": "sha512-h5PpgXkWitc38BBMYawTYMWJHFZJVnBquFE57xFpjB8pJFiF6gZ+bU+WyI/yqXiFR5mdLsgYNaPe8uao6Uv9Og==", + "dev": true, + "requires": { + "isobject": "^3.0.1" + } + }, + "is-redirect": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-redirect/-/is-redirect-1.0.0.tgz", + "integrity": "sha1-HQPd7VO9jbDzDCbk+V02/HyH3CQ=", + "dev": true + }, + "is-retry-allowed": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/is-retry-allowed/-/is-retry-allowed-1.1.0.tgz", + "integrity": "sha1-EaBgVotnM5REAz0BJaYaINVk+zQ=", + "dev": true + }, + "is-stream": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-1.1.0.tgz", + "integrity": "sha1-EtSj3U5o4Lec6428hBc66A2RykQ=", + "dev": true + }, + "is-typedarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-typedarray/-/is-typedarray-1.0.0.tgz", + "integrity": "sha1-5HnICFjfDBsR3dppQPlgEfzaSpo=", + "dev": true + }, + "is-utf8": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/is-utf8/-/is-utf8-0.2.1.tgz", + "integrity": "sha1-Sw2hRCEE0bM2NA6AeX6GXPOffXI=" + }, + "is-windows": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-windows/-/is-windows-1.0.2.tgz", + "integrity": "sha512-eXK1UInq2bPmjyX6e3VHIzMLobc4J94i4AWn+Hpq3OU5KkrRC96OAcR3PRJ/pGu6m8TRnBHP9dkXQVsT/COVIA==", + "dev": true + }, + "isarray": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", + "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", + "dev": true + }, + "isexe": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", + "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=", + "dev": true + }, + "isobject": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/isobject/-/isobject-3.0.1.tgz", + "integrity": "sha1-TkMekrEalzFjaqH5yNHMvP2reN8=", + "dev": true + }, + "isstream": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/isstream/-/isstream-0.1.2.tgz", + "integrity": "sha1-R+Y/evVa+m+S4VAOaQ64uFKcCZo=", + "dev": true + }, + "istanbul": { + "version": "0.4.5", + "resolved": "https://registry.npmjs.org/istanbul/-/istanbul-0.4.5.tgz", + "integrity": "sha1-ZcfXPUxNqE1POsMQuRj7C4Azczs=", + "dev": true, "requires": { - "bytes": "3.0.0", - "http-errors": "1.6.2", - "iconv-lite": "0.4.19", - "unpipe": "1.0.0" + "abbrev": "1.0.x", + "async": "1.x", + "escodegen": "1.8.x", + "esprima": "2.7.x", + "glob": "^5.0.15", + "handlebars": "^4.0.1", + "js-yaml": "3.x", + "mkdirp": "0.5.x", + "nopt": "3.x", + "once": "1.x", + "resolve": "1.1.x", + "supports-color": "^3.1.0", + "which": "^1.1.1", + "wordwrap": "^1.0.0" }, "dependencies": { - "depd": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/depd/-/depd-1.1.1.tgz", - "integrity": "sha1-V4O04cRZ8G+lyif5kfPQbnoxA1k=" + "abbrev": { + "version": "1.0.9", + "resolved": "https://registry.npmjs.org/abbrev/-/abbrev-1.0.9.tgz", + "integrity": "sha1-kbR5JYinc4wl813W9jdSovh3YTU=", + "dev": true + }, + "glob": { + "version": "5.0.15", + "resolved": "https://registry.npmjs.org/glob/-/glob-5.0.15.tgz", + "integrity": "sha1-G8k2ueAvSmA/zCIuz3Yz0wuLk7E=", + "dev": true, + "requires": { + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "2 || 3", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" + } + }, + "has-flag": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-1.0.0.tgz", + "integrity": "sha1-nZ55MWXOAXoA8AQYxD+UKnsdEfo=", + "dev": true }, - "http-errors": { - "version": "1.6.2", - "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.6.2.tgz", - "integrity": "sha1-CgAsyFcHGSp+eUbO7cERVfYOxzY=", + "nopt": { + "version": "3.0.6", + "resolved": "https://registry.npmjs.org/nopt/-/nopt-3.0.6.tgz", + "integrity": "sha1-xkZdvwirzU2zWTF/eaxopkayj/k=", + "dev": true, "requires": { - "depd": "1.1.1", - "inherits": "2.0.3", - "setprototypeof": "1.0.3", - "statuses": ">= 1.3.1 < 2" + "abbrev": "1" } }, - "setprototypeof": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.0.3.tgz", - "integrity": "sha1-ZlZ+NwQ+608E2RvWWMDL77VbjgQ=" + "resolve": { + "version": "1.1.7", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.1.7.tgz", + "integrity": "sha1-IDEU2CrSxe2ejgQRs5ModeiJ6Xs=", + "dev": true + }, + "supports-color": { + "version": "3.2.3", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-3.2.3.tgz", + "integrity": "sha1-ZawFBLOVQXHYpklGsq48u4pfVPY=", + "dev": true, + "requires": { + "has-flag": "^1.0.0" + } } } }, - "rc": { - "version": "1.2.6", - "resolved": "https://registry.npmjs.org/rc/-/rc-1.2.6.tgz", - "integrity": "sha1-6xiYnG1PTxYsOZ953dKfODVWgJI=", + "js-sha3": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/js-sha3/-/js-sha3-0.6.1.tgz", + "integrity": "sha1-W4n3enR3Z5h39YxKB1JAk0sflcA=", + "dev": true + }, + "js-yaml": { + "version": "3.12.1", + "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.12.1.tgz", + "integrity": "sha512-um46hB9wNOKlwkHgiuyEVAybXBjwFUV0Z/RaHJblRd9DXltue9FTYvzCr9ErQrK9Adz5MU4gHWVaNUfdmrC8qA==", "dev": true, "requires": { - "deep-extend": "~0.4.0", - "ini": "~1.3.0", - "minimist": "^1.2.0", - "strip-json-comments": "~2.0.1" + "argparse": "^1.0.7", + "esprima": "^4.0.0" }, "dependencies": { - "minimist": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz", - "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=", + "esprima": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/esprima/-/esprima-4.0.1.tgz", + "integrity": "sha512-eGuFFw7Upda+g4p+QHvnW0RyTX/SVeJBDM/gCtMARO0cLuT2HcEKnTPvhjV6aGeqrCB/sbNop0Kszm0jsaWU4A==", "dev": true } } }, - "read-chunk": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/read-chunk/-/read-chunk-2.1.0.tgz", - "integrity": "sha1-agTAkoAF7Z1C4aasVgDhnLx/9lU=", - "requires": { - "pify": "^3.0.0", - "safe-buffer": "^5.1.1" - }, - "dependencies": { - "pify": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", - "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=" - } - } + "jsbn": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/jsbn/-/jsbn-0.1.1.tgz", + "integrity": "sha1-peZUwuWi3rXyAdls77yoDA7y9RM=", + "dev": true }, - "read-pkg": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-1.1.0.tgz", - "integrity": "sha1-9f+qXs0pyzHAR0vKfXVra7KePyg=", - "requires": { - "load-json-file": "^1.0.0", - "normalize-package-data": "^2.3.2", - "path-type": "^1.0.0" - } + "json-schema": { + "version": "0.2.3", + "resolved": "https://registry.npmjs.org/json-schema/-/json-schema-0.2.3.tgz", + "integrity": "sha1-tIDIkuWaLwWVTOcnvT8qTogvnhM=", + "dev": true }, - "read-pkg-up": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/read-pkg-up/-/read-pkg-up-1.0.1.tgz", - "integrity": "sha1-nWPBMnbAZZGNV/ACpX9AobZD+wI=", - "requires": { - "find-up": "^1.0.0", - "read-pkg": "^1.0.0" - } + "json-schema-traverse": { + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", + "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", + "dev": true }, - "readable-stream": { - "version": "2.3.5", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.5.tgz", - "integrity": "sha512-tK0yDhrkygt/knjowCUiWP9YdV7c5R+8cR0r/kt9ZhBU906Fs6RpQJCEilamRJj1Nx2rWI6LkW9gKqjTkshhEw==", + "json-stringify-safe": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/json-stringify-safe/-/json-stringify-safe-5.0.1.tgz", + "integrity": "sha1-Epai1Y/UXxmg9s4B1lcB4sc1tus=", + "dev": true + }, + "jsonfile": { + "version": "2.4.0", + "resolved": "https://registry.npmjs.org/jsonfile/-/jsonfile-2.4.0.tgz", + "integrity": "sha1-NzaitCi4e72gzIO1P6PWM6NcKug=", "requires": { - "core-util-is": "~1.0.0", - "inherits": "~2.0.3", - "isarray": "~1.0.0", - "process-nextick-args": "~2.0.0", - "safe-buffer": "~5.1.1", - "string_decoder": "~1.0.3", - "util-deprecate": "~1.0.1" + "graceful-fs": "^4.1.6" } }, - "readdirp": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-2.1.0.tgz", - "integrity": "sha1-TtCtBg3zBzMAxIRANz9y0cxkLXg=", + "jsprim": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/jsprim/-/jsprim-1.4.1.tgz", + "integrity": "sha1-MT5mvB5cwG5Di8G3SZwuXFastqI=", "dev": true, "requires": { - "graceful-fs": "^4.1.2", - "minimatch": "^3.0.2", - "readable-stream": "^2.0.2", - "set-immediate-shim": "^1.0.1" + "assert-plus": "1.0.0", + "extsprintf": "1.3.0", + "json-schema": "0.2.3", + "verror": "1.10.0" } }, - "recast": { - "version": "0.14.7", - "resolved": "https://registry.npmjs.org/recast/-/recast-0.14.7.tgz", - "integrity": "sha512-/nwm9pkrcWagN40JeJhkPaRxiHXBRkXyRh/hgU088Z/v+qCy+zIHHY6bC6o7NaKAxPqtE6nD8zBH1LfU0/Wx6A==", + "keccakjs": { + "version": "0.2.3", + "resolved": "https://registry.npmjs.org/keccakjs/-/keccakjs-0.2.3.tgz", + "integrity": "sha512-BjLkNDcfaZ6l8HBG9tH0tpmDv3sS2mA7FNQxFHpCdzP3Gb2MVruXBSuoM66SnVxKJpAr5dKGdkHD+bDokt8fTg==", + "dev": true, "requires": { - "ast-types": "0.11.3", - "esprima": "~4.0.0", - "private": "~0.1.5", - "source-map": "~0.6.1" - }, - "dependencies": { - "source-map": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", - "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==" - } + "browserify-sha3": "^0.0.4", + "sha3": "^1.2.2" } }, - "rechoir": { - "version": "0.6.2", - "resolved": "https://registry.npmjs.org/rechoir/-/rechoir-0.6.2.tgz", - "integrity": "sha1-hSBLVNuoLVdC4oyWdW70OvUOM4Q=", + "kind-of": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-6.0.2.tgz", + "integrity": "sha512-s5kLOcnH0XqDO+FvuaLX8DDjZ18CGFk7VygH40QoKPUQhW4e2rvM0rwUq0t8IQDOwYSeLK01U90OjzBTme2QqA==", + "dev": true + }, + "klaw": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/klaw/-/klaw-1.3.1.tgz", + "integrity": "sha1-QIhDO0azsbolnXh4XY6W9zugJDk=", "requires": { - "resolve": "^1.1.6" + "graceful-fs": "^4.1.9" } }, - "regenerate": { - "version": "1.3.3", - "resolved": "https://registry.npmjs.org/regenerate/-/regenerate-1.3.3.tgz", - "integrity": "sha512-jVpo1GadrDAK59t/0jRx5VxYWQEDkkEKi6+HjE3joFVLfDOh9Xrdh0dF1eSq+BI/SwvTQ44gSscJ8N5zYL61sg==" - }, - "regenerator-runtime": { - "version": "0.11.1", - "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.11.1.tgz", - "integrity": "sha512-MguG95oij0fC3QV3URf4V2SDYGJhJnJGqvIIgdECeODCT98wSWDAJ94SSuVpYQUoTcGUIL6L4yNB7j1DFFHSBg==" - }, - "regenerator-transform": { - "version": "0.10.1", - "resolved": "https://registry.npmjs.org/regenerator-transform/-/regenerator-transform-0.10.1.tgz", - "integrity": "sha512-PJepbvDbuK1xgIgnau7Y90cwaAmO/LCLMI2mPvaXq2heGMR3aWW5/BQvYrhJ8jgmQjXewXvBjzfqKcVOmhjZ6Q==", + "latest-version": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/latest-version/-/latest-version-3.1.0.tgz", + "integrity": "sha1-ogU4P+oyKzO1rjsYq+4NwvNW7hU=", + "dev": true, "requires": { - "babel-runtime": "^6.18.0", - "babel-types": "^6.19.0", - "private": "^0.1.6" + "package-json": "^4.0.0" } }, - "regex-cache": { - "version": "0.4.4", - "resolved": "https://registry.npmjs.org/regex-cache/-/regex-cache-0.4.4.tgz", - "integrity": "sha512-nVIZwtCjkC9YgvWkpM55B5rBhBYRZhAaJbgcFYXXsHnbZ9UZI9nnVWYZpBlCqv9ho2eZryPnWrZGsOdPwVWXWQ==", + "lcid": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/lcid/-/lcid-1.0.0.tgz", + "integrity": "sha1-MIrMr6C8SDo4Z7S28rlQYlHRuDU=", "requires": { - "is-equal-shallow": "^0.1.3" + "invert-kv": "^1.0.0" } }, - "regex-not": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/regex-not/-/regex-not-1.0.2.tgz", - "integrity": "sha512-J6SDjUgDxQj5NusnOtdFxDwN/+HWykR8GELwctJ7mdqhcyy1xEc4SRFHUXvxTp661YaVKAjfRLZ9cCqS6tn32A==", + "levn": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/levn/-/levn-0.3.0.tgz", + "integrity": "sha1-OwmSTt+fCDwEkP3UwLxEIeBHZO4=", "dev": true, "requires": { - "extend-shallow": "^3.0.2", - "safe-regex": "^1.1.0" + "prelude-ls": "~1.1.2", + "type-check": "~0.3.2" } }, - "regexpu-core": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/regexpu-core/-/regexpu-core-2.0.0.tgz", - "integrity": "sha1-SdA4g3uNz4v6W5pCE5k45uoq4kA=", + "load-json-file": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-1.1.0.tgz", + "integrity": "sha1-lWkFcI1YtLq0wiYbBPWfMcmTdMA=", "requires": { - "regenerate": "^1.2.1", - "regjsgen": "^0.2.0", - "regjsparser": "^0.1.4" + "graceful-fs": "^4.1.2", + "parse-json": "^2.2.0", + "pify": "^2.0.0", + "pinkie-promise": "^2.0.0", + "strip-bom": "^2.0.0" } }, - "registry-auth-token": { - "version": "3.3.2", - "resolved": "https://registry.npmjs.org/registry-auth-token/-/registry-auth-token-3.3.2.tgz", - "integrity": "sha512-JL39c60XlzCVgNrO+qq68FoNb56w/m7JYvGR2jT5iR1xBrUA3Mfx5Twk5rqTThPmQKMWydGmq8oFtDlxfrmxnQ==", + "locate-path": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-2.0.0.tgz", + "integrity": "sha1-K1aLJl7slExtnA3pw9u7ygNUzY4=", "dev": true, "requires": { - "rc": "^1.1.6", - "safe-buffer": "^5.0.1" + "p-locate": "^2.0.0", + "path-exists": "^3.0.0" + }, + "dependencies": { + "path-exists": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", + "integrity": "sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=", + "dev": true + } } }, - "registry-url": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/registry-url/-/registry-url-3.1.0.tgz", - "integrity": "sha1-PU74cPc93h138M+aOBQyRE4XSUI=", - "dev": true, - "requires": { - "rc": "^1.0.1" - } + "lodash": { + "version": "4.17.11", + "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.11.tgz", + "integrity": "sha512-cQKh8igo5QUhZ7lg38DYWAxMvjSAKG0A8wGSVimP07SIUEK2UO+arSRKbRZWtelMtN5V0Hkwh5ryOto/SshYIg==" }, - "regjsgen": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/regjsgen/-/regjsgen-0.2.0.tgz", - "integrity": "sha1-bAFq3qxVT3WCP+N6wFuS1aTtsfc=" + "lodash.assign": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/lodash.assign/-/lodash.assign-4.2.0.tgz", + "integrity": "sha1-DZnzzNem0mHRm9rrkkUAXShYCOc=" }, - "regjsparser": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/regjsparser/-/regjsparser-0.1.5.tgz", - "integrity": "sha1-fuj4Tcb6eS0/0K4ijSS9lJ6tIFw=", + "lowercase-keys": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/lowercase-keys/-/lowercase-keys-1.0.1.tgz", + "integrity": "sha512-G2Lj61tXDnVFFOi8VZds+SoQjtQC3dgokKdDG2mTm1tx4m50NUHBOZSBwQQHyy0V12A0JTG4icfZQH+xPyh8VA==", + "dev": true + }, + "lru-cache": { + "version": "4.1.5", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-4.1.5.tgz", + "integrity": "sha512-sWZlbEP2OsHNkXrMl5GYk/jKk70MBng6UU4YI/qGDYbgf6YbP4EvmqISbXCoJiRKs+1bSpFHVgQxvJ17F2li5g==", + "dev": true, "requires": { - "jsesc": "~0.5.0" + "pseudomap": "^1.0.2", + "yallist": "^2.1.2" } }, - "remove-trailing-separator": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/remove-trailing-separator/-/remove-trailing-separator-1.1.0.tgz", - "integrity": "sha1-wkvOKig62tW8P1jg1IJJuSN52O8=" - }, - "repeat-element": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/repeat-element/-/repeat-element-1.1.2.tgz", - "integrity": "sha1-7wiaF40Ug7quTZPrmLT55OEdmQo=" - }, - "repeat-string": { - "version": "1.6.1", - "resolved": "https://registry.npmjs.org/repeat-string/-/repeat-string-1.6.1.tgz", - "integrity": "sha1-jcrkcOHIirwtYA//Sndihtp15jc=" - }, - "repeating": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/repeating/-/repeating-2.0.1.tgz", - "integrity": "sha1-UhTFOpJtNVJwdSf7q0FdvAjQbdo=", + "make-dir": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-1.3.0.tgz", + "integrity": "sha512-2w31R7SJtieJJnQtGc7RVL2StM2vGYVfqUOvUDxH6bC6aJTxPxTF0GnIgCyu7tjockiUWAYQRbxa7vKn34s5sQ==", + "dev": true, "requires": { - "is-finite": "^1.0.0" + "pify": "^3.0.0" + }, + "dependencies": { + "pify": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", + "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=", + "dev": true + } } }, - "replace-ext": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/replace-ext/-/replace-ext-0.0.1.tgz", - "integrity": "sha1-KbvZIHinOfC8zitO5B6DeVNSKSQ=" + "map-cache": { + "version": "0.2.2", + "resolved": "https://registry.npmjs.org/map-cache/-/map-cache-0.2.2.tgz", + "integrity": "sha1-wyq9C9ZSXZsFFkW7TyasXcmKDb8=", + "dev": true }, - "req-cwd": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/req-cwd/-/req-cwd-1.0.1.tgz", - "integrity": "sha1-DXOurpJm5penj3l2AZZ352rPD/8=", + "map-visit": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/map-visit/-/map-visit-1.0.0.tgz", + "integrity": "sha1-7Nyo8TFE5mDxtb1B8S80edmN+48=", "dev": true, "requires": { - "req-from": "^1.0.1" + "object-visit": "^1.0.0" } }, - "req-from": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/req-from/-/req-from-1.0.1.tgz", - "integrity": "sha1-v4HaUUeUfTLRO5R9wSpYrUWHNQ4=", + "memorystream": { + "version": "0.3.1", + "resolved": "https://registry.npmjs.org/memorystream/-/memorystream-0.3.1.tgz", + "integrity": "sha1-htcJCzDORV1j+64S3aUaR93K+bI=" + }, + "micromatch": { + "version": "3.1.10", + "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-3.1.10.tgz", + "integrity": "sha512-MWikgl9n9M3w+bpsY3He8L+w9eF9338xRl8IAO5viDizwSzziFEyUzo2xrrloB64ADbTf8uA8vRqqttDTOmccg==", "dev": true, "requires": { - "resolve-from": "^2.0.0" - }, - "dependencies": { - "resolve-from": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-2.0.0.tgz", - "integrity": "sha1-lICrIOlP+h2egKgEx+oUdhGWa1c=", - "dev": true - } + "arr-diff": "^4.0.0", + "array-unique": "^0.3.2", + "braces": "^2.3.1", + "define-property": "^2.0.2", + "extend-shallow": "^3.0.2", + "extglob": "^2.0.4", + "fragment-cache": "^0.2.1", + "kind-of": "^6.0.2", + "nanomatch": "^1.2.9", + "object.pick": "^1.3.0", + "regex-not": "^1.0.0", + "snapdragon": "^0.8.1", + "to-regex": "^3.0.2" } }, - "request": { - "version": "2.85.0", - "resolved": "https://registry.npmjs.org/request/-/request-2.85.0.tgz", - "integrity": "sha512-8H7Ehijd4js+s6wuVPLjwORxD4zeuyjYugprdOXlPSqaApmL/QOy+EB/beICHVCHkGMKNh5rvihb5ov+IDw4mg==", - "requires": { - "aws-sign2": "~0.7.0", - "aws4": "^1.6.0", - "caseless": "~0.12.0", - "combined-stream": "~1.0.5", - "extend": "~3.0.1", - "forever-agent": "~0.6.1", - "form-data": "~2.3.1", - "har-validator": "~5.0.3", - "hawk": "~6.0.2", - "http-signature": "~1.2.0", - "is-typedarray": "~1.0.0", - "isstream": "~0.1.2", - "json-stringify-safe": "~5.0.1", - "mime-types": "~2.1.17", - "oauth-sign": "~0.8.2", - "performance-now": "^2.1.0", - "qs": "~6.5.1", - "safe-buffer": "^5.1.1", - "stringstream": "~0.0.5", - "tough-cookie": "~2.3.3", - "tunnel-agent": "^0.6.0", - "uuid": "^3.1.0" - } + "mime-db": { + "version": "1.38.0", + "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.38.0.tgz", + "integrity": "sha512-bqVioMFFzc2awcdJZIzR3HjZFX20QhilVS7hytkKrv7xFAn8bM1gzc/FOX2awLISvWe0PV8ptFKcon+wZ5qYkg==", + "dev": true }, - "request-promise-core": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/request-promise-core/-/request-promise-core-1.1.1.tgz", - "integrity": "sha1-Pu4AssWqgyOc+wTFcA2jb4HNCLY=", + "mime-types": { + "version": "2.1.22", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.22.tgz", + "integrity": "sha512-aGl6TZGnhm/li6F7yx82bJiBZwgiEa4Hf6CNr8YO+r5UHr53tSTYZb102zyU50DOWWKeOv0uQLRL0/9EiKWCog==", "dev": true, "requires": { - "lodash": "^4.13.1" + "mime-db": "~1.38.0" } }, - "request-promise-native": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/request-promise-native/-/request-promise-native-1.0.5.tgz", - "integrity": "sha1-UoF3D2jgyXGeUWP9P6tIIhX0/aU=", - "dev": true, + "mimic-response": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-1.0.1.tgz", + "integrity": "sha512-j5EctnkH7amfV/q5Hgmoal1g2QHFJRraOtmx0JpIqkxhBhI/lJSl1nMpQ45hVarwNETOoWEimndZ4QK0RHxuxQ==" + }, + "min-document": { + "version": "2.19.0", + "resolved": "https://registry.npmjs.org/min-document/-/min-document-2.19.0.tgz", + "integrity": "sha1-e9KC4/WELtKVu3SM3Z8f+iyCRoU=", "requires": { - "request-promise-core": "1.1.1", - "stealthy-require": "^1.1.0", - "tough-cookie": ">=2.3.3" + "dom-walk": "^0.1.0" } }, - "require-directory": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/require-directory/-/require-directory-2.1.1.tgz", - "integrity": "sha1-jGStX9MNqxyXbiNE/+f3kqam30I=" - }, - "require-from-string": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/require-from-string/-/require-from-string-1.2.1.tgz", - "integrity": "sha1-UpyczvJzgK3+yaL5ZbZJu+5jZBg=" + "minimalistic-assert": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/minimalistic-assert/-/minimalistic-assert-1.0.1.tgz", + "integrity": "sha512-UtJcAD4yEaGtjPezWuO9wC4nwUnVH/8/Im3yEHQP4b67cXlD/Qr9hdITCU1xDbSEXg2XKNaP8jsReV7vQd00/A==" }, - "require-main-filename": { + "minimalistic-crypto-utils": { "version": "1.0.1", - "resolved": "https://registry.npmjs.org/require-main-filename/-/require-main-filename-1.0.1.tgz", - "integrity": "sha1-l/cXtp1IeE9fUmpsWqj/3aBVpNE=" + "resolved": "https://registry.npmjs.org/minimalistic-crypto-utils/-/minimalistic-crypto-utils-1.0.1.tgz", + "integrity": "sha1-9sAMHAsIIkblxNmd+4x8CDsrWCo=" }, - "resolve": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.6.0.tgz", - "integrity": "sha512-mw7JQNu5ExIkcw4LPih0owX/TZXjD/ZUF/ZQ/pDnkw3ZKhDcZZw5klmBlj6gVMwjQ3Pz5Jgu7F3d0jcDVuEWdw==", + "minimatch": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", + "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", "requires": { - "path-parse": "^1.0.5" + "brace-expansion": "^1.1.7" } }, - "resolve-cwd": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/resolve-cwd/-/resolve-cwd-2.0.0.tgz", - "integrity": "sha1-AKn3OHVW4nA46uIyyqNypqWbZlo=", + "minimist": { + "version": "0.0.8", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-0.0.8.tgz", + "integrity": "sha1-hX/Kv8M5fSYluCKCYuhqp6ARsF0=" + }, + "mixin-deep": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/mixin-deep/-/mixin-deep-1.3.1.tgz", + "integrity": "sha512-8ZItLHeEgaqEvd5lYBXfm4EZSFCX29Jb9K+lAHhDKzReKBQKj3R+7NOF6tjqYi9t4oI8VUfaWITJQm86wnXGNQ==", + "dev": true, "requires": { - "resolve-from": "^3.0.0" + "for-in": "^1.0.2", + "is-extendable": "^1.0.1" + }, + "dependencies": { + "is-extendable": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-1.0.1.tgz", + "integrity": "sha512-arnXMxT1hhoKo9k1LZdmlNyJdDDfy2v0fXjFlmok4+i8ul/6WlbVge9bhM74OpNPQPMGUToDtz+KXa1PneJxOA==", + "dev": true, + "requires": { + "is-plain-object": "^2.0.4" + } + } } }, - "resolve-dir": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/resolve-dir/-/resolve-dir-1.0.1.tgz", - "integrity": "sha1-eaQGRMNivoLybv/nOcm7U4IEb0M=", + "mkdirp": { + "version": "0.5.1", + "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.1.tgz", + "integrity": "sha1-MAV0OOrGz3+MR2fzhkjWaX11yQM=", "requires": { - "expand-tilde": "^2.0.0", - "global-modules": "^1.0.0" + "minimist": "0.0.8" } }, - "resolve-from": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-3.0.0.tgz", - "integrity": "sha1-six699nWiBvItuZTM17rywoYh0g=" - }, - "resolve-url": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/resolve-url/-/resolve-url-0.2.1.tgz", - "integrity": "sha1-LGN/53yJOv0qZj/iGqkIAGjiBSo=", - "dev": true - }, - "responselike": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/responselike/-/responselike-1.0.2.tgz", - "integrity": "sha1-kYcg7ztjHFZCvgaPFa3lpG9Loec=", + "mocha": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/mocha/-/mocha-4.1.0.tgz", + "integrity": "sha512-0RVnjg1HJsXY2YFDoTNzcc1NKhYuXKRrBAG2gDygmJJA136Cs2QlRliZG1mA0ap7cuaT30mw16luAeln+4RiNA==", "requires": { - "lowercase-keys": "^1.0.0" + "browser-stdout": "1.3.0", + "commander": "2.11.0", + "debug": "3.1.0", + "diff": "3.3.1", + "escape-string-regexp": "1.0.5", + "glob": "7.1.2", + "growl": "1.10.3", + "he": "1.1.1", + "mkdirp": "0.5.1", + "supports-color": "4.4.0" } }, - "restore-cursor": { + "ms": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-2.0.0.tgz", - "integrity": "sha1-n37ih/gv0ybU/RYpI9YhKe7g368=", - "requires": { - "onetime": "^2.0.0", - "signal-exit": "^3.0.2" - } + "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", + "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" }, - "ret": { - "version": "0.1.15", - "resolved": "https://registry.npmjs.org/ret/-/ret-0.1.15.tgz", - "integrity": "sha512-TTlYpa+OL+vMMNG24xSlQGEJ3B/RzEfUlLct7b5G/ytav+wPrplCpVMFuwzXbkecJrb6IYo1iFb0S9v37754mg==", - "dev": true + "nan": { + "version": "2.12.1", + "resolved": "https://registry.npmjs.org/nan/-/nan-2.12.1.tgz", + "integrity": "sha512-JY7V6lRkStKcKTvHO5NVSQRv+RV+FIL5pvDoLiAtSL9pKlC5x9PKQcZDsq7m4FO4d57mkhC6Z+QhAh3Jdk5JFw==", + "dev": true, + "optional": true }, - "right-align": { - "version": "0.1.3", - "resolved": "https://registry.npmjs.org/right-align/-/right-align-0.1.3.tgz", - "integrity": "sha1-YTObci/mo1FWiSENJOFMlhSGE+8=", + "nanomatch": { + "version": "1.2.13", + "resolved": "https://registry.npmjs.org/nanomatch/-/nanomatch-1.2.13.tgz", + "integrity": "sha512-fpoe2T0RbHwBTBUOftAfBPaDEi06ufaUai0mE6Yn1kacc3SnTErfb/h+X94VXzI64rKFHYImXSvdwGGCmwOqCA==", "dev": true, - "optional": true, "requires": { - "align-text": "^0.1.1" + "arr-diff": "^4.0.0", + "array-unique": "^0.3.2", + "define-property": "^2.0.2", + "extend-shallow": "^3.0.2", + "fragment-cache": "^0.2.1", + "is-windows": "^1.0.2", + "kind-of": "^6.0.2", + "object.pick": "^1.3.0", + "regex-not": "^1.0.0", + "snapdragon": "^0.8.1", + "to-regex": "^3.0.1" } }, - "rimraf": { - "version": "2.6.2", - "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.6.2.tgz", - "integrity": "sha512-lreewLK/BlghmxtfH36YYVg1i8IAce4TI7oao75I1g245+6BctqTVQiBP3YUJ9C6DQOXJmkYR9X9fCLtCOJc5w==", + "nodemon": { + "version": "1.18.10", + "resolved": "https://registry.npmjs.org/nodemon/-/nodemon-1.18.10.tgz", + "integrity": "sha512-we51yBb1TfEvZamFchRgcfLbVYgg0xlGbyXmOtbBzDwxwgewYS/YbZ5tnlnsH51+AoSTTsT3A2E/FloUbtH8cQ==", + "dev": true, "requires": { - "glob": "^7.0.5" + "chokidar": "^2.1.0", + "debug": "^3.1.0", + "ignore-by-default": "^1.0.1", + "minimatch": "^3.0.4", + "pstree.remy": "^1.1.6", + "semver": "^5.5.0", + "supports-color": "^5.2.0", + "touch": "^3.1.0", + "undefsafe": "^2.0.2", + "update-notifier": "^2.5.0" + }, + "dependencies": { + "has-flag": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", + "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=", + "dev": true + }, + "supports-color": { + "version": "5.5.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", + "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", + "dev": true, + "requires": { + "has-flag": "^3.0.0" + } + } } }, - "run-async": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/run-async/-/run-async-2.3.0.tgz", - "integrity": "sha1-A3GrSuC91yDUFm19/aZP96RFpsA=", + "nopt": { + "version": "1.0.10", + "resolved": "https://registry.npmjs.org/nopt/-/nopt-1.0.10.tgz", + "integrity": "sha1-bd0hvSoxQXuScn3Vhfim83YI6+4=", + "dev": true, "requires": { - "is-promise": "^2.1.0" + "abbrev": "1" } }, - "rx-lite": { - "version": "4.0.8", - "resolved": "https://registry.npmjs.org/rx-lite/-/rx-lite-4.0.8.tgz", - "integrity": "sha1-Cx4Rr4vESDbwSmQH6S2kJGe3lEQ=" - }, - "rx-lite-aggregates": { - "version": "4.0.8", - "resolved": "https://registry.npmjs.org/rx-lite-aggregates/-/rx-lite-aggregates-4.0.8.tgz", - "integrity": "sha1-dTuHqJoRyVRnxKwWJsTvxOBcZ74=", + "normalize-package-data": { + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-2.5.0.tgz", + "integrity": "sha512-/5CMN3T0R4XTj4DcGaexo+roZSdSFW/0AOOTROrjxzCG1wrWXEsGbRKevjlIL+ZDE4sZlJr5ED4YW0yqmkK+eA==", "requires": { - "rx-lite": "*" + "hosted-git-info": "^2.1.4", + "resolve": "^1.10.0", + "semver": "2 || 3 || 4 || 5", + "validate-npm-package-license": "^3.0.1" } }, - "rxjs": { - "version": "5.5.7", - "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-5.5.7.tgz", - "integrity": "sha512-Hxo2ac8gRQjwjtKgukMIwBRbq5+KAeEV5hXM4obYBOAghev41bDQWgFH4svYiU9UnQ5kNww2LgfyBdevCd2HXA==", + "normalize-path": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-3.0.0.tgz", + "integrity": "sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==", + "dev": true + }, + "npm-run-path": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/npm-run-path/-/npm-run-path-2.0.2.tgz", + "integrity": "sha1-NakjLfo11wZ7TLLd8jV7GHFTbF8=", + "dev": true, "requires": { - "symbol-observable": "1.0.1" + "path-key": "^2.0.0" } }, - "safe-buffer": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz", - "integrity": "sha512-kKvNJn6Mm93gAczWVJg7wH+wGYWNrDHdWvpUmHyEsgCtIwwo3bqPtV4tR5tuPaUhTOo/kvhVwd8XwwOllGYkbg==" + "number-is-nan": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/number-is-nan/-/number-is-nan-1.0.1.tgz", + "integrity": "sha1-CXtgK1NCKlIsGvuHkDGDNpQaAR0=" }, - "safe-regex": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/safe-regex/-/safe-regex-1.1.0.tgz", - "integrity": "sha1-QKNmnzsHfR6UPURinhV91IAjvy4=", - "dev": true, + "number-to-bn": { + "version": "1.7.0", + "resolved": "https://registry.npmjs.org/number-to-bn/-/number-to-bn-1.7.0.tgz", + "integrity": "sha1-uzYjWS9+X54AMLGXe9QaDFP+HqA=", "requires": { - "ret": "~0.1.10" + "bn.js": "4.11.6", + "strip-hex-prefix": "1.0.0" + }, + "dependencies": { + "bn.js": { + "version": "4.11.6", + "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.11.6.tgz", + "integrity": "sha1-UzRK2xRhehP26N0s4okF0cC6MhU=" + } } }, - "scoped-regex": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/scoped-regex/-/scoped-regex-1.0.0.tgz", - "integrity": "sha1-o0a7Gs1CB65wvXwMfKnlZra63bg=" + "oauth-sign": { + "version": "0.9.0", + "resolved": "https://registry.npmjs.org/oauth-sign/-/oauth-sign-0.9.0.tgz", + "integrity": "sha512-fexhUFFPTGV8ybAtSIGbV6gOkSv8UtRbDBnAyLQw4QPKkgNlsH2ByPGtMUqdWkos6YCRmAqViwgZrJc/mRDzZQ==", + "dev": true }, - "semver": { - "version": "5.5.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.5.0.tgz", - "integrity": "sha512-4SJ3dm0WAwWy/NVeioZh5AntkdJoWKxHxcmyP622fOkgHa4z3R0TdBJICINyaSDE6uNwVc8gZr+ZinwZAH4xIA==" + "object-assign": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", + "integrity": "sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM=" }, - "semver-diff": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/semver-diff/-/semver-diff-2.1.0.tgz", - "integrity": "sha1-S7uEN8jTfksM8aaP1ybsbWRdbTY=", + "object-copy": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/object-copy/-/object-copy-0.1.0.tgz", + "integrity": "sha1-fn2Fi3gb18mRpBupde04EnVOmYw=", "dev": true, "requires": { - "semver": "^5.0.3" - } - }, - "send": { - "version": "0.16.2", - "resolved": "https://registry.npmjs.org/send/-/send-0.16.2.tgz", - "integrity": "sha512-E64YFPUssFHEFBvpbbjr44NCLtI1AohxQ8ZSiJjQLskAdKuriYEP6VyGEsRDH8ScozGpkaX1BGvhanqCwkcEZw==", - "requires": { - "debug": "2.6.9", - "depd": "~1.1.2", - "destroy": "~1.0.4", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "etag": "~1.8.1", - "fresh": "0.5.2", - "http-errors": "~1.6.2", - "mime": "1.4.1", - "ms": "2.0.0", - "on-finished": "~2.3.0", - "range-parser": "~1.2.0", - "statuses": "~1.4.0" + "copy-descriptor": "^0.1.0", + "define-property": "^0.2.5", + "kind-of": "^3.0.3" }, "dependencies": { - "debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "dev": true, "requires": { - "ms": "2.0.0" + "is-descriptor": "^0.1.0" } }, - "statuses": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.4.0.tgz", - "integrity": "sha512-zhSCtt8v2NDrRlPQpCNtw/heZLtfUDqxBM1udqikb/Hbk52LK4nQSwr10u77iopCW5LsyHpuXS0GnEc48mLeew==" + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, + "requires": { + "is-buffer": "^1.1.5" + } } } }, - "serve-static": { - "version": "1.13.2", - "resolved": "https://registry.npmjs.org/serve-static/-/serve-static-1.13.2.tgz", - "integrity": "sha512-p/tdJrO4U387R9oMjb1oj7qSMaMfmOyd4j9hOFoxZe2baQszgHcSWjuya/CiT5kgZZKRudHNOA0pYXOl8rQ5nw==", + "object-visit": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/object-visit/-/object-visit-1.0.1.tgz", + "integrity": "sha1-95xEk68MU3e1n+OdOV5BBC3QRbs=", + "dev": true, + "requires": { + "isobject": "^3.0.0" + } + }, + "object.pick": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/object.pick/-/object.pick-1.3.0.tgz", + "integrity": "sha1-h6EKxMFpS9Lhy/U1kaZhQftd10c=", + "dev": true, "requires": { - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "parseurl": "~1.3.2", - "send": "0.16.2" + "isobject": "^3.0.1" } }, - "servify": { - "version": "0.1.12", - "resolved": "https://registry.npmjs.org/servify/-/servify-0.1.12.tgz", - "integrity": "sha512-/xE6GvsKKqyo1BAY+KxOWXcLpPsUUyji7Qg3bVD7hh1eRze5bR1uYiuDA/k3Gof1s9BTzQZEJK8sNcNGFIzeWw==", + "once": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", + "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", "requires": { - "body-parser": "^1.16.0", - "cors": "^2.8.1", - "express": "^4.14.0", - "request": "^2.79.0", - "xhr": "^2.3.3" + "wrappy": "1" } }, - "set-blocking": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/set-blocking/-/set-blocking-2.0.0.tgz", - "integrity": "sha1-BF+XgtARrppoA93TgrJDkrPYkPc=" - }, - "set-immediate-shim": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/set-immediate-shim/-/set-immediate-shim-1.0.1.tgz", - "integrity": "sha1-SysbJ+uAip+NzEgaWOXlb1mfP2E=", - "dev": true + "openzeppelin-solidity": { + "version": "1.12.0", + "resolved": "https://registry.npmjs.org/openzeppelin-solidity/-/openzeppelin-solidity-1.12.0.tgz", + "integrity": "sha512-WlorzMXIIurugiSdw121RVD5qA3EfSI7GybTn+/Du0mPNgairjt29NpVTAaH8eLjAeAwlw46y7uQKy0NYem/gA==" }, - "set-value": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/set-value/-/set-value-2.0.0.tgz", - "integrity": "sha512-hw0yxk9GT/Hr5yJEYnHNKYXkIA8mVJgd9ditYZCe16ZczcaELYYcfvaXesNACk2O8O0nTiPQcQhGUQj8JLzeeg==", + "optimist": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/optimist/-/optimist-0.6.1.tgz", + "integrity": "sha1-2j6nRob6IaGaERwybpDrFaAZZoY=", "dev": true, "requires": { - "extend-shallow": "^2.0.1", - "is-extendable": "^0.1.1", - "is-plain-object": "^2.0.3", - "split-string": "^3.0.1" + "minimist": "~0.0.1", + "wordwrap": "~0.0.2" }, "dependencies": { - "extend-shallow": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", - "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", - "dev": true, - "requires": { - "is-extendable": "^0.1.0" - } + "wordwrap": { + "version": "0.0.3", + "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-0.0.3.tgz", + "integrity": "sha1-o9XabNXAvAAI03I0u68b7WMFkQc=", + "dev": true } } }, - "setprototypeof": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.1.0.tgz", - "integrity": "sha512-BvE/TwpZX4FXExxOxZyRGQQv651MSwmWKZGqvmPcRIjDqWub67kTKuIMx43cZZrS/cBBzwBcNDWoFxt2XEFIpQ==" - }, - "sha1": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/sha1/-/sha1-1.1.1.tgz", - "integrity": "sha1-rdqnqTFo85PxnrKxUJFhjicA+Eg=", + "optionator": { + "version": "0.8.2", + "resolved": "https://registry.npmjs.org/optionator/-/optionator-0.8.2.tgz", + "integrity": "sha1-NkxeQJ0/TWMB1sC0wFu6UBgK62Q=", "dev": true, "requires": { - "charenc": ">= 0.0.1", - "crypt": ">= 0.0.1" + "deep-is": "~0.1.3", + "fast-levenshtein": "~2.0.4", + "levn": "~0.3.0", + "prelude-ls": "~1.1.2", + "type-check": "~0.3.2", + "wordwrap": "~1.0.0" } }, - "sha3": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/sha3/-/sha3-1.2.0.tgz", - "integrity": "sha1-aYnxtwpJhwWHajc+LGKs6WqpOZo=", - "requires": { - "nan": "^2.0.5" - } + "original-require": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/original-require/-/original-require-1.0.1.tgz", + "integrity": "sha1-DxMEcVhM0zURxew4yNWSE/msXiA=" }, - "shebang-command": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-1.2.0.tgz", - "integrity": "sha1-RKrGW2lbAzmJaMOfNj/uXer98eo=", + "os-locale": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/os-locale/-/os-locale-1.4.0.tgz", + "integrity": "sha1-IPnxeuKe00XoveWDsT0gCYA8FNk=", "requires": { - "shebang-regex": "^1.0.0" + "lcid": "^1.0.0" } }, - "shebang-regex": { + "p-finally": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-1.0.0.tgz", - "integrity": "sha1-2kL0l0DAtC2yypcoVxyxkMmO/qM=" + "resolved": "https://registry.npmjs.org/p-finally/-/p-finally-1.0.0.tgz", + "integrity": "sha1-P7z7FbiZpEEjs0ttzBi3JDNqLK4=", + "dev": true }, - "shelljs": { - "version": "0.8.1", - "resolved": "https://registry.npmjs.org/shelljs/-/shelljs-0.8.1.tgz", - "integrity": "sha512-YA/iYtZpzFe5HyWVGrb02FjPxc4EMCfpoU/Phg9fQoyMC72u9598OUBrsU8IrtwAKG0tO8IYaqbaLIw+k3IRGA==", + "p-limit": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-1.3.0.tgz", + "integrity": "sha512-vvcXsLAJ9Dr5rQOPk7toZQZJApBl2K4J6dANSsEuh6QI41JYcsS/qhTGa9ErIUUgK3WNQoJYvylxvjqmiqEA9Q==", + "dev": true, "requires": { - "glob": "^7.0.0", - "interpret": "^1.0.0", - "rechoir": "^0.6.2" + "p-try": "^1.0.0" } }, - "sigmund": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/sigmund/-/sigmund-1.0.1.tgz", - "integrity": "sha1-P/IfGYytIXX587eBhT/ZTQ0ZtZA=", - "dev": true - }, - "signal-exit": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.2.tgz", - "integrity": "sha1-tf3AjxKH6hF4Yo5BXiUTK3NkbG0=" - }, - "simple-concat": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/simple-concat/-/simple-concat-1.0.0.tgz", - "integrity": "sha1-c0TLuLbib7J9ZrL8hvn21Zl1IcY=" - }, - "simple-get": { - "version": "2.7.0", - "resolved": "https://registry.npmjs.org/simple-get/-/simple-get-2.7.0.tgz", - "integrity": "sha512-RkE9rGPHcxYZ/baYmgJtOSM63vH0Vyq+ma5TijBcLla41SWlh8t6XYIGMR/oeZcmr+/G8k+zrClkkVrtnQ0esg==", + "p-locate": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-2.0.0.tgz", + "integrity": "sha1-IKAQOyIqcMj9OcwuWAaA893l7EM=", + "dev": true, "requires": { - "decompress-response": "^3.3.0", - "once": "^1.3.1", - "simple-concat": "^1.0.0" + "p-limit": "^1.1.0" } }, - "slash": { + "p-try": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/slash/-/slash-1.0.0.tgz", - "integrity": "sha1-xB8vbDn8FtHNF61LXYlhFK5HDVU=" - }, - "slice-ansi": { - "version": "0.0.4", - "resolved": "https://registry.npmjs.org/slice-ansi/-/slice-ansi-0.0.4.tgz", - "integrity": "sha1-7b+JA/ZvfOL46v1s7tZeJkyDGzU=" - }, - "slide": { - "version": "1.1.6", - "resolved": "https://registry.npmjs.org/slide/-/slide-1.1.6.tgz", - "integrity": "sha1-VusCfWW00tzmyy4tMsTUr8nh1wc=" + "resolved": "https://registry.npmjs.org/p-try/-/p-try-1.0.0.tgz", + "integrity": "sha1-y8ec26+P1CKOE/Yh8rGiN8GyB7M=", + "dev": true }, - "snapdragon": { - "version": "0.8.2", - "resolved": "https://registry.npmjs.org/snapdragon/-/snapdragon-0.8.2.tgz", - "integrity": "sha512-FtyOnWN/wCHTVXOMwvSv26d+ko5vWlIDD6zoUJ7LW8vh+ZBC8QdljveRP+crNrtBwioEUWy/4dMtbBjA4ioNlg==", + "package-json": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/package-json/-/package-json-4.0.1.tgz", + "integrity": "sha1-iGmgQBJTZhxMTKPabCEh7VVfXu0=", "dev": true, "requires": { - "base": "^0.11.1", - "debug": "^2.2.0", - "define-property": "^0.2.5", - "extend-shallow": "^2.0.1", - "map-cache": "^0.2.2", - "source-map": "^0.5.6", - "source-map-resolve": "^0.5.0", - "use": "^3.1.0" - }, - "dependencies": { - "define-property": { - "version": "0.2.5", - "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", - "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", - "dev": true, - "requires": { - "is-descriptor": "^0.1.0" - } - }, - "extend-shallow": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", - "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", - "dev": true, - "requires": { - "is-extendable": "^0.1.0" - } - } + "got": "^6.7.1", + "registry-auth-token": "^3.0.1", + "registry-url": "^3.0.3", + "semver": "^5.1.0" } }, - "snapdragon-node": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/snapdragon-node/-/snapdragon-node-2.1.1.tgz", - "integrity": "sha512-O27l4xaMYt/RSQ5TR3vpWCAB5Kb/czIcqUFOM/C4fYcLnbZUc1PkjTAMjof2pBWaSTwOUd6qUHcFGVGj7aIwnw==", - "dev": true, + "parse-cache-control": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/parse-cache-control/-/parse-cache-control-1.0.1.tgz", + "integrity": "sha1-juqz5U+laSD+Fro493+iGqzC104=", + "dev": true + }, + "parse-headers": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/parse-headers/-/parse-headers-2.0.1.tgz", + "integrity": "sha1-aug6eqJanZtwCswoaYzR8e1+lTY=", "requires": { - "define-property": "^1.0.0", - "isobject": "^3.0.0", - "snapdragon-util": "^3.0.1" - }, - "dependencies": { - "define-property": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/define-property/-/define-property-1.0.0.tgz", - "integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=", - "dev": true, - "requires": { - "is-descriptor": "^1.0.0" - } - }, - "is-accessor-descriptor": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz", - "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", - "dev": true, - "requires": { - "kind-of": "^6.0.0" - } - }, - "is-data-descriptor": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz", - "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", - "dev": true, - "requires": { - "kind-of": "^6.0.0" - } - }, - "is-descriptor": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz", - "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", - "dev": true, - "requires": { - "is-accessor-descriptor": "^1.0.0", - "is-data-descriptor": "^1.0.0", - "kind-of": "^6.0.2" - } - } + "for-each": "^0.3.2", + "trim": "0.0.1" } }, - "snapdragon-util": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/snapdragon-util/-/snapdragon-util-3.0.1.tgz", - "integrity": "sha512-mbKkMdQKsjX4BAL4bRYTj21edOf8cN7XHdYUJEe+Zn99hVEYcMvKPct1IqNe7+AZPirn8BCDOQBHQZknqmKlZQ==", - "dev": true, + "parse-json": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-2.2.0.tgz", + "integrity": "sha1-9ID0BDTvgHQfhGkJn43qGPVaTck=", "requires": { - "kind-of": "^3.2.0" - }, - "dependencies": { - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", - "dev": true, - "requires": { - "is-buffer": "^1.1.5" - } - } + "error-ex": "^1.2.0" } }, - "sntp": { + "pascalcase": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/pascalcase/-/pascalcase-0.1.1.tgz", + "integrity": "sha1-s2PlXoAGym/iF4TS2yK9FdeRfxQ=", + "dev": true + }, + "path-dirname": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/path-dirname/-/path-dirname-1.0.2.tgz", + "integrity": "sha1-zDPSTVJeCZpTiMAzbG4yuRYGCeA=", + "dev": true + }, + "path-exists": { "version": "2.1.0", - "resolved": "https://registry.npmjs.org/sntp/-/sntp-2.1.0.tgz", - "integrity": "sha512-FL1b58BDrqS3A11lJ0zEdnJ3UOKqVxawAkF3k7F0CVN7VQ34aZrV+G8BZ1WC9ZL7NyrwsW0oviwsWDgRuVYtJg==", + "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-2.1.0.tgz", + "integrity": "sha1-D+tsZPD8UY2adU3V77YscCJ2H0s=", "requires": { - "hoek": "4.x.x" + "pinkie-promise": "^2.0.0" } }, - "sol-explore": { - "version": "1.6.2", - "resolved": "https://registry.npmjs.org/sol-explore/-/sol-explore-1.6.2.tgz", - "integrity": "sha1-Q66MQZ/TrAVqBfip0fsQIs1B7MI=", + "path-is-absolute": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", + "integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=" + }, + "path-is-inside": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/path-is-inside/-/path-is-inside-1.0.2.tgz", + "integrity": "sha1-NlQX3t5EQw0cEa9hAn+s8HS9/FM=", "dev": true }, - "solc": { - "version": "0.4.24", - "resolved": "https://registry.npmjs.org/solc/-/solc-0.4.24.tgz", - "integrity": "sha512-2xd7Cf1HeVwrIb6Bu1cwY2/TaLRodrppCq3l7rhLimFQgmxptXhTC3+/wesVLpB09F1A2kZgvbMOgH7wvhFnBQ==", - "requires": { - "fs-extra": "^0.30.0", - "memorystream": "^0.3.1", - "require-from-string": "^1.1.0", - "semver": "^5.3.0", - "yargs": "^4.7.1" - } + "path-key": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/path-key/-/path-key-2.0.1.tgz", + "integrity": "sha1-QRyttXTFoUDTpLGRDUDYDMn0C0A=", + "dev": true }, - "solidity-coverage": { - "version": "0.4.15", - "resolved": "https://registry.npmjs.org/solidity-coverage/-/solidity-coverage-0.4.15.tgz", - "integrity": "sha512-iA3MT20rh1LllcNwfxAKU3ZBDu8R/4K8jANJAk7BcJU1foOjEh3tYhGqL8w2kRJPIo5XtoW0wxyVt95X2eJk/A==", - "dev": true, + "path-parse": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.6.tgz", + "integrity": "sha512-GSmOT2EbHrINBf9SR7CDELwlJ8AENk3Qn7OikK4nFYAu3Ote2+JYNVvkpAEQm3/TLNEJFD/xZJjzyxg3KBWOzw==" + }, + "path-type": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/path-type/-/path-type-1.1.0.tgz", + "integrity": "sha1-WcRPfuSR2nBNpBXaWkBwuk+P5EE=", "requires": { - "death": "^1.1.0", - "ethereumjs-testrpc-sc": "6.1.2", - "istanbul": "^0.4.5", - "keccakjs": "^0.2.1", - "req-cwd": "^1.0.1", - "shelljs": "^0.7.4", - "sol-explore": "^1.6.2", - "solidity-parser-sc": "0.4.7", - "web3": "^0.18.4" - }, - "dependencies": { - "bignumber.js": { - "version": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", - "from": "bignumber.js@git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", - "dev": true - }, - "commander": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-2.3.0.tgz", - "integrity": "sha1-/UMOiJgy7DU7ms0d4hfBHLPu+HM=", - "dev": true - }, - "debug": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.2.0.tgz", - "integrity": "sha1-+HBX6ZWxofauaklgZkE3vFbwOdo=", - "dev": true, - "requires": { - "ms": "0.7.1" - } - }, - "diff": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/diff/-/diff-1.4.0.tgz", - "integrity": "sha1-fyjS657nsVqX79ic5j3P2qPMur8=", - "dev": true - }, - "escape-string-regexp": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.2.tgz", - "integrity": "sha1-Tbwv5nTnGUnK8/smlc5/LcHZqNE=", - "dev": true - }, - "minimatch": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-0.3.0.tgz", - "integrity": "sha1-J12O2qxPG7MyZHIInnlJyDlGmd0=", - "dev": true, - "requires": { - "lru-cache": "2", - "sigmund": "~1.0.0" - } - }, - "mocha": { - "version": "2.5.3", - "resolved": "https://registry.npmjs.org/mocha/-/mocha-2.5.3.tgz", - "integrity": "sha1-FhvlvetJZ3HrmzV0UFC2IrWu/Fg=", - "dev": true, - "requires": { - "commander": "2.3.0", - "debug": "2.2.0", - "diff": "1.4.0", - "escape-string-regexp": "1.0.2", - "glob": "3.2.11", - "growl": "1.9.2", - "jade": "0.26.3", - "mkdirp": "0.5.1", - "supports-color": "1.2.0", - "to-iso-string": "0.0.2" - }, - "dependencies": { - "glob": { - "version": "3.2.11", - "resolved": "https://registry.npmjs.org/glob/-/glob-3.2.11.tgz", - "integrity": "sha1-Spc/Y1uRkPcV0QmH1cAP0oFevj0=", - "dev": true, - "requires": { - "inherits": "2", - "minimatch": "0.3" - } - } - } - }, - "ms": { - "version": "0.7.1", - "resolved": "https://registry.npmjs.org/ms/-/ms-0.7.1.tgz", - "integrity": "sha1-nNE8A62/8ltl7/3nzoZO6VIBcJg=", - "dev": true - }, - "shelljs": { - "version": "0.7.8", - "resolved": "https://registry.npmjs.org/shelljs/-/shelljs-0.7.8.tgz", - "integrity": "sha1-3svPh0sNHl+3LhSxZKloMEjprLM=", - "dev": true, - "requires": { - "glob": "^7.0.0", - "interpret": "^1.0.0", - "rechoir": "^0.6.2" - } - }, - "solidity-parser-sc": { - "version": "0.4.7", - "resolved": "https://registry.npmjs.org/solidity-parser-sc/-/solidity-parser-sc-0.4.7.tgz", - "integrity": "sha512-wbX2806sm6thZME1aniqLcLH9HYwNwuKke6aw/FEgupCvoT9Iq5PdwuN9OyHWKGBOVeczpM5tCrnRXWNQ04YVw==", - "dev": true, - "requires": { - "mocha": "^2.4.5", - "pegjs": "^0.10.0", - "yargs": "^4.6.0" - } - }, - "supports-color": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-1.2.0.tgz", - "integrity": "sha1-/x7R5hFp0Gs88tWI4YixjYhH4X4=", - "dev": true - }, - "web3": { - "version": "0.18.4", - "resolved": "https://registry.npmjs.org/web3/-/web3-0.18.4.tgz", - "integrity": "sha1-gewXhBRUkfLqqJVbMcBgSeB8Xn0=", - "dev": true, - "requires": { - "bignumber.js": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", - "crypto-js": "^3.1.4", - "utf8": "^2.1.1", - "xhr2": "*", - "xmlhttprequest": "*" - } - } + "graceful-fs": "^4.1.2", + "pify": "^2.0.0", + "pinkie-promise": "^2.0.0" } }, - "solidity-parser": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/solidity-parser/-/solidity-parser-0.4.0.tgz", - "integrity": "sha1-o0PxPac8kWgyeQNGgOgMSR3jQPo=", - "dev": true, + "pathval": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/pathval/-/pathval-1.1.0.tgz", + "integrity": "sha1-uULm1L3mUwBe9rcTYd74cn0GReA=", + "dev": true + }, + "pegjs": { + "version": "0.10.0", + "resolved": "https://registry.npmjs.org/pegjs/-/pegjs-0.10.0.tgz", + "integrity": "sha1-z4uvrm7d/0tafvsYUmnqr0YQ3b0=", + "dev": true + }, + "performance-now": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/performance-now/-/performance-now-2.1.0.tgz", + "integrity": "sha1-Ywn04OX6kT7BxpMHrjZLSzd8nns=", + "dev": true + }, + "pify": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", + "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=" + }, + "pinkie": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/pinkie/-/pinkie-2.0.4.tgz", + "integrity": "sha1-clVrgM+g1IqXToDnckjoDtT3+HA=" + }, + "pinkie-promise": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/pinkie-promise/-/pinkie-promise-2.0.1.tgz", + "integrity": "sha1-ITXW36ejWMBprJsXh3YogihFD/o=", "requires": { - "mocha": "^2.4.5", - "pegjs": "^0.10.0", - "yargs": "^4.6.0" - }, - "dependencies": { - "commander": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-2.3.0.tgz", - "integrity": "sha1-/UMOiJgy7DU7ms0d4hfBHLPu+HM=", - "dev": true - }, - "debug": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.2.0.tgz", - "integrity": "sha1-+HBX6ZWxofauaklgZkE3vFbwOdo=", - "dev": true, - "requires": { - "ms": "0.7.1" - } - }, - "diff": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/diff/-/diff-1.4.0.tgz", - "integrity": "sha1-fyjS657nsVqX79ic5j3P2qPMur8=", - "dev": true - }, - "escape-string-regexp": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.2.tgz", - "integrity": "sha1-Tbwv5nTnGUnK8/smlc5/LcHZqNE=", - "dev": true - }, - "glob": { - "version": "3.2.11", - "resolved": "https://registry.npmjs.org/glob/-/glob-3.2.11.tgz", - "integrity": "sha1-Spc/Y1uRkPcV0QmH1cAP0oFevj0=", - "dev": true, - "requires": { - "inherits": "2", - "minimatch": "0.3" - } - }, - "minimatch": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-0.3.0.tgz", - "integrity": "sha1-J12O2qxPG7MyZHIInnlJyDlGmd0=", - "dev": true, - "requires": { - "lru-cache": "2", - "sigmund": "~1.0.0" - } - }, - "mocha": { - "version": "2.5.3", - "resolved": "https://registry.npmjs.org/mocha/-/mocha-2.5.3.tgz", - "integrity": "sha1-FhvlvetJZ3HrmzV0UFC2IrWu/Fg=", - "dev": true, - "requires": { - "commander": "2.3.0", - "debug": "2.2.0", - "diff": "1.4.0", - "escape-string-regexp": "1.0.2", - "glob": "3.2.11", - "growl": "1.9.2", - "jade": "0.26.3", - "mkdirp": "0.5.1", - "supports-color": "1.2.0", - "to-iso-string": "0.0.2" - } - }, - "ms": { - "version": "0.7.1", - "resolved": "https://registry.npmjs.org/ms/-/ms-0.7.1.tgz", - "integrity": "sha1-nNE8A62/8ltl7/3nzoZO6VIBcJg=", - "dev": true - }, - "supports-color": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-1.2.0.tgz", - "integrity": "sha1-/x7R5hFp0Gs88tWI4YixjYhH4X4=", - "dev": true - } + "pinkie": "^2.0.0" } }, - "solidity-parser-antlr": { - "version": "0.2.15", - "resolved": "https://registry.npmjs.org/solidity-parser-antlr/-/solidity-parser-antlr-0.2.15.tgz", - "integrity": "sha512-EzRI8/TR/ljTXkZAyAjb0w4G20wH2XM7pcNf87ifdV825AbUv7DkY7HmiZCTj6NeKtIx8Y1s0NZWPbj+JTp8Zw==", + "posix-character-classes": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/posix-character-classes/-/posix-character-classes-0.1.1.tgz", + "integrity": "sha1-AerA/jta9xoqbAL+q7jB/vfgDqs=", "dev": true }, - "sort-keys": { + "prelude-ls": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.1.2.tgz", + "integrity": "sha1-IZMqVJ9eUv/ZqCf1cOBL5iqX2lQ=", + "dev": true + }, + "prepend-http": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/prepend-http/-/prepend-http-1.0.4.tgz", + "integrity": "sha1-1PRWKwzjaW5BrFLQ4ALlemNdxtw=", + "dev": true + }, + "process": { + "version": "0.5.2", + "resolved": "https://registry.npmjs.org/process/-/process-0.5.2.tgz", + "integrity": "sha1-FjjYqONML0QKkduVq5rrZ3/Bhc8=" + }, + "process-nextick-args": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/sort-keys/-/sort-keys-2.0.0.tgz", - "integrity": "sha1-ZYU1WEhh7JfXMNbPQYIuH1ZoQSg=", + "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.0.tgz", + "integrity": "sha512-MtEC1TqN0EU5nephaJ4rAtThHtC86dNN9qCuEhtshvpVBkAW5ZO7BASN9REnF9eoXGcRub+pFuKEpOHE+HbEMw==", + "dev": true + }, + "promise": { + "version": "8.0.2", + "resolved": "https://registry.npmjs.org/promise/-/promise-8.0.2.tgz", + "integrity": "sha512-EIyzM39FpVOMbqgzEHhxdrEhtOSDOtjMZQ0M6iVfCE+kWNgCkAyOdnuCWqfmflylftfadU6FkiMgHZA2kUzwRw==", + "dev": true, "requires": { - "is-plain-obj": "^1.0.0" + "asap": "~2.0.6" } }, - "source-map": { - "version": "0.5.7", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", - "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=" + "pseudomap": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/pseudomap/-/pseudomap-1.0.2.tgz", + "integrity": "sha1-8FKijacOYYkX7wqKw0wa5aaChrM=", + "dev": true }, - "source-map-resolve": { - "version": "0.5.1", - "resolved": "https://registry.npmjs.org/source-map-resolve/-/source-map-resolve-0.5.1.tgz", - "integrity": "sha512-0KW2wvzfxm8NCTb30z0LMNyPqWCdDGE2viwzUaucqJdkTRXtZiSY3I+2A6nVAjmdOy0I4gU8DwnVVGsk9jvP2A==", - "dev": true, + "psl": { + "version": "1.1.31", + "resolved": "https://registry.npmjs.org/psl/-/psl-1.1.31.tgz", + "integrity": "sha512-/6pt4+C+T+wZUieKR620OpzN/LlnNKuWjy1iFLQ/UG35JqHlR/89MP1d96dUfkf6Dne3TuLQzOYEYshJ+Hx8mw==", + "dev": true + }, + "pstree.remy": { + "version": "1.1.6", + "resolved": "https://registry.npmjs.org/pstree.remy/-/pstree.remy-1.1.6.tgz", + "integrity": "sha512-NdF35+QsqD7EgNEI5mkI/X+UwaxVEbQaz9f4IooEmMUv6ZPmlTQYGjBPJGgrlzNdjSvIy4MWMg6Q6vCgBO2K+w==", + "dev": true + }, + "punycode": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.1.1.tgz", + "integrity": "sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A==", + "dev": true + }, + "qs": { + "version": "6.5.2", + "resolved": "https://registry.npmjs.org/qs/-/qs-6.5.2.tgz", + "integrity": "sha512-N5ZAX4/LxJmF+7wN74pUD6qAh9/wnvdQcjq9TZjevvXzSUo7bfmw91saqMjzGS2xq91/odN2dW/WOl7qQHNDGA==", + "dev": true + }, + "query-string": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/query-string/-/query-string-5.1.1.tgz", + "integrity": "sha512-gjWOsm2SoGlgLEdAGt7a6slVOk9mGiXmPFMqrEhLQ68rhQuBnpfs3+EmlvqKyxnCo9/PPlF+9MtY02S1aFg+Jw==", "requires": { - "atob": "^2.0.0", "decode-uri-component": "^0.2.0", - "resolve-url": "^0.2.1", - "source-map-url": "^0.4.0", - "urix": "^0.1.0" + "object-assign": "^4.1.0", + "strict-uri-encode": "^1.0.0" } }, - "source-map-support": { - "version": "0.5.4", - "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.4.tgz", - "integrity": "sha512-PETSPG6BjY1AHs2t64vS2aqAgu6dMIMXJULWFBGbh2Gr8nVLbCFDo6i/RMMvviIQ2h1Z8+5gQhVKSn2je9nmdg==", + "randomhex": { + "version": "0.1.5", + "resolved": "https://registry.npmjs.org/randomhex/-/randomhex-0.1.5.tgz", + "integrity": "sha1-us7vmCMpCRQA8qKRLGzQLxCU9YU=" + }, + "rc": { + "version": "1.2.8", + "resolved": "https://registry.npmjs.org/rc/-/rc-1.2.8.tgz", + "integrity": "sha512-y3bGgqKj3QBdxLbLkomlohkvsA8gdAiUQlSBJnBhfn+BPxg4bc62d8TcBW15wavDfgexCgccckhcZvywyQYPOw==", + "dev": true, "requires": { - "source-map": "^0.6.0" + "deep-extend": "^0.6.0", + "ini": "~1.3.0", + "minimist": "^1.2.0", + "strip-json-comments": "~2.0.1" }, "dependencies": { - "source-map": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", - "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==" + "minimist": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz", + "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=", + "dev": true } } }, - "source-map-url": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/source-map-url/-/source-map-url-0.4.0.tgz", - "integrity": "sha1-PpNdfd1zYxuXZZlW1VEo6HtQhKM=", - "dev": true - }, - "spdx-correct": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/spdx-correct/-/spdx-correct-1.0.2.tgz", - "integrity": "sha1-SzBz2TP/UfORLwOsVRlJikFQ20A=", + "read-pkg": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-1.1.0.tgz", + "integrity": "sha1-9f+qXs0pyzHAR0vKfXVra7KePyg=", "requires": { - "spdx-license-ids": "^1.0.2" + "load-json-file": "^1.0.0", + "normalize-package-data": "^2.3.2", + "path-type": "^1.0.0" } }, - "spdx-expression-parse": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/spdx-expression-parse/-/spdx-expression-parse-1.0.4.tgz", - "integrity": "sha1-m98vIOH0DtRH++JzJmGR/O1RYmw=" - }, - "spdx-license-ids": { - "version": "1.2.2", - "resolved": "https://registry.npmjs.org/spdx-license-ids/-/spdx-license-ids-1.2.2.tgz", - "integrity": "sha1-yd96NCRZSt5r0RkA1ZZpbcBrrFc=" - }, - "split": { - "version": "0.3.3", - "resolved": "https://registry.npmjs.org/split/-/split-0.3.3.tgz", - "integrity": "sha1-zQ7qXmOiEd//frDwkcQTPi0N0o8=", - "dev": true, + "read-pkg-up": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/read-pkg-up/-/read-pkg-up-1.0.1.tgz", + "integrity": "sha1-nWPBMnbAZZGNV/ACpX9AobZD+wI=", "requires": { - "through": "2" + "find-up": "^1.0.0", + "read-pkg": "^1.0.0" } }, - "split-string": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/split-string/-/split-string-3.1.0.tgz", - "integrity": "sha512-NzNVhJDYpwceVVii8/Hu6DKfD2G+NrQHlS/V/qgv763EYudVwEcMQNxd2lh+0VrUByXN/oJkl5grOhYWvQUYiw==", + "readable-stream": { + "version": "2.3.6", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.6.tgz", + "integrity": "sha512-tQtKA9WIAhBF3+VLAseyMqZeBjW0AHJoxOtYqSUZNJxauErmLbVm2FW1y+J/YA9dUrAC39ITejlZWhVIwawkKw==", "dev": true, "requires": { - "extend-shallow": "^3.0.0" + "core-util-is": "~1.0.0", + "inherits": "~2.0.3", + "isarray": "~1.0.0", + "process-nextick-args": "~2.0.0", + "safe-buffer": "~5.1.1", + "string_decoder": "~1.1.1", + "util-deprecate": "~1.0.1" } }, - "sprintf-js": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz", - "integrity": "sha1-BOaSb2YolTVPPdAVIDYzuFcpfiw=", - "dev": true - }, - "sshpk": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/sshpk/-/sshpk-1.14.1.tgz", - "integrity": "sha1-Ew9Zde3a2WPx1W+SuaxsUfqfg+s=", + "readdirp": { + "version": "2.2.1", + "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-2.2.1.tgz", + "integrity": "sha512-1JU/8q+VgFZyxwrJ+SVIOsh+KywWGpds3NTqikiKpDMZWScmAYyKIgqkO+ARvNWJfXeXR1zxz7aHF4u4CyH6vQ==", + "dev": true, "requires": { - "asn1": "~0.2.3", - "assert-plus": "^1.0.0", - "bcrypt-pbkdf": "^1.0.0", - "dashdash": "^1.12.0", - "ecc-jsbn": "~0.1.1", - "getpass": "^0.1.1", - "jsbn": "~0.1.0", - "tweetnacl": "~0.14.0" + "graceful-fs": "^4.1.11", + "micromatch": "^3.1.10", + "readable-stream": "^2.0.2" } }, - "static-extend": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/static-extend/-/static-extend-0.1.2.tgz", - "integrity": "sha1-YICcOcv/VTNyJv1eC1IPNB8ftcY=", + "rechoir": { + "version": "0.6.2", + "resolved": "https://registry.npmjs.org/rechoir/-/rechoir-0.6.2.tgz", + "integrity": "sha1-hSBLVNuoLVdC4oyWdW70OvUOM4Q=", "dev": true, "requires": { - "define-property": "^0.2.5", - "object-copy": "^0.1.0" - }, - "dependencies": { - "define-property": { - "version": "0.2.5", - "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", - "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", - "dev": true, - "requires": { - "is-descriptor": "^0.1.0" - } - } + "resolve": "^1.1.6" } }, - "statuses": { - "version": "1.5.0", - "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.5.0.tgz", - "integrity": "sha1-Fhx9rBd2Wf2YEfQ3cfqZOBR4Yow=" - }, - "stealthy-require": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/stealthy-require/-/stealthy-require-1.1.1.tgz", - "integrity": "sha1-NbCYdbT/SfJqd35QmzCQoyJr8ks=", - "dev": true + "regenerator-runtime": { + "version": "0.12.1", + "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.12.1.tgz", + "integrity": "sha512-odxIc1/vDlo4iZcfXqRYFj0vpXFNoGdKMAUieAlFYO6m/nl5e9KR/beGf41z4a1FI+aQgtjhuaSlDxQ0hmkrHg==" }, - "stream-combiner": { - "version": "0.0.4", - "resolved": "https://registry.npmjs.org/stream-combiner/-/stream-combiner-0.0.4.tgz", - "integrity": "sha1-TV5DPBhSYd3mI8o/RMWGvPXErRQ=", + "regex-not": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/regex-not/-/regex-not-1.0.2.tgz", + "integrity": "sha512-J6SDjUgDxQj5NusnOtdFxDwN/+HWykR8GELwctJ7mdqhcyy1xEc4SRFHUXvxTp661YaVKAjfRLZ9cCqS6tn32A==", "dev": true, "requires": { - "duplexer": "~0.1.1" + "extend-shallow": "^3.0.2", + "safe-regex": "^1.1.0" } }, - "stream-to-observable": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/stream-to-observable/-/stream-to-observable-0.2.0.tgz", - "integrity": "sha1-WdbqOT2HwsDdrBCqDVYbxrpvDhA=", + "registry-auth-token": { + "version": "3.3.2", + "resolved": "https://registry.npmjs.org/registry-auth-token/-/registry-auth-token-3.3.2.tgz", + "integrity": "sha512-JL39c60XlzCVgNrO+qq68FoNb56w/m7JYvGR2jT5iR1xBrUA3Mfx5Twk5rqTThPmQKMWydGmq8oFtDlxfrmxnQ==", + "dev": true, "requires": { - "any-observable": "^0.2.0" + "rc": "^1.1.6", + "safe-buffer": "^5.0.1" } }, - "strict-uri-encode": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/strict-uri-encode/-/strict-uri-encode-1.1.0.tgz", - "integrity": "sha1-J5siXfHVgrH1TmWt3UNS4Y+qBxM=" - }, - "string-template": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/string-template/-/string-template-0.2.1.tgz", - "integrity": "sha1-QpMuWYo1LQH8IuwzZ9nYTuxsmt0=" - }, - "string-width": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz", - "integrity": "sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=", + "registry-url": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/registry-url/-/registry-url-3.1.0.tgz", + "integrity": "sha1-PU74cPc93h138M+aOBQyRE4XSUI=", + "dev": true, "requires": { - "code-point-at": "^1.0.0", - "is-fullwidth-code-point": "^1.0.0", - "strip-ansi": "^3.0.0" + "rc": "^1.0.1" } }, - "string_decoder": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "integrity": "sha512-4AH6Z5fzNNBcH+6XDMfA/BTt87skxqJlO0lAh3Dker5zThcAxG6mKz+iGu308UKoPPQ8Dcqx/4JhujzltRa+hQ==", - "requires": { - "safe-buffer": "~5.1.0" - } + "remove-trailing-separator": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/remove-trailing-separator/-/remove-trailing-separator-1.1.0.tgz", + "integrity": "sha1-wkvOKig62tW8P1jg1IJJuSN52O8=", + "dev": true }, - "stringstream": { - "version": "0.0.5", - "resolved": "https://registry.npmjs.org/stringstream/-/stringstream-0.0.5.tgz", - "integrity": "sha1-TkhM1N5aC7vuGORjB3EKioFiGHg=" + "repeat-element": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/repeat-element/-/repeat-element-1.1.3.tgz", + "integrity": "sha512-ahGq0ZnV5m5XtZLMb+vP76kcAM5nkLqk0lpqAuojSKGgQtn4eRi4ZZGm2olo2zKFH+sMsWaqOCW1dqAnOru72g==", + "dev": true }, - "strip-ansi": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", - "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", - "requires": { - "ansi-regex": "^2.0.0" - } + "repeat-string": { + "version": "1.6.1", + "resolved": "https://registry.npmjs.org/repeat-string/-/repeat-string-1.6.1.tgz", + "integrity": "sha1-jcrkcOHIirwtYA//Sndihtp15jc=", + "dev": true }, - "strip-bom": { + "req-cwd": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-2.0.0.tgz", - "integrity": "sha1-YhmoVhZSBJHzV4i9vxRHqZx+aw4=", + "resolved": "https://registry.npmjs.org/req-cwd/-/req-cwd-2.0.0.tgz", + "integrity": "sha1-1AgrTURZgDZkD7c93qAe1T20nrw=", + "dev": true, "requires": { - "is-utf8": "^0.2.0" + "req-from": "^2.0.0" } }, - "strip-bom-stream": { + "req-from": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/strip-bom-stream/-/strip-bom-stream-2.0.0.tgz", - "integrity": "sha1-+H217yYT9paKpUWr/h7HKLaoKco=", - "requires": { - "first-chunk-stream": "^2.0.0", - "strip-bom": "^2.0.0" - } - }, - "strip-eof": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/strip-eof/-/strip-eof-1.0.0.tgz", - "integrity": "sha1-u0P/VZim6wXYm1n80SnJgzE2Br8=" - }, - "strip-hex-prefix": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/strip-hex-prefix/-/strip-hex-prefix-1.0.0.tgz", - "integrity": "sha1-DF8VX+8RUTczd96du1iNoFUA428=", + "resolved": "https://registry.npmjs.org/req-from/-/req-from-2.0.0.tgz", + "integrity": "sha1-10GI5H+TeW9Kpx327jWuaJ8+DnA=", + "dev": true, "requires": { - "is-hex-prefixed": "1.0.0" + "resolve-from": "^3.0.0" } }, - "strip-json-comments": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", - "integrity": "sha1-PFMZQukIwml8DsNEhYwobHygpgo=", - "dev": true - }, - "supports-color": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-3.1.2.tgz", - "integrity": "sha1-cqJiiU2dQIuVbKBf83su2KbiotU=", + "request": { + "version": "2.88.0", + "resolved": "https://registry.npmjs.org/request/-/request-2.88.0.tgz", + "integrity": "sha512-NAqBSrijGLZdM0WZNsInLJpkJokL72XYjUpnB0iwsRgxh7dB6COrHnTBNwN0E+lHDAJzu7kLAkDeY08z2/A0hg==", "dev": true, "requires": { - "has-flag": "^1.0.0" + "aws-sign2": "~0.7.0", + "aws4": "^1.8.0", + "caseless": "~0.12.0", + "combined-stream": "~1.0.6", + "extend": "~3.0.2", + "forever-agent": "~0.6.1", + "form-data": "~2.3.2", + "har-validator": "~5.1.0", + "http-signature": "~1.2.0", + "is-typedarray": "~1.0.0", + "isstream": "~0.1.2", + "json-stringify-safe": "~5.0.1", + "mime-types": "~2.1.19", + "oauth-sign": "~0.9.0", + "performance-now": "^2.1.0", + "qs": "~6.5.2", + "safe-buffer": "^5.1.2", + "tough-cookie": "~2.4.3", + "tunnel-agent": "^0.6.0", + "uuid": "^3.3.2" } }, - "symbol-observable": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/symbol-observable/-/symbol-observable-1.0.1.tgz", - "integrity": "sha1-g0D8RwLDEi310iKI+IKD9RPT/dQ=" - }, - "sync-request": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/sync-request/-/sync-request-6.0.0.tgz", - "integrity": "sha512-jGNIAlCi9iU4X3Dm4oQnNQshDD3h0/1A7r79LyqjbjUnj69sX6mShAXlhRXgImsfVKtTcnra1jfzabdZvp+Lmw==", + "request-promise-core": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/request-promise-core/-/request-promise-core-1.1.2.tgz", + "integrity": "sha512-UHYyq1MO8GsefGEt7EprS8UrXsm1TxEvFUX1IMTuSLU2Rh7fTIdFtl8xD7JiEYiWU2dl+NYAjCTksTehQUxPag==", "dev": true, "requires": { - "http-response-object": "^3.0.1", - "sync-rpc": "^1.2.1", - "then-request": "^6.0.0" + "lodash": "^4.17.11" } }, - "sync-rpc": { - "version": "1.3.4", - "resolved": "https://registry.npmjs.org/sync-rpc/-/sync-rpc-1.3.4.tgz", - "integrity": "sha512-Iug+t1ICVFenUcTnDu8WXFnT+k8IVoLKGh8VA3eXUtl2Rt9SjKX3YEv33OenABqpTPL9QEaHv1+CNn2LK8vMow==", + "request-promise-native": { + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/request-promise-native/-/request-promise-native-1.0.7.tgz", + "integrity": "sha512-rIMnbBdgNViL37nZ1b3L/VfPOpSi0TqVDQPAvO6U14lMzOLrt5nilxCQqtDKhZeDiW0/hkCXGoQjhgJd/tCh6w==", "dev": true, "requires": { - "get-port": "^3.1.0" + "request-promise-core": "1.1.2", + "stealthy-require": "^1.1.1", + "tough-cookie": "^2.3.3" } }, - "tapable": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/tapable/-/tapable-1.0.0.tgz", - "integrity": "sha512-dQRhbNQkRnaqauC7WqSJ21EEksgT0fYZX2lqXzGkpo8JNig9zGZTYoMGvyI2nWmXlE2VSVXVDu7wLVGu/mQEsg==" + "require-directory": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/require-directory/-/require-directory-2.1.1.tgz", + "integrity": "sha1-jGStX9MNqxyXbiNE/+f3kqam30I=" }, - "temp": { - "version": "0.8.3", - "resolved": "https://registry.npmjs.org/temp/-/temp-0.8.3.tgz", - "integrity": "sha1-4Ma8TSa5AxJEEOT+2BEDAU38H1k=", - "requires": { - "os-tmpdir": "^1.0.0", - "rimraf": "~2.2.6" - }, - "dependencies": { - "rimraf": { - "version": "2.2.8", - "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.2.8.tgz", - "integrity": "sha1-5Dm+Kq7jJzIZUnMPmaiSnk/FBYI=" - } - } + "require-from-string": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/require-from-string/-/require-from-string-1.2.1.tgz", + "integrity": "sha1-UpyczvJzgK3+yaL5ZbZJu+5jZBg=" }, - "term-size": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/term-size/-/term-size-1.2.0.tgz", - "integrity": "sha1-RYuDiH8oj8Vtb/+/rSYuJmOO+mk=", - "dev": true, + "require-main-filename": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/require-main-filename/-/require-main-filename-1.0.1.tgz", + "integrity": "sha1-l/cXtp1IeE9fUmpsWqj/3aBVpNE=" + }, + "resolve": { + "version": "1.10.0", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.10.0.tgz", + "integrity": "sha512-3sUr9aq5OfSg2S9pNtPA9hL1FVEAjvfOC4leW0SNf/mpnaakz2a9femSd6LqAww2RaFctwyf1lCqnTHuF1rxDg==", "requires": { - "execa": "^0.7.0" + "path-parse": "^1.0.6" } }, - "text-table": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/text-table/-/text-table-0.2.0.tgz", - "integrity": "sha1-f17oI66AUgfACvLfSoTsP8+lcLQ=" + "resolve-from": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-3.0.0.tgz", + "integrity": "sha1-six699nWiBvItuZTM17rywoYh0g=", + "dev": true + }, + "resolve-url": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/resolve-url/-/resolve-url-0.2.1.tgz", + "integrity": "sha1-LGN/53yJOv0qZj/iGqkIAGjiBSo=", + "dev": true }, - "textextensions": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/textextensions/-/textextensions-2.2.0.tgz", - "integrity": "sha512-j5EMxnryTvKxwH2Cq+Pb43tsf6sdEgw6Pdwxk83mPaq0ToeFJt6WE4J3s5BqY7vmjlLgkgXvhtXUxo80FyBhCA==" + "ret": { + "version": "0.1.15", + "resolved": "https://registry.npmjs.org/ret/-/ret-0.1.15.tgz", + "integrity": "sha512-TTlYpa+OL+vMMNG24xSlQGEJ3B/RzEfUlLct7b5G/ytav+wPrplCpVMFuwzXbkecJrb6IYo1iFb0S9v37754mg==", + "dev": true }, - "then-request": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/then-request/-/then-request-6.0.0.tgz", - "integrity": "sha512-xA+7uEMc+jsQIoyySJ93Ad08Kuqnik7u6jLS5hR91Z3smAoCfL3M8/MqMlobAa9gzBfO9pA88A/AntfepkkMJQ==", - "dev": true, + "rimraf": { + "version": "2.6.3", + "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.6.3.tgz", + "integrity": "sha512-mwqeW5XsA2qAejG46gYdENaxXjx9onRNCfn7L0duuP4hCuTIi/QO7PDK07KJfp1d+izWPrzEJDcSqBa0OZQriA==", "requires": { - "@types/concat-stream": "^1.6.0", - "@types/form-data": "0.0.33", - "@types/node": "^8.0.0", - "@types/qs": "^6.2.31", - "caseless": "~0.12.0", - "concat-stream": "^1.6.0", - "form-data": "^2.2.0", - "http-basic": "^7.0.0", - "http-response-object": "^3.0.1", - "promise": "^8.0.0", - "qs": "^6.4.0" + "glob": "^7.1.3" }, "dependencies": { - "@types/node": { - "version": "8.10.36", - "resolved": "https://registry.npmjs.org/@types/node/-/node-8.10.36.tgz", - "integrity": "sha512-SL6KhfM7PTqiFmbCW3eVNwVBZ+88Mrzbuvn9olPsfv43mbiWaFY+nRcz/TGGku0/lc2FepdMbImdMY1JrQ+zbw==", - "dev": true + "glob": { + "version": "7.1.3", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.3.tgz", + "integrity": "sha512-vcfuiIxogLV4DlGBHIUOwI0IbrJ8HWPc4MU7HzviGeNho/UJDfi6B5p3sHeWIQ0KGIU0Jpxi5ZHxemQfLkkAwQ==", + "requires": { + "fs.realpath": "^1.0.0", + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "^3.0.4", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" + } } } }, - "through": { - "version": "2.3.8", - "resolved": "https://registry.npmjs.org/through/-/through-2.3.8.tgz", - "integrity": "sha1-DdTJ/6q8NXlgsbckEV1+Doai4fU=" + "safe-buffer": { + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", + "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", + "dev": true }, - "through2": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/through2/-/through2-2.0.3.tgz", - "integrity": "sha1-AARWmzfHx0ujnEPzzteNGtlBQL4=", + "safe-regex": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/safe-regex/-/safe-regex-1.1.0.tgz", + "integrity": "sha1-QKNmnzsHfR6UPURinhV91IAjvy4=", + "dev": true, "requires": { - "readable-stream": "^2.1.5", - "xtend": "~4.0.1" + "ret": "~0.1.10" } }, - "timed-out": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/timed-out/-/timed-out-4.0.1.tgz", - "integrity": "sha1-8y6srFoXW+ol1/q1Zas+2HQe9W8=" + "safer-buffer": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", + "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==", + "dev": true }, - "tmp": { - "version": "0.0.33", - "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.0.33.tgz", - "integrity": "sha512-jRCJlojKnZ3addtTOjdIqoRuPEKBvNXcGYqzO6zWZX8KfKEpnGY5jfggJQ3EjKuu8D4bJRr0y+cYJFmYbImXGw==", + "semver": { + "version": "5.6.0", + "resolved": "https://registry.npmjs.org/semver/-/semver-5.6.0.tgz", + "integrity": "sha512-RS9R6R35NYgQn++fkDWaOmqGoj4Ek9gGs+DPxNUZKuwE183xjJroKvyo1IzVFeXvUrvmALy6FWD5xrdJT25gMg==" + }, + "semver-diff": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/semver-diff/-/semver-diff-2.1.0.tgz", + "integrity": "sha1-S7uEN8jTfksM8aaP1ybsbWRdbTY=", + "dev": true, "requires": { - "os-tmpdir": "~1.0.2" + "semver": "^5.0.3" } }, - "to-fast-properties": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/to-fast-properties/-/to-fast-properties-1.0.3.tgz", - "integrity": "sha1-uDVx+k2MJbguIxsG46MFXeTKGkc=" - }, - "to-iso-string": { - "version": "0.0.2", - "resolved": "https://registry.npmjs.org/to-iso-string/-/to-iso-string-0.0.2.tgz", - "integrity": "sha1-TcGeZk38y+Jb2NtQiwDG2hWCVdE=", - "dev": true + "set-blocking": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/set-blocking/-/set-blocking-2.0.0.tgz", + "integrity": "sha1-BF+XgtARrppoA93TgrJDkrPYkPc=" }, - "to-object-path": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/to-object-path/-/to-object-path-0.3.0.tgz", - "integrity": "sha1-KXWIt7Dn4KwI4E5nL4XB9JmeF68=", + "set-value": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/set-value/-/set-value-2.0.0.tgz", + "integrity": "sha512-hw0yxk9GT/Hr5yJEYnHNKYXkIA8mVJgd9ditYZCe16ZczcaELYYcfvaXesNACk2O8O0nTiPQcQhGUQj8JLzeeg==", "dev": true, "requires": { - "kind-of": "^3.0.2" + "extend-shallow": "^2.0.1", + "is-extendable": "^0.1.1", + "is-plain-object": "^2.0.3", + "split-string": "^3.0.1" }, "dependencies": { - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", "dev": true, "requires": { - "is-buffer": "^1.1.5" + "is-extendable": "^0.1.0" } } } }, - "to-regex": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/to-regex/-/to-regex-3.0.2.tgz", - "integrity": "sha512-FWtleNAtZ/Ki2qtqej2CXTOayOH9bHDQF+Q48VpWyDXjbYxA4Yz8iDB31zXOBUlOHHKidDbqGVrTUvQMPmBGBw==", + "sha1": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/sha1/-/sha1-1.1.1.tgz", + "integrity": "sha1-rdqnqTFo85PxnrKxUJFhjicA+Eg=", "dev": true, "requires": { - "define-property": "^2.0.2", - "extend-shallow": "^3.0.2", - "regex-not": "^1.0.2", - "safe-regex": "^1.1.0" + "charenc": ">= 0.0.1", + "crypt": ">= 0.0.1" } }, - "to-regex-range": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-2.1.1.tgz", - "integrity": "sha1-fIDBe53+vlmeJzZ+DU3VWQFB2zg=", + "sha3": { + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/sha3/-/sha3-1.2.2.tgz", + "integrity": "sha1-pmxQmN5MJbyIM27ItIF9AFvKe6k=", "dev": true, "requires": { - "is-number": "^3.0.0", - "repeat-string": "^1.6.1" + "nan": "2.10.0" + }, + "dependencies": { + "nan": { + "version": "2.10.0", + "resolved": "https://registry.npmjs.org/nan/-/nan-2.10.0.tgz", + "integrity": "sha512-bAdJv7fBLhWC+/Bls0Oza+mvTaNQtP+1RyhhhvD95pgUJz6XM5IzgmxOkItJ9tkoCiplvAnXI1tNmmUD/eScyA==", + "dev": true + } } }, - "touch": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/touch/-/touch-3.1.0.tgz", - "integrity": "sha512-WBx8Uy5TLtOSRtIq+M03/sKDrXCLHxwDcquSP2c43Le03/9serjQBIztjRz6FkJez9D/hleyAXTBGLwwZUw9lA==", + "shebang-command": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-1.2.0.tgz", + "integrity": "sha1-RKrGW2lbAzmJaMOfNj/uXer98eo=", "dev": true, "requires": { - "nopt": "~1.0.10" + "shebang-regex": "^1.0.0" } }, - "tough-cookie": { - "version": "2.3.4", - "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.3.4.tgz", - "integrity": "sha512-TZ6TTfI5NtZnuyy/Kecv+CnoROnyXn2DN97LontgQpCwsX2XyLYCC0ENhYkehSOwAp8rTQKc/NUIF7BkQ5rKLA==", + "shebang-regex": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-1.0.0.tgz", + "integrity": "sha1-2kL0l0DAtC2yypcoVxyxkMmO/qM=", + "dev": true + }, + "shelljs": { + "version": "0.7.8", + "resolved": "https://registry.npmjs.org/shelljs/-/shelljs-0.7.8.tgz", + "integrity": "sha1-3svPh0sNHl+3LhSxZKloMEjprLM=", + "dev": true, "requires": { - "punycode": "^1.4.1" + "glob": "^7.0.0", + "interpret": "^1.0.0", + "rechoir": "^0.6.2" } }, - "trim": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/trim/-/trim-0.0.1.tgz", - "integrity": "sha1-WFhUf2spB1fulczMZm+1AITEYN0=" + "signal-exit": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.2.tgz", + "integrity": "sha1-tf3AjxKH6hF4Yo5BXiUTK3NkbG0=", + "dev": true }, - "trim-right": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/trim-right/-/trim-right-1.0.1.tgz", - "integrity": "sha1-yy4SAwZ+DI3h9hQJS5/kVwTqYAM=" + "simple-concat": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/simple-concat/-/simple-concat-1.0.0.tgz", + "integrity": "sha1-c0TLuLbib7J9ZrL8hvn21Zl1IcY=" }, - "truffle": { - "version": "4.1.11", - "resolved": "https://registry.npmjs.org/truffle/-/truffle-4.1.11.tgz", - "integrity": "sha512-VNhc6jexZeM92sNJJr4U8ln3uJ/mJEQO/0y9ZLYc4pccyIskPtl+3r4mzymgGM/Mq5v6MpoQVD6NZgHUVKX+Dw==", + "simple-get": { + "version": "2.8.1", + "resolved": "https://registry.npmjs.org/simple-get/-/simple-get-2.8.1.tgz", + "integrity": "sha512-lSSHRSw3mQNUGPAYRqo7xy9dhKmxFXIjLjp4KHpf99GEH2VH7C3AM+Qfx6du6jhfUi6Vm7XnbEVEf7Wb6N8jRw==", "requires": { - "mocha": "^4.1.0", - "original-require": "^1.0.1", - "solc": "0.4.24" + "decompress-response": "^3.3.0", + "once": "^1.3.1", + "simple-concat": "^1.0.0" } }, - "truffle-blockchain-utils": { - "version": "0.0.4", - "resolved": "https://registry.npmjs.org/truffle-blockchain-utils/-/truffle-blockchain-utils-0.0.4.tgz", - "integrity": "sha512-wgRrhwqh0aea08Hz28hUV4tuF2uTVQH/e9kBou+WK04cqrutB5cxQVQ6HGjeZLltxBYOFvhrGOOq4l3WJFnPEA==", - "dev": true + "snapdragon": { + "version": "0.8.2", + "resolved": "https://registry.npmjs.org/snapdragon/-/snapdragon-0.8.2.tgz", + "integrity": "sha512-FtyOnWN/wCHTVXOMwvSv26d+ko5vWlIDD6zoUJ7LW8vh+ZBC8QdljveRP+crNrtBwioEUWy/4dMtbBjA4ioNlg==", + "dev": true, + "requires": { + "base": "^0.11.1", + "debug": "^2.2.0", + "define-property": "^0.2.5", + "extend-shallow": "^2.0.1", + "map-cache": "^0.2.2", + "source-map": "^0.5.6", + "source-map-resolve": "^0.5.0", + "use": "^3.1.0" + }, + "dependencies": { + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, + "requires": { + "ms": "2.0.0" + } + }, + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", + "dev": true, + "requires": { + "is-descriptor": "^0.1.0" + } + }, + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "dev": true, + "requires": { + "is-extendable": "^0.1.0" + } + } + } }, - "truffle-config": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/truffle-config/-/truffle-config-1.0.4.tgz", - "integrity": "sha512-E8pvJNAIjs7LNsjkYeS2dgoOnLoSBrTwb1xF5lJwfvZmGMFpKvVL1sa5jpFxozpf/WkRn/rfxy8zTdb3pq16jA==", + "snapdragon-node": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/snapdragon-node/-/snapdragon-node-2.1.1.tgz", + "integrity": "sha512-O27l4xaMYt/RSQ5TR3vpWCAB5Kb/czIcqUFOM/C4fYcLnbZUc1PkjTAMjof2pBWaSTwOUd6qUHcFGVGj7aIwnw==", "dev": true, "requires": { - "find-up": "^2.1.0", - "lodash": "^4.17.4", - "original-require": "^1.0.0", - "truffle-error": "^0.0.2", - "truffle-provider": "^0.0.4" + "define-property": "^1.0.0", + "isobject": "^3.0.0", + "snapdragon-util": "^3.0.1" }, "dependencies": { - "find-up": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", - "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", + "define-property": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-1.0.0.tgz", + "integrity": "sha1-dp66rz9KY6rTr56NMEybvnm/sOY=", + "dev": true, + "requires": { + "is-descriptor": "^1.0.0" + } + }, + "is-accessor-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-1.0.0.tgz", + "integrity": "sha512-m5hnHTkcVsPfqx3AKlyttIPb7J+XykHvJP2B9bZDjlhLIoEq4XoK64Vg7boZlVWYK6LUY94dYPEE7Lh0ZkZKcQ==", + "dev": true, + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-data-descriptor": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-data-descriptor/-/is-data-descriptor-1.0.0.tgz", + "integrity": "sha512-jbRXy1FmtAoCjQkVmIVYwuuqDFUbaOeDjmed1tOGPrsMhtJA4rD9tkgA0F1qJ3gRFRXcHYVkdeaP50Q5rE/jLQ==", + "dev": true, + "requires": { + "kind-of": "^6.0.0" + } + }, + "is-descriptor": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-1.0.2.tgz", + "integrity": "sha512-2eis5WqQGV7peooDyLmNEPUrps9+SXX5c9pL3xEB+4e9HnGuDa7mB7kHxHw4CbqS9k1T2hOH3miL8n8WtiYVtg==", "dev": true, "requires": { - "locate-path": "^2.0.0" + "is-accessor-descriptor": "^1.0.0", + "is-data-descriptor": "^1.0.0", + "kind-of": "^6.0.2" } } } }, - "truffle-contract": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/truffle-contract/-/truffle-contract-3.0.4.tgz", - "integrity": "sha512-/1LCtJFf5Jvm5Rv88T0d/rZSKvaiW/yO1SHXLGJgKzLsiG1F/2spFs4HrI1mRxP00opfrYXloEmLtkVV/kcndQ==", + "snapdragon-util": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/snapdragon-util/-/snapdragon-util-3.0.1.tgz", + "integrity": "sha512-mbKkMdQKsjX4BAL4bRYTj21edOf8cN7XHdYUJEe+Zn99hVEYcMvKPct1IqNe7+AZPirn8BCDOQBHQZknqmKlZQ==", "dev": true, "requires": { - "ethjs-abi": "0.1.8", - "truffle-blockchain-utils": "^0.0.4", - "truffle-contract-schema": "^2.0.0", - "truffle-error": "0.0.2", - "web3": "^0.20.1" + "kind-of": "^3.2.0" }, "dependencies": { - "ethjs-abi": { - "version": "0.1.8", - "resolved": "https://registry.npmjs.org/ethjs-abi/-/ethjs-abi-0.1.8.tgz", - "integrity": "sha1-zSiFg+1ijN+tr4re+juh28vKbBg=", + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", "dev": true, "requires": { - "bn.js": "4.11.6", - "js-sha3": "0.5.5", - "number-to-bn": "1.7.0" + "is-buffer": "^1.1.5" } } } }, - "truffle-contract-schema": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/truffle-contract-schema/-/truffle-contract-schema-2.0.0.tgz", - "integrity": "sha512-nLlspmu1GKDaluWksBwitHi/7Z3IpRjmBYeO9N+T1nVJD2V4IWJaptCKP1NqnPiJA+FChB7+F7pI6Br51/FtXQ==", + "sol-explore": { + "version": "1.6.2", + "resolved": "https://registry.npmjs.org/sol-explore/-/sol-explore-1.6.2.tgz", + "integrity": "sha1-Q66MQZ/TrAVqBfip0fsQIs1B7MI=", + "dev": true + }, + "solc": { + "version": "0.4.24", + "resolved": "https://registry.npmjs.org/solc/-/solc-0.4.24.tgz", + "integrity": "sha512-2xd7Cf1HeVwrIb6Bu1cwY2/TaLRodrppCq3l7rhLimFQgmxptXhTC3+/wesVLpB09F1A2kZgvbMOgH7wvhFnBQ==", + "requires": { + "fs-extra": "^0.30.0", + "memorystream": "^0.3.1", + "require-from-string": "^1.1.0", + "semver": "^5.3.0", + "yargs": "^4.7.1" + } + }, + "solidity-coverage": { + "version": "0.5.11", + "resolved": "https://registry.npmjs.org/solidity-coverage/-/solidity-coverage-0.5.11.tgz", + "integrity": "sha512-qikdsSi6+9XbfvwA0aI7HUVpF9fIFNqRWTw23M89GMDY+b6Gj0wWU9IngJS0fimoZIAdEp3bfChxvpfVcrUesg==", "dev": true, "requires": { - "ajv": "^5.1.1", - "crypto-js": "^3.1.9-1", - "debug": "^3.1.0" + "death": "^1.1.0", + "ethereumjs-testrpc-sc": "6.1.6", + "istanbul": "^0.4.5", + "keccakjs": "^0.2.1", + "req-cwd": "^1.0.1", + "shelljs": "^0.7.4", + "sol-explore": "^1.6.2", + "solidity-parser-sc": "0.4.11", + "tree-kill": "^1.2.0", + "web3": "^0.18.4" }, "dependencies": { - "crypto-js": { - "version": "3.1.9-1", - "resolved": "https://registry.npmjs.org/crypto-js/-/crypto-js-3.1.9-1.tgz", - "integrity": "sha1-/aGedh/Ad+Af+/3G6f38WeiAbNg=", - "dev": true + "req-cwd": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/req-cwd/-/req-cwd-1.0.1.tgz", + "integrity": "sha1-DXOurpJm5penj3l2AZZ352rPD/8=", + "dev": true, + "requires": { + "req-from": "^1.0.1" + } }, - "debug": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", - "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", + "req-from": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/req-from/-/req-from-1.0.1.tgz", + "integrity": "sha1-v4HaUUeUfTLRO5R9wSpYrUWHNQ4=", "dev": true, "requires": { - "ms": "2.0.0" + "resolve-from": "^2.0.0" } + }, + "resolve-from": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-2.0.0.tgz", + "integrity": "sha1-lICrIOlP+h2egKgEx+oUdhGWa1c=", + "dev": true } } }, - "truffle-error": { - "version": "0.0.2", - "resolved": "https://registry.npmjs.org/truffle-error/-/truffle-error-0.0.2.tgz", - "integrity": "sha1-AbGJt4UFVmrhaJwjnHyi3RIc/kw=", + "solidity-parser-antlr": { + "version": "0.2.15", + "resolved": "https://registry.npmjs.org/solidity-parser-antlr/-/solidity-parser-antlr-0.2.15.tgz", + "integrity": "sha512-EzRI8/TR/ljTXkZAyAjb0w4G20wH2XM7pcNf87ifdV825AbUv7DkY7HmiZCTj6NeKtIx8Y1s0NZWPbj+JTp8Zw==", "dev": true }, - "truffle-expect": { - "version": "0.0.3", - "resolved": "https://registry.npmjs.org/truffle-expect/-/truffle-expect-0.0.3.tgz", - "integrity": "sha1-m3XO80O9WW5+XbyHj18bLjGKlEw=", + "solidity-parser-sc": { + "version": "0.4.11", + "resolved": "https://registry.npmjs.org/solidity-parser-sc/-/solidity-parser-sc-0.4.11.tgz", + "integrity": "sha512-1kV5iC7m3CtMDfmHaVNwz2saSGQVIuF16rIxU417Al38MVCWHMQQ5vT6cmLsNwDe60S74auobWij9vNawSeOyw==", + "dev": true, + "requires": { + "mocha": "^4.1.0", + "pegjs": "^0.10.0", + "yargs": "^4.6.0" + } + }, + "source-map": { + "version": "0.5.7", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", + "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=", "dev": true }, - "truffle-flattener": { - "version": "1.2.3", - "resolved": "https://registry.npmjs.org/truffle-flattener/-/truffle-flattener-1.2.3.tgz", - "integrity": "sha512-DisthKMI1qH+Xbw/S84CLPGeXz/kMkVUxBpz8Elj2kI4paVjEFEFwrq0juQHwxr2w/046r2tUT5usCE38Bw6Qw==", + "source-map-resolve": { + "version": "0.5.2", + "resolved": "https://registry.npmjs.org/source-map-resolve/-/source-map-resolve-0.5.2.tgz", + "integrity": "sha512-MjqsvNwyz1s0k81Goz/9vRBe9SZdB09Bdw+/zYyO+3CuPk6fouTaxscHkgtE8jKvf01kVfl8riHzERQ/kefaSA==", "dev": true, "requires": { - "find-up": "^2.1.0", - "semver": "^5.4.1", - "solidity-parser": "^0.4.0", - "truffle-config": "^1.0.2", - "truffle-resolver": "^4.0.1", - "tsort": "0.0.1" - }, - "dependencies": { - "find-up": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", - "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", - "dev": true, - "requires": { - "locate-path": "^2.0.0" - } - } + "atob": "^2.1.1", + "decode-uri-component": "^0.2.0", + "resolve-url": "^0.2.1", + "source-map-url": "^0.4.0", + "urix": "^0.1.0" } }, - "truffle-provider": { - "version": "0.0.4", - "resolved": "https://registry.npmjs.org/truffle-provider/-/truffle-provider-0.0.4.tgz", - "integrity": "sha512-yVxxjocxnJcFspQ0T4Rjq/1wvvm3iLxidb6oa1EAX5LsnSQLPG8wAM5+JLlJ4FDBsqJdZLGOq1RR5Ln/w7x5JA==", + "source-map-support": { + "version": "0.5.10", + "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.10.tgz", + "integrity": "sha512-YfQ3tQFTK/yzlGJuX8pTwa4tifQj4QS2Mj7UegOu8jAz59MqIiMGPXxQhVQiIMNzayuUSF/jEuVnfFF5JqybmQ==", "dev": true, "requires": { - "truffle-error": "^0.0.2", - "web3": "^0.20.1" + "buffer-from": "^1.0.0", + "source-map": "^0.6.0" + }, + "dependencies": { + "source-map": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", + "dev": true + } } }, - "truffle-provisioner": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/truffle-provisioner/-/truffle-provisioner-0.1.0.tgz", - "integrity": "sha1-Ap5SScEBUwBzhTXgT97ZMaU8T2I=", + "source-map-url": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/source-map-url/-/source-map-url-0.4.0.tgz", + "integrity": "sha1-PpNdfd1zYxuXZZlW1VEo6HtQhKM=", "dev": true }, - "truffle-resolver": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/truffle-resolver/-/truffle-resolver-4.0.2.tgz", - "integrity": "sha512-HKRd45HSfAqb9/BCOgYq4zkyl2lF40MvPDIGhyoPXFj5/9PSFzclyTkkMOdb+Rnm7oC1vY4cE1/k453lgf81Kw==", - "dev": true, + "spdx-correct": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/spdx-correct/-/spdx-correct-3.1.0.tgz", + "integrity": "sha512-lr2EZCctC2BNR7j7WzJ2FpDznxky1sjfxvvYEyzxNyb6lZXHODmEoJeFu4JupYlkfha1KZpJyoqiJ7pgA1qq8Q==", "requires": { - "async": "^2.1.4", - "truffle-contract": "^3.0.4", - "truffle-expect": "0.0.3", - "truffle-provisioner": "^0.1.0" + "spdx-expression-parse": "^3.0.0", + "spdx-license-ids": "^3.0.0" } }, - "tsort": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/tsort/-/tsort-0.0.1.tgz", - "integrity": "sha1-4igPXoF/i/QnVlf9D5rr1E9aJ4Y=", - "dev": true + "spdx-exceptions": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/spdx-exceptions/-/spdx-exceptions-2.2.0.tgz", + "integrity": "sha512-2XQACfElKi9SlVb1CYadKDXvoajPgBVPn/gOQLrTvHdElaVhr7ZEbqJaRnJLVNeaI4cMEAgVCeBMKF6MWRDCRA==" }, - "tunnel-agent": { - "version": "0.6.0", - "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.6.0.tgz", - "integrity": "sha1-J6XeoGs2sEoKmWZ3SykIaPD8QP0=", + "spdx-expression-parse": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/spdx-expression-parse/-/spdx-expression-parse-3.0.0.tgz", + "integrity": "sha512-Yg6D3XpRD4kkOmTpdgbUiEJFKghJH03fiC1OPll5h/0sO6neh2jqRDVHOQ4o/LMea0tgCkbMgea5ip/e+MkWyg==", "requires": { - "safe-buffer": "^5.0.1" + "spdx-exceptions": "^2.1.0", + "spdx-license-ids": "^3.0.0" } }, - "tweetnacl": { - "version": "0.14.5", - "resolved": "https://registry.npmjs.org/tweetnacl/-/tweetnacl-0.14.5.tgz", - "integrity": "sha1-WuaBd/GS1EViadEIr6k/+HQ/T2Q=", - "optional": true + "spdx-license-ids": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/spdx-license-ids/-/spdx-license-ids-3.0.3.tgz", + "integrity": "sha512-uBIcIl3Ih6Phe3XHK1NqboJLdGfwr1UN3k6wSD1dZpmPsIkb8AGNbZYJ1fOBk834+Gxy8rpfDxrS6XLEMZMY2g==" }, - "type-check": { - "version": "0.3.2", - "resolved": "https://registry.npmjs.org/type-check/-/type-check-0.3.2.tgz", - "integrity": "sha1-WITKtRLPHTVeP7eE8wgEsrUg23I=", + "split-string": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/split-string/-/split-string-3.1.0.tgz", + "integrity": "sha512-NzNVhJDYpwceVVii8/Hu6DKfD2G+NrQHlS/V/qgv763EYudVwEcMQNxd2lh+0VrUByXN/oJkl5grOhYWvQUYiw==", "dev": true, "requires": { - "prelude-ls": "~1.1.2" + "extend-shallow": "^3.0.0" } }, - "type-detect": { - "version": "4.0.8", - "resolved": "https://registry.npmjs.org/type-detect/-/type-detect-4.0.8.tgz", - "integrity": "sha512-0fr/mIH1dlO+x7TlcMy+bIDqKPsw/70tVyeHW787goQjhmqaZe10uwLujubK9q9Lg6Fiho1KUKDYz0Z7k7g5/g==", + "sprintf-js": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz", + "integrity": "sha1-BOaSb2YolTVPPdAVIDYzuFcpfiw=", "dev": true }, - "type-is": { - "version": "1.6.16", - "resolved": "https://registry.npmjs.org/type-is/-/type-is-1.6.16.tgz", - "integrity": "sha512-HRkVv/5qY2G6I8iab9cI7v1bOIdhm94dVjQCPFElW9W+3GeDOSHmy2EBYe4VTApuzolPcmgFTN3ftVJRKR2J9Q==", + "sshpk": { + "version": "1.16.1", + "resolved": "https://registry.npmjs.org/sshpk/-/sshpk-1.16.1.tgz", + "integrity": "sha512-HXXqVUq7+pcKeLqqZj6mHFUMvXtOJt1uoUx09pFW6011inTMxqI8BA8PM95myrIyyKwdnzjdFjLiE6KBPVtJIg==", + "dev": true, "requires": { - "media-typer": "0.3.0", - "mime-types": "~2.1.18" + "asn1": "~0.2.3", + "assert-plus": "^1.0.0", + "bcrypt-pbkdf": "^1.0.0", + "dashdash": "^1.12.0", + "ecc-jsbn": "~0.1.1", + "getpass": "^0.1.1", + "jsbn": "~0.1.0", + "safer-buffer": "^2.0.2", + "tweetnacl": "~0.14.0" } }, - "typedarray": { - "version": "0.0.6", - "resolved": "https://registry.npmjs.org/typedarray/-/typedarray-0.0.6.tgz", - "integrity": "sha1-hnrHTjhkGHsdPUfZlqeOxciDB3c=", - "dev": true - }, - "uglify-js": { - "version": "2.8.29", - "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-2.8.29.tgz", - "integrity": "sha1-KcVzMUgFe7Th913zW3qcty5qWd0=", + "static-extend": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/static-extend/-/static-extend-0.1.2.tgz", + "integrity": "sha1-YICcOcv/VTNyJv1eC1IPNB8ftcY=", "dev": true, - "optional": true, "requires": { - "source-map": "~0.5.1", - "uglify-to-browserify": "~1.0.0", - "yargs": "~3.10.0" + "define-property": "^0.2.5", + "object-copy": "^0.1.0" }, "dependencies": { - "camelcase": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-1.2.1.tgz", - "integrity": "sha1-m7UwTS4LVmmLLHWLCKPqqdqlijk=", - "dev": true, - "optional": true - }, - "cliui": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/cliui/-/cliui-2.1.0.tgz", - "integrity": "sha1-S0dXYP+AJkx2LDoXGQMukcf+oNE=", - "dev": true, - "optional": true, - "requires": { - "center-align": "^0.1.1", - "right-align": "^0.1.1", - "wordwrap": "0.0.2" - } - }, - "window-size": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/window-size/-/window-size-0.1.0.tgz", - "integrity": "sha1-VDjNLqk7IC76Ohn+iIeu58lPnJ0=", - "dev": true, - "optional": true - }, - "wordwrap": { - "version": "0.0.2", - "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-0.0.2.tgz", - "integrity": "sha1-t5Zpu0LstAn4PVg8rVLKF+qhZD8=", - "dev": true, - "optional": true - }, - "yargs": { - "version": "3.10.0", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-3.10.0.tgz", - "integrity": "sha1-9+572FfdfB0tOMDnTvvWgdFDH9E=", + "define-property": { + "version": "0.2.5", + "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", + "integrity": "sha1-w1se+RjsPJkPmlvFe+BKrOxcgRY=", "dev": true, - "optional": true, "requires": { - "camelcase": "^1.0.2", - "cliui": "^2.1.0", - "decamelize": "^1.0.0", - "window-size": "0.1.0" + "is-descriptor": "^0.1.0" } } } }, - "uglify-to-browserify": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/uglify-to-browserify/-/uglify-to-browserify-1.0.2.tgz", - "integrity": "sha1-bgkk1r2mta/jSeOabWMoUKD4grc=", - "dev": true, - "optional": true + "stealthy-require": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/stealthy-require/-/stealthy-require-1.1.1.tgz", + "integrity": "sha1-NbCYdbT/SfJqd35QmzCQoyJr8ks=", + "dev": true + }, + "strict-uri-encode": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/strict-uri-encode/-/strict-uri-encode-1.1.0.tgz", + "integrity": "sha1-J5siXfHVgrH1TmWt3UNS4Y+qBxM=" + }, + "string-width": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz", + "integrity": "sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=", + "requires": { + "code-point-at": "^1.0.0", + "is-fullwidth-code-point": "^1.0.0", + "strip-ansi": "^3.0.0" + } + }, + "string_decoder": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", + "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", + "dev": true, + "requires": { + "safe-buffer": "~5.1.0" + } + }, + "strip-ansi": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", + "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", + "requires": { + "ansi-regex": "^2.0.0" + } + }, + "strip-bom": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-2.0.0.tgz", + "integrity": "sha1-YhmoVhZSBJHzV4i9vxRHqZx+aw4=", + "requires": { + "is-utf8": "^0.2.0" + } + }, + "strip-eof": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/strip-eof/-/strip-eof-1.0.0.tgz", + "integrity": "sha1-u0P/VZim6wXYm1n80SnJgzE2Br8=", + "dev": true + }, + "strip-hex-prefix": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/strip-hex-prefix/-/strip-hex-prefix-1.0.0.tgz", + "integrity": "sha1-DF8VX+8RUTczd96du1iNoFUA428=", + "requires": { + "is-hex-prefixed": "1.0.0" + } + }, + "strip-json-comments": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", + "integrity": "sha1-PFMZQukIwml8DsNEhYwobHygpgo=", + "dev": true }, - "ultron": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/ultron/-/ultron-1.1.1.tgz", - "integrity": "sha512-UIEXBNeYmKptWH6z8ZnqTeS8fV74zG0/eRU9VGkpzz+LIJNs8W/zM/L+7ctCkRrgbNnnR0xxw4bKOr0cW0N0Og==" + "supports-color": { + "version": "4.4.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-4.4.0.tgz", + "integrity": "sha512-rKC3+DyXWgK0ZLKwmRsrkyHVZAjNkfzeehuFWdGGcqGDTZFH73+RH6S/RDAAxl9GusSjZSUWYLmT9N5pzXFOXQ==", + "requires": { + "has-flag": "^2.0.0" + } }, - "undefsafe": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/undefsafe/-/undefsafe-2.0.2.tgz", - "integrity": "sha1-Il9rngM3Zj4Njnz9aG/Cg2zKznY=", + "sync-request": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/sync-request/-/sync-request-6.0.0.tgz", + "integrity": "sha512-jGNIAlCi9iU4X3Dm4oQnNQshDD3h0/1A7r79LyqjbjUnj69sX6mShAXlhRXgImsfVKtTcnra1jfzabdZvp+Lmw==", "dev": true, "requires": { - "debug": "^2.2.0" + "http-response-object": "^3.0.1", + "sync-rpc": "^1.2.1", + "then-request": "^6.0.0" } }, - "underscore": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.6.0.tgz", - "integrity": "sha1-izixDKze9jM3uLJOT/htRa6lKag=" + "sync-rpc": { + "version": "1.3.4", + "resolved": "https://registry.npmjs.org/sync-rpc/-/sync-rpc-1.3.4.tgz", + "integrity": "sha512-Iug+t1ICVFenUcTnDu8WXFnT+k8IVoLKGh8VA3eXUtl2Rt9SjKX3YEv33OenABqpTPL9QEaHv1+CNn2LK8vMow==", + "dev": true, + "requires": { + "get-port": "^3.1.0" + } }, - "union-value": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/union-value/-/union-value-1.0.0.tgz", - "integrity": "sha1-XHHDTLW61dzr4+oM0IIHulqhrqQ=", + "term-size": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/term-size/-/term-size-1.2.0.tgz", + "integrity": "sha1-RYuDiH8oj8Vtb/+/rSYuJmOO+mk=", "dev": true, "requires": { - "arr-union": "^3.1.0", - "get-value": "^2.0.6", - "is-extendable": "^0.1.1", - "set-value": "^0.4.3" - }, - "dependencies": { - "extend-shallow": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", - "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", - "dev": true, - "requires": { - "is-extendable": "^0.1.0" - } - }, - "set-value": { - "version": "0.4.3", - "resolved": "https://registry.npmjs.org/set-value/-/set-value-0.4.3.tgz", - "integrity": "sha1-fbCPnT0i3H945Trzw79GZuzfzPE=", - "dev": true, - "requires": { - "extend-shallow": "^2.0.1", - "is-extendable": "^0.1.1", - "is-plain-object": "^2.0.1", - "to-object-path": "^0.3.0" - } - } + "execa": "^0.7.0" } }, - "unique-string": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/unique-string/-/unique-string-1.0.0.tgz", - "integrity": "sha1-nhBXzKhRq7kzmPizOuGHuZyuwRo=", + "then-request": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/then-request/-/then-request-6.0.0.tgz", + "integrity": "sha512-xA+7uEMc+jsQIoyySJ93Ad08Kuqnik7u6jLS5hR91Z3smAoCfL3M8/MqMlobAa9gzBfO9pA88A/AntfepkkMJQ==", "dev": true, "requires": { - "crypto-random-string": "^1.0.0" + "@types/concat-stream": "^1.6.0", + "@types/form-data": "0.0.33", + "@types/node": "^8.0.0", + "@types/qs": "^6.2.31", + "caseless": "~0.12.0", + "concat-stream": "^1.6.0", + "form-data": "^2.2.0", + "http-basic": "^7.0.0", + "http-response-object": "^3.0.1", + "promise": "^8.0.0", + "qs": "^6.4.0" + }, + "dependencies": { + "@types/node": { + "version": "8.10.40", + "resolved": "https://registry.npmjs.org/@types/node/-/node-8.10.40.tgz", + "integrity": "sha512-RRSjdwz63kS4u7edIwJUn8NqKLLQ6LyqF/X4+4jp38MBT3Vwetewi2N4dgJEshLbDwNgOJXNYoOwzVZUSSLhkQ==", + "dev": true + } } }, - "unpipe": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/unpipe/-/unpipe-1.0.0.tgz", - "integrity": "sha1-sr9O6FFKrmFltIF4KdIbLvSZBOw=" + "timed-out": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/timed-out/-/timed-out-4.0.1.tgz", + "integrity": "sha1-8y6srFoXW+ol1/q1Zas+2HQe9W8=" }, - "unset-value": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/unset-value/-/unset-value-1.0.0.tgz", - "integrity": "sha1-g3aHP30jNRef+x5vw6jtDfyKtVk=", + "to-object-path": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/to-object-path/-/to-object-path-0.3.0.tgz", + "integrity": "sha1-KXWIt7Dn4KwI4E5nL4XB9JmeF68=", "dev": true, "requires": { - "has-value": "^0.3.1", - "isobject": "^3.0.0" + "kind-of": "^3.0.2" }, "dependencies": { - "has-value": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/has-value/-/has-value-0.3.1.tgz", - "integrity": "sha1-ex9YutpiyoJ+wKIHgCVlSEWZXh8=", + "kind-of": { + "version": "3.2.2", + "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", + "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", "dev": true, "requires": { - "get-value": "^2.0.3", - "has-values": "^0.1.4", - "isobject": "^2.0.0" - }, - "dependencies": { - "isobject": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/isobject/-/isobject-2.1.0.tgz", - "integrity": "sha1-8GVWEJaj8dou9GJy+BXIQNh+DIk=", - "dev": true, - "requires": { - "isarray": "1.0.0" - } - } + "is-buffer": "^1.1.5" } - }, - "has-values": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/has-values/-/has-values-0.1.4.tgz", - "integrity": "sha1-bWHeldkd/Km5oCCJrThL/49it3E=", - "dev": true } } }, - "untildify": { + "to-regex": { "version": "3.0.2", - "resolved": "https://registry.npmjs.org/untildify/-/untildify-3.0.2.tgz", - "integrity": "sha1-fx8wIFWz/qDz6B3HjrNnZstl4/E=" - }, - "unzip-response": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/unzip-response/-/unzip-response-2.0.1.tgz", - "integrity": "sha1-0vD3N9FrBhXnKmk17QQhRXLVb5c=", - "dev": true - }, - "upath": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/upath/-/upath-1.0.5.tgz", - "integrity": "sha512-qbKn90aDQ0YEwvXoLqj0oiuUYroLX2lVHZ+b+xwjozFasAOC4GneDq5+OaIG5Zj+jFmbz/uO+f7a9qxjktJQww==", - "dev": true - }, - "update-notifier": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/update-notifier/-/update-notifier-2.5.0.tgz", - "integrity": "sha512-gwMdhgJHGuj/+wHJJs9e6PcCszpxR1b236igrOkUofGhqJuG+amlIKwApH1IW1WWl7ovZxsX49lMBWLxSdm5Dw==", + "resolved": "https://registry.npmjs.org/to-regex/-/to-regex-3.0.2.tgz", + "integrity": "sha512-FWtleNAtZ/Ki2qtqej2CXTOayOH9bHDQF+Q48VpWyDXjbYxA4Yz8iDB31zXOBUlOHHKidDbqGVrTUvQMPmBGBw==", "dev": true, "requires": { - "boxen": "^1.2.1", - "chalk": "^2.0.1", - "configstore": "^3.0.0", - "import-lazy": "^2.1.0", - "is-ci": "^1.0.10", - "is-installed-globally": "^0.1.0", - "is-npm": "^1.0.0", - "latest-version": "^3.0.0", - "semver-diff": "^2.0.0", - "xdg-basedir": "^3.0.0" + "define-property": "^2.0.2", + "extend-shallow": "^3.0.2", + "regex-not": "^1.0.2", + "safe-regex": "^1.1.0" } }, - "urix": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/urix/-/urix-0.1.0.tgz", - "integrity": "sha1-2pN/emLiH+wf0Y1Js1wpNQZ6bHI=", - "dev": true - }, - "url-parse-lax": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/url-parse-lax/-/url-parse-lax-1.0.0.tgz", - "integrity": "sha1-evjzA2Rem9eaJy56FKxovAYJ2nM=", + "to-regex-range": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-2.1.1.tgz", + "integrity": "sha1-fIDBe53+vlmeJzZ+DU3VWQFB2zg=", + "dev": true, "requires": { - "prepend-http": "^1.0.1" + "is-number": "^3.0.0", + "repeat-string": "^1.6.1" } }, - "url-set-query": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/url-set-query/-/url-set-query-1.0.0.tgz", - "integrity": "sha1-AW6M/Xwg7gXK/neV6JK9BwL6ozk=" - }, - "url-to-options": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/url-to-options/-/url-to-options-1.0.1.tgz", - "integrity": "sha1-FQWgOiiaSMvXpDTvuu7FBV9WM6k=" - }, - "use": { + "touch": { "version": "3.1.0", - "resolved": "https://registry.npmjs.org/use/-/use-3.1.0.tgz", - "integrity": "sha512-6UJEQM/L+mzC3ZJNM56Q4DFGLX/evKGRg15UJHGB9X5j5Z3AFbgZvjUh2yq/UJUY4U5dh7Fal++XbNg1uzpRAw==", + "resolved": "https://registry.npmjs.org/touch/-/touch-3.1.0.tgz", + "integrity": "sha512-WBx8Uy5TLtOSRtIq+M03/sKDrXCLHxwDcquSP2c43Le03/9serjQBIztjRz6FkJez9D/hleyAXTBGLwwZUw9lA==", "dev": true, "requires": { - "kind-of": "^6.0.2" + "nopt": "~1.0.10" } }, - "utf8": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/utf8/-/utf8-2.1.2.tgz", - "integrity": "sha1-H6DZJw6b6FDZsFAn9jUZv0ZFfZY=", + "tough-cookie": { + "version": "2.4.3", + "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.4.3.tgz", + "integrity": "sha512-Q5srk/4vDM54WJsJio3XNn6K2sCG+CQ8G5Wz6bZhRZoAe/+TxjWB/GlFAnYEbkYVlON9FMk/fE3h2RLpPXo4lQ==", + "dev": true, + "requires": { + "psl": "^1.1.24", + "punycode": "^1.4.1" + }, + "dependencies": { + "punycode": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/punycode/-/punycode-1.4.1.tgz", + "integrity": "sha1-wNWmOycYgArY4esPpSachN1BhF4=", + "dev": true + } + } + }, + "tree-kill": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/tree-kill/-/tree-kill-1.2.1.tgz", + "integrity": "sha512-4hjqbObwlh2dLyW4tcz0Ymw0ggoaVDMveUB9w8kFSQScdRLo0gxO9J7WFcUBo+W3C1TLdFIEwNOWebgZZ0RH9Q==", "dev": true }, - "util-deprecate": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", - "integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=" + "trim": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/trim/-/trim-0.0.1.tgz", + "integrity": "sha1-WFhUf2spB1fulczMZm+1AITEYN0=" }, - "utils-merge": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/utils-merge/-/utils-merge-1.0.1.tgz", - "integrity": "sha1-n5VxD1CiZ5R7LMwSR0HBAoQn5xM=" + "truffle": { + "version": "4.1.11", + "resolved": "https://registry.npmjs.org/truffle/-/truffle-4.1.11.tgz", + "integrity": "sha512-VNhc6jexZeM92sNJJr4U8ln3uJ/mJEQO/0y9ZLYc4pccyIskPtl+3r4mzymgGM/Mq5v6MpoQVD6NZgHUVKX+Dw==", + "requires": { + "mocha": "^4.1.0", + "original-require": "^1.0.1", + "solc": "0.4.24" + } }, - "uuid": { - "version": "3.2.1", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.2.1.tgz", - "integrity": "sha512-jZnMwlb9Iku/O3smGWvZhauCf6cvvpKi4BKRiliS3cxnI+Gz9j5MEpTz2UFuXiKPJocb7gnsLHwiS05ige5BEA==" + "truffle-flattener": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/truffle-flattener/-/truffle-flattener-1.3.0.tgz", + "integrity": "sha512-ppJ9xI0tDuvCYjQlcWwMBcOKZph5U4YpG/gChyUVDxOjUIniG5g7y9vZho2PRj1FohPPnOjg1KOAVNlk/bPZrw==", + "dev": true, + "requires": { + "@resolver-engine/imports-fs": "^0.2.2", + "find-up": "^2.1.0", + "mkdirp": "^0.5.1", + "solidity-parser-antlr": "^0.4.0", + "tsort": "0.0.1" + }, + "dependencies": { + "find-up": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", + "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", + "dev": true, + "requires": { + "locate-path": "^2.0.0" + } + }, + "solidity-parser-antlr": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/solidity-parser-antlr/-/solidity-parser-antlr-0.4.0.tgz", + "integrity": "sha512-RrIsh5VoHmrMQia6yLY8u8rx3JPREhSiCFz4Xb0h1Oh0prUYU2ukyWO8gG892V0UMHIXCWqvdZ3wSctNwdWThg==", + "dev": true + } + } }, - "v8-compile-cache": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/v8-compile-cache/-/v8-compile-cache-1.1.2.tgz", - "integrity": "sha512-ejdrifsIydN1XDH7EuR2hn8ZrkRKUYF7tUcBjBy/lhrCvs2K+zRlbW9UHc0IQ9RsYFZJFqJrieoIHfkCa0DBRA==" + "tsort": { + "version": "0.0.1", + "resolved": "https://registry.npmjs.org/tsort/-/tsort-0.0.1.tgz", + "integrity": "sha1-4igPXoF/i/QnVlf9D5rr1E9aJ4Y=", + "dev": true }, - "validate-npm-package-license": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/validate-npm-package-license/-/validate-npm-package-license-3.0.1.tgz", - "integrity": "sha1-KAS6vnEq0zeUWaz74kdGqywwP7w=", + "tunnel-agent": { + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.6.0.tgz", + "integrity": "sha1-J6XeoGs2sEoKmWZ3SykIaPD8QP0=", + "dev": true, "requires": { - "spdx-correct": "~1.0.0", - "spdx-expression-parse": "~1.0.0" + "safe-buffer": "^5.0.1" } }, - "vary": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz", - "integrity": "sha1-IpnwLG3tMNSllhsLn3RSShj2NPw=" + "tweetnacl": { + "version": "0.14.5", + "resolved": "https://registry.npmjs.org/tweetnacl/-/tweetnacl-0.14.5.tgz", + "integrity": "sha1-WuaBd/GS1EViadEIr6k/+HQ/T2Q=", + "dev": true }, - "verror": { - "version": "1.10.0", - "resolved": "https://registry.npmjs.org/verror/-/verror-1.10.0.tgz", - "integrity": "sha1-OhBcoXBTr1XW4nDB+CiGguGNpAA=", + "type-check": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/type-check/-/type-check-0.3.2.tgz", + "integrity": "sha1-WITKtRLPHTVeP7eE8wgEsrUg23I=", + "dev": true, "requires": { - "assert-plus": "^1.0.0", - "core-util-is": "1.0.2", - "extsprintf": "^1.2.0" + "prelude-ls": "~1.1.2" } }, - "vinyl": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-1.2.0.tgz", - "integrity": "sha1-XIgDbPVl5d8FVYv8kR+GVt8hiIQ=", - "requires": { - "clone": "^1.0.0", - "clone-stats": "^0.0.1", - "replace-ext": "0.0.1" - } + "type-detect": { + "version": "4.0.8", + "resolved": "https://registry.npmjs.org/type-detect/-/type-detect-4.0.8.tgz", + "integrity": "sha512-0fr/mIH1dlO+x7TlcMy+bIDqKPsw/70tVyeHW787goQjhmqaZe10uwLujubK9q9Lg6Fiho1KUKDYz0Z7k7g5/g==", + "dev": true }, - "vinyl-file": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/vinyl-file/-/vinyl-file-2.0.0.tgz", - "integrity": "sha1-p+v1/779obfRjRQPyweyI++2dRo=", - "requires": { - "graceful-fs": "^4.1.2", - "pify": "^2.3.0", - "pinkie-promise": "^2.0.0", - "strip-bom": "^2.0.0", - "strip-bom-stream": "^2.0.0", - "vinyl": "^1.1.0" - } + "typedarray": { + "version": "0.0.6", + "resolved": "https://registry.npmjs.org/typedarray/-/typedarray-0.0.6.tgz", + "integrity": "sha1-hnrHTjhkGHsdPUfZlqeOxciDB3c=", + "dev": true }, - "web3": { - "version": "0.20.5", - "resolved": "https://registry.npmjs.org/web3/-/web3-0.20.5.tgz", - "integrity": "sha1-xQSNNfe/TixMKAzlH7u8lRKQsWU=", + "uglify-js": { + "version": "3.4.9", + "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-3.4.9.tgz", + "integrity": "sha512-8CJsbKOtEbnJsTyv6LE6m6ZKniqMiFWmm9sRbopbkGs3gMPPfd3Fh8iIA4Ykv5MgaTbqHr4BaoGLJLZNhsrW1Q==", "dev": true, + "optional": true, "requires": { - "bignumber.js": "git+https://github.com/frozeman/bignumber.js-nolookahead.git#57692b3ecfc98bbdd6b3a516cb2353652ea49934", - "crypto-js": "^3.1.4", - "utf8": "^2.1.1", - "xhr2": "*", - "xmlhttprequest": "*" - } - }, - "web3-utils": { - "version": "1.0.0-beta.34", - "resolved": "https://registry.npmjs.org/web3-utils/-/web3-utils-1.0.0-beta.34.tgz", - "integrity": "sha1-lBH8OarvOcpOBhafdiKX2f8CCXA=", - "requires": { - "bn.js": "4.11.6", - "eth-lib": "0.1.27", - "ethjs-unit": "0.1.6", - "number-to-bn": "1.7.0", - "randomhex": "0.1.5", - "underscore": "1.8.3", - "utf8": "2.1.1" + "commander": "~2.17.1", + "source-map": "~0.6.1" }, "dependencies": { - "underscore": { - "version": "1.8.3", - "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", - "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=" + "commander": { + "version": "2.17.1", + "resolved": "https://registry.npmjs.org/commander/-/commander-2.17.1.tgz", + "integrity": "sha512-wPMUt6FnH2yzG95SA6mzjQOEKUU3aLaDEmzs1ti+1E9h+CsrZghRlqEM/EJ4KscsQVG8uNN4uVreUeT8+drlgg==", + "dev": true, + "optional": true }, - "utf8": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/utf8/-/utf8-2.1.1.tgz", - "integrity": "sha1-LgHbAvfY0JRPdxBPFgnrDDBM92g=" + "source-map": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", + "dev": true, + "optional": true } } }, - "webpack-addons": { - "version": "1.1.5", - "resolved": "https://registry.npmjs.org/webpack-addons/-/webpack-addons-1.1.5.tgz", - "integrity": "sha512-MGO0nVniCLFAQz1qv22zM02QPjcpAoJdy7ED0i3Zy7SY1IecgXCm460ib7H/Wq7e9oL5VL6S2BxaObxwIcag0g==", + "undefsafe": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/undefsafe/-/undefsafe-2.0.2.tgz", + "integrity": "sha1-Il9rngM3Zj4Njnz9aG/Cg2zKznY=", + "dev": true, "requires": { - "jscodeshift": "^0.4.0" + "debug": "^2.2.0" }, "dependencies": { - "arr-diff": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/arr-diff/-/arr-diff-2.0.0.tgz", - "integrity": "sha1-jzuCf5Vai9ZpaX5KQlasPOrjVs8=", - "requires": { - "arr-flatten": "^1.0.1" - } - }, - "array-unique": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/array-unique/-/array-unique-0.2.1.tgz", - "integrity": "sha1-odl8yvy8JiXMcPrc6zalDFiwGlM=" - }, - "ast-types": { - "version": "0.10.1", - "resolved": "https://registry.npmjs.org/ast-types/-/ast-types-0.10.1.tgz", - "integrity": "sha512-UY7+9DPzlJ9VM8eY0b2TUZcZvF+1pO0hzMtAyjBYKhOmnvRlqYNYnWdtsMj0V16CGaMlpL0G1jnLbLo4AyotuQ==" - }, - "async": { - "version": "1.5.2", - "resolved": "https://registry.npmjs.org/async/-/async-1.5.2.tgz", - "integrity": "sha1-7GphrlZIDAw8skHJVhjiCJL5Zyo=" - }, - "babylon": { - "version": "6.18.0", - "resolved": "https://registry.npmjs.org/babylon/-/babylon-6.18.0.tgz", - "integrity": "sha512-q/UEjfGJ2Cm3oKV71DJz9d25TPnq5rhBVL2Q4fA5wcC3jcrdn7+SssEybFIxwAvvP+YCsCYNKughoF33GxgycQ==" - }, - "braces": { - "version": "1.8.5", - "resolved": "https://registry.npmjs.org/braces/-/braces-1.8.5.tgz", - "integrity": "sha1-uneWLhLf+WnWt2cR6RS3N4V79qc=", - "requires": { - "expand-range": "^1.8.1", - "preserve": "^0.2.0", - "repeat-element": "^1.1.2" - } - }, - "expand-brackets": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/expand-brackets/-/expand-brackets-0.1.5.tgz", - "integrity": "sha1-3wcoTjQqgHzXM6xa9yQR5YHRF3s=", - "requires": { - "is-posix-bracket": "^0.1.0" - } - }, - "extglob": { - "version": "0.3.2", - "resolved": "https://registry.npmjs.org/extglob/-/extglob-0.3.2.tgz", - "integrity": "sha1-Lhj/PS9JqydlzskCPwEdqo2DSaE=", - "requires": { - "is-extglob": "^1.0.0" - } - }, - "is-extglob": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-1.0.0.tgz", - "integrity": "sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA=" - }, - "is-glob": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-2.0.1.tgz", - "integrity": "sha1-0Jb5JqPe1WAPP9/ZEZjLCIjC2GM=", - "requires": { - "is-extglob": "^1.0.0" - } - }, - "jscodeshift": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/jscodeshift/-/jscodeshift-0.4.1.tgz", - "integrity": "sha512-iOX6If+hsw0q99V3n31t4f5VlD1TQZddH08xbT65ZqA7T4Vkx68emrDZMUOLVvCEAJ6NpAk7DECe3fjC/t52AQ==", - "requires": { - "async": "^1.5.0", - "babel-plugin-transform-flow-strip-types": "^6.8.0", - "babel-preset-es2015": "^6.9.0", - "babel-preset-stage-1": "^6.5.0", - "babel-register": "^6.9.0", - "babylon": "^6.17.3", - "colors": "^1.1.2", - "flow-parser": "^0.*", - "lodash": "^4.13.1", - "micromatch": "^2.3.7", - "node-dir": "0.1.8", - "nomnom": "^1.8.1", - "recast": "^0.12.5", - "temp": "^0.8.1", - "write-file-atomic": "^1.2.0" - } - }, - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", - "requires": { - "is-buffer": "^1.1.5" - } - }, - "micromatch": { - "version": "2.3.11", - "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-2.3.11.tgz", - "integrity": "sha1-hmd8l9FyCzY0MdBNDRUpO9OMFWU=", - "requires": { - "arr-diff": "^2.0.0", - "array-unique": "^0.2.1", - "braces": "^1.8.2", - "expand-brackets": "^0.1.4", - "extglob": "^0.3.1", - "filename-regex": "^2.0.0", - "is-extglob": "^1.0.0", - "is-glob": "^2.0.1", - "kind-of": "^3.0.2", - "normalize-path": "^2.0.1", - "object.omit": "^2.0.0", - "parse-glob": "^3.0.4", - "regex-cache": "^0.4.2" - } - }, - "recast": { - "version": "0.12.9", - "resolved": "https://registry.npmjs.org/recast/-/recast-0.12.9.tgz", - "integrity": "sha512-y7ANxCWmMW8xLOaiopiRDlyjQ9ajKRENBH+2wjntIbk3A6ZR1+BLQttkmSHMY7Arl+AAZFwJ10grg2T6f1WI8A==", - "requires": { - "ast-types": "0.10.1", - "core-js": "^2.4.1", - "esprima": "~4.0.0", - "private": "~0.1.5", - "source-map": "~0.6.1" - } - }, - "source-map": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", - "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==" - }, - "write-file-atomic": { - "version": "1.3.4", - "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-1.3.4.tgz", - "integrity": "sha1-+Aek8LHZ6ROuekgRLmzDrxmRtF8=", + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, "requires": { - "graceful-fs": "^4.1.11", - "imurmurhash": "^0.1.4", - "slide": "^1.1.5" + "ms": "2.0.0" } } } }, - "webpack-cli": { - "version": "2.0.13", - "resolved": "https://registry.npmjs.org/webpack-cli/-/webpack-cli-2.0.13.tgz", - "integrity": "sha512-0lnOi3yla8FsZVuMsbfnNRB/8DlfuDugKdekC+4ykydZG0+UOidMi5J5LLWN4c0VJ8PqC19yMXXkYyCq78OuqA==", - "requires": { - "chalk": "^2.3.2", - "cross-spawn": "^6.0.5", - "diff": "^3.5.0", - "enhanced-resolve": "^4.0.0", - "glob-all": "^3.1.0", - "global-modules": "^1.0.0", - "got": "^8.2.0", - "inquirer": "^5.1.0", - "interpret": "^1.0.4", - "jscodeshift": "^0.5.0", - "listr": "^0.13.0", - "loader-utils": "^1.1.0", - "lodash": "^4.17.5", - "log-symbols": "^2.2.0", - "mkdirp": "^0.5.1", - "p-each-series": "^1.0.0", - "p-lazy": "^1.0.0", - "prettier": "^1.5.3", - "resolve-cwd": "^2.0.0", - "supports-color": "^5.3.0", - "v8-compile-cache": "^1.1.2", - "webpack-addons": "^1.1.5", - "yargs": "^11.0.0", - "yeoman-environment": "^2.0.0", - "yeoman-generator": "^2.0.3" + "union-value": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/union-value/-/union-value-1.0.0.tgz", + "integrity": "sha1-XHHDTLW61dzr4+oM0IIHulqhrqQ=", + "dev": true, + "requires": { + "arr-union": "^3.1.0", + "get-value": "^2.0.6", + "is-extendable": "^0.1.1", + "set-value": "^0.4.3" }, "dependencies": { - "ansi-regex": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", - "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=" - }, - "camelcase": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-4.1.0.tgz", - "integrity": "sha1-1UVjW+HjPFQmScaRc+Xeas+uNN0=" - }, - "cliui": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/cliui/-/cliui-4.0.0.tgz", - "integrity": "sha512-nY3W5Gu2racvdDk//ELReY+dHjb9PlIcVDFXP72nVIhq2Gy3LuVXYwJoPVudwQnv1shtohpgkdCKT2YaKY0CKw==", - "requires": { - "string-width": "^2.1.1", - "strip-ansi": "^4.0.0", - "wrap-ansi": "^2.0.0" - } - }, - "cross-spawn": { - "version": "6.0.5", - "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-6.0.5.tgz", - "integrity": "sha512-eTVLrBSt7fjbDygz805pMnstIs2VTBNkRm0qxZd+M7A5XDdxVRWO5MxGBXZhjY4cqLYLdtrGqRf8mBPmzwSpWQ==", - "requires": { - "nice-try": "^1.0.4", - "path-key": "^2.0.1", - "semver": "^5.5.0", - "shebang-command": "^1.2.0", - "which": "^1.2.9" - } - }, - "diff": { - "version": "3.5.0", - "resolved": "https://registry.npmjs.org/diff/-/diff-3.5.0.tgz", - "integrity": "sha512-A46qtFgd+g7pDZinpnwiRJtxbC1hpgf0uzP3iG89scHk0AUC7A1TGxf5OiiOUv/JMZR8GOt8hL900hV0bOy5xA==" - }, - "find-up": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", - "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", - "requires": { - "locate-path": "^2.0.0" - } - }, - "got": { - "version": "8.3.0", - "resolved": "https://registry.npmjs.org/got/-/got-8.3.0.tgz", - "integrity": "sha512-kBNy/S2CGwrYgDSec5KTWGKUvupwkkTVAjIsVFF2shXO13xpZdFP4d4kxa//CLX2tN/rV0aYwK8vY6UKWGn2vQ==", - "requires": { - "@sindresorhus/is": "^0.7.0", - "cacheable-request": "^2.1.1", - "decompress-response": "^3.3.0", - "duplexer3": "^0.1.4", - "get-stream": "^3.0.0", - "into-stream": "^3.1.0", - "is-retry-allowed": "^1.1.0", - "isurl": "^1.0.0-alpha5", - "lowercase-keys": "^1.0.0", - "mimic-response": "^1.0.0", - "p-cancelable": "^0.4.0", - "p-timeout": "^2.0.1", - "pify": "^3.0.0", - "safe-buffer": "^5.1.1", - "timed-out": "^4.0.1", - "url-parse-lax": "^3.0.0", - "url-to-options": "^1.0.1" - } - }, - "has-flag": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", - "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=" - }, - "is-fullwidth-code-point": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", - "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=" - }, - "os-locale": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/os-locale/-/os-locale-2.1.0.tgz", - "integrity": "sha512-3sslG3zJbEYcaC4YVAvDorjGxc7tv6KVATnLPZONiljsUncvihe9BQoVCEs0RZ1kmf4Hk9OBqlZfJZWI4GanKA==", - "requires": { - "execa": "^0.7.0", - "lcid": "^1.0.0", - "mem": "^1.1.0" - } - }, - "pify": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", - "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=" - }, - "prepend-http": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/prepend-http/-/prepend-http-2.0.0.tgz", - "integrity": "sha1-6SQ0v6XqjBn0HN/UAddBo8gZ2Jc=" - }, - "string-width": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", - "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", - "requires": { - "is-fullwidth-code-point": "^2.0.0", - "strip-ansi": "^4.0.0" - } - }, - "strip-ansi": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", - "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", - "requires": { - "ansi-regex": "^3.0.0" - } - }, - "supports-color": { - "version": "5.3.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.3.0.tgz", - "integrity": "sha512-0aP01LLIskjKs3lq52EC0aGBAJhLq7B2Rd8HC/DR/PtNNpcLilNmHC12O+hu0usQpo7wtHNRqtrhBwtDb0+dNg==", + "extend-shallow": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/extend-shallow/-/extend-shallow-2.0.1.tgz", + "integrity": "sha1-Ua99YUrZqfYQ6huvu5idaxxWiQ8=", + "dev": true, "requires": { - "has-flag": "^3.0.0" + "is-extendable": "^0.1.0" } }, - "url-parse-lax": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/url-parse-lax/-/url-parse-lax-3.0.0.tgz", - "integrity": "sha1-FrXK/Afb42dsGxmZF3gj1lA6yww=", + "set-value": { + "version": "0.4.3", + "resolved": "https://registry.npmjs.org/set-value/-/set-value-0.4.3.tgz", + "integrity": "sha1-fbCPnT0i3H945Trzw79GZuzfzPE=", + "dev": true, "requires": { - "prepend-http": "^2.0.0" + "extend-shallow": "^2.0.1", + "is-extendable": "^0.1.1", + "is-plain-object": "^2.0.1", + "to-object-path": "^0.3.0" } - }, - "which-module": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/which-module/-/which-module-2.0.0.tgz", - "integrity": "sha1-2e8H3Od7mQK4o6j6SzHD4/fm6Ho=" - }, - "yargs": { - "version": "11.0.0", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-11.0.0.tgz", - "integrity": "sha512-Rjp+lMYQOWtgqojx1dEWorjCofi1YN7AoFvYV7b1gx/7dAAeuI4kN5SZiEvr0ZmsZTOpDRcCqrpI10L31tFkBw==", + } + } + }, + "unique-string": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/unique-string/-/unique-string-1.0.0.tgz", + "integrity": "sha1-nhBXzKhRq7kzmPizOuGHuZyuwRo=", + "dev": true, + "requires": { + "crypto-random-string": "^1.0.0" + } + }, + "unset-value": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/unset-value/-/unset-value-1.0.0.tgz", + "integrity": "sha1-g3aHP30jNRef+x5vw6jtDfyKtVk=", + "dev": true, + "requires": { + "has-value": "^0.3.1", + "isobject": "^3.0.0" + }, + "dependencies": { + "has-value": { + "version": "0.3.1", + "resolved": "https://registry.npmjs.org/has-value/-/has-value-0.3.1.tgz", + "integrity": "sha1-ex9YutpiyoJ+wKIHgCVlSEWZXh8=", + "dev": true, "requires": { - "cliui": "^4.0.0", - "decamelize": "^1.1.1", - "find-up": "^2.1.0", - "get-caller-file": "^1.0.1", - "os-locale": "^2.0.0", - "require-directory": "^2.1.1", - "require-main-filename": "^1.0.1", - "set-blocking": "^2.0.0", - "string-width": "^2.0.0", - "which-module": "^2.0.0", - "y18n": "^3.2.1", - "yargs-parser": "^9.0.2" + "get-value": "^2.0.3", + "has-values": "^0.1.4", + "isobject": "^2.0.0" + }, + "dependencies": { + "isobject": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/isobject/-/isobject-2.1.0.tgz", + "integrity": "sha1-8GVWEJaj8dou9GJy+BXIQNh+DIk=", + "dev": true, + "requires": { + "isarray": "1.0.0" + } + } } }, - "yargs-parser": { - "version": "9.0.2", - "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-9.0.2.tgz", - "integrity": "sha1-nM9qQ0YP5O1Aqbto9I1DuKaMwHc=", - "requires": { - "camelcase": "^4.1.0" - } + "has-values": { + "version": "0.1.4", + "resolved": "https://registry.npmjs.org/has-values/-/has-values-0.1.4.tgz", + "integrity": "sha1-bWHeldkd/Km5oCCJrThL/49it3E=", + "dev": true } } }, + "unzip-response": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/unzip-response/-/unzip-response-2.0.1.tgz", + "integrity": "sha1-0vD3N9FrBhXnKmk17QQhRXLVb5c=", + "dev": true + }, + "upath": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/upath/-/upath-1.1.0.tgz", + "integrity": "sha512-bzpH/oBhoS/QI/YtbkqCg6VEiPYjSZtrHQM6/QnJS6OL9pKUFLqb3aFh4Scvwm45+7iAgiMkLhSbaZxUqmrprw==", + "dev": true + }, + "update-notifier": { + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/update-notifier/-/update-notifier-2.5.0.tgz", + "integrity": "sha512-gwMdhgJHGuj/+wHJJs9e6PcCszpxR1b236igrOkUofGhqJuG+amlIKwApH1IW1WWl7ovZxsX49lMBWLxSdm5Dw==", + "dev": true, + "requires": { + "boxen": "^1.2.1", + "chalk": "^2.0.1", + "configstore": "^3.0.0", + "import-lazy": "^2.1.0", + "is-ci": "^1.0.10", + "is-installed-globally": "^0.1.0", + "is-npm": "^1.0.0", + "latest-version": "^3.0.0", + "semver-diff": "^2.0.0", + "xdg-basedir": "^3.0.0" + } + }, + "uri-js": { + "version": "4.2.2", + "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.2.2.tgz", + "integrity": "sha512-KY9Frmirql91X2Qgjry0Wd4Y+YTdrdZheS8TFwvkbLWf/G5KNJDCh6pKL5OZctEW4+0Baa5idK2ZQuELRwPznQ==", + "dev": true, + "requires": { + "punycode": "^2.1.0" + } + }, + "urix": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/urix/-/urix-0.1.0.tgz", + "integrity": "sha1-2pN/emLiH+wf0Y1Js1wpNQZ6bHI=", + "dev": true + }, + "url-parse-lax": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/url-parse-lax/-/url-parse-lax-1.0.0.tgz", + "integrity": "sha1-evjzA2Rem9eaJy56FKxovAYJ2nM=", + "dev": true, + "requires": { + "prepend-http": "^1.0.1" + } + }, + "url-set-query": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/url-set-query/-/url-set-query-1.0.0.tgz", + "integrity": "sha1-AW6M/Xwg7gXK/neV6JK9BwL6ozk=" + }, + "use": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/use/-/use-3.1.1.tgz", + "integrity": "sha512-cwESVXlO3url9YWlFW/TA9cshCEhtu7IKJ/p5soJ/gGpj7vbvFrAY/eIioQ6Dw23KjZhYgiIo8HOs1nQ2vr/oQ==", + "dev": true + }, + "utf8": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/utf8/-/utf8-2.1.1.tgz", + "integrity": "sha1-LgHbAvfY0JRPdxBPFgnrDDBM92g=" + }, + "util-deprecate": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", + "integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=", + "dev": true + }, + "uuid": { + "version": "3.3.2", + "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.3.2.tgz", + "integrity": "sha512-yXJmeNaw3DnnKAOKJE51sL/ZaYfWJRl1pK9dr19YFCu0ObS231AB1/LbqTKRAQ5kw8A90rA6fr4riOUpTZvQZA==", + "dev": true + }, + "validate-npm-package-license": { + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/validate-npm-package-license/-/validate-npm-package-license-3.0.4.tgz", + "integrity": "sha512-DpKm2Ui/xN7/HQKCtpZxoRWBhZ9Z0kqtygG8XCgNQ8ZlDnxuQmWhj566j8fN4Cu3/JmbhsDo7fcAJq4s9h27Ew==", + "requires": { + "spdx-correct": "^3.0.0", + "spdx-expression-parse": "^3.0.0" + } + }, + "verror": { + "version": "1.10.0", + "resolved": "https://registry.npmjs.org/verror/-/verror-1.10.0.tgz", + "integrity": "sha1-OhBcoXBTr1XW4nDB+CiGguGNpAA=", + "dev": true, + "requires": { + "assert-plus": "^1.0.0", + "core-util-is": "1.0.2", + "extsprintf": "^1.2.0" + } + }, + "web3": { + "version": "0.18.4", + "resolved": "https://registry.npmjs.org/web3/-/web3-0.18.4.tgz", + "integrity": "sha1-gewXhBRUkfLqqJVbMcBgSeB8Xn0=", + "dev": true, + "requires": { + "bignumber.js": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", + "crypto-js": "^3.1.4", + "utf8": "^2.1.1", + "xhr2": "*", + "xmlhttprequest": "*" + } + }, + "web3-utils": { + "version": "1.0.0-beta.46", + "resolved": "https://registry.npmjs.org/web3-utils/-/web3-utils-1.0.0-beta.46.tgz", + "integrity": "sha512-mSz+NrAil2fDZkxTXHPntCclZ8DofMjv8Q+BYR0VAyzTzylpYNXAV0WDdxBp/sXgniWRZXZMF7OkQNWqhZ1J9g==", + "requires": { + "@babel/runtime": "^7.3.1", + "@types/bn.js": "^4.11.4", + "@types/node": "^10.12.18", + "bn.js": "4.11.8", + "eth-lib": "0.2.8", + "ethjs-unit": "^0.1.6", + "lodash": "^4.17.11", + "number-to-bn": "1.7.0", + "randomhex": "0.1.5", + "utf8": "2.1.1" + } + }, "which": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/which/-/which-1.3.0.tgz", - "integrity": "sha512-xcJpopdamTuY5duC/KnTTNBraPK54YwpenP4lzxU8H91GudWpFv38u0CKjclE1Wi2EH2EDz5LRcHcKbCIzqGyg==", + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/which/-/which-1.3.1.tgz", + "integrity": "sha512-HxJdYWq1MTIQbJ3nw0cqssHoTNU267KlrDuGZ1WYlxDStUtKUhOaJmh112/TZmHxxUfuJqPXSOm7tDyas0OSIQ==", + "dev": true, "requires": { "isexe": "^2.0.0" } @@ -8448,9 +4994,9 @@ "integrity": "sha1-u6Y8qGGUiZT/MHc2CJ47lgJsKk8=" }, "widest-line": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/widest-line/-/widest-line-2.0.0.tgz", - "integrity": "sha1-AUKk6KJD+IgsAjOqDgKBqnYVInM=", + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/widest-line/-/widest-line-2.0.1.tgz", + "integrity": "sha512-Ba5m9/Fa4Xt9eb2ELXt77JxVDV8w7qQrH0zS/TWSJdLyAwQjWoOzpzj5lwVftDz6n/EOu3tNACS84v509qwnJA==", "dev": true, "requires": { "string-width": "^2.1.1" @@ -8515,9 +5061,9 @@ "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=" }, "write-file-atomic": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-2.3.0.tgz", - "integrity": "sha512-xuPeK4OdjWqtfi59ylvVL0Yn35SF3zgcAcv7rBPFHVaEapaDr4GdGgm3j7ckTwH9wHL7fGmgfAnb0+THrHb8tA==", + "version": "2.4.2", + "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-2.4.2.tgz", + "integrity": "sha512-s0b6vB3xIVRLWywa6X9TOMA7k9zio0TMOsl9ZnDkliA/cfJlpHXAscj0gbHVJiTdIuAYpIyqS5GW91fqm6gG5g==", "dev": true, "requires": { "graceful-fs": "^4.1.11", @@ -8525,16 +5071,6 @@ "signal-exit": "^3.0.2" } }, - "ws": { - "version": "3.3.3", - "resolved": "https://registry.npmjs.org/ws/-/ws-3.3.3.tgz", - "integrity": "sha512-nnWLa/NwZSt4KQJu51MYlCcSQ5g7INpOrOMt4XV8j4dqTXdmlUmSHQ8/oLC069ckre0fRsgfvsKwbTdtKLCDkA==", - "requires": { - "async-limiter": "~1.0.0", - "safe-buffer": "~5.1.0", - "ultron": "~1.1.0" - } - }, "xdg-basedir": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/xdg-basedir/-/xdg-basedir-3.0.0.tgz", @@ -8542,9 +5078,9 @@ "dev": true }, "xhr": { - "version": "2.4.1", - "resolved": "https://registry.npmjs.org/xhr/-/xhr-2.4.1.tgz", - "integrity": "sha512-pAIU5vBr9Hiy5cpFIbPnwf0C18ZF86DBsZKrlsf87N5De/JbA6RJ83UP/cv+aljl4S40iRVMqP4pr4sF9Dnj0A==", + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/xhr/-/xhr-2.5.0.tgz", + "integrity": "sha512-4nlO/14t3BNUZRXIXfXe+3N6w3s1KoxcJUUURctd64BLRe67E4gRwp4PjywtDY72fXpZ1y6Ch0VZQRY/gMPzzQ==", "requires": { "global": "~4.3.0", "is-function": "^1.0.1", @@ -8599,7 +5135,8 @@ "yallist": { "version": "2.1.2", "resolved": "https://registry.npmjs.org/yallist/-/yallist-2.1.2.tgz", - "integrity": "sha1-HBH5IY8HYImkfdUS+TxmmaaoHVI=" + "integrity": "sha1-HBH5IY8HYImkfdUS+TxmmaaoHVI=", + "dev": true }, "yargs": { "version": "4.8.1", @@ -8630,201 +5167,6 @@ "camelcase": "^3.0.0", "lodash.assign": "^4.0.6" } - }, - "yeoman-environment": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/yeoman-environment/-/yeoman-environment-2.0.5.tgz", - "integrity": "sha512-6/W7/B54OPHJXob0n0+pmkwFsirC8cokuQkPSmT/D0lCcSxkKtg/BA6ZnjUBIwjuGqmw3DTrT4en++htaUju5g==", - "requires": { - "chalk": "^2.1.0", - "debug": "^3.1.0", - "diff": "^3.3.1", - "escape-string-regexp": "^1.0.2", - "globby": "^6.1.0", - "grouped-queue": "^0.3.3", - "inquirer": "^3.3.0", - "is-scoped": "^1.0.0", - "lodash": "^4.17.4", - "log-symbols": "^2.1.0", - "mem-fs": "^1.1.0", - "text-table": "^0.2.0", - "untildify": "^3.0.2" - }, - "dependencies": { - "ansi-regex": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", - "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=" - }, - "debug": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", - "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", - "requires": { - "ms": "2.0.0" - } - }, - "diff": { - "version": "3.5.0", - "resolved": "https://registry.npmjs.org/diff/-/diff-3.5.0.tgz", - "integrity": "sha512-A46qtFgd+g7pDZinpnwiRJtxbC1hpgf0uzP3iG89scHk0AUC7A1TGxf5OiiOUv/JMZR8GOt8hL900hV0bOy5xA==" - }, - "inquirer": { - "version": "3.3.0", - "resolved": "https://registry.npmjs.org/inquirer/-/inquirer-3.3.0.tgz", - "integrity": "sha512-h+xtnyk4EwKvFWHrUYsWErEVR+igKtLdchu+o0Z1RL7VU/jVMFbYir2bp6bAj8efFNxWqHX0dIss6fJQ+/+qeQ==", - "requires": { - "ansi-escapes": "^3.0.0", - "chalk": "^2.0.0", - "cli-cursor": "^2.1.0", - "cli-width": "^2.0.0", - "external-editor": "^2.0.4", - "figures": "^2.0.0", - "lodash": "^4.3.0", - "mute-stream": "0.0.7", - "run-async": "^2.2.0", - "rx-lite": "^4.0.8", - "rx-lite-aggregates": "^4.0.8", - "string-width": "^2.1.0", - "strip-ansi": "^4.0.0", - "through": "^2.3.6" - } - }, - "is-fullwidth-code-point": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", - "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=" - }, - "string-width": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", - "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", - "requires": { - "is-fullwidth-code-point": "^2.0.0", - "strip-ansi": "^4.0.0" - } - }, - "strip-ansi": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", - "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", - "requires": { - "ansi-regex": "^3.0.0" - } - } - } - }, - "yeoman-generator": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/yeoman-generator/-/yeoman-generator-2.0.3.tgz", - "integrity": "sha512-mODmrZ26a94djmGZZuIiomSGlN4wULdou29ZwcySupb2e9FdvoCl7Ps2FqHFjEHio3kOl/iBeaNqrnx3C3NwWg==", - "requires": { - "async": "^2.6.0", - "chalk": "^2.3.0", - "cli-table": "^0.3.1", - "cross-spawn": "^5.1.0", - "dargs": "^5.1.0", - "dateformat": "^3.0.2", - "debug": "^3.1.0", - "detect-conflict": "^1.0.0", - "error": "^7.0.2", - "find-up": "^2.1.0", - "github-username": "^4.0.0", - "istextorbinary": "^2.1.0", - "lodash": "^4.17.4", - "make-dir": "^1.1.0", - "mem-fs-editor": "^3.0.2", - "minimist": "^1.2.0", - "pretty-bytes": "^4.0.2", - "read-chunk": "^2.1.0", - "read-pkg-up": "^3.0.0", - "rimraf": "^2.6.2", - "run-async": "^2.0.0", - "shelljs": "^0.8.0", - "text-table": "^0.2.0", - "through2": "^2.0.0", - "yeoman-environment": "^2.0.5" - }, - "dependencies": { - "debug": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", - "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", - "requires": { - "ms": "2.0.0" - } - }, - "find-up": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", - "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", - "requires": { - "locate-path": "^2.0.0" - } - }, - "load-json-file": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-4.0.0.tgz", - "integrity": "sha1-L19Fq5HjMhYjT9U62rZo607AmTs=", - "requires": { - "graceful-fs": "^4.1.2", - "parse-json": "^4.0.0", - "pify": "^3.0.0", - "strip-bom": "^3.0.0" - } - }, - "minimist": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz", - "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=" - }, - "parse-json": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-4.0.0.tgz", - "integrity": "sha1-vjX1Qlvh9/bHRxhPmKeIy5lHfuA=", - "requires": { - "error-ex": "^1.3.1", - "json-parse-better-errors": "^1.0.1" - } - }, - "path-type": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/path-type/-/path-type-3.0.0.tgz", - "integrity": "sha512-T2ZUsdZFHgA3u4e5PfPbjd7HDDpxPnQb5jN0SrDsjNSuVXHJqtwTnWqG0B1jZrgmJ/7lj1EmVIByWt1gxGkWvg==", - "requires": { - "pify": "^3.0.0" - } - }, - "pify": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", - "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=" - }, - "read-pkg": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-3.0.0.tgz", - "integrity": "sha1-nLxoaXj+5l0WwA4rGcI3/Pbjg4k=", - "requires": { - "load-json-file": "^4.0.0", - "normalize-package-data": "^2.3.2", - "path-type": "^3.0.0" - } - }, - "read-pkg-up": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/read-pkg-up/-/read-pkg-up-3.0.0.tgz", - "integrity": "sha1-PtSWaF26D4/hGNBpHcUfSh/5bwc=", - "requires": { - "find-up": "^2.0.0", - "read-pkg": "^3.0.0" - } - }, - "strip-bom": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-3.0.0.tgz", - "integrity": "sha1-IzTBjpx1n3vdVv3vfprj1YjmjtM=" - } - } } } -} \ No newline at end of file +} diff --git a/package.json b/package.json index efd6833eb..3dfb3abaf 100644 --- a/package.json +++ b/package.json @@ -24,7 +24,7 @@ "chai-bignumber": "^2.0.2", "eth-gas-reporter": "^0.1.12", "nodemon": "^1.17.3", - "solidity-coverage": "^0.4.15", + "solidity-coverage": "^0.5.11", "truffle-flattener": "^1.2.3" } } diff --git a/test/factories/foreign_factory.test.js b/test/factories/foreign_factory.test.js deleted file mode 100644 index 04e080448..000000000 --- a/test/factories/foreign_factory.test.js +++ /dev/null @@ -1,138 +0,0 @@ -const ForeignBridgeFactory = artifacts.require("ForeignBridgeFactory.sol") -const ForeignBridge = artifacts.require("ForeignBridgeErcToErc.sol") -const BridgeValidators = artifacts.require("BridgeValidators.sol") -const ERC677BridgeToken = artifacts.require("ERC677BridgeToken.sol") - -const {ERROR_MSG, ZERO_ADDRESS, INVALID_ARGUMENTS} = require('../setup') -const {getEventFromLogs} = require('../helpers/helpers') -const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")) -const requiredSignatures = 1 -const requiredBlockConfirmations = 8 -const gasPrice = web3.toWei('1', 'gwei') -const oneEther = web3.toBigNumber(web3.toWei(1, "ether")) -const homeDailyLimit = oneEther -const homeMaxPerTx = halfEther -const maxPerTx = halfEther - -contract('ForeignBridgeFactory', async (accounts) => { - let validatorContract, foreignBridgeContract, owner - before(async () => { - validatorContract = await BridgeValidators.new() - foreignBridgeContract = await ForeignBridge.new() - owner = accounts[0] - }) - - describe('#initialize', async () => { - it('should initialize', async () => { - let foreignBridgeFactory = await ForeignBridgeFactory.new() - - false.should.be.equal(await foreignBridgeFactory.isInitialized()) - ZERO_ADDRESS.should.be.equal(await foreignBridgeFactory.bridgeValidatorsImplementation()) - '0'.should.be.bignumber.equal(await foreignBridgeFactory.requiredSignatures()) - ZERO_ADDRESS.should.be.equal(await foreignBridgeFactory.bridgeValidatorsOwner()) - ZERO_ADDRESS.should.be.equal(await foreignBridgeFactory.bridgeValidatorsProxyOwner()) - ZERO_ADDRESS.should.be.equal(await foreignBridgeFactory.foreignBridgeErcToErcImplementation()) - '0'.should.be.bignumber.equal(await foreignBridgeFactory.requiredBlockConfirmations()) - '0'.should.be.bignumber.equal(await foreignBridgeFactory.gasPrice()) - '0'.should.be.bignumber.equal(await foreignBridgeFactory.foreignMaxPerTx()) - '0'.should.be.bignumber.equal(await foreignBridgeFactory.homeDailyLimit()) - '0'.should.be.bignumber.equal(await foreignBridgeFactory.homeMaxPerTx()) - ZERO_ADDRESS.should.be.equal(await foreignBridgeFactory.foreignBridgeOwner()) - ZERO_ADDRESS.should.be.equal(await foreignBridgeFactory.foreignBridgeProxyOwner()) - - await foreignBridgeFactory.initialize().should.be.rejectedWith(INVALID_ARGUMENTS) - await foreignBridgeFactory.initialize(ZERO_ADDRESS, validatorContract.address, requiredSignatures, [owner], owner, foreignBridgeContract.address, requiredBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) - await foreignBridgeFactory.initialize(owner, ZERO_ADDRESS, requiredSignatures, [owner], owner, foreignBridgeContract.address, requiredBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) - await foreignBridgeFactory.initialize(owner, validatorContract.address, 0, [owner], owner, foreignBridgeContract.address, requiredBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) - await foreignBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [], owner, foreignBridgeContract.address, requiredBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) - await foreignBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], ZERO_ADDRESS, foreignBridgeContract.address, requiredBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) - await foreignBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, ZERO_ADDRESS, requiredBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) - await foreignBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, foreignBridgeContract.address, 0, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) - await foreignBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, foreignBridgeContract.address, requiredBlockConfirmations, 0, maxPerTx, homeDailyLimit, homeMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) - await foreignBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, foreignBridgeContract.address, requiredBlockConfirmations, gasPrice, maxPerTx, 0, homeMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) - await foreignBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, foreignBridgeContract.address, requiredBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeDailyLimit, owner, owner).should.be.rejectedWith(ERROR_MSG) - await foreignBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, foreignBridgeContract.address, requiredBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, ZERO_ADDRESS, owner).should.be.rejectedWith(ERROR_MSG) - await foreignBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, foreignBridgeContract.address, requiredBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner, ZERO_ADDRESS).should.be.rejectedWith(ERROR_MSG) - - await foreignBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, foreignBridgeContract.address, requiredBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner, owner) - - true.should.be.equal(await foreignBridgeFactory.isInitialized()) - validatorContract.address.should.be.equal(await foreignBridgeFactory.bridgeValidatorsImplementation()) - requiredSignatures.should.be.bignumber.equal(await foreignBridgeFactory.requiredSignatures()) - owner.should.be.equal(await foreignBridgeFactory.bridgeValidatorsOwner()) - owner.should.be.equal(await foreignBridgeFactory.bridgeValidatorsProxyOwner()) - foreignBridgeContract.address.should.be.equal(await foreignBridgeFactory.foreignBridgeErcToErcImplementation()) - requiredBlockConfirmations.should.be.bignumber.equal(await foreignBridgeFactory.requiredBlockConfirmations()) - gasPrice.should.be.bignumber.equal(await foreignBridgeFactory.gasPrice()) - maxPerTx.should.be.bignumber.equal(await foreignBridgeFactory.foreignMaxPerTx()) - homeDailyLimit.should.be.bignumber.equal(await foreignBridgeFactory.homeDailyLimit()) - homeMaxPerTx.should.be.bignumber.equal(await foreignBridgeFactory.homeMaxPerTx()) - owner.should.be.equal(await foreignBridgeFactory.foreignBridgeOwner()) - owner.should.be.equal(await foreignBridgeFactory.foreignBridgeProxyOwner()) - const [major, minor, patch] = await foreignBridgeFactory.getBridgeFactoryVersion() - major.should.be.bignumber.gte(0) - minor.should.be.bignumber.gte(0) - patch.should.be.bignumber.gte(0) - }) - }) - - describe('#deployForeignBridge', async () => { - let foreignBridgeFactory - before(async () => { - foreignBridgeFactory = await ForeignBridgeFactory.new() - await foreignBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, foreignBridgeContract.address, requiredBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner, owner) - }) - - it('should deploy a foreign bridge', async () => { - let token = await ERC677BridgeToken.new("Some ERC20", "SMT_1", 18) - - const {logs} = await foreignBridgeFactory.deployForeignBridge(token.address) - const {args} = getEventFromLogs(logs, 'ForeignBridgeDeployed') - - ZERO_ADDRESS.should.not.be.equal(args._foreignBridge) - ZERO_ADDRESS.should.not.be.equal(args._foreignValidators) - args._blockNumber.should.be.bignumber.gte(0) - - let foreignBridge = await ForeignBridge.at(args._foreignBridge) - true.should.be.equal(await foreignBridge.isInitialized()) - args._foreignValidators.should.be.equal(await foreignBridge.validatorContract()) - token.address.should.be.equal(await foreignBridge.erc20token()) - const deployedAtBlock = await foreignBridge.deployedAtBlock() - deployedAtBlock.should.be.bignumber.above(0) - requiredBlockConfirmations.should.be.bignumber.equal(await foreignBridge.requiredBlockConfirmations()) - gasPrice.should.be.bignumber.equal(await foreignBridge.gasPrice()) - const bridgeMode = '0xba4690f5' // 4 bytes of keccak256('erc-to-erc-core') - bridgeMode.should.be.equal(await foreignBridge.getBridgeMode()) - const [major, minor, patch] = await foreignBridge.getBridgeInterfacesVersion() - major.should.be.bignumber.gte(0) - minor.should.be.bignumber.gte(0) - patch.should.be.bignumber.gte(0) - }) - - it('should deploy a second foreign bridge using same factory', async () => { - let token = await ERC677BridgeToken.new("Another ERC20", "SMT_2", 18) - - const {logs} = await foreignBridgeFactory.deployForeignBridge(token.address) - const {args} = getEventFromLogs(logs, 'ForeignBridgeDeployed') - - ZERO_ADDRESS.should.not.be.equal(args._foreignBridge) - ZERO_ADDRESS.should.not.be.equal(args._foreignValidators) - args._blockNumber.should.be.bignumber.gte(0) - - let foreignBridge = await ForeignBridge.at(args._foreignBridge) - true.should.be.equal(await foreignBridge.isInitialized()) - args._foreignValidators.should.be.equal(await foreignBridge.validatorContract()) - token.address.should.be.equal(await foreignBridge.erc20token()) - const deployedAtBlock = await foreignBridge.deployedAtBlock() - deployedAtBlock.should.be.bignumber.above(0) - requiredBlockConfirmations.should.be.bignumber.equal(await foreignBridge.requiredBlockConfirmations()) - gasPrice.should.be.bignumber.equal(await foreignBridge.gasPrice()) - const bridgeMode = '0xba4690f5' // 4 bytes of keccak256('erc-to-erc-core') - bridgeMode.should.be.equal(await foreignBridge.getBridgeMode()) - const [major, minor, patch] = await foreignBridge.getBridgeInterfacesVersion() - major.should.be.bignumber.gte(0) - minor.should.be.bignumber.gte(0) - patch.should.be.bignumber.gte(0) - }) - }) -}) diff --git a/test/factories/home_factory.test.js b/test/factories/home_factory.test.js deleted file mode 100644 index 2bcbfaf7d..000000000 --- a/test/factories/home_factory.test.js +++ /dev/null @@ -1,149 +0,0 @@ -const HomeBridgeFactory = artifacts.require("HomeBridgeFactory.sol") -const HomeBridge = artifacts.require("HomeBridgeErcToErc.sol") -const BridgeValidators = artifacts.require("BridgeValidators.sol") - -const {ERROR_MSG, ZERO_ADDRESS, INVALID_ARGUMENTS} = require('../setup') -const {getEventFromLogs} = require('../helpers/helpers') -const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")) -const quarterEther = web3.toBigNumber(web3.toWei(0.25, "ether")) -const requiredSignatures = 1 -const requiredBlockConfirmations = 8 -const gasPrice = web3.toWei('1', 'gwei') -const oneEther = web3.toBigNumber(web3.toWei(1, "ether")) -const homeDailyLimit = oneEther -const homeMaxPerTx = halfEther -const minPerTx = quarterEther -const foreignDailyLimit = oneEther -const foreignMaxPerTx = halfEther - -contract('HomeBridgeFactory', async (accounts) => { - let validatorContract, homeBridgeContract, owner - before(async () => { - validatorContract = await BridgeValidators.new() - homeBridgeContract = await HomeBridge.new() - owner = accounts[0] - }) - - describe('#initialize', async () => { - it('should initialize', async () => { - let homeBridgeFactory = await HomeBridgeFactory.new() - - false.should.be.equal(await homeBridgeFactory.isInitialized()) - ZERO_ADDRESS.should.be.equal(await homeBridgeFactory.bridgeValidatorsImplementation()) - '0'.should.be.bignumber.equal(await homeBridgeFactory.requiredSignatures()) - ZERO_ADDRESS.should.be.equal(await homeBridgeFactory.bridgeValidatorsOwner()) - ZERO_ADDRESS.should.be.equal(await homeBridgeFactory.bridgeValidatorsProxyOwner()) - ZERO_ADDRESS.should.be.equal(await homeBridgeFactory.homeBridgeErcToErcImplementation()) - '0'.should.be.bignumber.equal(await homeBridgeFactory.requiredBlockConfirmations()) - '0'.should.be.bignumber.equal(await homeBridgeFactory.gasPrice()) - '0'.should.be.bignumber.equal(await homeBridgeFactory.homeDailyLimit()) - '0'.should.be.bignumber.equal(await homeBridgeFactory.homeMaxPerTx()) - '0'.should.be.bignumber.equal(await homeBridgeFactory.minPerTx()) - '0'.should.be.bignumber.equal(await homeBridgeFactory.foreignDailyLimit()) - '0'.should.be.bignumber.equal(await homeBridgeFactory.foreignMaxPerTx()) - ZERO_ADDRESS.should.be.equal(await homeBridgeFactory.homeBridgeOwner()) - ZERO_ADDRESS.should.be.equal(await homeBridgeFactory.homeBridgeProxyOwner()) - - await homeBridgeFactory.initialize().should.be.rejectedWith(INVALID_ARGUMENTS) - await homeBridgeFactory.initialize(ZERO_ADDRESS, validatorContract.address, requiredSignatures, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) - await homeBridgeFactory.initialize(owner, ZERO_ADDRESS, requiredSignatures, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) - await homeBridgeFactory.initialize(owner, validatorContract.address, 0, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) - await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) - await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], ZERO_ADDRESS, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) - await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, ZERO_ADDRESS, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) - await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, homeBridgeContract.address, 0, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) - await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, 0, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) - await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, 0, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) - await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, 0, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) - await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, 0, foreignDailyLimit, foreignMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) - await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, 0, foreignMaxPerTx, owner, owner).should.be.rejectedWith(ERROR_MSG) - await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignDailyLimit, owner, owner).should.be.rejectedWith(ERROR_MSG) - await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, ZERO_ADDRESS, owner).should.be.rejectedWith(ERROR_MSG) - await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, ZERO_ADDRESS).should.be.rejectedWith(ERROR_MSG) - - await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, owner) - - true.should.be.equal(await homeBridgeFactory.isInitialized()) - validatorContract.address.should.be.equal(await homeBridgeFactory.bridgeValidatorsImplementation()) - requiredSignatures.should.be.bignumber.equal(await homeBridgeFactory.requiredSignatures()) - owner.should.be.equal(await homeBridgeFactory.bridgeValidatorsOwner()) - owner.should.be.equal(await homeBridgeFactory.bridgeValidatorsProxyOwner()) - homeBridgeContract.address.should.be.equal(await homeBridgeFactory.homeBridgeErcToErcImplementation()) - requiredBlockConfirmations.should.be.bignumber.equal(await homeBridgeFactory.requiredBlockConfirmations()) - gasPrice.should.be.bignumber.equal(await homeBridgeFactory.gasPrice()) - homeDailyLimit.should.be.bignumber.equal(await homeBridgeFactory.homeDailyLimit()) - homeMaxPerTx.should.be.bignumber.equal(await homeBridgeFactory.homeMaxPerTx()) - minPerTx.should.be.bignumber.equal(await homeBridgeFactory.minPerTx()) - foreignDailyLimit.should.be.bignumber.equal(await homeBridgeFactory.foreignDailyLimit()) - foreignMaxPerTx.should.be.bignumber.equal(await homeBridgeFactory.foreignMaxPerTx()) - owner.should.be.equal(await homeBridgeFactory.homeBridgeOwner()) - owner.should.be.equal(await homeBridgeFactory.homeBridgeProxyOwner()) - const [major, minor, patch] = await homeBridgeFactory.getBridgeFactoryVersion() - major.should.be.bignumber.gte(0) - minor.should.be.bignumber.gte(0) - patch.should.be.bignumber.gte(0) - }) - }) - - describe('#deployHomeBridge', async () => { - let homeBridgeFactory - before(async () => { - homeBridgeFactory = await HomeBridgeFactory.new() - await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, owner) - }) - - it('should deploy a home bridge', async () => { - let token = { name: "Some ERC20", symbol: "SMT_1", decimals: 18 } - - const {logs} = await homeBridgeFactory.deployHomeBridge(token.name, token.symbol, token.decimals) - const {args} = getEventFromLogs(logs, 'HomeBridgeDeployed') - - ZERO_ADDRESS.should.not.be.equal(args._homeBridge) - ZERO_ADDRESS.should.not.be.equal(args._homeValidators) - ZERO_ADDRESS.should.not.be.equal(args._token) - args._blockNumber.should.be.bignumber.gte(0) - - let homeBridge = await HomeBridge.at(args._homeBridge) - true.should.be.equal(await homeBridge.isInitialized()) - args._homeValidators.should.be.equal(await homeBridge.validatorContract()) - const deployedAtBlock = await homeBridge.deployedAtBlock() - deployedAtBlock.should.be.bignumber.above(0) - requiredBlockConfirmations.should.be.bignumber.equal(await homeBridge.requiredBlockConfirmations()) - gasPrice.should.be.bignumber.equal(await homeBridge.gasPrice()) - const bridgeMode = '0xba4690f5' // 4 bytes of keccak256('erc-to-erc-core') - const mode = await homeBridge.getBridgeMode() - mode.should.be.equal(bridgeMode) - const [major, minor, patch] = await homeBridge.getBridgeInterfacesVersion() - major.should.be.bignumber.gte(0) - minor.should.be.bignumber.gte(0) - patch.should.be.bignumber.gte(0) - }) - - it('should deploy a second home bridge using same factory', async () => { - let token = { name: "Another ERC20", symbol: "SMT_2", decimals: 18 } - - const {logs} = await homeBridgeFactory.deployHomeBridge(token.name, token.symbol, token.decimals) - const {args} = getEventFromLogs(logs, 'HomeBridgeDeployed') - - ZERO_ADDRESS.should.not.be.equal(args._homeBridge) - ZERO_ADDRESS.should.not.be.equal(args._homeValidators) - ZERO_ADDRESS.should.not.be.equal(args._token) - args._blockNumber.should.be.bignumber.gte(0) - - let homeBridge = await HomeBridge.at(args._homeBridge) - true.should.be.equal(await homeBridge.isInitialized()) - args._homeValidators.should.be.equal(await homeBridge.validatorContract()) - const deployedAtBlock = await homeBridge.deployedAtBlock() - deployedAtBlock.should.be.bignumber.above(0) - requiredBlockConfirmations.should.be.bignumber.equal(await homeBridge.requiredBlockConfirmations()) - gasPrice.should.be.bignumber.equal(await homeBridge.gasPrice()) - const bridgeMode = '0xba4690f5' // 4 bytes of keccak256('erc-to-erc-core') - const mode = await homeBridge.getBridgeMode() - mode.should.be.equal(bridgeMode) - const [major, minor, patch] = await homeBridge.getBridgeInterfacesVersion() - major.should.be.bignumber.gte(0) - minor.should.be.bignumber.gte(0) - patch.should.be.bignumber.gte(0) - }) - }) -}) diff --git a/test/helpers/helpers.js b/test/helpers/helpers.js index 306c40008..cb276a2a8 100644 --- a/test/helpers/helpers.js +++ b/test/helpers/helpers.js @@ -111,8 +111,3 @@ module.exports.range = range; function ignoreExpectedError() { } module.exports.ignoreExpectedError = ignoreExpectedError; - -function getEventFromLogs(logs, eventName) { - return logs.filter(log => log.event === eventName)[0] -} -module.exports.getEventFromLogs = getEventFromLogs; diff --git a/test/mapper/home_mapper.test.js b/test/mapper/home_mapper.test.js deleted file mode 100644 index c1a6ccca4..000000000 --- a/test/mapper/home_mapper.test.js +++ /dev/null @@ -1,160 +0,0 @@ -const BridgeMapper = artifacts.require("BridgeMapper.sol") -const ForeignBridgeFactory = artifacts.require("ForeignBridgeFactory.sol") -const HomeBridgeFactory = artifacts.require("HomeBridgeFactory.sol") -const ForeignBridge = artifacts.require("ForeignBridgeErcToErc.sol") -const HomeBridge = artifacts.require("HomeBridgeErcToErc.sol") -const BridgeValidators = artifacts.require("BridgeValidators.sol") -const ERC677BridgeToken = artifacts.require("ERC677BridgeToken.sol") - -const {ERROR_MSG, ZERO_ADDRESS, INVALID_ARGUMENTS} = require('../setup') -const {getEventFromLogs} = require('../helpers/helpers') -const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")) -const quarterEther = web3.toBigNumber(web3.toWei(0.25, "ether")) -const requiredSignatures = 1 -const requiredBlockConfirmations = 8 -const gasPrice = web3.toWei('1', 'gwei') -const oneEther = web3.toBigNumber(web3.toWei(1, "ether")) -const homeDailyLimit = oneEther -const homeMaxPerTx = halfEther -const maxPerTx = halfEther -const minPerTx = quarterEther -const foreignDailyLimit = oneEther -const foreignMaxPerTx = halfEther - -contract('BridgeMapper', async (accounts) => { - let validatorContract, owner, foreignBridgeContract, homeBridgeContract, homeBridgeFactory, foreignBridgeFactory - before(async () => { - owner = accounts[0] - - validatorContract = await BridgeValidators.new() - foreignBridgeContract = await ForeignBridge.new() - homeBridgeContract = await HomeBridge.new() - foreignBridgeFactory = await ForeignBridgeFactory.new() - homeBridgeFactory = await HomeBridgeFactory.new() - - await foreignBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, foreignBridgeContract.address, requiredBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner, owner) - await homeBridgeFactory.initialize(owner, validatorContract.address, requiredSignatures, [owner], owner, homeBridgeContract.address, requiredBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, minPerTx, foreignDailyLimit, foreignMaxPerTx, owner, owner) - }) - - describe('#initialize', async () => { - it('should initialize', async () => { - let bridgeMapper = await BridgeMapper.new() - - false.should.be.equal(await bridgeMapper.isInitialized()) - ZERO_ADDRESS.should.be.equal(await bridgeMapper.owner()) - - await bridgeMapper.initialize().should.be.rejectedWith(INVALID_ARGUMENTS) - - await bridgeMapper.initialize(owner) - - true.should.be.equal(await bridgeMapper.isInitialized()) - owner.should.be.equal(await bridgeMapper.owner()) - }) - }) - - describe('#addBridgeMapping', async () => { - let bridgeMapper - before(async () => { - bridgeMapper = await BridgeMapper.new() - await bridgeMapper.initialize(owner) - }) - - it('should not add mapping if params are wrong/missng', async () => { - let foreignToken = await ERC677BridgeToken.new("Foreign ERC20", "FSMT", 18) - let foreignBridgeDeployedArgs = getEventFromLogs((await foreignBridgeFactory.deployForeignBridge(foreignToken.address)).logs, 'ForeignBridgeDeployed').args - - let homeToken = { name: "Home ERC20", symbol: "HSMT", decimals: 18 } - let homeBridgeDeployedArgs = getEventFromLogs((await homeBridgeFactory.deployHomeBridge(homeToken.name, homeToken.symbol, homeToken.decimals)).logs, 'HomeBridgeDeployed').args - - await bridgeMapper.addBridgeMapping().should.be.rejectedWith(INVALID_ARGUMENTS) - await bridgeMapper.addBridgeMapping(ZERO_ADDRESS, homeBridgeDeployedArgs._token, foreignBridgeDeployedArgs._foreignBridge, homeBridgeDeployedArgs._homeBridge, foreignBridgeDeployedArgs._blockNumber, homeBridgeDeployedArgs._blockNumber).should.be.rejectedWith(ERROR_MSG) - await bridgeMapper.addBridgeMapping(foreignToken.address, ZERO_ADDRESS, foreignBridgeDeployedArgs._foreignBridge, homeBridgeDeployedArgs._homeBridge, foreignBridgeDeployedArgs._blockNumber, homeBridgeDeployedArgs._blockNumber).should.be.rejectedWith(ERROR_MSG) - await bridgeMapper.addBridgeMapping(foreignToken.address, homeBridgeDeployedArgs._token, ZERO_ADDRESS, homeBridgeDeployedArgs._homeBridge, foreignBridgeDeployedArgs._blockNumber, homeBridgeDeployedArgs._blockNumber).should.be.rejectedWith(ERROR_MSG) - await bridgeMapper.addBridgeMapping(foreignToken.address, homeBridgeDeployedArgs._token, foreignBridgeDeployedArgs._foreignBridge, ZERO_ADDRESS, foreignBridgeDeployedArgs._blockNumber, homeBridgeDeployedArgs._blockNumber).should.be.rejectedWith(ERROR_MSG) - await bridgeMapper.addBridgeMapping(foreignToken.address, homeBridgeDeployedArgs._token, foreignBridgeDeployedArgs._foreignBridge, homeBridgeDeployedArgs._homeBridge, 0, homeBridgeDeployedArgs._blockNumber).should.be.rejectedWith(ERROR_MSG) - await bridgeMapper.addBridgeMapping(foreignToken.address, homeBridgeDeployedArgs._token, foreignBridgeDeployedArgs._foreignBridge, homeBridgeDeployedArgs._homeBridge, foreignBridgeDeployedArgs._blockNumber, 0).should.be.rejectedWith(ERROR_MSG) - }) - - it('should add a bridge mapping', async () => { - let foreignToken = await ERC677BridgeToken.new("Foreign ERC20", "FSMT_1", 18) - let foreignBridgeDeployedArgs = getEventFromLogs((await foreignBridgeFactory.deployForeignBridge(foreignToken.address)).logs, 'ForeignBridgeDeployed').args - - let homeToken = { name: "Home ERC20", symbol: "HSMT_1", decimals: 18 } - let homeBridgeDeployedArgs = getEventFromLogs((await homeBridgeFactory.deployHomeBridge(homeToken.name, homeToken.symbol, homeToken.decimals)).logs, 'HomeBridgeDeployed').args - - let {logs} = await bridgeMapper.addBridgeMapping(foreignToken.address, homeBridgeDeployedArgs._token, foreignBridgeDeployedArgs._foreignBridge, homeBridgeDeployedArgs._homeBridge, foreignBridgeDeployedArgs._blockNumber, homeBridgeDeployedArgs._blockNumber) - let {args} = getEventFromLogs(logs, 'BridgeMappingUpdated') - - foreignToken.address.should.be.equal(args.foreignToken) - homeBridgeDeployedArgs._token.should.be.equal(args.homeToken) - foreignBridgeDeployedArgs._foreignBridge.should.be.equal(args.foreignBridge) - homeBridgeDeployedArgs._homeBridge.should.be.equal(args.homeBridge) - foreignBridgeDeployedArgs._blockNumber.should.be.bignumber.equal(args.foreignStartBlock) - homeBridgeDeployedArgs._blockNumber.should.be.bignumber.equal(args.homeStartBlock) - - homeBridgeDeployedArgs._token.should.be.equal(await bridgeMapper.homeTokenByForeignToken(foreignToken.address)) - foreignBridgeDeployedArgs._foreignBridge.should.be.equal(await bridgeMapper.foreignBridgeByForeignToken(foreignToken.address)) - homeBridgeDeployedArgs._homeBridge.should.be.equal(await bridgeMapper.homeBridgeByForeignToken(foreignToken.address)) - foreignBridgeDeployedArgs._blockNumber.should.be.bignumber.equal(await bridgeMapper.foreignStartBlockByForeignToken(foreignToken.address)) - homeBridgeDeployedArgs._blockNumber.should.be.bignumber.equal(await bridgeMapper.homeStartBlockByForeignToken(foreignToken.address)) - }) - - it('should add a second bridge mapping using same mapper', async () => { - let foreignToken = await ERC677BridgeToken.new("Another Foreign ERC20", "FSMT_2", 18) - let foreignBridgeDeployedArgs = getEventFromLogs((await foreignBridgeFactory.deployForeignBridge(foreignToken.address)).logs, 'ForeignBridgeDeployed').args - - let homeToken = { name: "Another Home ERC20", symbol: "HSMT_2", decimals: 18 } - let homeBridgeDeployedArgs = getEventFromLogs((await homeBridgeFactory.deployHomeBridge(homeToken.name, homeToken.symbol, homeToken.decimals)).logs, 'HomeBridgeDeployed').args - - let {logs} = await bridgeMapper.addBridgeMapping(foreignToken.address, homeBridgeDeployedArgs._token, foreignBridgeDeployedArgs._foreignBridge, homeBridgeDeployedArgs._homeBridge, foreignBridgeDeployedArgs._blockNumber, homeBridgeDeployedArgs._blockNumber) - let {args} = getEventFromLogs(logs, 'BridgeMappingUpdated') - - foreignToken.address.should.be.equal(args.foreignToken) - homeBridgeDeployedArgs._token.should.be.equal(args.homeToken) - foreignBridgeDeployedArgs._foreignBridge.should.be.equal(args.foreignBridge) - homeBridgeDeployedArgs._homeBridge.should.be.equal(args.homeBridge) - foreignBridgeDeployedArgs._blockNumber.should.be.bignumber.equal(args.foreignStartBlock) - homeBridgeDeployedArgs._blockNumber.should.be.bignumber.equal(args.homeStartBlock) - - homeBridgeDeployedArgs._token.should.be.equal(await bridgeMapper.homeTokenByForeignToken(foreignToken.address)) - foreignBridgeDeployedArgs._foreignBridge.should.be.equal(await bridgeMapper.foreignBridgeByForeignToken(foreignToken.address)) - homeBridgeDeployedArgs._homeBridge.should.be.equal(await bridgeMapper.homeBridgeByForeignToken(foreignToken.address)) - foreignBridgeDeployedArgs._blockNumber.should.be.bignumber.equal(await bridgeMapper.foreignStartBlockByForeignToken(foreignToken.address)) - homeBridgeDeployedArgs._blockNumber.should.be.bignumber.equal(await bridgeMapper.homeStartBlockByForeignToken(foreignToken.address)) - }) - }) - - describe('#removeBridgeMapping', async () => { - let bridgeMapper - before(async () => { - bridgeMapper = await BridgeMapper.new() - await bridgeMapper.initialize(owner) - }) - - it('should remove a bridge mapping', async () => { - let foreignToken = await ERC677BridgeToken.new("Foreign ERC20", "FSMT", 18) - let foreignBridgeDeployedArgs = getEventFromLogs((await foreignBridgeFactory.deployForeignBridge(foreignToken.address)).logs, 'ForeignBridgeDeployed').args - - let homeToken = { name: "Home ERC20", symbol: "HSMT", decimals: 18 } - let homeBridgeDeployedArgs = getEventFromLogs((await homeBridgeFactory.deployHomeBridge(homeToken.name, homeToken.symbol, homeToken.decimals)).logs, 'HomeBridgeDeployed').args - - await bridgeMapper.addBridgeMapping(foreignToken.address, homeBridgeDeployedArgs._token, foreignBridgeDeployedArgs._foreignBridge, homeBridgeDeployedArgs._homeBridge, foreignBridgeDeployedArgs._blockNumber, homeBridgeDeployedArgs._blockNumber) - - let {logs} = await bridgeMapper.removeBridgeMapping(foreignToken.address) - let {args} = getEventFromLogs(logs, 'BridgeMappingUpdated') - - foreignToken.address.should.be.equal(args.foreignToken) - ZERO_ADDRESS.should.be.equal(args.homeToken) - ZERO_ADDRESS.should.be.equal(args.foreignBridge) - ZERO_ADDRESS.should.be.equal(args.homeBridge) - '0'.should.be.bignumber.equal(args.foreignStartBlock) - '0'.should.be.bignumber.equal(args.homeStartBlock) - - ZERO_ADDRESS.should.be.equal(await bridgeMapper.homeBridgeByForeignToken(foreignToken.address)) - ZERO_ADDRESS.should.be.equal(await bridgeMapper.foreignBridgeByForeignToken(foreignToken.address)) - ZERO_ADDRESS.should.be.equal(await bridgeMapper.homeTokenByForeignToken(foreignToken.address)) - '0'.should.be.bignumber.equal(await bridgeMapper.homeStartBlockByForeignToken(foreignToken.address)) - '0'.should.be.bignumber.equal(await bridgeMapper.foreignStartBlockByForeignToken(foreignToken.address)) - }) - }) -}) From d2bdf62296ee63c16f5c14d37b84e8796d5e92d0 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Fri, 15 Mar 2019 16:06:49 -0300 Subject: [PATCH 114/187] Add fee manager for erc-to-native in posdao chain --- contracts/IBlockReward.sol | 1 + contracts/test/BlockReward.sol | 29 ++ .../erc20_to_native/FeeManagerErcToNative.sol | 4 + .../FeeManagerErcToNativePOSDAO.sol | 36 ++ .../erc20_to_native/HomeBridgeErcToNative.sol | 8 +- .../RewardableHomeBridgeErcToNative.sol | 14 + test/erc_to_native/home_bridge.test.js | 489 ++++++++++++++++++ 7 files changed, 579 insertions(+), 2 deletions(-) create mode 100644 contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNativePOSDAO.sol diff --git a/contracts/IBlockReward.sol b/contracts/IBlockReward.sol index 2d9e1b89a..663f21c56 100644 --- a/contracts/IBlockReward.sol +++ b/contracts/IBlockReward.sol @@ -6,4 +6,5 @@ interface IBlockReward { function mintedTotally() public view returns (uint256); function mintedTotallyByBridge(address _bridge) public view returns(uint256); function bridgesAllowedLength() external view returns(uint256); + function addBridgeNativeFeeReceivers(uint256 _amount) external; } diff --git a/contracts/test/BlockReward.sol b/contracts/test/BlockReward.sol index ea5c4cfa9..e46b446d5 100644 --- a/contracts/test/BlockReward.sol +++ b/contracts/test/BlockReward.sol @@ -7,7 +7,9 @@ import "../libraries/SafeMath.sol"; contract BlockReward is IBlockReward { using SafeMath for uint256; + address[] validatorList; uint256 public mintedCoins = 0; + uint256 public feeAmount = 0; mapping(bytes32 => uint256) internal uintStorage; bytes32 internal constant MINTED_TOTALLY_BY_BRIDGE = "mintedTotallyByBridge"; @@ -40,4 +42,31 @@ contract BlockReward is IBlockReward { bytes32 hash = keccak256(abi.encode(MINTED_TOTALLY_BY_BRIDGE, _bridge)); uintStorage[hash] = uintStorage[hash].add(_amount); } + + function setValidatorsRewards(address[] _initialValidators) external { + validatorList = _initialValidators; + } + + function addBridgeNativeFeeReceivers(uint256 _amount) external { + feeAmount = _amount; + uint256 feePerValidator = _amount.div(validatorList.length); + + uint256 randomValidatorIndex; + uint256 diff = _amount.sub(feePerValidator.mul(validatorList.length)); + if (diff > 0) { + randomValidatorIndex = random(validatorList.length); + } + + for (uint256 i = 0; i < validatorList.length; i++) { + uint256 feeToDistribute = feePerValidator; + if (diff > 0 && randomValidatorIndex == i) { + feeToDistribute = feeToDistribute.add(diff); + } + this.addExtraReceiver(feeToDistribute, validatorList[i]); + } + } + + function random(uint256 _count) public view returns(uint256) { + return uint256(blockhash(block.number.sub(1))) % _count; + } } diff --git a/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol index be80bdd03..00a974f4d 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol @@ -25,4 +25,8 @@ contract FeeManagerErcToNative is BaseFeeManager { (new Sacrifice).value(_fee)(_rewardAddress); } } + + function isPOSDAOFeeManager() public pure returns(bool) { + return false; + } } diff --git a/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNativePOSDAO.sol b/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNativePOSDAO.sol new file mode 100644 index 000000000..4658e1621 --- /dev/null +++ b/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNativePOSDAO.sol @@ -0,0 +1,36 @@ +pragma solidity 0.4.24; + +import "../BaseFeeManager.sol"; +import "../../IBlockReward.sol"; + +contract FeeManagerErcToNativePOSDAO is BaseFeeManager { + + function getFeeManagerMode() public pure returns(bytes4) { + return bytes4(keccak256(abi.encodePacked("manages-both-directions"))); + } + + function blockRewardContract() internal view returns(IBlockReward) { + return IBlockReward(addressStorage[keccak256(abi.encodePacked("blockRewardContract"))]); + } + + function distributeFeeFromAffirmation(uint256 _fee) external { + distributeFeeFromBlockReward(_fee); + } + + function distributeFeeFromSignatures(uint256 _fee) external { + distributeFeeFromBlockReward(_fee); + } + + function distributeFeeFromBlockReward(uint256 _fee) internal { + IBlockReward blockReward = blockRewardContract(); + blockReward.addBridgeNativeFeeReceivers(_fee); + } + + function isPOSDAOFeeManager() public pure returns(bool) { + return true; + } + + function onAffirmationFeeDistribution(address _rewardAddress, uint256 _fee) internal {} + + function onSignatureFeeDistribution(address _rewardAddress, uint256 _fee) internal {} +} diff --git a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol index a396fcd89..79af888b2 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol @@ -29,8 +29,12 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, uint256 fee = calculateFee(valueToTransfer, false, feeManager, HOME_FEE); valueToTransfer = valueToTransfer.sub(fee); } - setTotalBurntCoins(totalBurntCoins().add(valueToTransfer)); - address(0).transfer(valueToTransfer); + uint256 valueToBurn = valueToTransfer; + if(isPOSDAOFeeManager()) { + valueToBurn = msg.value; + } + setTotalBurntCoins(totalBurntCoins().add(valueToBurn)); + address(0).transfer(valueToBurn); emit UserRequestForSignature(msg.sender, valueToTransfer); } diff --git a/contracts/upgradeable_contracts/erc20_to_native/RewardableHomeBridgeErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/RewardableHomeBridgeErcToNative.sol index 8d0df3d0b..d164fbc82 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/RewardableHomeBridgeErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/RewardableHomeBridgeErcToNative.sol @@ -20,4 +20,18 @@ contract RewardableHomeBridgeErcToNative is RewardableBridge { function getForeignFee() public view returns(uint256) { return _getFee(FOREIGN_FEE); } + + function isPOSDAOFeeManager() public view returns(bool) { + bool mode; + bytes memory callData = abi.encodeWithSignature("isPOSDAOFeeManager()"); + address feeManager = feeManagerContract(); + assembly { + let result := callcode(gas, feeManager, 0x0, add(callData, 0x20), mload(callData), 0, 32) + mode := mload(0) + + switch result + case 0 { revert(0, 0) } + } + return mode; + } } diff --git a/test/erc_to_native/home_bridge.test.js b/test/erc_to_native/home_bridge.test.js index 7e856ccff..3aab662df 100644 --- a/test/erc_to_native/home_bridge.test.js +++ b/test/erc_to_native/home_bridge.test.js @@ -5,6 +5,7 @@ const BridgeValidators = artifacts.require('BridgeValidators.sol') const BlockReward = artifacts.require('BlockReward') const RewardableValidators = artifacts.require("RewardableValidators.sol"); const FeeManagerErcToNative = artifacts.require("FeeManagerErcToNative.sol"); +const FeeManagerErcToNativePOSDAO = artifacts.require("FeeManagerErcToNativePOSDAO"); const {ERROR_MSG, ZERO_ADDRESS} = require('../setup'); const {createMessage, sign } = require('../helpers/helpers'); const minPerTx = web3.toBigNumber(web3.toWei(0.01, "ether")); @@ -1422,4 +1423,492 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { } }) }) + describe('#feeManager_ExecuteAffirmation_POSDAO', async () => { + it('should distribute fee to validator', async () => { + // Initialize + const owner = accounts[9] + const validators = [accounts[1]] + const rewards = [accounts[2]] + const requiredSignatures = 1 + const rewardableValidators = await RewardableValidators.new() + const homeBridgeImpl = await HomeBridge.new(); + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled + const homeBridge = await HomeBridge.at(storageProxy.address); + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + + await blockRewardContract.setValidatorsRewards(rewards) + await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + await blockRewardContract.sendTransaction({ + from: accounts[2], + value: oneEther + }).should.be.fulfilled + + // Given + // 0.1% fee + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeManager = await FeeManagerErcToNativePOSDAO.new() + await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled + await homeBridge.setForeignFee(feeInWei, { from: owner }).should.be.fulfilled + + const recipient = accounts[5]; + const value = halfEther; + const balanceBefore = await web3.eth.getBalance(recipient) + const rewardAddressBalanceBefore = await web3.eth.getBalance(rewards[0]) + const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + + // When + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled + + // Then + logs[0].event.should.be.equal("SignedForAffirmation"); + logs[0].args.should.be.deep.equal({ + signer: validators[0], + transactionHash + }); + logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].args.should.be.deep.equal({ + recipient, + value, + transactionHash + }) + const balanceAfter = await web3.eth.getBalance(recipient) + const rewardAddressBalanceAfter = await web3.eth.getBalance(rewards[0]) + + rewardAddressBalanceAfter.should.be.bignumber.equal(rewardAddressBalanceBefore.add(value.mul(web3.toBigNumber(fee)))) + balanceAfter.should.be.bignumber.equal(balanceBefore.add(value.mul(web3.toBigNumber(1 - fee)))) + + const feeAmountBlockReward = await blockRewardContract.feeAmount() + feeAmountBlockReward.should.be.bignumber.equal(value.mul(web3.toBigNumber(fee))) + }) + it('should distribute fee to 3 validators', async () => { + // Initialize + const owner = accounts[9] + const validators = [accounts[1], accounts[2], accounts[3]] + const rewards = [accounts[4], accounts[5], accounts[6]] + const requiredSignatures = 2 + const rewardableValidators = await RewardableValidators.new() + const homeBridgeImpl = await HomeBridge.new(); + const blockRewardContract = await BlockReward.new() + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled + const homeBridge = await HomeBridge.at(storageProxy.address); + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + await blockRewardContract.setValidatorsRewards(rewards) + await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + await blockRewardContract.sendTransaction({ + from: accounts[0], + value: halfEther + }).should.be.fulfilled + + // Given + const initialBlockRewardBalance = await web3.eth.getBalance(blockRewardContract.address) + initialBlockRewardBalance.should.be.bignumber.equal(halfEther) + + const value = halfEther; + // 0.1% fee + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + // totalFee / 3 + const feePerValidator = web3.toBigNumber(166666666666666) + const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) + const feeManager = await FeeManagerErcToNativePOSDAO.new() + await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled + await homeBridge.setForeignFee(feeInWei, { from: owner }).should.be.fulfilled + + const recipient = accounts[8]; + const balanceBefore = await web3.eth.getBalance(recipient) + + const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const initialBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const initialBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + + + const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + + // When + const { logs: logsValidator1 } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[1]}).should.be.fulfilled + + // Then + logsValidator1.length.should.be.equals(1) + + logs[0].event.should.be.equal("SignedForAffirmation"); + logs[0].args.should.be.deep.equal({ + signer: validators[1], + transactionHash + }); + logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].args.should.be.deep.equal({ + recipient, + value, + transactionHash + }) + const balanceAfter = await web3.eth.getBalance(recipient) + balanceAfter.should.be.bignumber.equal(balanceBefore.add(value.mul(web3.toBigNumber(1 - fee)))) + + const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + + expect( + updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidator)) + || updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidatorPlusDiff))).to.equal(true) + expect( + updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidator)) + || updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidatorPlusDiff))).to.equal(true) + expect( + updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidator)) + || updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidatorPlusDiff))).to.equal(true) + + const feeAmountBlockReward = await blockRewardContract.feeAmount() + feeAmountBlockReward.should.be.bignumber.equal(value.mul(web3.toBigNumber(fee))) + + const blockRewardBalance = await web3.eth.getBalance(blockRewardContract.address) + blockRewardBalance.should.be.bignumber.equal('0') + }) + it('should distribute fee to 5 validators', async () => { + // Initialize + const owner = accounts[0] + const validators = [accounts[0], accounts[1], accounts[2], accounts[3], accounts[4]] + const rewards = [accounts[5], accounts[6], accounts[7], accounts[8], accounts[9]] + const requiredSignatures = 5 + const rewardableValidators = await RewardableValidators.new() + const homeBridgeImpl = await HomeBridge.new(); + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled + const homeBridge = await HomeBridge.at(storageProxy.address); + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + await blockRewardContract.setValidatorsRewards(rewards) + await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + await blockRewardContract.sendTransaction({ + from: accounts[0], + value: oneEther + }).should.be.fulfilled + + // Given + const value = halfEther; + // 0.1% fee + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeAmount = value.mul(web3.toBigNumber(fee)) + const feePerValidator = feeAmount.div(web3.toBigNumber(5)) + const feeManager = await FeeManagerErcToNativePOSDAO.new() + await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled + await homeBridge.setForeignFee(feeInWei, { from: owner }).should.be.fulfilled + + const recipient = "0xf4bef13f9f4f2b203faf0c3cbbaabe1afe056955"; + const balanceBefore = await web3.eth.getBalance(recipient) + + const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const initialBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const initialBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + const initialBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) + const initialBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) + + + const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + + // When + const { logs: logsValidator1 } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[1]}).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[2]}).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[3]}).should.be.fulfilled + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[4]}).should.be.fulfilled + + // Then + logsValidator1.length.should.be.equals(1) + + logs[0].event.should.be.equal("SignedForAffirmation"); + logs[0].args.should.be.deep.equal({ + signer: validators[4], + transactionHash + }); + logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].args.should.be.deep.equal({ + recipient, + value, + transactionHash + }) + const balanceAfter = await web3.eth.getBalance(recipient) + balanceAfter.should.be.bignumber.equal(balanceBefore.add(value.sub(feeAmount))) + + const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + const updatedBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) + const updatedBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) + + updatedBalanceRewardAddress1.should.be.bignumber.equal(initialBalanceRewardAddress1.add(feePerValidator)) + updatedBalanceRewardAddress2.should.be.bignumber.equal(initialBalanceRewardAddress2.add(feePerValidator)) + updatedBalanceRewardAddress3.should.be.bignumber.equal(initialBalanceRewardAddress3.add(feePerValidator)) + updatedBalanceRewardAddress4.should.be.bignumber.equal(initialBalanceRewardAddress4.add(feePerValidator)) + updatedBalanceRewardAddress5.should.be.bignumber.equal(initialBalanceRewardAddress5.add(feePerValidator)) + + const feeAmountBlockReward = await blockRewardContract.feeAmount() + feeAmountBlockReward.should.be.bignumber.equal(value.mul(web3.toBigNumber(fee))) + }) + }) + describe('#feeManager_fallback_POSDAO', function () { + let homeBridge, rewardableValidators + let owner = accounts[9] + let validators = [accounts[1]] + let rewards = [accounts[2]] + let requiredSignatures = 1 + beforeEach(async () => { + rewardableValidators = await RewardableValidators.new() + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled + const homeBridgeImpl = await HomeBridge.new(); + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled + homeBridge = await HomeBridge.at(storageProxy.address); + await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + await blockRewardContract.addMintedTotallyByBridge(oneEther, homeBridge.address) + }) + + it('should subtract fee from value', async () => { + // Given + // 0.1% fee + const value = halfEther + const recipient = accounts[8]; + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeManager = await FeeManagerErcToNativePOSDAO.new() + await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled + await homeBridge.setHomeFee(feeInWei, { from: owner }).should.be.fulfilled + + // When + const { logs } = await homeBridge.sendTransaction({ from: recipient, value }).should.be.fulfilled + + // Then + const finalValue = value.mul(web3.toBigNumber(1 - fee)) + logs[0].event.should.be.equal('UserRequestForSignature') + logs[0].args.should.be.deep.equal({ recipient: recipient, value: finalValue }) + const currentDay = await homeBridge.getCurrentDay() + value.should.be.bignumber.equal(await homeBridge.totalSpentPerDay(currentDay)) + value.should.be.bignumber.equal(await homeBridge.totalBurntCoins()) + const homeBridgeBalance = await web3.eth.getBalance(homeBridge.address) + homeBridgeBalance.should.be.bignumber.equal(0) + }) + }) + describe('#feeManager_submitSignature_POSDAO', async () => { + it('should distribute fee to validator', async () => { + // Initialize + const owner = accounts[9] + const validators = [accounts[1]] + const rewards = [accounts[2]] + const requiredSignatures = 1 + const rewardableValidators = await RewardableValidators.new() + const homeBridgeImpl = await HomeBridge.new(); + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled + const homeBridge = await HomeBridge.at(storageProxy.address); + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + await blockRewardContract.setValidatorsRewards(rewards) + await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + await blockRewardContract.addMintedTotallyByBridge(oneEther, homeBridge.address) + + // Given + // 0.1% fee + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeManager = await FeeManagerErcToNativePOSDAO.new() + await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled + await homeBridge.setHomeFee(feeInWei, { from: owner }).should.be.fulfilled + + const recipient = accounts[5]; + const initialValue = halfEther + const value = halfEther.mul(web3.toBigNumber(1-fee)); + const feeAmount = initialValue.mul(web3.toBigNumber(fee)) + const rewardAddressBalanceBefore = await web3.eth.getBalance(rewards[0]) + const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + + const initialBridgeBalance = await web3.eth.getBalance(homeBridge.address) + initialBridgeBalance.should.be.bignumber.equal('0') + + // When + await homeBridge.sendTransaction({ from: recipient, value: initialValue }).should.be.fulfilled + + const afterTransferBridgeBalance = await web3.eth.getBalance(homeBridge.address) + afterTransferBridgeBalance.should.be.bignumber.equal(0) + + const message = createMessage(recipient, value, transactionHash, homeBridge.address); + + const signature = await sign(validators[0], message) + + const { logs } = await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled; + + // Then + logs.length.should.be.equal(2) + logs[1].event.should.be.equal('CollectedSignatures') + + const finalBridgeBalance = await web3.eth.getBalance(homeBridge.address) + finalBridgeBalance.should.be.bignumber.equal('0') + + const rewardAddressBalanceAfter = await web3.eth.getBalance(rewards[0]) + rewardAddressBalanceAfter.should.be.bignumber.equal(rewardAddressBalanceBefore.add(feeAmount)) + + const feeAmountBlockReward = await blockRewardContract.feeAmount() + feeAmountBlockReward.should.be.bignumber.equal(initialValue.mul(web3.toBigNumber(fee))) + }) + it('should distribute fee to 3 validators', async () => { + // Initialize + const owner = accounts[9] + const validators = [accounts[1], accounts[2], accounts[3]] + const rewards = [accounts[4], accounts[5], accounts[6]] + const requiredSignatures = 3 + const rewardableValidators = await RewardableValidators.new() + const homeBridgeImpl = await HomeBridge.new(); + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled + const homeBridge = await HomeBridge.at(storageProxy.address); + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + await blockRewardContract.setValidatorsRewards(rewards) + await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + await blockRewardContract.addMintedTotallyByBridge(oneEther, homeBridge.address) + + // Given + // 0.1% fee + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeManager = await FeeManagerErcToNativePOSDAO.new() + const feePerValidator = web3.toBigNumber(166666666666666) + const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) + await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled + await homeBridge.setHomeFee(feeInWei, { from: owner }).should.be.fulfilled + + const recipient = accounts[7]; + const initialValue = halfEther + const value = halfEther.mul(web3.toBigNumber(1-fee)); + const feeAmount = initialValue.mul(web3.toBigNumber(fee)) + const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + + const initialBridgeBalance = await web3.eth.getBalance(homeBridge.address) + initialBridgeBalance.should.be.bignumber.equal('0') + + const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const initialBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const initialBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + + // When + await homeBridge.sendTransaction({ from: recipient, value: initialValue }).should.be.fulfilled + + const afterTransferBridgeBalance = await web3.eth.getBalance(homeBridge.address) + afterTransferBridgeBalance.should.be.bignumber.equal(0) + + const message = createMessage(recipient, value, transactionHash, homeBridge.address); + + const signature = await sign(validators[0], message) + const signature2 = await sign(validators[1], message) + const signature3 = await sign(validators[2], message) + + await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled; + await homeBridge.submitSignature(signature2, message, {from: validators[1]}).should.be.fulfilled; + const { logs } = await homeBridge.submitSignature(signature3, message, {from: validators[2]}).should.be.fulfilled; + + // Then + logs.length.should.be.equal(2) + logs[1].event.should.be.equal('CollectedSignatures') + + const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + + const bridgeBalance = await web3.eth.getBalance(homeBridge.address) + bridgeBalance.should.be.bignumber.equal('0') + + expect( + updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidator)) + || updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidatorPlusDiff))).to.equal(true) + expect( + updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidator)) + || updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidatorPlusDiff))).to.equal(true) + expect( + updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidator)) + || updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidatorPlusDiff))).to.equal(true) + + const feeAmountBlockReward = await blockRewardContract.feeAmount() + feeAmountBlockReward.should.be.bignumber.equal(feeAmount) + }) + it('should distribute fee to 5 validators', async () => { + // Initialize + const owner = accounts[0] + const validators = [accounts[0], accounts[1], accounts[2], accounts[3], accounts[4]] + const rewards = [accounts[5], accounts[6], accounts[7], accounts[8], accounts[9]] + const requiredSignatures = 5 + const rewardableValidators = await RewardableValidators.new() + const homeBridgeImpl = await HomeBridge.new(); + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled + const homeBridge = await HomeBridge.at(storageProxy.address); + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + await blockRewardContract.setValidatorsRewards(rewards) + await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + await blockRewardContract.addMintedTotallyByBridge(oneEther, homeBridge.address) + + // Given + // 0.1% fee + const fee = 0.001 + const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeManager = await FeeManagerErcToNativePOSDAO.new() + await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled + await homeBridge.setHomeFee(feeInWei, { from: owner }).should.be.fulfilled + + const recipient = accounts[0]; + const initialValue = halfEther + const value = halfEther.mul(web3.toBigNumber(1-fee)); + const feeAmount = initialValue.mul(web3.toBigNumber(fee)) + const feePerValidator = feeAmount.div(web3.toBigNumber(5)) + const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + + const initialBridgeBalance = await web3.eth.getBalance(homeBridge.address) + initialBridgeBalance.should.be.bignumber.equal('0') + + const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const initialBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const initialBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + const initialBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) + const initialBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) + + // When + await homeBridge.sendTransaction({ from: recipient, value: initialValue }).should.be.fulfilled + + const afterTransferBridgeBalance = await web3.eth.getBalance(homeBridge.address) + afterTransferBridgeBalance.should.be.bignumber.equal(0) + + const message = createMessage(recipient, value, transactionHash, homeBridge.address); + + const signature = await sign(validators[0], message) + const signature2 = await sign(validators[1], message) + const signature3 = await sign(validators[2], message) + const signature4 = await sign(validators[3], message) + const signature5 = await sign(validators[4], message) + + await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled; + await homeBridge.submitSignature(signature2, message, {from: validators[1]}).should.be.fulfilled; + await homeBridge.submitSignature(signature3, message, {from: validators[2]}).should.be.fulfilled; + await homeBridge.submitSignature(signature4, message, {from: validators[3]}).should.be.fulfilled; + const { logs } = await homeBridge.submitSignature(signature5, message, {from: validators[4]}).should.be.fulfilled; + + // Then + logs.length.should.be.equal(2) + logs[1].event.should.be.equal('CollectedSignatures') + + const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) + const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) + const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + const updatedBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) + const updatedBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) + + updatedBalanceRewardAddress1.should.be.bignumber.equal(initialBalanceRewardAddress1.add(feePerValidator)) + updatedBalanceRewardAddress2.should.be.bignumber.equal(initialBalanceRewardAddress2.add(feePerValidator)) + updatedBalanceRewardAddress3.should.be.bignumber.equal(initialBalanceRewardAddress3.add(feePerValidator)) + updatedBalanceRewardAddress4.should.be.bignumber.equal(initialBalanceRewardAddress4.add(feePerValidator)) + updatedBalanceRewardAddress5.should.be.bignumber.equal(initialBalanceRewardAddress5.add(feePerValidator)) + + const feeAmountBlockReward = await blockRewardContract.feeAmount() + feeAmountBlockReward.should.be.bignumber.equal(feeAmount) + }) + }) }) From 9a1ce9394816bc914dc2b3c557e89c924a6ed106 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Thu, 21 Mar 2019 10:16:12 -0300 Subject: [PATCH 115/187] Add FeeManagerErcToNativePOSDAO on deploy script --- deploy/.env.example | 1 + deploy/README.md | 2 ++ deploy/src/erc_to_native/home.js | 8 ++++++-- deploy/src/loadEnv.js | 7 +++++++ 4 files changed, 16 insertions(+), 2 deletions(-) diff --git a/deploy/.env.example b/deploy/.env.example index 62d114a8b..27679919a 100644 --- a/deploy/.env.example +++ b/deploy/.env.example @@ -56,3 +56,4 @@ FOREIGN_TRANSACTIONS_FEE=0.001 #for bridge native_to_erc mode DEPLOY_REWARDABLE_TOKEN=false DPOS_VALIDATOR_SET_ADDRESS= +HOME_POSDAO=false diff --git a/deploy/README.md b/deploy/README.md index e959e0a3f..80c9fba90 100644 --- a/deploy/README.md +++ b/deploy/README.md @@ -351,6 +351,8 @@ VALIDATORS=0x 0x 0x HOME_REWARDABLE=false # The flag defining whether to use RewardableValidators contract and set a fee manager contract on Foreign network FOREIGN_REWARDABLE=false +# Flag to define if Home network is a POSDAO and rewards are distributed by blockReward contract +HOME_POSDAO=false # List validators accounts were rewards should be transferred separated by space without quotes # Makes sense only when HOME_REWARDABLE=true or FOREIGN_REWARDABLE=true VALIDATORS_REWARD_ACCOUNTS=0x 0x 0x diff --git a/deploy/src/erc_to_native/home.js b/deploy/src/erc_to_native/home.js index 6a29343a8..dccbcf38d 100644 --- a/deploy/src/erc_to_native/home.js +++ b/deploy/src/erc_to_native/home.js @@ -14,6 +14,7 @@ const EternalStorageProxy = require('../../../build/contracts/EternalStorageProx const BridgeValidators = require('../../../build/contracts/BridgeValidators.json') const RewardableValidators = require('../../../build/contracts/RewardableValidators.json') const FeeManagerErcToNative = require('../../../build/contracts/FeeManagerErcToNative.json') +const FeeManagerErcToNativePOSDAO = require('../../../build/contracts/FeeManagerErcToNativePOSDAO') const HomeBridge = require('../../../build/contracts/HomeBridgeErcToNative.json') const VALIDATORS = env.VALIDATORS.split(' ') @@ -35,12 +36,14 @@ const { FOREIGN_MAX_AMOUNT_PER_TX, HOME_REWARDABLE, HOME_TRANSACTIONS_FEE, - FOREIGN_TRANSACTIONS_FEE + FOREIGN_TRANSACTIONS_FEE, + HOME_POSDAO } = env const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVATE_KEY) const isRewardableBridge = HOME_REWARDABLE === 'true' +const isHomePOSDAO = HOME_POSDAO === 'true' async function deployHome() { let homeNonce = await web3Home.eth.getTransactionCount(DEPLOYMENT_ACCOUNT_ADDRESS) @@ -161,7 +164,8 @@ async function deployHome() { if (isRewardableBridge) { console.log('\ndeploying implementation for fee manager') - const feeManager = await deployContract(FeeManagerErcToNative, [], { + const feeManagerContract = isHomePOSDAO ? FeeManagerErcToNativePOSDAO : FeeManagerErcToNative + const feeManager = await deployContract(feeManagerContract, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, nonce: homeNonce }) diff --git a/deploy/src/loadEnv.js b/deploy/src/loadEnv.js index d95b86f74..df9413824 100644 --- a/deploy/src/loadEnv.js +++ b/deploy/src/loadEnv.js @@ -112,6 +112,13 @@ if (BRIDGE_MODE === 'ERC_TO_NATIVE') { `Collecting fees on Foreign Network on ${BRIDGE_MODE} bridge mode is not supported.` ) } + + if (HOME_REWARDABLE === 'true') { + validations = { + ...validations, + HOME_POSDAO: envalid.bool() + } + } } if (HOME_REWARDABLE === 'true' || FOREIGN_REWARDABLE === 'true') { From 04ab82f62aa7e19fee4b0b148e25f44618f8a36f Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 26 Mar 2019 17:03:53 -0300 Subject: [PATCH 116/187] Add fee manager erc-to-erc --- contracts/IBlockReward.sol | 1 + contracts/test/BlockReward.sol | 39 ++++++ .../FeeManagerErcToErcPOSDAO.sol | 36 ++++++ .../erc20_to_erc20/HomeBridgeErcToErc.sol | 118 +++++++++++++++++- .../RewardableHomeBridgeErcToErc.sol | 23 ++++ 5 files changed, 211 insertions(+), 6 deletions(-) create mode 100644 contracts/upgradeable_contracts/erc20_to_erc20/FeeManagerErcToErcPOSDAO.sol create mode 100644 contracts/upgradeable_contracts/erc20_to_erc20/RewardableHomeBridgeErcToErc.sol diff --git a/contracts/IBlockReward.sol b/contracts/IBlockReward.sol index 2d9e1b89a..b4a2da589 100644 --- a/contracts/IBlockReward.sol +++ b/contracts/IBlockReward.sol @@ -6,4 +6,5 @@ interface IBlockReward { function mintedTotally() public view returns (uint256); function mintedTotallyByBridge(address _bridge) public view returns(uint256); function bridgesAllowedLength() external view returns(uint256); + function addBridgeTokenFeeReceivers(uint256 _amount) external; } diff --git a/contracts/test/BlockReward.sol b/contracts/test/BlockReward.sol index ea5c4cfa9..7a9b868b2 100644 --- a/contracts/test/BlockReward.sol +++ b/contracts/test/BlockReward.sol @@ -7,9 +7,12 @@ import "../libraries/SafeMath.sol"; contract BlockReward is IBlockReward { using SafeMath for uint256; + address[] public validatorList; uint256 public mintedCoins = 0; + uint256 public feeAmount = 0; mapping(bytes32 => uint256) internal uintStorage; bytes32 internal constant MINTED_TOTALLY_BY_BRIDGE = "mintedTotallyByBridge"; + address public token; function () external payable { } @@ -40,4 +43,40 @@ contract BlockReward is IBlockReward { bytes32 hash = keccak256(abi.encode(MINTED_TOTALLY_BY_BRIDGE, _bridge)); uintStorage[hash] = uintStorage[hash].add(_amount); } + + function setValidatorsRewards(address[] _initialValidators) external { + validatorList = _initialValidators; + } + + function setToken(address _token) external { + token = _token; + } + + function addBridgeTokenFeeReceivers(uint256 _amount) external { + address[] memory receivers = new address[](validatorList.length); + uint256[] memory rewards = new uint256[](validatorList.length); + feeAmount = _amount; + uint256 feePerValidator = _amount.div(validatorList.length); + + uint256 randomValidatorIndex; + uint256 diff = _amount.sub(feePerValidator.mul(validatorList.length)); + if (diff > 0) { + randomValidatorIndex = random(validatorList.length); + } + + for (uint256 i = 0; i < validatorList.length; i++) { + uint256 feeToDistribute = feePerValidator; + if (diff > 0 && randomValidatorIndex == i) { + feeToDistribute = feeToDistribute.add(diff); + } + receivers[i] = validatorList[i]; + rewards[i] = feeToDistribute; + } + + require(token.call(abi.encodeWithSignature("mintReward(address[],uint256[])", receivers, rewards))); + } + + function random(uint256 _count) public view returns(uint256) { + return uint256(blockhash(block.number.sub(1))) % _count; + } } diff --git a/contracts/upgradeable_contracts/erc20_to_erc20/FeeManagerErcToErcPOSDAO.sol b/contracts/upgradeable_contracts/erc20_to_erc20/FeeManagerErcToErcPOSDAO.sol new file mode 100644 index 000000000..4323c7f85 --- /dev/null +++ b/contracts/upgradeable_contracts/erc20_to_erc20/FeeManagerErcToErcPOSDAO.sol @@ -0,0 +1,36 @@ +pragma solidity 0.4.24; + +import "../BaseFeeManager.sol"; +import "../../IBlockReward.sol"; + +contract FeeManagerErcToErcPOSDAO is BaseFeeManager { + + function getFeeManagerMode() public pure returns(bytes4) { + return bytes4(keccak256(abi.encodePacked("manages-both-directions"))); + } + + function blockRewardContract() internal view returns(IBlockReward) { + return IBlockReward(addressStorage[keccak256(abi.encodePacked("blockRewardContract"))]); + } + + function distributeFeeFromAffirmation(uint256 _fee) external { + distributeFeeFromBlockReward(_fee); + } + + function distributeFeeFromSignatures(uint256 _fee) external { + distributeFeeFromBlockReward(_fee); + } + + function distributeFeeFromBlockReward(uint256 _fee) internal { + IBlockReward blockReward = blockRewardContract(); + blockReward.addBridgeTokenFeeReceivers(_fee); + } + + function isPOSDAOFeeManager() public pure returns(bool) { + return true; + } + + function onAffirmationFeeDistribution(address _rewardAddress, uint256 _fee) internal {} + + function onSignatureFeeDistribution(address _rewardAddress, uint256 _fee) internal {} +} diff --git a/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol b/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol index 51313be11..4ed2bbad5 100644 --- a/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol +++ b/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol @@ -8,9 +8,11 @@ import "../../ERC677Receiver.sol"; import "../BasicHomeBridge.sol"; import "../ERC677Bridge.sol"; import "../OverdrawManagement.sol"; +import "./RewardableHomeBridgeErcToErc.sol"; +import "../../IBlockReward.sol"; -contract HomeBridgeErcToErc is ERC677Receiver, EternalStorage, BasicBridge, BasicHomeBridge, ERC677Bridge, OverdrawManagement { +contract HomeBridgeErcToErc is ERC677Receiver, EternalStorage, BasicBridge, BasicHomeBridge, ERC677Bridge, OverdrawManagement, RewardableHomeBridgeErcToErc { event AmountLimitExceeded(address recipient, uint256 value, bytes32 transactionHash); @@ -27,6 +29,78 @@ contract HomeBridgeErcToErc is ERC677Receiver, EternalStorage, BasicBridge, Basi address _owner ) public returns(bool) + { + _initialize ( + _validatorContract, + _dailyLimit, + _maxPerTx, + _minPerTx, + _homeGasPrice, + _requiredBlockConfirmations, + _erc677token, + _foreignDailyLimit, + _foreignMaxPerTx, + _owner + ); + setInitialize(true); + + return isInitialized(); + } + + function rewardableInitialize ( + address _validatorContract, + uint256 _dailyLimit, + uint256 _maxPerTx, + uint256 _minPerTx, + uint256 _homeGasPrice, + uint256 _requiredBlockConfirmations, + address _erc677token, + uint256 _foreignDailyLimit, + uint256 _foreignMaxPerTx, + address _owner, + address _blockReward, + address _feeManager, + uint256 _homeFee, + uint256 _foreignFee + ) public + returns(bool) + { + _initialize ( + _validatorContract, + _dailyLimit, + _maxPerTx, + _minPerTx, + _homeGasPrice, + _requiredBlockConfirmations, + _erc677token, + _foreignDailyLimit, + _foreignMaxPerTx, + _owner + ); + require(isContract(_feeManager)); + require(_blockReward == address(0) || isContract(_blockReward)); + addressStorage[keccak256(abi.encodePacked("feeManagerContract"))] = _feeManager; + _setFee(_feeManager, _homeFee, HOME_FEE); + _setFee(_feeManager, _foreignFee, FOREIGN_FEE); + addressStorage[keccak256(abi.encodePacked("blockRewardContract"))] = _blockReward; + setInitialize(true); + + return isInitialized(); + } + + function _initialize ( + address _validatorContract, + uint256 _dailyLimit, + uint256 _maxPerTx, + uint256 _minPerTx, + uint256 _homeGasPrice, + uint256 _requiredBlockConfirmations, + address _erc677token, + uint256 _foreignDailyLimit, + uint256 _foreignMaxPerTx, + address _owner + ) public + returns(bool) { require(!isInitialized()); require(_validatorContract != address(0) && isContract(_validatorContract)); @@ -45,10 +119,7 @@ contract HomeBridgeErcToErc is ERC677Receiver, EternalStorage, BasicBridge, Basi uintStorage[keccak256(abi.encodePacked("executionDailyLimit"))] = _foreignDailyLimit; uintStorage[keccak256(abi.encodePacked("executionMaxPerTx"))] = _foreignMaxPerTx; setOwner(_owner); - setInitialize(true); setErc677token(_erc677token); - - return isInitialized(); } function getBridgeMode() public pure returns(bytes4 _data) { @@ -59,13 +130,48 @@ contract HomeBridgeErcToErc is ERC677Receiver, EternalStorage, BasicBridge, Basi revert(); } + function blockRewardContract() public view returns(IBlockReward) { + return IBlockReward(addressStorage[keccak256(abi.encodePacked("blockRewardContract"))]); + } + + function setBlockRewardContract(address _blockReward) public onlyOwner { + require(_blockReward != address(0) && isContract(_blockReward) && (IBlockReward(_blockReward).bridgesAllowedLength() != 0)); + addressStorage[keccak256(abi.encodePacked("blockRewardContract"))] = _blockReward; + } + function onExecuteAffirmation(address _recipient, uint256 _value) internal returns(bool) { setTotalExecutedPerDay(getCurrentDay(), totalExecutedPerDay(getCurrentDay()).add(_value)); - return erc677token().mint(_recipient, _value); + uint256 valueToMint = _value; + address feeManager = feeManagerContract(); + if (feeManager != address(0)) { + uint256 fee = calculateFee(valueToMint, false, feeManager, FOREIGN_FEE); + distributeFeeFromAffirmation(fee, feeManager); + valueToMint = valueToMint.sub(fee); + } + return erc677token().mint(_recipient, valueToMint); } function fireEventOnTokenTransfer(address _from, uint256 _value) internal { - emit UserRequestForSignature(_from, _value); + uint256 valueToTransfer = _value; + address feeManager = feeManagerContract(); + if (feeManager != address(0)) { + uint256 fee = calculateFee(valueToTransfer, false, feeManager, HOME_FEE); + valueToTransfer = valueToTransfer.sub(fee); + } + emit UserRequestForSignature(_from, valueToTransfer); + } + + function onSignaturesCollected(bytes _message) internal { + address feeManager = feeManagerContract(); + if (feeManager != address(0)) { + address recipient; + uint256 amount; + bytes32 txHash; + address contractAddress; + (recipient, amount, txHash, contractAddress) = Message.parseMessage(_message); + uint256 fee = calculateFee(amount, true, feeManager, HOME_FEE); + distributeFeeFromSignatures(fee, feeManager); + } } function affirmationWithinLimits(uint256 _amount) internal view returns(bool) { diff --git a/contracts/upgradeable_contracts/erc20_to_erc20/RewardableHomeBridgeErcToErc.sol b/contracts/upgradeable_contracts/erc20_to_erc20/RewardableHomeBridgeErcToErc.sol new file mode 100644 index 000000000..0b9282755 --- /dev/null +++ b/contracts/upgradeable_contracts/erc20_to_erc20/RewardableHomeBridgeErcToErc.sol @@ -0,0 +1,23 @@ +pragma solidity 0.4.24; + +import "../RewardableBridge.sol"; + + +contract RewardableHomeBridgeErcToErc is RewardableBridge { + + function setHomeFee(uint256 _fee) external onlyOwner { + _setFee(feeManagerContract(), _fee, HOME_FEE); + } + + function setForeignFee(uint256 _fee) external onlyOwner { + _setFee(feeManagerContract(), _fee, FOREIGN_FEE); + } + + function getHomeFee() public view returns(uint256) { + return _getFee(HOME_FEE); + } + + function getForeignFee() public view returns(uint256) { + return _getFee(FOREIGN_FEE); + } +} From 4cfb6179b2f59d300b8f6ddf9cb86b85fd8a2516 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 26 Mar 2019 17:04:30 -0300 Subject: [PATCH 117/187] Add erc-to-erc fee manager unit tests --- test/erc_to_erc/home_bridge.test.js | 364 +++++++++++++++++++++- test/helpers/helpers.js | 17 + test/native_to_erc/foreign_bridge_test.js | 16 +- 3 files changed, 381 insertions(+), 16 deletions(-) diff --git a/test/erc_to_erc/home_bridge.test.js b/test/erc_to_erc/home_bridge.test.js index b145acb8f..182548af2 100644 --- a/test/erc_to_erc/home_bridge.test.js +++ b/test/erc_to_erc/home_bridge.test.js @@ -3,8 +3,12 @@ const HomeBridge = artifacts.require("HomeBridgeErcToErc.sol"); const EternalStorageProxy = artifacts.require("EternalStorageProxy.sol"); const BridgeValidators = artifacts.require("BridgeValidators.sol"); const ERC677BridgeToken = artifacts.require("ERC677BridgeToken.sol"); +const ERC677BridgeTokenRewardable = artifacts.require("ERC677BridgeTokenRewardable.sol"); +const FeeManagerErcToErcPOSDAO = artifacts.require("FeeManagerErcToErcPOSDAO.sol"); +const RewardableValidators = artifacts.require("RewardableValidators.sol"); +const BlockReward = artifacts.require('BlockReward') const {ERROR_MSG, ZERO_ADDRESS} = require('../setup'); -const {createMessage, sign, signatureToVRS} = require('../helpers/helpers'); +const {createMessage, sign, getEvents} = require('../helpers/helpers'); const minPerTx = web3.toBigNumber(web3.toWei(0.01, "ether")); const requireBlockConfirmations = 8; const gasPrice = Web3Utils.toWei('1', 'gwei'); @@ -619,4 +623,362 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { upgradeabilityAdmin.should.be.equal(proxyOwner) }) }) + + describe('#rewardableInitialize', async () => { + let homeFee, foreignFee, homeBridge, rewardableValidators, blockRewardContract + let validators = [accounts[1]] + let rewards = [accounts[2]] + let requiredSignatures = 1 + beforeEach(async () => { + token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); + rewardableValidators = await RewardableValidators.new() + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled + homeBridge = await HomeBridge.new() + homeFee = web3.toBigNumber(web3.toWei(0.002, "ether")) + foreignFee = web3.toBigNumber(web3.toWei(0.002, "ether")) + blockRewardContract = await BlockReward.new() + }) + it('sets variables', async () => { + const feeManager = await FeeManagerErcToErcPOSDAO.new() + ZERO_ADDRESS.should.be.equal(await homeBridge.validatorContract()) + '0'.should.be.bignumber.equal(await homeBridge.deployedAtBlock()) + '0'.should.be.bignumber.equal(await homeBridge.dailyLimit()) + '0'.should.be.bignumber.equal(await homeBridge.maxPerTx()) + false.should.be.equal(await homeBridge.isInitialized()) + + await homeBridge.rewardableInitialize(ZERO_ADDRESS, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, blockRewardContract.address, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, 0, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, blockRewardContract.address, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, 0, foreignDailyLimit, token.address, foreignMaxPerTx, owner, blockRewardContract.address, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, blockRewardContract.address, ZERO_ADDRESS, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, blockRewardContract.address, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + + true.should.be.equal(await homeBridge.isInitialized()) + rewardableValidators.address.should.be.equal(await homeBridge.validatorContract()); + (await homeBridge.deployedAtBlock()).should.be.bignumber.above(0); + oneEther.should.be.bignumber.equal(await homeBridge.dailyLimit()) + halfEther.should.be.bignumber.equal(await homeBridge.maxPerTx()) + minPerTx.should.be.bignumber.equal(await homeBridge.minPerTx()) + const bridgeMode = '0xba4690f5' // 4 bytes of keccak256('erc-to-erc-core') + const mode = await homeBridge.getBridgeMode(); + mode.should.be.equal(bridgeMode) + const [major, minor, patch] = await homeBridge.getBridgeInterfacesVersion() + major.should.be.bignumber.gte(0) + minor.should.be.bignumber.gte(0) + patch.should.be.bignumber.gte(0) + + const feeManagerContract = await homeBridge.feeManagerContract() + feeManagerContract.should.be.equals(feeManager.address) + const bridgeHomeFee = await homeBridge.getHomeFee() + bridgeHomeFee.should.be.bignumber.equal(homeFee) + const bridgeForeignFee = await homeBridge.getForeignFee() + bridgeForeignFee.should.be.bignumber.equal(foreignFee) + }) + it('can update fee contract', async () => { + const feeManager = await FeeManagerErcToErcPOSDAO.new() + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, blockRewardContract.address, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + + // Given + const newFeeManager = await FeeManagerErcToErcPOSDAO.new() + + // When + await homeBridge.setFeeManagerContract(newFeeManager.address, {from: owner}).should.be.fulfilled + + // Then + const feeManagerContract = await homeBridge.feeManagerContract() + feeManagerContract.should.be.equals(newFeeManager.address) + }) + it('can update fee', async () => { + const feeManager = await FeeManagerErcToErcPOSDAO.new() + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, blockRewardContract.address, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + + // Given + const newHomeFee = web3.toBigNumber(web3.toWei(0.1, "ether")) + const newForeignFee = web3.toBigNumber(web3.toWei(0.4, "ether")) + + // When + await homeBridge.setHomeFee(newHomeFee, {from: owner}).should.be.fulfilled + await homeBridge.setForeignFee(newForeignFee, {from: owner}).should.be.fulfilled + + // Then + const bridgeHomeFee = await homeBridge.getHomeFee() + const bridgeForeignFee = await homeBridge.getForeignFee() + bridgeHomeFee.should.be.bignumber.equal(newHomeFee) + bridgeForeignFee.should.be.bignumber.equal(newForeignFee) + }) + it('should be able to get fee manager mode', async () => { + // Given + const feeManager = await FeeManagerErcToErcPOSDAO.new() + const bothDirectionsModeHash = '0xd7de965f' + + // When + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, blockRewardContract.address, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + + // Then + const feeManagerMode = await homeBridge.getFeeManagerMode() + feeManagerMode.should.be.equals(bothDirectionsModeHash) + }) + }) + + // transferAndCall and check that is was burned and event fired + describe('#onTokenTransfer', async () => { + let homeBridge + beforeEach(async () => { + homeBridge = await HomeBridge.new() + token = await ERC677BridgeToken.new("Some ERC20", "TEST", 18); + }) + it('should trigger UserRequestForSignature with transfer value', async () => { + // Given + const owner = accounts[0] + const user = accounts[4] + await homeBridge.initialize(validatorContract.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled; + const value = halfEther + await token.mint(user, value, {from: owner}).should.be.fulfilled; + + // When + await token.transferAndCall(homeBridge.address, value, '0x00', {from: user}).should.be.fulfilled; + + // Then + const events = await getEvents(homeBridge, {event: 'UserRequestForSignature'}); + events[0].args.should.be.deep.equal({ + recipient: user, + value + }) + }) + it('should trigger UserRequestForSignature with fee subtracted', async () => { + // Given + const owner = accounts[0] + const user = accounts[4] + const validators = [accounts[1]] + const rewards = [accounts[2]] + const requiredSignatures = 1 + const blockRewardContract = await BlockReward.new() + const rewardableValidators = await RewardableValidators.new() + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled + const feeManager = await FeeManagerErcToErcPOSDAO.new() + const fee = 0.001 + const homeFee = web3.toBigNumber(web3.toWei(0.001, "ether")) + const foreignFee = web3.toBigNumber(web3.toWei(0.001, "ether")) + + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, blockRewardContract.address, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + const value = halfEther + const finalValue = value.mul(web3.toBigNumber(1 - fee)) + await token.mint(user, value, {from: owner}).should.be.fulfilled; + + // When + await token.transferAndCall(homeBridge.address, value, '0x00', {from: user}).should.be.fulfilled; + + // Then + const events = await getEvents(homeBridge, {event: 'UserRequestForSignature'}); + events[0].args.should.be.deep.equal({ + recipient: user, + value: finalValue + }) + }) + }) + + // submit signatures + describe('#rewardable_submitSignatures', () => { + let fee, homeFee, foreignFee, homeBridge, rewardableValidators, blockRewardContract, feeManager + beforeEach(async () => { + token = await ERC677BridgeTokenRewardable.new("Some ERC20", "RSZT", 18); + rewardableValidators = await RewardableValidators.new() + feeManager = await FeeManagerErcToErcPOSDAO.new() + homeBridge = await HomeBridge.new() + fee = 0.001 + homeFee = web3.toBigNumber(web3.toWei(fee, "ether")) + foreignFee = web3.toBigNumber(web3.toWei(fee, "ether")) + blockRewardContract = await BlockReward.new() + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, blockRewardContract.address, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + }) + it('should distribute fee to one validator', async () => { + // Given + const recipient = accounts[9]; + const owner = accounts[0] + const validators = [accounts[1]] + const rewards = [accounts[2]] + const requiredSignatures = 1 + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled + await blockRewardContract.setValidatorsRewards(rewards) + await blockRewardContract.setToken(token.address) + await token.setBlockRewardContract(blockRewardContract.address, {from: owner}) + await token.transferOwnership(homeBridge.address, {from: owner}) + + const initialValue = halfEther + const value = initialValue.mul(web3.toBigNumber(1 - fee)) + const feeAmount = initialValue.mul(web3.toBigNumber(fee)) + const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; + const message = createMessage(recipient, value, transactionHash, homeBridge.address); + const signature = await sign(validators[0], message) + + const rewardAddressBalanceBefore = await token.balanceOf(rewards[0]) + rewardAddressBalanceBefore.should.be.bignumber.equal('0') + + // When + const { logs } = await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled; + + // Then + logs.length.should.be.equal(2) + logs[1].event.should.be.equal('CollectedSignatures') + + const finalBridgeBalance = await token.balanceOf(homeBridge.address) + finalBridgeBalance.should.be.bignumber.equal('0') + + const feeDistributed = await blockRewardContract.feeAmount() + feeDistributed.should.be.bignumber.equal(feeAmount) + + const rewardAddressBalanceAfter = await token.balanceOf(rewards[0]) + rewardAddressBalanceAfter.should.be.bignumber.equal(feeAmount) + }) + it('should distribute fee to 3 validators', async () => { + // Given + const recipient = accounts[8]; + const owner = accounts[9] + const validators = [accounts[1], accounts[2], accounts[3]] + const rewards = [accounts[4], accounts[5], accounts[6]] + const requiredSignatures = 2 + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled + await blockRewardContract.setValidatorsRewards(rewards) + await blockRewardContract.setToken(token.address) + await token.setBlockRewardContract(blockRewardContract.address) + await token.transferOwnership(homeBridge.address) + + const initialValue = halfEther + const value = initialValue.mul(web3.toBigNumber(1 - fee)) + const feeAmount = initialValue.mul(web3.toBigNumber(fee)) + const feePerValidator = web3.toBigNumber(166666666666666) + const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) + const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; + const message = createMessage(recipient, value, transactionHash, homeBridge.address); + const signature = await sign(validators[0], message) + const signature2 = await sign(validators[1], message) + + // When + await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled; + const { logs } = await homeBridge.submitSignature(signature2, message, {from: validators[1]}).should.be.fulfilled; + + // Then + logs.length.should.be.equal(2) + logs[1].event.should.be.equal('CollectedSignatures') + + const finalBridgeBalance = await token.balanceOf(homeBridge.address) + finalBridgeBalance.should.be.bignumber.equal('0') + + const feeDistributed = await blockRewardContract.feeAmount() + feeDistributed.should.be.bignumber.equal(feeAmount) + + const balanceRewardAddress1 = await token.balanceOf(rewards[0]) + const balanceRewardAddress2 = await token.balanceOf(rewards[1]) + const balanceRewardAddress3 = await token.balanceOf(rewards[2]) + + expect(balanceRewardAddress1.eq(feePerValidator) || balanceRewardAddress1.eq(feePerValidatorPlusDiff)).to.equal(true) + expect(balanceRewardAddress2.eq(feePerValidator) || balanceRewardAddress2.eq(feePerValidatorPlusDiff)).to.equal(true) + expect(balanceRewardAddress3.eq(feePerValidator) || balanceRewardAddress3.eq(feePerValidatorPlusDiff)).to.equal(true) + }) + it('should distribute fee to 5 validators', async () => { + // Given + const recipient = accounts[0]; + const owner = accounts[0] + const validators = [accounts[0], accounts[1], accounts[2], accounts[3], accounts[4]] + const rewards = [accounts[5], accounts[6], accounts[7], accounts[8], accounts[9]] + const requiredSignatures = 3 + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled + await blockRewardContract.setValidatorsRewards(rewards) + await blockRewardContract.setToken(token.address) + await token.setBlockRewardContract(blockRewardContract.address) + await token.transferOwnership(homeBridge.address) + + const initialValue = halfEther + const value = initialValue.mul(web3.toBigNumber(1 - fee)) + const feeAmount = initialValue.mul(web3.toBigNumber(fee)) + const feePerValidator = feeAmount.div(web3.toBigNumber(5)) + const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; + const message = createMessage(recipient, value, transactionHash, homeBridge.address); + const signature = await sign(validators[0], message) + const signature2 = await sign(validators[1], message) + const signature3 = await sign(validators[2], message) + + // When + await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled; + await homeBridge.submitSignature(signature2, message, {from: validators[1]}).should.be.fulfilled; + const { logs } = await homeBridge.submitSignature(signature3, message, {from: validators[2]}).should.be.fulfilled; + + // Then + logs.length.should.be.equal(2) + logs[1].event.should.be.equal('CollectedSignatures') + + const finalBridgeBalance = await token.balanceOf(homeBridge.address) + finalBridgeBalance.should.be.bignumber.equal('0') + + const feeDistributed = await blockRewardContract.feeAmount() + feeDistributed.should.be.bignumber.equal(feeAmount) + + const balanceRewardAddress1 = await token.balanceOf(rewards[0]) + const balanceRewardAddress2 = await token.balanceOf(rewards[1]) + const balanceRewardAddress3 = await token.balanceOf(rewards[2]) + const balanceRewardAddress4 = await token.balanceOf(rewards[3]) + const balanceRewardAddress5 = await token.balanceOf(rewards[4]) + + balanceRewardAddress1.should.be.bignumber.equal(feePerValidator) + balanceRewardAddress2.should.be.bignumber.equal(feePerValidator) + balanceRewardAddress3.should.be.bignumber.equal(feePerValidator) + balanceRewardAddress4.should.be.bignumber.equal(feePerValidator) + balanceRewardAddress5.should.be.bignumber.equal(feePerValidator) + }) + }) + // executeAffirmation + describe('#rewardable_executeAffirmation', () => { + let fee, homeFee, foreignFee, homeBridge, rewardableValidators, blockRewardContract, feeManager + beforeEach(async () => { + token = await ERC677BridgeTokenRewardable.new("Some ERC20", "RSZT", 18); + rewardableValidators = await RewardableValidators.new() + feeManager = await FeeManagerErcToErcPOSDAO.new() + homeBridge = await HomeBridge.new() + fee = 0.001 + homeFee = web3.toBigNumber(web3.toWei(fee, "ether")) + foreignFee = web3.toBigNumber(web3.toWei(fee, "ether")) + blockRewardContract = await BlockReward.new() + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, blockRewardContract.address, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + }) + it('should distribute fee to one validator', async () => { + // Given + const recipient = accounts[9]; + const owner = accounts[0] + const validators = [accounts[1]] + const rewards = [accounts[2]] + const requiredSignatures = 1 + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled + await blockRewardContract.setValidatorsRewards(rewards) + await blockRewardContract.setToken(token.address) + await token.setBlockRewardContract(blockRewardContract.address) + await token.transferOwnership(homeBridge.address) + + const initialValue = halfEther + const value = initialValue.mul(web3.toBigNumber(1 - fee)) + const feeAmount = initialValue.mul(web3.toBigNumber(fee)) + const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; + + const rewardAddressBalanceBefore = await token.balanceOf(rewards[0]) + rewardAddressBalanceBefore.should.be.bignumber.equal('0') + + // When + const { logs } = await homeBridge.executeAffirmation(recipient, initialValue, transactionHash, {from: validators[0]}).should.be.fulfilled; + + // Then + logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].args.should.be.deep.equal({ + recipient, + value: initialValue, + transactionHash + }) + + const feeDistributed = await blockRewardContract.feeAmount() + feeDistributed.should.be.bignumber.equal(feeAmount) + + const rewardAddressBalanceAfter = await token.balanceOf(rewards[0]) + rewardAddressBalanceAfter.should.be.bignumber.equal(feeAmount) + + const recipientBalance = await token.balanceOf(recipient) + recipientBalance.should.be.bignumber.equal(value) + }) + }) }) diff --git a/test/helpers/helpers.js b/test/helpers/helpers.js index cb276a2a8..c5012a8a3 100644 --- a/test/helpers/helpers.js +++ b/test/helpers/helpers.js @@ -111,3 +111,20 @@ module.exports.range = range; function ignoreExpectedError() { } module.exports.ignoreExpectedError = ignoreExpectedError; + +const getEvents = function(contract, filter) { + return new Promise((resolve, reject) => { + var event = contract[filter.event](); + event.watch(); + event.get((error, logs) => { + if(logs.length > 0){ + resolve(logs); + } else { + throw Error("Failed to find filtered event for " + filter.event); + } + }); + event.stopWatching(); + }); +} + +module.exports.getEvents = getEvents; diff --git a/test/native_to_erc/foreign_bridge_test.js b/test/native_to_erc/foreign_bridge_test.js index 0a1fb406f..4e1ef2ed0 100644 --- a/test/native_to_erc/foreign_bridge_test.js +++ b/test/native_to_erc/foreign_bridge_test.js @@ -7,7 +7,7 @@ const RewardableValidators = artifacts.require("RewardableValidators.sol"); const POA20 = artifacts.require("ERC677BridgeToken.sol"); const {ERROR_MSG, ZERO_ADDRESS, ERROR_MSG_OPCODE} = require('../setup'); -const {createMessage, sign, signatureToVRS, strip0x} = require('../helpers/helpers'); +const {createMessage, sign, signatureToVRS, strip0x, getEvents} = require('../helpers/helpers'); const oneEther = web3.toBigNumber(web3.toWei(1, "ether")); const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")); const minPerTx = web3.toBigNumber(web3.toWei(0.01, "ether")); @@ -17,20 +17,6 @@ const gasPrice = Web3Utils.toWei('1', 'gwei'); const homeDailyLimit = oneEther const homeMaxPerTx = halfEther -const getEvents = function(contract, filter) { - return new Promise((resolve, reject) => { - var event = contract[filter.event](); - event.watch(); - event.get((error, logs) => { - if(logs.length > 0){ - resolve(logs); - } else { - throw Error("Failed to find filtered event for " + filter.event); - } - }); - event.stopWatching(); - }); -} contract('ForeignBridge', async (accounts) => { let validatorContract, authorities, rewards, owner, token; before(async () => { From 96d75f2b781bb6fb431d4f8576387e50fb008019 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Fri, 29 Mar 2019 11:11:36 -0300 Subject: [PATCH 118/187] Add rewardable erc-to-erc executeAffirmation tests --- test/erc_to_erc/home_bridge.test.js | 107 ++++++++++++++++++++++++++-- 1 file changed, 102 insertions(+), 5 deletions(-) diff --git a/test/erc_to_erc/home_bridge.test.js b/test/erc_to_erc/home_bridge.test.js index 182548af2..27833c0b4 100644 --- a/test/erc_to_erc/home_bridge.test.js +++ b/test/erc_to_erc/home_bridge.test.js @@ -718,8 +718,6 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { feeManagerMode.should.be.equals(bothDirectionsModeHash) }) }) - - // transferAndCall and check that is was burned and event fired describe('#onTokenTransfer', async () => { let homeBridge beforeEach(async () => { @@ -775,8 +773,6 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { }) }) }) - - // submit signatures describe('#rewardable_submitSignatures', () => { let fee, homeFee, foreignFee, homeBridge, rewardableValidators, blockRewardContract, feeManager beforeEach(async () => { @@ -925,7 +921,6 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { balanceRewardAddress5.should.be.bignumber.equal(feePerValidator) }) }) - // executeAffirmation describe('#rewardable_executeAffirmation', () => { let fee, homeFee, foreignFee, homeBridge, rewardableValidators, blockRewardContract, feeManager beforeEach(async () => { @@ -980,5 +975,107 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const recipientBalance = await token.balanceOf(recipient) recipientBalance.should.be.bignumber.equal(value) }) + it('should distribute fee to 3 validators', async () => { + // Given + const recipient = accounts[8] + const owner = accounts[9] + const validators = [accounts[1], accounts[2], accounts[3]] + const rewards = [accounts[4], accounts[5], accounts[6]] + const requiredSignatures = 2 + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled + await blockRewardContract.setValidatorsRewards(rewards) + await blockRewardContract.setToken(token.address) + await token.setBlockRewardContract(blockRewardContract.address) + await token.transferOwnership(homeBridge.address) + + const initialValue = halfEther + const value = initialValue.mul(web3.toBigNumber(1 - fee)) + const feeAmount = initialValue.mul(web3.toBigNumber(fee)) + const feePerValidator = web3.toBigNumber(166666666666666) + const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) + const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80" + + const rewardAddressBalanceBefore = await token.balanceOf(rewards[0]) + rewardAddressBalanceBefore.should.be.bignumber.equal('0') + + // When + await homeBridge.executeAffirmation(recipient, initialValue, transactionHash, {from: validators[0]}).should.be.fulfilled + const { logs } = await homeBridge.executeAffirmation(recipient, initialValue, transactionHash, {from: validators[1]}).should.be.fulfilled + + // Then + logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].args.should.be.deep.equal({ + recipient, + value: initialValue, + transactionHash + }) + + const feeDistributed = await blockRewardContract.feeAmount() + feeDistributed.should.be.bignumber.equal(feeAmount) + + const recipientBalance = await token.balanceOf(recipient) + recipientBalance.should.be.bignumber.equal(value) + + const balanceRewardAddress1 = await token.balanceOf(rewards[0]) + const balanceRewardAddress2 = await token.balanceOf(rewards[1]) + const balanceRewardAddress3 = await token.balanceOf(rewards[2]) + + expect(balanceRewardAddress1.eq(feePerValidator) || balanceRewardAddress1.eq(feePerValidatorPlusDiff)).to.equal(true) + expect(balanceRewardAddress2.eq(feePerValidator) || balanceRewardAddress2.eq(feePerValidatorPlusDiff)).to.equal(true) + expect(balanceRewardAddress3.eq(feePerValidator) || balanceRewardAddress3.eq(feePerValidatorPlusDiff)).to.equal(true) + }) + it('should distribute fee to 5 validators', async () => { + // Given + const recipient = accounts[0] + const owner = accounts[0] + const validators = [accounts[0], accounts[1], accounts[2], accounts[3], accounts[4]] + const rewards = [accounts[5], accounts[6], accounts[7], accounts[8], accounts[9]] + const requiredSignatures = 3 + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled + await blockRewardContract.setValidatorsRewards(rewards) + await blockRewardContract.setToken(token.address) + await token.setBlockRewardContract(blockRewardContract.address) + await token.transferOwnership(homeBridge.address) + + const initialValue = halfEther + const value = initialValue.mul(web3.toBigNumber(1 - fee)) + const feeAmount = initialValue.mul(web3.toBigNumber(fee)) + const feePerValidator = feeAmount.div(web3.toBigNumber(5)) + const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80" + + const rewardAddressBalanceBefore = await token.balanceOf(rewards[0]) + rewardAddressBalanceBefore.should.be.bignumber.equal('0') + + // When + await homeBridge.executeAffirmation(recipient, initialValue, transactionHash, {from: validators[0]}).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, initialValue, transactionHash, {from: validators[1]}).should.be.fulfilled + const { logs } = await homeBridge.executeAffirmation(recipient, initialValue, transactionHash, {from: validators[2]}).should.be.fulfilled + + // Then + logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].args.should.be.deep.equal({ + recipient, + value: initialValue, + transactionHash + }) + + const feeDistributed = await blockRewardContract.feeAmount() + feeDistributed.should.be.bignumber.equal(feeAmount) + + const recipientBalance = await token.balanceOf(recipient) + recipientBalance.should.be.bignumber.equal(value) + + const balanceRewardAddress1 = await token.balanceOf(rewards[0]) + const balanceRewardAddress2 = await token.balanceOf(rewards[1]) + const balanceRewardAddress3 = await token.balanceOf(rewards[2]) + const balanceRewardAddress4 = await token.balanceOf(rewards[3]) + const balanceRewardAddress5 = await token.balanceOf(rewards[4]) + + balanceRewardAddress1.should.be.bignumber.equal(feePerValidator) + balanceRewardAddress2.should.be.bignumber.equal(feePerValidator) + balanceRewardAddress3.should.be.bignumber.equal(feePerValidator) + balanceRewardAddress4.should.be.bignumber.equal(feePerValidator) + balanceRewardAddress5.should.be.bignumber.equal(feePerValidator) + }) }) }) From 0092b10e0eff3bd1fc7fe5922f80ca9181030a46 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Fri, 29 Mar 2019 11:11:58 -0300 Subject: [PATCH 119/187] Fix truffle version --- package-lock.json | 4236 +++++++++++++++++++++++++-------------------- package.json | 4 +- 2 files changed, 2365 insertions(+), 1875 deletions(-) diff --git a/package-lock.json b/package-lock.json index 37f350ac1..00aab6225 100644 --- a/package-lock.json +++ b/package-lock.json @@ -4,14 +4,82 @@ "lockfileVersion": 1, "requires": true, "dependencies": { + "@mrmlnc/readdir-enhanced": { + "version": "2.2.1", + "resolved": "https://registry.npmjs.org/@mrmlnc/readdir-enhanced/-/readdir-enhanced-2.2.1.tgz", + "integrity": "sha512-bPHp6Ji8b41szTOcaP63VlnbbO5Ny6dwAATtY6JTjh5N2OLrb5Qk/Th5cRkRQhkWCt+EJsYrNB0MiL+Gpn6e3g==", + "dev": true, + "requires": { + "call-me-maybe": "^1.0.1", + "glob-to-regexp": "^0.3.0" + } + }, + "@nodelib/fs.stat": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/@nodelib/fs.stat/-/fs.stat-1.1.3.tgz", + "integrity": "sha512-shAmDyaQC4H92APFoIaVDHCx5bStIocgvbwQyxPRrbUY20V1EYTbSDchWbuwlMG3V17cprZhA6+78JfB+3DTPw==", + "dev": true + }, + "@resolver-engine/core": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/@resolver-engine/core/-/core-0.2.1.tgz", + "integrity": "sha512-nsLQHmPJ77QuifqsIvqjaF5B9aHnDzJjp73Q1z6apY3e9nqYrx4Dtowhpsf7Jwftg/XzVDEMQC+OzUBNTS+S1A==", + "dev": true, + "requires": { + "debug": "^3.1.0", + "request": "^2.85.0" + } + }, + "@resolver-engine/fs": { + "version": "0.2.1", + "resolved": "https://registry.npmjs.org/@resolver-engine/fs/-/fs-0.2.1.tgz", + "integrity": "sha512-7kJInM1Qo2LJcKyDhuYzh9ZWd+mal/fynfL9BNjWOiTcOpX+jNfqb/UmGUqros5pceBITlWGqS4lU709yHFUbg==", + "dev": true, + "requires": { + "@resolver-engine/core": "^0.2.1", + "debug": "^3.1.0" + } + }, + "@resolver-engine/imports": { + "version": "0.2.2", + "resolved": "https://registry.npmjs.org/@resolver-engine/imports/-/imports-0.2.2.tgz", + "integrity": "sha512-u5/HUkvo8q34AA+hnxxqqXGfby5swnH0Myw91o3Sm2TETJlNKXibFGSKBavAH+wvWdBi4Z5gS2Odu0PowgVOUg==", + "dev": true, + "requires": { + "@resolver-engine/core": "^0.2.1", + "debug": "^3.1.0", + "hosted-git-info": "^2.6.0" + } + }, + "@resolver-engine/imports-fs": { + "version": "0.2.2", + "resolved": "https://registry.npmjs.org/@resolver-engine/imports-fs/-/imports-fs-0.2.2.tgz", + "integrity": "sha512-gFCgMvCwyppjwq0UzIjde/WI+yDs3oatJhozG9xdjJdewwtd7LiF0T5i9lrHAUtqrQbqoFE4E+ZMRVHWpWHpKQ==", + "dev": true, + "requires": { + "@resolver-engine/fs": "^0.2.1", + "@resolver-engine/imports": "^0.2.2", + "debug": "^3.1.0" + } + }, + "@samverschueren/stream-to-observable": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/@samverschueren/stream-to-observable/-/stream-to-observable-0.3.0.tgz", + "integrity": "sha512-MI4Xx6LHs4Webyvi6EbspgyAb4D2Q2VtnCQ1blOJcoLS6mVa8lNN2rkIy1CVxfTUpoyIbCTkXES1rLXztFD1lg==", + "dev": true, + "requires": { + "any-observable": "^0.3.0" + } + }, "@sindresorhus/is": { "version": "0.7.0", "resolved": "https://registry.npmjs.org/@sindresorhus/is/-/is-0.7.0.tgz", - "integrity": "sha512-ONhaKPIufzzrlNbqtWFFd+jlnemX6lJAgq9ZeiZtS7I1PIf/la7CW4m83rTXRnVnsMbW2k56pGYu7AUFJD9Pow==" + "integrity": "sha512-ONhaKPIufzzrlNbqtWFFd+jlnemX6lJAgq9ZeiZtS7I1PIf/la7CW4m83rTXRnVnsMbW2k56pGYu7AUFJD9Pow==", + "dev": true }, "@types/concat-stream": { "version": "1.6.0", - "resolved": "http://registry.npmjs.org/@types/concat-stream/-/concat-stream-1.6.0.tgz", + "resolved": "https://registry.npmjs.org/@types/concat-stream/-/concat-stream-1.6.0.tgz", "integrity": "sha1-OU2+C7X+5Gs42JZzXoto7yOQ0A0=", "dev": true, "requires": { @@ -20,7 +88,7 @@ }, "@types/form-data": { "version": "0.0.33", - "resolved": "http://registry.npmjs.org/@types/form-data/-/form-data-0.0.33.tgz", + "resolved": "https://registry.npmjs.org/@types/form-data/-/form-data-0.0.33.tgz", "integrity": "sha1-yayFsqX9GENbjIXZ7LUObWyJP/g=", "dev": true, "requires": { @@ -28,15 +96,15 @@ } }, "@types/node": { - "version": "9.6.35", - "resolved": "https://registry.npmjs.org/@types/node/-/node-9.6.35.tgz", - "integrity": "sha512-h5zvHS8wXHGa+Gcqs9K8vqCgOtqjr0+NqG/DDJmQIX1wpR9HivAfgV8bjcD3mGM4bPfQw5Aneb2Pn8355L83jA==", + "version": "10.14.4", + "resolved": "https://registry.npmjs.org/@types/node/-/node-10.14.4.tgz", + "integrity": "sha512-DT25xX/YgyPKiHFOpNuANIQIVvYEwCWXgK2jYYwqgaMrYE6+tq+DtmMwlD3drl6DJbUwtlIDnn0d7tIn/EbXBg==", "dev": true }, "@types/qs": { - "version": "6.5.1", - "resolved": "https://registry.npmjs.org/@types/qs/-/qs-6.5.1.tgz", - "integrity": "sha512-mNhVdZHdtKHMMxbqzNK3RzkBcN1cux3AvuCYGTvjEIQT2uheH3eCAyYsbMbh2Bq8nXkeOWs1kyDiF7geWRFQ4Q==", + "version": "6.5.2", + "resolved": "https://registry.npmjs.org/@types/qs/-/qs-6.5.2.tgz", + "integrity": "sha512-47kAAs3yV/hROraCTQYDMh4p/6zI9+gtssjD0kq9OWsGdLcBge59rl49FnCuJ+iWxEKiqFz6KXzeGH5DRVjNJA==", "dev": true }, "abbrev": { @@ -52,26 +120,6 @@ "dev": true, "requires": { "web3": "^0.18.4" - }, - "dependencies": { - "bignumber.js": { - "version": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", - "from": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", - "dev": true - }, - "web3": { - "version": "0.18.4", - "resolved": "https://registry.npmjs.org/web3/-/web3-0.18.4.tgz", - "integrity": "sha1-gewXhBRUkfLqqJVbMcBgSeB8Xn0=", - "dev": true, - "requires": { - "bignumber.js": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", - "crypto-js": "^3.1.4", - "utf8": "^2.1.1", - "xhr2": "*", - "xmlhttprequest": "*" - } - } } }, "accepts": { @@ -84,43 +132,22 @@ } }, "ajv": { - "version": "5.5.2", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-5.5.2.tgz", - "integrity": "sha1-c7Xuyj+rZT49P5Qis0GtQiBdyWU=", + "version": "6.10.0", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.10.0.tgz", + "integrity": "sha512-nffhOpkymDECQyR0mnsUtoCE8RlX38G0rYP+wgLWFyZuUyuuojSSvi/+euOiQBIn63whYwYVIIH1TvE3tu4OEg==", "requires": { - "co": "^4.6.0", - "fast-deep-equal": "^1.0.0", + "fast-deep-equal": "^2.0.1", "fast-json-stable-stringify": "^2.0.0", - "json-schema-traverse": "^0.3.0" - } - }, - "align-text": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/align-text/-/align-text-0.1.4.tgz", - "integrity": "sha1-DNkKVhCT810KmSVsIrcGlDP60Rc=", - "dev": true, - "requires": { - "kind-of": "^3.0.2", - "longest": "^1.0.1", - "repeat-string": "^1.5.2" - }, - "dependencies": { - "kind-of": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", - "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", - "dev": true, - "requires": { - "is-buffer": "^1.1.5" - } - } + "json-schema-traverse": "^0.4.1", + "uri-js": "^4.2.2" } }, "amdefine": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/amdefine/-/amdefine-1.0.1.tgz", "integrity": "sha1-SlKCrBZHKek2Gbz9OtFR+BfOkfU=", - "dev": true + "dev": true, + "optional": true }, "ansi-align": { "version": "2.0.0", @@ -165,9 +192,10 @@ } }, "ansi-escapes": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-3.1.0.tgz", - "integrity": "sha512-UgAb8H9D41AQnu/PbWlCofQVcnV4Gs2bBJi9eZPxfU/hgglFh3SMDMENRIqdr7H6XFnXdoknctFByVsCOotTVw==" + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-3.2.0.tgz", + "integrity": "sha512-cBhpre4ma+U0T1oM5fXg7Dy1Jw7zzwv7lt/GoCpr+hDQJoYnKVPLL4dCvSEFMmQurOQvSrwT7SL/DAlhBI97RQ==", + "dev": true }, "ansi-regex": { "version": "2.1.1", @@ -178,14 +206,16 @@ "version": "3.2.1", "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.1.tgz", "integrity": "sha512-VT0ZI6kZRdTh8YyJw3SMbYm/u+NqfsAxEpWO0Pf9sq8/e94WxxOpPKx9FR1FlyCtOVDNOQ+8ntlqFxiRc+r5qA==", + "dev": true, "requires": { "color-convert": "^1.9.0" } }, "any-observable": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/any-observable/-/any-observable-0.2.0.tgz", - "integrity": "sha1-xnhwBYADV5AJCD9UrAq6+1wz0kI=" + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/any-observable/-/any-observable-0.3.0.tgz", + "integrity": "sha512-/FQM1EDkTsf63Ub2C6O7GuYFDsSXUwsaZDurV0np41ocwq0jthUAYCmhBX9f+KwlaCgIuWyr/4WlUQUBfKfZog==", + "dev": true }, "anymatch": { "version": "2.0.0", @@ -195,6 +225,17 @@ "requires": { "micromatch": "^3.1.4", "normalize-path": "^2.1.1" + }, + "dependencies": { + "normalize-path": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-2.1.1.tgz", + "integrity": "sha1-GrKLVW4Zg2Oowab35vogE3/mrtk=", + "dev": true, + "requires": { + "remove-trailing-separator": "^1.0.1" + } + } } }, "argparse": { @@ -215,7 +256,8 @@ "arr-flatten": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/arr-flatten/-/arr-flatten-1.1.0.tgz", - "integrity": "sha512-L3hKV5R/p5o81R7O02IGnwpDmkp6E982XhtbuwSe3O4qOtMMMtodicASA1Cny2U+aCXcNpml+m4dPsvsJ3jatg==" + "integrity": "sha512-L3hKV5R/p5o81R7O02IGnwpDmkp6E982XhtbuwSe3O4qOtMMMtodicASA1Cny2U+aCXcNpml+m4dPsvsJ3jatg==", + "dev": true }, "arr-union": { "version": "3.1.0", @@ -226,7 +268,8 @@ "array-differ": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/array-differ/-/array-differ-1.0.0.tgz", - "integrity": "sha1-7/UuN1gknTO+QCuLuOVkuytdQDE=" + "integrity": "sha1-7/UuN1gknTO+QCuLuOVkuytdQDE=", + "dev": true }, "array-flatten": { "version": "1.1.1", @@ -237,6 +280,7 @@ "version": "1.0.2", "resolved": "https://registry.npmjs.org/array-union/-/array-union-1.0.2.tgz", "integrity": "sha1-mjRBDk9OPaI96jdb5b5w8kd47Dk=", + "dev": true, "requires": { "array-uniq": "^1.0.1" } @@ -244,7 +288,8 @@ "array-uniq": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/array-uniq/-/array-uniq-1.0.3.tgz", - "integrity": "sha1-r2rId6Jcx/dOBYiUdThY39sk/bY=" + "integrity": "sha1-r2rId6Jcx/dOBYiUdThY39sk/bY=", + "dev": true }, "array-unique": { "version": "0.3.2", @@ -255,7 +300,8 @@ "arrify": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/arrify/-/arrify-1.0.1.tgz", - "integrity": "sha1-iYUI2iIm84DfkEcoRWhJwVAaSw0=" + "integrity": "sha1-iYUI2iIm84DfkEcoRWhJwVAaSw0=", + "dev": true }, "asap": { "version": "2.0.6", @@ -264,9 +310,12 @@ "dev": true }, "asn1": { - "version": "0.2.3", - "resolved": "https://registry.npmjs.org/asn1/-/asn1-0.2.3.tgz", - "integrity": "sha1-2sh4dxPJlmhJ/IGAd36+nB3fO4Y=" + "version": "0.2.4", + "resolved": "https://registry.npmjs.org/asn1/-/asn1-0.2.4.tgz", + "integrity": "sha512-jxwzQpLQjSmWXgwaCZE9Nz+glAG01yF1QnWgbhGwHI5A6FRIEY6IVqtHhIepHqI7/kyEyQEagBC5mBEFlIYvdg==", + "requires": { + "safer-buffer": "~2.1.0" + } }, "assert-plus": { "version": "1.0.0", @@ -286,22 +335,21 @@ "dev": true }, "ast-types": { - "version": "0.11.3", - "resolved": "https://registry.npmjs.org/ast-types/-/ast-types-0.11.3.tgz", - "integrity": "sha512-XA5o5dsNw8MhyW0Q7MWXJWc4oOzZKbdsEJq45h7c8q/d9DwWZ5F2ugUc1PuMLPGsUnphCt/cNDHu8JeBbxf1qA==" + "version": "0.11.5", + "resolved": "https://registry.npmjs.org/ast-types/-/ast-types-0.11.5.tgz", + "integrity": "sha512-oJjo+5e7/vEc2FBK8gUalV0pba4L3VdBIs2EKhOLHLcOd2FgQIVQN9xb0eZ9IjEWyAL7vq6fGJxOvVvdCHNyMw==", + "dev": true }, "async": { - "version": "2.6.0", - "resolved": "https://registry.npmjs.org/async/-/async-2.6.0.tgz", - "integrity": "sha512-xAfGg1/NTLBBKlHFmnd7PlmUW9KhVQIUuSrYem9xzFUZy13ScvtyGGejaae9iAVRiRq9+Cx7DPFaAAhCpyxyPw==", - "requires": { - "lodash": "^4.14.0" - } + "version": "1.5.2", + "resolved": "https://registry.npmjs.org/async/-/async-1.5.2.tgz", + "integrity": "sha1-7GphrlZIDAw8skHJVhjiCJL5Zyo=", + "dev": true }, "async-each": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/async-each/-/async-each-1.0.1.tgz", - "integrity": "sha1-GdOGodntxufByF04iu28xW0zYC0=", + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/async-each/-/async-each-1.0.2.tgz", + "integrity": "sha512-6xrbvN0MOBKSJDdonmSSz2OwFSgxRaVtBDes26mj9KIGtDo+g9xosFRSC+i1gQh2oAN/tQ62AI/pGZGQjVOiRg==", "dev": true }, "async-limiter": { @@ -315,9 +363,9 @@ "integrity": "sha1-x57Zf380y48robyXkLzDZkdLS3k=" }, "atob": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/atob/-/atob-2.1.1.tgz", - "integrity": "sha1-ri1acpR38onWDdf5amMUoi3Wwio=", + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/atob/-/atob-2.1.2.tgz", + "integrity": "sha512-Wm6ukoaOGJi/73p/cl2GvLjTI5JM1k/O14isD73YML8StrH/7/lRFgmg8nICZgD3bZZvjwCGxtMOD3wWNAu8cg==", "dev": true }, "aws-sign2": { @@ -326,14 +374,15 @@ "integrity": "sha1-tG6JCTSpWR8tL2+G1+ap8bP+dqg=" }, "aws4": { - "version": "1.7.0", - "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.7.0.tgz", - "integrity": "sha512-32NDda82rhwD9/JBCCkB+MRYDp0oSvlo2IL6rQWA10PQi7tDUM3eqMSltXmY+Oyl/7N3P3qNtAlv7X0d9bI28w==" + "version": "1.8.0", + "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.8.0.tgz", + "integrity": "sha512-ReZxvNHIOv88FlT7rxcXIIC0fPt4KZqZbOlivyWtXLt8ESx84zd3kMC6iK5jVeS2qt+g7ftS7ye4fi06X5rtRQ==" }, "babel-code-frame": { "version": "6.26.0", "resolved": "https://registry.npmjs.org/babel-code-frame/-/babel-code-frame-6.26.0.tgz", "integrity": "sha1-Y/1D99weO7fONZR9uP42mj9Yx0s=", + "dev": true, "requires": { "chalk": "^1.1.3", "esutils": "^2.0.2", @@ -343,12 +392,14 @@ "ansi-styles": { "version": "2.2.1", "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-2.2.1.tgz", - "integrity": "sha1-tDLdM1i2NM914eRmQ2gkBTPB3b4=" + "integrity": "sha1-tDLdM1i2NM914eRmQ2gkBTPB3b4=", + "dev": true }, "chalk": { "version": "1.1.3", "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz", "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=", + "dev": true, "requires": { "ansi-styles": "^2.2.1", "escape-string-regexp": "^1.0.2", @@ -360,14 +411,16 @@ "supports-color": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz", - "integrity": "sha1-U10EXOa2Nj+kARcIRimZXp3zJMc=" + "integrity": "sha1-U10EXOa2Nj+kARcIRimZXp3zJMc=", + "dev": true } } }, "babel-core": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-core/-/babel-core-6.26.0.tgz", - "integrity": "sha1-rzL3izGm/O8RnIew/Y2XU/A6C7g=", + "version": "6.26.3", + "resolved": "https://registry.npmjs.org/babel-core/-/babel-core-6.26.3.tgz", + "integrity": "sha512-6jyFLuDmeidKmUEb3NM+/yawG0M2bDZ9Z1qbZP59cyHLz8kYGKYwpJP0UwUKKUiTRNvxfLesJnTedqczP7cTDA==", + "dev": true, "requires": { "babel-code-frame": "^6.26.0", "babel-generator": "^6.26.0", @@ -379,21 +432,31 @@ "babel-traverse": "^6.26.0", "babel-types": "^6.26.0", "babylon": "^6.18.0", - "convert-source-map": "^1.5.0", - "debug": "^2.6.8", + "convert-source-map": "^1.5.1", + "debug": "^2.6.9", "json5": "^0.5.1", "lodash": "^4.17.4", "minimatch": "^3.0.4", "path-is-absolute": "^1.0.1", - "private": "^0.1.7", + "private": "^0.1.8", "slash": "^1.0.0", - "source-map": "^0.5.6" + "source-map": "^0.5.7" }, "dependencies": { "babylon": { "version": "6.18.0", "resolved": "https://registry.npmjs.org/babylon/-/babylon-6.18.0.tgz", - "integrity": "sha512-q/UEjfGJ2Cm3oKV71DJz9d25TPnq5rhBVL2Q4fA5wcC3jcrdn7+SssEybFIxwAvvP+YCsCYNKughoF33GxgycQ==" + "integrity": "sha512-q/UEjfGJ2Cm3oKV71DJz9d25TPnq5rhBVL2Q4fA5wcC3jcrdn7+SssEybFIxwAvvP+YCsCYNKughoF33GxgycQ==", + "dev": true + }, + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, + "requires": { + "ms": "2.0.0" + } } } }, @@ -401,6 +464,7 @@ "version": "6.26.1", "resolved": "https://registry.npmjs.org/babel-generator/-/babel-generator-6.26.1.tgz", "integrity": "sha512-HyfwY6ApZj7BYTcJURpM5tznulaBvyio7/0d4zFOeMPUmfxkCjHocCuoLa2SAGzBI8AREcH3eP3758F672DppA==", + "dev": true, "requires": { "babel-messages": "^6.23.0", "babel-runtime": "^6.26.0", @@ -415,7 +479,8 @@ "jsesc": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-1.3.0.tgz", - "integrity": "sha1-RsP+yMGJKxKwgz25vHYiF226s0s=" + "integrity": "sha1-RsP+yMGJKxKwgz25vHYiF226s0s=", + "dev": true } } }, @@ -423,6 +488,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-helper-bindify-decorators/-/babel-helper-bindify-decorators-6.24.1.tgz", "integrity": "sha1-FMGeXxQte0fxmlJDHlKxzLxAozA=", + "dev": true, "requires": { "babel-runtime": "^6.22.0", "babel-traverse": "^6.24.1", @@ -433,6 +499,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-helper-builder-binary-assignment-operator-visitor/-/babel-helper-builder-binary-assignment-operator-visitor-6.24.1.tgz", "integrity": "sha1-zORReto1b0IgvK6KAsKzRvmlZmQ=", + "dev": true, "requires": { "babel-helper-explode-assignable-expression": "^6.24.1", "babel-runtime": "^6.22.0", @@ -443,6 +510,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-helper-call-delegate/-/babel-helper-call-delegate-6.24.1.tgz", "integrity": "sha1-7Oaqzdx25Bw0YfiL/Fdb0Nqi340=", + "dev": true, "requires": { "babel-helper-hoist-variables": "^6.24.1", "babel-runtime": "^6.22.0", @@ -454,6 +522,7 @@ "version": "6.26.0", "resolved": "https://registry.npmjs.org/babel-helper-define-map/-/babel-helper-define-map-6.26.0.tgz", "integrity": "sha1-pfVtq0GiX5fstJjH66ypgZ+Vvl8=", + "dev": true, "requires": { "babel-helper-function-name": "^6.24.1", "babel-runtime": "^6.26.0", @@ -465,6 +534,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-helper-explode-assignable-expression/-/babel-helper-explode-assignable-expression-6.24.1.tgz", "integrity": "sha1-8luCz33BBDPFX3BZLVdGQArCLKo=", + "dev": true, "requires": { "babel-runtime": "^6.22.0", "babel-traverse": "^6.24.1", @@ -475,6 +545,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-helper-explode-class/-/babel-helper-explode-class-6.24.1.tgz", "integrity": "sha1-fcKjkQ3uAHBW4eMdZAztPVTqqes=", + "dev": true, "requires": { "babel-helper-bindify-decorators": "^6.24.1", "babel-runtime": "^6.22.0", @@ -486,6 +557,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-helper-function-name/-/babel-helper-function-name-6.24.1.tgz", "integrity": "sha1-00dbjAPtmCQqJbSDUasYOZ01gKk=", + "dev": true, "requires": { "babel-helper-get-function-arity": "^6.24.1", "babel-runtime": "^6.22.0", @@ -498,6 +570,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-helper-get-function-arity/-/babel-helper-get-function-arity-6.24.1.tgz", "integrity": "sha1-j3eCqpNAfEHTqlCQj4mwMbG2hT0=", + "dev": true, "requires": { "babel-runtime": "^6.22.0", "babel-types": "^6.24.1" @@ -507,6 +580,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-helper-hoist-variables/-/babel-helper-hoist-variables-6.24.1.tgz", "integrity": "sha1-HssnaJydJVE+rbyZFKc/VAi+enY=", + "dev": true, "requires": { "babel-runtime": "^6.22.0", "babel-types": "^6.24.1" @@ -516,6 +590,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-helper-optimise-call-expression/-/babel-helper-optimise-call-expression-6.24.1.tgz", "integrity": "sha1-96E0J7qfc/j0+pk8VKl4gtEkQlc=", + "dev": true, "requires": { "babel-runtime": "^6.22.0", "babel-types": "^6.24.1" @@ -525,6 +600,7 @@ "version": "6.26.0", "resolved": "https://registry.npmjs.org/babel-helper-regex/-/babel-helper-regex-6.26.0.tgz", "integrity": "sha1-MlxZ+QL4LyS3T6zu0DY5VPZJXnI=", + "dev": true, "requires": { "babel-runtime": "^6.26.0", "babel-types": "^6.26.0", @@ -535,6 +611,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-helper-remap-async-to-generator/-/babel-helper-remap-async-to-generator-6.24.1.tgz", "integrity": "sha1-XsWBgnrXI/7N04HxySg5BnbkVRs=", + "dev": true, "requires": { "babel-helper-function-name": "^6.24.1", "babel-runtime": "^6.22.0", @@ -547,6 +624,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-helper-replace-supers/-/babel-helper-replace-supers-6.24.1.tgz", "integrity": "sha1-v22/5Dk40XNpohPKiov3S2qQqxo=", + "dev": true, "requires": { "babel-helper-optimise-call-expression": "^6.24.1", "babel-messages": "^6.23.0", @@ -560,6 +638,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-helpers/-/babel-helpers-6.24.1.tgz", "integrity": "sha1-NHHenK7DiOXIUOWX5Yom3fN2ArI=", + "dev": true, "requires": { "babel-runtime": "^6.22.0", "babel-template": "^6.24.1" @@ -569,6 +648,7 @@ "version": "6.23.0", "resolved": "https://registry.npmjs.org/babel-messages/-/babel-messages-6.23.0.tgz", "integrity": "sha1-8830cDhYA1sqKVHG7F7fbGLyYw4=", + "dev": true, "requires": { "babel-runtime": "^6.22.0" } @@ -577,6 +657,7 @@ "version": "6.22.0", "resolved": "https://registry.npmjs.org/babel-plugin-check-es2015-constants/-/babel-plugin-check-es2015-constants-6.22.0.tgz", "integrity": "sha1-NRV7EBQm/S/9PaP3XH0ekYNbv4o=", + "dev": true, "requires": { "babel-runtime": "^6.22.0" } @@ -584,62 +665,74 @@ "babel-plugin-syntax-async-functions": { "version": "6.13.0", "resolved": "https://registry.npmjs.org/babel-plugin-syntax-async-functions/-/babel-plugin-syntax-async-functions-6.13.0.tgz", - "integrity": "sha1-ytnK0RkbWtY0vzCuCHI5HgZHvpU=" + "integrity": "sha1-ytnK0RkbWtY0vzCuCHI5HgZHvpU=", + "dev": true }, "babel-plugin-syntax-async-generators": { "version": "6.13.0", "resolved": "https://registry.npmjs.org/babel-plugin-syntax-async-generators/-/babel-plugin-syntax-async-generators-6.13.0.tgz", - "integrity": "sha1-a8lj67FuzLrmuStZbrfzXDQqi5o=" + "integrity": "sha1-a8lj67FuzLrmuStZbrfzXDQqi5o=", + "dev": true }, "babel-plugin-syntax-class-constructor-call": { "version": "6.18.0", "resolved": "https://registry.npmjs.org/babel-plugin-syntax-class-constructor-call/-/babel-plugin-syntax-class-constructor-call-6.18.0.tgz", - "integrity": "sha1-nLnTn+Q8hgC+yBRkVt3L1OGnZBY=" + "integrity": "sha1-nLnTn+Q8hgC+yBRkVt3L1OGnZBY=", + "dev": true }, "babel-plugin-syntax-class-properties": { "version": "6.13.0", "resolved": "https://registry.npmjs.org/babel-plugin-syntax-class-properties/-/babel-plugin-syntax-class-properties-6.13.0.tgz", - "integrity": "sha1-1+sjt5oxf4VDlixQW4J8fWysJ94=" + "integrity": "sha1-1+sjt5oxf4VDlixQW4J8fWysJ94=", + "dev": true }, "babel-plugin-syntax-decorators": { "version": "6.13.0", "resolved": "https://registry.npmjs.org/babel-plugin-syntax-decorators/-/babel-plugin-syntax-decorators-6.13.0.tgz", - "integrity": "sha1-MSVjtNvePMgGzuPkFszurd0RrAs=" + "integrity": "sha1-MSVjtNvePMgGzuPkFszurd0RrAs=", + "dev": true }, "babel-plugin-syntax-dynamic-import": { "version": "6.18.0", "resolved": "https://registry.npmjs.org/babel-plugin-syntax-dynamic-import/-/babel-plugin-syntax-dynamic-import-6.18.0.tgz", - "integrity": "sha1-jWomIpyDdFqZgqRBBRVyyqF5sdo=" + "integrity": "sha1-jWomIpyDdFqZgqRBBRVyyqF5sdo=", + "dev": true }, "babel-plugin-syntax-exponentiation-operator": { "version": "6.13.0", "resolved": "https://registry.npmjs.org/babel-plugin-syntax-exponentiation-operator/-/babel-plugin-syntax-exponentiation-operator-6.13.0.tgz", - "integrity": "sha1-nufoM3KQ2pUoggGmpX9BcDF4MN4=" + "integrity": "sha1-nufoM3KQ2pUoggGmpX9BcDF4MN4=", + "dev": true }, "babel-plugin-syntax-export-extensions": { "version": "6.13.0", "resolved": "https://registry.npmjs.org/babel-plugin-syntax-export-extensions/-/babel-plugin-syntax-export-extensions-6.13.0.tgz", - "integrity": "sha1-cKFITw+QiaToStRLrDU8lbmxJyE=" + "integrity": "sha1-cKFITw+QiaToStRLrDU8lbmxJyE=", + "dev": true }, "babel-plugin-syntax-flow": { "version": "6.18.0", "resolved": "https://registry.npmjs.org/babel-plugin-syntax-flow/-/babel-plugin-syntax-flow-6.18.0.tgz", - "integrity": "sha1-TDqyCiryaqIM0lmVw5jE63AxDI0=" + "integrity": "sha1-TDqyCiryaqIM0lmVw5jE63AxDI0=", + "dev": true }, "babel-plugin-syntax-object-rest-spread": { "version": "6.13.0", "resolved": "https://registry.npmjs.org/babel-plugin-syntax-object-rest-spread/-/babel-plugin-syntax-object-rest-spread-6.13.0.tgz", - "integrity": "sha1-/WU28rzhODb/o6VFjEkDpZe7O/U=" + "integrity": "sha1-/WU28rzhODb/o6VFjEkDpZe7O/U=", + "dev": true }, "babel-plugin-syntax-trailing-function-commas": { "version": "6.22.0", "resolved": "https://registry.npmjs.org/babel-plugin-syntax-trailing-function-commas/-/babel-plugin-syntax-trailing-function-commas-6.22.0.tgz", - "integrity": "sha1-ugNgk3+NBuQBgKQ/4NVhb/9TLPM=" + "integrity": "sha1-ugNgk3+NBuQBgKQ/4NVhb/9TLPM=", + "dev": true }, "babel-plugin-transform-async-generator-functions": { "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-plugin-transform-async-generator-functions/-/babel-plugin-transform-async-generator-functions-6.24.1.tgz", "integrity": "sha1-8FiQAUX9PpkHpt3yjaWfIVJYpds=", + "dev": true, "requires": { "babel-helper-remap-async-to-generator": "^6.24.1", "babel-plugin-syntax-async-generators": "^6.5.0", @@ -650,6 +743,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-plugin-transform-async-to-generator/-/babel-plugin-transform-async-to-generator-6.24.1.tgz", "integrity": "sha1-ZTbjeK/2yx1VF6wOQOs+n8jQh2E=", + "dev": true, "requires": { "babel-helper-remap-async-to-generator": "^6.24.1", "babel-plugin-syntax-async-functions": "^6.8.0", @@ -660,6 +754,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-plugin-transform-class-constructor-call/-/babel-plugin-transform-class-constructor-call-6.24.1.tgz", "integrity": "sha1-gNwoVQWsBn3LjWxl4vbxGrd2Xvk=", + "dev": true, "requires": { "babel-plugin-syntax-class-constructor-call": "^6.18.0", "babel-runtime": "^6.22.0", @@ -670,6 +765,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-plugin-transform-class-properties/-/babel-plugin-transform-class-properties-6.24.1.tgz", "integrity": "sha1-anl2PqYdM9NvN7YRqp3vgagbRqw=", + "dev": true, "requires": { "babel-helper-function-name": "^6.24.1", "babel-plugin-syntax-class-properties": "^6.8.0", @@ -681,6 +777,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-plugin-transform-decorators/-/babel-plugin-transform-decorators-6.24.1.tgz", "integrity": "sha1-eIAT2PjGtSIr33s0Q5Df13Vp4k0=", + "dev": true, "requires": { "babel-helper-explode-class": "^6.24.1", "babel-plugin-syntax-decorators": "^6.13.0", @@ -693,6 +790,7 @@ "version": "6.22.0", "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-arrow-functions/-/babel-plugin-transform-es2015-arrow-functions-6.22.0.tgz", "integrity": "sha1-RSaSy3EdX3ncf4XkQM5BufJE0iE=", + "dev": true, "requires": { "babel-runtime": "^6.22.0" } @@ -701,6 +799,7 @@ "version": "6.22.0", "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-block-scoped-functions/-/babel-plugin-transform-es2015-block-scoped-functions-6.22.0.tgz", "integrity": "sha1-u8UbSflk1wy42OC5ToICRs46YUE=", + "dev": true, "requires": { "babel-runtime": "^6.22.0" } @@ -709,6 +808,7 @@ "version": "6.26.0", "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-block-scoping/-/babel-plugin-transform-es2015-block-scoping-6.26.0.tgz", "integrity": "sha1-1w9SmcEwjQXBL0Y4E7CgnnOxiV8=", + "dev": true, "requires": { "babel-runtime": "^6.26.0", "babel-template": "^6.26.0", @@ -721,6 +821,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-classes/-/babel-plugin-transform-es2015-classes-6.24.1.tgz", "integrity": "sha1-WkxYpQyclGHlZLSyo7+ryXolhNs=", + "dev": true, "requires": { "babel-helper-define-map": "^6.24.1", "babel-helper-function-name": "^6.24.1", @@ -737,6 +838,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-computed-properties/-/babel-plugin-transform-es2015-computed-properties-6.24.1.tgz", "integrity": "sha1-b+Ko0WiV1WNPTNmZttNICjCBWbM=", + "dev": true, "requires": { "babel-runtime": "^6.22.0", "babel-template": "^6.24.1" @@ -746,6 +848,7 @@ "version": "6.23.0", "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-destructuring/-/babel-plugin-transform-es2015-destructuring-6.23.0.tgz", "integrity": "sha1-mXux8auWf2gtKwh2/jWNYOdlxW0=", + "dev": true, "requires": { "babel-runtime": "^6.22.0" } @@ -754,6 +857,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-duplicate-keys/-/babel-plugin-transform-es2015-duplicate-keys-6.24.1.tgz", "integrity": "sha1-c+s9MQypaePvnskcU3QabxV2Qj4=", + "dev": true, "requires": { "babel-runtime": "^6.22.0", "babel-types": "^6.24.1" @@ -763,6 +867,7 @@ "version": "6.23.0", "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-for-of/-/babel-plugin-transform-es2015-for-of-6.23.0.tgz", "integrity": "sha1-9HyVsrYT3x0+zC/bdXNiPHUkhpE=", + "dev": true, "requires": { "babel-runtime": "^6.22.0" } @@ -771,6 +876,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-function-name/-/babel-plugin-transform-es2015-function-name-6.24.1.tgz", "integrity": "sha1-g0yJhTvDaxrw86TF26qU/Y6sqos=", + "dev": true, "requires": { "babel-helper-function-name": "^6.24.1", "babel-runtime": "^6.22.0", @@ -781,6 +887,7 @@ "version": "6.22.0", "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-literals/-/babel-plugin-transform-es2015-literals-6.22.0.tgz", "integrity": "sha1-T1SgLWzWbPkVKAAZox0xklN3yi4=", + "dev": true, "requires": { "babel-runtime": "^6.22.0" } @@ -789,6 +896,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-modules-amd/-/babel-plugin-transform-es2015-modules-amd-6.24.1.tgz", "integrity": "sha1-Oz5UAXI5hC1tGcMBHEvS8AoA0VQ=", + "dev": true, "requires": { "babel-plugin-transform-es2015-modules-commonjs": "^6.24.1", "babel-runtime": "^6.22.0", @@ -796,9 +904,10 @@ } }, "babel-plugin-transform-es2015-modules-commonjs": { - "version": "6.26.0", - "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-modules-commonjs/-/babel-plugin-transform-es2015-modules-commonjs-6.26.0.tgz", - "integrity": "sha1-DYOUApt9xqvhqX7xgeAHWN0uXYo=", + "version": "6.26.2", + "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-modules-commonjs/-/babel-plugin-transform-es2015-modules-commonjs-6.26.2.tgz", + "integrity": "sha512-CV9ROOHEdrjcwhIaJNBGMBCodN+1cfkwtM1SbUHmvyy35KGT7fohbpOxkE2uLz1o6odKK2Ck/tz47z+VqQfi9Q==", + "dev": true, "requires": { "babel-plugin-transform-strict-mode": "^6.24.1", "babel-runtime": "^6.26.0", @@ -810,6 +919,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-modules-systemjs/-/babel-plugin-transform-es2015-modules-systemjs-6.24.1.tgz", "integrity": "sha1-/4mhQrkRmpBhlfXxBuzzBdlAfSM=", + "dev": true, "requires": { "babel-helper-hoist-variables": "^6.24.1", "babel-runtime": "^6.22.0", @@ -820,6 +930,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-modules-umd/-/babel-plugin-transform-es2015-modules-umd-6.24.1.tgz", "integrity": "sha1-rJl+YoXNGO1hdq22B9YCNErThGg=", + "dev": true, "requires": { "babel-plugin-transform-es2015-modules-amd": "^6.24.1", "babel-runtime": "^6.22.0", @@ -830,6 +941,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-object-super/-/babel-plugin-transform-es2015-object-super-6.24.1.tgz", "integrity": "sha1-JM72muIcuDp/hgPa0CH1cusnj40=", + "dev": true, "requires": { "babel-helper-replace-supers": "^6.24.1", "babel-runtime": "^6.22.0" @@ -839,6 +951,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-parameters/-/babel-plugin-transform-es2015-parameters-6.24.1.tgz", "integrity": "sha1-V6w1GrScrxSpfNE7CfZv3wpiXys=", + "dev": true, "requires": { "babel-helper-call-delegate": "^6.24.1", "babel-helper-get-function-arity": "^6.24.1", @@ -852,6 +965,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-shorthand-properties/-/babel-plugin-transform-es2015-shorthand-properties-6.24.1.tgz", "integrity": "sha1-JPh11nIch2YbvZmkYi5R8U3jiqA=", + "dev": true, "requires": { "babel-runtime": "^6.22.0", "babel-types": "^6.24.1" @@ -861,6 +975,7 @@ "version": "6.22.0", "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-spread/-/babel-plugin-transform-es2015-spread-6.22.0.tgz", "integrity": "sha1-1taKmfia7cRTbIGlQujdnxdG+NE=", + "dev": true, "requires": { "babel-runtime": "^6.22.0" } @@ -869,6 +984,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-sticky-regex/-/babel-plugin-transform-es2015-sticky-regex-6.24.1.tgz", "integrity": "sha1-AMHNsaynERLN8M9hJsLta0V8zbw=", + "dev": true, "requires": { "babel-helper-regex": "^6.24.1", "babel-runtime": "^6.22.0", @@ -879,6 +995,7 @@ "version": "6.22.0", "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-template-literals/-/babel-plugin-transform-es2015-template-literals-6.22.0.tgz", "integrity": "sha1-qEs0UPfp+PH2g51taH2oS7EjbY0=", + "dev": true, "requires": { "babel-runtime": "^6.22.0" } @@ -887,6 +1004,7 @@ "version": "6.23.0", "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-typeof-symbol/-/babel-plugin-transform-es2015-typeof-symbol-6.23.0.tgz", "integrity": "sha1-3sCfHN3/lLUqxz1QXITfWdzOs3I=", + "dev": true, "requires": { "babel-runtime": "^6.22.0" } @@ -895,6 +1013,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-plugin-transform-es2015-unicode-regex/-/babel-plugin-transform-es2015-unicode-regex-6.24.1.tgz", "integrity": "sha1-04sS9C6nMj9yk4fxinxa4frrNek=", + "dev": true, "requires": { "babel-helper-regex": "^6.24.1", "babel-runtime": "^6.22.0", @@ -905,6 +1024,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-plugin-transform-exponentiation-operator/-/babel-plugin-transform-exponentiation-operator-6.24.1.tgz", "integrity": "sha1-KrDJx/MJj6SJB3cruBP+QejeOg4=", + "dev": true, "requires": { "babel-helper-builder-binary-assignment-operator-visitor": "^6.24.1", "babel-plugin-syntax-exponentiation-operator": "^6.8.0", @@ -915,6 +1035,7 @@ "version": "6.22.0", "resolved": "https://registry.npmjs.org/babel-plugin-transform-export-extensions/-/babel-plugin-transform-export-extensions-6.22.0.tgz", "integrity": "sha1-U3OLR+deghhYnuqUbLvTkQm75lM=", + "dev": true, "requires": { "babel-plugin-syntax-export-extensions": "^6.8.0", "babel-runtime": "^6.22.0" @@ -924,6 +1045,7 @@ "version": "6.22.0", "resolved": "https://registry.npmjs.org/babel-plugin-transform-flow-strip-types/-/babel-plugin-transform-flow-strip-types-6.22.0.tgz", "integrity": "sha1-hMtnKTXUNxT9wyvOhFaNh0Qc988=", + "dev": true, "requires": { "babel-plugin-syntax-flow": "^6.18.0", "babel-runtime": "^6.22.0" @@ -933,6 +1055,7 @@ "version": "6.26.0", "resolved": "https://registry.npmjs.org/babel-plugin-transform-object-rest-spread/-/babel-plugin-transform-object-rest-spread-6.26.0.tgz", "integrity": "sha1-DzZpLVD+9rfi1LOsFHgTepY7ewY=", + "dev": true, "requires": { "babel-plugin-syntax-object-rest-spread": "^6.8.0", "babel-runtime": "^6.26.0" @@ -942,6 +1065,7 @@ "version": "6.26.0", "resolved": "https://registry.npmjs.org/babel-plugin-transform-regenerator/-/babel-plugin-transform-regenerator-6.26.0.tgz", "integrity": "sha1-4HA2lvveJ/Cj78rPi03KL3s6jy8=", + "dev": true, "requires": { "regenerator-transform": "^0.10.0" } @@ -950,6 +1074,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-plugin-transform-strict-mode/-/babel-plugin-transform-strict-mode-6.24.1.tgz", "integrity": "sha1-1fr3qleKZbvlkc9e2uBKDGcCB1g=", + "dev": true, "requires": { "babel-runtime": "^6.22.0", "babel-types": "^6.24.1" @@ -959,6 +1084,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-preset-es2015/-/babel-preset-es2015-6.24.1.tgz", "integrity": "sha1-1EBQ1rwsn+6nAqrzjXJ6AhBTiTk=", + "dev": true, "requires": { "babel-plugin-check-es2015-constants": "^6.22.0", "babel-plugin-transform-es2015-arrow-functions": "^6.22.0", @@ -990,6 +1116,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-preset-stage-1/-/babel-preset-stage-1-6.24.1.tgz", "integrity": "sha1-dpLNfc1oSZB+auSgqFWJz7niv7A=", + "dev": true, "requires": { "babel-plugin-transform-class-constructor-call": "^6.24.1", "babel-plugin-transform-export-extensions": "^6.22.0", @@ -1000,6 +1127,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-preset-stage-2/-/babel-preset-stage-2-6.24.1.tgz", "integrity": "sha1-2eKWD7PXEYfw5k7sYrwHdnIZvcE=", + "dev": true, "requires": { "babel-plugin-syntax-dynamic-import": "^6.18.0", "babel-plugin-transform-class-properties": "^6.24.1", @@ -1011,6 +1139,7 @@ "version": "6.24.1", "resolved": "https://registry.npmjs.org/babel-preset-stage-3/-/babel-preset-stage-3-6.24.1.tgz", "integrity": "sha1-g2raCp56f6N8sTj7kyb4eTSkg5U=", + "dev": true, "requires": { "babel-plugin-syntax-trailing-function-commas": "^6.22.0", "babel-plugin-transform-async-generator-functions": "^6.24.1", @@ -1023,6 +1152,7 @@ "version": "6.26.0", "resolved": "https://registry.npmjs.org/babel-register/-/babel-register-6.26.0.tgz", "integrity": "sha1-btAhFz4vy0htestFxgCahW9kcHE=", + "dev": true, "requires": { "babel-core": "^6.26.0", "babel-runtime": "^6.26.0", @@ -1037,6 +1167,7 @@ "version": "0.4.18", "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.4.18.tgz", "integrity": "sha512-try0/JqxPLF9nOjvSta7tVondkP5dwgyLDjVoyMDlmjugT2lRZ1OfsrYTkCd2hkDnJTKRbO/Rl3orm8vlsUzbA==", + "dev": true, "requires": { "source-map": "^0.5.6" } @@ -1047,6 +1178,7 @@ "version": "6.26.0", "resolved": "https://registry.npmjs.org/babel-runtime/-/babel-runtime-6.26.0.tgz", "integrity": "sha1-llxwWGaOgrVde/4E/yM3vItWR/4=", + "dev": true, "requires": { "core-js": "^2.4.0", "regenerator-runtime": "^0.11.0" @@ -1056,6 +1188,7 @@ "version": "6.26.0", "resolved": "https://registry.npmjs.org/babel-template/-/babel-template-6.26.0.tgz", "integrity": "sha1-3gPi0WOWsGn0bdn/+FIfsaDjXgI=", + "dev": true, "requires": { "babel-runtime": "^6.26.0", "babel-traverse": "^6.26.0", @@ -1067,7 +1200,8 @@ "babylon": { "version": "6.18.0", "resolved": "https://registry.npmjs.org/babylon/-/babylon-6.18.0.tgz", - "integrity": "sha512-q/UEjfGJ2Cm3oKV71DJz9d25TPnq5rhBVL2Q4fA5wcC3jcrdn7+SssEybFIxwAvvP+YCsCYNKughoF33GxgycQ==" + "integrity": "sha512-q/UEjfGJ2Cm3oKV71DJz9d25TPnq5rhBVL2Q4fA5wcC3jcrdn7+SssEybFIxwAvvP+YCsCYNKughoF33GxgycQ==", + "dev": true } } }, @@ -1075,6 +1209,7 @@ "version": "6.26.0", "resolved": "https://registry.npmjs.org/babel-traverse/-/babel-traverse-6.26.0.tgz", "integrity": "sha1-RqnL1+3MYsjlwGTi0tjQ9ANXZu4=", + "dev": true, "requires": { "babel-code-frame": "^6.26.0", "babel-messages": "^6.23.0", @@ -1090,7 +1225,17 @@ "babylon": { "version": "6.18.0", "resolved": "https://registry.npmjs.org/babylon/-/babylon-6.18.0.tgz", - "integrity": "sha512-q/UEjfGJ2Cm3oKV71DJz9d25TPnq5rhBVL2Q4fA5wcC3jcrdn7+SssEybFIxwAvvP+YCsCYNKughoF33GxgycQ==" + "integrity": "sha512-q/UEjfGJ2Cm3oKV71DJz9d25TPnq5rhBVL2Q4fA5wcC3jcrdn7+SssEybFIxwAvvP+YCsCYNKughoF33GxgycQ==", + "dev": true + }, + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, + "requires": { + "ms": "2.0.0" + } } } }, @@ -1098,6 +1243,7 @@ "version": "6.26.0", "resolved": "https://registry.npmjs.org/babel-types/-/babel-types-6.26.0.tgz", "integrity": "sha1-o7Bz+Uq0nrb6Vc1lInozQ4BjJJc=", + "dev": true, "requires": { "babel-runtime": "^6.26.0", "esutils": "^2.0.2", @@ -1106,9 +1252,10 @@ } }, "babylon": { - "version": "7.0.0-beta.42", - "resolved": "https://registry.npmjs.org/babylon/-/babylon-7.0.0-beta.42.tgz", - "integrity": "sha512-h6E/OkkvcBw/JimbL0p8dIaxrcuQn3QmIYGC/GtJlRYif5LTKBYPHXYwqluJpfS/kOXoz0go+9mkmOVC0M+zWw==" + "version": "7.0.0-beta.47", + "resolved": "https://registry.npmjs.org/babylon/-/babylon-7.0.0-beta.47.tgz", + "integrity": "sha512-+rq2cr4GDhtToEzKFD6KZZMDBXhjFAr9JjPw9pAppZACeEWqNM294j+NdBzkSHYXwzzBmVjZ3nEVJlOhbR2gOQ==", + "dev": true }, "balanced-match": { "version": "1.0.0", @@ -1171,34 +1318,35 @@ } }, "bcrypt-pbkdf": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.1.tgz", - "integrity": "sha1-Y7xdy2EzG5K8Bf1SiVPDNGKgb40=", - "optional": true, + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.2.tgz", + "integrity": "sha1-pDAdOJtqQ/m2f/PKEaP2Y342Dp4=", "requires": { "tweetnacl": "^0.14.3" } }, "big.js": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/big.js/-/big.js-3.2.0.tgz", - "integrity": "sha512-+hN/Zh2D08Mx65pZ/4g5bsmNiZUuChDiQfTUQ7qJr4/kuopCr88xZsAXv6mBoZEsUI4OuGHlX59qE94K2mMW8Q==" + "version": "5.2.2", + "resolved": "https://registry.npmjs.org/big.js/-/big.js-5.2.2.tgz", + "integrity": "sha512-vyL2OymJxmarO8gxMr0mhChsO9QGwhynfuu4+MHTAW6czfq9humCB7rKpUjDd9YUiDPU4mzpyupFSvOClAwbmQ==", + "dev": true }, "bignumber.js": { - "version": "git+https://github.com/frozeman/bignumber.js-nolookahead.git#57692b3ecfc98bbdd6b3a516cb2353652ea49934", - "from": "bignumber.js@git+https://github.com/frozeman/bignumber.js-nolookahead.git#57692b3ecfc98bbdd6b3a516cb2353652ea49934", + "version": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", + "from": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", "dev": true }, "binary-extensions": { - "version": "1.11.0", - "resolved": "https://registry.npmjs.org/binary-extensions/-/binary-extensions-1.11.0.tgz", - "integrity": "sha1-RqoXUftqL5PuXmibsQh9SxTGwgU=", + "version": "1.13.1", + "resolved": "https://registry.npmjs.org/binary-extensions/-/binary-extensions-1.13.1.tgz", + "integrity": "sha512-Un7MIEDdUC5gNpcGDV97op1Ywk748MpHcFTHoYs6qnj1Z3j7I53VG3nwZhKzoBZmbdRNnb6WRdFlwl7tSDuZGw==", "dev": true }, "binaryextensions": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/binaryextensions/-/binaryextensions-2.1.1.tgz", - "integrity": "sha512-XBaoWE9RW8pPdPQNibZsW2zh8TW6gcarXp1FZPwT8Uop8ScSNldJEWf2k9l3HeTqdrEwsOsFcq74RiJECW34yA==" + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/binaryextensions/-/binaryextensions-2.1.2.tgz", + "integrity": "sha512-xVNN69YGDghOqCCtA6FI7avYrr02mTJjOgB0/f1VPD3pJC8QEvjTKWc4epDx8AqxxA75NI0QpVM2gPJXUbE4Tg==", + "dev": true }, "bn.js": { "version": "4.11.6", @@ -1206,20 +1354,20 @@ "integrity": "sha1-UzRK2xRhehP26N0s4okF0cC6MhU=" }, "body-parser": { - "version": "1.18.2", - "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.18.2.tgz", - "integrity": "sha1-h2eKGdhLR9hZuDGZvVm84iKxBFQ=", + "version": "1.18.3", + "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.18.3.tgz", + "integrity": "sha1-WykhmP/dVTs6DyDe0FkrlWlVyLQ=", "requires": { "bytes": "3.0.0", "content-type": "~1.0.4", "debug": "2.6.9", - "depd": "~1.1.1", - "http-errors": "~1.6.2", - "iconv-lite": "0.4.19", + "depd": "~1.1.2", + "http-errors": "~1.6.3", + "iconv-lite": "0.4.23", "on-finished": "~2.3.0", - "qs": "6.5.1", - "raw-body": "2.3.2", - "type-is": "~1.6.15" + "qs": "6.5.2", + "raw-body": "2.3.3", + "type-is": "~1.6.16" }, "dependencies": { "debug": { @@ -1232,14 +1380,6 @@ } } }, - "boom": { - "version": "4.3.1", - "resolved": "https://registry.npmjs.org/boom/-/boom-4.3.1.tgz", - "integrity": "sha1-T4owBctKfjiJ90kDD9JbluAdLjE=", - "requires": { - "hoek": "4.x.x" - } - }, "boxen": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/boxen/-/boxen-1.3.0.tgz", @@ -1343,20 +1483,36 @@ "integrity": "sha1-81HTKWnTL6XXpVZxVCY9korjvR8=" }, "browserify-sha3": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/browserify-sha3/-/browserify-sha3-0.0.1.tgz", - "integrity": "sha1-P/NKMAbvFcD7NWflQbkaI0ASPRE=", + "version": "0.0.4", + "resolved": "https://registry.npmjs.org/browserify-sha3/-/browserify-sha3-0.0.4.tgz", + "integrity": "sha1-CGxHuMgjFsnUcCLCYYWVRXbdjiY=", "requires": { - "js-sha3": "^0.3.1" - }, - "dependencies": { - "js-sha3": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/js-sha3/-/js-sha3-0.3.1.tgz", - "integrity": "sha1-hhIoAhQvCChQKg0d7h2V4lO7AkM=" - } + "js-sha3": "^0.6.1", + "safe-buffer": "^5.1.1" + } + }, + "buffer-alloc": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/buffer-alloc/-/buffer-alloc-1.2.0.tgz", + "integrity": "sha512-CFsHQgjtW1UChdXgbyJGtnm+O/uLQeZdtbDo8mfUgYXCHSM1wgrVxXm6bSyrUuErEb+4sYVGCzASBRot7zyrow==", + "dev": true, + "requires": { + "buffer-alloc-unsafe": "^1.1.0", + "buffer-fill": "^1.0.0" } }, + "buffer-alloc-unsafe": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/buffer-alloc-unsafe/-/buffer-alloc-unsafe-1.1.0.tgz", + "integrity": "sha512-TEM2iMIEQdJ2yjPJoSIsldnleVaAk1oW3DBVUykyOLsEsFmEc9kn+SFFPz+gl54KQNxlDnAwCXosOS9Okx2xAg==", + "dev": true + }, + "buffer-fill": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/buffer-fill/-/buffer-fill-1.0.0.tgz", + "integrity": "sha1-+PeLdniYiO858gXNY39o5wISKyw=", + "dev": true + }, "buffer-from": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.1.tgz", @@ -1368,11 +1524,6 @@ "resolved": "https://registry.npmjs.org/buffer-to-arraybuffer/-/buffer-to-arraybuffer-0.0.5.tgz", "integrity": "sha1-YGSkD6dutDxyOrqe+PbhIW0QURo=" }, - "builtin-modules": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/builtin-modules/-/builtin-modules-1.1.1.tgz", - "integrity": "sha1-Jw8HbFpywC9bZaR9+Uxf46J4iS8=" - }, "bytes": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.0.0.tgz", @@ -1399,6 +1550,7 @@ "version": "2.1.4", "resolved": "https://registry.npmjs.org/cacheable-request/-/cacheable-request-2.1.4.tgz", "integrity": "sha1-DYCIAbY0KtM8kd+dC0TcCbkeXD0=", + "dev": true, "requires": { "clone-response": "1.0.2", "get-stream": "3.0.0", @@ -1407,17 +1559,31 @@ "lowercase-keys": "1.0.0", "normalize-url": "2.0.1", "responselike": "1.0.2" + }, + "dependencies": { + "lowercase-keys": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/lowercase-keys/-/lowercase-keys-1.0.0.tgz", + "integrity": "sha1-TjNms55/VFfjXxMkvfb4jQv8cwY=", + "dev": true + } } }, + "call-me-maybe": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/call-me-maybe/-/call-me-maybe-1.0.1.tgz", + "integrity": "sha1-JtII6onje1y95gJQoV8DHBak1ms=", + "dev": true + }, "camelcase": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-3.0.0.tgz", "integrity": "sha1-MvxLn82vhF/N9+c7uXysImHwqwo=" }, "capture-stack-trace": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/capture-stack-trace/-/capture-stack-trace-1.0.0.tgz", - "integrity": "sha1-Sm+gc5nCa7pH8LJJa00PtAjFVQ0=", + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/capture-stack-trace/-/capture-stack-trace-1.0.1.tgz", + "integrity": "sha512-mYQLZnx5Qt1JgB1WEiMCf2647plpGeQ2NMR/5L0HNZzGQo4fuSPnK+wjfPnKZV0aiJDgzmWqqkV/g7JD+DW0qw==", "dev": true }, "caseless": { @@ -1425,29 +1591,18 @@ "resolved": "https://registry.npmjs.org/caseless/-/caseless-0.12.0.tgz", "integrity": "sha1-G2gcIf+EAzyCZUMJBolCDRhxUdw=" }, - "center-align": { - "version": "0.1.3", - "resolved": "https://registry.npmjs.org/center-align/-/center-align-0.1.3.tgz", - "integrity": "sha1-qg0yYptu6XIgBBHL1EYckHvCt60=", - "dev": true, - "optional": true, - "requires": { - "align-text": "^0.1.3", - "lazy-cache": "^1.0.3" - } - }, "chai": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/chai/-/chai-4.1.2.tgz", - "integrity": "sha1-D2RYS6ZC8PKs4oBiefTwbKI61zw=", + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/chai/-/chai-4.2.0.tgz", + "integrity": "sha512-XQU3bhBukrOsQCuwZndwGcCVQHyZi53fQ6Ys1Fym7E4olpIqqZZhhoFJoaKVvV17lWQoXYwgWN2nF5crA8J2jw==", "dev": true, "requires": { - "assertion-error": "^1.0.1", - "check-error": "^1.0.1", - "deep-eql": "^3.0.0", + "assertion-error": "^1.1.0", + "check-error": "^1.0.2", + "deep-eql": "^3.0.1", "get-func-name": "^2.0.0", - "pathval": "^1.0.0", - "type-detect": "^4.0.0" + "pathval": "^1.1.0", + "type-detect": "^4.0.5" } }, "chai-as-promised": { @@ -1466,9 +1621,10 @@ "dev": true }, "chalk": { - "version": "2.3.2", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.3.2.tgz", - "integrity": "sha512-ZM4j2/ld/YZDc3Ma8PgN7gyAk+kHMMMyzLNryCPGhWrsfAuDVeuid5bpRFTDgMH9JBK2lA4dyyAkkZYF/WcqDQ==", + "version": "2.4.2", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.4.2.tgz", + "integrity": "sha512-Mti+f9lpJNcwF4tWV8/OrTTtF1gZi+f8FqlyAdouralcFWFQWF2+NgCHShjkCb+IFBLq9buZwE1xckQU4peSuQ==", + "dev": true, "requires": { "ansi-styles": "^3.2.1", "escape-string-regexp": "^1.0.5", @@ -1478,12 +1634,14 @@ "has-flag": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", - "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=" + "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=", + "dev": true }, "supports-color": { - "version": "5.3.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.3.0.tgz", - "integrity": "sha512-0aP01LLIskjKs3lq52EC0aGBAJhLq7B2Rd8HC/DR/PtNNpcLilNmHC12O+hu0usQpo7wtHNRqtrhBwtDb0+dNg==", + "version": "5.5.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", + "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", + "dev": true, "requires": { "has-flag": "^3.0.0" } @@ -1493,7 +1651,8 @@ "chardet": { "version": "0.4.2", "resolved": "https://registry.npmjs.org/chardet/-/chardet-0.4.2.tgz", - "integrity": "sha1-tUc7M9yXxCTl2Y3IfVXU2KKci/I=" + "integrity": "sha1-tUc7M9yXxCTl2Y3IfVXU2KKci/I=", + "dev": true }, "charenc": { "version": "0.0.2", @@ -1508,29 +1667,29 @@ "dev": true }, "chokidar": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-2.0.3.tgz", - "integrity": "sha512-zW8iXYZtXMx4kux/nuZVXjkLP+CyIK5Al5FHnj1OgTKGZfp4Oy6/ymtMSKFv3GD8DviEmUPmJg9eFdJ/JzudMg==", + "version": "2.1.5", + "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-2.1.5.tgz", + "integrity": "sha512-i0TprVWp+Kj4WRPtInjexJ8Q+BqTE909VpH8xVhXrJkoc5QC8VO9TryGOqTr+2hljzc1sC62t22h5tZePodM/A==", "dev": true, "requires": { "anymatch": "^2.0.0", - "async-each": "^1.0.0", - "braces": "^2.3.0", - "fsevents": "^1.1.2", + "async-each": "^1.0.1", + "braces": "^2.3.2", + "fsevents": "^1.2.7", "glob-parent": "^3.1.0", - "inherits": "^2.0.1", + "inherits": "^2.0.3", "is-binary-path": "^1.0.0", "is-glob": "^4.0.0", - "normalize-path": "^2.1.1", + "normalize-path": "^3.0.0", "path-is-absolute": "^1.0.0", - "readdirp": "^2.0.0", - "upath": "^1.0.0" + "readdirp": "^2.2.1", + "upath": "^1.1.1" } }, "ci-info": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/ci-info/-/ci-info-1.1.3.tgz", - "integrity": "sha512-SK/846h/Rcy8q9Z9CAwGBLfCJ6EkjJWdpelWDufQpqVDYq2Wnnv8zlSO6AMQap02jvhVruKKpEtQOufo3pFhLg==", + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/ci-info/-/ci-info-1.6.0.tgz", + "integrity": "sha512-vsGdkwSCDpWmP80ncATX7iea5DWQemg1UgCW5J8tqjU3lYw4FBYuj89J0CTVomA7BEfvSZd84GmHko+MxFQU2A==", "dev": true }, "class-utils": { @@ -1566,19 +1725,16 @@ "version": "2.1.0", "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-2.1.0.tgz", "integrity": "sha1-s12sN2R5+sw+lHR9QdDQ9SOP/LU=", + "dev": true, "requires": { "restore-cursor": "^2.0.0" } }, - "cli-spinners": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/cli-spinners/-/cli-spinners-0.1.2.tgz", - "integrity": "sha1-u3ZNiOGF+54eaiofGXcjGPYF4xw=" - }, "cli-table": { "version": "0.3.1", "resolved": "https://registry.npmjs.org/cli-table/-/cli-table-0.3.1.tgz", "integrity": "sha1-9TsFJmqLGguTSz0IIebi3FkUriM=", + "dev": true, "requires": { "colors": "1.0.3" }, @@ -1586,7 +1742,8 @@ "colors": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/colors/-/colors-1.0.3.tgz", - "integrity": "sha1-BDP0TYCWgP3rYO0mDxsMJi6CpAs=" + "integrity": "sha1-BDP0TYCWgP3rYO0mDxsMJi6CpAs=", + "dev": true } } }, @@ -1638,6 +1795,7 @@ "version": "0.2.1", "resolved": "https://registry.npmjs.org/cli-truncate/-/cli-truncate-0.2.1.tgz", "integrity": "sha1-nxXPuwcFAFNpIWxiasfQWrkN1XQ=", + "dev": true, "requires": { "slice-ansi": "0.0.4", "string-width": "^1.0.1" @@ -1646,7 +1804,8 @@ "cli-width": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/cli-width/-/cli-width-2.2.0.tgz", - "integrity": "sha1-/xnt6Kml5XkyQUewwR8PvLq+1jk=" + "integrity": "sha1-/xnt6Kml5XkyQUewwR8PvLq+1jk=", + "dev": true }, "cliui": { "version": "3.2.0", @@ -1661,17 +1820,20 @@ "clone": { "version": "1.0.4", "resolved": "https://registry.npmjs.org/clone/-/clone-1.0.4.tgz", - "integrity": "sha1-2jCcwmPfFZlMaIypAheco8fNfH4=" + "integrity": "sha1-2jCcwmPfFZlMaIypAheco8fNfH4=", + "dev": true }, "clone-buffer": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/clone-buffer/-/clone-buffer-1.0.0.tgz", - "integrity": "sha1-4+JbIHrE5wGvch4staFnksrD3Fg=" + "integrity": "sha1-4+JbIHrE5wGvch4staFnksrD3Fg=", + "dev": true }, "clone-response": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/clone-response/-/clone-response-1.0.2.tgz", "integrity": "sha1-0dyXOSAxTfZ/vrlCI7TuNQI56Ws=", + "dev": true, "requires": { "mimic-response": "^1.0.0" } @@ -1679,23 +1841,20 @@ "clone-stats": { "version": "0.0.1", "resolved": "https://registry.npmjs.org/clone-stats/-/clone-stats-0.0.1.tgz", - "integrity": "sha1-uI+UqCzzi4eR1YBG6kAprYjKmdE=" + "integrity": "sha1-uI+UqCzzi4eR1YBG6kAprYjKmdE=", + "dev": true }, "cloneable-readable": { "version": "1.1.2", "resolved": "https://registry.npmjs.org/cloneable-readable/-/cloneable-readable-1.1.2.tgz", "integrity": "sha512-Bq6+4t+lbM8vhTs/Bef5c5AdEMtapp/iFb6+s4/Hh9MVTt8OLKH7ZOOZSCT+Ys7hsHvqv0GuMPJ1lnQJVHvxpg==", + "dev": true, "requires": { "inherits": "^2.0.1", "process-nextick-args": "^2.0.0", "readable-stream": "^2.3.5" } }, - "co": { - "version": "4.6.0", - "resolved": "https://registry.npmjs.org/co/-/co-4.6.0.tgz", - "integrity": "sha1-bqa989hTrlTMuOR7+gvz+QMfsYQ=" - }, "code-point-at": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/code-point-at/-/code-point-at-1.1.0.tgz", @@ -1712,27 +1871,30 @@ } }, "color-convert": { - "version": "1.9.1", - "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.1.tgz", - "integrity": "sha512-mjGanIiwQJskCC18rPR6OmrZ6fm2Lc7PeGFYwCmy5J34wC6F1PzdGL6xeMfmgicfYcNLGuVFA3WzXtIDCQSZxQ==", + "version": "1.9.3", + "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.3.tgz", + "integrity": "sha512-QfAUtd+vFdAtFQcC8CCyYt1fYWxSqAiK2cSD6zDB8N3cpsEBAvRxp9zOGg6G/SHHJYAT88/az/IuDGALsNVbGg==", + "dev": true, "requires": { - "color-name": "^1.1.1" + "color-name": "1.1.3" } }, "color-name": { "version": "1.1.3", "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz", - "integrity": "sha1-p9BVi9icQveV3UIyj3QIMcpTvCU=" + "integrity": "sha1-p9BVi9icQveV3UIyj3QIMcpTvCU=", + "dev": true }, "colors": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/colors/-/colors-1.2.1.tgz", - "integrity": "sha512-s8+wktIuDSLffCywiwSxQOMqtPxML11a/dtHE17tMn4B1MSWw/C22EKf7M2KGUBcDaVFEGT+S8N02geDXeuNKg==" + "version": "1.3.3", + "resolved": "https://registry.npmjs.org/colors/-/colors-1.3.3.tgz", + "integrity": "sha512-mmGt/1pZqYRjMxB1axhTo16/snVZ5krrKkcmMeVKxzECMMXoCgnvTPp10QgHfcbQZw8Dq2jMNG6je4JlWU0gWg==", + "dev": true }, "combined-stream": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.6.tgz", - "integrity": "sha1-cj599ugBrFYTETp+RFqbactjKBg=", + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.7.tgz", + "integrity": "sha512-brWl9y6vOB1xYPZcpZde3N9zDByXTosAeMDo4p1wzo6UMOX4vumB+TP1RZ76sfE6Md68Q0NJSrE/gbezd4Ul+w==", "requires": { "delayed-stream": "~1.0.0" } @@ -1745,7 +1907,8 @@ "commondir": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/commondir/-/commondir-1.0.1.tgz", - "integrity": "sha1-3dgA2gxmEnOTzKWVDqloo6rxJTs=" + "integrity": "sha1-3dgA2gxmEnOTzKWVDqloo6rxJTs=", + "dev": true }, "component-emitter": { "version": "1.2.1", @@ -1795,9 +1958,13 @@ "integrity": "sha512-hIP3EEPs8tB9AT1L+NUqtwOAps4mk2Zob89MWXMHjHWg9milF/j4osnnQLXBCBFBk/tvIG/tUc9mOUJiPBhPXA==" }, "convert-source-map": { - "version": "1.5.1", - "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-1.5.1.tgz", - "integrity": "sha1-uCeAl7m8IpNl3lxiz1/K7YtVmeU=" + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/convert-source-map/-/convert-source-map-1.6.0.tgz", + "integrity": "sha512-eFu7XigvxdZ1ETfbgPBohgyQ/Z++C0eEhTor0qRwBw9unw+L0/6V8wkSuGgzdThkiS5lSpdptOQPD8Ak40a+7A==", + "dev": true, + "requires": { + "safe-buffer": "~5.1.1" + } }, "cookie": { "version": "0.3.1", @@ -1816,9 +1983,10 @@ "dev": true }, "core-js": { - "version": "2.5.3", - "resolved": "https://registry.npmjs.org/core-js/-/core-js-2.5.3.tgz", - "integrity": "sha1-isw4NFgk8W2DZbfJtCWRaOjtYD4=" + "version": "2.6.5", + "resolved": "https://registry.npmjs.org/core-js/-/core-js-2.6.5.tgz", + "integrity": "sha512-klh/kDpwX8hryYL14M9w/xei6vrv6sE8gTHDG7/T/+SEovB/G4ejwcfE/CBzO6Edsu+OETZMZ3wcX/EjUkrl5A==", + "dev": true }, "core-util-is": { "version": "1.0.2", @@ -1826,9 +1994,9 @@ "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=" }, "cors": { - "version": "2.8.4", - "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.4.tgz", - "integrity": "sha1-K9OB8usgECAQXNUOpZ2mMJBpRoY=", + "version": "2.8.5", + "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.5.tgz", + "integrity": "sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==", "requires": { "object-assign": "^4", "vary": "^1" @@ -1847,21 +2015,11 @@ "version": "5.1.0", "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-5.1.0.tgz", "integrity": "sha1-6L0O/uWPz/b4+UUQoKVUu/ojVEk=", + "dev": true, "requires": { "lru-cache": "^4.0.1", "shebang-command": "^1.2.0", "which": "^1.2.9" - }, - "dependencies": { - "lru-cache": { - "version": "4.1.2", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-4.1.2.tgz", - "integrity": "sha512-wgeVXhrDwAWnIF/yZARsFnMBtdFXOg1b8RIrhilp+0iDYN4mdQcNZElDZ0e4B64BhaxeQ5zN7PMyvu7we1kPeQ==", - "requires": { - "pseudomap": "^1.0.2", - "yallist": "^2.1.2" - } - } } }, "crypt": { @@ -1870,24 +2028,6 @@ "integrity": "sha1-iNf/fsDfuG9xPch7u0LQRNPmxBs=", "dev": true }, - "cryptiles": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/cryptiles/-/cryptiles-3.1.2.tgz", - "integrity": "sha1-qJ+7Ig9c4l7FboxKqKT9e1sNKf4=", - "requires": { - "boom": "5.x.x" - }, - "dependencies": { - "boom": { - "version": "5.2.0", - "resolved": "https://registry.npmjs.org/boom/-/boom-5.2.0.tgz", - "integrity": "sha512-Z5BTk6ZRe4tXXQlkqftmsAUANpXmuwlsF5Oov8ThoMbQRzdGTA1ngYRW160GexgOgjsFOKJz0LYhoNi+2AMBUw==", - "requires": { - "hoek": "4.x.x" - } - } - } - }, "crypto-js": { "version": "3.1.8", "resolved": "https://registry.npmjs.org/crypto-js/-/crypto-js-3.1.8.tgz", @@ -1903,7 +2043,8 @@ "dargs": { "version": "5.1.0", "resolved": "https://registry.npmjs.org/dargs/-/dargs-5.1.0.tgz", - "integrity": "sha1-7H6lDHhWTNNsnV7Bj2Yyn63ieCk=" + "integrity": "sha1-7H6lDHhWTNNsnV7Bj2Yyn63ieCk=", + "dev": true }, "dashdash": { "version": "1.14.1", @@ -1914,14 +2055,16 @@ } }, "date-fns": { - "version": "1.29.0", - "resolved": "https://registry.npmjs.org/date-fns/-/date-fns-1.29.0.tgz", - "integrity": "sha512-lbTXWZ6M20cWH8N9S6afb0SBm6tMk+uUg6z3MqHPKE9atmsY3kJkTm8vKe93izJ2B2+q5MV990sM2CHgtAZaOw==" + "version": "1.30.1", + "resolved": "https://registry.npmjs.org/date-fns/-/date-fns-1.30.1.tgz", + "integrity": "sha512-hBSVCvSmWC+QypYObzwGOd9wqdDpOt+0wl0KbU+R+uuZBS1jN8VsD1ss3irQDknRj5NvxiTF6oj/nDRnN/UQNw==", + "dev": true }, "dateformat": { "version": "3.0.3", "resolved": "https://registry.npmjs.org/dateformat/-/dateformat-3.0.3.tgz", - "integrity": "sha512-jyCETtSl3VMZMWeRo7iY1FL19ges1t55hMo5yaam4Jrsm5EPL89UQkoQRyiI+Yf4k8r2ZpdngkV8hr1lIdjb3Q==" + "integrity": "sha512-jyCETtSl3VMZMWeRo7iY1FL19ges1t55hMo5yaam4Jrsm5EPL89UQkoQRyiI+Yf4k8r2ZpdngkV8hr1lIdjb3Q==", + "dev": true }, "death": { "version": "1.1.0", @@ -1930,9 +2073,9 @@ "dev": true }, "debug": { - "version": "2.6.8", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.8.tgz", - "integrity": "sha1-5zFTHKLt4n0YgiJCfaF4IdaP9Pw=", + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", + "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", "requires": { "ms": "2.0.0" } @@ -1965,9 +2108,10 @@ } }, "deep-extend": { - "version": "0.4.2", - "resolved": "https://registry.npmjs.org/deep-extend/-/deep-extend-0.4.2.tgz", - "integrity": "sha1-SLaZwn4zS/ifEIkr5DL25MfTSn8=" + "version": "0.6.0", + "resolved": "https://registry.npmjs.org/deep-extend/-/deep-extend-0.6.0.tgz", + "integrity": "sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA==", + "dev": true }, "deep-is": { "version": "0.1.3", @@ -1975,6 +2119,14 @@ "integrity": "sha1-s2nW+128E+7PUk+RsHD+7cNXzzQ=", "dev": true }, + "define-properties": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/define-properties/-/define-properties-1.1.3.tgz", + "integrity": "sha512-3MqfYKj2lLzdMSf8ZIZE/V+Zuy+BgD6f164e8K2w7dgnpKArBDerGYpM46IYYcjnkdPNMjPk9A6VFB8+3SKlXQ==", + "requires": { + "object-keys": "^1.0.12" + } + }, "define-property": { "version": "2.0.2", "resolved": "https://registry.npmjs.org/define-property/-/define-property-2.0.2.tgz", @@ -2034,12 +2186,14 @@ "detect-conflict": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/detect-conflict/-/detect-conflict-1.0.1.tgz", - "integrity": "sha1-CIZXpmqWHAUBnbfEIwiDsca0F24=" + "integrity": "sha1-CIZXpmqWHAUBnbfEIwiDsca0F24=", + "dev": true }, "detect-indent": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/detect-indent/-/detect-indent-4.0.0.tgz", "integrity": "sha1-920GQ1LN9Docts5hnE7jqUdd4gg=", + "dev": true, "requires": { "repeating": "^2.0.0" } @@ -2049,6 +2203,33 @@ "resolved": "https://registry.npmjs.org/diff/-/diff-3.3.1.tgz", "integrity": "sha512-MKPHZDMB0o6yHyDryUOScqZibp914ksXwAMYMTHj6KO8UeKsRYNJD3oNCKjTqZon+V488P7N/HzXF8t7ZR95ww==" }, + "dir-glob": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/dir-glob/-/dir-glob-2.0.0.tgz", + "integrity": "sha512-37qirFDz8cA5fimp9feo43fSuRo2gHwaIn6dXL8Ber1dGwUosDrGZeCCXq57WnIqE4aQ+u3eQZzsk1yOzhdwag==", + "dev": true, + "requires": { + "arrify": "^1.0.1", + "path-type": "^3.0.0" + }, + "dependencies": { + "path-type": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/path-type/-/path-type-3.0.0.tgz", + "integrity": "sha512-T2ZUsdZFHgA3u4e5PfPbjd7HDDpxPnQb5jN0SrDsjNSuVXHJqtwTnWqG0B1jZrgmJ/7lj1EmVIByWt1gxGkWvg==", + "dev": true, + "requires": { + "pify": "^3.0.0" + } + }, + "pify": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", + "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=", + "dev": true + } + } + }, "dom-walk": { "version": "0.1.1", "resolved": "https://registry.npmjs.org/dom-walk/-/dom-walk-0.1.1.tgz", @@ -2063,30 +2244,30 @@ "is-obj": "^1.0.0" } }, - "duplexer": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/duplexer/-/duplexer-0.1.1.tgz", - "integrity": "sha1-rOb/gIwc5mtX0ev5eXessCM0z8E=", - "dev": true - }, "duplexer3": { "version": "0.1.4", "resolved": "https://registry.npmjs.org/duplexer3/-/duplexer3-0.1.4.tgz", - "integrity": "sha1-7gHdHKwO08vH/b6jfcCo8c4ALOI=" + "integrity": "sha1-7gHdHKwO08vH/b6jfcCo8c4ALOI=", + "dev": true }, "ecc-jsbn": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/ecc-jsbn/-/ecc-jsbn-0.1.1.tgz", - "integrity": "sha1-D8c6ntXw1Tw4GTOYUj735UN3dQU=", - "optional": true, + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/ecc-jsbn/-/ecc-jsbn-0.1.2.tgz", + "integrity": "sha1-OoOpBOVDUyh4dMVkt1SThoSamMk=", "requires": { - "jsbn": "~0.1.0" + "jsbn": "~0.1.0", + "safer-buffer": "^2.1.0" } }, "editions": { - "version": "1.3.4", - "resolved": "https://registry.npmjs.org/editions/-/editions-1.3.4.tgz", - "integrity": "sha512-gzao+mxnYDzIysXKMQi/+M1mjy/rjestjg6OPoYTtI+3Izp23oiGZitsl9lPDPiTGXbcSIk1iJWhliSaglxnUg==" + "version": "2.1.3", + "resolved": "https://registry.npmjs.org/editions/-/editions-2.1.3.tgz", + "integrity": "sha512-xDZyVm0A4nLgMNWVVLJvcwMjI80ShiH/27RyLiCnW1L273TcJIA25C4pwJ33AWV01OX6UriP35Xu+lH4S7HWQw==", + "dev": true, + "requires": { + "errlop": "^1.1.1", + "semver": "^5.6.0" + } }, "ee-first": { "version": "1.1.1", @@ -2094,19 +2275,21 @@ "integrity": "sha1-WQxhFWsK4vTwJVcyoViyZrxWsh0=" }, "ejs": { - "version": "2.5.8", - "resolved": "https://registry.npmjs.org/ejs/-/ejs-2.5.8.tgz", - "integrity": "sha512-QIDZL54fyV8MDcAsO91BMH1ft2qGGaHIJsJIA/+t+7uvXol1dm413fPcUgUb4k8F/9457rx4/KFE4XfDifrQxQ==" + "version": "2.6.1", + "resolved": "https://registry.npmjs.org/ejs/-/ejs-2.6.1.tgz", + "integrity": "sha512-0xy4A/twfrRCnkhfk8ErDi5DqdAsAqeGxht4xkCUrsvhhbQNs7E+4jV0CN7+NKIY0aHE72+XvqtBIXzD31ZbXQ==", + "dev": true }, "elegant-spinner": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/elegant-spinner/-/elegant-spinner-1.0.1.tgz", - "integrity": "sha1-2wQ1IcldfjA/2PNFvtwzSc+wcp4=" + "integrity": "sha1-2wQ1IcldfjA/2PNFvtwzSc+wcp4=", + "dev": true }, "elliptic": { - "version": "6.4.0", - "resolved": "https://registry.npmjs.org/elliptic/-/elliptic-6.4.0.tgz", - "integrity": "sha1-ysmvh2LIWDYYcAPI3+GT5eLq5d8=", + "version": "6.4.1", + "resolved": "https://registry.npmjs.org/elliptic/-/elliptic-6.4.1.tgz", + "integrity": "sha512-BsXLz5sqX8OHcsh7CqBMztyXARmGQ3LWPtGjJi6DiJHq5C/qvi9P3OqgswKSDftbu8+IoI/QDTAm2fFnQ9SZSQ==", "requires": { "bn.js": "^4.4.0", "brorand": "^1.0.1", @@ -2120,7 +2303,8 @@ "emojis-list": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/emojis-list/-/emojis-list-2.1.0.tgz", - "integrity": "sha1-TapNnbAPmBmIDHn6RXrlsJof04k=" + "integrity": "sha1-TapNnbAPmBmIDHn6RXrlsJof04k=", + "dev": true }, "encodeurl": { "version": "1.0.2", @@ -2128,19 +2312,36 @@ "integrity": "sha1-rT/0yG7C0CkyL1oCw6mmBslbP1k=" }, "enhanced-resolve": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/enhanced-resolve/-/enhanced-resolve-4.0.0.tgz", - "integrity": "sha512-jox/62b2GofV1qTUQTMPEJSDIGycS43evqYzD/KVtEb9OCoki9cnacUPxCrZa7JfPzZSYOCZhu9O9luaMxAX8g==", + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/enhanced-resolve/-/enhanced-resolve-4.1.0.tgz", + "integrity": "sha512-F/7vkyTtyc/llOIn8oWclcB25KdRaiPBpZYDgJHgh/UHtpgT2p2eldQgtQnLtUvfMKPKxbRaQM/hHkvLHt1Vng==", + "dev": true, "requires": { "graceful-fs": "^4.1.2", "memory-fs": "^0.4.0", "tapable": "^1.0.0" } }, + "envinfo": { + "version": "5.12.1", + "resolved": "https://registry.npmjs.org/envinfo/-/envinfo-5.12.1.tgz", + "integrity": "sha512-pwdo0/G3CIkQ0y6PCXq4RdkvId2elvtPCJMG0konqlrfkWQbf1DWeH9K2b/cvu2YgGvPPTOnonZxXM1gikFu1w==", + "dev": true + }, + "errlop": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/errlop/-/errlop-1.1.1.tgz", + "integrity": "sha512-WX7QjiPHhsny7/PQvrhS5VMizXXKoKCS3udaBp8gjlARdbn+XmK300eKBAAN0hGyRaTCtRpOaxK+xFVPUJ3zkw==", + "dev": true, + "requires": { + "editions": "^2.1.2" + } + }, "errno": { "version": "0.1.7", "resolved": "https://registry.npmjs.org/errno/-/errno-0.1.7.tgz", "integrity": "sha512-MfrRBDWzIWifgq6tJj60gkAwtLNb6sQPlcFrSOflcP1aFmmruKQ2wRnze/8V6kgyz7H3FF8Npzv78mZ7XLLflg==", + "dev": true, "requires": { "prr": "~1.0.1" } @@ -2149,19 +2350,43 @@ "version": "7.0.2", "resolved": "https://registry.npmjs.org/error/-/error-7.0.2.tgz", "integrity": "sha1-pfdf/02ZJhJt2sDqXcOOaJFTywI=", + "dev": true, "requires": { "string-template": "~0.2.1", "xtend": "~4.0.0" } }, "error-ex": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.1.tgz", - "integrity": "sha1-+FWobOYa3E6GIcPNoh56dhLDqNw=", + "version": "1.3.2", + "resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.2.tgz", + "integrity": "sha512-7dFHNmqeFSEt2ZBsCriorKnn3Z2pj+fd9kmI6QoWw4//DL+icEBfc0U7qJCisqrTsKTjw4fNFy2pW9OqStD84g==", "requires": { "is-arrayish": "^0.2.1" } }, + "es-abstract": { + "version": "1.13.0", + "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.13.0.tgz", + "integrity": "sha512-vDZfg/ykNxQVwup/8E1BZhVzFfBxs9NqMzGcvIJrqg5k2/5Za2bWo40dK2J1pgLngZ7c+Shh8lwYtLGyrwPutg==", + "requires": { + "es-to-primitive": "^1.2.0", + "function-bind": "^1.1.1", + "has": "^1.0.3", + "is-callable": "^1.1.4", + "is-regex": "^1.0.4", + "object-keys": "^1.0.12" + } + }, + "es-to-primitive": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/es-to-primitive/-/es-to-primitive-1.2.0.tgz", + "integrity": "sha512-qZryBOJjV//LaxLTV6UC//WewneB3LcXOL9NP++ozKVXsIIIpm/2c13UDiD9Jp2eThsecw9m3jPqDwTyobcdbg==", + "requires": { + "is-callable": "^1.1.4", + "is-date-object": "^1.0.1", + "is-symbol": "^1.0.2" + } + }, "escape-html": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/escape-html/-/escape-html-1.0.3.tgz", @@ -2204,9 +2429,10 @@ } }, "esprima": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/esprima/-/esprima-4.0.0.tgz", - "integrity": "sha512-oftTcaMu/EGrEIu904mWteKIv8vMuOgGYo7EhVJJN00R/EED9DCua/xxHRdYnKtcECzVg7xOWhflvJMnqcFZjw==" + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/esprima/-/esprima-4.0.1.tgz", + "integrity": "sha512-eGuFFw7Upda+g4p+QHvnW0RyTX/SVeJBDM/gCtMARO0cLuT2HcEKnTPvhjV6aGeqrCB/sbNop0Kszm0jsaWU4A==", + "dev": true }, "estraverse": { "version": "1.9.3", @@ -2217,7 +2443,8 @@ "esutils": { "version": "2.0.2", "resolved": "https://registry.npmjs.org/esutils/-/esutils-2.0.2.tgz", - "integrity": "sha1-Cr9PHKpbyx96nYrMbepPqqBLrJs=" + "integrity": "sha1-Cr9PHKpbyx96nYrMbepPqqBLrJs=", + "dev": true }, "etag": { "version": "1.8.1", @@ -2242,37 +2469,6 @@ "shelljs": "^0.7.8", "solidity-parser-antlr": "^0.2.10", "sync-request": "^6.0.0" - }, - "dependencies": { - "req-cwd": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/req-cwd/-/req-cwd-2.0.0.tgz", - "integrity": "sha1-1AgrTURZgDZkD7c93qAe1T20nrw=", - "dev": true, - "requires": { - "req-from": "^2.0.0" - } - }, - "req-from": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/req-from/-/req-from-2.0.0.tgz", - "integrity": "sha1-10GI5H+TeW9Kpx327jWuaJ8+DnA=", - "dev": true, - "requires": { - "resolve-from": "^3.0.0" - } - }, - "shelljs": { - "version": "0.7.8", - "resolved": "https://registry.npmjs.org/shelljs/-/shelljs-0.7.8.tgz", - "integrity": "sha1-3svPh0sNHl+3LhSxZKloMEjprLM=", - "dev": true, - "requires": { - "glob": "^7.0.0", - "interpret": "^1.0.0", - "rechoir": "^0.6.2" - } - } } }, "eth-lib": { @@ -2308,25 +2504,11 @@ "number-to-bn": "1.7.0" } }, - "event-stream": { - "version": "3.3.4", - "resolved": "http://registry.npmjs.org/event-stream/-/event-stream-3.3.4.tgz", - "integrity": "sha1-SrTJoPWlTbkzi0w02Gv86PSzVXE=", - "dev": true, - "requires": { - "duplexer": "~0.1.1", - "from": "~0", - "map-stream": "~0.1.0", - "pause-stream": "0.0.11", - "split": "0.3", - "stream-combiner": "~0.0.4", - "through": "~2.3.1" - } - }, "execa": { "version": "0.7.0", "resolved": "https://registry.npmjs.org/execa/-/execa-0.7.0.tgz", "integrity": "sha1-lEvs00zEHuMqY6n68nrVpl/Fl3c=", + "dev": true, "requires": { "cross-spawn": "^5.0.1", "get-stream": "^3.0.0", @@ -2337,11 +2519,6 @@ "strip-eof": "^1.0.0" } }, - "exit-hook": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/exit-hook/-/exit-hook-1.1.1.tgz", - "integrity": "sha1-8FyiM7SMBdVP/wd2XfhQfpXAL/g=" - }, "expand-brackets": { "version": "2.1.4", "resolved": "https://registry.npmjs.org/expand-brackets/-/expand-brackets-2.1.4.tgz", @@ -2357,6 +2534,15 @@ "to-regex": "^3.0.1" }, "dependencies": { + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, + "requires": { + "ms": "2.0.0" + } + }, "define-property": { "version": "0.2.5", "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", @@ -2381,18 +2567,20 @@ "version": "1.8.2", "resolved": "https://registry.npmjs.org/expand-range/-/expand-range-1.8.2.tgz", "integrity": "sha1-opnv/TNf4nIeuujiV+x5ZE/IUzc=", + "dev": true, "requires": { "fill-range": "^2.1.0" }, "dependencies": { "fill-range": { - "version": "2.2.3", - "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-2.2.3.tgz", - "integrity": "sha1-ULd9/X5Gm8dJJHCWNpn+eoSFpyM=", + "version": "2.2.4", + "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-2.2.4.tgz", + "integrity": "sha512-cnrcCbj01+j2gTG921VZPnHbjmdAf8oQV/iGeV2kZxGSyfYjjTyY79ErsK1WJWMpw6DaApEX72binqJE+/d+5Q==", + "dev": true, "requires": { "is-number": "^2.1.0", "isobject": "^2.0.0", - "randomatic": "^1.1.3", + "randomatic": "^3.0.0", "repeat-element": "^1.1.2", "repeat-string": "^1.5.2" } @@ -2401,6 +2589,7 @@ "version": "2.1.0", "resolved": "https://registry.npmjs.org/is-number/-/is-number-2.1.0.tgz", "integrity": "sha1-Afy7s5NGOlSPL0ZszhbezknbkI8=", + "dev": true, "requires": { "kind-of": "^3.0.2" } @@ -2409,6 +2598,7 @@ "version": "2.1.0", "resolved": "https://registry.npmjs.org/isobject/-/isobject-2.1.0.tgz", "integrity": "sha1-8GVWEJaj8dou9GJy+BXIQNh+DIk=", + "dev": true, "requires": { "isarray": "1.0.0" } @@ -2417,6 +2607,7 @@ "version": "3.2.2", "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, "requires": { "is-buffer": "^1.1.5" } @@ -2427,18 +2618,19 @@ "version": "2.0.2", "resolved": "https://registry.npmjs.org/expand-tilde/-/expand-tilde-2.0.2.tgz", "integrity": "sha1-l+gBqgUt8CRU3kawK/YhZCzchQI=", + "dev": true, "requires": { "homedir-polyfill": "^1.0.1" } }, "express": { - "version": "4.16.3", - "resolved": "https://registry.npmjs.org/express/-/express-4.16.3.tgz", - "integrity": "sha1-avilAjUNsyRuzEvs9rWjTSL37VM=", + "version": "4.16.4", + "resolved": "https://registry.npmjs.org/express/-/express-4.16.4.tgz", + "integrity": "sha512-j12Uuyb4FMrd/qQAm6uCHAkPtO8FDTRJZBDd5D2KOL2eLaz1yUNdUB/NOIyq0iU4q4cFarsUCrnFDPBcnksuOg==", "requires": { "accepts": "~1.3.5", "array-flatten": "1.1.1", - "body-parser": "1.18.2", + "body-parser": "1.18.3", "content-disposition": "0.5.2", "content-type": "~1.0.4", "cookie": "0.3.1", @@ -2455,10 +2647,10 @@ "on-finished": "~2.3.0", "parseurl": "~1.3.2", "path-to-regexp": "0.1.7", - "proxy-addr": "~2.0.3", - "qs": "6.5.1", + "proxy-addr": "~2.0.4", + "qs": "6.5.2", "range-parser": "~1.2.0", - "safe-buffer": "5.1.1", + "safe-buffer": "5.1.2", "send": "0.16.2", "serve-static": "1.13.2", "setprototypeof": "1.1.0", @@ -2484,9 +2676,9 @@ } }, "extend": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.1.tgz", - "integrity": "sha1-p1Xqe8Gt/MWjHOfnYtuq3F5jZEQ=" + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz", + "integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==" }, "extend-shallow": { "version": "3.0.2", @@ -2510,9 +2702,10 @@ } }, "external-editor": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/external-editor/-/external-editor-2.1.0.tgz", - "integrity": "sha512-E44iT5QVOUJBKij4IIV3uvxuNlbKS38Tw1HiupxEIHPv9qtC2PrDYohbXV5U+1jnfIXttny8gUhj+oZvflFlzA==", + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/external-editor/-/external-editor-2.2.0.tgz", + "integrity": "sha512-bSn6gvGxKt+b7+6TKEv1ZycHleA7aHhRHyAqJyp5pbUFuYYNIzpZnQDk7AsYckyWdEnTeAnay0aCy2aV6iTk9A==", + "dev": true, "requires": { "chardet": "^0.4.0", "iconv-lite": "^0.4.17", @@ -2590,9 +2783,23 @@ "integrity": "sha1-lpGEQOMEGnpBT4xS48V06zw+HgU=" }, "fast-deep-equal": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-1.1.0.tgz", - "integrity": "sha1-wFNHeBfIa1HaqFPIHgWbcz0CNhQ=" + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-2.0.1.tgz", + "integrity": "sha1-ewUhjd+WZ79/Nwv3/bLLFf3Qqkk=" + }, + "fast-glob": { + "version": "2.2.6", + "resolved": "https://registry.npmjs.org/fast-glob/-/fast-glob-2.2.6.tgz", + "integrity": "sha512-0BvMaZc1k9F+MeWWMe8pL6YltFzZYcJsYU7D4JyDA6PAczaXvxqQQ/z+mDF7/4Mw01DeUc+i3CTKajnkANkV4w==", + "dev": true, + "requires": { + "@mrmlnc/readdir-enhanced": "^2.2.1", + "@nodelib/fs.stat": "^1.1.2", + "glob-parent": "^3.1.0", + "is-glob": "^4.0.0", + "merge2": "^1.2.3", + "micromatch": "^3.1.10" + } }, "fast-json-stable-stringify": { "version": "2.0.0", @@ -2609,6 +2816,7 @@ "version": "2.0.0", "resolved": "https://registry.npmjs.org/figures/-/figures-2.0.0.tgz", "integrity": "sha1-OrGi0qYsi/tDGgyUy3l6L84nyWI=", + "dev": true, "requires": { "escape-string-regexp": "^1.0.5" } @@ -2616,7 +2824,8 @@ "filename-regex": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/filename-regex/-/filename-regex-2.0.1.tgz", - "integrity": "sha1-wcS5vuPglyXdsQa3XB4wH+LxiyY=" + "integrity": "sha1-wcS5vuPglyXdsQa3XB4wH+LxiyY=", + "dev": true }, "fill-range": { "version": "4.0.0", @@ -2683,32 +2892,36 @@ "version": "2.0.0", "resolved": "https://registry.npmjs.org/first-chunk-stream/-/first-chunk-stream-2.0.0.tgz", "integrity": "sha1-G97NuOCDwGZLkZRVgVd6Q6nzHXA=", + "dev": true, "requires": { "readable-stream": "^2.0.2" } }, "flow-parser": { - "version": "0.68.0", - "resolved": "https://registry.npmjs.org/flow-parser/-/flow-parser-0.68.0.tgz", - "integrity": "sha1-nMlmIKEC4xajFLa81WIFzqzoYtg=" + "version": "0.95.2", + "resolved": "https://registry.npmjs.org/flow-parser/-/flow-parser-0.95.2.tgz", + "integrity": "sha512-klLZSnXVtc6ZS1WRkjJvbsNksQZexEXPDaAM739jHkJFXMkcOPpwbBPd+z6EL8RJ8vx1EdzO3CT5ZwWKApTCfA==", + "dev": true }, "for-each": { - "version": "0.3.2", - "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.2.tgz", - "integrity": "sha1-LEBFC5NI6X8oEyJZO6lnBLmr1NQ=", + "version": "0.3.3", + "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.3.tgz", + "integrity": "sha512-jqYfLp7mo9vIyQf8ykW2v7A+2N4QjeCeI5+Dz9XraiO1ign81wjiH7Fb9vSOWvQfNtmSa4H2RoQTrrXivdUZmw==", "requires": { - "is-function": "~1.0.0" + "is-callable": "^1.1.3" } }, "for-in": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/for-in/-/for-in-1.0.2.tgz", - "integrity": "sha1-gQaNKVqBQuwKxybG4iAMMPttXoA=" + "integrity": "sha1-gQaNKVqBQuwKxybG4iAMMPttXoA=", + "dev": true }, "for-own": { "version": "0.1.5", "resolved": "https://registry.npmjs.org/for-own/-/for-own-0.1.5.tgz", "integrity": "sha1-UmXGgaTylNq78XyVCbZ2OqhFEM4=", + "dev": true, "requires": { "for-in": "^1.0.1" } @@ -2719,12 +2932,12 @@ "integrity": "sha1-+8cfDEGt6zf5bFd60e1C2P2sypE=" }, "form-data": { - "version": "2.3.2", - "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.3.2.tgz", - "integrity": "sha1-SXBJi+YEwgwAXU9cI67NIda0kJk=", + "version": "2.3.3", + "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.3.3.tgz", + "integrity": "sha512-1lLKB2Mu3aGP1Q/2eCOx0fNbRMe7XdwktwOruhfqqd0rIJWwN4Dh+E3hrPSlDCXnSR7UtZ1N38rVXm+6+MEhJQ==", "requires": { "asynckit": "^0.4.0", - "combined-stream": "1.0.6", + "combined-stream": "^1.0.6", "mime-types": "^2.1.12" } }, @@ -2747,16 +2960,11 @@ "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.5.2.tgz", "integrity": "sha1-PYyt2Q2XZWn6g1qx+OSyOhBWBac=" }, - "from": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/from/-/from-0.1.7.tgz", - "integrity": "sha1-g8YK/Fi5xWmXAH7Rp2izqzA6RP4=", - "dev": true - }, "from2": { "version": "2.3.0", "resolved": "https://registry.npmjs.org/from2/-/from2-2.3.0.tgz", "integrity": "sha1-i/tVAr3kpNNs/e6gB/zKIdfjgq8=", + "dev": true, "requires": { "inherits": "^2.0.1", "readable-stream": "^2.0.0" @@ -2780,14 +2988,14 @@ "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=" }, "fsevents": { - "version": "1.2.3", - "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-1.2.3.tgz", - "integrity": "sha512-X+57O5YkDTiEQGiw8i7wYc2nQgweIekqkepI8Q3y4wVlurgBt2SuwxTeYUYMZIGpLZH3r/TsMjczCMXE5ZOt7Q==", + "version": "1.2.7", + "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-1.2.7.tgz", + "integrity": "sha512-Pxm6sI2MeBD7RdD12RYsqaP0nMiwx8eZBXCa6z2L+mRHm2DYrOYwihmhjpkdjUHwQhslWQjRpEgNq4XvBmaAuw==", "dev": true, "optional": true, "requires": { "nan": "^2.9.2", - "node-pre-gyp": "^0.9.0" + "node-pre-gyp": "^0.10.0" }, "dependencies": { "abbrev": { @@ -2808,7 +3016,7 @@ "optional": true }, "are-we-there-yet": { - "version": "1.1.4", + "version": "1.1.5", "bundled": true, "dev": true, "optional": true, @@ -2832,7 +3040,7 @@ } }, "chownr": { - "version": "1.0.1", + "version": "1.1.1", "bundled": true, "dev": true, "optional": true @@ -2868,7 +3076,7 @@ } }, "deep-extend": { - "version": "0.4.2", + "version": "0.6.0", "bundled": true, "dev": true, "optional": true @@ -2917,7 +3125,7 @@ } }, "glob": { - "version": "7.1.2", + "version": "7.1.3", "bundled": true, "dev": true, "optional": true, @@ -2937,12 +3145,12 @@ "optional": true }, "iconv-lite": { - "version": "0.4.21", + "version": "0.4.24", "bundled": true, "dev": true, "optional": true, "requires": { - "safer-buffer": "^2.1.0" + "safer-buffer": ">= 2.1.2 < 3" } }, "ignore-walk": { @@ -3003,16 +3211,16 @@ "dev": true }, "minipass": { - "version": "2.2.4", + "version": "2.3.5", "bundled": true, "dev": true, "requires": { - "safe-buffer": "^5.1.1", + "safe-buffer": "^5.1.2", "yallist": "^3.0.0" } }, "minizlib": { - "version": "1.1.0", + "version": "1.2.1", "bundled": true, "dev": true, "optional": true, @@ -3035,7 +3243,7 @@ "optional": true }, "needle": { - "version": "2.2.0", + "version": "2.2.4", "bundled": true, "dev": true, "optional": true, @@ -3046,18 +3254,18 @@ } }, "node-pre-gyp": { - "version": "0.9.1", + "version": "0.10.3", "bundled": true, "dev": true, "optional": true, "requires": { "detect-libc": "^1.0.2", "mkdirp": "^0.5.1", - "needle": "^2.2.0", + "needle": "^2.2.1", "nopt": "^4.0.1", "npm-packlist": "^1.1.6", "npmlog": "^4.0.2", - "rc": "^1.1.7", + "rc": "^1.2.7", "rimraf": "^2.6.1", "semver": "^5.3.0", "tar": "^4" @@ -3074,13 +3282,13 @@ } }, "npm-bundled": { - "version": "1.0.3", + "version": "1.0.5", "bundled": true, "dev": true, "optional": true }, "npm-packlist": { - "version": "1.1.10", + "version": "1.2.0", "bundled": true, "dev": true, "optional": true, @@ -3155,12 +3363,12 @@ "optional": true }, "rc": { - "version": "1.2.6", + "version": "1.2.8", "bundled": true, "dev": true, "optional": true, "requires": { - "deep-extend": "~0.4.0", + "deep-extend": "^0.6.0", "ini": "~1.3.0", "minimist": "^1.2.0", "strip-json-comments": "~2.0.1" @@ -3190,16 +3398,16 @@ } }, "rimraf": { - "version": "2.6.2", + "version": "2.6.3", "bundled": true, "dev": true, "optional": true, "requires": { - "glob": "^7.0.5" + "glob": "^7.1.3" } }, "safe-buffer": { - "version": "5.1.1", + "version": "5.1.2", "bundled": true, "dev": true }, @@ -3216,7 +3424,7 @@ "optional": true }, "semver": { - "version": "5.5.0", + "version": "5.6.0", "bundled": true, "dev": true, "optional": true @@ -3267,17 +3475,17 @@ "optional": true }, "tar": { - "version": "4.4.1", + "version": "4.4.8", "bundled": true, "dev": true, "optional": true, "requires": { - "chownr": "^1.0.1", + "chownr": "^1.1.1", "fs-minipass": "^1.2.5", - "minipass": "^2.2.4", - "minizlib": "^1.1.0", + "minipass": "^2.3.4", + "minizlib": "^1.1.1", "mkdirp": "^0.5.0", - "safe-buffer": "^5.1.1", + "safe-buffer": "^5.1.2", "yallist": "^3.0.2" } }, @@ -3288,12 +3496,12 @@ "optional": true }, "wide-align": { - "version": "1.1.2", + "version": "1.1.3", "bundled": true, "dev": true, "optional": true, "requires": { - "string-width": "^1.0.2" + "string-width": "^1.0.2 || 2" } }, "wrappy": { @@ -3302,61 +3510,384 @@ "dev": true }, "yallist": { - "version": "3.0.2", + "version": "3.0.3", "bundled": true, "dev": true } } }, - "ganache-cli": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/ganache-cli/-/ganache-cli-6.1.0.tgz", - "integrity": "sha512-FdTeyk4uLRHGeFiMe+Qnh4Hc5KiTVqvRVVvLDFJEVVKC1P1yHhEgZeh9sp1KhuvxSrxToxgJS25UapYQwH4zHw==", - "requires": { - "source-map-support": "^0.5.3", - "webpack-cli": "^2.0.9" - } - }, - "get-caller-file": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/get-caller-file/-/get-caller-file-1.0.2.tgz", - "integrity": "sha1-9wLmMSfn4jHBYKgMFVSstw1QR+U=" - }, - "get-func-name": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/get-func-name/-/get-func-name-2.0.0.tgz", - "integrity": "sha1-6td0q+5y4gQJQzoGY2YCPdaIekE=", - "dev": true - }, - "get-port": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/get-port/-/get-port-3.2.0.tgz", - "integrity": "sha1-3Xzn3hh8Bsi/NTeWrHHgmfCYDrw=", - "dev": true - }, - "get-stream": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-3.0.0.tgz", - "integrity": "sha1-jpQ9E1jcN1VQVOy+LtsFqhdO3hQ=" - }, - "get-value": { - "version": "2.0.6", - "resolved": "https://registry.npmjs.org/get-value/-/get-value-2.0.6.tgz", - "integrity": "sha1-3BXKHGcjh8p2vTesCjlbogQqLCg=", - "dev": true + "function-bind": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz", + "integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==" }, - "getpass": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/getpass/-/getpass-0.1.7.tgz", - "integrity": "sha1-Xv+OPmhNVprkyysSgmBOi6YhSfo=", + "ganache-cli": { + "version": "6.4.1", + "resolved": "https://registry.npmjs.org/ganache-cli/-/ganache-cli-6.4.1.tgz", + "integrity": "sha512-MUZ1DNnmlTrXnH6EuINuew75AI9d/wbIC0WpZCJo5Endsf6ZwEvfnfxGMpEnVizRri1mon2WWxLGAmALDxVcRQ==", "requires": { - "assert-plus": "^1.0.0" - } - }, - "gh-got": { + "bn.js": "4.11.8", + "source-map-support": "0.5.9", + "yargs": "11.1.0" + }, + "dependencies": { + "ansi-regex": { + "version": "3.0.0", + "bundled": true + }, + "bn.js": { + "version": "4.11.8", + "bundled": true + }, + "buffer-from": { + "version": "1.1.1", + "bundled": true + }, + "camelcase": { + "version": "4.1.0", + "bundled": true + }, + "cliui": { + "version": "4.1.0", + "bundled": true, + "requires": { + "string-width": "^2.1.1", + "strip-ansi": "^4.0.0", + "wrap-ansi": "^2.0.0" + } + }, + "code-point-at": { + "version": "1.1.0", + "bundled": true + }, + "cross-spawn": { + "version": "5.1.0", + "bundled": true, + "requires": { + "lru-cache": "^4.0.1", + "shebang-command": "^1.2.0", + "which": "^1.2.9" + } + }, + "decamelize": { + "version": "1.2.0", + "bundled": true + }, + "execa": { + "version": "0.7.0", + "bundled": true, + "requires": { + "cross-spawn": "^5.0.1", + "get-stream": "^3.0.0", + "is-stream": "^1.1.0", + "npm-run-path": "^2.0.0", + "p-finally": "^1.0.0", + "signal-exit": "^3.0.0", + "strip-eof": "^1.0.0" + } + }, + "find-up": { + "version": "2.1.0", + "bundled": true, + "requires": { + "locate-path": "^2.0.0" + } + }, + "get-caller-file": { + "version": "1.0.3", + "bundled": true + }, + "get-stream": { + "version": "3.0.0", + "bundled": true + }, + "invert-kv": { + "version": "1.0.0", + "bundled": true + }, + "is-fullwidth-code-point": { + "version": "2.0.0", + "bundled": true + }, + "is-stream": { + "version": "1.1.0", + "bundled": true + }, + "isexe": { + "version": "2.0.0", + "bundled": true + }, + "lcid": { + "version": "1.0.0", + "bundled": true, + "requires": { + "invert-kv": "^1.0.0" + } + }, + "locate-path": { + "version": "2.0.0", + "bundled": true, + "requires": { + "p-locate": "^2.0.0", + "path-exists": "^3.0.0" + } + }, + "lru-cache": { + "version": "4.1.4", + "bundled": true, + "requires": { + "pseudomap": "^1.0.2", + "yallist": "^3.0.2" + } + }, + "mem": { + "version": "1.1.0", + "bundled": true, + "requires": { + "mimic-fn": "^1.0.0" + } + }, + "mimic-fn": { + "version": "1.2.0", + "bundled": true + }, + "npm-run-path": { + "version": "2.0.2", + "bundled": true, + "requires": { + "path-key": "^2.0.0" + } + }, + "number-is-nan": { + "version": "1.0.1", + "bundled": true + }, + "os-locale": { + "version": "2.1.0", + "bundled": true, + "requires": { + "execa": "^0.7.0", + "lcid": "^1.0.0", + "mem": "^1.1.0" + } + }, + "p-finally": { + "version": "1.0.0", + "bundled": true + }, + "p-limit": { + "version": "1.3.0", + "bundled": true, + "requires": { + "p-try": "^1.0.0" + } + }, + "p-locate": { + "version": "2.0.0", + "bundled": true, + "requires": { + "p-limit": "^1.1.0" + } + }, + "p-try": { + "version": "1.0.0", + "bundled": true + }, + "path-exists": { + "version": "3.0.0", + "bundled": true + }, + "path-key": { + "version": "2.0.1", + "bundled": true + }, + "pseudomap": { + "version": "1.0.2", + "bundled": true + }, + "require-directory": { + "version": "2.1.1", + "bundled": true + }, + "require-main-filename": { + "version": "1.0.1", + "bundled": true + }, + "set-blocking": { + "version": "2.0.0", + "bundled": true + }, + "shebang-command": { + "version": "1.2.0", + "bundled": true, + "requires": { + "shebang-regex": "^1.0.0" + } + }, + "shebang-regex": { + "version": "1.0.0", + "bundled": true + }, + "signal-exit": { + "version": "3.0.2", + "bundled": true + }, + "source-map": { + "version": "0.6.1", + "bundled": true + }, + "source-map-support": { + "version": "0.5.9", + "bundled": true, + "requires": { + "buffer-from": "^1.0.0", + "source-map": "^0.6.0" + } + }, + "string-width": { + "version": "2.1.1", + "bundled": true, + "requires": { + "is-fullwidth-code-point": "^2.0.0", + "strip-ansi": "^4.0.0" + } + }, + "strip-ansi": { + "version": "4.0.0", + "bundled": true, + "requires": { + "ansi-regex": "^3.0.0" + } + }, + "strip-eof": { + "version": "1.0.0", + "bundled": true + }, + "which": { + "version": "1.3.1", + "bundled": true, + "requires": { + "isexe": "^2.0.0" + } + }, + "which-module": { + "version": "2.0.0", + "bundled": true + }, + "wrap-ansi": { + "version": "2.1.0", + "bundled": true, + "requires": { + "string-width": "^1.0.1", + "strip-ansi": "^3.0.1" + }, + "dependencies": { + "ansi-regex": { + "version": "2.1.1", + "bundled": true + }, + "is-fullwidth-code-point": { + "version": "1.0.0", + "bundled": true, + "requires": { + "number-is-nan": "^1.0.0" + } + }, + "string-width": { + "version": "1.0.2", + "bundled": true, + "requires": { + "code-point-at": "^1.0.0", + "is-fullwidth-code-point": "^1.0.0", + "strip-ansi": "^3.0.0" + } + }, + "strip-ansi": { + "version": "3.0.1", + "bundled": true, + "requires": { + "ansi-regex": "^2.0.0" + } + } + } + }, + "y18n": { + "version": "3.2.1", + "bundled": true + }, + "yallist": { + "version": "3.0.2", + "bundled": true + }, + "yargs": { + "version": "11.1.0", + "bundled": true, + "requires": { + "cliui": "^4.0.0", + "decamelize": "^1.1.1", + "find-up": "^2.1.0", + "get-caller-file": "^1.0.1", + "os-locale": "^2.0.0", + "require-directory": "^2.1.1", + "require-main-filename": "^1.0.1", + "set-blocking": "^2.0.0", + "string-width": "^2.0.0", + "which-module": "^2.0.0", + "y18n": "^3.2.1", + "yargs-parser": "^9.0.2" + } + }, + "yargs-parser": { + "version": "9.0.2", + "bundled": true, + "requires": { + "camelcase": "^4.1.0" + } + } + } + }, + "get-caller-file": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/get-caller-file/-/get-caller-file-1.0.3.tgz", + "integrity": "sha512-3t6rVToeoZfYSGd8YoLFR2DJkiQrIiUrGcjvFX2mDw3bn6k2OtwHN0TNCLbBO+w8qTvimhDkv+LSscbJY1vE6w==" + }, + "get-func-name": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/get-func-name/-/get-func-name-2.0.0.tgz", + "integrity": "sha1-6td0q+5y4gQJQzoGY2YCPdaIekE=", + "dev": true + }, + "get-port": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/get-port/-/get-port-3.2.0.tgz", + "integrity": "sha1-3Xzn3hh8Bsi/NTeWrHHgmfCYDrw=", + "dev": true + }, + "get-stream": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-3.0.0.tgz", + "integrity": "sha1-jpQ9E1jcN1VQVOy+LtsFqhdO3hQ=", + "dev": true + }, + "get-value": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/get-value/-/get-value-2.0.6.tgz", + "integrity": "sha1-3BXKHGcjh8p2vTesCjlbogQqLCg=", + "dev": true + }, + "getpass": { + "version": "0.1.7", + "resolved": "https://registry.npmjs.org/getpass/-/getpass-0.1.7.tgz", + "integrity": "sha1-Xv+OPmhNVprkyysSgmBOi6YhSfo=", + "requires": { + "assert-plus": "^1.0.0" + } + }, + "gh-got": { "version": "6.0.0", "resolved": "https://registry.npmjs.org/gh-got/-/gh-got-6.0.0.tgz", "integrity": "sha512-F/mS+fsWQMo1zfgG9MD8KWvTWPPzzhuVwY++fhQ5Ggd+0P+CAMHtzMZhNxG+TqGfHDChJKsbh6otfMGqO2AKBw==", + "dev": true, "requires": { "got": "^7.0.0", "is-plain-obj": "^1.1.0" @@ -3366,6 +3897,7 @@ "version": "7.1.0", "resolved": "https://registry.npmjs.org/got/-/got-7.1.0.tgz", "integrity": "sha512-Y5WMo7xKKq1muPsxD+KmrR8DH5auG7fBdDVueZwETwV6VytKyU9OX/ddpq2/1hp1vIPvVb4T81dKQz3BivkNLw==", + "dev": true, "requires": { "decompress-response": "^3.2.0", "duplexer3": "^0.1.4", @@ -3386,12 +3918,14 @@ "p-cancelable": { "version": "0.3.0", "resolved": "https://registry.npmjs.org/p-cancelable/-/p-cancelable-0.3.0.tgz", - "integrity": "sha512-RVbZPLso8+jFeq1MfNvgXtCRED2raz/dKpacfTNxsx6pLEpEomM7gah6VeHSYV3+vo0OAi4MkArtQcWWXuQoyw==" + "integrity": "sha512-RVbZPLso8+jFeq1MfNvgXtCRED2raz/dKpacfTNxsx6pLEpEomM7gah6VeHSYV3+vo0OAi4MkArtQcWWXuQoyw==", + "dev": true }, "p-timeout": { "version": "1.2.1", "resolved": "https://registry.npmjs.org/p-timeout/-/p-timeout-1.2.1.tgz", "integrity": "sha1-XrOzU7f86Z8QGhA4iAuwVOu+o4Y=", + "dev": true, "requires": { "p-finally": "^1.0.0" } @@ -3402,19 +3936,20 @@ "version": "4.1.0", "resolved": "https://registry.npmjs.org/github-username/-/github-username-4.1.0.tgz", "integrity": "sha1-y+KABBiDIG2kISrp5LXxacML9Bc=", + "dev": true, "requires": { "gh-got": "^6.0.0" } }, "glob": { - "version": "7.1.1", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.1.tgz", - "integrity": "sha1-gFIR3wT6rxxjo2ADBs31reULLsg=", + "version": "7.1.2", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz", + "integrity": "sha512-MJTUg1kjuLeQCJ+ccE4Vpa6kKVXkPYJ2mOCQyUuKLcLQsdrMCpBPUi8qVE6+YuaJkozeA9NusTAw3hLr8Xe5EQ==", "requires": { "fs.realpath": "^1.0.0", "inflight": "^1.0.4", "inherits": "2", - "minimatch": "^3.0.2", + "minimatch": "^3.0.4", "once": "^1.3.0", "path-is-absolute": "^1.0.0" } @@ -3423,6 +3958,7 @@ "version": "3.1.0", "resolved": "https://registry.npmjs.org/glob-all/-/glob-all-3.1.0.tgz", "integrity": "sha1-iRPd+17hrHgSZWJBsD1SF8ZLAqs=", + "dev": true, "requires": { "glob": "^7.0.5", "yargs": "~1.2.6" @@ -3431,12 +3967,14 @@ "minimist": { "version": "0.1.0", "resolved": "https://registry.npmjs.org/minimist/-/minimist-0.1.0.tgz", - "integrity": "sha1-md9lelJXTCHJBXSX33QnkLK0wN4=" + "integrity": "sha1-md9lelJXTCHJBXSX33QnkLK0wN4=", + "dev": true }, "yargs": { "version": "1.2.6", "resolved": "https://registry.npmjs.org/yargs/-/yargs-1.2.6.tgz", "integrity": "sha1-nHtKgv1dWVsr8Xq23MQxNUMv40s=", + "dev": true, "requires": { "minimist": "^0.1.0" } @@ -3447,6 +3985,7 @@ "version": "0.3.0", "resolved": "https://registry.npmjs.org/glob-base/-/glob-base-0.3.0.tgz", "integrity": "sha1-27Fk9iIbHAscz4Kuoyi0l98Oo8Q=", + "dev": true, "requires": { "glob-parent": "^2.0.0", "is-glob": "^2.0.0" @@ -3456,6 +3995,7 @@ "version": "2.0.0", "resolved": "https://registry.npmjs.org/glob-parent/-/glob-parent-2.0.0.tgz", "integrity": "sha1-gTg9ctsFT8zPUzbaqQLxgvbtuyg=", + "dev": true, "requires": { "is-glob": "^2.0.0" } @@ -3463,12 +4003,14 @@ "is-extglob": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-1.0.0.tgz", - "integrity": "sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA=" + "integrity": "sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA=", + "dev": true }, "is-glob": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-2.0.1.tgz", "integrity": "sha1-0Jb5JqPe1WAPP9/ZEZjLCIjC2GM=", + "dev": true, "requires": { "is-extglob": "^1.0.0" } @@ -3496,6 +4038,12 @@ } } }, + "glob-to-regexp": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/glob-to-regexp/-/glob-to-regexp-0.3.0.tgz", + "integrity": "sha1-jFoUlNIGbFcMw7/kSWF1rMTVAqs=", + "dev": true + }, "global": { "version": "4.3.2", "resolved": "https://registry.npmjs.org/global/-/global-4.3.2.tgz", @@ -3518,6 +4066,7 @@ "version": "1.0.0", "resolved": "https://registry.npmjs.org/global-modules/-/global-modules-1.0.0.tgz", "integrity": "sha512-sKzpEkf11GpOFuw0Zzjzmt4B4UZwjOcG757PPvrfhxcLFbq0wpsgpOqxpxtxFiCG4DtG93M6XRVbF2oGdev7bg==", + "dev": true, "requires": { "global-prefix": "^1.0.1", "is-windows": "^1.0.1", @@ -3528,6 +4077,7 @@ "version": "1.0.2", "resolved": "https://registry.npmjs.org/global-prefix/-/global-prefix-1.0.2.tgz", "integrity": "sha1-2/dDxsFJklk8ZVVoy2btMsASLr4=", + "dev": true, "requires": { "expand-tilde": "^2.0.2", "homedir-polyfill": "^1.0.1", @@ -3539,18 +4089,30 @@ "globals": { "version": "9.18.0", "resolved": "https://registry.npmjs.org/globals/-/globals-9.18.0.tgz", - "integrity": "sha512-S0nG3CLEQiY/ILxqtztTWH/3iRRdyBLw6KMDxnKMchrtbj2OFmehVh0WUCfW3DUrIgx/qFrJPICrq4Z4sTR9UQ==" + "integrity": "sha512-S0nG3CLEQiY/ILxqtztTWH/3iRRdyBLw6KMDxnKMchrtbj2OFmehVh0WUCfW3DUrIgx/qFrJPICrq4Z4sTR9UQ==", + "dev": true }, "globby": { - "version": "6.1.0", - "resolved": "https://registry.npmjs.org/globby/-/globby-6.1.0.tgz", - "integrity": "sha1-9abXDoOV4hyFj7BInWTfAkJNUGw=", + "version": "8.0.2", + "resolved": "https://registry.npmjs.org/globby/-/globby-8.0.2.tgz", + "integrity": "sha512-yTzMmKygLp8RUpG1Ymu2VXPSJQZjNAZPD4ywgYEaG7e4tBJeUQBO8OpXrf1RCNcEs5alsoJYPAMiIHP0cmeC7w==", + "dev": true, "requires": { "array-union": "^1.0.1", - "glob": "^7.0.3", - "object-assign": "^4.0.1", - "pify": "^2.0.0", - "pinkie-promise": "^2.0.0" + "dir-glob": "2.0.0", + "fast-glob": "^2.0.2", + "glob": "^7.1.2", + "ignore": "^3.3.5", + "pify": "^3.0.0", + "slash": "^1.0.0" + }, + "dependencies": { + "pify": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", + "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=", + "dev": true + } } }, "got": { @@ -3573,50 +4135,41 @@ } }, "graceful-fs": { - "version": "4.1.11", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.11.tgz", - "integrity": "sha1-Dovf5NHduIVNZOBOp8AOKgJuVlg=" + "version": "4.1.15", + "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.15.tgz", + "integrity": "sha512-6uHUhOPEBgQ24HM+r6b/QwWfZq+yiFcipKFrOFiBEnWdy5sdzYoi+pJeQaPI5qOLRFqWmAXUPQNsielzdLoecA==" }, "grouped-queue": { "version": "0.3.3", "resolved": "https://registry.npmjs.org/grouped-queue/-/grouped-queue-0.3.3.tgz", "integrity": "sha1-wWfSpTGcWg4JZO9qJbfC34mWyFw=", + "dev": true, "requires": { "lodash": "^4.17.2" } }, "growl": { - "version": "1.9.2", - "resolved": "https://registry.npmjs.org/growl/-/growl-1.9.2.tgz", - "integrity": "sha1-Dqd0NxXbjY3ixe3hd14bRayFwC8=", - "dev": true + "version": "1.10.3", + "resolved": "https://registry.npmjs.org/growl/-/growl-1.10.3.tgz", + "integrity": "sha512-hKlsbA5Vu3xsh1Cg3J7jSmX/WaW6A5oBeqzM88oNbCRQFz+zUaXm6yxS4RVytp1scBoJzSYl4YAEOQIt6O8V1Q==" }, "handlebars": { - "version": "4.0.11", - "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.0.11.tgz", - "integrity": "sha1-Ywo13+ApS8KB7a5v/F0yn8eYLcw=", + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.1.1.tgz", + "integrity": "sha512-3Zhi6C0euYZL5sM0Zcy7lInLXKQ+YLcF/olbN010mzGQ4XVm50JeyBnMqofHh696GrciGruC7kCcApPDJvVgwA==", "dev": true, "requires": { - "async": "^1.4.0", + "neo-async": "^2.6.0", "optimist": "^0.6.1", - "source-map": "^0.4.4", - "uglify-js": "^2.6" + "source-map": "^0.6.1", + "uglify-js": "^3.1.4" }, "dependencies": { - "async": { - "version": "1.5.2", - "resolved": "https://registry.npmjs.org/async/-/async-1.5.2.tgz", - "integrity": "sha1-7GphrlZIDAw8skHJVhjiCJL5Zyo=", - "dev": true - }, "source-map": { - "version": "0.4.4", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.4.4.tgz", - "integrity": "sha1-66T12pwNyZneaAMti092FzZSA2s=", - "dev": true, - "requires": { - "amdefine": ">=0.0.4" - } + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", + "dev": true } } }, @@ -3626,18 +4179,27 @@ "integrity": "sha1-qUwiJOvKwEeCoNkDVSHyRzW37JI=" }, "har-validator": { - "version": "5.0.3", - "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-5.0.3.tgz", - "integrity": "sha1-ukAsJmGU8VlW7xXg/PJCmT9qff0=", + "version": "5.1.3", + "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-5.1.3.tgz", + "integrity": "sha512-sNvOCzEQNr/qrvJgc3UG/kD4QtlHycrzwS+6mfTrrSq97BvaYcPZZI1ZSqGSPR73Cxn4LKTD4PttRwfU7jWq5g==", "requires": { - "ajv": "^5.1.0", + "ajv": "^6.5.5", "har-schema": "^2.0.0" } }, + "has": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/has/-/has-1.0.3.tgz", + "integrity": "sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw==", + "requires": { + "function-bind": "^1.1.1" + } + }, "has-ansi": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/has-ansi/-/has-ansi-2.0.0.tgz", "integrity": "sha1-NPUEnOHs3ysGSa8+8k5F7TVBbZE=", + "dev": true, "requires": { "ansi-regex": "^2.0.0" } @@ -3645,23 +4207,30 @@ "has-color": { "version": "0.1.7", "resolved": "https://registry.npmjs.org/has-color/-/has-color-0.1.7.tgz", - "integrity": "sha1-ZxRKUmDDT8PMpnfQQdr1L+e3iy8=" + "integrity": "sha1-ZxRKUmDDT8PMpnfQQdr1L+e3iy8=", + "dev": true }, "has-flag": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-1.0.0.tgz", - "integrity": "sha1-nZ55MWXOAXoA8AQYxD+UKnsdEfo=", - "dev": true + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-2.0.0.tgz", + "integrity": "sha1-6CB68cx7MNRGzHC3NLXovhj4jVE=" }, "has-symbol-support-x": { "version": "1.4.2", "resolved": "https://registry.npmjs.org/has-symbol-support-x/-/has-symbol-support-x-1.4.2.tgz", - "integrity": "sha512-3ToOva++HaW+eCpgqZrCfN51IPB+7bJNVT6CUATzueB5Heb8o6Nam0V3HG5dlDvZU1Gn5QLcbahiKw/XVk5JJw==" + "integrity": "sha512-3ToOva++HaW+eCpgqZrCfN51IPB+7bJNVT6CUATzueB5Heb8o6Nam0V3HG5dlDvZU1Gn5QLcbahiKw/XVk5JJw==", + "dev": true + }, + "has-symbols": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.0.0.tgz", + "integrity": "sha1-uhqPGvKg/DllD1yFA2dwQSIGO0Q=" }, "has-to-string-tag-x": { "version": "1.4.1", "resolved": "https://registry.npmjs.org/has-to-string-tag-x/-/has-to-string-tag-x-1.4.1.tgz", "integrity": "sha512-vdbKfmw+3LoOYVr+mtxHaX5a96+0f3DljYd8JOqvOLsf5mw2Otda2qCDT9qRqLAhrjyQ0h7ual5nOiASpsGNFw==", + "dev": true, "requires": { "has-symbol-support-x": "^1.4.1" } @@ -3699,23 +4268,12 @@ } }, "hash.js": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/hash.js/-/hash.js-1.1.3.tgz", - "integrity": "sha512-/UETyP0W22QILqS+6HowevwhEFJ3MBJnwTf75Qob9Wz9t0DPuisL8kW8YZMK62dHAKE1c1p+gY1TtOLY+USEHA==", + "version": "1.1.7", + "resolved": "https://registry.npmjs.org/hash.js/-/hash.js-1.1.7.tgz", + "integrity": "sha512-taOaskGt4z4SOANNseOviYDvjEJinIkRgmp7LbKP2YTTmVxWBl87s/uzK9r+44BclBSp2X7K1hqeNfz9JbBeXA==", "requires": { "inherits": "^2.0.3", - "minimalistic-assert": "^1.0.0" - } - }, - "hawk": { - "version": "6.0.2", - "resolved": "https://registry.npmjs.org/hawk/-/hawk-6.0.2.tgz", - "integrity": "sha512-miowhl2+U7Qle4vdLqDdPt9m09K6yZhkLDTWGoUiUzrQCn+mHHSmfJgAyGaLRZbPmTqfFFjRV1QWCW0VWUJBbQ==", - "requires": { - "boom": "4.x.x", - "cryptiles": "3.x.x", - "hoek": "4.x.x", - "sntp": "2.x.x" + "minimalistic-assert": "^1.0.1" } }, "he": { @@ -3733,43 +4291,38 @@ "minimalistic-crypto-utils": "^1.0.1" } }, - "hoek": { - "version": "4.2.1", - "resolved": "https://registry.npmjs.org/hoek/-/hoek-4.2.1.tgz", - "integrity": "sha512-QLg82fGkfnJ/4iy1xZ81/9SIJiq1NGFUMGs6ParyjBZr6jW2Ufj/snDqTHixNlHdPNwN2RLVD0Pi3igeK9+JfA==" - }, "home-or-tmp": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/home-or-tmp/-/home-or-tmp-2.0.0.tgz", "integrity": "sha1-42w/LSyufXRqhX440Y1fMqeILbg=", + "dev": true, "requires": { "os-homedir": "^1.0.0", "os-tmpdir": "^1.0.1" } }, "homedir-polyfill": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/homedir-polyfill/-/homedir-polyfill-1.0.1.tgz", - "integrity": "sha1-TCu8inWJmP7r9e1oWA921GdotLw=", + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/homedir-polyfill/-/homedir-polyfill-1.0.3.tgz", + "integrity": "sha512-eSmmWE5bZTK2Nou4g0AI3zZ9rswp7GRKoKXS1BLUkvPviOqs4YTN1djQIqrXy9k5gEtdLPy86JjRwsNM9tnDcA==", + "dev": true, "requires": { "parse-passwd": "^1.0.0" } }, "hosted-git-info": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-2.5.0.tgz", - "integrity": "sha512-pNgbURSuab90KbTqvRPsseaTxOJCZBD0a7t+haSN33piP9cCM4l0CqdzAif2hUqm716UovKB2ROmiabGAKVXyg==" + "version": "2.7.1", + "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-2.7.1.tgz", + "integrity": "sha512-7T/BxH19zbcCTa8XkMlbK5lTo1WtgkFi3GvdWEyNuc4Vex7/9Dqbnpsf4JMydcfj9HCg4zUWFTL3Za6lapg5/w==" }, "http-basic": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/http-basic/-/http-basic-7.0.0.tgz", - "integrity": "sha1-gvClBr6UJzLsje6+6A50bvVzbbo=", + "version": "8.1.1", + "resolved": "https://registry.npmjs.org/http-basic/-/http-basic-8.1.1.tgz", + "integrity": "sha512-RRPtpg/R7HbDEoICA1MlLy0IH0D/1ShY9AcvY6U2zqT/8mjjJ893H/2URxx6JtFYEfL3IlKTkQQcKwTyLuubKA==", "dev": true, "requires": { - "@types/concat-stream": "^1.6.0", - "@types/node": "^9.4.1", - "caseless": "~0.12.0", - "concat-stream": "^1.4.6", + "caseless": "^0.12.0", + "concat-stream": "^1.6.2", "http-response-object": "^3.0.1", "parse-cache-control": "^1.0.1" } @@ -3777,7 +4330,8 @@ "http-cache-semantics": { "version": "3.8.1", "resolved": "https://registry.npmjs.org/http-cache-semantics/-/http-cache-semantics-3.8.1.tgz", - "integrity": "sha512-5ai2iksyV8ZXmnZhHH4rWPoxxistEexSi5936zIQ1bnNTW5VnA85B6P/VpXiRM017IgRvb2kKo1a//y+0wSp3w==" + "integrity": "sha512-5ai2iksyV8ZXmnZhHH4rWPoxxistEexSi5936zIQ1bnNTW5VnA85B6P/VpXiRM017IgRvb2kKo1a//y+0wSp3w==", + "dev": true }, "http-errors": { "version": "1.6.3", @@ -3791,12 +4345,12 @@ } }, "http-response-object": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/http-response-object/-/http-response-object-3.0.1.tgz", - "integrity": "sha512-6L0Fkd6TozA8kFSfh9Widst0wfza3U1Ex2RjJ6zNDK0vR1U1auUR6jY4Nn2Xl7CCy0ikFmxW1XcspVpb9RvwTg==", + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/http-response-object/-/http-response-object-3.0.2.tgz", + "integrity": "sha512-bqX0XTF6fnXSQcEJ2Iuyr75yVakyjIDCqroJQ/aHfSdlM743Cwqoi2nDYMzLGWUcuTWGWy8AAvOKXTfiv6q9RA==", "dev": true, "requires": { - "@types/node": "^9.3.0" + "@types/node": "^10.0.3" } }, "http-signature": { @@ -3810,9 +4364,18 @@ } }, "iconv-lite": { - "version": "0.4.19", - "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.19.tgz", - "integrity": "sha512-oTZqweIP51xaGPI4uPa56/Pri/480R+mo7SeU+YETByQNhDG55ycFyNLIgta9vXhILrxXDmF7ZGhqZIcuN0gJQ==" + "version": "0.4.23", + "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.23.tgz", + "integrity": "sha512-neyTUVFtahjf0mB3dZT77u+8O0QB89jFdnBkd5P1JgYPbPaia3gXXOVL2fq8VyU2gMMD7SaN7QukTB/pmXYvDA==", + "requires": { + "safer-buffer": ">= 2.1.2 < 3" + } + }, + "ignore": { + "version": "3.3.10", + "resolved": "https://registry.npmjs.org/ignore/-/ignore-3.3.10.tgz", + "integrity": "sha512-Pgs951kaMm5GXP7MOvxERINe3gsaVjUWFm+UZPSq9xYriQAksyhg0csnS0KXSNRD5NmNdapXEpjxG49+AKh/ug==", + "dev": true }, "ignore-by-default": { "version": "1.0.1", @@ -3826,18 +4389,27 @@ "integrity": "sha1-BWmOPUXIjo1+nZLLBYTnfwlvPkM=", "dev": true }, + "import-local": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/import-local/-/import-local-1.0.0.tgz", + "integrity": "sha512-vAaZHieK9qjGo58agRBg+bhHX3hoTZU/Oa3GESWLz7t1U62fk63aHuDJJEteXoDeTCcPmUT+z38gkHPZkkmpmQ==", + "dev": true, + "requires": { + "pkg-dir": "^2.0.0", + "resolve-cwd": "^2.0.0" + } + }, "imurmurhash": { "version": "0.1.4", "resolved": "https://registry.npmjs.org/imurmurhash/-/imurmurhash-0.1.4.tgz", - "integrity": "sha1-khi5srkoojixPcT7a21XbyMUU+o=" + "integrity": "sha1-khi5srkoojixPcT7a21XbyMUU+o=", + "dev": true }, "indent-string": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/indent-string/-/indent-string-2.1.0.tgz", - "integrity": "sha1-ji1INIdCEhtKghi3oTfppSBJ3IA=", - "requires": { - "repeating": "^2.0.0" - } + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/indent-string/-/indent-string-3.2.0.tgz", + "integrity": "sha1-Sl/W0nzDMvN+VBmlBNu4NxBckok=", + "dev": true }, "inflight": { "version": "1.0.6", @@ -3856,12 +4428,14 @@ "ini": { "version": "1.3.5", "resolved": "https://registry.npmjs.org/ini/-/ini-1.3.5.tgz", - "integrity": "sha512-RZY5huIKCMRWDUqZlEi72f/lmXKMvuszcMBduliQ3nnWbx9X/ZBQO7DijMEYS9EhHBb2qacRUMtC7svLwe0lcw==" + "integrity": "sha512-RZY5huIKCMRWDUqZlEi72f/lmXKMvuszcMBduliQ3nnWbx9X/ZBQO7DijMEYS9EhHBb2qacRUMtC7svLwe0lcw==", + "dev": true }, "inquirer": { "version": "5.2.0", "resolved": "https://registry.npmjs.org/inquirer/-/inquirer-5.2.0.tgz", "integrity": "sha512-E9BmnJbAKLPGonz0HeWHtbKf+EeSP93paWO3ZYoUpq/aowXvYGjjCSuashhXPpzbArIjBbji39THkxTz9ZeEUQ==", + "dev": true, "requires": { "ansi-escapes": "^3.0.0", "chalk": "^2.0.0", @@ -3881,17 +4455,20 @@ "ansi-regex": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", - "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=" + "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=", + "dev": true }, "is-fullwidth-code-point": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", - "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=" + "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=", + "dev": true }, "string-width": { "version": "2.1.1", "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", + "dev": true, "requires": { "is-fullwidth-code-point": "^2.0.0", "strip-ansi": "^4.0.0" @@ -3901,6 +4478,7 @@ "version": "4.0.0", "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", + "dev": true, "requires": { "ansi-regex": "^3.0.0" } @@ -3908,14 +4486,16 @@ } }, "interpret": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/interpret/-/interpret-1.1.0.tgz", - "integrity": "sha1-ftGxQQxqDg94z5XTuEQMY/eLhhQ=" + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/interpret/-/interpret-1.2.0.tgz", + "integrity": "sha512-mT34yGKMNceBQUoVn7iCDKDntA7SC6gycMAWzGx1z/CMCTV7b2AAtXlo3nRyHZ1FelRkQbQjprHSYGwzLtkVbw==", + "dev": true }, "into-stream": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/into-stream/-/into-stream-3.1.0.tgz", "integrity": "sha1-lvsKk2wSur1v8XUqF9BWFqvQlMY=", + "dev": true, "requires": { "from2": "^2.1.1", "p-is-promise": "^1.1.0" @@ -3925,6 +4505,7 @@ "version": "2.2.4", "resolved": "https://registry.npmjs.org/invariant/-/invariant-2.2.4.tgz", "integrity": "sha512-phJfQVBuaJM5raOpJjSfkiD6BpbCE4Ns//LaXl6wGYtUBY83nWS6Rf9tXm2e8VaK60JEjYldbPif/A2B1C2gNA==", + "dev": true, "requires": { "loose-envify": "^1.0.0" } @@ -3935,9 +4516,9 @@ "integrity": "sha1-EEqOSqym09jNFXqO+L+rLXo//bY=" }, "ipaddr.js": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.6.0.tgz", - "integrity": "sha1-4/o1e3c9phnybpXwSdBVxyeW+Gs=" + "version": "1.8.0", + "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.8.0.tgz", + "integrity": "sha1-6qM9bd16zo9/b+DJygRA5wZzix4=" }, "is-accessor-descriptor": { "version": "0.1.6", @@ -3976,23 +4557,21 @@ "is-buffer": { "version": "1.1.6", "resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-1.1.6.tgz", - "integrity": "sha512-NcdALwpXkTm5Zvvbk7owOUSvVvBKDgKP5/ewfXEznmQFfs4ZRmanOeKBTjRVjka3QFoN6XJ+9F3USqfHqTaU5w==" + "integrity": "sha512-NcdALwpXkTm5Zvvbk7owOUSvVvBKDgKP5/ewfXEznmQFfs4ZRmanOeKBTjRVjka3QFoN6XJ+9F3USqfHqTaU5w==", + "dev": true }, - "is-builtin-module": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-builtin-module/-/is-builtin-module-1.0.0.tgz", - "integrity": "sha1-VAVy0096wxGfj3bDDLwbHgN6/74=", - "requires": { - "builtin-modules": "^1.0.0" - } + "is-callable": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/is-callable/-/is-callable-1.1.4.tgz", + "integrity": "sha512-r5p9sxJjYnArLjObpjA4xu5EKI3CuKHkJXMhT7kwbpUyIFD1n5PMAsoPvWnvtZiNz7LjkYDRZhd7FlI0eMijEA==" }, "is-ci": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/is-ci/-/is-ci-1.1.0.tgz", - "integrity": "sha512-c7TnwxLePuqIlxHgr7xtxzycJPegNHFuIrBkwbf8hc58//+Op1CqFkyS+xnIMkwn9UsJIwc174BIjkyBmSpjKg==", + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/is-ci/-/is-ci-1.2.1.tgz", + "integrity": "sha512-s6tfsaQaQi3JNciBH6shVqEDvhGut0SUXr31ag8Pd8BBbVVlcGfWhpPmEOoM6RJ5TFhbypvf5yyRw/VXW1IiWg==", "dev": true, "requires": { - "ci-info": "^1.0.0" + "ci-info": "^1.5.0" } }, "is-data-descriptor": { @@ -4015,6 +4594,11 @@ } } }, + "is-date-object": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-date-object/-/is-date-object-1.0.1.tgz", + "integrity": "sha1-mqIOtq7rv/d/vTPnTKAbM1gdOhY=" + }, "is-descriptor": { "version": "0.1.6", "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-0.1.6.tgz", @@ -4037,12 +4621,14 @@ "is-dotfile": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/is-dotfile/-/is-dotfile-1.0.3.tgz", - "integrity": "sha1-pqLzL/0t+wT1yiXs0Pa4PPeYoeE=" + "integrity": "sha1-pqLzL/0t+wT1yiXs0Pa4PPeYoeE=", + "dev": true }, "is-equal-shallow": { "version": "0.1.3", "resolved": "https://registry.npmjs.org/is-equal-shallow/-/is-equal-shallow-0.1.3.tgz", "integrity": "sha1-IjgJj8Ih3gvPpdnqxMRdY4qhxTQ=", + "dev": true, "requires": { "is-primitive": "^2.0.0" } @@ -4050,7 +4636,8 @@ "is-extendable": { "version": "0.1.1", "resolved": "https://registry.npmjs.org/is-extendable/-/is-extendable-0.1.1.tgz", - "integrity": "sha1-YrEQ4omkcUGOPsNqYX1HLjAd/Ik=" + "integrity": "sha1-YrEQ4omkcUGOPsNqYX1HLjAd/Ik=", + "dev": true }, "is-extglob": { "version": "2.1.1", @@ -4062,6 +4649,7 @@ "version": "1.0.2", "resolved": "https://registry.npmjs.org/is-finite/-/is-finite-1.0.2.tgz", "integrity": "sha1-zGZ3aVYCvlUO8R6LSqYwU0K20Ko=", + "dev": true, "requires": { "number-is-nan": "^1.0.0" } @@ -4080,9 +4668,9 @@ "integrity": "sha1-Es+5i2W1fdPRk6MSH19uL0N2ArU=" }, "is-glob": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.0.tgz", - "integrity": "sha1-lSHHaEXMJhCoUgPd8ICpWML/q8A=", + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.1.tgz", + "integrity": "sha512-5G0tKtBTFImOqDnLB2hG6Bp2qcKEFduo4tZu9MT/H6NQv/ghhy30o55ufafxJ/LdH79LLs2Kfrn85TLKyA7BUg==", "dev": true, "requires": { "is-extglob": "^2.1.1" @@ -4113,6 +4701,7 @@ "version": "3.0.0", "resolved": "https://registry.npmjs.org/is-number/-/is-number-3.0.0.tgz", "integrity": "sha1-JP1iAaR4LPUFYcgQJ2r8fRLXEZU=", + "dev": true, "requires": { "kind-of": "^3.0.2" }, @@ -4121,6 +4710,7 @@ "version": "3.2.2", "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, "requires": { "is-buffer": "^1.1.5" } @@ -4136,36 +4726,22 @@ "is-object": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/is-object/-/is-object-1.0.1.tgz", - "integrity": "sha1-iVJojF7C/9awPsyF52ngKQMINHA=" + "integrity": "sha1-iVJojF7C/9awPsyF52ngKQMINHA=", + "dev": true }, "is-observable": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/is-observable/-/is-observable-0.2.0.tgz", - "integrity": "sha1-s2ExHYPG5dcmyr9eJQsCNxBvWuI=", - "requires": { - "symbol-observable": "^0.2.2" - }, - "dependencies": { - "symbol-observable": { - "version": "0.2.4", - "resolved": "https://registry.npmjs.org/symbol-observable/-/symbol-observable-0.2.4.tgz", - "integrity": "sha1-lag9smGG1q9+ehjb2XYKL4bQj0A=" - } - } - }, - "is-odd": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-odd/-/is-odd-2.0.0.tgz", - "integrity": "sha512-OTiixgpZAT1M4NHgS5IguFp/Vz2VI3U7Goh4/HA1adtwyLtSBrxYlcSYkhpAE07s4fKEcjrFxyvtQBND4vFQyQ==", + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/is-observable/-/is-observable-1.1.0.tgz", + "integrity": "sha512-NqCa4Sa2d+u7BWc6CukaObG3Fh+CU9bvixbpcXYhy2VvYS7vVGIdAgnIS5Ks3A/cqk4rebLJ9s8zBstT2aKnIA==", "dev": true, "requires": { - "is-number": "^4.0.0" + "symbol-observable": "^1.1.0" }, "dependencies": { - "is-number": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/is-number/-/is-number-4.0.0.tgz", - "integrity": "sha512-rSklcAIlf1OmFdyAqbnWTLVelsQ58uvZ66S/ZyawjWqIviTWCjg2PzVGw8WUA+nNuPTqb4wgA+NszrJ+08LlgQ==", + "symbol-observable": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/symbol-observable/-/symbol-observable-1.2.0.tgz", + "integrity": "sha512-e900nM8RRtGhlV36KGEU9k65K3mPb1WV70OdjfxlG2EAuM1noi/E/BaW/uMhL7bPEssK8QV57vN3esixjUvcXQ==", "dev": true } } @@ -4182,7 +4758,8 @@ "is-plain-obj": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-1.1.0.tgz", - "integrity": "sha1-caUMhCnfync8kqOQpKA7OfzVHT4=" + "integrity": "sha1-caUMhCnfync8kqOQpKA7OfzVHT4=", + "dev": true }, "is-plain-object": { "version": "2.0.4", @@ -4196,17 +4773,20 @@ "is-posix-bracket": { "version": "0.1.1", "resolved": "https://registry.npmjs.org/is-posix-bracket/-/is-posix-bracket-0.1.1.tgz", - "integrity": "sha1-MzTceXdDaOkvAW5vvAqI9c1ua8Q=" + "integrity": "sha1-MzTceXdDaOkvAW5vvAqI9c1ua8Q=", + "dev": true }, "is-primitive": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/is-primitive/-/is-primitive-2.0.0.tgz", - "integrity": "sha1-IHurkWOEmcB7Kt8kCkGochADRXU=" + "integrity": "sha1-IHurkWOEmcB7Kt8kCkGochADRXU=", + "dev": true }, "is-promise": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/is-promise/-/is-promise-2.1.0.tgz", - "integrity": "sha1-eaKp7OfwlugPNtKy87wWwf9L8/o=" + "integrity": "sha1-eaKp7OfwlugPNtKy87wWwf9L8/o=", + "dev": true }, "is-redirect": { "version": "1.0.0", @@ -4214,15 +4794,25 @@ "integrity": "sha1-HQPd7VO9jbDzDCbk+V02/HyH3CQ=", "dev": true }, + "is-regex": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-regex/-/is-regex-1.0.4.tgz", + "integrity": "sha1-VRdIm1RwkbCTDglWVM7SXul+lJE=", + "requires": { + "has": "^1.0.1" + } + }, "is-retry-allowed": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/is-retry-allowed/-/is-retry-allowed-1.1.0.tgz", - "integrity": "sha1-EaBgVotnM5REAz0BJaYaINVk+zQ=" + "integrity": "sha1-EaBgVotnM5REAz0BJaYaINVk+zQ=", + "dev": true }, "is-scoped": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/is-scoped/-/is-scoped-1.0.0.tgz", "integrity": "sha1-RJypgpnnEwOCViieyytUDcQ3yzA=", + "dev": true, "requires": { "scoped-regex": "^1.0.0" } @@ -4230,7 +4820,16 @@ "is-stream": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-1.1.0.tgz", - "integrity": "sha1-EtSj3U5o4Lec6428hBc66A2RykQ=" + "integrity": "sha1-EtSj3U5o4Lec6428hBc66A2RykQ=", + "dev": true + }, + "is-symbol": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-symbol/-/is-symbol-1.0.2.tgz", + "integrity": "sha512-HS8bZ9ox60yCJLH9snBpIwv9pYUAkcuLhSA1oero1UB5y9aiQpRA8y2ex945AOtCZL1lJDeIk3G5LthswI46Lw==", + "requires": { + "has-symbols": "^1.0.0" + } }, "is-typedarray": { "version": "1.0.0", @@ -4245,17 +4844,29 @@ "is-windows": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/is-windows/-/is-windows-1.0.2.tgz", - "integrity": "sha512-eXK1UInq2bPmjyX6e3VHIzMLobc4J94i4AWn+Hpq3OU5KkrRC96OAcR3PRJ/pGu6m8TRnBHP9dkXQVsT/COVIA==" + "integrity": "sha512-eXK1UInq2bPmjyX6e3VHIzMLobc4J94i4AWn+Hpq3OU5KkrRC96OAcR3PRJ/pGu6m8TRnBHP9dkXQVsT/COVIA==", + "dev": true }, "isarray": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=" + "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", + "dev": true + }, + "isbinaryfile": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/isbinaryfile/-/isbinaryfile-3.0.3.tgz", + "integrity": "sha512-8cJBL5tTd2OS0dM4jz07wQd5g0dCCqIhUxPIGtZfa5L6hWlvV5MHTITy/DBAsF+Oe2LS1X3krBUhNwaGUWpWxw==", + "dev": true, + "requires": { + "buffer-alloc": "^1.2.0" + } }, "isexe": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", - "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=" + "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=", + "dev": true }, "isobject": { "version": "3.0.1", @@ -4296,12 +4907,6 @@ "integrity": "sha1-kbR5JYinc4wl813W9jdSovh3YTU=", "dev": true }, - "async": { - "version": "1.5.2", - "resolved": "https://registry.npmjs.org/async/-/async-1.5.2.tgz", - "integrity": "sha1-7GphrlZIDAw8skHJVhjiCJL5Zyo=", - "dev": true - }, "esprima": { "version": "2.7.3", "resolved": "https://registry.npmjs.org/esprima/-/esprima-2.7.3.tgz", @@ -4321,6 +4926,12 @@ "path-is-absolute": "^1.0.0" } }, + "has-flag": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-1.0.0.tgz", + "integrity": "sha1-nZ55MWXOAXoA8AQYxD+UKnsdEfo=", + "dev": true + }, "nopt": { "version": "3.0.6", "resolved": "https://registry.npmjs.org/nopt/-/nopt-3.0.6.tgz", @@ -4335,23 +4946,34 @@ "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.1.7.tgz", "integrity": "sha1-IDEU2CrSxe2ejgQRs5ModeiJ6Xs=", "dev": true + }, + "supports-color": { + "version": "3.2.3", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-3.2.3.tgz", + "integrity": "sha1-ZawFBLOVQXHYpklGsq48u4pfVPY=", + "dev": true, + "requires": { + "has-flag": "^1.0.0" + } } } }, "istextorbinary": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/istextorbinary/-/istextorbinary-2.2.1.tgz", - "integrity": "sha512-TS+hoFl8Z5FAFMK38nhBkdLt44CclNRgDHWeMgsV8ko3nDlr/9UI2Sf839sW7enijf8oKsZYXRvM8g0it9Zmcw==", + "version": "2.5.1", + "resolved": "https://registry.npmjs.org/istextorbinary/-/istextorbinary-2.5.1.tgz", + "integrity": "sha512-pv/JNPWnfpwGjPx7JrtWTwsWsxkrK3fNzcEVnt92YKEIErps4Fsk49+qzCe9iQF2hjqK8Naqf8P9kzoeCuQI1g==", + "dev": true, "requires": { - "binaryextensions": "2", - "editions": "^1.3.3", - "textextensions": "2" + "binaryextensions": "^2.1.2", + "editions": "^2.1.3", + "textextensions": "^2.4.0" } }, "isurl": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/isurl/-/isurl-1.0.0.tgz", "integrity": "sha512-1P/yWsxPlDtn7QeRD+ULKQPaIaN6yF368GZ2vDfv0AL0NwpStafjWCDDdn0k8wgFMWpVAqG7oJhxHnlud42i9w==", + "dev": true, "requires": { "has-to-string-tag-x": "^1.2.0", "is-object": "^1.0.1" @@ -4382,20 +5004,20 @@ } }, "js-sha3": { - "version": "0.5.5", - "resolved": "https://registry.npmjs.org/js-sha3/-/js-sha3-0.5.5.tgz", - "integrity": "sha1-uvDA6MVK1ZA0R9+Wreekobynmko=", - "dev": true + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/js-sha3/-/js-sha3-0.6.1.tgz", + "integrity": "sha1-W4n3enR3Z5h39YxKB1JAk0sflcA=" }, "js-tokens": { "version": "3.0.2", "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-3.0.2.tgz", - "integrity": "sha1-mGbfOVECEw449/mWvOtlRDIJwls=" + "integrity": "sha1-mGbfOVECEw449/mWvOtlRDIJwls=", + "dev": true }, "js-yaml": { - "version": "3.11.0", - "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.11.0.tgz", - "integrity": "sha512-saJstZWv7oNeOyBh3+Dx1qWzhW0+e6/8eDzo7p5rDFqxntSztloLtuKu+Ejhtq82jsilwOIZYsCz+lIjthg1Hw==", + "version": "3.13.0", + "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.13.0.tgz", + "integrity": "sha512-pZZoSxcCYco+DIKBTimr67J6Hy+EYGZDY/HCWC+iAEA9h1ByhMXAIVUXMcMFpOCxQ/xjXmPI2MkDL5HRm5eFrQ==", "dev": true, "requires": { "argparse": "^1.0.7", @@ -4405,19 +5027,19 @@ "jsbn": { "version": "0.1.1", "resolved": "https://registry.npmjs.org/jsbn/-/jsbn-0.1.1.tgz", - "integrity": "sha1-peZUwuWi3rXyAdls77yoDA7y9RM=", - "optional": true + "integrity": "sha1-peZUwuWi3rXyAdls77yoDA7y9RM=" }, "jscodeshift": { - "version": "0.5.0", - "resolved": "https://registry.npmjs.org/jscodeshift/-/jscodeshift-0.5.0.tgz", - "integrity": "sha512-JAcQINNMFpdzzpKJN8k5xXjF3XDuckB1/48uScSzcnNyK199iWEc9AxKL9OoX5144M2w5zEx9Qs4/E/eBZZUlw==", + "version": "0.5.1", + "resolved": "https://registry.npmjs.org/jscodeshift/-/jscodeshift-0.5.1.tgz", + "integrity": "sha512-sRMollbhbmSDrR79JMAnhEjyZJlQQVozeeY9A6/KNuV26DNcuB3mGSCWXp0hks9dcwRNOELbNOiwraZaXXRk5Q==", + "dev": true, "requires": { "babel-plugin-transform-flow-strip-types": "^6.8.0", "babel-preset-es2015": "^6.9.0", "babel-preset-stage-1": "^6.5.0", "babel-register": "^6.9.0", - "babylon": "^7.0.0-beta.30", + "babylon": "^7.0.0-beta.47", "colors": "^1.1.2", "flow-parser": "^0.*", "lodash": "^4.13.1", @@ -4425,7 +5047,7 @@ "neo-async": "^2.5.0", "node-dir": "0.1.8", "nomnom": "^1.8.1", - "recast": "^0.14.1", + "recast": "^0.15.0", "temp": "^0.8.1", "write-file-atomic": "^1.2.0" }, @@ -4434,6 +5056,7 @@ "version": "2.0.0", "resolved": "https://registry.npmjs.org/arr-diff/-/arr-diff-2.0.0.tgz", "integrity": "sha1-jzuCf5Vai9ZpaX5KQlasPOrjVs8=", + "dev": true, "requires": { "arr-flatten": "^1.0.1" } @@ -4441,12 +5064,14 @@ "array-unique": { "version": "0.2.1", "resolved": "https://registry.npmjs.org/array-unique/-/array-unique-0.2.1.tgz", - "integrity": "sha1-odl8yvy8JiXMcPrc6zalDFiwGlM=" + "integrity": "sha1-odl8yvy8JiXMcPrc6zalDFiwGlM=", + "dev": true }, "braces": { "version": "1.8.5", "resolved": "https://registry.npmjs.org/braces/-/braces-1.8.5.tgz", "integrity": "sha1-uneWLhLf+WnWt2cR6RS3N4V79qc=", + "dev": true, "requires": { "expand-range": "^1.8.1", "preserve": "^0.2.0", @@ -4457,6 +5082,7 @@ "version": "0.1.5", "resolved": "https://registry.npmjs.org/expand-brackets/-/expand-brackets-0.1.5.tgz", "integrity": "sha1-3wcoTjQqgHzXM6xa9yQR5YHRF3s=", + "dev": true, "requires": { "is-posix-bracket": "^0.1.0" } @@ -4465,6 +5091,7 @@ "version": "0.3.2", "resolved": "https://registry.npmjs.org/extglob/-/extglob-0.3.2.tgz", "integrity": "sha1-Lhj/PS9JqydlzskCPwEdqo2DSaE=", + "dev": true, "requires": { "is-extglob": "^1.0.0" } @@ -4472,12 +5099,14 @@ "is-extglob": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-1.0.0.tgz", - "integrity": "sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA=" + "integrity": "sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA=", + "dev": true }, "is-glob": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-2.0.1.tgz", "integrity": "sha1-0Jb5JqPe1WAPP9/ZEZjLCIjC2GM=", + "dev": true, "requires": { "is-extglob": "^1.0.0" } @@ -4486,6 +5115,7 @@ "version": "3.2.2", "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, "requires": { "is-buffer": "^1.1.5" } @@ -4494,6 +5124,7 @@ "version": "2.3.11", "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-2.3.11.tgz", "integrity": "sha1-hmd8l9FyCzY0MdBNDRUpO9OMFWU=", + "dev": true, "requires": { "arr-diff": "^2.0.0", "array-unique": "^0.2.1", @@ -4510,10 +5141,20 @@ "regex-cache": "^0.4.2" } }, + "normalize-path": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-2.1.1.tgz", + "integrity": "sha1-GrKLVW4Zg2Oowab35vogE3/mrtk=", + "dev": true, + "requires": { + "remove-trailing-separator": "^1.0.1" + } + }, "write-file-atomic": { "version": "1.3.4", "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-1.3.4.tgz", "integrity": "sha1-+Aek8LHZ6ROuekgRLmzDrxmRtF8=", + "dev": true, "requires": { "graceful-fs": "^4.1.11", "imurmurhash": "^0.1.4", @@ -4525,17 +5166,20 @@ "jsesc": { "version": "0.5.0", "resolved": "https://registry.npmjs.org/jsesc/-/jsesc-0.5.0.tgz", - "integrity": "sha1-597mbjXW/Bb3EP6R1c9p9w8IkR0=" + "integrity": "sha1-597mbjXW/Bb3EP6R1c9p9w8IkR0=", + "dev": true }, "json-buffer": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/json-buffer/-/json-buffer-3.0.0.tgz", - "integrity": "sha1-Wx85evx11ne96Lz8Dkfh+aPZqJg=" + "integrity": "sha1-Wx85evx11ne96Lz8Dkfh+aPZqJg=", + "dev": true }, "json-parse-better-errors": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/json-parse-better-errors/-/json-parse-better-errors-1.0.1.tgz", - "integrity": "sha512-xyQpxeWWMKyJps9CuGJYeng6ssI5bpqS9ltQpdVQ90t4ql6NdnxFKh95JcRt2cun/DjMVNrdjniLPuMA69xmCw==" + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/json-parse-better-errors/-/json-parse-better-errors-1.0.2.tgz", + "integrity": "sha512-mrqyZKfX5EhL7hvqcV6WG1yYjnjeuYDzDhhcAAUrq8Po85NBQBJP+ZDUT75qZQ98IkUoBqdkExkukOU7Ts2wrw==", + "dev": true }, "json-schema": { "version": "0.2.3", @@ -4543,9 +5187,9 @@ "integrity": "sha1-tIDIkuWaLwWVTOcnvT8qTogvnhM=" }, "json-schema-traverse": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.3.1.tgz", - "integrity": "sha1-NJptRMU6Ud6JtAgFxdXlm0F9M0A=" + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", + "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==" }, "json-stringify-safe": { "version": "5.0.1", @@ -4555,7 +5199,8 @@ "json5": { "version": "0.5.1", "resolved": "https://registry.npmjs.org/json5/-/json5-0.5.1.tgz", - "integrity": "sha1-Hq3nrMASA0rYTiOWdn6tn6VJWCE=" + "integrity": "sha1-Hq3nrMASA0rYTiOWdn6tn6VJWCE=", + "dev": true }, "jsonfile": { "version": "2.4.0", @@ -4577,18 +5222,19 @@ } }, "keccakjs": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/keccakjs/-/keccakjs-0.2.1.tgz", - "integrity": "sha1-HWM6+QfvMFu/ny+mFtVsRFYd+k0=", + "version": "0.2.3", + "resolved": "https://registry.npmjs.org/keccakjs/-/keccakjs-0.2.3.tgz", + "integrity": "sha512-BjLkNDcfaZ6l8HBG9tH0tpmDv3sS2mA7FNQxFHpCdzP3Gb2MVruXBSuoM66SnVxKJpAr5dKGdkHD+bDokt8fTg==", "requires": { - "browserify-sha3": "^0.0.1", - "sha3": "^1.1.0" + "browserify-sha3": "^0.0.4", + "sha3": "^1.2.2" } }, "keyv": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/keyv/-/keyv-3.0.0.tgz", "integrity": "sha512-eguHnq22OE3uVoSYG0LVWNP+4ppamWr9+zWBe1bsNcovIMy6huUJFPgy4mGwCd/rnl3vOLGW1MTlu4c57CT1xA==", + "dev": true, "requires": { "json-buffer": "3.0.0" } @@ -4616,13 +5262,6 @@ "package-json": "^4.0.0" } }, - "lazy-cache": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/lazy-cache/-/lazy-cache-1.0.4.tgz", - "integrity": "sha1-odePw6UEdMuAhF07O24dpJpEbo4=", - "dev": true, - "optional": true - }, "lcid": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/lcid/-/lcid-1.0.0.tgz", @@ -4642,79 +5281,44 @@ } }, "listr": { - "version": "0.13.0", - "resolved": "https://registry.npmjs.org/listr/-/listr-0.13.0.tgz", - "integrity": "sha1-ILsLowuuZg7oTMBQPfS+PVYjiH0=", + "version": "0.14.3", + "resolved": "https://registry.npmjs.org/listr/-/listr-0.14.3.tgz", + "integrity": "sha512-RmAl7su35BFd/xoMamRjpIE4j3v+L28o8CT5YhAXQJm1fD+1l9ngXY8JAQRJ+tFK2i5njvi0iRUKV09vPwA0iA==", + "dev": true, "requires": { - "chalk": "^1.1.3", - "cli-truncate": "^0.2.1", - "figures": "^1.7.0", - "indent-string": "^2.1.0", - "is-observable": "^0.2.0", + "@samverschueren/stream-to-observable": "^0.3.0", + "is-observable": "^1.1.0", "is-promise": "^2.1.0", "is-stream": "^1.1.0", "listr-silent-renderer": "^1.1.1", - "listr-update-renderer": "^0.4.0", - "listr-verbose-renderer": "^0.4.0", - "log-symbols": "^1.0.2", - "log-update": "^1.0.2", - "ora": "^0.2.3", - "p-map": "^1.1.1", - "rxjs": "^5.4.2", - "stream-to-observable": "^0.2.0", - "strip-ansi": "^3.0.1" + "listr-update-renderer": "^0.5.0", + "listr-verbose-renderer": "^0.5.0", + "p-map": "^2.0.0", + "rxjs": "^6.3.3" }, "dependencies": { - "ansi-styles": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-2.2.1.tgz", - "integrity": "sha1-tDLdM1i2NM914eRmQ2gkBTPB3b4=" - }, - "chalk": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz", - "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=", - "requires": { - "ansi-styles": "^2.2.1", - "escape-string-regexp": "^1.0.2", - "has-ansi": "^2.0.0", - "strip-ansi": "^3.0.0", - "supports-color": "^2.0.0" - } - }, - "figures": { - "version": "1.7.0", - "resolved": "https://registry.npmjs.org/figures/-/figures-1.7.0.tgz", - "integrity": "sha1-y+Hjr/zxzUS4DK3+0o3Hk6lwHS4=", - "requires": { - "escape-string-regexp": "^1.0.5", - "object-assign": "^4.1.0" - } - }, - "log-symbols": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/log-symbols/-/log-symbols-1.0.2.tgz", - "integrity": "sha1-N2/3tY6jCGoPCfrMdGF+ylAeGhg=", + "rxjs": { + "version": "6.4.0", + "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-6.4.0.tgz", + "integrity": "sha512-Z9Yfa11F6B9Sg/BK9MnqnQ+aQYicPLtilXBp2yUtDt2JRCE0h26d33EnfO3ZxoNxG0T92OUucP3Ct7cpfkdFfw==", + "dev": true, "requires": { - "chalk": "^1.0.0" + "tslib": "^1.9.0" } - }, - "supports-color": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz", - "integrity": "sha1-U10EXOa2Nj+kARcIRimZXp3zJMc=" } } }, "listr-silent-renderer": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/listr-silent-renderer/-/listr-silent-renderer-1.1.1.tgz", - "integrity": "sha1-kktaN1cVN3C/Go4/v3S4u/P5JC4=" + "integrity": "sha1-kktaN1cVN3C/Go4/v3S4u/P5JC4=", + "dev": true }, "listr-update-renderer": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/listr-update-renderer/-/listr-update-renderer-0.4.0.tgz", - "integrity": "sha1-NE2YDaLKLosUW6MFkI8yrj9MyKc=", + "version": "0.5.0", + "resolved": "https://registry.npmjs.org/listr-update-renderer/-/listr-update-renderer-0.5.0.tgz", + "integrity": "sha512-tKRsZpKz8GSGqoI/+caPmfrypiaq+OQCbd+CovEC24uk1h952lVj5sC7SqyFUm+OaJ5HN/a1YLt5cit2FMNsFA==", + "dev": true, "requires": { "chalk": "^1.1.3", "cli-truncate": "^0.2.1", @@ -4722,19 +5326,21 @@ "figures": "^1.7.0", "indent-string": "^3.0.0", "log-symbols": "^1.0.2", - "log-update": "^1.0.2", + "log-update": "^2.3.0", "strip-ansi": "^3.0.1" }, "dependencies": { "ansi-styles": { "version": "2.2.1", "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-2.2.1.tgz", - "integrity": "sha1-tDLdM1i2NM914eRmQ2gkBTPB3b4=" + "integrity": "sha1-tDLdM1i2NM914eRmQ2gkBTPB3b4=", + "dev": true }, "chalk": { "version": "1.1.3", "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz", "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=", + "dev": true, "requires": { "ansi-styles": "^2.2.1", "escape-string-regexp": "^1.0.2", @@ -4747,20 +5353,17 @@ "version": "1.7.0", "resolved": "https://registry.npmjs.org/figures/-/figures-1.7.0.tgz", "integrity": "sha1-y+Hjr/zxzUS4DK3+0o3Hk6lwHS4=", + "dev": true, "requires": { "escape-string-regexp": "^1.0.5", "object-assign": "^4.1.0" } }, - "indent-string": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/indent-string/-/indent-string-3.2.0.tgz", - "integrity": "sha1-Sl/W0nzDMvN+VBmlBNu4NxBckok=" - }, "log-symbols": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/log-symbols/-/log-symbols-1.0.2.tgz", "integrity": "sha1-N2/3tY6jCGoPCfrMdGF+ylAeGhg=", + "dev": true, "requires": { "chalk": "^1.0.0" } @@ -4768,74 +5371,21 @@ "supports-color": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz", - "integrity": "sha1-U10EXOa2Nj+kARcIRimZXp3zJMc=" + "integrity": "sha1-U10EXOa2Nj+kARcIRimZXp3zJMc=", + "dev": true } } }, "listr-verbose-renderer": { - "version": "0.4.1", - "resolved": "https://registry.npmjs.org/listr-verbose-renderer/-/listr-verbose-renderer-0.4.1.tgz", - "integrity": "sha1-ggb0z21S3cWCfl/RSYng6WWTOjU=", + "version": "0.5.0", + "resolved": "https://registry.npmjs.org/listr-verbose-renderer/-/listr-verbose-renderer-0.5.0.tgz", + "integrity": "sha512-04PDPqSlsqIOaaaGZ+41vq5FejI9auqTInicFRndCBgE3bXG8D6W1I+mWhk+1nqbHmyhla/6BUrd5OSiHwKRXw==", + "dev": true, "requires": { - "chalk": "^1.1.3", - "cli-cursor": "^1.0.2", + "chalk": "^2.4.1", + "cli-cursor": "^2.1.0", "date-fns": "^1.27.2", - "figures": "^1.7.0" - }, - "dependencies": { - "ansi-styles": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-2.2.1.tgz", - "integrity": "sha1-tDLdM1i2NM914eRmQ2gkBTPB3b4=" - }, - "chalk": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz", - "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=", - "requires": { - "ansi-styles": "^2.2.1", - "escape-string-regexp": "^1.0.2", - "has-ansi": "^2.0.0", - "strip-ansi": "^3.0.0", - "supports-color": "^2.0.0" - } - }, - "cli-cursor": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-1.0.2.tgz", - "integrity": "sha1-ZNo/fValRBLll5S9Ytw1KV6PKYc=", - "requires": { - "restore-cursor": "^1.0.1" - } - }, - "figures": { - "version": "1.7.0", - "resolved": "https://registry.npmjs.org/figures/-/figures-1.7.0.tgz", - "integrity": "sha1-y+Hjr/zxzUS4DK3+0o3Hk6lwHS4=", - "requires": { - "escape-string-regexp": "^1.0.5", - "object-assign": "^4.1.0" - } - }, - "onetime": { - "version": "1.1.0", - "resolved": "http://registry.npmjs.org/onetime/-/onetime-1.1.0.tgz", - "integrity": "sha1-ofeDj4MUxRbwXs78vEzP4EtO14k=" - }, - "restore-cursor": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-1.0.1.tgz", - "integrity": "sha1-NGYfRohjJ/7SmRR5FSJS35LapUE=", - "requires": { - "exit-hook": "^1.0.0", - "onetime": "^1.0.0" - } - }, - "supports-color": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz", - "integrity": "sha1-U10EXOa2Nj+kARcIRimZXp3zJMc=" - } + "figures": "^2.0.0" } }, "load-json-file": { @@ -4851,19 +5401,38 @@ } }, "loader-utils": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/loader-utils/-/loader-utils-1.1.0.tgz", - "integrity": "sha1-yYrvSIvM7aL/teLeZG1qdUQp9c0=", + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/loader-utils/-/loader-utils-1.2.3.tgz", + "integrity": "sha512-fkpz8ejdnEMG3s37wGL07iSBDg99O9D5yflE9RGNH3hRdx9SOwYfnGYdZOUIZitN8E+E2vkq3MUMYMvPYl5ZZA==", + "dev": true, "requires": { - "big.js": "^3.1.3", + "big.js": "^5.2.2", "emojis-list": "^2.0.0", - "json5": "^0.5.0" + "json5": "^1.0.1" + }, + "dependencies": { + "json5": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/json5/-/json5-1.0.1.tgz", + "integrity": "sha512-aKS4WQjPenRxiQsC93MNfjx+nbF4PAdYzmd/1JIj8HYzqfbu86beTuNgXDzPknWk0n0uARlyewZo4s++ES36Ow==", + "dev": true, + "requires": { + "minimist": "^1.2.0" + } + }, + "minimist": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz", + "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=", + "dev": true + } } }, "locate-path": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-2.0.0.tgz", "integrity": "sha1-K1aLJl7slExtnA3pw9u7ygNUzY4=", + "dev": true, "requires": { "p-locate": "^2.0.0", "path-exists": "^3.0.0" @@ -4872,14 +5441,16 @@ "path-exists": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", - "integrity": "sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=" + "integrity": "sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=", + "dev": true } } }, "lodash": { - "version": "4.17.5", - "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.5.tgz", - "integrity": "sha512-svL3uiZf1RwhH+cWrfZn3A4+U58wbP0tGVTLQPbjplZxZ8ROD9VLuNgsRniTlLe7OlSqR79RUehXgpBW/s0IQw==" + "version": "4.17.11", + "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.11.tgz", + "integrity": "sha512-cQKh8igo5QUhZ7lg38DYWAxMvjSAKG0A8wGSVimP07SIUEK2UO+arSRKbRZWtelMtN5V0Hkwh5ryOto/SshYIg==", + "dev": true }, "lodash.assign": { "version": "4.2.0", @@ -4890,77 +5461,95 @@ "version": "2.2.0", "resolved": "https://registry.npmjs.org/log-symbols/-/log-symbols-2.2.0.tgz", "integrity": "sha512-VeIAFslyIerEJLXHziedo2basKbMKtTw3vfn5IzG0XTjhAVEJyNHnL2p7vc+wBDSdQuUpNw3M2u6xb9QsAY5Eg==", + "dev": true, "requires": { "chalk": "^2.0.1" } }, "log-update": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/log-update/-/log-update-1.0.2.tgz", - "integrity": "sha1-GZKfZMQJPS0ucHWh2tivWcKWuNE=", + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/log-update/-/log-update-2.3.0.tgz", + "integrity": "sha1-iDKP19HOeTiykoN0bwsbwSayRwg=", + "dev": true, "requires": { - "ansi-escapes": "^1.0.0", - "cli-cursor": "^1.0.2" + "ansi-escapes": "^3.0.0", + "cli-cursor": "^2.0.0", + "wrap-ansi": "^3.0.1" }, "dependencies": { - "ansi-escapes": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-1.4.0.tgz", - "integrity": "sha1-06ioOzGapneTZisT52HHkRQiMG4=" + "ansi-regex": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", + "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=", + "dev": true }, - "cli-cursor": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-1.0.2.tgz", - "integrity": "sha1-ZNo/fValRBLll5S9Ytw1KV6PKYc=", + "is-fullwidth-code-point": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", + "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=", + "dev": true + }, + "string-width": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", + "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", + "dev": true, "requires": { - "restore-cursor": "^1.0.1" + "is-fullwidth-code-point": "^2.0.0", + "strip-ansi": "^4.0.0" } }, - "onetime": { - "version": "1.1.0", - "resolved": "http://registry.npmjs.org/onetime/-/onetime-1.1.0.tgz", - "integrity": "sha1-ofeDj4MUxRbwXs78vEzP4EtO14k=" + "strip-ansi": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", + "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", + "dev": true, + "requires": { + "ansi-regex": "^3.0.0" + } }, - "restore-cursor": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-1.0.1.tgz", - "integrity": "sha1-NGYfRohjJ/7SmRR5FSJS35LapUE=", + "wrap-ansi": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-3.0.1.tgz", + "integrity": "sha1-KIoE2H7aXChuBg3+jxNc6NAH+Lo=", + "dev": true, "requires": { - "exit-hook": "^1.0.0", - "onetime": "^1.0.0" + "string-width": "^2.1.1", + "strip-ansi": "^4.0.0" } } } }, - "longest": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/longest/-/longest-1.0.1.tgz", - "integrity": "sha1-MKCy2jj3N3DoKUoNIuZiXtd9AJc=", - "dev": true - }, "loose-envify": { - "version": "1.3.1", - "resolved": "https://registry.npmjs.org/loose-envify/-/loose-envify-1.3.1.tgz", - "integrity": "sha1-0aitM/qc4OcT1l/dCsi3SNR4yEg=", + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/loose-envify/-/loose-envify-1.4.0.tgz", + "integrity": "sha512-lyuxPGr/Wfhrlem2CL/UcnUc1zcqKAImBDzukY7Y5F/yQiNdko6+fRLevlw1HgMySw7f611UIY408EtxRSoK3Q==", + "dev": true, "requires": { - "js-tokens": "^3.0.0" + "js-tokens": "^3.0.0 || ^4.0.0" } }, "lowercase-keys": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/lowercase-keys/-/lowercase-keys-1.0.0.tgz", - "integrity": "sha1-TjNms55/VFfjXxMkvfb4jQv8cwY=" + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/lowercase-keys/-/lowercase-keys-1.0.1.tgz", + "integrity": "sha512-G2Lj61tXDnVFFOi8VZds+SoQjtQC3dgokKdDG2mTm1tx4m50NUHBOZSBwQQHyy0V12A0JTG4icfZQH+xPyh8VA==", + "dev": true }, "lru-cache": { - "version": "2.7.3", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-2.7.3.tgz", - "integrity": "sha1-bUUk6LlV+V1PW1iFHOId1y+06VI=", - "dev": true + "version": "4.1.5", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-4.1.5.tgz", + "integrity": "sha512-sWZlbEP2OsHNkXrMl5GYk/jKk70MBng6UU4YI/qGDYbgf6YbP4EvmqISbXCoJiRKs+1bSpFHVgQxvJ17F2li5g==", + "dev": true, + "requires": { + "pseudomap": "^1.0.2", + "yallist": "^2.1.2" + } }, "make-dir": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-1.2.0.tgz", - "integrity": "sha512-aNUAa4UMg/UougV25bbrU4ZaaKNjJ/3/xnvg/twpmKROPdKZPZ9wGgI0opdZzO8q/zUFawoUuixuOv33eZ61Iw==", + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/make-dir/-/make-dir-1.3.0.tgz", + "integrity": "sha512-2w31R7SJtieJJnQtGc7RVL2StM2vGYVfqUOvUDxH6bC6aJTxPxTF0GnIgCyu7tjockiUWAYQRbxa7vKn34s5sQ==", + "dev": true, "requires": { "pify": "^3.0.0" }, @@ -4968,7 +5557,8 @@ "pify": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", - "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=" + "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=", + "dev": true } } }, @@ -4978,12 +5568,6 @@ "integrity": "sha1-wyq9C9ZSXZsFFkW7TyasXcmKDb8=", "dev": true }, - "map-stream": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/map-stream/-/map-stream-0.1.0.tgz", - "integrity": "sha1-5WqpTEyAVaFkBKBnS3jyFffI4ZQ=", - "dev": true - }, "map-visit": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/map-visit/-/map-visit-1.0.0.tgz", @@ -4993,6 +5577,12 @@ "object-visit": "^1.0.0" } }, + "math-random": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/math-random/-/math-random-1.0.4.tgz", + "integrity": "sha512-rUxjysqif/BZQH2yhd5Aaq7vXMSx9NdEsQcyA07uEzIvxgI7zIr33gGsh+RU0/XjmQpCW7RsVof1vlkvQVCK5A==", + "dev": true + }, "media-typer": { "version": "0.3.0", "resolved": "https://registry.npmjs.org/media-typer/-/media-typer-0.3.0.tgz", @@ -5002,6 +5592,7 @@ "version": "1.1.0", "resolved": "https://registry.npmjs.org/mem/-/mem-1.1.0.tgz", "integrity": "sha1-Xt1StIXKHZAP5kiVUFOZoN+kX3Y=", + "dev": true, "requires": { "mimic-fn": "^1.0.0" } @@ -5010,6 +5601,7 @@ "version": "1.1.3", "resolved": "https://registry.npmjs.org/mem-fs/-/mem-fs-1.1.3.tgz", "integrity": "sha1-uK6NLj/Lb10/kWXBLUVRoGXZicw=", + "dev": true, "requires": { "through2": "^2.0.0", "vinyl": "^1.1.0", @@ -5017,15 +5609,17 @@ } }, "mem-fs-editor": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/mem-fs-editor/-/mem-fs-editor-3.0.2.tgz", - "integrity": "sha1-3Qpuryu4prN3QAZ6pUnrUwEFr58=", + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/mem-fs-editor/-/mem-fs-editor-4.0.3.tgz", + "integrity": "sha512-tgWmwI/+6vwu6POan82dTjxEpwAoaj0NAFnghtVo/FcLK2/7IhPUtFUUYlwou4MOY6OtjTUJtwpfH1h+eSUziw==", + "dev": true, "requires": { "commondir": "^1.0.1", - "deep-extend": "^0.4.0", - "ejs": "^2.3.1", + "deep-extend": "^0.6.0", + "ejs": "^2.5.9", "glob": "^7.0.3", - "globby": "^6.1.0", + "globby": "^7.1.1", + "isbinaryfile": "^3.0.2", "mkdirp": "^0.5.0", "multimatch": "^2.0.0", "rimraf": "^2.2.8", @@ -5036,22 +5630,46 @@ "clone": { "version": "2.1.2", "resolved": "https://registry.npmjs.org/clone/-/clone-2.1.2.tgz", - "integrity": "sha1-G39Ln1kfHo+DZwQBYANFoCiHQ18=" + "integrity": "sha1-G39Ln1kfHo+DZwQBYANFoCiHQ18=", + "dev": true }, "clone-stats": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/clone-stats/-/clone-stats-1.0.0.tgz", - "integrity": "sha1-s3gt/4u1R04Yuba/D9/ngvh3doA=" + "integrity": "sha1-s3gt/4u1R04Yuba/D9/ngvh3doA=", + "dev": true + }, + "globby": { + "version": "7.1.1", + "resolved": "https://registry.npmjs.org/globby/-/globby-7.1.1.tgz", + "integrity": "sha1-+yzP+UAfhgCUXfral0QMypcrhoA=", + "dev": true, + "requires": { + "array-union": "^1.0.1", + "dir-glob": "^2.0.0", + "glob": "^7.1.2", + "ignore": "^3.3.5", + "pify": "^3.0.0", + "slash": "^1.0.0" + } + }, + "pify": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", + "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=", + "dev": true }, "replace-ext": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/replace-ext/-/replace-ext-1.0.0.tgz", - "integrity": "sha1-3mMSg3P8v3w8z6TeWkgMRaZ5WOs=" + "integrity": "sha1-3mMSg3P8v3w8z6TeWkgMRaZ5WOs=", + "dev": true }, "vinyl": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-2.1.0.tgz", - "integrity": "sha1-Ah+cLPlR1rk5lDyJ617lrdT9kkw=", + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-2.2.0.tgz", + "integrity": "sha512-MBH+yP0kC/GQ5GwBqrTPTzEfiiLjta7hTtvQtbxBgTeSXsmKQRQecjibMbxIXzVT3Y9KJK+drOz1/k+vsu8Nkg==", + "dev": true, "requires": { "clone": "^2.1.1", "clone-buffer": "^1.0.0", @@ -5067,6 +5685,7 @@ "version": "0.4.1", "resolved": "https://registry.npmjs.org/memory-fs/-/memory-fs-0.4.1.tgz", "integrity": "sha1-OpoguEYlI+RHz7x+i7gO1me/xVI=", + "dev": true, "requires": { "errno": "^0.1.3", "readable-stream": "^2.0.1" @@ -5082,6 +5701,12 @@ "resolved": "https://registry.npmjs.org/merge-descriptors/-/merge-descriptors-1.0.1.tgz", "integrity": "sha1-sAqqVW3YtEVoFQ7J0blT8/kMu2E=" }, + "merge2": { + "version": "1.2.3", + "resolved": "https://registry.npmjs.org/merge2/-/merge2-1.2.3.tgz", + "integrity": "sha512-gdUU1Fwj5ep4kplwcmftruWofEFt6lfpkkr3h860CXbAB9c3hGb55EOL2ali0Td5oebvW0E1+3Sr+Ur7XfKpRA==", + "dev": true + }, "methods": { "version": "1.1.2", "resolved": "https://registry.npmjs.org/methods/-/methods-1.1.2.tgz", @@ -5114,27 +5739,28 @@ "integrity": "sha512-KI1+qOZu5DcW6wayYHSzR/tXKCDC5Om4s1z2QJjDULzLcmf3DvzS7oluY4HCTrc+9FiKmWUgeNLg7W3uIQvxtQ==" }, "mime-db": { - "version": "1.33.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.33.0.tgz", - "integrity": "sha512-BHJ/EKruNIqJf/QahvxwQZXKygOQ256myeN/Ew+THcAa5q+PjyTTMMeNQC4DZw5AwfvelsUrA6B67NKMqXDbzQ==" + "version": "1.38.0", + "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.38.0.tgz", + "integrity": "sha512-bqVioMFFzc2awcdJZIzR3HjZFX20QhilVS7hytkKrv7xFAn8bM1gzc/FOX2awLISvWe0PV8ptFKcon+wZ5qYkg==" }, "mime-types": { - "version": "2.1.18", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.18.tgz", - "integrity": "sha512-lc/aahn+t4/SWV/qcmumYjymLsWfN3ELhpmVuUFjgsORruuZPVSwAQryq+HHGvO/SI2KVX26bx+En+zhM8g8hQ==", + "version": "2.1.22", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.22.tgz", + "integrity": "sha512-aGl6TZGnhm/li6F7yx82bJiBZwgiEa4Hf6CNr8YO+r5UHr53tSTYZb102zyU50DOWWKeOv0uQLRL0/9EiKWCog==", "requires": { - "mime-db": "~1.33.0" + "mime-db": "~1.38.0" } }, "mimic-fn": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-1.2.0.tgz", - "integrity": "sha512-jf84uxzwiuiIVKiOLpfYk7N46TSy8ubTonmneY9vrpHNAnp0QBt2BxWV9dO3/j+BoVAb+a5G6YDPW3M5HOdMWQ==" + "integrity": "sha512-jf84uxzwiuiIVKiOLpfYk7N46TSy8ubTonmneY9vrpHNAnp0QBt2BxWV9dO3/j+BoVAb+a5G6YDPW3M5HOdMWQ==", + "dev": true }, "mimic-response": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-1.0.0.tgz", - "integrity": "sha1-3z02Uqc/3ta5sLJBRub9BSNTRY4=" + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-1.0.1.tgz", + "integrity": "sha512-j5EctnkH7amfV/q5Hgmoal1g2QHFJRraOtmx0JpIqkxhBhI/lJSl1nMpQ45hVarwNETOoWEimndZ4QK0RHxuxQ==" }, "min-document": { "version": "2.19.0", @@ -5211,47 +5837,6 @@ "he": "1.1.1", "mkdirp": "0.5.1", "supports-color": "4.4.0" - }, - "dependencies": { - "debug": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", - "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", - "requires": { - "ms": "2.0.0" - } - }, - "glob": { - "version": "7.1.2", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz", - "integrity": "sha512-MJTUg1kjuLeQCJ+ccE4Vpa6kKVXkPYJ2mOCQyUuKLcLQsdrMCpBPUi8qVE6+YuaJkozeA9NusTAw3hLr8Xe5EQ==", - "requires": { - "fs.realpath": "^1.0.0", - "inflight": "^1.0.4", - "inherits": "2", - "minimatch": "^3.0.4", - "once": "^1.3.0", - "path-is-absolute": "^1.0.0" - } - }, - "growl": { - "version": "1.10.3", - "resolved": "https://registry.npmjs.org/growl/-/growl-1.10.3.tgz", - "integrity": "sha512-hKlsbA5Vu3xsh1Cg3J7jSmX/WaW6A5oBeqzM88oNbCRQFz+zUaXm6yxS4RVytp1scBoJzSYl4YAEOQIt6O8V1Q==" - }, - "has-flag": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-2.0.0.tgz", - "integrity": "sha1-6CB68cx7MNRGzHC3NLXovhj4jVE=" - }, - "supports-color": { - "version": "4.4.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-4.4.0.tgz", - "integrity": "sha512-rKC3+DyXWgK0ZLKwmRsrkyHVZAjNkfzeehuFWdGGcqGDTZFH73+RH6S/RDAAxl9GusSjZSUWYLmT9N5pzXFOXQ==", - "requires": { - "has-flag": "^2.0.0" - } - } } }, "ms": { @@ -5263,6 +5848,7 @@ "version": "2.1.0", "resolved": "https://registry.npmjs.org/multimatch/-/multimatch-2.1.0.tgz", "integrity": "sha1-nHkGoi+0wCkZ4vX3UWG0zb1LKis=", + "dev": true, "requires": { "array-differ": "^1.0.0", "array-union": "^1.0.1", @@ -5273,7 +5859,8 @@ "mute-stream": { "version": "0.0.7", "resolved": "https://registry.npmjs.org/mute-stream/-/mute-stream-0.0.7.tgz", - "integrity": "sha1-MHXOk7whuPq0PhvE2n6BFe0ee6s=" + "integrity": "sha1-MHXOk7whuPq0PhvE2n6BFe0ee6s=", + "dev": true }, "nan": { "version": "2.10.0", @@ -5286,9 +5873,9 @@ "integrity": "sha1-DMj20OK2IrR5xA1JnEbWS3Vcb18=" }, "nanomatch": { - "version": "1.2.9", - "resolved": "https://registry.npmjs.org/nanomatch/-/nanomatch-1.2.9.tgz", - "integrity": "sha512-n8R9bS8yQ6eSXaV6jHUpKzD8gLsin02w1HSFiegwrs9E098Ylhw5jdyKPaYqvHknHaSCKTPp7C8dGCQ0q9koXA==", + "version": "1.2.13", + "resolved": "https://registry.npmjs.org/nanomatch/-/nanomatch-1.2.13.tgz", + "integrity": "sha512-fpoe2T0RbHwBTBUOftAfBPaDEi06ufaUai0mE6Yn1kacc3SnTErfb/h+X94VXzI64rKFHYImXSvdwGGCmwOqCA==", "dev": true, "requires": { "arr-diff": "^4.0.0", @@ -5296,7 +5883,6 @@ "define-property": "^2.0.2", "extend-shallow": "^3.0.2", "fragment-cache": "^0.2.1", - "is-odd": "^2.0.0", "is-windows": "^1.0.2", "kind-of": "^6.0.2", "object.pick": "^1.3.0", @@ -5311,47 +5897,41 @@ "integrity": "sha1-KzJxhOiZIQEXeyhWP7XnECrNDKk=" }, "neo-async": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/neo-async/-/neo-async-2.5.0.tgz", - "integrity": "sha512-nJmSswG4As/MkRq7QZFuH/sf/yuv8ODdMZrY4Bedjp77a5MK4A6s7YbBB64c9u79EBUOfXUXBvArmvzTD0X+6g==" + "version": "2.6.0", + "resolved": "https://registry.npmjs.org/neo-async/-/neo-async-2.6.0.tgz", + "integrity": "sha512-MFh0d/Wa7vkKO3Y3LlacqAEeHK0mckVqzDieUKTT+KGxi+zIpeVsFxymkIiRpbpDziHc290Xr9A1O4Om7otoRA==", + "dev": true }, "nice-try": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/nice-try/-/nice-try-1.0.4.tgz", - "integrity": "sha512-2NpiFHqC87y/zFke0fC0spBXL3bBsoh/p5H1EFhshxjCR5+0g2d6BiXbUFz9v1sAcxsk2htp2eQnNIci2dIYcA==" + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/nice-try/-/nice-try-1.0.5.tgz", + "integrity": "sha512-1nh45deeb5olNY7eX82BkPO7SSxR5SSYJiPTrTdFUVYwAl8CKMA5N9PjTYkHiRjisVcxcQ1HXdLhx2qxxJzLNQ==", + "dev": true }, "node-dir": { "version": "0.1.8", "resolved": "https://registry.npmjs.org/node-dir/-/node-dir-0.1.8.tgz", - "integrity": "sha1-VfuN62mQcHB/tn+RpGDwRIKUx30=" + "integrity": "sha1-VfuN62mQcHB/tn+RpGDwRIKUx30=", + "dev": true }, "nodemon": { - "version": "1.17.3", - "resolved": "https://registry.npmjs.org/nodemon/-/nodemon-1.17.3.tgz", - "integrity": "sha512-8AtS+wA5u6qoE12LONjqOzUzxAI5ObzSw6U5LgqpaO/0y6wwId4l5dN0ZulYyYdpLZD1MbkBp7GjG1hqaoRqYg==", + "version": "1.18.10", + "resolved": "https://registry.npmjs.org/nodemon/-/nodemon-1.18.10.tgz", + "integrity": "sha512-we51yBb1TfEvZamFchRgcfLbVYgg0xlGbyXmOtbBzDwxwgewYS/YbZ5tnlnsH51+AoSTTsT3A2E/FloUbtH8cQ==", "dev": true, "requires": { - "chokidar": "^2.0.2", + "chokidar": "^2.1.0", "debug": "^3.1.0", "ignore-by-default": "^1.0.1", "minimatch": "^3.0.4", - "pstree.remy": "^1.1.0", + "pstree.remy": "^1.1.6", "semver": "^5.5.0", "supports-color": "^5.2.0", "touch": "^3.1.0", "undefsafe": "^2.0.2", - "update-notifier": "^2.3.0" + "update-notifier": "^2.5.0" }, "dependencies": { - "debug": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", - "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", - "dev": true, - "requires": { - "ms": "2.0.0" - } - }, "has-flag": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", @@ -5359,9 +5939,9 @@ "dev": true }, "supports-color": { - "version": "5.4.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.4.0.tgz", - "integrity": "sha512-zjaXglF5nnWpsq470jSv6P9DwPvgLkuapYmfDm3JWOm0vkNTVF2tI4UrN2r6jH1qM/uc/WtxYY1hYoA2dOKj5w==", + "version": "5.5.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", + "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", "dev": true, "requires": { "has-flag": "^3.0.0" @@ -5373,6 +5953,7 @@ "version": "1.8.1", "resolved": "https://registry.npmjs.org/nomnom/-/nomnom-1.8.1.tgz", "integrity": "sha1-IVH3Ikcrp55Qp2/BJbuMjy5Nwqc=", + "dev": true, "requires": { "chalk": "~0.4.0", "underscore": "~1.6.0" @@ -5381,12 +5962,14 @@ "ansi-styles": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-1.0.0.tgz", - "integrity": "sha1-yxAt8cVvUSPquLZ817mAJ6AnkXg=" + "integrity": "sha1-yxAt8cVvUSPquLZ817mAJ6AnkXg=", + "dev": true }, "chalk": { "version": "0.4.0", "resolved": "https://registry.npmjs.org/chalk/-/chalk-0.4.0.tgz", "integrity": "sha1-UZmj3c0MHv4jvAjBsCewYXbgxk8=", + "dev": true, "requires": { "ansi-styles": "~1.0.0", "has-color": "~0.1.0", @@ -5396,7 +5979,14 @@ "strip-ansi": { "version": "0.1.1", "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-0.1.1.tgz", - "integrity": "sha1-OeipjQRNFQZgq+SmgIrPcLt7yZE=" + "integrity": "sha1-OeipjQRNFQZgq+SmgIrPcLt7yZE=", + "dev": true + }, + "underscore": { + "version": "1.6.0", + "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.6.0.tgz", + "integrity": "sha1-izixDKze9jM3uLJOT/htRa6lKag=", + "dev": true } } }, @@ -5410,28 +6000,27 @@ } }, "normalize-package-data": { - "version": "2.4.0", - "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-2.4.0.tgz", - "integrity": "sha512-9jjUFbTPfEy3R/ad/2oNbKtW9Hgovl5O1FvFWKkKblNXoN/Oou6+9+KKohPK13Yc3/TyunyWhJp6gvRNR/PPAw==", + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-2.5.0.tgz", + "integrity": "sha512-/5CMN3T0R4XTj4DcGaexo+roZSdSFW/0AOOTROrjxzCG1wrWXEsGbRKevjlIL+ZDE4sZlJr5ED4YW0yqmkK+eA==", "requires": { "hosted-git-info": "^2.1.4", - "is-builtin-module": "^1.0.0", + "resolve": "^1.10.0", "semver": "2 || 3 || 4 || 5", "validate-npm-package-license": "^3.0.1" } }, "normalize-path": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-2.1.1.tgz", - "integrity": "sha1-GrKLVW4Zg2Oowab35vogE3/mrtk=", - "requires": { - "remove-trailing-separator": "^1.0.1" - } + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-3.0.0.tgz", + "integrity": "sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==", + "dev": true }, "normalize-url": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/normalize-url/-/normalize-url-2.0.1.tgz", "integrity": "sha512-D6MUW4K/VzoJ4rJ01JFKxDrtY1v9wrgzCX5f2qj/lzH1m/lW6MhUZFKerVsnyjOhOsYzI9Kqqak+10l4LvLpMw==", + "dev": true, "requires": { "prepend-http": "^2.0.0", "query-string": "^5.0.1", @@ -5441,7 +6030,8 @@ "prepend-http": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/prepend-http/-/prepend-http-2.0.0.tgz", - "integrity": "sha1-6SQ0v6XqjBn0HN/UAddBo8gZ2Jc=" + "integrity": "sha1-6SQ0v6XqjBn0HN/UAddBo8gZ2Jc=", + "dev": true } } }, @@ -5449,6 +6039,7 @@ "version": "2.0.2", "resolved": "https://registry.npmjs.org/npm-run-path/-/npm-run-path-2.0.2.tgz", "integrity": "sha1-NakjLfo11wZ7TLLd8jV7GHFTbF8=", + "dev": true, "requires": { "path-key": "^2.0.0" } @@ -5468,9 +6059,9 @@ } }, "oauth-sign": { - "version": "0.8.2", - "resolved": "https://registry.npmjs.org/oauth-sign/-/oauth-sign-0.8.2.tgz", - "integrity": "sha1-Rqarfwrq2N6unsBWV4C31O/rnUM=" + "version": "0.9.0", + "resolved": "https://registry.npmjs.org/oauth-sign/-/oauth-sign-0.9.0.tgz", + "integrity": "sha512-fexhUFFPTGV8ybAtSIGbV6gOkSv8UtRbDBnAyLQw4QPKkgNlsH2ByPGtMUqdWkos6YCRmAqViwgZrJc/mRDzZQ==" }, "object-assign": { "version": "4.1.1", @@ -5508,6 +6099,11 @@ } } }, + "object-keys": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/object-keys/-/object-keys-1.1.0.tgz", + "integrity": "sha512-6OO5X1+2tYkNyNEx6TsCxEqFfRWaqx6EtMiSbGrw8Ob8v9Ne+Hl8rBAgLBZn5wjEz3s/s6U1WXFUFOcxxAwUpg==" + }, "object-visit": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/object-visit/-/object-visit-1.0.1.tgz", @@ -5521,6 +6117,7 @@ "version": "2.0.1", "resolved": "https://registry.npmjs.org/object.omit/-/object.omit-2.0.1.tgz", "integrity": "sha1-Gpx0SCnznbuFjHbKNXmuKlTr0fo=", + "dev": true, "requires": { "for-own": "^0.1.4", "is-extendable": "^0.1.1" @@ -5555,14 +6152,15 @@ "version": "2.0.1", "resolved": "https://registry.npmjs.org/onetime/-/onetime-2.0.1.tgz", "integrity": "sha1-BnQoIw/WdEOyeUsiu6UotoZ5YtQ=", + "dev": true, "requires": { "mimic-fn": "^1.0.0" } }, "openzeppelin-solidity": { - "version": "1.10.0", - "resolved": "https://registry.npmjs.org/openzeppelin-solidity/-/openzeppelin-solidity-1.10.0.tgz", - "integrity": "sha512-igkrumQQ2lrN2zjeQV4Dnb0GpTBj1fzMcd8HPyBUqwI0hhuscX/HzXiqKT6gFQl1j9Wy/ppVVs9fqL/foF7Gmg==" + "version": "1.12.0", + "resolved": "https://registry.npmjs.org/openzeppelin-solidity/-/openzeppelin-solidity-1.12.0.tgz", + "integrity": "sha512-WlorzMXIIurugiSdw121RVD5qA3EfSI7GybTn+/Du0mPNgairjt29NpVTAaH8eLjAeAwlw46y7uQKy0NYem/gA==" }, "optimist": { "version": "0.6.1", @@ -5596,63 +6194,6 @@ "wordwrap": "~1.0.0" } }, - "ora": { - "version": "0.2.3", - "resolved": "https://registry.npmjs.org/ora/-/ora-0.2.3.tgz", - "integrity": "sha1-N1J9Igrc1Tw5tzVx11QVbV22V6Q=", - "requires": { - "chalk": "^1.1.1", - "cli-cursor": "^1.0.2", - "cli-spinners": "^0.1.2", - "object-assign": "^4.0.1" - }, - "dependencies": { - "ansi-styles": { - "version": "2.2.1", - "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-2.2.1.tgz", - "integrity": "sha1-tDLdM1i2NM914eRmQ2gkBTPB3b4=" - }, - "chalk": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz", - "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=", - "requires": { - "ansi-styles": "^2.2.1", - "escape-string-regexp": "^1.0.2", - "has-ansi": "^2.0.0", - "strip-ansi": "^3.0.0", - "supports-color": "^2.0.0" - } - }, - "cli-cursor": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-1.0.2.tgz", - "integrity": "sha1-ZNo/fValRBLll5S9Ytw1KV6PKYc=", - "requires": { - "restore-cursor": "^1.0.1" - } - }, - "onetime": { - "version": "1.1.0", - "resolved": "http://registry.npmjs.org/onetime/-/onetime-1.1.0.tgz", - "integrity": "sha1-ofeDj4MUxRbwXs78vEzP4EtO14k=" - }, - "restore-cursor": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-1.0.1.tgz", - "integrity": "sha1-NGYfRohjJ/7SmRR5FSJS35LapUE=", - "requires": { - "exit-hook": "^1.0.0", - "onetime": "^1.0.0" - } - }, - "supports-color": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz", - "integrity": "sha1-U10EXOa2Nj+kARcIRimZXp3zJMc=" - } - } - }, "original-require": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/original-require/-/original-require-1.0.1.tgz", @@ -5661,7 +6202,8 @@ "os-homedir": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/os-homedir/-/os-homedir-1.0.2.tgz", - "integrity": "sha1-/7xJiDNuDoM94MFox+8VISGqf7M=" + "integrity": "sha1-/7xJiDNuDoM94MFox+8VISGqf7M=", + "dev": true }, "os-locale": { "version": "1.4.0", @@ -5674,17 +6216,20 @@ "os-tmpdir": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/os-tmpdir/-/os-tmpdir-1.0.2.tgz", - "integrity": "sha1-u+Z0BseaqFxc/sdm/lc0VV36EnQ=" + "integrity": "sha1-u+Z0BseaqFxc/sdm/lc0VV36EnQ=", + "dev": true }, "p-cancelable": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/p-cancelable/-/p-cancelable-0.4.0.tgz", - "integrity": "sha512-/AodqPe1y/GYbhSlnMjxukLGQfQIgsmjSy2CXCNB96kg4ozKvmlovuHEKICToOO/yS3LLWgrWI1dFtFfrePS1g==" + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/p-cancelable/-/p-cancelable-0.4.1.tgz", + "integrity": "sha512-HNa1A8LvB1kie7cERyy21VNeHb2CWJJYqyyC2o3klWFfMGlFmWv2Z7sFgZH8ZiaYL95ydToKTFVXgMV/Os0bBQ==", + "dev": true }, "p-each-series": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/p-each-series/-/p-each-series-1.0.0.tgz", "integrity": "sha1-kw89Et0fUOdDRFeiLNbwSsatf3E=", + "dev": true, "requires": { "p-reduce": "^1.0.0" } @@ -5692,22 +6237,26 @@ "p-finally": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/p-finally/-/p-finally-1.0.0.tgz", - "integrity": "sha1-P7z7FbiZpEEjs0ttzBi3JDNqLK4=" + "integrity": "sha1-P7z7FbiZpEEjs0ttzBi3JDNqLK4=", + "dev": true }, "p-is-promise": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/p-is-promise/-/p-is-promise-1.1.0.tgz", - "integrity": "sha1-nJRWmJ6fZYgBewQ01WCXZ1w9oF4=" + "integrity": "sha1-nJRWmJ6fZYgBewQ01WCXZ1w9oF4=", + "dev": true }, "p-lazy": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/p-lazy/-/p-lazy-1.0.0.tgz", - "integrity": "sha1-7FPIAvLuOsKPFmzILQsrAt4nqDU=" + "integrity": "sha1-7FPIAvLuOsKPFmzILQsrAt4nqDU=", + "dev": true }, "p-limit": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-1.2.0.tgz", - "integrity": "sha512-Y/OtIaXtUPr4/YpMv1pCL5L5ed0rumAaAeBSj12F+bSlMdys7i8oQF/GUJmfpTS/QoaRrS/k6pma29haJpsMng==", + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-1.3.0.tgz", + "integrity": "sha512-vvcXsLAJ9Dr5rQOPk7toZQZJApBl2K4J6dANSsEuh6QI41JYcsS/qhTGa9ErIUUgK3WNQoJYvylxvjqmiqEA9Q==", + "dev": true, "requires": { "p-try": "^1.0.0" } @@ -5716,24 +6265,28 @@ "version": "2.0.0", "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-2.0.0.tgz", "integrity": "sha1-IKAQOyIqcMj9OcwuWAaA893l7EM=", + "dev": true, "requires": { "p-limit": "^1.1.0" } }, "p-map": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/p-map/-/p-map-1.2.0.tgz", - "integrity": "sha512-r6zKACMNhjPJMTl8KcFH4li//gkrXWfbD6feV8l6doRHlzljFWGJ2AP6iKaCJXyZmAUMOPtvbW7EXkbWO/pLEA==" + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/p-map/-/p-map-2.0.0.tgz", + "integrity": "sha512-GO107XdrSUmtHxVoi60qc9tUl/KkNKm+X2CF4P9amalpGxv5YqVPJNfSb0wcA+syCopkZvYYIzW8OVTQW59x/w==", + "dev": true }, "p-reduce": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/p-reduce/-/p-reduce-1.0.0.tgz", - "integrity": "sha1-GMKw3ZNqRpClKfgjH1ig/bakffo=" + "integrity": "sha1-GMKw3ZNqRpClKfgjH1ig/bakffo=", + "dev": true }, "p-timeout": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/p-timeout/-/p-timeout-2.0.1.tgz", "integrity": "sha512-88em58dDVB/KzPEx1X0N3LwFfYZPyDc4B6eF38M1rk9VTZMbxXXgjugz8mmwpS9Ox4BDZ+t6t3QP5+/gazweIA==", + "dev": true, "requires": { "p-finally": "^1.0.0" } @@ -5741,7 +6294,8 @@ "p-try": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/p-try/-/p-try-1.0.0.tgz", - "integrity": "sha1-y8ec26+P1CKOE/Yh8rGiN8GyB7M=" + "integrity": "sha1-y8ec26+P1CKOE/Yh8rGiN8GyB7M=", + "dev": true }, "package-json": { "version": "4.0.1", @@ -5765,6 +6319,7 @@ "version": "3.0.4", "resolved": "https://registry.npmjs.org/parse-glob/-/parse-glob-3.0.4.tgz", "integrity": "sha1-ssN2z7EfNVE7rdFz7wu246OIORw=", + "dev": true, "requires": { "glob-base": "^0.3.0", "is-dotfile": "^1.0.0", @@ -5775,12 +6330,14 @@ "is-extglob": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-1.0.0.tgz", - "integrity": "sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA=" + "integrity": "sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA=", + "dev": true }, "is-glob": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-2.0.1.tgz", "integrity": "sha1-0Jb5JqPe1WAPP9/ZEZjLCIjC2GM=", + "dev": true, "requires": { "is-extglob": "^1.0.0" } @@ -5788,12 +6345,12 @@ } }, "parse-headers": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/parse-headers/-/parse-headers-2.0.1.tgz", - "integrity": "sha1-aug6eqJanZtwCswoaYzR8e1+lTY=", + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/parse-headers/-/parse-headers-2.0.2.tgz", + "integrity": "sha512-/LypJhzFmyBIDYP9aDVgeyEb5sQfbfY5mnDq4hVhlQ69js87wXfmEI5V3xI6vvXasqebp0oCytYFLxsBVfCzSg==", "requires": { - "for-each": "^0.3.2", - "trim": "0.0.1" + "for-each": "^0.3.3", + "string.prototype.trim": "^1.1.2" } }, "parse-json": { @@ -5807,7 +6364,8 @@ "parse-passwd": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/parse-passwd/-/parse-passwd-1.0.0.tgz", - "integrity": "sha1-bVuTSkVpk7I9N/QKOC1vFmao5cY=" + "integrity": "sha1-bVuTSkVpk7I9N/QKOC1vFmao5cY=", + "dev": true }, "parseurl": { "version": "1.3.2", @@ -5848,12 +6406,13 @@ "path-key": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/path-key/-/path-key-2.0.1.tgz", - "integrity": "sha1-QRyttXTFoUDTpLGRDUDYDMn0C0A=" + "integrity": "sha1-QRyttXTFoUDTpLGRDUDYDMn0C0A=", + "dev": true }, "path-parse": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.5.tgz", - "integrity": "sha1-PBrfhx6pzWyUMbbqK9dKD/BVxME=" + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.6.tgz", + "integrity": "sha512-GSmOT2EbHrINBf9SR7CDELwlJ8AENk3Qn7OikK4nFYAu3Ote2+JYNVvkpAEQm3/TLNEJFD/xZJjzyxg3KBWOzw==" }, "path-to-regexp": { "version": "0.1.7", @@ -5876,15 +6435,6 @@ "integrity": "sha1-uULm1L3mUwBe9rcTYd74cn0GReA=", "dev": true }, - "pause-stream": { - "version": "0.0.11", - "resolved": "https://registry.npmjs.org/pause-stream/-/pause-stream-0.0.11.tgz", - "integrity": "sha1-/lo0sMvOErWqaitAPuLnO2AvFEU=", - "dev": true, - "requires": { - "through": "~2.3" - } - }, "pegjs": { "version": "0.10.0", "resolved": "https://registry.npmjs.org/pegjs/-/pegjs-0.10.0.tgz", @@ -5914,6 +6464,26 @@ "pinkie": "^2.0.0" } }, + "pkg-dir": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/pkg-dir/-/pkg-dir-2.0.0.tgz", + "integrity": "sha1-9tXREJ4Z1j7fQo4L1X4Sd3YVM0s=", + "dev": true, + "requires": { + "find-up": "^2.1.0" + }, + "dependencies": { + "find-up": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", + "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", + "dev": true, + "requires": { + "locate-path": "^2.0.0" + } + } + } + }, "posix-character-classes": { "version": "0.1.1", "resolved": "https://registry.npmjs.org/posix-character-classes/-/posix-character-classes-0.1.1.tgz", @@ -5929,27 +6499,32 @@ "prepend-http": { "version": "1.0.4", "resolved": "https://registry.npmjs.org/prepend-http/-/prepend-http-1.0.4.tgz", - "integrity": "sha1-1PRWKwzjaW5BrFLQ4ALlemNdxtw=" + "integrity": "sha1-1PRWKwzjaW5BrFLQ4ALlemNdxtw=", + "dev": true }, "preserve": { "version": "0.2.0", "resolved": "https://registry.npmjs.org/preserve/-/preserve-0.2.0.tgz", - "integrity": "sha1-gV7R9uvGWSb4ZbMQwHE7yzMVzks=" + "integrity": "sha1-gV7R9uvGWSb4ZbMQwHE7yzMVzks=", + "dev": true }, "prettier": { - "version": "1.11.1", - "resolved": "https://registry.npmjs.org/prettier/-/prettier-1.11.1.tgz", - "integrity": "sha512-T/KD65Ot0PB97xTrG8afQ46x3oiVhnfGjGESSI9NWYcG92+OUPZKkwHqGWXH2t9jK1crnQjubECW0FuOth+hxw==" + "version": "1.16.4", + "resolved": "https://registry.npmjs.org/prettier/-/prettier-1.16.4.tgz", + "integrity": "sha512-ZzWuos7TI5CKUeQAtFd6Zhm2s6EpAD/ZLApIhsF9pRvRtM1RFo61dM/4MSRUA0SuLugA/zgrZD8m0BaY46Og7g==", + "dev": true }, "pretty-bytes": { "version": "4.0.2", "resolved": "https://registry.npmjs.org/pretty-bytes/-/pretty-bytes-4.0.2.tgz", - "integrity": "sha1-sr+C5zUNZcbDOqlaqlpPYyf2HNk=" + "integrity": "sha1-sr+C5zUNZcbDOqlaqlpPYyf2HNk=", + "dev": true }, "private": { "version": "0.1.8", "resolved": "https://registry.npmjs.org/private/-/private-0.1.8.tgz", - "integrity": "sha512-VvivMrbvd2nKkiG38qjULzlc+4Vx4wm/whI9pQD35YrARNnhxeiRktSOhSukRLFNlzg6Br/cJPet5J/u19r/mg==" + "integrity": "sha512-VvivMrbvd2nKkiG38qjULzlc+4Vx4wm/whI9pQD35YrARNnhxeiRktSOhSukRLFNlzg6Br/cJPet5J/u19r/mg==", + "dev": true }, "process": { "version": "0.5.2", @@ -5959,63 +6534,59 @@ "process-nextick-args": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.0.tgz", - "integrity": "sha512-MtEC1TqN0EU5nephaJ4rAtThHtC86dNN9qCuEhtshvpVBkAW5ZO7BASN9REnF9eoXGcRub+pFuKEpOHE+HbEMw==" + "integrity": "sha512-MtEC1TqN0EU5nephaJ4rAtThHtC86dNN9qCuEhtshvpVBkAW5ZO7BASN9REnF9eoXGcRub+pFuKEpOHE+HbEMw==", + "dev": true }, "promise": { - "version": "8.0.2", - "resolved": "https://registry.npmjs.org/promise/-/promise-8.0.2.tgz", - "integrity": "sha512-EIyzM39FpVOMbqgzEHhxdrEhtOSDOtjMZQ0M6iVfCE+kWNgCkAyOdnuCWqfmflylftfadU6FkiMgHZA2kUzwRw==", + "version": "8.0.3", + "resolved": "https://registry.npmjs.org/promise/-/promise-8.0.3.tgz", + "integrity": "sha512-HeRDUL1RJiLhyA0/grn+PTShlBAcLuh/1BJGtrvjwbvRDCTLLMEz9rOGCV+R3vHY4MixIuoMEd9Yq/XvsTPcjw==", "dev": true, "requires": { "asap": "~2.0.6" } }, "proxy-addr": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.3.tgz", - "integrity": "sha512-jQTChiCJteusULxjBp8+jftSQE5Obdl3k4cnmLA6WXtK6XFuWRnvVL7aCiBqaLPM8c4ph0S4tKna8XvmIwEnXQ==", + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.4.tgz", + "integrity": "sha512-5erio2h9jp5CHGwcybmxmVqHmnCBZeewlfJ0pex+UW7Qny7OOZXTtH56TGNyBizkgiOwhJtMKrVzDTeKcySZwA==", "requires": { "forwarded": "~0.1.2", - "ipaddr.js": "1.6.0" + "ipaddr.js": "1.8.0" } }, "prr": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/prr/-/prr-1.0.1.tgz", - "integrity": "sha1-0/wRS6BplaRexok/SEzrHXj19HY=" - }, - "ps-tree": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/ps-tree/-/ps-tree-1.1.0.tgz", - "integrity": "sha1-tCGyQUDWID8e08dplrRCewjowBQ=", - "dev": true, - "requires": { - "event-stream": "~3.3.0" - } + "integrity": "sha1-0/wRS6BplaRexok/SEzrHXj19HY=", + "dev": true }, "pseudomap": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/pseudomap/-/pseudomap-1.0.2.tgz", - "integrity": "sha1-8FKijacOYYkX7wqKw0wa5aaChrM=" + "integrity": "sha1-8FKijacOYYkX7wqKw0wa5aaChrM=", + "dev": true + }, + "psl": { + "version": "1.1.31", + "resolved": "https://registry.npmjs.org/psl/-/psl-1.1.31.tgz", + "integrity": "sha512-/6pt4+C+T+wZUieKR620OpzN/LlnNKuWjy1iFLQ/UG35JqHlR/89MP1d96dUfkf6Dne3TuLQzOYEYshJ+Hx8mw==" }, "pstree.remy": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/pstree.remy/-/pstree.remy-1.1.0.tgz", - "integrity": "sha512-q5I5vLRMVtdWa8n/3UEzZX7Lfghzrg9eG2IKk2ENLSofKRCXVqMvMUHxCKgXNaqH/8ebhBxrqftHWnyTFweJ5Q==", - "dev": true, - "requires": { - "ps-tree": "^1.1.0" - } + "version": "1.1.6", + "resolved": "https://registry.npmjs.org/pstree.remy/-/pstree.remy-1.1.6.tgz", + "integrity": "sha512-NdF35+QsqD7EgNEI5mkI/X+UwaxVEbQaz9f4IooEmMUv6ZPmlTQYGjBPJGgrlzNdjSvIy4MWMg6Q6vCgBO2K+w==", + "dev": true }, "punycode": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/punycode/-/punycode-1.4.1.tgz", - "integrity": "sha1-wNWmOycYgArY4esPpSachN1BhF4=" + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.1.1.tgz", + "integrity": "sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A==" }, "qs": { - "version": "6.5.1", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.5.1.tgz", - "integrity": "sha512-eRzhrN1WSINYCDCbrz796z37LOe3m5tmW7RQf6oBntukAG1nmovJvhnwHHRMAfeoItc1m2Hk02WER2aQ/iqs+A==" + "version": "6.5.2", + "resolved": "https://registry.npmjs.org/qs/-/qs-6.5.2.tgz", + "integrity": "sha512-N5ZAX4/LxJmF+7wN74pUD6qAh9/wnvdQcjq9TZjevvXzSUo7bfmw91saqMjzGS2xq91/odN2dW/WOl7qQHNDGA==" }, "query-string": { "version": "5.1.1", @@ -6028,21 +6599,21 @@ } }, "randomatic": { - "version": "1.1.7", - "resolved": "https://registry.npmjs.org/randomatic/-/randomatic-1.1.7.tgz", - "integrity": "sha512-D5JUjPyJbaJDkuAazpVnSfVkLlpeO3wDlPROTMLGKG1zMFNFRgrciKo1ltz/AzNTkqE0HzDx655QOL51N06how==", + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/randomatic/-/randomatic-3.1.1.tgz", + "integrity": "sha512-TuDE5KxZ0J461RVjrJZCJc+J+zCkTb1MbH9AQUq68sMhOMcy9jLcb3BrZKgp9q9Ncltdg4QVqWrH02W2EFFVYw==", + "dev": true, "requires": { - "is-number": "^3.0.0", - "kind-of": "^4.0.0" + "is-number": "^4.0.0", + "kind-of": "^6.0.0", + "math-random": "^1.0.1" }, "dependencies": { - "kind-of": { + "is-number": { "version": "4.0.0", - "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-4.0.0.tgz", - "integrity": "sha1-IIE989cSkosgc3hpGkUGb65y3Vc=", - "requires": { - "is-buffer": "^1.1.5" - } + "resolved": "https://registry.npmjs.org/is-number/-/is-number-4.0.0.tgz", + "integrity": "sha512-rSklcAIlf1OmFdyAqbnWTLVelsQ58uvZ66S/ZyawjWqIviTWCjg2PzVGw8WUA+nNuPTqb4wgA+NszrJ+08LlgQ==", + "dev": true } } }, @@ -6057,46 +6628,23 @@ "integrity": "sha1-9JvmtIeJTdxA3MlKMi9hEJLgDV4=" }, "raw-body": { - "version": "2.3.2", - "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-2.3.2.tgz", - "integrity": "sha1-vNYMd9Prk83gBQKVw/N5OJvIj4k=", + "version": "2.3.3", + "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-2.3.3.tgz", + "integrity": "sha512-9esiElv1BrZoI3rCDuOuKCBRbuApGGaDPQfjSflGxdy4oyzqghxu6klEkkVIvBje+FF0BX9coEv8KqW6X/7njw==", "requires": { "bytes": "3.0.0", - "http-errors": "1.6.2", - "iconv-lite": "0.4.19", + "http-errors": "1.6.3", + "iconv-lite": "0.4.23", "unpipe": "1.0.0" - }, - "dependencies": { - "depd": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/depd/-/depd-1.1.1.tgz", - "integrity": "sha1-V4O04cRZ8G+lyif5kfPQbnoxA1k=" - }, - "http-errors": { - "version": "1.6.2", - "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.6.2.tgz", - "integrity": "sha1-CgAsyFcHGSp+eUbO7cERVfYOxzY=", - "requires": { - "depd": "1.1.1", - "inherits": "2.0.3", - "setprototypeof": "1.0.3", - "statuses": ">= 1.3.1 < 2" - } - }, - "setprototypeof": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.0.3.tgz", - "integrity": "sha1-ZlZ+NwQ+608E2RvWWMDL77VbjgQ=" - } } }, "rc": { - "version": "1.2.6", - "resolved": "https://registry.npmjs.org/rc/-/rc-1.2.6.tgz", - "integrity": "sha1-6xiYnG1PTxYsOZ953dKfODVWgJI=", + "version": "1.2.8", + "resolved": "https://registry.npmjs.org/rc/-/rc-1.2.8.tgz", + "integrity": "sha512-y3bGgqKj3QBdxLbLkomlohkvsA8gdAiUQlSBJnBhfn+BPxg4bc62d8TcBW15wavDfgexCgccckhcZvywyQYPOw==", "dev": true, "requires": { - "deep-extend": "~0.4.0", + "deep-extend": "^0.6.0", "ini": "~1.3.0", "minimist": "^1.2.0", "strip-json-comments": "~2.0.1" @@ -6114,6 +6662,7 @@ "version": "2.1.0", "resolved": "https://registry.npmjs.org/read-chunk/-/read-chunk-2.1.0.tgz", "integrity": "sha1-agTAkoAF7Z1C4aasVgDhnLx/9lU=", + "dev": true, "requires": { "pify": "^3.0.0", "safe-buffer": "^5.1.1" @@ -6122,7 +6671,8 @@ "pify": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", - "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=" + "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=", + "dev": true } } }, @@ -6146,37 +6696,38 @@ } }, "readable-stream": { - "version": "2.3.5", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.5.tgz", - "integrity": "sha512-tK0yDhrkygt/knjowCUiWP9YdV7c5R+8cR0r/kt9ZhBU906Fs6RpQJCEilamRJj1Nx2rWI6LkW9gKqjTkshhEw==", + "version": "2.3.6", + "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.6.tgz", + "integrity": "sha512-tQtKA9WIAhBF3+VLAseyMqZeBjW0AHJoxOtYqSUZNJxauErmLbVm2FW1y+J/YA9dUrAC39ITejlZWhVIwawkKw==", + "dev": true, "requires": { "core-util-is": "~1.0.0", "inherits": "~2.0.3", "isarray": "~1.0.0", "process-nextick-args": "~2.0.0", "safe-buffer": "~5.1.1", - "string_decoder": "~1.0.3", + "string_decoder": "~1.1.1", "util-deprecate": "~1.0.1" } }, "readdirp": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-2.1.0.tgz", - "integrity": "sha1-TtCtBg3zBzMAxIRANz9y0cxkLXg=", + "version": "2.2.1", + "resolved": "https://registry.npmjs.org/readdirp/-/readdirp-2.2.1.tgz", + "integrity": "sha512-1JU/8q+VgFZyxwrJ+SVIOsh+KywWGpds3NTqikiKpDMZWScmAYyKIgqkO+ARvNWJfXeXR1zxz7aHF4u4CyH6vQ==", "dev": true, "requires": { - "graceful-fs": "^4.1.2", - "minimatch": "^3.0.2", - "readable-stream": "^2.0.2", - "set-immediate-shim": "^1.0.1" + "graceful-fs": "^4.1.11", + "micromatch": "^3.1.10", + "readable-stream": "^2.0.2" } }, "recast": { - "version": "0.14.7", - "resolved": "https://registry.npmjs.org/recast/-/recast-0.14.7.tgz", - "integrity": "sha512-/nwm9pkrcWagN40JeJhkPaRxiHXBRkXyRh/hgU088Z/v+qCy+zIHHY6bC6o7NaKAxPqtE6nD8zBH1LfU0/Wx6A==", + "version": "0.15.5", + "resolved": "https://registry.npmjs.org/recast/-/recast-0.15.5.tgz", + "integrity": "sha512-nkAYNqarh73cMWRKFiPQ8I9dOLFvFk6SnG8u/LUlOYfArDOD/EjsVRAs860TlBLrpxqAXHGET/AUAVjdEymL5w==", + "dev": true, "requires": { - "ast-types": "0.11.3", + "ast-types": "0.11.5", "esprima": "~4.0.0", "private": "~0.1.5", "source-map": "~0.6.1" @@ -6185,7 +6736,8 @@ "source-map": { "version": "0.6.1", "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", - "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==" + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", + "dev": true } } }, @@ -6193,24 +6745,28 @@ "version": "0.6.2", "resolved": "https://registry.npmjs.org/rechoir/-/rechoir-0.6.2.tgz", "integrity": "sha1-hSBLVNuoLVdC4oyWdW70OvUOM4Q=", + "dev": true, "requires": { "resolve": "^1.1.6" } }, "regenerate": { - "version": "1.3.3", - "resolved": "https://registry.npmjs.org/regenerate/-/regenerate-1.3.3.tgz", - "integrity": "sha512-jVpo1GadrDAK59t/0jRx5VxYWQEDkkEKi6+HjE3joFVLfDOh9Xrdh0dF1eSq+BI/SwvTQ44gSscJ8N5zYL61sg==" + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/regenerate/-/regenerate-1.4.0.tgz", + "integrity": "sha512-1G6jJVDWrt0rK99kBjvEtziZNCICAuvIPkSiUFIQxVP06RCVpq3dmDo2oi6ABpYaDYaTRr67BEhL8r1wgEZZKg==", + "dev": true }, "regenerator-runtime": { "version": "0.11.1", "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.11.1.tgz", - "integrity": "sha512-MguG95oij0fC3QV3URf4V2SDYGJhJnJGqvIIgdECeODCT98wSWDAJ94SSuVpYQUoTcGUIL6L4yNB7j1DFFHSBg==" + "integrity": "sha512-MguG95oij0fC3QV3URf4V2SDYGJhJnJGqvIIgdECeODCT98wSWDAJ94SSuVpYQUoTcGUIL6L4yNB7j1DFFHSBg==", + "dev": true }, "regenerator-transform": { "version": "0.10.1", "resolved": "https://registry.npmjs.org/regenerator-transform/-/regenerator-transform-0.10.1.tgz", "integrity": "sha512-PJepbvDbuK1xgIgnau7Y90cwaAmO/LCLMI2mPvaXq2heGMR3aWW5/BQvYrhJ8jgmQjXewXvBjzfqKcVOmhjZ6Q==", + "dev": true, "requires": { "babel-runtime": "^6.18.0", "babel-types": "^6.19.0", @@ -6221,6 +6777,7 @@ "version": "0.4.4", "resolved": "https://registry.npmjs.org/regex-cache/-/regex-cache-0.4.4.tgz", "integrity": "sha512-nVIZwtCjkC9YgvWkpM55B5rBhBYRZhAaJbgcFYXXsHnbZ9UZI9nnVWYZpBlCqv9ho2eZryPnWrZGsOdPwVWXWQ==", + "dev": true, "requires": { "is-equal-shallow": "^0.1.3" } @@ -6239,6 +6796,7 @@ "version": "2.0.0", "resolved": "https://registry.npmjs.org/regexpu-core/-/regexpu-core-2.0.0.tgz", "integrity": "sha1-SdA4g3uNz4v6W5pCE5k45uoq4kA=", + "dev": true, "requires": { "regenerate": "^1.2.1", "regjsgen": "^0.2.0", @@ -6246,9 +6804,9 @@ } }, "registry-auth-token": { - "version": "3.3.2", - "resolved": "https://registry.npmjs.org/registry-auth-token/-/registry-auth-token-3.3.2.tgz", - "integrity": "sha512-JL39c60XlzCVgNrO+qq68FoNb56w/m7JYvGR2jT5iR1xBrUA3Mfx5Twk5rqTThPmQKMWydGmq8oFtDlxfrmxnQ==", + "version": "3.4.0", + "resolved": "https://registry.npmjs.org/registry-auth-token/-/registry-auth-token-3.4.0.tgz", + "integrity": "sha512-4LM6Fw8eBQdwMYcES4yTnn2TqIasbXuwDx3um+QRs7S55aMKCBKBxvPXl2RiUjHwuJLTyYfxSpmfSAjQpcuP+A==", "dev": true, "requires": { "rc": "^1.1.6", @@ -6267,12 +6825,14 @@ "regjsgen": { "version": "0.2.0", "resolved": "https://registry.npmjs.org/regjsgen/-/regjsgen-0.2.0.tgz", - "integrity": "sha1-bAFq3qxVT3WCP+N6wFuS1aTtsfc=" + "integrity": "sha1-bAFq3qxVT3WCP+N6wFuS1aTtsfc=", + "dev": true }, "regjsparser": { "version": "0.1.5", "resolved": "https://registry.npmjs.org/regjsparser/-/regjsparser-0.1.5.tgz", "integrity": "sha1-fuj4Tcb6eS0/0K4ijSS9lJ6tIFw=", + "dev": true, "requires": { "jsesc": "~0.5.0" } @@ -6280,22 +6840,26 @@ "remove-trailing-separator": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/remove-trailing-separator/-/remove-trailing-separator-1.1.0.tgz", - "integrity": "sha1-wkvOKig62tW8P1jg1IJJuSN52O8=" + "integrity": "sha1-wkvOKig62tW8P1jg1IJJuSN52O8=", + "dev": true }, "repeat-element": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/repeat-element/-/repeat-element-1.1.2.tgz", - "integrity": "sha1-7wiaF40Ug7quTZPrmLT55OEdmQo=" + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/repeat-element/-/repeat-element-1.1.3.tgz", + "integrity": "sha512-ahGq0ZnV5m5XtZLMb+vP76kcAM5nkLqk0lpqAuojSKGgQtn4eRi4ZZGm2olo2zKFH+sMsWaqOCW1dqAnOru72g==", + "dev": true }, "repeat-string": { "version": "1.6.1", "resolved": "https://registry.npmjs.org/repeat-string/-/repeat-string-1.6.1.tgz", - "integrity": "sha1-jcrkcOHIirwtYA//Sndihtp15jc=" + "integrity": "sha1-jcrkcOHIirwtYA//Sndihtp15jc=", + "dev": true }, "repeating": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/repeating/-/repeating-2.0.1.tgz", "integrity": "sha1-UhTFOpJtNVJwdSf7q0FdvAjQbdo=", + "dev": true, "requires": { "is-finite": "^1.0.0" } @@ -6303,81 +6867,72 @@ "replace-ext": { "version": "0.0.1", "resolved": "https://registry.npmjs.org/replace-ext/-/replace-ext-0.0.1.tgz", - "integrity": "sha1-KbvZIHinOfC8zitO5B6DeVNSKSQ=" + "integrity": "sha1-KbvZIHinOfC8zitO5B6DeVNSKSQ=", + "dev": true }, "req-cwd": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/req-cwd/-/req-cwd-1.0.1.tgz", - "integrity": "sha1-DXOurpJm5penj3l2AZZ352rPD/8=", + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/req-cwd/-/req-cwd-2.0.0.tgz", + "integrity": "sha1-1AgrTURZgDZkD7c93qAe1T20nrw=", "dev": true, "requires": { - "req-from": "^1.0.1" + "req-from": "^2.0.0" } }, "req-from": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/req-from/-/req-from-1.0.1.tgz", - "integrity": "sha1-v4HaUUeUfTLRO5R9wSpYrUWHNQ4=", + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/req-from/-/req-from-2.0.0.tgz", + "integrity": "sha1-10GI5H+TeW9Kpx327jWuaJ8+DnA=", "dev": true, "requires": { - "resolve-from": "^2.0.0" - }, - "dependencies": { - "resolve-from": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-2.0.0.tgz", - "integrity": "sha1-lICrIOlP+h2egKgEx+oUdhGWa1c=", - "dev": true - } + "resolve-from": "^3.0.0" } }, "request": { - "version": "2.85.0", - "resolved": "https://registry.npmjs.org/request/-/request-2.85.0.tgz", - "integrity": "sha512-8H7Ehijd4js+s6wuVPLjwORxD4zeuyjYugprdOXlPSqaApmL/QOy+EB/beICHVCHkGMKNh5rvihb5ov+IDw4mg==", + "version": "2.88.0", + "resolved": "https://registry.npmjs.org/request/-/request-2.88.0.tgz", + "integrity": "sha512-NAqBSrijGLZdM0WZNsInLJpkJokL72XYjUpnB0iwsRgxh7dB6COrHnTBNwN0E+lHDAJzu7kLAkDeY08z2/A0hg==", "requires": { "aws-sign2": "~0.7.0", - "aws4": "^1.6.0", + "aws4": "^1.8.0", "caseless": "~0.12.0", - "combined-stream": "~1.0.5", - "extend": "~3.0.1", + "combined-stream": "~1.0.6", + "extend": "~3.0.2", "forever-agent": "~0.6.1", - "form-data": "~2.3.1", - "har-validator": "~5.0.3", - "hawk": "~6.0.2", + "form-data": "~2.3.2", + "har-validator": "~5.1.0", "http-signature": "~1.2.0", "is-typedarray": "~1.0.0", "isstream": "~0.1.2", "json-stringify-safe": "~5.0.1", - "mime-types": "~2.1.17", - "oauth-sign": "~0.8.2", + "mime-types": "~2.1.19", + "oauth-sign": "~0.9.0", "performance-now": "^2.1.0", - "qs": "~6.5.1", - "safe-buffer": "^5.1.1", - "stringstream": "~0.0.5", - "tough-cookie": "~2.3.3", + "qs": "~6.5.2", + "safe-buffer": "^5.1.2", + "tough-cookie": "~2.4.3", "tunnel-agent": "^0.6.0", - "uuid": "^3.1.0" + "uuid": "^3.3.2" } }, "request-promise-core": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/request-promise-core/-/request-promise-core-1.1.1.tgz", - "integrity": "sha1-Pu4AssWqgyOc+wTFcA2jb4HNCLY=", + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/request-promise-core/-/request-promise-core-1.1.2.tgz", + "integrity": "sha512-UHYyq1MO8GsefGEt7EprS8UrXsm1TxEvFUX1IMTuSLU2Rh7fTIdFtl8xD7JiEYiWU2dl+NYAjCTksTehQUxPag==", "dev": true, "requires": { - "lodash": "^4.13.1" + "lodash": "^4.17.11" } }, "request-promise-native": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/request-promise-native/-/request-promise-native-1.0.5.tgz", - "integrity": "sha1-UoF3D2jgyXGeUWP9P6tIIhX0/aU=", + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/request-promise-native/-/request-promise-native-1.0.7.tgz", + "integrity": "sha512-rIMnbBdgNViL37nZ1b3L/VfPOpSi0TqVDQPAvO6U14lMzOLrt5nilxCQqtDKhZeDiW0/hkCXGoQjhgJd/tCh6w==", "dev": true, "requires": { - "request-promise-core": "1.1.1", - "stealthy-require": "^1.1.0", - "tough-cookie": ">=2.3.3" + "request-promise-core": "1.1.2", + "stealthy-require": "^1.1.1", + "tough-cookie": "^2.3.3" } }, "require-directory": { @@ -6396,17 +6951,18 @@ "integrity": "sha1-l/cXtp1IeE9fUmpsWqj/3aBVpNE=" }, "resolve": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.6.0.tgz", - "integrity": "sha512-mw7JQNu5ExIkcw4LPih0owX/TZXjD/ZUF/ZQ/pDnkw3ZKhDcZZw5klmBlj6gVMwjQ3Pz5Jgu7F3d0jcDVuEWdw==", + "version": "1.10.0", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.10.0.tgz", + "integrity": "sha512-3sUr9aq5OfSg2S9pNtPA9hL1FVEAjvfOC4leW0SNf/mpnaakz2a9femSd6LqAww2RaFctwyf1lCqnTHuF1rxDg==", "requires": { - "path-parse": "^1.0.5" + "path-parse": "^1.0.6" } }, "resolve-cwd": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/resolve-cwd/-/resolve-cwd-2.0.0.tgz", "integrity": "sha1-AKn3OHVW4nA46uIyyqNypqWbZlo=", + "dev": true, "requires": { "resolve-from": "^3.0.0" } @@ -6415,6 +6971,7 @@ "version": "1.0.1", "resolved": "https://registry.npmjs.org/resolve-dir/-/resolve-dir-1.0.1.tgz", "integrity": "sha1-eaQGRMNivoLybv/nOcm7U4IEb0M=", + "dev": true, "requires": { "expand-tilde": "^2.0.0", "global-modules": "^1.0.0" @@ -6423,7 +6980,8 @@ "resolve-from": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-3.0.0.tgz", - "integrity": "sha1-six699nWiBvItuZTM17rywoYh0g=" + "integrity": "sha1-six699nWiBvItuZTM17rywoYh0g=", + "dev": true }, "resolve-url": { "version": "0.2.1", @@ -6435,6 +6993,7 @@ "version": "1.0.2", "resolved": "https://registry.npmjs.org/responselike/-/responselike-1.0.2.tgz", "integrity": "sha1-kYcg7ztjHFZCvgaPFa3lpG9Loec=", + "dev": true, "requires": { "lowercase-keys": "^1.0.0" } @@ -6443,6 +7002,7 @@ "version": "2.0.0", "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-2.0.0.tgz", "integrity": "sha1-n37ih/gv0ybU/RYpI9YhKe7g368=", + "dev": true, "requires": { "onetime": "^2.0.0", "signal-exit": "^3.0.2" @@ -6454,57 +7014,51 @@ "integrity": "sha512-TTlYpa+OL+vMMNG24xSlQGEJ3B/RzEfUlLct7b5G/ytav+wPrplCpVMFuwzXbkecJrb6IYo1iFb0S9v37754mg==", "dev": true }, - "right-align": { - "version": "0.1.3", - "resolved": "https://registry.npmjs.org/right-align/-/right-align-0.1.3.tgz", - "integrity": "sha1-YTObci/mo1FWiSENJOFMlhSGE+8=", - "dev": true, - "optional": true, - "requires": { - "align-text": "^0.1.1" - } - }, "rimraf": { - "version": "2.6.2", - "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.6.2.tgz", - "integrity": "sha512-lreewLK/BlghmxtfH36YYVg1i8IAce4TI7oao75I1g245+6BctqTVQiBP3YUJ9C6DQOXJmkYR9X9fCLtCOJc5w==", + "version": "2.6.3", + "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.6.3.tgz", + "integrity": "sha512-mwqeW5XsA2qAejG46gYdENaxXjx9onRNCfn7L0duuP4hCuTIi/QO7PDK07KJfp1d+izWPrzEJDcSqBa0OZQriA==", "requires": { - "glob": "^7.0.5" + "glob": "^7.1.3" + }, + "dependencies": { + "glob": { + "version": "7.1.3", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.3.tgz", + "integrity": "sha512-vcfuiIxogLV4DlGBHIUOwI0IbrJ8HWPc4MU7HzviGeNho/UJDfi6B5p3sHeWIQ0KGIU0Jpxi5ZHxemQfLkkAwQ==", + "requires": { + "fs.realpath": "^1.0.0", + "inflight": "^1.0.4", + "inherits": "2", + "minimatch": "^3.0.4", + "once": "^1.3.0", + "path-is-absolute": "^1.0.0" + } + } } }, "run-async": { "version": "2.3.0", "resolved": "https://registry.npmjs.org/run-async/-/run-async-2.3.0.tgz", "integrity": "sha1-A3GrSuC91yDUFm19/aZP96RFpsA=", + "dev": true, "requires": { "is-promise": "^2.1.0" } }, - "rx-lite": { - "version": "4.0.8", - "resolved": "https://registry.npmjs.org/rx-lite/-/rx-lite-4.0.8.tgz", - "integrity": "sha1-Cx4Rr4vESDbwSmQH6S2kJGe3lEQ=" - }, - "rx-lite-aggregates": { - "version": "4.0.8", - "resolved": "https://registry.npmjs.org/rx-lite-aggregates/-/rx-lite-aggregates-4.0.8.tgz", - "integrity": "sha1-dTuHqJoRyVRnxKwWJsTvxOBcZ74=", - "requires": { - "rx-lite": "*" - } - }, "rxjs": { - "version": "5.5.7", - "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-5.5.7.tgz", - "integrity": "sha512-Hxo2ac8gRQjwjtKgukMIwBRbq5+KAeEV5hXM4obYBOAghev41bDQWgFH4svYiU9UnQ5kNww2LgfyBdevCd2HXA==", + "version": "5.5.12", + "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-5.5.12.tgz", + "integrity": "sha512-xx2itnL5sBbqeeiVgNPVuQQ1nC8Jp2WfNJhXWHmElW9YmrpS9UVnNzhP3EH3HFqexO5Tlp8GhYY+WEcqcVMvGw==", + "dev": true, "requires": { "symbol-observable": "1.0.1" } }, "safe-buffer": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz", - "integrity": "sha512-kKvNJn6Mm93gAczWVJg7wH+wGYWNrDHdWvpUmHyEsgCtIwwo3bqPtV4tR5tuPaUhTOo/kvhVwd8XwwOllGYkbg==" + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", + "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==" }, "safe-regex": { "version": "1.1.0", @@ -6515,15 +7069,21 @@ "ret": "~0.1.10" } }, + "safer-buffer": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", + "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==" + }, "scoped-regex": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/scoped-regex/-/scoped-regex-1.0.0.tgz", - "integrity": "sha1-o0a7Gs1CB65wvXwMfKnlZra63bg=" + "integrity": "sha1-o0a7Gs1CB65wvXwMfKnlZra63bg=", + "dev": true }, "semver": { - "version": "5.5.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.5.0.tgz", - "integrity": "sha512-4SJ3dm0WAwWy/NVeioZh5AntkdJoWKxHxcmyP622fOkgHa4z3R0TdBJICINyaSDE6uNwVc8gZr+ZinwZAH4xIA==" + "version": "5.7.0", + "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.0.tgz", + "integrity": "sha512-Ya52jSX2u7QKghxeoFGpLwCtGlt7j0oY9DYb5apt9nPlJ42ID+ulTXESnt/qAQcoSERyZ5sl3LDIOw0nAn/5DA==" }, "semver-diff": { "version": "2.1.0", @@ -6597,12 +7157,6 @@ "resolved": "https://registry.npmjs.org/set-blocking/-/set-blocking-2.0.0.tgz", "integrity": "sha1-BF+XgtARrppoA93TgrJDkrPYkPc=" }, - "set-immediate-shim": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/set-immediate-shim/-/set-immediate-shim-1.0.1.tgz", - "integrity": "sha1-SysbJ+uAip+NzEgaWOXlb1mfP2E=", - "dev": true - }, "set-value": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/set-value/-/set-value-2.0.0.tgz", @@ -6642,17 +7196,18 @@ } }, "sha3": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/sha3/-/sha3-1.2.0.tgz", - "integrity": "sha1-aYnxtwpJhwWHajc+LGKs6WqpOZo=", + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/sha3/-/sha3-1.2.2.tgz", + "integrity": "sha1-pmxQmN5MJbyIM27ItIF9AFvKe6k=", "requires": { - "nan": "^2.0.5" + "nan": "2.10.0" } }, "shebang-command": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-1.2.0.tgz", "integrity": "sha1-RKrGW2lbAzmJaMOfNj/uXer98eo=", + "dev": true, "requires": { "shebang-regex": "^1.0.0" } @@ -6660,12 +7215,14 @@ "shebang-regex": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-1.0.0.tgz", - "integrity": "sha1-2kL0l0DAtC2yypcoVxyxkMmO/qM=" + "integrity": "sha1-2kL0l0DAtC2yypcoVxyxkMmO/qM=", + "dev": true }, "shelljs": { - "version": "0.8.1", - "resolved": "https://registry.npmjs.org/shelljs/-/shelljs-0.8.1.tgz", - "integrity": "sha512-YA/iYtZpzFe5HyWVGrb02FjPxc4EMCfpoU/Phg9fQoyMC72u9598OUBrsU8IrtwAKG0tO8IYaqbaLIw+k3IRGA==", + "version": "0.7.8", + "resolved": "https://registry.npmjs.org/shelljs/-/shelljs-0.7.8.tgz", + "integrity": "sha1-3svPh0sNHl+3LhSxZKloMEjprLM=", + "dev": true, "requires": { "glob": "^7.0.0", "interpret": "^1.0.0", @@ -6681,7 +7238,8 @@ "signal-exit": { "version": "3.0.2", "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.2.tgz", - "integrity": "sha1-tf3AjxKH6hF4Yo5BXiUTK3NkbG0=" + "integrity": "sha1-tf3AjxKH6hF4Yo5BXiUTK3NkbG0=", + "dev": true }, "simple-concat": { "version": "1.0.0", @@ -6689,9 +7247,9 @@ "integrity": "sha1-c0TLuLbib7J9ZrL8hvn21Zl1IcY=" }, "simple-get": { - "version": "2.7.0", - "resolved": "https://registry.npmjs.org/simple-get/-/simple-get-2.7.0.tgz", - "integrity": "sha512-RkE9rGPHcxYZ/baYmgJtOSM63vH0Vyq+ma5TijBcLla41SWlh8t6XYIGMR/oeZcmr+/G8k+zrClkkVrtnQ0esg==", + "version": "2.8.1", + "resolved": "https://registry.npmjs.org/simple-get/-/simple-get-2.8.1.tgz", + "integrity": "sha512-lSSHRSw3mQNUGPAYRqo7xy9dhKmxFXIjLjp4KHpf99GEH2VH7C3AM+Qfx6du6jhfUi6Vm7XnbEVEf7Wb6N8jRw==", "requires": { "decompress-response": "^3.3.0", "once": "^1.3.1", @@ -6701,17 +7259,20 @@ "slash": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/slash/-/slash-1.0.0.tgz", - "integrity": "sha1-xB8vbDn8FtHNF61LXYlhFK5HDVU=" + "integrity": "sha1-xB8vbDn8FtHNF61LXYlhFK5HDVU=", + "dev": true }, "slice-ansi": { "version": "0.0.4", "resolved": "https://registry.npmjs.org/slice-ansi/-/slice-ansi-0.0.4.tgz", - "integrity": "sha1-7b+JA/ZvfOL46v1s7tZeJkyDGzU=" + "integrity": "sha1-7b+JA/ZvfOL46v1s7tZeJkyDGzU=", + "dev": true }, "slide": { "version": "1.1.6", "resolved": "https://registry.npmjs.org/slide/-/slide-1.1.6.tgz", - "integrity": "sha1-VusCfWW00tzmyy4tMsTUr8nh1wc=" + "integrity": "sha1-VusCfWW00tzmyy4tMsTUr8nh1wc=", + "dev": true }, "snapdragon": { "version": "0.8.2", @@ -6729,6 +7290,15 @@ "use": "^3.1.0" }, "dependencies": { + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, + "requires": { + "ms": "2.0.0" + } + }, "define-property": { "version": "0.2.5", "resolved": "https://registry.npmjs.org/define-property/-/define-property-0.2.5.tgz", @@ -6820,14 +7390,6 @@ } } }, - "sntp": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/sntp/-/sntp-2.1.0.tgz", - "integrity": "sha512-FL1b58BDrqS3A11lJ0zEdnJ3UOKqVxawAkF3k7F0CVN7VQ34aZrV+G8BZ1WC9ZL7NyrwsW0oviwsWDgRuVYtJg==", - "requires": { - "hoek": "4.x.x" - } - }, "sol-explore": { "version": "1.6.2", "resolved": "https://registry.npmjs.org/sol-explore/-/sol-explore-1.6.2.tgz", @@ -6863,131 +7425,42 @@ "web3": "^0.18.4" }, "dependencies": { - "bignumber.js": { - "version": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", - "from": "bignumber.js@git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", - "dev": true - }, - "commander": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-2.3.0.tgz", - "integrity": "sha1-/UMOiJgy7DU7ms0d4hfBHLPu+HM=", - "dev": true - }, - "debug": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.2.0.tgz", - "integrity": "sha1-+HBX6ZWxofauaklgZkE3vFbwOdo=", - "dev": true, - "requires": { - "ms": "0.7.1" - } - }, - "diff": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/diff/-/diff-1.4.0.tgz", - "integrity": "sha1-fyjS657nsVqX79ic5j3P2qPMur8=", - "dev": true - }, - "escape-string-regexp": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.2.tgz", - "integrity": "sha1-Tbwv5nTnGUnK8/smlc5/LcHZqNE=", - "dev": true - }, - "minimatch": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-0.3.0.tgz", - "integrity": "sha1-J12O2qxPG7MyZHIInnlJyDlGmd0=", - "dev": true, - "requires": { - "lru-cache": "2", - "sigmund": "~1.0.0" - } - }, - "mocha": { - "version": "2.5.3", - "resolved": "https://registry.npmjs.org/mocha/-/mocha-2.5.3.tgz", - "integrity": "sha1-FhvlvetJZ3HrmzV0UFC2IrWu/Fg=", - "dev": true, - "requires": { - "commander": "2.3.0", - "debug": "2.2.0", - "diff": "1.4.0", - "escape-string-regexp": "1.0.2", - "glob": "3.2.11", - "growl": "1.9.2", - "jade": "0.26.3", - "mkdirp": "0.5.1", - "supports-color": "1.2.0", - "to-iso-string": "0.0.2" - }, - "dependencies": { - "glob": { - "version": "3.2.11", - "resolved": "https://registry.npmjs.org/glob/-/glob-3.2.11.tgz", - "integrity": "sha1-Spc/Y1uRkPcV0QmH1cAP0oFevj0=", - "dev": true, - "requires": { - "inherits": "2", - "minimatch": "0.3" - } - } - } - }, - "ms": { - "version": "0.7.1", - "resolved": "https://registry.npmjs.org/ms/-/ms-0.7.1.tgz", - "integrity": "sha1-nNE8A62/8ltl7/3nzoZO6VIBcJg=", - "dev": true - }, - "shelljs": { - "version": "0.7.8", - "resolved": "https://registry.npmjs.org/shelljs/-/shelljs-0.7.8.tgz", - "integrity": "sha1-3svPh0sNHl+3LhSxZKloMEjprLM=", + "req-cwd": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/req-cwd/-/req-cwd-1.0.1.tgz", + "integrity": "sha1-DXOurpJm5penj3l2AZZ352rPD/8=", "dev": true, "requires": { - "glob": "^7.0.0", - "interpret": "^1.0.0", - "rechoir": "^0.6.2" + "req-from": "^1.0.1" } }, - "solidity-parser-sc": { - "version": "0.4.7", - "resolved": "https://registry.npmjs.org/solidity-parser-sc/-/solidity-parser-sc-0.4.7.tgz", - "integrity": "sha512-wbX2806sm6thZME1aniqLcLH9HYwNwuKke6aw/FEgupCvoT9Iq5PdwuN9OyHWKGBOVeczpM5tCrnRXWNQ04YVw==", + "req-from": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/req-from/-/req-from-1.0.1.tgz", + "integrity": "sha1-v4HaUUeUfTLRO5R9wSpYrUWHNQ4=", "dev": true, "requires": { - "mocha": "^2.4.5", - "pegjs": "^0.10.0", - "yargs": "^4.6.0" + "resolve-from": "^2.0.0" } }, - "supports-color": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-1.2.0.tgz", - "integrity": "sha1-/x7R5hFp0Gs88tWI4YixjYhH4X4=", + "resolve-from": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-2.0.0.tgz", + "integrity": "sha1-lICrIOlP+h2egKgEx+oUdhGWa1c=", "dev": true - }, - "web3": { - "version": "0.18.4", - "resolved": "https://registry.npmjs.org/web3/-/web3-0.18.4.tgz", - "integrity": "sha1-gewXhBRUkfLqqJVbMcBgSeB8Xn0=", - "dev": true, - "requires": { - "bignumber.js": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", - "crypto-js": "^3.1.4", - "utf8": "^2.1.1", - "xhr2": "*", - "xmlhttprequest": "*" - } } } }, - "solidity-parser": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/solidity-parser/-/solidity-parser-0.4.0.tgz", - "integrity": "sha1-o0PxPac8kWgyeQNGgOgMSR3jQPo=", + "solidity-parser-antlr": { + "version": "0.2.15", + "resolved": "https://registry.npmjs.org/solidity-parser-antlr/-/solidity-parser-antlr-0.2.15.tgz", + "integrity": "sha512-EzRI8/TR/ljTXkZAyAjb0w4G20wH2XM7pcNf87ifdV825AbUv7DkY7HmiZCTj6NeKtIx8Y1s0NZWPbj+JTp8Zw==", + "dev": true + }, + "solidity-parser-sc": { + "version": "0.4.7", + "resolved": "https://registry.npmjs.org/solidity-parser-sc/-/solidity-parser-sc-0.4.7.tgz", + "integrity": "sha512-wbX2806sm6thZME1aniqLcLH9HYwNwuKke6aw/FEgupCvoT9Iq5PdwuN9OyHWKGBOVeczpM5tCrnRXWNQ04YVw==", "dev": true, "requires": { "mocha": "^2.4.5", @@ -7032,6 +7505,18 @@ "minimatch": "0.3" } }, + "growl": { + "version": "1.9.2", + "resolved": "https://registry.npmjs.org/growl/-/growl-1.9.2.tgz", + "integrity": "sha1-Dqd0NxXbjY3ixe3hd14bRayFwC8=", + "dev": true + }, + "lru-cache": { + "version": "2.7.3", + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-2.7.3.tgz", + "integrity": "sha1-bUUk6LlV+V1PW1iFHOId1y+06VI=", + "dev": true + }, "minimatch": { "version": "0.3.0", "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-0.3.0.tgz", @@ -7074,16 +7559,11 @@ } } }, - "solidity-parser-antlr": { - "version": "0.2.15", - "resolved": "https://registry.npmjs.org/solidity-parser-antlr/-/solidity-parser-antlr-0.2.15.tgz", - "integrity": "sha512-EzRI8/TR/ljTXkZAyAjb0w4G20wH2XM7pcNf87ifdV825AbUv7DkY7HmiZCTj6NeKtIx8Y1s0NZWPbj+JTp8Zw==", - "dev": true - }, "sort-keys": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/sort-keys/-/sort-keys-2.0.0.tgz", "integrity": "sha1-ZYU1WEhh7JfXMNbPQYIuH1ZoQSg=", + "dev": true, "requires": { "is-plain-obj": "^1.0.0" } @@ -7091,15 +7571,16 @@ "source-map": { "version": "0.5.7", "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", - "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=" + "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=", + "dev": true }, "source-map-resolve": { - "version": "0.5.1", - "resolved": "https://registry.npmjs.org/source-map-resolve/-/source-map-resolve-0.5.1.tgz", - "integrity": "sha512-0KW2wvzfxm8NCTb30z0LMNyPqWCdDGE2viwzUaucqJdkTRXtZiSY3I+2A6nVAjmdOy0I4gU8DwnVVGsk9jvP2A==", + "version": "0.5.2", + "resolved": "https://registry.npmjs.org/source-map-resolve/-/source-map-resolve-0.5.2.tgz", + "integrity": "sha512-MjqsvNwyz1s0k81Goz/9vRBe9SZdB09Bdw+/zYyO+3CuPk6fouTaxscHkgtE8jKvf01kVfl8riHzERQ/kefaSA==", "dev": true, "requires": { - "atob": "^2.0.0", + "atob": "^2.1.1", "decode-uri-component": "^0.2.0", "resolve-url": "^0.2.1", "source-map-url": "^0.4.0", @@ -7107,17 +7588,20 @@ } }, "source-map-support": { - "version": "0.5.4", - "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.4.tgz", - "integrity": "sha512-PETSPG6BjY1AHs2t64vS2aqAgu6dMIMXJULWFBGbh2Gr8nVLbCFDo6i/RMMvviIQ2h1Z8+5gQhVKSn2je9nmdg==", + "version": "0.5.11", + "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.11.tgz", + "integrity": "sha512-//sajEx/fGL3iw6fltKMdPvy8kL3kJ2O3iuYlRoT3k9Kb4BjOoZ+BZzaNHeuaruSt+Kf3Zk9tnfAQg9/AJqUVQ==", + "dev": true, "requires": { + "buffer-from": "^1.0.0", "source-map": "^0.6.0" }, "dependencies": { "source-map": { "version": "0.6.1", "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", - "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==" + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", + "dev": true } } }, @@ -7128,32 +7612,33 @@ "dev": true }, "spdx-correct": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/spdx-correct/-/spdx-correct-1.0.2.tgz", - "integrity": "sha1-SzBz2TP/UfORLwOsVRlJikFQ20A=", + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/spdx-correct/-/spdx-correct-3.1.0.tgz", + "integrity": "sha512-lr2EZCctC2BNR7j7WzJ2FpDznxky1sjfxvvYEyzxNyb6lZXHODmEoJeFu4JupYlkfha1KZpJyoqiJ7pgA1qq8Q==", "requires": { - "spdx-license-ids": "^1.0.2" + "spdx-expression-parse": "^3.0.0", + "spdx-license-ids": "^3.0.0" } }, - "spdx-expression-parse": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/spdx-expression-parse/-/spdx-expression-parse-1.0.4.tgz", - "integrity": "sha1-m98vIOH0DtRH++JzJmGR/O1RYmw=" - }, - "spdx-license-ids": { - "version": "1.2.2", - "resolved": "https://registry.npmjs.org/spdx-license-ids/-/spdx-license-ids-1.2.2.tgz", - "integrity": "sha1-yd96NCRZSt5r0RkA1ZZpbcBrrFc=" + "spdx-exceptions": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/spdx-exceptions/-/spdx-exceptions-2.2.0.tgz", + "integrity": "sha512-2XQACfElKi9SlVb1CYadKDXvoajPgBVPn/gOQLrTvHdElaVhr7ZEbqJaRnJLVNeaI4cMEAgVCeBMKF6MWRDCRA==" }, - "split": { - "version": "0.3.3", - "resolved": "https://registry.npmjs.org/split/-/split-0.3.3.tgz", - "integrity": "sha1-zQ7qXmOiEd//frDwkcQTPi0N0o8=", - "dev": true, + "spdx-expression-parse": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/spdx-expression-parse/-/spdx-expression-parse-3.0.0.tgz", + "integrity": "sha512-Yg6D3XpRD4kkOmTpdgbUiEJFKghJH03fiC1OPll5h/0sO6neh2jqRDVHOQ4o/LMea0tgCkbMgea5ip/e+MkWyg==", "requires": { - "through": "2" + "spdx-exceptions": "^2.1.0", + "spdx-license-ids": "^3.0.0" } }, + "spdx-license-ids": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/spdx-license-ids/-/spdx-license-ids-3.0.3.tgz", + "integrity": "sha512-uBIcIl3Ih6Phe3XHK1NqboJLdGfwr1UN3k6wSD1dZpmPsIkb8AGNbZYJ1fOBk834+Gxy8rpfDxrS6XLEMZMY2g==" + }, "split-string": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/split-string/-/split-string-3.1.0.tgz", @@ -7170,9 +7655,9 @@ "dev": true }, "sshpk": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/sshpk/-/sshpk-1.14.1.tgz", - "integrity": "sha1-Ew9Zde3a2WPx1W+SuaxsUfqfg+s=", + "version": "1.16.1", + "resolved": "https://registry.npmjs.org/sshpk/-/sshpk-1.16.1.tgz", + "integrity": "sha512-HXXqVUq7+pcKeLqqZj6mHFUMvXtOJt1uoUx09pFW6011inTMxqI8BA8PM95myrIyyKwdnzjdFjLiE6KBPVtJIg==", "requires": { "asn1": "~0.2.3", "assert-plus": "^1.0.0", @@ -7181,6 +7666,7 @@ "ecc-jsbn": "~0.1.1", "getpass": "^0.1.1", "jsbn": "~0.1.0", + "safer-buffer": "^2.0.2", "tweetnacl": "~0.14.0" } }, @@ -7216,23 +7702,6 @@ "integrity": "sha1-NbCYdbT/SfJqd35QmzCQoyJr8ks=", "dev": true }, - "stream-combiner": { - "version": "0.0.4", - "resolved": "https://registry.npmjs.org/stream-combiner/-/stream-combiner-0.0.4.tgz", - "integrity": "sha1-TV5DPBhSYd3mI8o/RMWGvPXErRQ=", - "dev": true, - "requires": { - "duplexer": "~0.1.1" - } - }, - "stream-to-observable": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/stream-to-observable/-/stream-to-observable-0.2.0.tgz", - "integrity": "sha1-WdbqOT2HwsDdrBCqDVYbxrpvDhA=", - "requires": { - "any-observable": "^0.2.0" - } - }, "strict-uri-encode": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/strict-uri-encode/-/strict-uri-encode-1.1.0.tgz", @@ -7241,7 +7710,8 @@ "string-template": { "version": "0.2.1", "resolved": "https://registry.npmjs.org/string-template/-/string-template-0.2.1.tgz", - "integrity": "sha1-QpMuWYo1LQH8IuwzZ9nYTuxsmt0=" + "integrity": "sha1-QpMuWYo1LQH8IuwzZ9nYTuxsmt0=", + "dev": true }, "string-width": { "version": "1.0.2", @@ -7253,19 +7723,25 @@ "strip-ansi": "^3.0.0" } }, + "string.prototype.trim": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/string.prototype.trim/-/string.prototype.trim-1.1.2.tgz", + "integrity": "sha1-0E3iyJ4Tf019IG8Ia17S+ua+jOo=", + "requires": { + "define-properties": "^1.1.2", + "es-abstract": "^1.5.0", + "function-bind": "^1.0.2" + } + }, "string_decoder": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", - "integrity": "sha512-4AH6Z5fzNNBcH+6XDMfA/BTt87skxqJlO0lAh3Dker5zThcAxG6mKz+iGu308UKoPPQ8Dcqx/4JhujzltRa+hQ==", + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", + "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", + "dev": true, "requires": { "safe-buffer": "~5.1.0" } }, - "stringstream": { - "version": "0.0.5", - "resolved": "https://registry.npmjs.org/stringstream/-/stringstream-0.0.5.tgz", - "integrity": "sha1-TkhM1N5aC7vuGORjB3EKioFiGHg=" - }, "strip-ansi": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", @@ -7286,6 +7762,7 @@ "version": "2.0.0", "resolved": "https://registry.npmjs.org/strip-bom-stream/-/strip-bom-stream-2.0.0.tgz", "integrity": "sha1-+H217yYT9paKpUWr/h7HKLaoKco=", + "dev": true, "requires": { "first-chunk-stream": "^2.0.0", "strip-bom": "^2.0.0" @@ -7294,7 +7771,8 @@ "strip-eof": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/strip-eof/-/strip-eof-1.0.0.tgz", - "integrity": "sha1-u0P/VZim6wXYm1n80SnJgzE2Br8=" + "integrity": "sha1-u0P/VZim6wXYm1n80SnJgzE2Br8=", + "dev": true }, "strip-hex-prefix": { "version": "1.0.0", @@ -7311,23 +7789,23 @@ "dev": true }, "supports-color": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-3.1.2.tgz", - "integrity": "sha1-cqJiiU2dQIuVbKBf83su2KbiotU=", - "dev": true, + "version": "4.4.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-4.4.0.tgz", + "integrity": "sha512-rKC3+DyXWgK0ZLKwmRsrkyHVZAjNkfzeehuFWdGGcqGDTZFH73+RH6S/RDAAxl9GusSjZSUWYLmT9N5pzXFOXQ==", "requires": { - "has-flag": "^1.0.0" + "has-flag": "^2.0.0" } }, "symbol-observable": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/symbol-observable/-/symbol-observable-1.0.1.tgz", - "integrity": "sha1-g0D8RwLDEi310iKI+IKD9RPT/dQ=" + "integrity": "sha1-g0D8RwLDEi310iKI+IKD9RPT/dQ=", + "dev": true }, "sync-request": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/sync-request/-/sync-request-6.0.0.tgz", - "integrity": "sha512-jGNIAlCi9iU4X3Dm4oQnNQshDD3h0/1A7r79LyqjbjUnj69sX6mShAXlhRXgImsfVKtTcnra1jfzabdZvp+Lmw==", + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/sync-request/-/sync-request-6.1.0.tgz", + "integrity": "sha512-8fjNkrNlNCrVc/av+Jn+xxqfCjYaBoHqCsDz6mt030UMxJGr+GSfCV1dQt2gRtlL63+VPidwDVLr7V2OcTSdRw==", "dev": true, "requires": { "http-response-object": "^3.0.1", @@ -7345,14 +7823,16 @@ } }, "tapable": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/tapable/-/tapable-1.0.0.tgz", - "integrity": "sha512-dQRhbNQkRnaqauC7WqSJ21EEksgT0fYZX2lqXzGkpo8JNig9zGZTYoMGvyI2nWmXlE2VSVXVDu7wLVGu/mQEsg==" + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/tapable/-/tapable-1.1.1.tgz", + "integrity": "sha512-9I2ydhj8Z9veORCw5PRm4u9uebCn0mcCa6scWoNcbZ6dAtoo2618u9UUzxgmsCOreJpqDDuv61LvwofW7hLcBA==", + "dev": true }, "temp": { "version": "0.8.3", "resolved": "https://registry.npmjs.org/temp/-/temp-0.8.3.tgz", "integrity": "sha1-4Ma8TSa5AxJEEOT+2BEDAU38H1k=", + "dev": true, "requires": { "os-tmpdir": "^1.0.0", "rimraf": "~2.2.6" @@ -7361,7 +7841,8 @@ "rimraf": { "version": "2.2.8", "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.2.8.tgz", - "integrity": "sha1-5Dm+Kq7jJzIZUnMPmaiSnk/FBYI=" + "integrity": "sha1-5Dm+Kq7jJzIZUnMPmaiSnk/FBYI=", + "dev": true } } }, @@ -7377,17 +7858,19 @@ "text-table": { "version": "0.2.0", "resolved": "https://registry.npmjs.org/text-table/-/text-table-0.2.0.tgz", - "integrity": "sha1-f17oI66AUgfACvLfSoTsP8+lcLQ=" + "integrity": "sha1-f17oI66AUgfACvLfSoTsP8+lcLQ=", + "dev": true }, "textextensions": { - "version": "2.2.0", - "resolved": "https://registry.npmjs.org/textextensions/-/textextensions-2.2.0.tgz", - "integrity": "sha512-j5EMxnryTvKxwH2Cq+Pb43tsf6sdEgw6Pdwxk83mPaq0ToeFJt6WE4J3s5BqY7vmjlLgkgXvhtXUxo80FyBhCA==" + "version": "2.4.0", + "resolved": "https://registry.npmjs.org/textextensions/-/textextensions-2.4.0.tgz", + "integrity": "sha512-qftQXnX1DzpSV8EddtHIT0eDDEiBF8ywhFYR2lI9xrGtxqKN+CvLXhACeCIGbCpQfxxERbrkZEFb8cZcDKbVZA==", + "dev": true }, "then-request": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/then-request/-/then-request-6.0.0.tgz", - "integrity": "sha512-xA+7uEMc+jsQIoyySJ93Ad08Kuqnik7u6jLS5hR91Z3smAoCfL3M8/MqMlobAa9gzBfO9pA88A/AntfepkkMJQ==", + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/then-request/-/then-request-6.0.2.tgz", + "integrity": "sha512-3ZBiG7JvP3wbDzA9iNY5zJQcHL4jn/0BWtXIkagfz7QgOL/LqjCEOBQuJNZfu0XYnv5JhKh+cDxCPM4ILrqruA==", "dev": true, "requires": { "@types/concat-stream": "^1.6.0", @@ -7397,16 +7880,16 @@ "caseless": "~0.12.0", "concat-stream": "^1.6.0", "form-data": "^2.2.0", - "http-basic": "^7.0.0", + "http-basic": "^8.1.1", "http-response-object": "^3.0.1", "promise": "^8.0.0", "qs": "^6.4.0" }, "dependencies": { "@types/node": { - "version": "8.10.36", - "resolved": "https://registry.npmjs.org/@types/node/-/node-8.10.36.tgz", - "integrity": "sha512-SL6KhfM7PTqiFmbCW3eVNwVBZ+88Mrzbuvn9olPsfv43mbiWaFY+nRcz/TGGku0/lc2FepdMbImdMY1JrQ+zbw==", + "version": "8.10.45", + "resolved": "https://registry.npmjs.org/@types/node/-/node-8.10.45.tgz", + "integrity": "sha512-tGVTbA+i3qfXsLbq9rEq/hezaHY55QxQLeXQL2ejNgFAxxrgu8eMmYIOsRcl7hN1uTLVsKOOYacV/rcJM3sfgQ==", "dev": true } } @@ -7414,14 +7897,16 @@ "through": { "version": "2.3.8", "resolved": "https://registry.npmjs.org/through/-/through-2.3.8.tgz", - "integrity": "sha1-DdTJ/6q8NXlgsbckEV1+Doai4fU=" + "integrity": "sha1-DdTJ/6q8NXlgsbckEV1+Doai4fU=", + "dev": true }, "through2": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/through2/-/through2-2.0.3.tgz", - "integrity": "sha1-AARWmzfHx0ujnEPzzteNGtlBQL4=", + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/through2/-/through2-2.0.5.tgz", + "integrity": "sha512-/mrRod8xqpA+IHSLyGCQ2s8SPHiCDEeQJSep1jqLYeEUClOFG2Qsh+4FU6G9VeqpZnGW/Su8LQGc4YKni5rYSQ==", + "dev": true, "requires": { - "readable-stream": "^2.1.5", + "readable-stream": "~2.3.6", "xtend": "~4.0.1" } }, @@ -7434,6 +7919,7 @@ "version": "0.0.33", "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.0.33.tgz", "integrity": "sha512-jRCJlojKnZ3addtTOjdIqoRuPEKBvNXcGYqzO6zWZX8KfKEpnGY5jfggJQ3EjKuu8D4bJRr0y+cYJFmYbImXGw==", + "dev": true, "requires": { "os-tmpdir": "~1.0.2" } @@ -7441,7 +7927,8 @@ "to-fast-properties": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/to-fast-properties/-/to-fast-properties-1.0.3.tgz", - "integrity": "sha1-uDVx+k2MJbguIxsG46MFXeTKGkc=" + "integrity": "sha1-uDVx+k2MJbguIxsG46MFXeTKGkc=", + "dev": true }, "to-iso-string": { "version": "0.0.2", @@ -7501,140 +7988,47 @@ } }, "tough-cookie": { - "version": "2.3.4", - "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.3.4.tgz", - "integrity": "sha512-TZ6TTfI5NtZnuyy/Kecv+CnoROnyXn2DN97LontgQpCwsX2XyLYCC0ENhYkehSOwAp8rTQKc/NUIF7BkQ5rKLA==", + "version": "2.4.3", + "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.4.3.tgz", + "integrity": "sha512-Q5srk/4vDM54WJsJio3XNn6K2sCG+CQ8G5Wz6bZhRZoAe/+TxjWB/GlFAnYEbkYVlON9FMk/fE3h2RLpPXo4lQ==", "requires": { + "psl": "^1.1.24", "punycode": "^1.4.1" - } - }, - "trim": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/trim/-/trim-0.0.1.tgz", - "integrity": "sha1-WFhUf2spB1fulczMZm+1AITEYN0=" - }, - "trim-right": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/trim-right/-/trim-right-1.0.1.tgz", - "integrity": "sha1-yy4SAwZ+DI3h9hQJS5/kVwTqYAM=" - }, - "truffle": { - "version": "4.1.11", - "resolved": "https://registry.npmjs.org/truffle/-/truffle-4.1.11.tgz", - "integrity": "sha512-VNhc6jexZeM92sNJJr4U8ln3uJ/mJEQO/0y9ZLYc4pccyIskPtl+3r4mzymgGM/Mq5v6MpoQVD6NZgHUVKX+Dw==", - "requires": { - "mocha": "^4.1.0", - "original-require": "^1.0.1", - "solc": "0.4.24" - } - }, - "truffle-blockchain-utils": { - "version": "0.0.4", - "resolved": "https://registry.npmjs.org/truffle-blockchain-utils/-/truffle-blockchain-utils-0.0.4.tgz", - "integrity": "sha512-wgRrhwqh0aea08Hz28hUV4tuF2uTVQH/e9kBou+WK04cqrutB5cxQVQ6HGjeZLltxBYOFvhrGOOq4l3WJFnPEA==", - "dev": true - }, - "truffle-config": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/truffle-config/-/truffle-config-1.0.4.tgz", - "integrity": "sha512-E8pvJNAIjs7LNsjkYeS2dgoOnLoSBrTwb1xF5lJwfvZmGMFpKvVL1sa5jpFxozpf/WkRn/rfxy8zTdb3pq16jA==", - "dev": true, - "requires": { - "find-up": "^2.1.0", - "lodash": "^4.17.4", - "original-require": "^1.0.0", - "truffle-error": "^0.0.2", - "truffle-provider": "^0.0.4" - }, - "dependencies": { - "find-up": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", - "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", - "dev": true, - "requires": { - "locate-path": "^2.0.0" - } - } - } - }, - "truffle-contract": { - "version": "3.0.4", - "resolved": "https://registry.npmjs.org/truffle-contract/-/truffle-contract-3.0.4.tgz", - "integrity": "sha512-/1LCtJFf5Jvm5Rv88T0d/rZSKvaiW/yO1SHXLGJgKzLsiG1F/2spFs4HrI1mRxP00opfrYXloEmLtkVV/kcndQ==", - "dev": true, - "requires": { - "ethjs-abi": "0.1.8", - "truffle-blockchain-utils": "^0.0.4", - "truffle-contract-schema": "^2.0.0", - "truffle-error": "0.0.2", - "web3": "^0.20.1" - }, - "dependencies": { - "ethjs-abi": { - "version": "0.1.8", - "resolved": "https://registry.npmjs.org/ethjs-abi/-/ethjs-abi-0.1.8.tgz", - "integrity": "sha1-zSiFg+1ijN+tr4re+juh28vKbBg=", - "dev": true, - "requires": { - "bn.js": "4.11.6", - "js-sha3": "0.5.5", - "number-to-bn": "1.7.0" - } - } - } - }, - "truffle-contract-schema": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/truffle-contract-schema/-/truffle-contract-schema-2.0.0.tgz", - "integrity": "sha512-nLlspmu1GKDaluWksBwitHi/7Z3IpRjmBYeO9N+T1nVJD2V4IWJaptCKP1NqnPiJA+FChB7+F7pI6Br51/FtXQ==", - "dev": true, - "requires": { - "ajv": "^5.1.1", - "crypto-js": "^3.1.9-1", - "debug": "^3.1.0" }, "dependencies": { - "crypto-js": { - "version": "3.1.9-1", - "resolved": "https://registry.npmjs.org/crypto-js/-/crypto-js-3.1.9-1.tgz", - "integrity": "sha1-/aGedh/Ad+Af+/3G6f38WeiAbNg=", - "dev": true - }, - "debug": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", - "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", - "dev": true, - "requires": { - "ms": "2.0.0" - } + "punycode": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/punycode/-/punycode-1.4.1.tgz", + "integrity": "sha1-wNWmOycYgArY4esPpSachN1BhF4=" } } }, - "truffle-error": { - "version": "0.0.2", - "resolved": "https://registry.npmjs.org/truffle-error/-/truffle-error-0.0.2.tgz", - "integrity": "sha1-AbGJt4UFVmrhaJwjnHyi3RIc/kw=", + "trim-right": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/trim-right/-/trim-right-1.0.1.tgz", + "integrity": "sha1-yy4SAwZ+DI3h9hQJS5/kVwTqYAM=", "dev": true }, - "truffle-expect": { - "version": "0.0.3", - "resolved": "https://registry.npmjs.org/truffle-expect/-/truffle-expect-0.0.3.tgz", - "integrity": "sha1-m3XO80O9WW5+XbyHj18bLjGKlEw=", - "dev": true + "truffle": { + "version": "4.1.11", + "resolved": "https://registry.npmjs.org/truffle/-/truffle-4.1.11.tgz", + "integrity": "sha512-VNhc6jexZeM92sNJJr4U8ln3uJ/mJEQO/0y9ZLYc4pccyIskPtl+3r4mzymgGM/Mq5v6MpoQVD6NZgHUVKX+Dw==", + "requires": { + "mocha": "^4.1.0", + "original-require": "^1.0.1", + "solc": "0.4.24" + } }, "truffle-flattener": { - "version": "1.2.3", - "resolved": "https://registry.npmjs.org/truffle-flattener/-/truffle-flattener-1.2.3.tgz", - "integrity": "sha512-DisthKMI1qH+Xbw/S84CLPGeXz/kMkVUxBpz8Elj2kI4paVjEFEFwrq0juQHwxr2w/046r2tUT5usCE38Bw6Qw==", + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/truffle-flattener/-/truffle-flattener-1.3.0.tgz", + "integrity": "sha512-ppJ9xI0tDuvCYjQlcWwMBcOKZph5U4YpG/gChyUVDxOjUIniG5g7y9vZho2PRj1FohPPnOjg1KOAVNlk/bPZrw==", "dev": true, "requires": { + "@resolver-engine/imports-fs": "^0.2.2", "find-up": "^2.1.0", - "semver": "^5.4.1", - "solidity-parser": "^0.4.0", - "truffle-config": "^1.0.2", - "truffle-resolver": "^4.0.1", + "mkdirp": "^0.5.1", + "solidity-parser-antlr": "^0.4.0", "tsort": "0.0.1" }, "dependencies": { @@ -7646,37 +8040,21 @@ "requires": { "locate-path": "^2.0.0" } + }, + "solidity-parser-antlr": { + "version": "0.4.2", + "resolved": "https://registry.npmjs.org/solidity-parser-antlr/-/solidity-parser-antlr-0.4.2.tgz", + "integrity": "sha512-0OKT2YKZAqPe14HN7Nbo24hjmnyUYh92UjyZG0Zz2rpQhl/w8asX8qHb+ASSXfayQaiW8g9zGIupXEE355tOQQ==", + "dev": true } } }, - "truffle-provider": { - "version": "0.0.4", - "resolved": "https://registry.npmjs.org/truffle-provider/-/truffle-provider-0.0.4.tgz", - "integrity": "sha512-yVxxjocxnJcFspQ0T4Rjq/1wvvm3iLxidb6oa1EAX5LsnSQLPG8wAM5+JLlJ4FDBsqJdZLGOq1RR5Ln/w7x5JA==", - "dev": true, - "requires": { - "truffle-error": "^0.0.2", - "web3": "^0.20.1" - } - }, - "truffle-provisioner": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/truffle-provisioner/-/truffle-provisioner-0.1.0.tgz", - "integrity": "sha1-Ap5SScEBUwBzhTXgT97ZMaU8T2I=", + "tslib": { + "version": "1.9.3", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.9.3.tgz", + "integrity": "sha512-4krF8scpejhaOgqzBEcGM7yDIEfi0/8+8zDRZhNZZ2kjmHJ4hv3zCbQWxoJGz1iw5U0Jl0nma13xzHXcncMavQ==", "dev": true }, - "truffle-resolver": { - "version": "4.0.2", - "resolved": "https://registry.npmjs.org/truffle-resolver/-/truffle-resolver-4.0.2.tgz", - "integrity": "sha512-HKRd45HSfAqb9/BCOgYq4zkyl2lF40MvPDIGhyoPXFj5/9PSFzclyTkkMOdb+Rnm7oC1vY4cE1/k453lgf81Kw==", - "dev": true, - "requires": { - "async": "^2.1.4", - "truffle-contract": "^3.0.4", - "truffle-expect": "0.0.3", - "truffle-provisioner": "^0.1.0" - } - }, "tsort": { "version": "0.0.1", "resolved": "https://registry.npmjs.org/tsort/-/tsort-0.0.1.tgz", @@ -7694,8 +8072,7 @@ "tweetnacl": { "version": "0.14.5", "resolved": "https://registry.npmjs.org/tweetnacl/-/tweetnacl-0.14.5.tgz", - "integrity": "sha1-WuaBd/GS1EViadEIr6k/+HQ/T2Q=", - "optional": true + "integrity": "sha1-WuaBd/GS1EViadEIr6k/+HQ/T2Q=" }, "type-check": { "version": "0.3.2", @@ -7728,72 +8105,32 @@ "dev": true }, "uglify-js": { - "version": "2.8.29", - "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-2.8.29.tgz", - "integrity": "sha1-KcVzMUgFe7Th913zW3qcty5qWd0=", + "version": "3.5.2", + "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-3.5.2.tgz", + "integrity": "sha512-imog1WIsi9Yb56yRt5TfYVxGmnWs3WSGU73ieSOlMVFwhJCA9W8fqFFMMj4kgDqiS/80LGdsYnWL7O9UcjEBlg==", "dev": true, "optional": true, "requires": { - "source-map": "~0.5.1", - "uglify-to-browserify": "~1.0.0", - "yargs": "~3.10.0" + "commander": "~2.19.0", + "source-map": "~0.6.1" }, "dependencies": { - "camelcase": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-1.2.1.tgz", - "integrity": "sha1-m7UwTS4LVmmLLHWLCKPqqdqlijk=", - "dev": true, - "optional": true - }, - "cliui": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/cliui/-/cliui-2.1.0.tgz", - "integrity": "sha1-S0dXYP+AJkx2LDoXGQMukcf+oNE=", - "dev": true, - "optional": true, - "requires": { - "center-align": "^0.1.1", - "right-align": "^0.1.1", - "wordwrap": "0.0.2" - } - }, - "window-size": { - "version": "0.1.0", - "resolved": "https://registry.npmjs.org/window-size/-/window-size-0.1.0.tgz", - "integrity": "sha1-VDjNLqk7IC76Ohn+iIeu58lPnJ0=", + "commander": { + "version": "2.19.0", + "resolved": "https://registry.npmjs.org/commander/-/commander-2.19.0.tgz", + "integrity": "sha512-6tvAOO+D6OENvRAh524Dh9jcfKTYDQAqvqezbCW82xj5X0pSrcpxtvRKHLG0yBY6SD7PSDrJaj+0AiOcKVd1Xg==", "dev": true, "optional": true }, - "wordwrap": { - "version": "0.0.2", - "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-0.0.2.tgz", - "integrity": "sha1-t5Zpu0LstAn4PVg8rVLKF+qhZD8=", + "source-map": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", "dev": true, "optional": true - }, - "yargs": { - "version": "3.10.0", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-3.10.0.tgz", - "integrity": "sha1-9+572FfdfB0tOMDnTvvWgdFDH9E=", - "dev": true, - "optional": true, - "requires": { - "camelcase": "^1.0.2", - "cliui": "^2.1.0", - "decamelize": "^1.0.0", - "window-size": "0.1.0" - } } } }, - "uglify-to-browserify": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/uglify-to-browserify/-/uglify-to-browserify-1.0.2.tgz", - "integrity": "sha1-bgkk1r2mta/jSeOabWMoUKD4grc=", - "dev": true, - "optional": true - }, "ultron": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/ultron/-/ultron-1.1.1.tgz", @@ -7806,12 +8143,23 @@ "dev": true, "requires": { "debug": "^2.2.0" + }, + "dependencies": { + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, + "requires": { + "ms": "2.0.0" + } + } } }, "underscore": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.6.0.tgz", - "integrity": "sha1-izixDKze9jM3uLJOT/htRa6lKag=" + "version": "1.8.3", + "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", + "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=" }, "union-value": { "version": "1.0.0", @@ -7903,9 +8251,10 @@ } }, "untildify": { - "version": "3.0.2", - "resolved": "https://registry.npmjs.org/untildify/-/untildify-3.0.2.tgz", - "integrity": "sha1-fx8wIFWz/qDz6B3HjrNnZstl4/E=" + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/untildify/-/untildify-3.0.3.tgz", + "integrity": "sha512-iSk/J8efr8uPT/Z4eSUywnqyrQU7DSdMfdqK4iWEaUVVmcP5JcnpRqmVMwcwcnmI1ATFNgC5V90u09tBynNFKA==", + "dev": true }, "unzip-response": { "version": "2.0.1", @@ -7914,9 +8263,9 @@ "dev": true }, "upath": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/upath/-/upath-1.0.5.tgz", - "integrity": "sha512-qbKn90aDQ0YEwvXoLqj0oiuUYroLX2lVHZ+b+xwjozFasAOC4GneDq5+OaIG5Zj+jFmbz/uO+f7a9qxjktJQww==", + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/upath/-/upath-1.1.2.tgz", + "integrity": "sha512-kXpym8nmDmlCBr7nKdIx8P2jNBa+pBpIUFRnKJ4dr8htyYGJFokkr2ZvERRtUN+9SY+JqXouNgUPtv6JQva/2Q==", "dev": true }, "update-notifier": { @@ -7937,6 +8286,14 @@ "xdg-basedir": "^3.0.0" } }, + "uri-js": { + "version": "4.2.2", + "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.2.2.tgz", + "integrity": "sha512-KY9Frmirql91X2Qgjry0Wd4Y+YTdrdZheS8TFwvkbLWf/G5KNJDCh6pKL5OZctEW4+0Baa5idK2ZQuELRwPznQ==", + "requires": { + "punycode": "^2.1.0" + } + }, "urix": { "version": "0.1.0", "resolved": "https://registry.npmjs.org/urix/-/urix-0.1.0.tgz", @@ -7947,6 +8304,7 @@ "version": "1.0.0", "resolved": "https://registry.npmjs.org/url-parse-lax/-/url-parse-lax-1.0.0.tgz", "integrity": "sha1-evjzA2Rem9eaJy56FKxovAYJ2nM=", + "dev": true, "requires": { "prepend-http": "^1.0.1" } @@ -7959,27 +8317,25 @@ "url-to-options": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/url-to-options/-/url-to-options-1.0.1.tgz", - "integrity": "sha1-FQWgOiiaSMvXpDTvuu7FBV9WM6k=" + "integrity": "sha1-FQWgOiiaSMvXpDTvuu7FBV9WM6k=", + "dev": true }, "use": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/use/-/use-3.1.0.tgz", - "integrity": "sha512-6UJEQM/L+mzC3ZJNM56Q4DFGLX/evKGRg15UJHGB9X5j5Z3AFbgZvjUh2yq/UJUY4U5dh7Fal++XbNg1uzpRAw==", - "dev": true, - "requires": { - "kind-of": "^6.0.2" - } + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/use/-/use-3.1.1.tgz", + "integrity": "sha512-cwESVXlO3url9YWlFW/TA9cshCEhtu7IKJ/p5soJ/gGpj7vbvFrAY/eIioQ6Dw23KjZhYgiIo8HOs1nQ2vr/oQ==", + "dev": true }, "utf8": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/utf8/-/utf8-2.1.2.tgz", - "integrity": "sha1-H6DZJw6b6FDZsFAn9jUZv0ZFfZY=", - "dev": true + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/utf8/-/utf8-2.1.1.tgz", + "integrity": "sha1-LgHbAvfY0JRPdxBPFgnrDDBM92g=" }, "util-deprecate": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", - "integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=" + "integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=", + "dev": true }, "utils-merge": { "version": "1.0.1", @@ -7987,22 +8343,23 @@ "integrity": "sha1-n5VxD1CiZ5R7LMwSR0HBAoQn5xM=" }, "uuid": { - "version": "3.2.1", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.2.1.tgz", - "integrity": "sha512-jZnMwlb9Iku/O3smGWvZhauCf6cvvpKi4BKRiliS3cxnI+Gz9j5MEpTz2UFuXiKPJocb7gnsLHwiS05ige5BEA==" + "version": "3.3.2", + "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.3.2.tgz", + "integrity": "sha512-yXJmeNaw3DnnKAOKJE51sL/ZaYfWJRl1pK9dr19YFCu0ObS231AB1/LbqTKRAQ5kw8A90rA6fr4riOUpTZvQZA==" }, "v8-compile-cache": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/v8-compile-cache/-/v8-compile-cache-1.1.2.tgz", - "integrity": "sha512-ejdrifsIydN1XDH7EuR2hn8ZrkRKUYF7tUcBjBy/lhrCvs2K+zRlbW9UHc0IQ9RsYFZJFqJrieoIHfkCa0DBRA==" + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/v8-compile-cache/-/v8-compile-cache-2.0.2.tgz", + "integrity": "sha512-1wFuMUIM16MDJRCrpbpuEPTUGmM5QMUg0cr3KFwra2XgOgFcPGDQHDh3CszSCD2Zewc/dh/pamNEW8CbfDebUw==", + "dev": true }, "validate-npm-package-license": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/validate-npm-package-license/-/validate-npm-package-license-3.0.1.tgz", - "integrity": "sha1-KAS6vnEq0zeUWaz74kdGqywwP7w=", + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/validate-npm-package-license/-/validate-npm-package-license-3.0.4.tgz", + "integrity": "sha512-DpKm2Ui/xN7/HQKCtpZxoRWBhZ9Z0kqtygG8XCgNQ8ZlDnxuQmWhj566j8fN4Cu3/JmbhsDo7fcAJq4s9h27Ew==", "requires": { - "spdx-correct": "~1.0.0", - "spdx-expression-parse": "~1.0.0" + "spdx-correct": "^3.0.0", + "spdx-expression-parse": "^3.0.0" } }, "vary": { @@ -8024,6 +8381,7 @@ "version": "1.2.0", "resolved": "https://registry.npmjs.org/vinyl/-/vinyl-1.2.0.tgz", "integrity": "sha1-XIgDbPVl5d8FVYv8kR+GVt8hiIQ=", + "dev": true, "requires": { "clone": "^1.0.0", "clone-stats": "^0.0.1", @@ -8034,6 +8392,7 @@ "version": "2.0.0", "resolved": "https://registry.npmjs.org/vinyl-file/-/vinyl-file-2.0.0.tgz", "integrity": "sha1-p+v1/779obfRjRQPyweyI++2dRo=", + "dev": true, "requires": { "graceful-fs": "^4.1.2", "pify": "^2.3.0", @@ -8044,12 +8403,12 @@ } }, "web3": { - "version": "0.20.5", - "resolved": "https://registry.npmjs.org/web3/-/web3-0.20.5.tgz", - "integrity": "sha1-xQSNNfe/TixMKAzlH7u8lRKQsWU=", + "version": "0.18.4", + "resolved": "https://registry.npmjs.org/web3/-/web3-0.18.4.tgz", + "integrity": "sha1-gewXhBRUkfLqqJVbMcBgSeB8Xn0=", "dev": true, "requires": { - "bignumber.js": "git+https://github.com/frozeman/bignumber.js-nolookahead.git#57692b3ecfc98bbdd6b3a516cb2353652ea49934", + "bignumber.js": "git+https://github.com/debris/bignumber.js.git#94d7146671b9719e00a09c29b01a691bc85048c2", "crypto-js": "^3.1.4", "utf8": "^2.1.1", "xhr2": "*", @@ -8068,24 +8427,13 @@ "randomhex": "0.1.5", "underscore": "1.8.3", "utf8": "2.1.1" - }, - "dependencies": { - "underscore": { - "version": "1.8.3", - "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", - "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=" - }, - "utf8": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/utf8/-/utf8-2.1.1.tgz", - "integrity": "sha1-LgHbAvfY0JRPdxBPFgnrDDBM92g=" - } } }, "webpack-addons": { "version": "1.1.5", "resolved": "https://registry.npmjs.org/webpack-addons/-/webpack-addons-1.1.5.tgz", "integrity": "sha512-MGO0nVniCLFAQz1qv22zM02QPjcpAoJdy7ED0i3Zy7SY1IecgXCm460ib7H/Wq7e9oL5VL6S2BxaObxwIcag0g==", + "dev": true, "requires": { "jscodeshift": "^0.4.0" }, @@ -8094,6 +8442,7 @@ "version": "2.0.0", "resolved": "https://registry.npmjs.org/arr-diff/-/arr-diff-2.0.0.tgz", "integrity": "sha1-jzuCf5Vai9ZpaX5KQlasPOrjVs8=", + "dev": true, "requires": { "arr-flatten": "^1.0.1" } @@ -8101,27 +8450,26 @@ "array-unique": { "version": "0.2.1", "resolved": "https://registry.npmjs.org/array-unique/-/array-unique-0.2.1.tgz", - "integrity": "sha1-odl8yvy8JiXMcPrc6zalDFiwGlM=" + "integrity": "sha1-odl8yvy8JiXMcPrc6zalDFiwGlM=", + "dev": true }, "ast-types": { "version": "0.10.1", "resolved": "https://registry.npmjs.org/ast-types/-/ast-types-0.10.1.tgz", - "integrity": "sha512-UY7+9DPzlJ9VM8eY0b2TUZcZvF+1pO0hzMtAyjBYKhOmnvRlqYNYnWdtsMj0V16CGaMlpL0G1jnLbLo4AyotuQ==" - }, - "async": { - "version": "1.5.2", - "resolved": "https://registry.npmjs.org/async/-/async-1.5.2.tgz", - "integrity": "sha1-7GphrlZIDAw8skHJVhjiCJL5Zyo=" + "integrity": "sha512-UY7+9DPzlJ9VM8eY0b2TUZcZvF+1pO0hzMtAyjBYKhOmnvRlqYNYnWdtsMj0V16CGaMlpL0G1jnLbLo4AyotuQ==", + "dev": true }, "babylon": { "version": "6.18.0", "resolved": "https://registry.npmjs.org/babylon/-/babylon-6.18.0.tgz", - "integrity": "sha512-q/UEjfGJ2Cm3oKV71DJz9d25TPnq5rhBVL2Q4fA5wcC3jcrdn7+SssEybFIxwAvvP+YCsCYNKughoF33GxgycQ==" + "integrity": "sha512-q/UEjfGJ2Cm3oKV71DJz9d25TPnq5rhBVL2Q4fA5wcC3jcrdn7+SssEybFIxwAvvP+YCsCYNKughoF33GxgycQ==", + "dev": true }, "braces": { "version": "1.8.5", "resolved": "https://registry.npmjs.org/braces/-/braces-1.8.5.tgz", "integrity": "sha1-uneWLhLf+WnWt2cR6RS3N4V79qc=", + "dev": true, "requires": { "expand-range": "^1.8.1", "preserve": "^0.2.0", @@ -8132,6 +8480,7 @@ "version": "0.1.5", "resolved": "https://registry.npmjs.org/expand-brackets/-/expand-brackets-0.1.5.tgz", "integrity": "sha1-3wcoTjQqgHzXM6xa9yQR5YHRF3s=", + "dev": true, "requires": { "is-posix-bracket": "^0.1.0" } @@ -8140,6 +8489,7 @@ "version": "0.3.2", "resolved": "https://registry.npmjs.org/extglob/-/extglob-0.3.2.tgz", "integrity": "sha1-Lhj/PS9JqydlzskCPwEdqo2DSaE=", + "dev": true, "requires": { "is-extglob": "^1.0.0" } @@ -8147,12 +8497,14 @@ "is-extglob": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/is-extglob/-/is-extglob-1.0.0.tgz", - "integrity": "sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA=" + "integrity": "sha1-rEaBd8SUNAWgkvyPKXYMb/xiBsA=", + "dev": true }, "is-glob": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-2.0.1.tgz", "integrity": "sha1-0Jb5JqPe1WAPP9/ZEZjLCIjC2GM=", + "dev": true, "requires": { "is-extglob": "^1.0.0" } @@ -8161,6 +8513,7 @@ "version": "0.4.1", "resolved": "https://registry.npmjs.org/jscodeshift/-/jscodeshift-0.4.1.tgz", "integrity": "sha512-iOX6If+hsw0q99V3n31t4f5VlD1TQZddH08xbT65ZqA7T4Vkx68emrDZMUOLVvCEAJ6NpAk7DECe3fjC/t52AQ==", + "dev": true, "requires": { "async": "^1.5.0", "babel-plugin-transform-flow-strip-types": "^6.8.0", @@ -8183,6 +8536,7 @@ "version": "3.2.2", "resolved": "https://registry.npmjs.org/kind-of/-/kind-of-3.2.2.tgz", "integrity": "sha1-MeohpzS6ubuw8yRm2JOupR5KPGQ=", + "dev": true, "requires": { "is-buffer": "^1.1.5" } @@ -8191,6 +8545,7 @@ "version": "2.3.11", "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-2.3.11.tgz", "integrity": "sha1-hmd8l9FyCzY0MdBNDRUpO9OMFWU=", + "dev": true, "requires": { "arr-diff": "^2.0.0", "array-unique": "^0.2.1", @@ -8207,10 +8562,20 @@ "regex-cache": "^0.4.2" } }, + "normalize-path": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/normalize-path/-/normalize-path-2.1.1.tgz", + "integrity": "sha1-GrKLVW4Zg2Oowab35vogE3/mrtk=", + "dev": true, + "requires": { + "remove-trailing-separator": "^1.0.1" + } + }, "recast": { "version": "0.12.9", "resolved": "https://registry.npmjs.org/recast/-/recast-0.12.9.tgz", "integrity": "sha512-y7ANxCWmMW8xLOaiopiRDlyjQ9ajKRENBH+2wjntIbk3A6ZR1+BLQttkmSHMY7Arl+AAZFwJ10grg2T6f1WI8A==", + "dev": true, "requires": { "ast-types": "0.10.1", "core-js": "^2.4.1", @@ -8222,12 +8587,14 @@ "source-map": { "version": "0.6.1", "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", - "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==" + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", + "dev": true }, "write-file-atomic": { "version": "1.3.4", "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-1.3.4.tgz", "integrity": "sha1-+Aek8LHZ6ROuekgRLmzDrxmRtF8=", + "dev": true, "requires": { "graceful-fs": "^4.1.11", "imurmurhash": "^0.1.4", @@ -8237,51 +8604,56 @@ } }, "webpack-cli": { - "version": "2.0.13", - "resolved": "https://registry.npmjs.org/webpack-cli/-/webpack-cli-2.0.13.tgz", - "integrity": "sha512-0lnOi3yla8FsZVuMsbfnNRB/8DlfuDugKdekC+4ykydZG0+UOidMi5J5LLWN4c0VJ8PqC19yMXXkYyCq78OuqA==", + "version": "2.1.5", + "resolved": "https://registry.npmjs.org/webpack-cli/-/webpack-cli-2.1.5.tgz", + "integrity": "sha512-CiWQR+1JS77rmyiO6y1q8Kt/O+e8nUUC9YfJ25JtSmzDwbqJV7vIsh3+QKRHVTbTCa0DaVh8iY1LBiagUIDB3g==", + "dev": true, "requires": { - "chalk": "^2.3.2", + "chalk": "^2.4.1", "cross-spawn": "^6.0.5", "diff": "^3.5.0", "enhanced-resolve": "^4.0.0", + "envinfo": "^5.7.0", "glob-all": "^3.1.0", "global-modules": "^1.0.0", - "got": "^8.2.0", - "inquirer": "^5.1.0", - "interpret": "^1.0.4", + "got": "^8.3.1", + "import-local": "^1.0.0", + "inquirer": "^5.2.0", + "interpret": "^1.1.0", "jscodeshift": "^0.5.0", - "listr": "^0.13.0", + "listr": "^0.14.1", "loader-utils": "^1.1.0", - "lodash": "^4.17.5", + "lodash": "^4.17.10", "log-symbols": "^2.2.0", "mkdirp": "^0.5.1", "p-each-series": "^1.0.0", "p-lazy": "^1.0.0", - "prettier": "^1.5.3", - "resolve-cwd": "^2.0.0", - "supports-color": "^5.3.0", - "v8-compile-cache": "^1.1.2", + "prettier": "^1.12.1", + "supports-color": "^5.4.0", + "v8-compile-cache": "^2.0.0", "webpack-addons": "^1.1.5", - "yargs": "^11.0.0", - "yeoman-environment": "^2.0.0", - "yeoman-generator": "^2.0.3" + "yargs": "^11.1.0", + "yeoman-environment": "^2.1.1", + "yeoman-generator": "^2.0.5" }, "dependencies": { "ansi-regex": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", - "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=" + "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=", + "dev": true }, "camelcase": { "version": "4.1.0", "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-4.1.0.tgz", - "integrity": "sha1-1UVjW+HjPFQmScaRc+Xeas+uNN0=" + "integrity": "sha1-1UVjW+HjPFQmScaRc+Xeas+uNN0=", + "dev": true }, "cliui": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/cliui/-/cliui-4.0.0.tgz", - "integrity": "sha512-nY3W5Gu2racvdDk//ELReY+dHjb9PlIcVDFXP72nVIhq2Gy3LuVXYwJoPVudwQnv1shtohpgkdCKT2YaKY0CKw==", + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/cliui/-/cliui-4.1.0.tgz", + "integrity": "sha512-4FG+RSG9DL7uEwRUZXZn3SS34DiDPfzP0VOiEwtUWlE+AR2EIg+hSyvrIgUUfhdgR/UkAeW2QHgeP+hWrXs7jQ==", + "dev": true, "requires": { "string-width": "^2.1.1", "strip-ansi": "^4.0.0", @@ -8292,6 +8664,7 @@ "version": "6.0.5", "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-6.0.5.tgz", "integrity": "sha512-eTVLrBSt7fjbDygz805pMnstIs2VTBNkRm0qxZd+M7A5XDdxVRWO5MxGBXZhjY4cqLYLdtrGqRf8mBPmzwSpWQ==", + "dev": true, "requires": { "nice-try": "^1.0.4", "path-key": "^2.0.1", @@ -8303,20 +8676,23 @@ "diff": { "version": "3.5.0", "resolved": "https://registry.npmjs.org/diff/-/diff-3.5.0.tgz", - "integrity": "sha512-A46qtFgd+g7pDZinpnwiRJtxbC1hpgf0uzP3iG89scHk0AUC7A1TGxf5OiiOUv/JMZR8GOt8hL900hV0bOy5xA==" + "integrity": "sha512-A46qtFgd+g7pDZinpnwiRJtxbC1hpgf0uzP3iG89scHk0AUC7A1TGxf5OiiOUv/JMZR8GOt8hL900hV0bOy5xA==", + "dev": true }, "find-up": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", + "dev": true, "requires": { "locate-path": "^2.0.0" } }, "got": { - "version": "8.3.0", - "resolved": "https://registry.npmjs.org/got/-/got-8.3.0.tgz", - "integrity": "sha512-kBNy/S2CGwrYgDSec5KTWGKUvupwkkTVAjIsVFF2shXO13xpZdFP4d4kxa//CLX2tN/rV0aYwK8vY6UKWGn2vQ==", + "version": "8.3.2", + "resolved": "https://registry.npmjs.org/got/-/got-8.3.2.tgz", + "integrity": "sha512-qjUJ5U/hawxosMryILofZCkm3C84PLJS/0grRIpjAwu+Lkxxj5cxeCU25BG0/3mDSpXKTyZr8oh8wIgLaH0QCw==", + "dev": true, "requires": { "@sindresorhus/is": "^0.7.0", "cacheable-request": "^2.1.1", @@ -8340,17 +8716,20 @@ "has-flag": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-3.0.0.tgz", - "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=" + "integrity": "sha1-tdRU3CGZriJWmfNGfloH87lVuv0=", + "dev": true }, "is-fullwidth-code-point": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", - "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=" + "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=", + "dev": true }, "os-locale": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/os-locale/-/os-locale-2.1.0.tgz", "integrity": "sha512-3sslG3zJbEYcaC4YVAvDorjGxc7tv6KVATnLPZONiljsUncvihe9BQoVCEs0RZ1kmf4Hk9OBqlZfJZWI4GanKA==", + "dev": true, "requires": { "execa": "^0.7.0", "lcid": "^1.0.0", @@ -8360,17 +8739,20 @@ "pify": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", - "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=" + "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=", + "dev": true }, "prepend-http": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/prepend-http/-/prepend-http-2.0.0.tgz", - "integrity": "sha1-6SQ0v6XqjBn0HN/UAddBo8gZ2Jc=" + "integrity": "sha1-6SQ0v6XqjBn0HN/UAddBo8gZ2Jc=", + "dev": true }, "string-width": { "version": "2.1.1", "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", + "dev": true, "requires": { "is-fullwidth-code-point": "^2.0.0", "strip-ansi": "^4.0.0" @@ -8380,14 +8762,16 @@ "version": "4.0.0", "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", + "dev": true, "requires": { "ansi-regex": "^3.0.0" } }, "supports-color": { - "version": "5.3.0", - "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.3.0.tgz", - "integrity": "sha512-0aP01LLIskjKs3lq52EC0aGBAJhLq7B2Rd8HC/DR/PtNNpcLilNmHC12O+hu0usQpo7wtHNRqtrhBwtDb0+dNg==", + "version": "5.5.0", + "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-5.5.0.tgz", + "integrity": "sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==", + "dev": true, "requires": { "has-flag": "^3.0.0" } @@ -8396,6 +8780,7 @@ "version": "3.0.0", "resolved": "https://registry.npmjs.org/url-parse-lax/-/url-parse-lax-3.0.0.tgz", "integrity": "sha1-FrXK/Afb42dsGxmZF3gj1lA6yww=", + "dev": true, "requires": { "prepend-http": "^2.0.0" } @@ -8403,12 +8788,14 @@ "which-module": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/which-module/-/which-module-2.0.0.tgz", - "integrity": "sha1-2e8H3Od7mQK4o6j6SzHD4/fm6Ho=" + "integrity": "sha1-2e8H3Od7mQK4o6j6SzHD4/fm6Ho=", + "dev": true }, "yargs": { - "version": "11.0.0", - "resolved": "https://registry.npmjs.org/yargs/-/yargs-11.0.0.tgz", - "integrity": "sha512-Rjp+lMYQOWtgqojx1dEWorjCofi1YN7AoFvYV7b1gx/7dAAeuI4kN5SZiEvr0ZmsZTOpDRcCqrpI10L31tFkBw==", + "version": "11.1.0", + "resolved": "https://registry.npmjs.org/yargs/-/yargs-11.1.0.tgz", + "integrity": "sha512-NwW69J42EsCSanF8kyn5upxvjp5ds+t3+udGBeTbFnERA+lF541DDpMawzo4z6W/QrzNM18D+BPMiOBibnFV5A==", + "dev": true, "requires": { "cliui": "^4.0.0", "decamelize": "^1.1.1", @@ -8428,6 +8815,7 @@ "version": "9.0.2", "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-9.0.2.tgz", "integrity": "sha1-nM9qQ0YP5O1Aqbto9I1DuKaMwHc=", + "dev": true, "requires": { "camelcase": "^4.1.0" } @@ -8435,9 +8823,10 @@ } }, "which": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/which/-/which-1.3.0.tgz", - "integrity": "sha512-xcJpopdamTuY5duC/KnTTNBraPK54YwpenP4lzxU8H91GudWpFv38u0CKjclE1Wi2EH2EDz5LRcHcKbCIzqGyg==", + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/which/-/which-1.3.1.tgz", + "integrity": "sha512-HxJdYWq1MTIQbJ3nw0cqssHoTNU267KlrDuGZ1WYlxDStUtKUhOaJmh112/TZmHxxUfuJqPXSOm7tDyas0OSIQ==", + "dev": true, "requires": { "isexe": "^2.0.0" } @@ -8448,9 +8837,9 @@ "integrity": "sha1-u6Y8qGGUiZT/MHc2CJ47lgJsKk8=" }, "widest-line": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/widest-line/-/widest-line-2.0.0.tgz", - "integrity": "sha1-AUKk6KJD+IgsAjOqDgKBqnYVInM=", + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/widest-line/-/widest-line-2.0.1.tgz", + "integrity": "sha512-Ba5m9/Fa4Xt9eb2ELXt77JxVDV8w7qQrH0zS/TWSJdLyAwQjWoOzpzj5lwVftDz6n/EOu3tNACS84v509qwnJA==", "dev": true, "requires": { "string-width": "^2.1.1" @@ -8515,9 +8904,9 @@ "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=" }, "write-file-atomic": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-2.3.0.tgz", - "integrity": "sha512-xuPeK4OdjWqtfi59ylvVL0Yn35SF3zgcAcv7rBPFHVaEapaDr4GdGgm3j7ckTwH9wHL7fGmgfAnb0+THrHb8tA==", + "version": "2.4.2", + "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-2.4.2.tgz", + "integrity": "sha512-s0b6vB3xIVRLWywa6X9TOMA7k9zio0TMOsl9ZnDkliA/cfJlpHXAscj0gbHVJiTdIuAYpIyqS5GW91fqm6gG5g==", "dev": true, "requires": { "graceful-fs": "^4.1.11", @@ -8542,9 +8931,9 @@ "dev": true }, "xhr": { - "version": "2.4.1", - "resolved": "https://registry.npmjs.org/xhr/-/xhr-2.4.1.tgz", - "integrity": "sha512-pAIU5vBr9Hiy5cpFIbPnwf0C18ZF86DBsZKrlsf87N5De/JbA6RJ83UP/cv+aljl4S40iRVMqP4pr4sF9Dnj0A==", + "version": "2.5.0", + "resolved": "https://registry.npmjs.org/xhr/-/xhr-2.5.0.tgz", + "integrity": "sha512-4nlO/14t3BNUZRXIXfXe+3N6w3s1KoxcJUUURctd64BLRe67E4gRwp4PjywtDY72fXpZ1y6Ch0VZQRY/gMPzzQ==", "requires": { "global": "~4.3.0", "is-function": "^1.0.1", @@ -8599,7 +8988,8 @@ "yallist": { "version": "2.1.2", "resolved": "https://registry.npmjs.org/yallist/-/yallist-2.1.2.tgz", - "integrity": "sha1-HBH5IY8HYImkfdUS+TxmmaaoHVI=" + "integrity": "sha1-HBH5IY8HYImkfdUS+TxmmaaoHVI=", + "dev": true }, "yargs": { "version": "4.8.1", @@ -8632,73 +9022,137 @@ } }, "yeoman-environment": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/yeoman-environment/-/yeoman-environment-2.0.5.tgz", - "integrity": "sha512-6/W7/B54OPHJXob0n0+pmkwFsirC8cokuQkPSmT/D0lCcSxkKtg/BA6ZnjUBIwjuGqmw3DTrT4en++htaUju5g==", + "version": "2.3.4", + "resolved": "https://registry.npmjs.org/yeoman-environment/-/yeoman-environment-2.3.4.tgz", + "integrity": "sha512-KLxE5ft/74Qj7h3AsQZv8G6MEEHYJwmD5F99nfOVaep3rBzCtbrJKkdqWc7bDV141Nr8UZZsIXmzc3IcCm6E2w==", + "dev": true, "requires": { - "chalk": "^2.1.0", + "chalk": "^2.4.1", + "cross-spawn": "^6.0.5", "debug": "^3.1.0", - "diff": "^3.3.1", + "diff": "^3.5.0", "escape-string-regexp": "^1.0.2", - "globby": "^6.1.0", + "globby": "^8.0.1", "grouped-queue": "^0.3.3", - "inquirer": "^3.3.0", + "inquirer": "^6.0.0", "is-scoped": "^1.0.0", - "lodash": "^4.17.4", - "log-symbols": "^2.1.0", + "lodash": "^4.17.10", + "log-symbols": "^2.2.0", "mem-fs": "^1.1.0", + "strip-ansi": "^4.0.0", "text-table": "^0.2.0", - "untildify": "^3.0.2" + "untildify": "^3.0.3" }, "dependencies": { "ansi-regex": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", - "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=" + "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=", + "dev": true }, - "debug": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", - "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", + "chardet": { + "version": "0.7.0", + "resolved": "https://registry.npmjs.org/chardet/-/chardet-0.7.0.tgz", + "integrity": "sha512-mT8iDcrh03qDGRRmoA2hmBJnxpllMR+0/0qlzjqZES6NdiWDcZkCNAk4rPFZ9Q85r27unkiNNg8ZOiwZXBHwcA==", + "dev": true + }, + "cross-spawn": { + "version": "6.0.5", + "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-6.0.5.tgz", + "integrity": "sha512-eTVLrBSt7fjbDygz805pMnstIs2VTBNkRm0qxZd+M7A5XDdxVRWO5MxGBXZhjY4cqLYLdtrGqRf8mBPmzwSpWQ==", + "dev": true, "requires": { - "ms": "2.0.0" + "nice-try": "^1.0.4", + "path-key": "^2.0.1", + "semver": "^5.5.0", + "shebang-command": "^1.2.0", + "which": "^1.2.9" } }, "diff": { "version": "3.5.0", "resolved": "https://registry.npmjs.org/diff/-/diff-3.5.0.tgz", - "integrity": "sha512-A46qtFgd+g7pDZinpnwiRJtxbC1hpgf0uzP3iG89scHk0AUC7A1TGxf5OiiOUv/JMZR8GOt8hL900hV0bOy5xA==" + "integrity": "sha512-A46qtFgd+g7pDZinpnwiRJtxbC1hpgf0uzP3iG89scHk0AUC7A1TGxf5OiiOUv/JMZR8GOt8hL900hV0bOy5xA==", + "dev": true + }, + "external-editor": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/external-editor/-/external-editor-3.0.3.tgz", + "integrity": "sha512-bn71H9+qWoOQKyZDo25mOMVpSmXROAsTJVVVYzrrtol3d4y+AsKjf4Iwl2Q+IuT0kFSQ1qo166UuIwqYq7mGnA==", + "dev": true, + "requires": { + "chardet": "^0.7.0", + "iconv-lite": "^0.4.24", + "tmp": "^0.0.33" + } + }, + "iconv-lite": { + "version": "0.4.24", + "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.24.tgz", + "integrity": "sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==", + "dev": true, + "requires": { + "safer-buffer": ">= 2.1.2 < 3" + } }, "inquirer": { - "version": "3.3.0", - "resolved": "https://registry.npmjs.org/inquirer/-/inquirer-3.3.0.tgz", - "integrity": "sha512-h+xtnyk4EwKvFWHrUYsWErEVR+igKtLdchu+o0Z1RL7VU/jVMFbYir2bp6bAj8efFNxWqHX0dIss6fJQ+/+qeQ==", + "version": "6.2.2", + "resolved": "https://registry.npmjs.org/inquirer/-/inquirer-6.2.2.tgz", + "integrity": "sha512-Z2rREiXA6cHRR9KBOarR3WuLlFzlIfAEIiB45ll5SSadMg7WqOh1MKEjjndfuH5ewXdixWCxqnVfGOQzPeiztA==", + "dev": true, "requires": { - "ansi-escapes": "^3.0.0", - "chalk": "^2.0.0", + "ansi-escapes": "^3.2.0", + "chalk": "^2.4.2", "cli-cursor": "^2.1.0", "cli-width": "^2.0.0", - "external-editor": "^2.0.4", + "external-editor": "^3.0.3", "figures": "^2.0.0", - "lodash": "^4.3.0", + "lodash": "^4.17.11", "mute-stream": "0.0.7", "run-async": "^2.2.0", - "rx-lite": "^4.0.8", - "rx-lite-aggregates": "^4.0.8", + "rxjs": "^6.4.0", "string-width": "^2.1.0", - "strip-ansi": "^4.0.0", + "strip-ansi": "^5.0.0", "through": "^2.3.6" + }, + "dependencies": { + "ansi-regex": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-4.1.0.tgz", + "integrity": "sha512-1apePfXM1UOSqw0o9IiFAovVz9M5S1Dg+4TrDwfMewQ6p/rmMueb7tWZjQ1rx4Loy1ArBggoqGpfqqdI4rondg==", + "dev": true + }, + "strip-ansi": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-5.2.0.tgz", + "integrity": "sha512-DuRs1gKbBqsMKIZlrffwlug8MHkcnpjs5VPmL1PAh+mA30U0DTotfDZ0d2UUsXpPmPmMMJ6W773MaA3J+lbiWA==", + "dev": true, + "requires": { + "ansi-regex": "^4.1.0" + } + } } }, "is-fullwidth-code-point": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", - "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=" + "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=", + "dev": true + }, + "rxjs": { + "version": "6.4.0", + "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-6.4.0.tgz", + "integrity": "sha512-Z9Yfa11F6B9Sg/BK9MnqnQ+aQYicPLtilXBp2yUtDt2JRCE0h26d33EnfO3ZxoNxG0T92OUucP3Ct7cpfkdFfw==", + "dev": true, + "requires": { + "tslib": "^1.9.0" + } }, "string-width": { "version": "2.1.1", "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", + "dev": true, "requires": { "is-fullwidth-code-point": "^2.0.0", "strip-ansi": "^4.0.0" @@ -8708,6 +9162,7 @@ "version": "4.0.0", "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", + "dev": true, "requires": { "ansi-regex": "^3.0.0" } @@ -8715,25 +9170,26 @@ } }, "yeoman-generator": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/yeoman-generator/-/yeoman-generator-2.0.3.tgz", - "integrity": "sha512-mODmrZ26a94djmGZZuIiomSGlN4wULdou29ZwcySupb2e9FdvoCl7Ps2FqHFjEHio3kOl/iBeaNqrnx3C3NwWg==", + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/yeoman-generator/-/yeoman-generator-2.0.5.tgz", + "integrity": "sha512-rV6tJ8oYzm4mmdF2T3wjY+Q42jKF2YiiD0VKfJ8/0ZYwmhCKC9Xs2346HVLPj/xE13i68psnFJv7iS6gWRkeAg==", + "dev": true, "requires": { "async": "^2.6.0", "chalk": "^2.3.0", "cli-table": "^0.3.1", - "cross-spawn": "^5.1.0", + "cross-spawn": "^6.0.5", "dargs": "^5.1.0", - "dateformat": "^3.0.2", + "dateformat": "^3.0.3", "debug": "^3.1.0", "detect-conflict": "^1.0.0", "error": "^7.0.2", "find-up": "^2.1.0", "github-username": "^4.0.0", - "istextorbinary": "^2.1.0", - "lodash": "^4.17.4", + "istextorbinary": "^2.2.1", + "lodash": "^4.17.10", "make-dir": "^1.1.0", - "mem-fs-editor": "^3.0.2", + "mem-fs-editor": "^4.0.0", "minimist": "^1.2.0", "pretty-bytes": "^4.0.2", "read-chunk": "^2.1.0", @@ -8746,18 +9202,33 @@ "yeoman-environment": "^2.0.5" }, "dependencies": { - "debug": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", - "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", + "async": { + "version": "2.6.2", + "resolved": "https://registry.npmjs.org/async/-/async-2.6.2.tgz", + "integrity": "sha512-H1qVYh1MYhEEFLsP97cVKqCGo7KfCyTt6uEWqsTBr9SO84oK9Uwbyd/yCW+6rKJLHksBNUVWZDAjfS+Ccx0Bbg==", + "dev": true, "requires": { - "ms": "2.0.0" + "lodash": "^4.17.11" + } + }, + "cross-spawn": { + "version": "6.0.5", + "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-6.0.5.tgz", + "integrity": "sha512-eTVLrBSt7fjbDygz805pMnstIs2VTBNkRm0qxZd+M7A5XDdxVRWO5MxGBXZhjY4cqLYLdtrGqRf8mBPmzwSpWQ==", + "dev": true, + "requires": { + "nice-try": "^1.0.4", + "path-key": "^2.0.1", + "semver": "^5.5.0", + "shebang-command": "^1.2.0", + "which": "^1.2.9" } }, "find-up": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", + "dev": true, "requires": { "locate-path": "^2.0.0" } @@ -8766,6 +9237,7 @@ "version": "4.0.0", "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-4.0.0.tgz", "integrity": "sha1-L19Fq5HjMhYjT9U62rZo607AmTs=", + "dev": true, "requires": { "graceful-fs": "^4.1.2", "parse-json": "^4.0.0", @@ -8776,12 +9248,14 @@ "minimist": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.0.tgz", - "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=" + "integrity": "sha1-o1AIsg9BOD7sH7kU9M1d95omQoQ=", + "dev": true }, "parse-json": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-4.0.0.tgz", "integrity": "sha1-vjX1Qlvh9/bHRxhPmKeIy5lHfuA=", + "dev": true, "requires": { "error-ex": "^1.3.1", "json-parse-better-errors": "^1.0.1" @@ -8791,6 +9265,7 @@ "version": "3.0.0", "resolved": "https://registry.npmjs.org/path-type/-/path-type-3.0.0.tgz", "integrity": "sha512-T2ZUsdZFHgA3u4e5PfPbjd7HDDpxPnQb5jN0SrDsjNSuVXHJqtwTnWqG0B1jZrgmJ/7lj1EmVIByWt1gxGkWvg==", + "dev": true, "requires": { "pify": "^3.0.0" } @@ -8798,12 +9273,14 @@ "pify": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/pify/-/pify-3.0.0.tgz", - "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=" + "integrity": "sha1-5aSs0sEB/fPZpNB/DbxNtJ3SgXY=", + "dev": true }, "read-pkg": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-3.0.0.tgz", "integrity": "sha1-nLxoaXj+5l0WwA4rGcI3/Pbjg4k=", + "dev": true, "requires": { "load-json-file": "^4.0.0", "normalize-package-data": "^2.3.2", @@ -8814,15 +9291,28 @@ "version": "3.0.0", "resolved": "https://registry.npmjs.org/read-pkg-up/-/read-pkg-up-3.0.0.tgz", "integrity": "sha1-PtSWaF26D4/hGNBpHcUfSh/5bwc=", + "dev": true, "requires": { "find-up": "^2.0.0", "read-pkg": "^3.0.0" } }, + "shelljs": { + "version": "0.8.3", + "resolved": "https://registry.npmjs.org/shelljs/-/shelljs-0.8.3.tgz", + "integrity": "sha512-fc0BKlAWiLpwZljmOvAOTE/gXawtCoNrP5oaY7KIaQbbyHeQVg01pSEuEGvGh3HEdBU4baCD7wQBwADmM/7f7A==", + "dev": true, + "requires": { + "glob": "^7.0.0", + "interpret": "^1.0.0", + "rechoir": "^0.6.2" + } + }, "strip-bom": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-3.0.0.tgz", - "integrity": "sha1-IzTBjpx1n3vdVv3vfprj1YjmjtM=" + "integrity": "sha1-IzTBjpx1n3vdVv3vfprj1YjmjtM=", + "dev": true } } } diff --git a/package.json b/package.json index 299b5b46e..8bfc3dcf4 100644 --- a/package.json +++ b/package.json @@ -15,8 +15,8 @@ "dependencies": { "ganache-cli": "^6.1.0", "openzeppelin-solidity": "^1.10.0", - "truffle": "^4.1.11", - "web3-utils": "^1.0.0-beta.34" + "truffle": "4.1.11", + "web3-utils": "1.0.0-beta.34" }, "devDependencies": { "chai": "^4.1.2", From bf2222da9562b827daa4e997a0f3fcc14eebfd77 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Fri, 29 Mar 2019 16:09:44 -0300 Subject: [PATCH 120/187] Add fee manager on erc-to-erc deploy script --- deploy/src/erc_to_erc/home.js | 150 ++++++++++++++++++++++++++-------- deploy/src/loadEnv.js | 6 ++ 2 files changed, 122 insertions(+), 34 deletions(-) diff --git a/deploy/src/erc_to_erc/home.js b/deploy/src/erc_to_erc/home.js index d8f238d21..390542f05 100644 --- a/deploy/src/erc_to_erc/home.js +++ b/deploy/src/erc_to_erc/home.js @@ -2,15 +2,23 @@ const assert = require('assert') const Web3Utils = require('web3-utils') const env = require('../loadEnv') -const { deployContract, privateKeyToAddress, sendRawTxHome } = require('../deploymentUtils') +const { + deployContract, + privateKeyToAddress, + sendRawTxHome, + logValidatorsAndRewardAccounts +} = require('../deploymentUtils') const { web3Home, deploymentPrivateKey, HOME_RPC_URL } = require('../web3') const EternalStorageProxy = require('../../../build/contracts/EternalStorageProxy.json') const BridgeValidators = require('../../../build/contracts/BridgeValidators.json') +const RewardableValidators = require('../../../build/contracts/RewardableValidators.json') +const FeeManagerErcToErcPOSDAO = require('../../../build/contracts/FeeManagerErcToErcPOSDAO') const HomeBridge = require('../../../build/contracts/HomeBridgeErcToErc.json') const ERC677BridgeToken = require('../../../build/contracts/ERC677BridgeToken.json') const VALIDATORS = env.VALIDATORS.split(' ') +const VALIDATORS_REWARD_ACCOUNTS = env.VALIDATORS_REWARD_ACCOUNTS.split(' ') const { DEPLOYMENT_ACCOUNT_PRIVATE_KEY, @@ -27,11 +35,17 @@ const { BRIDGEABLE_TOKEN_SYMBOL, BRIDGEABLE_TOKEN_DECIMALS, FOREIGN_DAILY_LIMIT, - FOREIGN_MAX_AMOUNT_PER_TX + FOREIGN_MAX_AMOUNT_PER_TX, + HOME_REWARDABLE, + HOME_TRANSACTIONS_FEE, + FOREIGN_TRANSACTIONS_FEE, + BLOCK_REWARD_ADDRESS } = env const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVATE_KEY) +const isRewardableBridge = HOME_REWARDABLE === 'true' + async function deployHome() { let homeNonce = await web3Home.eth.getTransactionCount(DEPLOYMENT_ACCOUNT_ADDRESS) console.log('deploying storage for home validators') @@ -43,7 +57,8 @@ async function deployHome() { homeNonce++ console.log('\ndeploying implementation for home validators') - const bridgeValidatorsHome = await deployContract(BridgeValidators, [], { + const bridgeValidatorsContract = isRewardableBridge ? RewardableValidators : BridgeValidators + const bridgeValidatorsHome = await deployContract(bridgeValidatorsContract, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, nonce: homeNonce }) @@ -65,13 +80,31 @@ async function deployHome() { homeNonce++ console.log('\ninitializing Home Bridge Validators with following parameters:\n') - console.log( - `REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, VALIDATORS: ${VALIDATORS}` - ) bridgeValidatorsHome.options.address = storageValidatorsHome.options.address - const initializeData = await bridgeValidatorsHome.methods - .initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, HOME_VALIDATORS_OWNER) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + + let initializeData + + if (isRewardableBridge) { + console.log( + `REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, HOME_VALIDATORS_OWNER: ${HOME_VALIDATORS_OWNER}` + ) + logValidatorsAndRewardAccounts(VALIDATORS, VALIDATORS_REWARD_ACCOUNTS) + initializeData = await bridgeValidatorsHome.methods + .initialize( + REQUIRED_NUMBER_OF_VALIDATORS, + VALIDATORS, + VALIDATORS_REWARD_ACCOUNTS, + HOME_VALIDATORS_OWNER + ) + .encodeABI() + } else { + console.log( + `REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, VALIDATORS: ${VALIDATORS}` + ) + initializeData = await bridgeValidatorsHome.methods + .initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, HOME_VALIDATORS_OWNER) + .encodeABI() + } const txInitialize = await sendRawTxHome({ data: initializeData, nonce: homeNonce, @@ -163,32 +196,81 @@ async function deployHome() { assert.strictEqual(Web3Utils.hexToNumber(txOwnership.status), 1, 'Transaction Failed') homeNonce++ - console.log('\ninitializing Home Bridge with following parameters:\n') - console.log(`Home Validators: ${storageValidatorsHome.options.address}, - HOME_DAILY_LIMIT : ${HOME_DAILY_LIMIT} which is ${Web3Utils.fromWei(HOME_DAILY_LIMIT)} in eth, - HOME_MAX_AMOUNT_PER_TX: ${HOME_MAX_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( - HOME_MAX_AMOUNT_PER_TX - )} in eth, - HOME_MIN_AMOUNT_PER_TX: ${HOME_MIN_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( - HOME_MIN_AMOUNT_PER_TX - )} in eth, - HOME_GAS_PRICE: ${HOME_GAS_PRICE}, HOME_REQUIRED_BLOCK_CONFIRMATIONS : ${HOME_REQUIRED_BLOCK_CONFIRMATIONS} - `) + let initializeHomeBridgeData homeBridgeImplementation.options.address = homeBridgeStorage.options.address - const initializeHomeBridgeData = await homeBridgeImplementation.methods - .initialize( - storageValidatorsHome.options.address, - HOME_DAILY_LIMIT, - HOME_MAX_AMOUNT_PER_TX, - HOME_MIN_AMOUNT_PER_TX, - HOME_GAS_PRICE, - HOME_REQUIRED_BLOCK_CONFIRMATIONS, - erc677token.options.address, - FOREIGN_DAILY_LIMIT, - FOREIGN_MAX_AMOUNT_PER_TX, - HOME_BRIDGE_OWNER - ) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + + if (isRewardableBridge) { + console.log('\ndeploying implementation for fee manager') + const feeManager = await deployContract(FeeManagerErcToErcPOSDAO, [], { + from: DEPLOYMENT_ACCOUNT_ADDRESS, + nonce: homeNonce + }) + console.log('[Home] feeManager Implementation: ', feeManager.options.address) + homeNonce++ + + const homeFeeInWei = Web3Utils.toWei(HOME_TRANSACTIONS_FEE.toString(), 'ether') + const foreignFeeInWei = Web3Utils.toWei(FOREIGN_TRANSACTIONS_FEE.toString(), 'ether') + console.log('\ninitializing Home Bridge with fee contract:\n') + console.log(`Home Validators: ${storageValidatorsHome.options.address}, + HOME_DAILY_LIMIT : ${HOME_DAILY_LIMIT} which is ${Web3Utils.fromWei(HOME_DAILY_LIMIT)} in eth, + HOME_MAX_AMOUNT_PER_TX: ${HOME_MAX_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( + HOME_MAX_AMOUNT_PER_TX + )} in eth, + HOME_MIN_AMOUNT_PER_TX: ${HOME_MIN_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( + HOME_MIN_AMOUNT_PER_TX + )} in eth, + HOME_GAS_PRICE: ${HOME_GAS_PRICE}, HOME_REQUIRED_BLOCK_CONFIRMATIONS : ${HOME_REQUIRED_BLOCK_CONFIRMATIONS}, + Block Reward: ${BLOCK_REWARD_ADDRESS}, + Fee Manager: ${feeManager.options.address}, + Home Fee: ${homeFeeInWei} which is ${HOME_TRANSACTIONS_FEE * 100}% + Foreign Fee: ${foreignFeeInWei} which is ${FOREIGN_TRANSACTIONS_FEE * 100}%`) + initializeHomeBridgeData = await homeBridgeImplementation.methods + .rewardableInitialize( + storageValidatorsHome.options.address, + HOME_DAILY_LIMIT, + HOME_MAX_AMOUNT_PER_TX, + HOME_MIN_AMOUNT_PER_TX, + HOME_GAS_PRICE, + HOME_REQUIRED_BLOCK_CONFIRMATIONS, + erc677token.options.address, + FOREIGN_DAILY_LIMIT, + FOREIGN_MAX_AMOUNT_PER_TX, + HOME_BRIDGE_OWNER, + BLOCK_REWARD_ADDRESS, + feeManager.options.address, + homeFeeInWei, + foreignFeeInWei + ) + .encodeABI() + } else { + console.log('\ninitializing Home Bridge with following parameters:\n') + console.log(`Home Validators: ${storageValidatorsHome.options.address}, + HOME_DAILY_LIMIT : ${HOME_DAILY_LIMIT} which is ${Web3Utils.fromWei(HOME_DAILY_LIMIT)} in eth, + HOME_MAX_AMOUNT_PER_TX: ${HOME_MAX_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( + HOME_MAX_AMOUNT_PER_TX + )} in eth, + HOME_MIN_AMOUNT_PER_TX: ${HOME_MIN_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( + HOME_MIN_AMOUNT_PER_TX + )} in eth, + HOME_GAS_PRICE: ${HOME_GAS_PRICE}, HOME_REQUIRED_BLOCK_CONFIRMATIONS : ${HOME_REQUIRED_BLOCK_CONFIRMATIONS} + `) + + initializeHomeBridgeData = await homeBridgeImplementation.methods + .initialize( + storageValidatorsHome.options.address, + HOME_DAILY_LIMIT, + HOME_MAX_AMOUNT_PER_TX, + HOME_MIN_AMOUNT_PER_TX, + HOME_GAS_PRICE, + HOME_REQUIRED_BLOCK_CONFIRMATIONS, + erc677token.options.address, + FOREIGN_DAILY_LIMIT, + FOREIGN_MAX_AMOUNT_PER_TX, + HOME_BRIDGE_OWNER + ) + .encodeABI() + } + const txInitializeHomeBridge = await sendRawTxHome({ data: initializeHomeBridgeData, nonce: homeNonce, diff --git a/deploy/src/loadEnv.js b/deploy/src/loadEnv.js index d95b86f74..f3c2b3097 100644 --- a/deploy/src/loadEnv.js +++ b/deploy/src/loadEnv.js @@ -97,6 +97,12 @@ if (BRIDGE_MODE === 'ERC_TO_ERC') { BRIDGEABLE_TOKEN_SYMBOL: envalid.str(), BRIDGEABLE_TOKEN_DECIMALS: envalid.num() } + + if (FOREIGN_REWARDABLE === 'true') { + throw new Error( + `Collecting fees on Foreign Network on ${BRIDGE_MODE} bridge mode is not supported.` + ) + } } if (BRIDGE_MODE === 'ERC_TO_NATIVE') { validations = { From 595315d6afbb2d85998f68ec4e6546dc6405a0cb Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 1 Apr 2019 11:48:51 -0300 Subject: [PATCH 121/187] Avoid calling blockReward if zero value from foreign transfer on erc-to-native --- .../erc20_to_native/HomeBridgeErcToNative.sol | 10 ++++--- test/erc_to_native/home_bridge.test.js | 26 +++++++++++++++++++ 2 files changed, 32 insertions(+), 4 deletions(-) diff --git a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol index 8a42f4586..6acd1a4f4 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol @@ -81,10 +81,12 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, } function onExecuteAffirmation(address _recipient, uint256 _value) internal returns(bool) { - setTotalExecutedPerDay(getCurrentDay(), totalExecutedPerDay(getCurrentDay()).add(_value)); - IBlockReward blockReward = blockRewardContract(); - require(blockReward != address(0)); - blockReward.addExtraReceiver(_value, _recipient); + if (_value > 0) { + setTotalExecutedPerDay(getCurrentDay(), totalExecutedPerDay(getCurrentDay()).add(_value)); + IBlockReward blockReward = blockRewardContract(); + require(blockReward != address(0)); + blockReward.addExtraReceiver(_value, _recipient); + } return true; } diff --git a/test/erc_to_native/home_bridge.test.js b/test/erc_to_native/home_bridge.test.js index 9660f7b2d..0ee0aeeed 100644 --- a/test/erc_to_native/home_bridge.test.js +++ b/test/erc_to_native/home_bridge.test.js @@ -365,6 +365,32 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { true.should.be.equal(await homeBridge.affirmationsSigned(senderHash)) }) + it('should allow validator to executeAffirmation with zero value', async () => { + const recipient = accounts[5]; + const value = web3.toBigNumber(web3.toWei(0, "ether")); + const balanceBefore = await web3.eth.getBalance(recipient) + const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const {logs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}) + + logs[0].event.should.be.equal("SignedForAffirmation"); + logs[0].args.should.be.deep.equal({ + signer: authorities[0], + transactionHash + }); + logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].args.should.be.deep.equal({ + recipient, + value, + transactionHash + }) + const balanceAfter = await web3.eth.getBalance(recipient) + balanceAfter.should.be.bignumber.equal(balanceBefore.add(value)) + + const msgHash = Web3Utils.soliditySha3(recipient, value, transactionHash); + const senderHash = Web3Utils.soliditySha3(authorities[0], msgHash) + true.should.be.equal(await homeBridge.affirmationsSigned(senderHash)) + }) + it('test with 2 signatures required', async () => { const validatorContractWith2Signatures = await BridgeValidators.new() const authoritiesTwoAccs = [accounts[1], accounts[2], accounts[3]]; From 905bac8cea9b70cb59dae64eb24e7c15911cdc32 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 1 Apr 2019 12:28:32 -0300 Subject: [PATCH 122/187] call onExecuteAffirmation if non zero value --- contracts/upgradeable_contracts/BasicHomeBridge.sol | 4 +++- .../erc20_to_native/HomeBridgeErcToNative.sol | 10 ++++------ 2 files changed, 7 insertions(+), 7 deletions(-) diff --git a/contracts/upgradeable_contracts/BasicHomeBridge.sol b/contracts/upgradeable_contracts/BasicHomeBridge.sol index f1c27d03b..cb80fbdea 100644 --- a/contracts/upgradeable_contracts/BasicHomeBridge.sol +++ b/contracts/upgradeable_contracts/BasicHomeBridge.sol @@ -36,7 +36,9 @@ contract BasicHomeBridge is EternalStorage, Validatable { // If the bridge contract does not own enough tokens to transfer // it will couse funds lock on the home side of the bridge setNumAffirmationsSigned(hashMsg, markAsProcessed(signed)); - require(onExecuteAffirmation(recipient, value)); + if (value > 0) { + require(onExecuteAffirmation(recipient, value)); + } emit AffirmationCompleted(recipient, value, transactionHash); } } else { diff --git a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol index 6acd1a4f4..8a42f4586 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol @@ -81,12 +81,10 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, } function onExecuteAffirmation(address _recipient, uint256 _value) internal returns(bool) { - if (_value > 0) { - setTotalExecutedPerDay(getCurrentDay(), totalExecutedPerDay(getCurrentDay()).add(_value)); - IBlockReward blockReward = blockRewardContract(); - require(blockReward != address(0)); - blockReward.addExtraReceiver(_value, _recipient); - } + setTotalExecutedPerDay(getCurrentDay(), totalExecutedPerDay(getCurrentDay()).add(_value)); + IBlockReward blockReward = blockRewardContract(); + require(blockReward != address(0)); + blockReward.addExtraReceiver(_value, _recipient); return true; } From dc3052f9845cce67a552c8d293dde3cc3536ca53 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 1 Apr 2019 12:38:05 -0300 Subject: [PATCH 123/187] Add executeAffirmation test for zero value --- test/erc_to_erc/home_bridge.test.js | 30 ++++++++++++++++++++++++++ test/native_to_erc/home_bridge_test.js | 26 ++++++++++++++++++++++ 2 files changed, 56 insertions(+) diff --git a/test/erc_to_erc/home_bridge.test.js b/test/erc_to_erc/home_bridge.test.js index 25805ce42..c7902ded7 100644 --- a/test/erc_to_erc/home_bridge.test.js +++ b/test/erc_to_erc/home_bridge.test.js @@ -155,6 +155,36 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG) }) + it('should allow validator to withdraw with zero value', async () => { + const recipient = accounts[5]; + const value = web3.toBigNumber(web3.toWei(0, "ether")); + const balanceBefore = await token.balanceOf(recipient) + const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const {logs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}) + logs[0].event.should.be.equal("SignedForAffirmation"); + logs[0].args.should.be.deep.equal({ + signer: authorities[0], + transactionHash + }); + logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].args.should.be.deep.equal({ + recipient, + value, + transactionHash + }) + const totalSupply = await token.totalSupply() + const balanceAfter = await token.balanceOf(recipient) + balanceAfter.should.be.bignumber.equal(balanceBefore.add(value)) + totalSupply.should.be.bignumber.equal(value) + + const msgHash = Web3Utils.soliditySha3(recipient, value, transactionHash); + const senderHash = Web3Utils.soliditySha3(authorities[0], msgHash) + true.should.be.equal(await homeBridge.affirmationsSigned(senderHash)) + const markedAsProcessed = new web3.BigNumber(2).pow(255).add(1); + markedAsProcessed.should.be.bignumber.equal(await homeBridge.numAffirmationsSigned(msgHash)); + await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG) + }) + it('test with 2 signatures required', async () => { let token2sig = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); let validatorContractWith2Signatures = await BridgeValidators.new() diff --git a/test/native_to_erc/home_bridge_test.js b/test/native_to_erc/home_bridge_test.js index 39aefcace..526daab04 100644 --- a/test/native_to_erc/home_bridge_test.js +++ b/test/native_to_erc/home_bridge_test.js @@ -213,6 +213,32 @@ contract('HomeBridge', async (accounts) => { true.should.be.equal(await homeBridge.affirmationsSigned(senderHash)) }) + it('should allow validator to executeAffirmation with zero value', async () => { + const recipient = accounts[5]; + const value = web3.toBigNumber(web3.toWei(0, "ether")); + const balanceBefore = await web3.eth.getBalance(recipient) + const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const {logs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}) + logs[0].event.should.be.equal("SignedForAffirmation"); + logs[0].args.should.be.deep.equal({ + signer: authorities[0], + transactionHash + }); + logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].args.should.be.deep.equal({ + recipient, + value, + transactionHash + }) + + const balanceAfter = await web3.eth.getBalance(recipient) + balanceAfter.should.be.bignumber.equal(balanceBefore.add(value)) + + const msgHash = Web3Utils.soliditySha3(recipient, value, transactionHash); + const senderHash = Web3Utils.soliditySha3(authorities[0], msgHash) + true.should.be.equal(await homeBridge.affirmationsSigned(senderHash)) + }) + it('test with 2 signatures required', async () => { let validatorContractWith2Signatures = await BridgeValidators.new() let authoritiesTwoAccs = [accounts[1], accounts[2], accounts[3]]; From 88a503bf0033daed80bd596cf2724aaf5b3e4136 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 1 Apr 2019 15:06:21 -0300 Subject: [PATCH 124/187] Use ERC677BridgeTokenRewardable if rewards distributed on erc-to-erc --- deploy/src/erc_to_erc/home.js | 25 ++++++++++++++++++++++++- 1 file changed, 24 insertions(+), 1 deletion(-) diff --git a/deploy/src/erc_to_erc/home.js b/deploy/src/erc_to_erc/home.js index 390542f05..e52a6051f 100644 --- a/deploy/src/erc_to_erc/home.js +++ b/deploy/src/erc_to_erc/home.js @@ -8,6 +8,7 @@ const { sendRawTxHome, logValidatorsAndRewardAccounts } = require('../deploymentUtils') +const { ZERO_ADDRESS } = require('../constants') const { web3Home, deploymentPrivateKey, HOME_RPC_URL } = require('../web3') const EternalStorageProxy = require('../../../build/contracts/EternalStorageProxy.json') @@ -16,6 +17,7 @@ const RewardableValidators = require('../../../build/contracts/RewardableValidat const FeeManagerErcToErcPOSDAO = require('../../../build/contracts/FeeManagerErcToErcPOSDAO') const HomeBridge = require('../../../build/contracts/HomeBridgeErcToErc.json') const ERC677BridgeToken = require('../../../build/contracts/ERC677BridgeToken.json') +const ERC677BridgeTokenRewardable = require('../../../build/contracts/ERC677BridgeTokenRewardable.json') const VALIDATORS = env.VALIDATORS.split(' ') const VALIDATORS_REWARD_ACCOUNTS = env.VALIDATORS_REWARD_ACCOUNTS.split(' ') @@ -160,8 +162,9 @@ async function deployHome() { homeNonce++ console.log('\n[Home] deploying Bridgeble token') + const erc677Contract = isRewardableBridge ? ERC677BridgeTokenRewardable : ERC677BridgeToken const erc677token = await deployContract( - ERC677BridgeToken, + erc677Contract, [BRIDGEABLE_TOKEN_NAME, BRIDGEABLE_TOKEN_SYMBOL, BRIDGEABLE_TOKEN_DECIMALS], { from: DEPLOYMENT_ACCOUNT_ADDRESS, network: 'home', nonce: homeNonce } ) @@ -182,6 +185,26 @@ async function deployHome() { assert.strictEqual(Web3Utils.hexToNumber(setBridgeContract.status), 1, 'Transaction Failed') homeNonce++ + if (isRewardableBridge && BLOCK_REWARD_ADDRESS !== ZERO_ADDRESS) { + console.log('\nset block reward contract on ERC677BridgeToken') + const setBlockRewardContractData = await erc677token.methods + .setBlockRewardContract(BLOCK_REWARD_ADDRESS) + .encodeABI() + const setBlockRewardContract = await sendRawTxHome({ + data: setBlockRewardContractData, + nonce: homeNonce, + to: erc677token.options.address, + privateKey: deploymentPrivateKey, + url: HOME_RPC_URL + }) + assert.strictEqual( + Web3Utils.hexToNumber(setBlockRewardContract.status), + 1, + 'Transaction Failed' + ) + homeNonce++ + } + console.log('transferring ownership of Bridgeble token to homeBridge contract') const txOwnershipData = await erc677token.methods .transferOwnership(homeBridgeStorage.options.address) From 5400cd9c538f2211a0b83d3e623db5d96ae8e6a1 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 1 Apr 2019 16:20:40 -0300 Subject: [PATCH 125/187] Add erc-to-erc reward management schema --- REWARD_MANAGEMENT.md | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/REWARD_MANAGEMENT.md b/REWARD_MANAGEMENT.md index 270655cf1..9b2bb78d4 100644 --- a/REWARD_MANAGEMENT.md +++ b/REWARD_MANAGEMENT.md @@ -19,3 +19,13 @@ Fees are calculated and distributed on Home network. Validators will receive nat ### Home to Foreign transfer Fees are calculated and distributed on Home network. Validators will receive native coins. ![erc-native-hometoforeign](https://user-images.githubusercontent.com/4614574/51607508-96f47480-1ef3-11e9-93a1-0f1111793f2a.png) + +## ERC-TO-ERC + +### Foreign to Home transfer +Fees are calculated and distributed on Home network. Validators will receive ERC20 tokens. +![ERC-ERC-ForeignToHome](https://user-images.githubusercontent.com/4614574/55352936-70752b80-5498-11e9-98ec-f2ca4d9fcb8b.png) + +### Home to Foreign transfer +Fees are calculated and distributed on Home network. Validators will receive ERC20 tokens. +![ERC-ERC-HomeToForeign](https://user-images.githubusercontent.com/4614574/55352955-7d921a80-5498-11e9-92f5-8391952d1f78.png) From 0ae69e69cf97b4c1d9c66cbf878e7d41bedcb32f Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 3 Apr 2019 11:57:35 -0300 Subject: [PATCH 126/187] Fix package-lock.json --- package-lock.json | 1056 +++++++++++++++++++++++++++++++-------------- 1 file changed, 742 insertions(+), 314 deletions(-) diff --git a/package-lock.json b/package-lock.json index 301109f25..8301e96f5 100644 --- a/package-lock.json +++ b/package-lock.json @@ -4,14 +4,6 @@ "lockfileVersion": 1, "requires": true, "dependencies": { - "@babel/runtime": { - "version": "7.3.1", - "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.3.1.tgz", - "integrity": "sha512-7jGW8ppV0ant637pIqAcFfQDDH1orEPGJb8aXfUozuCU3QqX7rX4DA8iwrbPrR1hcH0FTTHz47yQnk+bl5xHQA==", - "requires": { - "regenerator-runtime": "^0.12.0" - } - }, "@resolver-engine/core": { "version": "0.2.1", "resolved": "https://registry.npmjs.org/@resolver-engine/core/-/core-0.2.1.tgz", @@ -54,14 +46,6 @@ "debug": "^3.1.0" } }, - "@types/bn.js": { - "version": "4.11.4", - "resolved": "https://registry.npmjs.org/@types/bn.js/-/bn.js-4.11.4.tgz", - "integrity": "sha512-AO8WW+aRcKWKQAYTfKLzwnpL6U+TfPqS+haRrhCy5ff04Da8WZud3ZgVjspQXaEXJDcTlsjUEVvL39wegDek5w==", - "requires": { - "@types/node": "*" - } - }, "@types/concat-stream": { "version": "1.6.0", "resolved": "https://registry.npmjs.org/@types/concat-stream/-/concat-stream-1.6.0.tgz", @@ -81,14 +65,15 @@ } }, "@types/node": { - "version": "10.12.26", - "resolved": "https://registry.npmjs.org/@types/node/-/node-10.12.26.tgz", - "integrity": "sha512-nMRqS+mL1TOnIJrL6LKJcNZPB8V3eTfRo9FQA2b5gDvrHurC8XbSA86KNe0dShlEL7ReWJv/OU9NL7Z0dnqWTg==" + "version": "10.14.4", + "resolved": "https://registry.npmjs.org/@types/node/-/node-10.14.4.tgz", + "integrity": "sha512-DT25xX/YgyPKiHFOpNuANIQIVvYEwCWXgK2jYYwqgaMrYE6+tq+DtmMwlD3drl6DJbUwtlIDnn0d7tIn/EbXBg==", + "dev": true }, "@types/qs": { - "version": "6.5.1", - "resolved": "https://registry.npmjs.org/@types/qs/-/qs-6.5.1.tgz", - "integrity": "sha512-mNhVdZHdtKHMMxbqzNK3RzkBcN1cux3AvuCYGTvjEIQT2uheH3eCAyYsbMbh2Bq8nXkeOWs1kyDiF7geWRFQ4Q==", + "version": "6.5.2", + "resolved": "https://registry.npmjs.org/@types/qs/-/qs-6.5.2.tgz", + "integrity": "sha512-47kAAs3yV/hROraCTQYDMh4p/6zI9+gtssjD0kq9OWsGdLcBge59rl49FnCuJ+iWxEKiqFz6KXzeGH5DRVjNJA==", "dev": true }, "abbrev": { @@ -106,11 +91,19 @@ "web3": "^0.18.4" } }, + "accepts": { + "version": "1.3.5", + "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.5.tgz", + "integrity": "sha1-63d99gEXI6OxTopywIBcjoZ0a9I=", + "requires": { + "mime-types": "~2.1.18", + "negotiator": "0.6.1" + } + }, "ajv": { - "version": "6.9.1", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.9.1.tgz", - "integrity": "sha512-XDN92U311aINL77ieWHmqCcNlwjoP5cHXDxIxbf2MaPYuCXOHS7gHH8jktxeK5omgd52XbSTX6a4Piwd1pQmzA==", - "dev": true, + "version": "6.10.0", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.10.0.tgz", + "integrity": "sha512-nffhOpkymDECQyR0mnsUtoCE8RlX38G0rYP+wgLWFyZuUyuuojSSvi/+euOiQBIn63whYwYVIIH1TvE3tu4OEg==", "requires": { "fast-deep-equal": "^2.0.1", "fast-json-stable-stringify": "^2.0.0", @@ -229,6 +222,11 @@ "integrity": "sha1-45sJrqne+Gao8gbiiK9jkZuuOcQ=", "dev": true }, + "array-flatten": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-1.1.1.tgz", + "integrity": "sha1-ml9pkFGx5wczKPKgCJaLZOopVdI=" + }, "array-unique": { "version": "0.3.2", "resolved": "https://registry.npmjs.org/array-unique/-/array-unique-0.3.2.tgz", @@ -245,7 +243,6 @@ "version": "0.2.4", "resolved": "https://registry.npmjs.org/asn1/-/asn1-0.2.4.tgz", "integrity": "sha512-jxwzQpLQjSmWXgwaCZE9Nz+glAG01yF1QnWgbhGwHI5A6FRIEY6IVqtHhIepHqI7/kyEyQEagBC5mBEFlIYvdg==", - "dev": true, "requires": { "safer-buffer": "~2.1.0" } @@ -253,8 +250,7 @@ "assert-plus": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", - "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", - "dev": true + "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=" }, "assertion-error": { "version": "1.1.0", @@ -275,16 +271,20 @@ "dev": true }, "async-each": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/async-each/-/async-each-1.0.1.tgz", - "integrity": "sha1-GdOGodntxufByF04iu28xW0zYC0=", + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/async-each/-/async-each-1.0.2.tgz", + "integrity": "sha512-6xrbvN0MOBKSJDdonmSSz2OwFSgxRaVtBDes26mj9KIGtDo+g9xosFRSC+i1gQh2oAN/tQ62AI/pGZGQjVOiRg==", "dev": true }, + "async-limiter": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/async-limiter/-/async-limiter-1.0.0.tgz", + "integrity": "sha512-jp/uFnooOiO+L211eZOoSyzpOITMXx1rBITauYykG3BRYPu8h0UcxsPNB04RR5vo4Tyz3+ay17tR6JVf9qzYWg==" + }, "asynckit": { "version": "0.4.0", "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", - "integrity": "sha1-x57Zf380y48robyXkLzDZkdLS3k=", - "dev": true + "integrity": "sha1-x57Zf380y48robyXkLzDZkdLS3k=" }, "atob": { "version": "2.1.2", @@ -295,14 +295,12 @@ "aws-sign2": { "version": "0.7.0", "resolved": "https://registry.npmjs.org/aws-sign2/-/aws-sign2-0.7.0.tgz", - "integrity": "sha1-tG6JCTSpWR8tL2+G1+ap8bP+dqg=", - "dev": true + "integrity": "sha1-tG6JCTSpWR8tL2+G1+ap8bP+dqg=" }, "aws4": { "version": "1.8.0", "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.8.0.tgz", - "integrity": "sha512-ReZxvNHIOv88FlT7rxcXIIC0fPt4KZqZbOlivyWtXLt8ESx84zd3kMC6iK5jVeS2qt+g7ftS7ye4fi06X5rtRQ==", - "dev": true + "integrity": "sha512-ReZxvNHIOv88FlT7rxcXIIC0fPt4KZqZbOlivyWtXLt8ESx84zd3kMC6iK5jVeS2qt+g7ftS7ye4fi06X5rtRQ==" }, "balanced-match": { "version": "1.0.0", @@ -368,7 +366,6 @@ "version": "1.0.2", "resolved": "https://registry.npmjs.org/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.2.tgz", "integrity": "sha1-pDAdOJtqQ/m2f/PKEaP2Y342Dp4=", - "dev": true, "requires": { "tweetnacl": "^0.14.3" } @@ -379,15 +376,42 @@ "dev": true }, "binary-extensions": { - "version": "1.13.0", - "resolved": "https://registry.npmjs.org/binary-extensions/-/binary-extensions-1.13.0.tgz", - "integrity": "sha512-EgmjVLMn22z7eGGv3kcnHwSnJXmFHjISTY9E/S5lIcTD3Oxw05QTcBLNkJFzcb3cNueUdF/IN4U+d78V0zO8Hw==", + "version": "1.13.1", + "resolved": "https://registry.npmjs.org/binary-extensions/-/binary-extensions-1.13.1.tgz", + "integrity": "sha512-Un7MIEDdUC5gNpcGDV97op1Ywk748MpHcFTHoYs6qnj1Z3j7I53VG3nwZhKzoBZmbdRNnb6WRdFlwl7tSDuZGw==", "dev": true }, "bn.js": { - "version": "4.11.8", - "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.11.8.tgz", - "integrity": "sha512-ItfYfPLkWHUjckQCk8xC+LwxgK8NYcXywGigJgSwOP8Y2iyWT4f2vsZnoOXTTbo+o5yXmIUJ4gn5538SO5S3gA==" + "version": "4.11.6", + "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.11.6.tgz", + "integrity": "sha1-UzRK2xRhehP26N0s4okF0cC6MhU=" + }, + "body-parser": { + "version": "1.18.3", + "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.18.3.tgz", + "integrity": "sha1-WykhmP/dVTs6DyDe0FkrlWlVyLQ=", + "requires": { + "bytes": "3.0.0", + "content-type": "~1.0.4", + "debug": "2.6.9", + "depd": "~1.1.2", + "http-errors": "~1.6.3", + "iconv-lite": "0.4.23", + "on-finished": "~2.3.0", + "qs": "6.5.2", + "raw-body": "2.3.3", + "type-is": "~1.6.16" + }, + "dependencies": { + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "requires": { + "ms": "2.0.0" + } + } + } }, "boxen": { "version": "1.3.0", @@ -495,7 +519,6 @@ "version": "0.0.4", "resolved": "https://registry.npmjs.org/browserify-sha3/-/browserify-sha3-0.0.4.tgz", "integrity": "sha1-CGxHuMgjFsnUcCLCYYWVRXbdjiY=", - "dev": true, "requires": { "js-sha3": "^0.6.1", "safe-buffer": "^5.1.1" @@ -512,6 +535,11 @@ "resolved": "https://registry.npmjs.org/buffer-to-arraybuffer/-/buffer-to-arraybuffer-0.0.5.tgz", "integrity": "sha1-YGSkD6dutDxyOrqe+PbhIW0QURo=" }, + "bytes": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.0.0.tgz", + "integrity": "sha1-0ygVQE1olpn4Wk6k+odV3ROpYEg=" + }, "cache-base": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/cache-base/-/cache-base-1.0.1.tgz", @@ -543,8 +571,7 @@ "caseless": { "version": "0.12.0", "resolved": "https://registry.npmjs.org/caseless/-/caseless-0.12.0.tgz", - "integrity": "sha1-G2gcIf+EAzyCZUMJBolCDRhxUdw=", - "dev": true + "integrity": "sha1-G2gcIf+EAzyCZUMJBolCDRhxUdw=" }, "chai": { "version": "4.2.0", @@ -616,9 +643,9 @@ "dev": true }, "chokidar": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-2.1.1.tgz", - "integrity": "sha512-gfw3p2oQV2wEt+8VuMlNsPjCxDxvvgnm/kz+uATu805mWVF8IJN7uz9DN7iBz+RMJISmiVbCOBFs9qBGMjtPfQ==", + "version": "2.1.5", + "resolved": "https://registry.npmjs.org/chokidar/-/chokidar-2.1.5.tgz", + "integrity": "sha512-i0TprVWp+Kj4WRPtInjexJ8Q+BqTE909VpH8xVhXrJkoc5QC8VO9TryGOqTr+2hljzc1sC62t22h5tZePodM/A==", "dev": true, "requires": { "anymatch": "^2.0.0", @@ -632,7 +659,7 @@ "normalize-path": "^3.0.0", "path-is-absolute": "^1.0.0", "readdirp": "^2.2.1", - "upath": "^1.1.0" + "upath": "^1.1.1" } }, "ci-info": { @@ -764,7 +791,6 @@ "version": "1.0.7", "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.7.tgz", "integrity": "sha512-brWl9y6vOB1xYPZcpZde3N9zDByXTosAeMDo4p1wzo6UMOX4vumB+TP1RZ76sfE6Md68Q0NJSrE/gbezd4Ul+w==", - "dev": true, "requires": { "delayed-stream": "~1.0.0" } @@ -811,6 +837,26 @@ "xdg-basedir": "^3.0.0" } }, + "content-disposition": { + "version": "0.5.2", + "resolved": "https://registry.npmjs.org/content-disposition/-/content-disposition-0.5.2.tgz", + "integrity": "sha1-DPaLud318r55YcOoUXjLhdunjLQ=" + }, + "content-type": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/content-type/-/content-type-1.0.4.tgz", + "integrity": "sha512-hIP3EEPs8tB9AT1L+NUqtwOAps4mk2Zob89MWXMHjHWg9milF/j4osnnQLXBCBFBk/tvIG/tUc9mOUJiPBhPXA==" + }, + "cookie": { + "version": "0.3.1", + "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.3.1.tgz", + "integrity": "sha1-5+Ch+e9DtMi6klxcWpboBtFoc7s=" + }, + "cookie-signature": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz", + "integrity": "sha1-4wOogrNCzD7oylE6eZmXNNqzriw=" + }, "copy-descriptor": { "version": "0.1.1", "resolved": "https://registry.npmjs.org/copy-descriptor/-/copy-descriptor-0.1.1.tgz", @@ -820,8 +866,16 @@ "core-util-is": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz", - "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=", - "dev": true + "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=" + }, + "cors": { + "version": "2.8.5", + "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.5.tgz", + "integrity": "sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==", + "requires": { + "object-assign": "^4", + "vary": "^1" + } }, "create-error-class": { "version": "3.0.2", @@ -865,7 +919,6 @@ "version": "1.14.1", "resolved": "https://registry.npmjs.org/dashdash/-/dashdash-1.14.1.tgz", "integrity": "sha1-hTz6D3y+L+1d4gMmuN1YEDX24vA=", - "dev": true, "requires": { "assert-plus": "^1.0.0" } @@ -923,6 +976,14 @@ "integrity": "sha1-s2nW+128E+7PUk+RsHD+7cNXzzQ=", "dev": true }, + "define-properties": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/define-properties/-/define-properties-1.1.3.tgz", + "integrity": "sha512-3MqfYKj2lLzdMSf8ZIZE/V+Zuy+BgD6f164e8K2w7dgnpKArBDerGYpM46IYYcjnkdPNMjPk9A6VFB8+3SKlXQ==", + "requires": { + "object-keys": "^1.0.12" + } + }, "define-property": { "version": "2.0.2", "resolved": "https://registry.npmjs.org/define-property/-/define-property-2.0.2.tgz", @@ -967,8 +1028,17 @@ "delayed-stream": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", - "integrity": "sha1-3zrhmayt+31ECqrgsp4icrJOxhk=", - "dev": true + "integrity": "sha1-3zrhmayt+31ECqrgsp4icrJOxhk=" + }, + "depd": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/depd/-/depd-1.1.2.tgz", + "integrity": "sha1-m81S4UwJd2PnSbJ0xDRu0uVgtak=" + }, + "destroy": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/destroy/-/destroy-1.0.4.tgz", + "integrity": "sha1-l4hXRCxEdJ5CBmE+N5RiBYJqvYA=" }, "diff": { "version": "3.3.1", @@ -999,12 +1069,16 @@ "version": "0.1.2", "resolved": "https://registry.npmjs.org/ecc-jsbn/-/ecc-jsbn-0.1.2.tgz", "integrity": "sha1-OoOpBOVDUyh4dMVkt1SThoSamMk=", - "dev": true, "requires": { "jsbn": "~0.1.0", "safer-buffer": "^2.1.0" } }, + "ee-first": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/ee-first/-/ee-first-1.1.1.tgz", + "integrity": "sha1-WQxhFWsK4vTwJVcyoViyZrxWsh0=" + }, "elliptic": { "version": "6.4.1", "resolved": "https://registry.npmjs.org/elliptic/-/elliptic-6.4.1.tgz", @@ -1019,6 +1093,11 @@ "minimalistic-crypto-utils": "^1.0.0" } }, + "encodeurl": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-1.0.2.tgz", + "integrity": "sha1-rT/0yG7C0CkyL1oCw6mmBslbP1k=" + }, "error-ex": { "version": "1.3.2", "resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.2.tgz", @@ -1027,6 +1106,34 @@ "is-arrayish": "^0.2.1" } }, + "es-abstract": { + "version": "1.13.0", + "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.13.0.tgz", + "integrity": "sha512-vDZfg/ykNxQVwup/8E1BZhVzFfBxs9NqMzGcvIJrqg5k2/5Za2bWo40dK2J1pgLngZ7c+Shh8lwYtLGyrwPutg==", + "requires": { + "es-to-primitive": "^1.2.0", + "function-bind": "^1.1.1", + "has": "^1.0.3", + "is-callable": "^1.1.4", + "is-regex": "^1.0.4", + "object-keys": "^1.0.12" + } + }, + "es-to-primitive": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/es-to-primitive/-/es-to-primitive-1.2.0.tgz", + "integrity": "sha512-qZryBOJjV//LaxLTV6UC//WewneB3LcXOL9NP++ozKVXsIIIpm/2c13UDiD9Jp2eThsecw9m3jPqDwTyobcdbg==", + "requires": { + "is-callable": "^1.1.4", + "is-date-object": "^1.0.1", + "is-symbol": "^1.0.2" + } + }, + "escape-html": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/escape-html/-/escape-html-1.0.3.tgz", + "integrity": "sha1-Aljq5NPQwJdN4cFpGI7wBR0dGYg=" + }, "escape-string-regexp": { "version": "1.0.5", "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", @@ -1075,6 +1182,11 @@ "integrity": "sha1-Cr9PHKpbyx96nYrMbepPqqBLrJs=", "dev": true }, + "etag": { + "version": "1.8.1", + "resolved": "https://registry.npmjs.org/etag/-/etag-1.8.1.tgz", + "integrity": "sha1-Qa4u62XvpiJorr/qg6x9eSmbCIc=" + }, "eth-gas-reporter": { "version": "0.1.12", "resolved": "https://registry.npmjs.org/eth-gas-reporter/-/eth-gas-reporter-0.1.12.tgz", @@ -1096,12 +1208,16 @@ } }, "eth-lib": { - "version": "0.2.8", - "resolved": "https://registry.npmjs.org/eth-lib/-/eth-lib-0.2.8.tgz", - "integrity": "sha512-ArJ7x1WcWOlSpzdoTBX8vkwlkSQ85CjjifSZtV4co64vWxSV8geWfPI9x4SVYu3DSxnX4yWFVTtGL+j9DUFLNw==", + "version": "0.1.27", + "resolved": "https://registry.npmjs.org/eth-lib/-/eth-lib-0.1.27.tgz", + "integrity": "sha512-B8czsfkJYzn2UIEMwjc7Mbj+Cy72V+/OXH/tb44LV8jhrjizQJJ325xMOMyk3+ETa6r6oi0jsUY14+om8mQMWA==", "requires": { "bn.js": "^4.11.6", "elliptic": "^6.4.0", + "keccakjs": "^0.2.1", + "nano-json-stream-parser": "^0.1.2", + "servify": "^0.1.12", + "ws": "^3.0.0", "xhr-request-promise": "^0.1.2" } }, @@ -1121,13 +1237,6 @@ "requires": { "bn.js": "4.11.6", "number-to-bn": "1.7.0" - }, - "dependencies": { - "bn.js": { - "version": "4.11.6", - "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.11.6.tgz", - "integrity": "sha1-UzRK2xRhehP26N0s4okF0cC6MhU=" - } } }, "execa": { @@ -1189,11 +1298,62 @@ } } }, + "express": { + "version": "4.16.4", + "resolved": "https://registry.npmjs.org/express/-/express-4.16.4.tgz", + "integrity": "sha512-j12Uuyb4FMrd/qQAm6uCHAkPtO8FDTRJZBDd5D2KOL2eLaz1yUNdUB/NOIyq0iU4q4cFarsUCrnFDPBcnksuOg==", + "requires": { + "accepts": "~1.3.5", + "array-flatten": "1.1.1", + "body-parser": "1.18.3", + "content-disposition": "0.5.2", + "content-type": "~1.0.4", + "cookie": "0.3.1", + "cookie-signature": "1.0.6", + "debug": "2.6.9", + "depd": "~1.1.2", + "encodeurl": "~1.0.2", + "escape-html": "~1.0.3", + "etag": "~1.8.1", + "finalhandler": "1.1.1", + "fresh": "0.5.2", + "merge-descriptors": "1.0.1", + "methods": "~1.1.2", + "on-finished": "~2.3.0", + "parseurl": "~1.3.2", + "path-to-regexp": "0.1.7", + "proxy-addr": "~2.0.4", + "qs": "6.5.2", + "range-parser": "~1.2.0", + "safe-buffer": "5.1.2", + "send": "0.16.2", + "serve-static": "1.13.2", + "setprototypeof": "1.1.0", + "statuses": "~1.4.0", + "type-is": "~1.6.16", + "utils-merge": "1.0.1", + "vary": "~1.1.2" + }, + "dependencies": { + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "requires": { + "ms": "2.0.0" + } + }, + "statuses": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.4.0.tgz", + "integrity": "sha512-zhSCtt8v2NDrRlPQpCNtw/heZLtfUDqxBM1udqikb/Hbk52LK4nQSwr10u77iopCW5LsyHpuXS0GnEc48mLeew==" + } + } + }, "extend": { "version": "3.0.2", "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz", - "integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==", - "dev": true + "integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==" }, "extend-shallow": { "version": "3.0.2", @@ -1284,20 +1444,17 @@ "extsprintf": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/extsprintf/-/extsprintf-1.3.0.tgz", - "integrity": "sha1-lpGEQOMEGnpBT4xS48V06zw+HgU=", - "dev": true + "integrity": "sha1-lpGEQOMEGnpBT4xS48V06zw+HgU=" }, "fast-deep-equal": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-2.0.1.tgz", - "integrity": "sha1-ewUhjd+WZ79/Nwv3/bLLFf3Qqkk=", - "dev": true + "integrity": "sha1-ewUhjd+WZ79/Nwv3/bLLFf3Qqkk=" }, "fast-json-stable-stringify": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.0.0.tgz", - "integrity": "sha1-1RQsDK7msRifh9OnYREGT4bIu/I=", - "dev": true + "integrity": "sha1-1RQsDK7msRifh9OnYREGT4bIu/I=" }, "fast-levenshtein": { "version": "2.0.6", @@ -1328,6 +1485,35 @@ } } }, + "finalhandler": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/finalhandler/-/finalhandler-1.1.1.tgz", + "integrity": "sha512-Y1GUDo39ez4aHAw7MysnUD5JzYX+WaIj8I57kO3aEPT1fFRL4sr7mjei97FgnwhAyyzRYmQZaTHb2+9uZ1dPtg==", + "requires": { + "debug": "2.6.9", + "encodeurl": "~1.0.2", + "escape-html": "~1.0.3", + "on-finished": "~2.3.0", + "parseurl": "~1.3.2", + "statuses": "~1.4.0", + "unpipe": "~1.0.0" + }, + "dependencies": { + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "requires": { + "ms": "2.0.0" + } + }, + "statuses": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.4.0.tgz", + "integrity": "sha512-zhSCtt8v2NDrRlPQpCNtw/heZLtfUDqxBM1udqikb/Hbk52LK4nQSwr10u77iopCW5LsyHpuXS0GnEc48mLeew==" + } + } + }, "find-up": { "version": "1.1.2", "resolved": "https://registry.npmjs.org/find-up/-/find-up-1.1.2.tgz", @@ -1354,20 +1540,23 @@ "forever-agent": { "version": "0.6.1", "resolved": "https://registry.npmjs.org/forever-agent/-/forever-agent-0.6.1.tgz", - "integrity": "sha1-+8cfDEGt6zf5bFd60e1C2P2sypE=", - "dev": true + "integrity": "sha1-+8cfDEGt6zf5bFd60e1C2P2sypE=" }, "form-data": { "version": "2.3.3", "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.3.3.tgz", "integrity": "sha512-1lLKB2Mu3aGP1Q/2eCOx0fNbRMe7XdwktwOruhfqqd0rIJWwN4Dh+E3hrPSlDCXnSR7UtZ1N38rVXm+6+MEhJQ==", - "dev": true, "requires": { "asynckit": "^0.4.0", "combined-stream": "^1.0.6", "mime-types": "^2.1.12" } }, + "forwarded": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.1.2.tgz", + "integrity": "sha1-mMI9qxF1ZXuMBXPozszZGw/xjIQ=" + }, "fragment-cache": { "version": "0.2.1", "resolved": "https://registry.npmjs.org/fragment-cache/-/fragment-cache-0.2.1.tgz", @@ -1377,6 +1566,11 @@ "map-cache": "^0.2.2" } }, + "fresh": { + "version": "0.5.2", + "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.5.2.tgz", + "integrity": "sha1-PYyt2Q2XZWn6g1qx+OSyOhBWBac=" + }, "fs-extra": { "version": "0.30.0", "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-0.30.0.tgz", @@ -1923,10 +2117,15 @@ } } }, + "function-bind": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz", + "integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==" + }, "ganache-cli": { - "version": "6.3.0", - "resolved": "https://registry.npmjs.org/ganache-cli/-/ganache-cli-6.3.0.tgz", - "integrity": "sha512-8SyzfX2ipRVBx1fBZLg3j8I3E334U3Vazk5mEpYcWqnIjC2ace6jtOXHG4aTuAvSz3+HzQ8p8pRjOJxdDZ2pnQ==", + "version": "6.4.1", + "resolved": "https://registry.npmjs.org/ganache-cli/-/ganache-cli-6.4.1.tgz", + "integrity": "sha512-MUZ1DNnmlTrXnH6EuINuew75AI9d/wbIC0WpZCJo5Endsf6ZwEvfnfxGMpEnVizRri1mon2WWxLGAmALDxVcRQ==", "requires": { "bn.js": "4.11.8", "source-map-support": "0.5.9", @@ -1935,23 +2134,28 @@ "dependencies": { "ansi-regex": { "version": "3.0.0", - "bundled": true + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", + "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=" }, "bn.js": { "version": "4.11.8", - "bundled": true + "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.11.8.tgz", + "integrity": "sha512-ItfYfPLkWHUjckQCk8xC+LwxgK8NYcXywGigJgSwOP8Y2iyWT4f2vsZnoOXTTbo+o5yXmIUJ4gn5538SO5S3gA==" }, "buffer-from": { "version": "1.1.1", - "bundled": true + "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.1.tgz", + "integrity": "sha512-MQcXEUbCKtEo7bhqEs6560Hyd4XaovZlO/k9V3hjVUF/zwW7KBVdSK4gIt/bzwS9MbR5qob+F5jusZsb0YQK2A==" }, "camelcase": { "version": "4.1.0", - "bundled": true + "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-4.1.0.tgz", + "integrity": "sha1-1UVjW+HjPFQmScaRc+Xeas+uNN0=" }, "cliui": { "version": "4.1.0", - "bundled": true, + "resolved": "https://registry.npmjs.org/cliui/-/cliui-4.1.0.tgz", + "integrity": "sha512-4FG+RSG9DL7uEwRUZXZn3SS34DiDPfzP0VOiEwtUWlE+AR2EIg+hSyvrIgUUfhdgR/UkAeW2QHgeP+hWrXs7jQ==", "requires": { "string-width": "^2.1.1", "strip-ansi": "^4.0.0", @@ -1960,11 +2164,13 @@ }, "code-point-at": { "version": "1.1.0", - "bundled": true + "resolved": "https://registry.npmjs.org/code-point-at/-/code-point-at-1.1.0.tgz", + "integrity": "sha1-DQcLTQQ6W+ozovGkDi7bPZpMz3c=" }, "cross-spawn": { "version": "5.1.0", - "bundled": true, + "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-5.1.0.tgz", + "integrity": "sha1-6L0O/uWPz/b4+UUQoKVUu/ojVEk=", "requires": { "lru-cache": "^4.0.1", "shebang-command": "^1.2.0", @@ -1973,11 +2179,13 @@ }, "decamelize": { "version": "1.2.0", - "bundled": true + "resolved": "https://registry.npmjs.org/decamelize/-/decamelize-1.2.0.tgz", + "integrity": "sha1-9lNNFRSCabIDUue+4m9QH5oZEpA=" }, "execa": { "version": "0.7.0", - "bundled": true, + "resolved": "https://registry.npmjs.org/execa/-/execa-0.7.0.tgz", + "integrity": "sha1-lEvs00zEHuMqY6n68nrVpl/Fl3c=", "requires": { "cross-spawn": "^5.0.1", "get-stream": "^3.0.0", @@ -1990,45 +2198,54 @@ }, "find-up": { "version": "2.1.0", - "bundled": true, + "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", + "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", "requires": { "locate-path": "^2.0.0" } }, "get-caller-file": { "version": "1.0.3", - "bundled": true + "resolved": "https://registry.npmjs.org/get-caller-file/-/get-caller-file-1.0.3.tgz", + "integrity": "sha512-3t6rVToeoZfYSGd8YoLFR2DJkiQrIiUrGcjvFX2mDw3bn6k2OtwHN0TNCLbBO+w8qTvimhDkv+LSscbJY1vE6w==" }, "get-stream": { "version": "3.0.0", - "bundled": true + "resolved": "http://registry.npmjs.org/get-stream/-/get-stream-3.0.0.tgz", + "integrity": "sha1-jpQ9E1jcN1VQVOy+LtsFqhdO3hQ=" }, "invert-kv": { "version": "1.0.0", - "bundled": true + "resolved": "https://registry.npmjs.org/invert-kv/-/invert-kv-1.0.0.tgz", + "integrity": "sha1-EEqOSqym09jNFXqO+L+rLXo//bY=" }, "is-fullwidth-code-point": { "version": "2.0.0", - "bundled": true + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", + "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=" }, "is-stream": { "version": "1.1.0", - "bundled": true + "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-1.1.0.tgz", + "integrity": "sha1-EtSj3U5o4Lec6428hBc66A2RykQ=" }, "isexe": { "version": "2.0.0", - "bundled": true + "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", + "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=" }, "lcid": { "version": "1.0.0", - "bundled": true, + "resolved": "https://registry.npmjs.org/lcid/-/lcid-1.0.0.tgz", + "integrity": "sha1-MIrMr6C8SDo4Z7S28rlQYlHRuDU=", "requires": { "invert-kv": "^1.0.0" } }, "locate-path": { "version": "2.0.0", - "bundled": true, + "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-2.0.0.tgz", + "integrity": "sha1-K1aLJl7slExtnA3pw9u7ygNUzY4=", "requires": { "p-locate": "^2.0.0", "path-exists": "^3.0.0" @@ -2036,7 +2253,8 @@ }, "lru-cache": { "version": "4.1.4", - "bundled": true, + "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-4.1.4.tgz", + "integrity": "sha512-EPstzZ23znHUVLKj+lcXO1KvZkrlw+ZirdwvOmnAnA/1PB4ggyXJ77LRkCqkff+ShQ+cqoxCxLQOh4cKITO5iA==", "requires": { "pseudomap": "^1.0.2", "yallist": "^3.0.2" @@ -2044,29 +2262,34 @@ }, "mem": { "version": "1.1.0", - "bundled": true, + "resolved": "https://registry.npmjs.org/mem/-/mem-1.1.0.tgz", + "integrity": "sha1-Xt1StIXKHZAP5kiVUFOZoN+kX3Y=", "requires": { "mimic-fn": "^1.0.0" } }, "mimic-fn": { "version": "1.2.0", - "bundled": true + "resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-1.2.0.tgz", + "integrity": "sha512-jf84uxzwiuiIVKiOLpfYk7N46TSy8ubTonmneY9vrpHNAnp0QBt2BxWV9dO3/j+BoVAb+a5G6YDPW3M5HOdMWQ==" }, "npm-run-path": { "version": "2.0.2", - "bundled": true, + "resolved": "https://registry.npmjs.org/npm-run-path/-/npm-run-path-2.0.2.tgz", + "integrity": "sha1-NakjLfo11wZ7TLLd8jV7GHFTbF8=", "requires": { "path-key": "^2.0.0" } }, "number-is-nan": { "version": "1.0.1", - "bundled": true + "resolved": "https://registry.npmjs.org/number-is-nan/-/number-is-nan-1.0.1.tgz", + "integrity": "sha1-CXtgK1NCKlIsGvuHkDGDNpQaAR0=" }, "os-locale": { "version": "2.1.0", - "bundled": true, + "resolved": "https://registry.npmjs.org/os-locale/-/os-locale-2.1.0.tgz", + "integrity": "sha512-3sslG3zJbEYcaC4YVAvDorjGxc7tv6KVATnLPZONiljsUncvihe9BQoVCEs0RZ1kmf4Hk9OBqlZfJZWI4GanKA==", "requires": { "execa": "^0.7.0", "lcid": "^1.0.0", @@ -2075,72 +2298,87 @@ }, "p-finally": { "version": "1.0.0", - "bundled": true + "resolved": "https://registry.npmjs.org/p-finally/-/p-finally-1.0.0.tgz", + "integrity": "sha1-P7z7FbiZpEEjs0ttzBi3JDNqLK4=" }, "p-limit": { "version": "1.3.0", - "bundled": true, + "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-1.3.0.tgz", + "integrity": "sha512-vvcXsLAJ9Dr5rQOPk7toZQZJApBl2K4J6dANSsEuh6QI41JYcsS/qhTGa9ErIUUgK3WNQoJYvylxvjqmiqEA9Q==", "requires": { "p-try": "^1.0.0" } }, "p-locate": { "version": "2.0.0", - "bundled": true, + "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-2.0.0.tgz", + "integrity": "sha1-IKAQOyIqcMj9OcwuWAaA893l7EM=", "requires": { "p-limit": "^1.1.0" } }, "p-try": { "version": "1.0.0", - "bundled": true + "resolved": "https://registry.npmjs.org/p-try/-/p-try-1.0.0.tgz", + "integrity": "sha1-y8ec26+P1CKOE/Yh8rGiN8GyB7M=" }, "path-exists": { "version": "3.0.0", - "bundled": true + "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", + "integrity": "sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=" }, "path-key": { "version": "2.0.1", - "bundled": true + "resolved": "https://registry.npmjs.org/path-key/-/path-key-2.0.1.tgz", + "integrity": "sha1-QRyttXTFoUDTpLGRDUDYDMn0C0A=" }, "pseudomap": { "version": "1.0.2", - "bundled": true + "resolved": "https://registry.npmjs.org/pseudomap/-/pseudomap-1.0.2.tgz", + "integrity": "sha1-8FKijacOYYkX7wqKw0wa5aaChrM=" }, "require-directory": { "version": "2.1.1", - "bundled": true + "resolved": "https://registry.npmjs.org/require-directory/-/require-directory-2.1.1.tgz", + "integrity": "sha1-jGStX9MNqxyXbiNE/+f3kqam30I=" }, "require-main-filename": { "version": "1.0.1", - "bundled": true + "resolved": "https://registry.npmjs.org/require-main-filename/-/require-main-filename-1.0.1.tgz", + "integrity": "sha1-l/cXtp1IeE9fUmpsWqj/3aBVpNE=" }, "set-blocking": { "version": "2.0.0", - "bundled": true + "resolved": "https://registry.npmjs.org/set-blocking/-/set-blocking-2.0.0.tgz", + "integrity": "sha1-BF+XgtARrppoA93TgrJDkrPYkPc=" }, "shebang-command": { "version": "1.2.0", - "bundled": true, + "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-1.2.0.tgz", + "integrity": "sha1-RKrGW2lbAzmJaMOfNj/uXer98eo=", "requires": { "shebang-regex": "^1.0.0" } }, "shebang-regex": { "version": "1.0.0", - "bundled": true + "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-1.0.0.tgz", + "integrity": "sha1-2kL0l0DAtC2yypcoVxyxkMmO/qM=" }, "signal-exit": { "version": "3.0.2", - "bundled": true + "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.2.tgz", + "integrity": "sha1-tf3AjxKH6hF4Yo5BXiUTK3NkbG0=" }, "source-map": { "version": "0.6.1", - "bundled": true + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==" }, "source-map-support": { "version": "0.5.9", - "bundled": true, + "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.9.tgz", + "integrity": "sha512-gR6Rw4MvUlYy83vP0vxoVNzM6t8MUXqNuRsuBmBHQDu1Fh6X015FrLdgoDKcNdkwGubozq0P4N0Q37UyFVr1EA==", "requires": { "buffer-from": "^1.0.0", "source-map": "^0.6.0" @@ -2148,7 +2386,8 @@ }, "string-width": { "version": "2.1.1", - "bundled": true, + "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", + "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", "requires": { "is-fullwidth-code-point": "^2.0.0", "strip-ansi": "^4.0.0" @@ -2156,29 +2395,34 @@ }, "strip-ansi": { "version": "4.0.0", - "bundled": true, + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", + "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", "requires": { "ansi-regex": "^3.0.0" } }, "strip-eof": { "version": "1.0.0", - "bundled": true + "resolved": "http://registry.npmjs.org/strip-eof/-/strip-eof-1.0.0.tgz", + "integrity": "sha1-u0P/VZim6wXYm1n80SnJgzE2Br8=" }, "which": { "version": "1.3.1", - "bundled": true, + "resolved": "https://registry.npmjs.org/which/-/which-1.3.1.tgz", + "integrity": "sha512-HxJdYWq1MTIQbJ3nw0cqssHoTNU267KlrDuGZ1WYlxDStUtKUhOaJmh112/TZmHxxUfuJqPXSOm7tDyas0OSIQ==", "requires": { "isexe": "^2.0.0" } }, "which-module": { "version": "2.0.0", - "bundled": true + "resolved": "https://registry.npmjs.org/which-module/-/which-module-2.0.0.tgz", + "integrity": "sha1-2e8H3Od7mQK4o6j6SzHD4/fm6Ho=" }, "wrap-ansi": { "version": "2.1.0", - "bundled": true, + "resolved": "http://registry.npmjs.org/wrap-ansi/-/wrap-ansi-2.1.0.tgz", + "integrity": "sha1-2Pw9KE3QV5T+hJc8rs3Rz4JP3YU=", "requires": { "string-width": "^1.0.1", "strip-ansi": "^3.0.1" @@ -2186,18 +2430,21 @@ "dependencies": { "ansi-regex": { "version": "2.1.1", - "bundled": true + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz", + "integrity": "sha1-w7M6te42DYbg5ijwRorn7yfWVN8=" }, "is-fullwidth-code-point": { "version": "1.0.0", - "bundled": true, + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz", + "integrity": "sha1-754xOG8DGn8NZDr4L95QxFfvAMs=", "requires": { "number-is-nan": "^1.0.0" } }, "string-width": { "version": "1.0.2", - "bundled": true, + "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz", + "integrity": "sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=", "requires": { "code-point-at": "^1.0.0", "is-fullwidth-code-point": "^1.0.0", @@ -2206,7 +2453,8 @@ }, "strip-ansi": { "version": "3.0.1", - "bundled": true, + "resolved": "http://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", + "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", "requires": { "ansi-regex": "^2.0.0" } @@ -2215,15 +2463,18 @@ }, "y18n": { "version": "3.2.1", - "bundled": true + "resolved": "https://registry.npmjs.org/y18n/-/y18n-3.2.1.tgz", + "integrity": "sha1-bRX7qITAhnnA136I53WegR4H+kE=" }, "yallist": { "version": "3.0.2", - "bundled": true + "resolved": "https://registry.npmjs.org/yallist/-/yallist-3.0.2.tgz", + "integrity": "sha1-hFK0u36Dx8GI2AQcGoN8dz1ti7k=" }, "yargs": { "version": "11.1.0", - "bundled": true, + "resolved": "http://registry.npmjs.org/yargs/-/yargs-11.1.0.tgz", + "integrity": "sha512-NwW69J42EsCSanF8kyn5upxvjp5ds+t3+udGBeTbFnERA+lF541DDpMawzo4z6W/QrzNM18D+BPMiOBibnFV5A==", "requires": { "cliui": "^4.0.0", "decamelize": "^1.1.1", @@ -2241,7 +2492,8 @@ }, "yargs-parser": { "version": "9.0.2", - "bundled": true, + "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-9.0.2.tgz", + "integrity": "sha1-nM9qQ0YP5O1Aqbto9I1DuKaMwHc=", "requires": { "camelcase": "^4.1.0" } @@ -2281,7 +2533,6 @@ "version": "0.1.7", "resolved": "https://registry.npmjs.org/getpass/-/getpass-0.1.7.tgz", "integrity": "sha1-Xv+OPmhNVprkyysSgmBOi6YhSfo=", - "dev": true, "requires": { "assert-plus": "^1.0.0" } @@ -2368,26 +2619,17 @@ "integrity": "sha512-hKlsbA5Vu3xsh1Cg3J7jSmX/WaW6A5oBeqzM88oNbCRQFz+zUaXm6yxS4RVytp1scBoJzSYl4YAEOQIt6O8V1Q==" }, "handlebars": { - "version": "4.1.0", - "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.1.0.tgz", - "integrity": "sha512-l2jRuU1NAWK6AW5qqcTATWQJvNPEwkM7NEKSiv/gqOsoSQbVoWyqVEY5GS+XPQ88zLNmqASRpzfdm8d79hJS+w==", + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.1.1.tgz", + "integrity": "sha512-3Zhi6C0euYZL5sM0Zcy7lInLXKQ+YLcF/olbN010mzGQ4XVm50JeyBnMqofHh696GrciGruC7kCcApPDJvVgwA==", "dev": true, "requires": { - "async": "^2.5.0", + "neo-async": "^2.6.0", "optimist": "^0.6.1", "source-map": "^0.6.1", "uglify-js": "^3.1.4" }, "dependencies": { - "async": { - "version": "2.6.2", - "resolved": "https://registry.npmjs.org/async/-/async-2.6.2.tgz", - "integrity": "sha512-H1qVYh1MYhEEFLsP97cVKqCGo7KfCyTt6uEWqsTBr9SO84oK9Uwbyd/yCW+6rKJLHksBNUVWZDAjfS+Ccx0Bbg==", - "dev": true, - "requires": { - "lodash": "^4.17.11" - } - }, "source-map": { "version": "0.6.1", "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", @@ -2399,24 +2641,35 @@ "har-schema": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/har-schema/-/har-schema-2.0.0.tgz", - "integrity": "sha1-qUwiJOvKwEeCoNkDVSHyRzW37JI=", - "dev": true + "integrity": "sha1-qUwiJOvKwEeCoNkDVSHyRzW37JI=" }, "har-validator": { "version": "5.1.3", "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-5.1.3.tgz", "integrity": "sha512-sNvOCzEQNr/qrvJgc3UG/kD4QtlHycrzwS+6mfTrrSq97BvaYcPZZI1ZSqGSPR73Cxn4LKTD4PttRwfU7jWq5g==", - "dev": true, "requires": { "ajv": "^6.5.5", "har-schema": "^2.0.0" } }, + "has": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/has/-/has-1.0.3.tgz", + "integrity": "sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw==", + "requires": { + "function-bind": "^1.1.1" + } + }, "has-flag": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-2.0.0.tgz", "integrity": "sha1-6CB68cx7MNRGzHC3NLXovhj4jVE=" }, + "has-symbols": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.0.0.tgz", + "integrity": "sha1-uhqPGvKg/DllD1yFA2dwQSIGO0Q=" + }, "has-value": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/has-value/-/has-value-1.0.0.tgz", @@ -2479,55 +2732,55 @@ "integrity": "sha512-7T/BxH19zbcCTa8XkMlbK5lTo1WtgkFi3GvdWEyNuc4Vex7/9Dqbnpsf4JMydcfj9HCg4zUWFTL3Za6lapg5/w==" }, "http-basic": { - "version": "7.0.0", - "resolved": "https://registry.npmjs.org/http-basic/-/http-basic-7.0.0.tgz", - "integrity": "sha1-gvClBr6UJzLsje6+6A50bvVzbbo=", + "version": "8.1.1", + "resolved": "https://registry.npmjs.org/http-basic/-/http-basic-8.1.1.tgz", + "integrity": "sha512-RRPtpg/R7HbDEoICA1MlLy0IH0D/1ShY9AcvY6U2zqT/8mjjJ893H/2URxx6JtFYEfL3IlKTkQQcKwTyLuubKA==", "dev": true, "requires": { - "@types/concat-stream": "^1.6.0", - "@types/node": "^9.4.1", - "caseless": "~0.12.0", - "concat-stream": "^1.4.6", + "caseless": "^0.12.0", + "concat-stream": "^1.6.2", "http-response-object": "^3.0.1", "parse-cache-control": "^1.0.1" - }, - "dependencies": { - "@types/node": { - "version": "9.6.42", - "resolved": "https://registry.npmjs.org/@types/node/-/node-9.6.42.tgz", - "integrity": "sha512-SpeVQJFekfnEaZZO1yl4je/36upII36L7gOT4DBx51B1GeAB45mmDb3a5OBQB+ZeFxVVOP37r8Owsl940G/fBg==", - "dev": true - } + } + }, + "http-errors": { + "version": "1.6.3", + "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.6.3.tgz", + "integrity": "sha1-i1VoC7S+KDoLW/TqLjhYC+HZMg0=", + "requires": { + "depd": "~1.1.2", + "inherits": "2.0.3", + "setprototypeof": "1.1.0", + "statuses": ">= 1.4.0 < 2" } }, "http-response-object": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/http-response-object/-/http-response-object-3.0.1.tgz", - "integrity": "sha512-6L0Fkd6TozA8kFSfh9Widst0wfza3U1Ex2RjJ6zNDK0vR1U1auUR6jY4Nn2Xl7CCy0ikFmxW1XcspVpb9RvwTg==", + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/http-response-object/-/http-response-object-3.0.2.tgz", + "integrity": "sha512-bqX0XTF6fnXSQcEJ2Iuyr75yVakyjIDCqroJQ/aHfSdlM743Cwqoi2nDYMzLGWUcuTWGWy8AAvOKXTfiv6q9RA==", "dev": true, "requires": { - "@types/node": "^9.3.0" - }, - "dependencies": { - "@types/node": { - "version": "9.6.42", - "resolved": "https://registry.npmjs.org/@types/node/-/node-9.6.42.tgz", - "integrity": "sha512-SpeVQJFekfnEaZZO1yl4je/36upII36L7gOT4DBx51B1GeAB45mmDb3a5OBQB+ZeFxVVOP37r8Owsl940G/fBg==", - "dev": true - } + "@types/node": "^10.0.3" } }, "http-signature": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/http-signature/-/http-signature-1.2.0.tgz", "integrity": "sha1-muzZJRFHcvPZW2WmCruPfBj7rOE=", - "dev": true, "requires": { "assert-plus": "^1.0.0", "jsprim": "^1.2.2", "sshpk": "^1.7.0" } }, + "iconv-lite": { + "version": "0.4.23", + "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.23.tgz", + "integrity": "sha512-neyTUVFtahjf0mB3dZT77u+8O0QB89jFdnBkd5P1JgYPbPaia3gXXOVL2fq8VyU2gMMD7SaN7QukTB/pmXYvDA==", + "requires": { + "safer-buffer": ">= 2.1.2 < 3" + } + }, "ignore-by-default": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/ignore-by-default/-/ignore-by-default-1.0.1.tgz", @@ -2577,6 +2830,11 @@ "resolved": "https://registry.npmjs.org/invert-kv/-/invert-kv-1.0.0.tgz", "integrity": "sha1-EEqOSqym09jNFXqO+L+rLXo//bY=" }, + "ipaddr.js": { + "version": "1.8.0", + "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.8.0.tgz", + "integrity": "sha1-6qM9bd16zo9/b+DJygRA5wZzix4=" + }, "is-accessor-descriptor": { "version": "0.1.6", "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-0.1.6.tgz", @@ -2651,6 +2909,11 @@ } } }, + "is-date-object": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-date-object/-/is-date-object-1.0.1.tgz", + "integrity": "sha1-mqIOtq7rv/d/vTPnTKAbM1gdOhY=" + }, "is-descriptor": { "version": "0.1.6", "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-0.1.6.tgz", @@ -2696,9 +2959,9 @@ "integrity": "sha1-Es+5i2W1fdPRk6MSH19uL0N2ArU=" }, "is-glob": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.0.tgz", - "integrity": "sha1-lSHHaEXMJhCoUgPd8ICpWML/q8A=", + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.1.tgz", + "integrity": "sha512-5G0tKtBTFImOqDnLB2hG6Bp2qcKEFduo4tZu9MT/H6NQv/ghhy30o55ufafxJ/LdH79LLs2Kfrn85TLKyA7BUg==", "dev": true, "requires": { "is-extglob": "^2.1.1" @@ -2775,6 +3038,14 @@ "integrity": "sha1-HQPd7VO9jbDzDCbk+V02/HyH3CQ=", "dev": true }, + "is-regex": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-regex/-/is-regex-1.0.4.tgz", + "integrity": "sha1-VRdIm1RwkbCTDglWVM7SXul+lJE=", + "requires": { + "has": "^1.0.1" + } + }, "is-retry-allowed": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/is-retry-allowed/-/is-retry-allowed-1.1.0.tgz", @@ -2787,11 +3058,18 @@ "integrity": "sha1-EtSj3U5o4Lec6428hBc66A2RykQ=", "dev": true }, + "is-symbol": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-symbol/-/is-symbol-1.0.2.tgz", + "integrity": "sha512-HS8bZ9ox60yCJLH9snBpIwv9pYUAkcuLhSA1oero1UB5y9aiQpRA8y2ex945AOtCZL1lJDeIk3G5LthswI46Lw==", + "requires": { + "has-symbols": "^1.0.0" + } + }, "is-typedarray": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/is-typedarray/-/is-typedarray-1.0.0.tgz", - "integrity": "sha1-5HnICFjfDBsR3dppQPlgEfzaSpo=", - "dev": true + "integrity": "sha1-5HnICFjfDBsR3dppQPlgEfzaSpo=" }, "is-utf8": { "version": "0.2.1", @@ -2825,8 +3103,7 @@ "isstream": { "version": "0.1.2", "resolved": "https://registry.npmjs.org/isstream/-/isstream-0.1.2.tgz", - "integrity": "sha1-R+Y/evVa+m+S4VAOaQ64uFKcCZo=", - "dev": true + "integrity": "sha1-R+Y/evVa+m+S4VAOaQ64uFKcCZo=" }, "istanbul": { "version": "0.4.5", @@ -2904,13 +3181,12 @@ "js-sha3": { "version": "0.6.1", "resolved": "https://registry.npmjs.org/js-sha3/-/js-sha3-0.6.1.tgz", - "integrity": "sha1-W4n3enR3Z5h39YxKB1JAk0sflcA=", - "dev": true + "integrity": "sha1-W4n3enR3Z5h39YxKB1JAk0sflcA=" }, "js-yaml": { - "version": "3.12.1", - "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.12.1.tgz", - "integrity": "sha512-um46hB9wNOKlwkHgiuyEVAybXBjwFUV0Z/RaHJblRd9DXltue9FTYvzCr9ErQrK9Adz5MU4gHWVaNUfdmrC8qA==", + "version": "3.13.0", + "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.13.0.tgz", + "integrity": "sha512-pZZoSxcCYco+DIKBTimr67J6Hy+EYGZDY/HCWC+iAEA9h1ByhMXAIVUXMcMFpOCxQ/xjXmPI2MkDL5HRm5eFrQ==", "dev": true, "requires": { "argparse": "^1.0.7", @@ -2928,26 +3204,22 @@ "jsbn": { "version": "0.1.1", "resolved": "https://registry.npmjs.org/jsbn/-/jsbn-0.1.1.tgz", - "integrity": "sha1-peZUwuWi3rXyAdls77yoDA7y9RM=", - "dev": true + "integrity": "sha1-peZUwuWi3rXyAdls77yoDA7y9RM=" }, "json-schema": { "version": "0.2.3", "resolved": "https://registry.npmjs.org/json-schema/-/json-schema-0.2.3.tgz", - "integrity": "sha1-tIDIkuWaLwWVTOcnvT8qTogvnhM=", - "dev": true + "integrity": "sha1-tIDIkuWaLwWVTOcnvT8qTogvnhM=" }, "json-schema-traverse": { "version": "0.4.1", "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", - "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", - "dev": true + "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==" }, "json-stringify-safe": { "version": "5.0.1", "resolved": "https://registry.npmjs.org/json-stringify-safe/-/json-stringify-safe-5.0.1.tgz", - "integrity": "sha1-Epai1Y/UXxmg9s4B1lcB4sc1tus=", - "dev": true + "integrity": "sha1-Epai1Y/UXxmg9s4B1lcB4sc1tus=" }, "jsonfile": { "version": "2.4.0", @@ -2961,7 +3233,6 @@ "version": "1.4.1", "resolved": "https://registry.npmjs.org/jsprim/-/jsprim-1.4.1.tgz", "integrity": "sha1-MT5mvB5cwG5Di8G3SZwuXFastqI=", - "dev": true, "requires": { "assert-plus": "1.0.0", "extsprintf": "1.3.0", @@ -2973,7 +3244,6 @@ "version": "0.2.3", "resolved": "https://registry.npmjs.org/keccakjs/-/keccakjs-0.2.3.tgz", "integrity": "sha512-BjLkNDcfaZ6l8HBG9tH0tpmDv3sS2mA7FNQxFHpCdzP3Gb2MVruXBSuoM66SnVxKJpAr5dKGdkHD+bDokt8fTg==", - "dev": true, "requires": { "browserify-sha3": "^0.0.4", "sha3": "^1.2.2" @@ -3053,7 +3323,8 @@ "lodash": { "version": "4.17.11", "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.11.tgz", - "integrity": "sha512-cQKh8igo5QUhZ7lg38DYWAxMvjSAKG0A8wGSVimP07SIUEK2UO+arSRKbRZWtelMtN5V0Hkwh5ryOto/SshYIg==" + "integrity": "sha512-cQKh8igo5QUhZ7lg38DYWAxMvjSAKG0A8wGSVimP07SIUEK2UO+arSRKbRZWtelMtN5V0Hkwh5ryOto/SshYIg==", + "dev": true }, "lodash.assign": { "version": "4.2.0", @@ -3108,11 +3379,26 @@ "object-visit": "^1.0.0" } }, + "media-typer": { + "version": "0.3.0", + "resolved": "https://registry.npmjs.org/media-typer/-/media-typer-0.3.0.tgz", + "integrity": "sha1-hxDXrwqmJvj/+hzgAWhUUmMlV0g=" + }, "memorystream": { "version": "0.3.1", "resolved": "https://registry.npmjs.org/memorystream/-/memorystream-0.3.1.tgz", "integrity": "sha1-htcJCzDORV1j+64S3aUaR93K+bI=" }, + "merge-descriptors": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/merge-descriptors/-/merge-descriptors-1.0.1.tgz", + "integrity": "sha1-sAqqVW3YtEVoFQ7J0blT8/kMu2E=" + }, + "methods": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/methods/-/methods-1.1.2.tgz", + "integrity": "sha1-VSmk1nZUE07cxSZmVoNbD4Ua/O4=" + }, "micromatch": { "version": "3.1.10", "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-3.1.10.tgz", @@ -3134,17 +3420,20 @@ "to-regex": "^3.0.2" } }, + "mime": { + "version": "1.4.1", + "resolved": "https://registry.npmjs.org/mime/-/mime-1.4.1.tgz", + "integrity": "sha512-KI1+qOZu5DcW6wayYHSzR/tXKCDC5Om4s1z2QJjDULzLcmf3DvzS7oluY4HCTrc+9FiKmWUgeNLg7W3uIQvxtQ==" + }, "mime-db": { "version": "1.38.0", "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.38.0.tgz", - "integrity": "sha512-bqVioMFFzc2awcdJZIzR3HjZFX20QhilVS7hytkKrv7xFAn8bM1gzc/FOX2awLISvWe0PV8ptFKcon+wZ5qYkg==", - "dev": true + "integrity": "sha512-bqVioMFFzc2awcdJZIzR3HjZFX20QhilVS7hytkKrv7xFAn8bM1gzc/FOX2awLISvWe0PV8ptFKcon+wZ5qYkg==" }, "mime-types": { "version": "2.1.22", "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.22.tgz", "integrity": "sha512-aGl6TZGnhm/li6F7yx82bJiBZwgiEa4Hf6CNr8YO+r5UHr53tSTYZb102zyU50DOWWKeOv0uQLRL0/9EiKWCog==", - "dev": true, "requires": { "mime-db": "~1.38.0" } @@ -3237,11 +3526,14 @@ "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" }, "nan": { - "version": "2.12.1", - "resolved": "https://registry.npmjs.org/nan/-/nan-2.12.1.tgz", - "integrity": "sha512-JY7V6lRkStKcKTvHO5NVSQRv+RV+FIL5pvDoLiAtSL9pKlC5x9PKQcZDsq7m4FO4d57mkhC6Z+QhAh3Jdk5JFw==", - "dev": true, - "optional": true + "version": "2.10.0", + "resolved": "https://registry.npmjs.org/nan/-/nan-2.10.0.tgz", + "integrity": "sha512-bAdJv7fBLhWC+/Bls0Oza+mvTaNQtP+1RyhhhvD95pgUJz6XM5IzgmxOkItJ9tkoCiplvAnXI1tNmmUD/eScyA==" + }, + "nano-json-stream-parser": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/nano-json-stream-parser/-/nano-json-stream-parser-0.1.2.tgz", + "integrity": "sha1-DMj20OK2IrR5xA1JnEbWS3Vcb18=" }, "nanomatch": { "version": "1.2.13", @@ -3262,6 +3554,17 @@ "to-regex": "^3.0.1" } }, + "negotiator": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-0.6.1.tgz", + "integrity": "sha1-KzJxhOiZIQEXeyhWP7XnECrNDKk=" + }, + "neo-async": { + "version": "2.6.0", + "resolved": "https://registry.npmjs.org/neo-async/-/neo-async-2.6.0.tgz", + "integrity": "sha512-MFh0d/Wa7vkKO3Y3LlacqAEeHK0mckVqzDieUKTT+KGxi+zIpeVsFxymkIiRpbpDziHc290Xr9A1O4Om7otoRA==", + "dev": true + }, "nodemon": { "version": "1.18.10", "resolved": "https://registry.npmjs.org/nodemon/-/nodemon-1.18.10.tgz", @@ -3344,20 +3647,12 @@ "requires": { "bn.js": "4.11.6", "strip-hex-prefix": "1.0.0" - }, - "dependencies": { - "bn.js": { - "version": "4.11.6", - "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.11.6.tgz", - "integrity": "sha1-UzRK2xRhehP26N0s4okF0cC6MhU=" - } } }, "oauth-sign": { "version": "0.9.0", "resolved": "https://registry.npmjs.org/oauth-sign/-/oauth-sign-0.9.0.tgz", - "integrity": "sha512-fexhUFFPTGV8ybAtSIGbV6gOkSv8UtRbDBnAyLQw4QPKkgNlsH2ByPGtMUqdWkos6YCRmAqViwgZrJc/mRDzZQ==", - "dev": true + "integrity": "sha512-fexhUFFPTGV8ybAtSIGbV6gOkSv8UtRbDBnAyLQw4QPKkgNlsH2ByPGtMUqdWkos6YCRmAqViwgZrJc/mRDzZQ==" }, "object-assign": { "version": "4.1.1", @@ -3395,6 +3690,11 @@ } } }, + "object-keys": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/object-keys/-/object-keys-1.1.0.tgz", + "integrity": "sha512-6OO5X1+2tYkNyNEx6TsCxEqFfRWaqx6EtMiSbGrw8Ob8v9Ne+Hl8rBAgLBZn5wjEz3s/s6U1WXFUFOcxxAwUpg==" + }, "object-visit": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/object-visit/-/object-visit-1.0.1.tgz", @@ -3413,6 +3713,14 @@ "isobject": "^3.0.1" } }, + "on-finished": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/on-finished/-/on-finished-2.3.0.tgz", + "integrity": "sha1-IPEzZIGwg811M3mSoWlxqi2QaUc=", + "requires": { + "ee-first": "1.1.1" + } + }, "once": { "version": "1.4.0", "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", @@ -3520,12 +3828,12 @@ "dev": true }, "parse-headers": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/parse-headers/-/parse-headers-2.0.1.tgz", - "integrity": "sha1-aug6eqJanZtwCswoaYzR8e1+lTY=", + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/parse-headers/-/parse-headers-2.0.2.tgz", + "integrity": "sha512-/LypJhzFmyBIDYP9aDVgeyEb5sQfbfY5mnDq4hVhlQ69js87wXfmEI5V3xI6vvXasqebp0oCytYFLxsBVfCzSg==", "requires": { - "for-each": "^0.3.2", - "trim": "0.0.1" + "for-each": "^0.3.3", + "string.prototype.trim": "^1.1.2" } }, "parse-json": { @@ -3536,6 +3844,11 @@ "error-ex": "^1.2.0" } }, + "parseurl": { + "version": "1.3.2", + "resolved": "https://registry.npmjs.org/parseurl/-/parseurl-1.3.2.tgz", + "integrity": "sha1-/CidTtiZMRlGDBViUyYs3I3mW/M=" + }, "pascalcase": { "version": "0.1.1", "resolved": "https://registry.npmjs.org/pascalcase/-/pascalcase-0.1.1.tgz", @@ -3578,6 +3891,11 @@ "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.6.tgz", "integrity": "sha512-GSmOT2EbHrINBf9SR7CDELwlJ8AENk3Qn7OikK4nFYAu3Ote2+JYNVvkpAEQm3/TLNEJFD/xZJjzyxg3KBWOzw==" }, + "path-to-regexp": { + "version": "0.1.7", + "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-0.1.7.tgz", + "integrity": "sha1-32BBeABfUi8V60SQ5yR6G/qmf4w=" + }, "path-type": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/path-type/-/path-type-1.1.0.tgz", @@ -3603,8 +3921,7 @@ "performance-now": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/performance-now/-/performance-now-2.1.0.tgz", - "integrity": "sha1-Ywn04OX6kT7BxpMHrjZLSzd8nns=", - "dev": true + "integrity": "sha1-Ywn04OX6kT7BxpMHrjZLSzd8nns=" }, "pify": { "version": "2.3.0", @@ -3654,14 +3971,23 @@ "dev": true }, "promise": { - "version": "8.0.2", - "resolved": "https://registry.npmjs.org/promise/-/promise-8.0.2.tgz", - "integrity": "sha512-EIyzM39FpVOMbqgzEHhxdrEhtOSDOtjMZQ0M6iVfCE+kWNgCkAyOdnuCWqfmflylftfadU6FkiMgHZA2kUzwRw==", + "version": "8.0.3", + "resolved": "https://registry.npmjs.org/promise/-/promise-8.0.3.tgz", + "integrity": "sha512-HeRDUL1RJiLhyA0/grn+PTShlBAcLuh/1BJGtrvjwbvRDCTLLMEz9rOGCV+R3vHY4MixIuoMEd9Yq/XvsTPcjw==", "dev": true, "requires": { "asap": "~2.0.6" } }, + "proxy-addr": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.4.tgz", + "integrity": "sha512-5erio2h9jp5CHGwcybmxmVqHmnCBZeewlfJ0pex+UW7Qny7OOZXTtH56TGNyBizkgiOwhJtMKrVzDTeKcySZwA==", + "requires": { + "forwarded": "~0.1.2", + "ipaddr.js": "1.8.0" + } + }, "pseudomap": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/pseudomap/-/pseudomap-1.0.2.tgz", @@ -3671,8 +3997,7 @@ "psl": { "version": "1.1.31", "resolved": "https://registry.npmjs.org/psl/-/psl-1.1.31.tgz", - "integrity": "sha512-/6pt4+C+T+wZUieKR620OpzN/LlnNKuWjy1iFLQ/UG35JqHlR/89MP1d96dUfkf6Dne3TuLQzOYEYshJ+Hx8mw==", - "dev": true + "integrity": "sha512-/6pt4+C+T+wZUieKR620OpzN/LlnNKuWjy1iFLQ/UG35JqHlR/89MP1d96dUfkf6Dne3TuLQzOYEYshJ+Hx8mw==" }, "pstree.remy": { "version": "1.1.6", @@ -3683,14 +4008,12 @@ "punycode": { "version": "2.1.1", "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.1.1.tgz", - "integrity": "sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A==", - "dev": true + "integrity": "sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A==" }, "qs": { "version": "6.5.2", "resolved": "https://registry.npmjs.org/qs/-/qs-6.5.2.tgz", - "integrity": "sha512-N5ZAX4/LxJmF+7wN74pUD6qAh9/wnvdQcjq9TZjevvXzSUo7bfmw91saqMjzGS2xq91/odN2dW/WOl7qQHNDGA==", - "dev": true + "integrity": "sha512-N5ZAX4/LxJmF+7wN74pUD6qAh9/wnvdQcjq9TZjevvXzSUo7bfmw91saqMjzGS2xq91/odN2dW/WOl7qQHNDGA==" }, "query-string": { "version": "5.1.1", @@ -3707,6 +4030,22 @@ "resolved": "https://registry.npmjs.org/randomhex/-/randomhex-0.1.5.tgz", "integrity": "sha1-us7vmCMpCRQA8qKRLGzQLxCU9YU=" }, + "range-parser": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/range-parser/-/range-parser-1.2.0.tgz", + "integrity": "sha1-9JvmtIeJTdxA3MlKMi9hEJLgDV4=" + }, + "raw-body": { + "version": "2.3.3", + "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-2.3.3.tgz", + "integrity": "sha512-9esiElv1BrZoI3rCDuOuKCBRbuApGGaDPQfjSflGxdy4oyzqghxu6klEkkVIvBje+FF0BX9coEv8KqW6X/7njw==", + "requires": { + "bytes": "3.0.0", + "http-errors": "1.6.3", + "iconv-lite": "0.4.23", + "unpipe": "1.0.0" + } + }, "rc": { "version": "1.2.8", "resolved": "https://registry.npmjs.org/rc/-/rc-1.2.8.tgz", @@ -3781,11 +4120,6 @@ "resolve": "^1.1.6" } }, - "regenerator-runtime": { - "version": "0.12.1", - "resolved": "https://registry.npmjs.org/regenerator-runtime/-/regenerator-runtime-0.12.1.tgz", - "integrity": "sha512-odxIc1/vDlo4iZcfXqRYFj0vpXFNoGdKMAUieAlFYO6m/nl5e9KR/beGf41z4a1FI+aQgtjhuaSlDxQ0hmkrHg==" - }, "regex-not": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/regex-not/-/regex-not-1.0.2.tgz", @@ -3797,9 +4131,9 @@ } }, "registry-auth-token": { - "version": "3.3.2", - "resolved": "https://registry.npmjs.org/registry-auth-token/-/registry-auth-token-3.3.2.tgz", - "integrity": "sha512-JL39c60XlzCVgNrO+qq68FoNb56w/m7JYvGR2jT5iR1xBrUA3Mfx5Twk5rqTThPmQKMWydGmq8oFtDlxfrmxnQ==", + "version": "3.4.0", + "resolved": "https://registry.npmjs.org/registry-auth-token/-/registry-auth-token-3.4.0.tgz", + "integrity": "sha512-4LM6Fw8eBQdwMYcES4yTnn2TqIasbXuwDx3um+QRs7S55aMKCBKBxvPXl2RiUjHwuJLTyYfxSpmfSAjQpcuP+A==", "dev": true, "requires": { "rc": "^1.1.6", @@ -3855,7 +4189,6 @@ "version": "2.88.0", "resolved": "https://registry.npmjs.org/request/-/request-2.88.0.tgz", "integrity": "sha512-NAqBSrijGLZdM0WZNsInLJpkJokL72XYjUpnB0iwsRgxh7dB6COrHnTBNwN0E+lHDAJzu7kLAkDeY08z2/A0hg==", - "dev": true, "requires": { "aws-sign2": "~0.7.0", "aws4": "^1.8.0", @@ -3966,8 +4299,7 @@ "safe-buffer": { "version": "5.1.2", "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", - "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==", - "dev": true + "integrity": "sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==" }, "safe-regex": { "version": "1.1.0", @@ -3981,13 +4313,12 @@ "safer-buffer": { "version": "2.1.2", "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", - "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==", - "dev": true + "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==" }, "semver": { - "version": "5.6.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.6.0.tgz", - "integrity": "sha512-RS9R6R35NYgQn++fkDWaOmqGoj4Ek9gGs+DPxNUZKuwE183xjJroKvyo1IzVFeXvUrvmALy6FWD5xrdJT25gMg==" + "version": "5.7.0", + "resolved": "https://registry.npmjs.org/semver/-/semver-5.7.0.tgz", + "integrity": "sha512-Ya52jSX2u7QKghxeoFGpLwCtGlt7j0oY9DYb5apt9nPlJ42ID+ulTXESnt/qAQcoSERyZ5sl3LDIOw0nAn/5DA==" }, "semver-diff": { "version": "2.1.0", @@ -3998,6 +4329,64 @@ "semver": "^5.0.3" } }, + "send": { + "version": "0.16.2", + "resolved": "https://registry.npmjs.org/send/-/send-0.16.2.tgz", + "integrity": "sha512-E64YFPUssFHEFBvpbbjr44NCLtI1AohxQ8ZSiJjQLskAdKuriYEP6VyGEsRDH8ScozGpkaX1BGvhanqCwkcEZw==", + "requires": { + "debug": "2.6.9", + "depd": "~1.1.2", + "destroy": "~1.0.4", + "encodeurl": "~1.0.2", + "escape-html": "~1.0.3", + "etag": "~1.8.1", + "fresh": "0.5.2", + "http-errors": "~1.6.2", + "mime": "1.4.1", + "ms": "2.0.0", + "on-finished": "~2.3.0", + "range-parser": "~1.2.0", + "statuses": "~1.4.0" + }, + "dependencies": { + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "requires": { + "ms": "2.0.0" + } + }, + "statuses": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.4.0.tgz", + "integrity": "sha512-zhSCtt8v2NDrRlPQpCNtw/heZLtfUDqxBM1udqikb/Hbk52LK4nQSwr10u77iopCW5LsyHpuXS0GnEc48mLeew==" + } + } + }, + "serve-static": { + "version": "1.13.2", + "resolved": "https://registry.npmjs.org/serve-static/-/serve-static-1.13.2.tgz", + "integrity": "sha512-p/tdJrO4U387R9oMjb1oj7qSMaMfmOyd4j9hOFoxZe2baQszgHcSWjuya/CiT5kgZZKRudHNOA0pYXOl8rQ5nw==", + "requires": { + "encodeurl": "~1.0.2", + "escape-html": "~1.0.3", + "parseurl": "~1.3.2", + "send": "0.16.2" + } + }, + "servify": { + "version": "0.1.12", + "resolved": "https://registry.npmjs.org/servify/-/servify-0.1.12.tgz", + "integrity": "sha512-/xE6GvsKKqyo1BAY+KxOWXcLpPsUUyji7Qg3bVD7hh1eRze5bR1uYiuDA/k3Gof1s9BTzQZEJK8sNcNGFIzeWw==", + "requires": { + "body-parser": "^1.16.0", + "cors": "^2.8.1", + "express": "^4.14.0", + "request": "^2.79.0", + "xhr": "^2.3.3" + } + }, "set-blocking": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/set-blocking/-/set-blocking-2.0.0.tgz", @@ -4026,6 +4415,11 @@ } } }, + "setprototypeof": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.1.0.tgz", + "integrity": "sha512-BvE/TwpZX4FXExxOxZyRGQQv651MSwmWKZGqvmPcRIjDqWub67kTKuIMx43cZZrS/cBBzwBcNDWoFxt2XEFIpQ==" + }, "sha1": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/sha1/-/sha1-1.1.1.tgz", @@ -4040,17 +4434,8 @@ "version": "1.2.2", "resolved": "https://registry.npmjs.org/sha3/-/sha3-1.2.2.tgz", "integrity": "sha1-pmxQmN5MJbyIM27ItIF9AFvKe6k=", - "dev": true, "requires": { "nan": "2.10.0" - }, - "dependencies": { - "nan": { - "version": "2.10.0", - "resolved": "https://registry.npmjs.org/nan/-/nan-2.10.0.tgz", - "integrity": "sha512-bAdJv7fBLhWC+/Bls0Oza+mvTaNQtP+1RyhhhvD95pgUJz6XM5IzgmxOkItJ9tkoCiplvAnXI1tNmmUD/eScyA==", - "dev": true - } } }, "shebang-command": { @@ -4315,9 +4700,9 @@ } }, "source-map-support": { - "version": "0.5.10", - "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.10.tgz", - "integrity": "sha512-YfQ3tQFTK/yzlGJuX8pTwa4tifQj4QS2Mj7UegOu8jAz59MqIiMGPXxQhVQiIMNzayuUSF/jEuVnfFF5JqybmQ==", + "version": "0.5.11", + "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.11.tgz", + "integrity": "sha512-//sajEx/fGL3iw6fltKMdPvy8kL3kJ2O3iuYlRoT3k9Kb4BjOoZ+BZzaNHeuaruSt+Kf3Zk9tnfAQg9/AJqUVQ==", "dev": true, "requires": { "buffer-from": "^1.0.0", @@ -4385,7 +4770,6 @@ "version": "1.16.1", "resolved": "https://registry.npmjs.org/sshpk/-/sshpk-1.16.1.tgz", "integrity": "sha512-HXXqVUq7+pcKeLqqZj6mHFUMvXtOJt1uoUx09pFW6011inTMxqI8BA8PM95myrIyyKwdnzjdFjLiE6KBPVtJIg==", - "dev": true, "requires": { "asn1": "~0.2.3", "assert-plus": "^1.0.0", @@ -4419,6 +4803,11 @@ } } }, + "statuses": { + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.5.0.tgz", + "integrity": "sha1-Fhx9rBd2Wf2YEfQ3cfqZOBR4Yow=" + }, "stealthy-require": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/stealthy-require/-/stealthy-require-1.1.1.tgz", @@ -4440,6 +4829,16 @@ "strip-ansi": "^3.0.0" } }, + "string.prototype.trim": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/string.prototype.trim/-/string.prototype.trim-1.1.2.tgz", + "integrity": "sha1-0E3iyJ4Tf019IG8Ia17S+ua+jOo=", + "requires": { + "define-properties": "^1.1.2", + "es-abstract": "^1.5.0", + "function-bind": "^1.0.2" + } + }, "string_decoder": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", @@ -4494,9 +4893,9 @@ } }, "sync-request": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/sync-request/-/sync-request-6.0.0.tgz", - "integrity": "sha512-jGNIAlCi9iU4X3Dm4oQnNQshDD3h0/1A7r79LyqjbjUnj69sX6mShAXlhRXgImsfVKtTcnra1jfzabdZvp+Lmw==", + "version": "6.1.0", + "resolved": "https://registry.npmjs.org/sync-request/-/sync-request-6.1.0.tgz", + "integrity": "sha512-8fjNkrNlNCrVc/av+Jn+xxqfCjYaBoHqCsDz6mt030UMxJGr+GSfCV1dQt2gRtlL63+VPidwDVLr7V2OcTSdRw==", "dev": true, "requires": { "http-response-object": "^3.0.1", @@ -4523,9 +4922,9 @@ } }, "then-request": { - "version": "6.0.0", - "resolved": "https://registry.npmjs.org/then-request/-/then-request-6.0.0.tgz", - "integrity": "sha512-xA+7uEMc+jsQIoyySJ93Ad08Kuqnik7u6jLS5hR91Z3smAoCfL3M8/MqMlobAa9gzBfO9pA88A/AntfepkkMJQ==", + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/then-request/-/then-request-6.0.2.tgz", + "integrity": "sha512-3ZBiG7JvP3wbDzA9iNY5zJQcHL4jn/0BWtXIkagfz7QgOL/LqjCEOBQuJNZfu0XYnv5JhKh+cDxCPM4ILrqruA==", "dev": true, "requires": { "@types/concat-stream": "^1.6.0", @@ -4535,16 +4934,16 @@ "caseless": "~0.12.0", "concat-stream": "^1.6.0", "form-data": "^2.2.0", - "http-basic": "^7.0.0", + "http-basic": "^8.1.1", "http-response-object": "^3.0.1", "promise": "^8.0.0", "qs": "^6.4.0" }, "dependencies": { "@types/node": { - "version": "8.10.40", - "resolved": "https://registry.npmjs.org/@types/node/-/node-8.10.40.tgz", - "integrity": "sha512-RRSjdwz63kS4u7edIwJUn8NqKLLQ6LyqF/X4+4jp38MBT3Vwetewi2N4dgJEshLbDwNgOJXNYoOwzVZUSSLhkQ==", + "version": "8.10.45", + "resolved": "https://registry.npmjs.org/@types/node/-/node-8.10.45.tgz", + "integrity": "sha512-tGVTbA+i3qfXsLbq9rEq/hezaHY55QxQLeXQL2ejNgFAxxrgu8eMmYIOsRcl7hN1uTLVsKOOYacV/rcJM3sfgQ==", "dev": true } } @@ -4609,7 +5008,6 @@ "version": "2.4.3", "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.4.3.tgz", "integrity": "sha512-Q5srk/4vDM54WJsJio3XNn6K2sCG+CQ8G5Wz6bZhRZoAe/+TxjWB/GlFAnYEbkYVlON9FMk/fE3h2RLpPXo4lQ==", - "dev": true, "requires": { "psl": "^1.1.24", "punycode": "^1.4.1" @@ -4618,8 +5016,7 @@ "punycode": { "version": "1.4.1", "resolved": "https://registry.npmjs.org/punycode/-/punycode-1.4.1.tgz", - "integrity": "sha1-wNWmOycYgArY4esPpSachN1BhF4=", - "dev": true + "integrity": "sha1-wNWmOycYgArY4esPpSachN1BhF4=" } } }, @@ -4629,11 +5026,6 @@ "integrity": "sha512-4hjqbObwlh2dLyW4tcz0Ymw0ggoaVDMveUB9w8kFSQScdRLo0gxO9J7WFcUBo+W3C1TLdFIEwNOWebgZZ0RH9Q==", "dev": true }, - "trim": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/trim/-/trim-0.0.1.tgz", - "integrity": "sha1-WFhUf2spB1fulczMZm+1AITEYN0=" - }, "truffle": { "version": "4.1.11", "resolved": "https://registry.npmjs.org/truffle/-/truffle-4.1.11.tgz", @@ -4667,9 +5059,9 @@ } }, "solidity-parser-antlr": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/solidity-parser-antlr/-/solidity-parser-antlr-0.4.0.tgz", - "integrity": "sha512-RrIsh5VoHmrMQia6yLY8u8rx3JPREhSiCFz4Xb0h1Oh0prUYU2ukyWO8gG892V0UMHIXCWqvdZ3wSctNwdWThg==", + "version": "0.4.2", + "resolved": "https://registry.npmjs.org/solidity-parser-antlr/-/solidity-parser-antlr-0.4.2.tgz", + "integrity": "sha512-0OKT2YKZAqPe14HN7Nbo24hjmnyUYh92UjyZG0Zz2rpQhl/w8asX8qHb+ASSXfayQaiW8g9zGIupXEE355tOQQ==", "dev": true } } @@ -4684,7 +5076,6 @@ "version": "0.6.0", "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.6.0.tgz", "integrity": "sha1-J6XeoGs2sEoKmWZ3SykIaPD8QP0=", - "dev": true, "requires": { "safe-buffer": "^5.0.1" } @@ -4692,8 +5083,7 @@ "tweetnacl": { "version": "0.14.5", "resolved": "https://registry.npmjs.org/tweetnacl/-/tweetnacl-0.14.5.tgz", - "integrity": "sha1-WuaBd/GS1EViadEIr6k/+HQ/T2Q=", - "dev": true + "integrity": "sha1-WuaBd/GS1EViadEIr6k/+HQ/T2Q=" }, "type-check": { "version": "0.3.2", @@ -4710,6 +5100,15 @@ "integrity": "sha512-0fr/mIH1dlO+x7TlcMy+bIDqKPsw/70tVyeHW787goQjhmqaZe10uwLujubK9q9Lg6Fiho1KUKDYz0Z7k7g5/g==", "dev": true }, + "type-is": { + "version": "1.6.16", + "resolved": "https://registry.npmjs.org/type-is/-/type-is-1.6.16.tgz", + "integrity": "sha512-HRkVv/5qY2G6I8iab9cI7v1bOIdhm94dVjQCPFElW9W+3GeDOSHmy2EBYe4VTApuzolPcmgFTN3ftVJRKR2J9Q==", + "requires": { + "media-typer": "0.3.0", + "mime-types": "~2.1.18" + } + }, "typedarray": { "version": "0.0.6", "resolved": "https://registry.npmjs.org/typedarray/-/typedarray-0.0.6.tgz", @@ -4717,20 +5116,20 @@ "dev": true }, "uglify-js": { - "version": "3.4.9", - "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-3.4.9.tgz", - "integrity": "sha512-8CJsbKOtEbnJsTyv6LE6m6ZKniqMiFWmm9sRbopbkGs3gMPPfd3Fh8iIA4Ykv5MgaTbqHr4BaoGLJLZNhsrW1Q==", + "version": "3.5.3", + "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-3.5.3.tgz", + "integrity": "sha512-rIQPT2UMDnk4jRX+w4WO84/pebU2jiLsjgIyrCktYgSvx28enOE3iYQMr+BD1rHiitWnDmpu0cY/LfIEpKcjcw==", "dev": true, "optional": true, "requires": { - "commander": "~2.17.1", + "commander": "~2.19.0", "source-map": "~0.6.1" }, "dependencies": { "commander": { - "version": "2.17.1", - "resolved": "https://registry.npmjs.org/commander/-/commander-2.17.1.tgz", - "integrity": "sha512-wPMUt6FnH2yzG95SA6mzjQOEKUU3aLaDEmzs1ti+1E9h+CsrZghRlqEM/EJ4KscsQVG8uNN4uVreUeT8+drlgg==", + "version": "2.19.0", + "resolved": "https://registry.npmjs.org/commander/-/commander-2.19.0.tgz", + "integrity": "sha512-6tvAOO+D6OENvRAh524Dh9jcfKTYDQAqvqezbCW82xj5X0pSrcpxtvRKHLG0yBY6SD7PSDrJaj+0AiOcKVd1Xg==", "dev": true, "optional": true }, @@ -4743,6 +5142,11 @@ } } }, + "ultron": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/ultron/-/ultron-1.1.1.tgz", + "integrity": "sha512-UIEXBNeYmKptWH6z8ZnqTeS8fV74zG0/eRU9VGkpzz+LIJNs8W/zM/L+7ctCkRrgbNnnR0xxw4bKOr0cW0N0Og==" + }, "undefsafe": { "version": "2.0.2", "resolved": "https://registry.npmjs.org/undefsafe/-/undefsafe-2.0.2.tgz", @@ -4763,6 +5167,11 @@ } } }, + "underscore": { + "version": "1.8.3", + "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", + "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=" + }, "union-value": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/union-value/-/union-value-1.0.0.tgz", @@ -4807,6 +5216,11 @@ "crypto-random-string": "^1.0.0" } }, + "unpipe": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/unpipe/-/unpipe-1.0.0.tgz", + "integrity": "sha1-sr9O6FFKrmFltIF4KdIbLvSZBOw=" + }, "unset-value": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/unset-value/-/unset-value-1.0.0.tgz", @@ -4854,9 +5268,9 @@ "dev": true }, "upath": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/upath/-/upath-1.1.0.tgz", - "integrity": "sha512-bzpH/oBhoS/QI/YtbkqCg6VEiPYjSZtrHQM6/QnJS6OL9pKUFLqb3aFh4Scvwm45+7iAgiMkLhSbaZxUqmrprw==", + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/upath/-/upath-1.1.2.tgz", + "integrity": "sha512-kXpym8nmDmlCBr7nKdIx8P2jNBa+pBpIUFRnKJ4dr8htyYGJFokkr2ZvERRtUN+9SY+JqXouNgUPtv6JQva/2Q==", "dev": true }, "update-notifier": { @@ -4881,7 +5295,6 @@ "version": "4.2.2", "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.2.2.tgz", "integrity": "sha512-KY9Frmirql91X2Qgjry0Wd4Y+YTdrdZheS8TFwvkbLWf/G5KNJDCh6pKL5OZctEW4+0Baa5idK2ZQuELRwPznQ==", - "dev": true, "requires": { "punycode": "^2.1.0" } @@ -4923,11 +5336,15 @@ "integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=", "dev": true }, + "utils-merge": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/utils-merge/-/utils-merge-1.0.1.tgz", + "integrity": "sha1-n5VxD1CiZ5R7LMwSR0HBAoQn5xM=" + }, "uuid": { "version": "3.3.2", "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.3.2.tgz", - "integrity": "sha512-yXJmeNaw3DnnKAOKJE51sL/ZaYfWJRl1pK9dr19YFCu0ObS231AB1/LbqTKRAQ5kw8A90rA6fr4riOUpTZvQZA==", - "dev": true + "integrity": "sha512-yXJmeNaw3DnnKAOKJE51sL/ZaYfWJRl1pK9dr19YFCu0ObS231AB1/LbqTKRAQ5kw8A90rA6fr4riOUpTZvQZA==" }, "validate-npm-package-license": { "version": "3.0.4", @@ -4938,11 +5355,15 @@ "spdx-expression-parse": "^3.0.0" } }, + "vary": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz", + "integrity": "sha1-IpnwLG3tMNSllhsLn3RSShj2NPw=" + }, "verror": { "version": "1.10.0", "resolved": "https://registry.npmjs.org/verror/-/verror-1.10.0.tgz", "integrity": "sha1-OhBcoXBTr1XW4nDB+CiGguGNpAA=", - "dev": true, "requires": { "assert-plus": "^1.0.0", "core-util-is": "1.0.2", @@ -4963,19 +5384,16 @@ } }, "web3-utils": { - "version": "1.0.0-beta.46", - "resolved": "https://registry.npmjs.org/web3-utils/-/web3-utils-1.0.0-beta.46.tgz", - "integrity": "sha512-mSz+NrAil2fDZkxTXHPntCclZ8DofMjv8Q+BYR0VAyzTzylpYNXAV0WDdxBp/sXgniWRZXZMF7OkQNWqhZ1J9g==", + "version": "1.0.0-beta.34", + "resolved": "https://registry.npmjs.org/web3-utils/-/web3-utils-1.0.0-beta.34.tgz", + "integrity": "sha1-lBH8OarvOcpOBhafdiKX2f8CCXA=", "requires": { - "@babel/runtime": "^7.3.1", - "@types/bn.js": "^4.11.4", - "@types/node": "^10.12.18", - "bn.js": "4.11.8", - "eth-lib": "0.2.8", - "ethjs-unit": "^0.1.6", - "lodash": "^4.17.11", + "bn.js": "4.11.6", + "eth-lib": "0.1.27", + "ethjs-unit": "0.1.6", "number-to-bn": "1.7.0", "randomhex": "0.1.5", + "underscore": "1.8.3", "utf8": "2.1.1" } }, @@ -5071,6 +5489,16 @@ "signal-exit": "^3.0.2" } }, + "ws": { + "version": "3.3.3", + "resolved": "https://registry.npmjs.org/ws/-/ws-3.3.3.tgz", + "integrity": "sha512-nnWLa/NwZSt4KQJu51MYlCcSQ5g7INpOrOMt4XV8j4dqTXdmlUmSHQ8/oLC069ckre0fRsgfvsKwbTdtKLCDkA==", + "requires": { + "async-limiter": "~1.0.0", + "safe-buffer": "~5.1.0", + "ultron": "~1.1.0" + } + }, "xdg-basedir": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/xdg-basedir/-/xdg-basedir-3.0.0.tgz", From 05d5a2bdc25b0be163aae22c48981a13d39467c3 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 3 Apr 2019 14:02:38 -0300 Subject: [PATCH 127/187] Fix merge conflicts --- deploy/src/erc_to_erc/home.js | 13 +++++++++---- 1 file changed, 9 insertions(+), 4 deletions(-) diff --git a/deploy/src/erc_to_erc/home.js b/deploy/src/erc_to_erc/home.js index 6f3fe441f..98bc675b0 100644 --- a/deploy/src/erc_to_erc/home.js +++ b/deploy/src/erc_to_erc/home.js @@ -8,7 +8,6 @@ const { sendRawTxHome, logValidatorsAndRewardAccounts } = require('../deploymentUtils') -const { ZERO_ADDRESS } = require('../constants') const { web3Home, deploymentPrivateKey, HOME_RPC_URL } = require('../web3') const EternalStorageProxy = require('../../../build/contracts/EternalStorageProxy.json') @@ -164,10 +163,10 @@ async function deployHome() { homeNonce++ console.log('\n[Home] deploying Bridgeble token') - const erc677Contract = isRewardableBridge || DEPLOY_REWARDABLE_TOKEN ? ERC677BridgeTokenRewardable : ERC677BridgeToken + const erc677Contract = + isRewardableBridge || DEPLOY_REWARDABLE_TOKEN ? ERC677BridgeTokenRewardable : ERC677BridgeToken const erc677token = await deployContract( erc677Contract, - DEPLOY_REWARDABLE_TOKEN ? ERC677BridgeTokenRewardable : ERC677BridgeToken, [BRIDGEABLE_TOKEN_NAME, BRIDGEABLE_TOKEN_SYMBOL, BRIDGEABLE_TOKEN_DECIMALS], { from: DEPLOYMENT_ACCOUNT_ADDRESS, network: 'home', nonce: homeNonce } ) @@ -200,9 +199,15 @@ async function deployHome() { privateKey: deploymentPrivateKey, url: HOME_RPC_URL }) - assert.strictEqual(Web3Utils.hexToNumber(setBlockRewardContract.status), 1, 'Transaction Failed') + assert.strictEqual( + Web3Utils.hexToNumber(setBlockRewardContract.status), + 1, + 'Transaction Failed' + ) homeNonce++ + } + if (DEPLOY_REWARDABLE_TOKEN) { console.log('\nset Staking contract on ERC677BridgeTokenRewardable') const setStakingContractData = await erc677token.methods .setStakingContract(DPOS_STAKING_ADDRESS) From 745eeb049323af2dab62fdf7d72c87173932b6d0 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Thu, 11 Apr 2019 12:10:23 -0300 Subject: [PATCH 128/187] Add validatorList on BaseBridgeValidators --- .../BaseBridgeValidators.sol | 19 +++++++++++++++++++ .../RewardableValidators.sol | 19 ------------------- test/validators_test.js | 15 +++++++++++++++ 3 files changed, 34 insertions(+), 19 deletions(-) diff --git a/contracts/upgradeable_contracts/BaseBridgeValidators.sol b/contracts/upgradeable_contracts/BaseBridgeValidators.sol index 4405c0e9e..efa76da1c 100644 --- a/contracts/upgradeable_contracts/BaseBridgeValidators.sol +++ b/contracts/upgradeable_contracts/BaseBridgeValidators.sol @@ -30,6 +30,25 @@ contract BaseBridgeValidators is EternalStorage, Ownable { return (2, 1, 0); } + function validatorList() public view returns (address[]) { + address [] memory list = new address[](validatorCount()); + uint256 counter = 0; + address nextValidator = getNextValidator(F_ADDR); + require(nextValidator != address(0)); + + while (nextValidator != F_ADDR) { + list[counter] = nextValidator; + nextValidator = getNextValidator(nextValidator); + counter++; + + if (nextValidator == address(0) ) { + revert(); + } + } + + return list; + } + function _addValidator(address _validator) internal { require(_validator != address(0) && _validator != F_ADDR); require(!isValidator(_validator)); diff --git a/contracts/upgradeable_contracts/RewardableValidators.sol b/contracts/upgradeable_contracts/RewardableValidators.sol index 989df6b78..c0aedcd81 100644 --- a/contracts/upgradeable_contracts/RewardableValidators.sol +++ b/contracts/upgradeable_contracts/RewardableValidators.sol @@ -67,25 +67,6 @@ contract RewardableValidators is BaseBridgeValidators { emit ValidatorRemoved(_validator); } - function validatorList() public view returns (address[]) { - address [] memory list = new address[](validatorCount()); - uint256 counter = 0; - address nextValidator = getNextValidator(F_ADDR); - require(nextValidator != address(0)); - - while (nextValidator != F_ADDR) { - list[counter] = nextValidator; - nextValidator = getNextValidator(nextValidator); - counter++; - - if (nextValidator == address(0) ) { - revert(); - } - } - - return list; - } - function getValidatorRewardAddress(address _validator) public view returns (address) { return addressStorage[keccak256(abi.encodePacked("validatorsRewards", _validator))]; } diff --git a/test/validators_test.js b/test/validators_test.js index a98ae5145..e2d7517eb 100644 --- a/test/validators_test.js +++ b/test/validators_test.js @@ -219,4 +219,19 @@ contract('BridgeValidators', async (accounts) => { }) }) }) + + describe('#Validators list', () => { + it('should return validators list', async () => { + // Given + const validators = accounts.slice(0, 5) + const { initialize, validatorList } = bridgeValidators + await initialize(1, validators, owner, { from: owner }).should.be.fulfilled + + // When + const returnedList = await validatorList() + + // Then + returnedList.should.be.eql(validators) + }) + }) }) From d2f6b0ac3acf22c2dac146e59c4f1ff690473b0d Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Fri, 12 Apr 2019 14:11:42 -0300 Subject: [PATCH 129/187] Update addValidator method and ValidatorAdded event --- .../RewardableValidators.sol | 8 ++++---- test/rewardable_validators_test.js | 17 ++++++++++------- 2 files changed, 14 insertions(+), 11 deletions(-) diff --git a/contracts/upgradeable_contracts/RewardableValidators.sol b/contracts/upgradeable_contracts/RewardableValidators.sol index 989df6b78..32acab05f 100644 --- a/contracts/upgradeable_contracts/RewardableValidators.sol +++ b/contracts/upgradeable_contracts/RewardableValidators.sol @@ -5,7 +5,7 @@ import "./BaseBridgeValidators.sol"; contract RewardableValidators is BaseBridgeValidators { - event ValidatorAdded (address indexed validator, address reward); + event ValidatorAdded (address indexed validator); event ValidatorRemoved (address indexed validator); function initialize( @@ -43,7 +43,7 @@ contract RewardableValidators is BaseBridgeValidators { setValidatorCount(validatorCount().add(1)); setValidatorRewardAddress(_initialValidators[i], _initialRewards[i]); - emit ValidatorAdded(_initialValidators[i], _initialRewards[i]); + emit ValidatorAdded(_initialValidators[i]); } uintStorage[keccak256(abi.encodePacked("requiredSignatures"))] = _requiredSignatures; @@ -54,11 +54,11 @@ contract RewardableValidators is BaseBridgeValidators { return isInitialized(); } - function addValidator(address _validator, address _reward) external onlyOwner { + function addRewardableValidator(address _validator, address _reward) external onlyOwner { require(_reward != address(0)); _addValidator(_validator); setValidatorRewardAddress(_validator, _reward); - emit ValidatorAdded(_validator, _reward); + emit ValidatorAdded(_validator); } function removeValidator(address _validator) external onlyOwner { diff --git a/test/rewardable_validators_test.js b/test/rewardable_validators_test.js index c595b7adc..27b505e02 100644 --- a/test/rewardable_validators_test.js +++ b/test/rewardable_validators_test.js @@ -53,31 +53,34 @@ contract('RewardableValidators', async (accounts) => { let newReward = accounts[5]; false.should.be.equal(await bridgeValidators.isValidator(newValidator)) - await bridgeValidators.addValidator(newValidator, newReward, {from: validators[0]}).should.be.rejectedWith(ERROR_MSG) - const {logs} = await bridgeValidators.addValidator(newValidator, newReward, {from: owner}).should.be.fulfilled + await bridgeValidators.addRewardableValidator(newValidator, newReward, {from: validators[0]}).should.be.rejectedWith(ERROR_MSG) + const {logs} = await bridgeValidators.addRewardableValidator(newValidator, newReward, {from: owner}).should.be.fulfilled true.should.be.equal(await bridgeValidators.isValidator(newValidator)) '3'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) logs[0].event.should.be.equal('ValidatorAdded') - logs[0].args.should.be.deep.equal({ validator: newValidator, reward: newReward }) + logs[0].args.should.be.deep.equal({ validator: newValidator }) + + const rewardAddress = await bridgeValidators.getValidatorRewardAddress(newValidator) + rewardAddress.should.be.equal(newReward) }) it('cannot add already existing validator', async () => { true.should.be.equal(await bridgeValidators.isValidator(validators[0])) - await bridgeValidators.addValidator(validators[0], rewards[0], {from: owner}).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.addRewardableValidator(validators[0], rewards[0], {from: owner}).should.be.rejectedWith(ERROR_MSG) '2'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) }) it(`cannot add 0xf as validator address`, async () => { // Given - await bridgeValidators.addValidator(F_ADDRESS, rewards[0], { from: owner }).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.addRewardableValidator(F_ADDRESS, rewards[0], { from: owner }).should.be.rejectedWith(ERROR_MSG) }) it(`cannot add 0x0 as validator address`, async () => { - await bridgeValidators.addValidator(ZERO_ADDRESS, rewards[0], {from: owner}).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.addRewardableValidator(ZERO_ADDRESS, rewards[0], {from: owner}).should.be.rejectedWith(ERROR_MSG) }) it(`cannot add 0x0 as reward address`, async () => { - await bridgeValidators.addValidator(accounts[4], ZERO_ADDRESS, { from: owner }).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.addRewardableValidator(accounts[4], ZERO_ADDRESS, { from: owner }).should.be.rejectedWith(ERROR_MSG) }) }) From 7581f1241a8152fb03c6a8be3569d93005b2b664 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 15 Apr 2019 09:10:40 -0300 Subject: [PATCH 130/187] Increase validator interface version --- contracts/upgradeable_contracts/BaseBridgeValidators.sol | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/contracts/upgradeable_contracts/BaseBridgeValidators.sol b/contracts/upgradeable_contracts/BaseBridgeValidators.sol index efa76da1c..3bf8fd067 100644 --- a/contracts/upgradeable_contracts/BaseBridgeValidators.sol +++ b/contracts/upgradeable_contracts/BaseBridgeValidators.sol @@ -27,7 +27,7 @@ contract BaseBridgeValidators is EternalStorage, Ownable { pure returns (uint64 major, uint64 minor, uint64 patch) { - return (2, 1, 0); + return (2, 2, 0); } function validatorList() public view returns (address[]) { From 4c8e66422649bac032b9156ae2a35137ed9402cb Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 15 Apr 2019 13:51:34 -0300 Subject: [PATCH 131/187] Emit event on fee distribution from transfer --- .../upgradeable_contracts/BasicHomeBridge.sol | 4 +-- .../erc20_to_erc20/HomeBridgeErcToErc.sol | 2 +- .../erc20_to_native/HomeBridgeErcToNative.sol | 6 +++- .../native_to_erc20/HomeBridgeNativeToErc.sol | 5 +++- test/erc_to_native/home_bridge.test.js | 30 +++++++++++++++---- test/native_to_erc/home_bridge_test.js | 21 +++++++++++-- 6 files changed, 54 insertions(+), 14 deletions(-) diff --git a/contracts/upgradeable_contracts/BasicHomeBridge.sol b/contracts/upgradeable_contracts/BasicHomeBridge.sol index d068a08cf..1c2608dc6 100644 --- a/contracts/upgradeable_contracts/BasicHomeBridge.sol +++ b/contracts/upgradeable_contracts/BasicHomeBridge.sol @@ -37,7 +37,7 @@ contract BasicHomeBridge is EternalStorage, Validatable { // If the bridge contract does not own enough tokens to transfer // it will couse funds lock on the home side of the bridge setNumAffirmationsSigned(hashMsg, markAsProcessed(signed)); - require(onExecuteAffirmation(recipient, value)); + require(onExecuteAffirmation(recipient, value, transactionHash)); emit AffirmationCompleted(recipient, value, transactionHash); } } else { @@ -84,7 +84,7 @@ contract BasicHomeBridge is EternalStorage, Validatable { boolStorage[keccak256(abi.encodePacked("messagesSigned", _hash))] = _status; } - function onExecuteAffirmation(address, uint256) internal returns(bool) { + function onExecuteAffirmation(address, uint256, bytes32) internal returns(bool) { } function onSignaturesCollected(bytes) internal { diff --git a/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol b/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol index 51313be11..c65dd11e4 100644 --- a/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol +++ b/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol @@ -59,7 +59,7 @@ contract HomeBridgeErcToErc is ERC677Receiver, EternalStorage, BasicBridge, Basi revert(); } - function onExecuteAffirmation(address _recipient, uint256 _value) internal returns(bool) { + function onExecuteAffirmation(address _recipient, uint256 _value, bytes32 txHash) internal returns(bool) { setTotalExecutedPerDay(getCurrentDay(), totalExecutedPerDay(getCurrentDay()).add(_value)); return erc677token().mint(_recipient, _value); } diff --git a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol index a396fcd89..7f6f8da87 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol @@ -14,6 +14,8 @@ import "./RewardableHomeBridgeErcToNative.sol"; contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, OverdrawManagement, RewardableHomeBridgeErcToNative { event AmountLimitExceeded(address recipient, uint256 value, bytes32 transactionHash); + event FeeDistributedFromAffirmation(uint256 feeAmount, bytes32 indexed transactionHash); + event FeeDistributedFromSignatures(uint256 feeAmount, bytes32 indexed transactionHash); function () public payable { require(msg.value > 0); @@ -151,7 +153,7 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, setOwner(_owner); } - function onExecuteAffirmation(address _recipient, uint256 _value) internal returns(bool) { + function onExecuteAffirmation(address _recipient, uint256 _value, bytes32 txHash) internal returns(bool) { setTotalExecutedPerDay(getCurrentDay(), totalExecutedPerDay(getCurrentDay()).add(_value)); IBlockReward blockReward = blockRewardContract(); require(blockReward != address(0)); @@ -162,6 +164,7 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, uint256 fee = calculateFee(valueToMint, false, feeManager, FOREIGN_FEE); distributeFeeFromAffirmation(fee, feeManager); valueToMint = valueToMint.sub(fee); + emit FeeDistributedFromAffirmation(fee, txHash); } blockReward.addExtraReceiver(valueToMint, _recipient); return true; @@ -177,6 +180,7 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, (recipient, amount, txHash, contractAddress) = Message.parseMessage(_message); uint256 fee = calculateFee(amount, true, feeManager, HOME_FEE); distributeFeeFromSignatures(fee, feeManager); + emit FeeDistributedFromSignatures(fee, txHash); } } diff --git a/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol index 6b225fd56..e235f2c2b 100644 --- a/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol +++ b/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol @@ -10,6 +10,8 @@ import "../Sacrifice.sol"; contract HomeBridgeNativeToErc is EternalStorage, BasicBridge, BasicHomeBridge, RewardableHomeBridgeNativeToErc { + event FeeDistributedFromAffirmation(uint256 feeAmount, bytes32 indexed transactionHash); + function () public payable { require(msg.value > 0); require(msg.data.length == 0); @@ -112,7 +114,7 @@ contract HomeBridgeNativeToErc is EternalStorage, BasicBridge, BasicHomeBridge, setOwner(_owner); } - function onExecuteAffirmation(address _recipient, uint256 _value) internal returns(bool) { + function onExecuteAffirmation(address _recipient, uint256 _value, bytes32 txHash) internal returns(bool) { setTotalExecutedPerDay(getCurrentDay(), totalExecutedPerDay(getCurrentDay()).add(_value)); uint256 valueToTransfer = _value; @@ -121,6 +123,7 @@ contract HomeBridgeNativeToErc is EternalStorage, BasicBridge, BasicHomeBridge, uint256 fee = calculateFee(valueToTransfer, false, feeManager, FOREIGN_FEE); distributeFeeFromAffirmation(fee, feeManager); valueToTransfer = valueToTransfer.sub(fee); + emit FeeDistributedFromAffirmation(fee, txHash); } if (!_recipient.send(valueToTransfer)) { diff --git a/test/erc_to_native/home_bridge.test.js b/test/erc_to_native/home_bridge.test.js index 7e856ccff..3758f90f3 100644 --- a/test/erc_to_native/home_bridge.test.js +++ b/test/erc_to_native/home_bridge.test.js @@ -983,8 +983,13 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { signer: validators[0], transactionHash }); - logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); logs[1].args.should.be.deep.equal({ + feeAmount: value.mul(web3.toBigNumber(fee)), + transactionHash + }) + logs[2].event.should.be.equal("AffirmationCompleted"); + logs[2].args.should.be.deep.equal({ recipient, value, transactionHash @@ -1051,8 +1056,13 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { signer: validators[1], transactionHash }); - logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); logs[1].args.should.be.deep.equal({ + feeAmount: value.mul(web3.toBigNumber(fee)), + transactionHash + }) + logs[2].event.should.be.equal("AffirmationCompleted"); + logs[2].args.should.be.deep.equal({ recipient, value, transactionHash @@ -1133,8 +1143,13 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { signer: validators[4], transactionHash }); - logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); logs[1].args.should.be.deep.equal({ + feeAmount: value.mul(web3.toBigNumber(fee)), + transactionHash + }) + logs[2].event.should.be.equal("AffirmationCompleted"); + logs[2].args.should.be.deep.equal({ recipient, value, transactionHash @@ -1244,8 +1259,9 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const { logs } = await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled; // Then - logs.length.should.be.equal(2) + logs.length.should.be.equal(3) logs[1].event.should.be.equal('CollectedSignatures') + logs[2].event.should.be.equal('FeeDistributedFromSignatures') const finalBridgeBalance = await web3.eth.getBalance(homeBridge.address) finalBridgeBalance.should.be.bignumber.equal('0') @@ -1308,8 +1324,9 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const { logs } = await homeBridge.submitSignature(signature3, message, {from: validators[2]}).should.be.fulfilled; // Then - logs.length.should.be.equal(2) + logs.length.should.be.equal(3) logs[1].event.should.be.equal('CollectedSignatures') + logs[2].event.should.be.equal('FeeDistributedFromSignatures') const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) @@ -1388,8 +1405,9 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const { logs } = await homeBridge.submitSignature(signature5, message, {from: validators[4]}).should.be.fulfilled; // Then - logs.length.should.be.equal(2) + logs.length.should.be.equal(3) logs[1].event.should.be.equal('CollectedSignatures') + logs[2].event.should.be.equal('FeeDistributedFromSignatures') const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) diff --git a/test/native_to_erc/home_bridge_test.js b/test/native_to_erc/home_bridge_test.js index 3846e3519..3f512b0da 100644 --- a/test/native_to_erc/home_bridge_test.js +++ b/test/native_to_erc/home_bridge_test.js @@ -686,8 +686,13 @@ contract('HomeBridge', async (accounts) => { signer: validators[0], transactionHash }); - logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); logs[1].args.should.be.deep.equal({ + feeAmount: value.mul(web3.toBigNumber(fee)), + transactionHash + }) + logs[2].event.should.be.equal("AffirmationCompleted"); + logs[2].args.should.be.deep.equal({ recipient, value, transactionHash @@ -744,8 +749,13 @@ contract('HomeBridge', async (accounts) => { signer: validators[1], transactionHash }); - logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); logs[1].args.should.be.deep.equal({ + feeAmount: value.mul(web3.toBigNumber(fee)), + transactionHash + }) + logs[2].event.should.be.equal("AffirmationCompleted"); + logs[2].args.should.be.deep.equal({ recipient, value, transactionHash @@ -821,8 +831,13 @@ contract('HomeBridge', async (accounts) => { signer: validators[4], transactionHash }); - logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); logs[1].args.should.be.deep.equal({ + feeAmount: value.mul(web3.toBigNumber(fee)), + transactionHash + }) + logs[2].event.should.be.equal("AffirmationCompleted"); + logs[2].args.should.be.deep.equal({ recipient, value, transactionHash From aa5721ae21251dcaaf98b9190db0345991dc4780 Mon Sep 17 00:00:00 2001 From: Andrew Gross Date: Mon, 15 Apr 2019 11:53:42 -0600 Subject: [PATCH 132/187] update FOREIGN_DAILY_LIMIT & FOREIGN_MAX_AMOUNT_PER_TX for bridge modes --- deploy/README.md | 48 ++++++++++++++++++++++++++++++------------------ 1 file changed, 30 insertions(+), 18 deletions(-) diff --git a/deploy/README.md b/deploy/README.md index 50b38b473..2f339a2a5 100644 --- a/deploy/README.md +++ b/deploy/README.md @@ -18,7 +18,7 @@ cp .env.example .env 4. Adjust the parameters in the `.env` file depending on the desired bridge mode. See below for comments related to each parameter. -5. Add funds to the deployment accounts in both theHome and Foreign networks. +5. Add funds to the deployment accounts in both the Home and Foreign networks. 6. Run `node deploy.js`. @@ -64,7 +64,8 @@ HOME_RPC_URL=https://poa.infura.io HOME_BRIDGE_OWNER=0x # Address on Home network with permissions to change parameters of bridge validator contract. HOME_VALIDATORS_OWNER=0x -# Address on Home network with permissions to upgrade the bridge contract and the bridge validator contract. +# Address on Home network with permissions to upgrade the bridge contract and the +# bridge validator contract. HOME_UPGRADEABLE_ADMIN=0x # The daily transaction limit in Wei. As soon as this limit is exceeded, any # transaction which requests to relay assets will fail. @@ -93,7 +94,8 @@ FOREIGN_RPC_URL=https://mainnet.infura.io FOREIGN_BRIDGE_OWNER=0x # Address on Foreign network with permissions to change parameters of bridge validator contract. FOREIGN_VALIDATORS_OWNER=0x -# Address on Foreign network with permissions to upgrade the bridge contract and the bridge validator contract. +# Address on Foreign network with permissions to upgrade the bridge contract and the +# bridge validator contract. FOREIGN_UPGRADEABLE_ADMIN=0x # The daily limit in Wei. As soon as this limit is exceeded, any transaction # requesting to relay assets will fail. @@ -166,7 +168,8 @@ HOME_RPC_URL=https://poa.infura.io HOME_BRIDGE_OWNER=0x # Address on Home network with permissions to change parameters of bridge validator contract. HOME_VALIDATORS_OWNER=0x -# Address on Home network with permissions to upgrade the bridge contract and the bridge validator contract. +# Address on Home network with permissions to upgrade the bridge contract and +# the bridge validator contract. HOME_UPGRADEABLE_ADMIN=0x # The daily transaction limit in Wei. As soon as this limit is exceeded, any # transaction which requests to relay assets will fail. @@ -195,13 +198,16 @@ FOREIGN_RPC_URL=https://mainnet.infura.io FOREIGN_BRIDGE_OWNER=0x # Address on Foreign network with permissions to change parameters of bridge validator contract. FOREIGN_VALIDATORS_OWNER=0x -# Address on Foreign network with permissions to upgrade the bridge contract and the bridge validator contract. +# Address on Foreign network with permissions to upgrade the bridge contract and the +# bridge validator contract. FOREIGN_UPGRADEABLE_ADMIN=0x -# These three parameters are not used in this mode, but the deployment script -# requires it to be set to some value. -FOREIGN_DAILY_LIMIT=0 -FOREIGN_MAX_AMOUNT_PER_TX=0 -FOREIGN_MIN_AMOUNT_PER_TX=0 +# The daily transaction limit in Wei. This is used on the Home side to check the bridge validator’s actions. +FOREIGN_DAILY_LIMIT=15000000000000000000000000 +# The maximum limit for one transaction in Wei. FOREIGN_MAX_AMOUNT_PER_TX must be less +# than FOREIGN_DAILY_LIMIT +FOREIGN_MAX_AMOUNT_PER_TX=750000000000000000000000 +# Not used in this mode, comment out or delete this variable. +# FOREIGN_MIN_AMOUNT_PER_TX= # The finalization threshold. The number of blocks issued after the block with # the corresponding deposit transaction to guarantee the transaction will not be # rolled back. @@ -257,7 +263,8 @@ HOME_RPC_URL=https://poa.infura.io HOME_BRIDGE_OWNER=0x # Address on Home network with permissions to change parameters of bridge validator contract. HOME_VALIDATORS_OWNER=0x -# Address on Home network with permissions to upgrade the bridge contract and the bridge validator contract. +# Address on Home network with permissions to upgrade the bridge contract and the +# bridge validator contract. HOME_UPGRADEABLE_ADMIN=0x # The daily transaction limit in Wei. As soon as this limit is exceeded, any # transaction which requests to relay assets will fail. @@ -287,15 +294,20 @@ FOREIGN_RPC_URL=https://mainnet.infura.io # Address on Foreign network with permissions to change parameters of the bridge contract. # For extra security we recommended using a multi-sig wallet contract address here. FOREIGN_BRIDGE_OWNER=0x -# Address on Foreign network with permissions to change parameters of bridge validator contract. +# Address on the Foreign network with permissions to change parameters of +# the bridge validator contract. FOREIGN_VALIDATORS_OWNER=0x -# Address on Foreign network with permissions to upgrade the bridge contract and the bridge validator contract. +# Address on the Foreign network with permissions to upgrade the bridge contract +# and the bridge validator contract. FOREIGN_UPGRADEABLE_ADMIN=0x -# These three parameters are not used in this mode, but the deployment script -# requires it to be set to some value. -FOREIGN_DAILY_LIMIT=0 -FOREIGN_MAX_AMOUNT_PER_TX=0 -FOREIGN_MIN_AMOUNT_PER_TX=0 +# The daily transaction limit in Wei. This is used on the Home side to check +# the bridge validator’s actions. +FOREIGN_DAILY_LIMIT=15000000000000000000000000 +# The maximum limit for one transaction in Wei. FOREIGN_MAX_AMOUNT_PER_TX must be +# less than FOREIGN_DAILY_LIMIT +FOREIGN_MAX_AMOUNT_PER_TX=750000000000000000000000 +# Not used in this mode, comment out or delete this variable. +# FOREIGN_MIN_AMOUNT_PER_TX= # The finalization threshold. The number of blocks issued after the block with # the corresponding deposit transaction to guarantee the transaction will not be # rolled back. From 93fca5b975224c7f3466f40ad1ab7ff1dbf50306 Mon Sep 17 00:00:00 2001 From: Andrew Gross Date: Mon, 15 Apr 2019 16:18:16 -0600 Subject: [PATCH 133/187] review comments --- deploy/README.md | 24 ++++++++++++++---------- 1 file changed, 14 insertions(+), 10 deletions(-) diff --git a/deploy/README.md b/deploy/README.md index 2f339a2a5..115609ea2 100644 --- a/deploy/README.md +++ b/deploy/README.md @@ -71,7 +71,8 @@ HOME_UPGRADEABLE_ADMIN=0x # transaction which requests to relay assets will fail. HOME_DAILY_LIMIT=30000000000000000000000000 # The maximum limit for one transaction in Wei. If a single transaction tries to -# relay funds exceeding this limit it will fail. +# relay funds exceeding this limit it will fail. HOME_MAX_AMOUNT_PER_TX must be +# less than HOME_DAILY_LIMIT. HOME_MAX_AMOUNT_PER_TX=1500000000000000000000000 # The minimum limit for one transaction in Wei. If a transaction tries to relay # funds below this limit it will fail. This is required to prevent dryout @@ -101,7 +102,8 @@ FOREIGN_UPGRADEABLE_ADMIN=0x # requesting to relay assets will fail. FOREIGN_DAILY_LIMIT=15000000000000000000000000 # The maximum limit per one transaction in Wei. If a transaction tries to relay -# funds exceeding this limit it will fail. +# funds exceeding this limit it will fail. FOREIGN_MAX_AMOUNT_PER_TX must be less +# than FOREIGN_DAILY_LIMIT. FOREIGN_MAX_AMOUNT_PER_TX=750000000000000000000000 # The minimum limit for one transaction in Wei. If a transaction tries to relay # funds below this limit it will fail. This is required to prevent dryout @@ -175,11 +177,12 @@ HOME_UPGRADEABLE_ADMIN=0x # transaction which requests to relay assets will fail. HOME_DAILY_LIMIT=30000000000000000000000000 # The maximum limit for one transaction in Wei. If a single transaction tries to -# relay funds exceeding this limit it will fail. +# relay funds exceeding this limit it will fail. HOME_MAX_AMOUNT_PER_TX must be +# less than HOME_DAILY_LIMIT. HOME_MAX_AMOUNT_PER_TX=1500000000000000000000000 # The minimum limit for one transaction in Wei. If a transaction tries to relay # funds below this limit it will fail. This is required to prevent dryout -# validator accounts. +# validator accounts. HOME_MIN_AMOUNT_PER_TX=500000000000000000 # The finalization threshold. The number of blocks issued after the block with # the corresponding deposit transaction to guarantee the transaction will not be @@ -201,10 +204,10 @@ FOREIGN_VALIDATORS_OWNER=0x # Address on Foreign network with permissions to upgrade the bridge contract and the # bridge validator contract. FOREIGN_UPGRADEABLE_ADMIN=0x -# The daily transaction limit in Wei. This is used on the Home side to check the bridge validator’s actions. +# The daily transaction limit in Wei. Used on the Home side to check the bridge validator’s actions. FOREIGN_DAILY_LIMIT=15000000000000000000000000 # The maximum limit for one transaction in Wei. FOREIGN_MAX_AMOUNT_PER_TX must be less -# than FOREIGN_DAILY_LIMIT +# than FOREIGN_DAILY_LIMIT. Used on the Home side to check the bridge validator’s actions. FOREIGN_MAX_AMOUNT_PER_TX=750000000000000000000000 # Not used in this mode, comment out or delete this variable. # FOREIGN_MIN_AMOUNT_PER_TX= @@ -270,7 +273,8 @@ HOME_UPGRADEABLE_ADMIN=0x # transaction which requests to relay assets will fail. HOME_DAILY_LIMIT=30000000000000000000000000 # The maximum limit for one transaction in Wei. If a single transaction tries to -# relay funds exceeding this limit it will fail. +# relay funds exceeding this limit it will fail. HOME_MAX_AMOUNT_PER_TX must be +# less than HOME_DAILY_LIMIT. HOME_MAX_AMOUNT_PER_TX=1500000000000000000000000 # The minimum limit for one transaction in Wei. If a transaction tries to relay # funds below this limit it will fail. This is required to prevent dryout @@ -300,11 +304,11 @@ FOREIGN_VALIDATORS_OWNER=0x # Address on the Foreign network with permissions to upgrade the bridge contract # and the bridge validator contract. FOREIGN_UPGRADEABLE_ADMIN=0x -# The daily transaction limit in Wei. This is used on the Home side to check -# the bridge validator’s actions. +# The daily transaction limit in Wei. Used on the Home side to check +# the bridge validator’s actions. FOREIGN_DAILY_LIMIT=15000000000000000000000000 # The maximum limit for one transaction in Wei. FOREIGN_MAX_AMOUNT_PER_TX must be -# less than FOREIGN_DAILY_LIMIT +# less than FOREIGN_DAILY_LIMIT. Used on the Home side to check the bridge validator’s actions. FOREIGN_MAX_AMOUNT_PER_TX=750000000000000000000000 # Not used in this mode, comment out or delete this variable. # FOREIGN_MIN_AMOUNT_PER_TX= From 9be3f38bdf2fa584a0b1367154abf33a6757ad99 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 16 Apr 2019 11:44:39 -0300 Subject: [PATCH 134/187] Move validator events to BaseBridgeValidators --- contracts/upgradeable_contracts/BaseBridgeValidators.sol | 2 ++ contracts/upgradeable_contracts/BridgeValidators.sol | 3 --- contracts/upgradeable_contracts/RewardableValidators.sol | 3 --- 3 files changed, 2 insertions(+), 6 deletions(-) diff --git a/contracts/upgradeable_contracts/BaseBridgeValidators.sol b/contracts/upgradeable_contracts/BaseBridgeValidators.sol index 4405c0e9e..cf0190f35 100644 --- a/contracts/upgradeable_contracts/BaseBridgeValidators.sol +++ b/contracts/upgradeable_contracts/BaseBridgeValidators.sol @@ -10,6 +10,8 @@ contract BaseBridgeValidators is EternalStorage, Ownable { address public constant F_ADDR = 0xFFfFfFffFFfffFFfFFfFFFFFffFFFffffFfFFFfF; + event ValidatorAdded (address indexed validator); + event ValidatorRemoved (address indexed validator); event RequiredSignaturesChanged (uint256 requiredSignatures); function setRequiredSignatures(uint256 _requiredSignatures) diff --git a/contracts/upgradeable_contracts/BridgeValidators.sol b/contracts/upgradeable_contracts/BridgeValidators.sol index 371bdc332..58a7e4795 100644 --- a/contracts/upgradeable_contracts/BridgeValidators.sol +++ b/contracts/upgradeable_contracts/BridgeValidators.sol @@ -5,9 +5,6 @@ import "./BaseBridgeValidators.sol"; contract BridgeValidators is BaseBridgeValidators { - event ValidatorAdded (address indexed validator); - event ValidatorRemoved (address indexed validator); - function initialize( uint256 _requiredSignatures, address[] _initialValidators, diff --git a/contracts/upgradeable_contracts/RewardableValidators.sol b/contracts/upgradeable_contracts/RewardableValidators.sol index 32acab05f..2245fd261 100644 --- a/contracts/upgradeable_contracts/RewardableValidators.sol +++ b/contracts/upgradeable_contracts/RewardableValidators.sol @@ -5,9 +5,6 @@ import "./BaseBridgeValidators.sol"; contract RewardableValidators is BaseBridgeValidators { - event ValidatorAdded (address indexed validator); - event ValidatorRemoved (address indexed validator); - function initialize( uint256 _requiredSignatures, address[] _initialValidators, From 16be3f8229d5bc2c2c34eec5c90bc7721bd3da1c Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 16 Apr 2019 16:13:21 -0300 Subject: [PATCH 135/187] Add event on fee distribution --- .../erc20_to_erc20/HomeBridgeErcToErc.sol | 4 ++ test/erc_to_erc/home_bridge.test.js | 42 ++++++++++++++++--- 2 files changed, 40 insertions(+), 6 deletions(-) diff --git a/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol b/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol index a63bdd0b9..38477bef5 100644 --- a/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol +++ b/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol @@ -15,6 +15,8 @@ import "../../IBlockReward.sol"; contract HomeBridgeErcToErc is ERC677Receiver, EternalStorage, BasicBridge, BasicHomeBridge, ERC677Bridge, OverdrawManagement, RewardableHomeBridgeErcToErc { event AmountLimitExceeded(address recipient, uint256 value, bytes32 transactionHash); + event FeeDistributedFromAffirmation(uint256 feeAmount, bytes32 indexed transactionHash); + event FeeDistributedFromSignatures(uint256 feeAmount, bytes32 indexed transactionHash); function initialize ( address _validatorContract, @@ -146,6 +148,7 @@ contract HomeBridgeErcToErc is ERC677Receiver, EternalStorage, BasicBridge, Basi if (feeManager != address(0)) { uint256 fee = calculateFee(valueToMint, false, feeManager, FOREIGN_FEE); distributeFeeFromAffirmation(fee, feeManager); + emit FeeDistributedFromAffirmation(fee, txHash); valueToMint = valueToMint.sub(fee); } return erc677token().mint(_recipient, valueToMint); @@ -171,6 +174,7 @@ contract HomeBridgeErcToErc is ERC677Receiver, EternalStorage, BasicBridge, Basi (recipient, amount, txHash, contractAddress) = Message.parseMessage(_message); uint256 fee = calculateFee(amount, true, feeManager, HOME_FEE); distributeFeeFromSignatures(fee, feeManager); + emit FeeDistributedFromSignatures(fee, txHash); } } diff --git a/test/erc_to_erc/home_bridge.test.js b/test/erc_to_erc/home_bridge.test.js index 27833c0b4..e7cb11d7d 100644 --- a/test/erc_to_erc/home_bridge.test.js +++ b/test/erc_to_erc/home_bridge.test.js @@ -813,8 +813,13 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const { logs } = await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled; // Then - logs.length.should.be.equal(2) + logs.length.should.be.equal(3) logs[1].event.should.be.equal('CollectedSignatures') + logs[2].event.should.be.equal("FeeDistributedFromSignatures"); + logs[2].args.should.be.deep.equal({ + feeAmount, + transactionHash + }) const finalBridgeBalance = await token.balanceOf(homeBridge.address) finalBridgeBalance.should.be.bignumber.equal('0') @@ -853,8 +858,13 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const { logs } = await homeBridge.submitSignature(signature2, message, {from: validators[1]}).should.be.fulfilled; // Then - logs.length.should.be.equal(2) + logs.length.should.be.equal(3) logs[1].event.should.be.equal('CollectedSignatures') + logs[2].event.should.be.equal("FeeDistributedFromSignatures"); + logs[2].args.should.be.deep.equal({ + feeAmount, + transactionHash + }) const finalBridgeBalance = await token.balanceOf(homeBridge.address) finalBridgeBalance.should.be.bignumber.equal('0') @@ -899,8 +909,13 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const { logs } = await homeBridge.submitSignature(signature3, message, {from: validators[2]}).should.be.fulfilled; // Then - logs.length.should.be.equal(2) + logs.length.should.be.equal(3) logs[1].event.should.be.equal('CollectedSignatures') + logs[2].event.should.be.equal("FeeDistributedFromSignatures"); + logs[2].args.should.be.deep.equal({ + feeAmount, + transactionHash + }) const finalBridgeBalance = await token.balanceOf(homeBridge.address) finalBridgeBalance.should.be.bignumber.equal('0') @@ -959,8 +974,13 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const { logs } = await homeBridge.executeAffirmation(recipient, initialValue, transactionHash, {from: validators[0]}).should.be.fulfilled; // Then - logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); logs[1].args.should.be.deep.equal({ + feeAmount, + transactionHash + }) + logs[2].event.should.be.equal("AffirmationCompleted"); + logs[2].args.should.be.deep.equal({ recipient, value: initialValue, transactionHash @@ -1003,8 +1023,13 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const { logs } = await homeBridge.executeAffirmation(recipient, initialValue, transactionHash, {from: validators[1]}).should.be.fulfilled // Then - logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); logs[1].args.should.be.deep.equal({ + feeAmount, + transactionHash + }) + logs[2].event.should.be.equal("AffirmationCompleted"); + logs[2].args.should.be.deep.equal({ recipient, value: initialValue, transactionHash @@ -1052,8 +1077,13 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const { logs } = await homeBridge.executeAffirmation(recipient, initialValue, transactionHash, {from: validators[2]}).should.be.fulfilled // Then - logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); logs[1].args.should.be.deep.equal({ + feeAmount, + transactionHash + }) + logs[2].event.should.be.equal("AffirmationCompleted"); + logs[2].args.should.be.deep.equal({ recipient, value: initialValue, transactionHash From cf81b767ba72e4ce120b3bd536133fc5a7a0ab7c Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 16 Apr 2019 17:05:06 -0300 Subject: [PATCH 136/187] Refactor BaseFeeManager --- .../upgradeable_contracts/BaseFeeManager.sol | 45 +--------------- .../BlockRewardFeeManager.sol | 24 +++++++++ .../ValidatorsFeeManager.sol | 52 +++++++++++++++++++ .../FeeManagerErcToErcPOSDAO.sol | 30 +---------- .../erc20_to_native/FeeManagerErcToNative.sol | 4 +- .../native_to_erc20/FeeManagerNativeToErc.sol | 4 +- 6 files changed, 84 insertions(+), 75 deletions(-) create mode 100644 contracts/upgradeable_contracts/BlockRewardFeeManager.sol create mode 100644 contracts/upgradeable_contracts/ValidatorsFeeManager.sol diff --git a/contracts/upgradeable_contracts/BaseFeeManager.sol b/contracts/upgradeable_contracts/BaseFeeManager.sol index 52eb98865..9915dc737 100644 --- a/contracts/upgradeable_contracts/BaseFeeManager.sol +++ b/contracts/upgradeable_contracts/BaseFeeManager.sol @@ -43,54 +43,13 @@ contract BaseFeeManager is EternalStorage, FeeTypes { return uintStorage[keccak256(abi.encodePacked("foreignFee"))]; } - function distributeFeeFromAffirmation(uint256 _fee) external { - distributeFeeProportionally(_fee, REWARD_FOR_TRANSFERRING_FROM_FOREIGN); - } + function distributeFeeFromAffirmation(uint256 _fee) external; - function distributeFeeFromSignatures(uint256 _fee) external { - distributeFeeProportionally(_fee, REWARD_FOR_TRANSFERRING_FROM_HOME); - } + function distributeFeeFromSignatures(uint256 _fee) external; function getFeeManagerMode() public pure returns(bytes4); function random(uint256 _count) public view returns(uint256) { return uint256(blockhash(block.number.sub(1))) % _count; } - - function distributeFeeProportionally(uint256 _fee, bytes32 _direction) internal { - IRewardableValidators validators = rewardableValidatorContract(); - address[] memory validatorList = validators.validatorList(); - uint256 feePerValidator = _fee.div(validatorList.length); - - uint256 randomValidatorIndex; - uint256 diff = _fee.sub(feePerValidator.mul(validatorList.length)); - if (diff > 0) { - randomValidatorIndex = random(validatorList.length); - } - - for (uint256 i = 0; i < validatorList.length; i++) { - uint256 feeToDistribute = feePerValidator; - if (diff > 0 && randomValidatorIndex == i) { - feeToDistribute = feeToDistribute.add(diff); - } - address rewardAddress = validators.getValidatorRewardAddress(validatorList[i]); - onFeeDistribution(rewardAddress, feeToDistribute, _direction); - } - } - - function onFeeDistribution(address _rewardAddress, uint256 _fee, bytes32 _direction) internal { - if (_direction == REWARD_FOR_TRANSFERRING_FROM_FOREIGN) { - onAffirmationFeeDistribution(_rewardAddress, _fee); - } else { - onSignatureFeeDistribution(_rewardAddress, _fee); - } - } - - function onAffirmationFeeDistribution(address _rewardAddress, uint256 _fee) internal; - - function onSignatureFeeDistribution(address _rewardAddress, uint256 _fee) internal; - - function rewardableValidatorContract() public view returns(IRewardableValidators) { - return IRewardableValidators(addressStorage[keccak256(abi.encodePacked("validatorContract"))]); - } } diff --git a/contracts/upgradeable_contracts/BlockRewardFeeManager.sol b/contracts/upgradeable_contracts/BlockRewardFeeManager.sol new file mode 100644 index 000000000..cfdeedc6f --- /dev/null +++ b/contracts/upgradeable_contracts/BlockRewardFeeManager.sol @@ -0,0 +1,24 @@ +pragma solidity 0.4.24; + +import "./BaseFeeManager.sol"; +import "../IBlockReward.sol"; + +contract BlockRewardFeeManager is BaseFeeManager { + + function distributeFeeFromAffirmation(uint256 _fee) external { + distributeFeeFromBlockReward(_fee); + } + + function distributeFeeFromSignatures(uint256 _fee) external { + distributeFeeFromBlockReward(_fee); + } + + function distributeFeeFromBlockReward(uint256 _fee) internal { + IBlockReward blockReward = _blockRewardContract(); + blockReward.addBridgeTokenFeeReceivers(_fee); + } + + function _blockRewardContract() internal view returns(IBlockReward) { + return IBlockReward(addressStorage[keccak256(abi.encodePacked("blockRewardContract"))]); + } +} diff --git a/contracts/upgradeable_contracts/ValidatorsFeeManager.sol b/contracts/upgradeable_contracts/ValidatorsFeeManager.sol new file mode 100644 index 000000000..c3ea01885 --- /dev/null +++ b/contracts/upgradeable_contracts/ValidatorsFeeManager.sol @@ -0,0 +1,52 @@ +pragma solidity 0.4.24; + +import "./BaseFeeManager.sol"; +import "../IRewardableValidators.sol"; + +contract ValidatorsFeeManager is BaseFeeManager { + + function distributeFeeFromAffirmation(uint256 _fee) external { + distributeFeeProportionally(_fee, REWARD_FOR_TRANSFERRING_FROM_FOREIGN); + } + + function distributeFeeFromSignatures(uint256 _fee) external { + distributeFeeProportionally(_fee, REWARD_FOR_TRANSFERRING_FROM_HOME); + } + + function rewardableValidatorContract() internal view returns(IRewardableValidators) { + return IRewardableValidators(addressStorage[keccak256(abi.encodePacked("validatorContract"))]); + } + + function distributeFeeProportionally(uint256 _fee, bytes32 _direction) internal { + IRewardableValidators validators = rewardableValidatorContract(); + address[] memory validatorList = validators.validatorList(); + uint256 feePerValidator = _fee.div(validatorList.length); + + uint256 randomValidatorIndex; + uint256 diff = _fee.sub(feePerValidator.mul(validatorList.length)); + if (diff > 0) { + randomValidatorIndex = random(validatorList.length); + } + + for (uint256 i = 0; i < validatorList.length; i++) { + uint256 feeToDistribute = feePerValidator; + if (diff > 0 && randomValidatorIndex == i) { + feeToDistribute = feeToDistribute.add(diff); + } + address rewardAddress = validators.getValidatorRewardAddress(validatorList[i]); + onFeeDistribution(rewardAddress, feeToDistribute, _direction); + } + } + + function onFeeDistribution(address _rewardAddress, uint256 _fee, bytes32 _direction) internal { + if (_direction == REWARD_FOR_TRANSFERRING_FROM_FOREIGN) { + onAffirmationFeeDistribution(_rewardAddress, _fee); + } else { + onSignatureFeeDistribution(_rewardAddress, _fee); + } + } + + function onAffirmationFeeDistribution(address _rewardAddress, uint256 _fee) internal; + + function onSignatureFeeDistribution(address _rewardAddress, uint256 _fee) internal; +} diff --git a/contracts/upgradeable_contracts/erc20_to_erc20/FeeManagerErcToErcPOSDAO.sol b/contracts/upgradeable_contracts/erc20_to_erc20/FeeManagerErcToErcPOSDAO.sol index 4323c7f85..3db72b73f 100644 --- a/contracts/upgradeable_contracts/erc20_to_erc20/FeeManagerErcToErcPOSDAO.sol +++ b/contracts/upgradeable_contracts/erc20_to_erc20/FeeManagerErcToErcPOSDAO.sol @@ -1,36 +1,10 @@ pragma solidity 0.4.24; -import "../BaseFeeManager.sol"; -import "../../IBlockReward.sol"; +import "../BlockRewardFeeManager.sol"; -contract FeeManagerErcToErcPOSDAO is BaseFeeManager { +contract FeeManagerErcToErcPOSDAO is BlockRewardFeeManager { function getFeeManagerMode() public pure returns(bytes4) { return bytes4(keccak256(abi.encodePacked("manages-both-directions"))); } - - function blockRewardContract() internal view returns(IBlockReward) { - return IBlockReward(addressStorage[keccak256(abi.encodePacked("blockRewardContract"))]); - } - - function distributeFeeFromAffirmation(uint256 _fee) external { - distributeFeeFromBlockReward(_fee); - } - - function distributeFeeFromSignatures(uint256 _fee) external { - distributeFeeFromBlockReward(_fee); - } - - function distributeFeeFromBlockReward(uint256 _fee) internal { - IBlockReward blockReward = blockRewardContract(); - blockReward.addBridgeTokenFeeReceivers(_fee); - } - - function isPOSDAOFeeManager() public pure returns(bool) { - return true; - } - - function onAffirmationFeeDistribution(address _rewardAddress, uint256 _fee) internal {} - - function onSignatureFeeDistribution(address _rewardAddress, uint256 _fee) internal {} } diff --git a/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol index be80bdd03..0829fbfe5 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol @@ -1,11 +1,11 @@ pragma solidity 0.4.24; -import "../BaseFeeManager.sol"; import "../../IBlockReward.sol"; import "../Sacrifice.sol"; +import "../ValidatorsFeeManager.sol"; -contract FeeManagerErcToNative is BaseFeeManager { +contract FeeManagerErcToNative is ValidatorsFeeManager { function getFeeManagerMode() public pure returns(bytes4) { return bytes4(keccak256(abi.encodePacked("manages-both-directions"))); diff --git a/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErc.sol index a1f5b4c4e..521ff559a 100644 --- a/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErc.sol +++ b/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErc.sol @@ -1,11 +1,11 @@ pragma solidity 0.4.24; -import "../BaseFeeManager.sol"; import "../../IBurnableMintableERC677Token.sol"; import "../Sacrifice.sol"; +import "../ValidatorsFeeManager.sol"; -contract FeeManagerNativeToErc is BaseFeeManager { +contract FeeManagerNativeToErc is ValidatorsFeeManager { function getFeeManagerMode() public pure returns(bytes4) { return bytes4(keccak256(abi.encodePacked("manages-one-direction"))); From 95f236205b2652b4bfe507ac376de5626d75cf52 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 16 Apr 2019 17:09:09 -0300 Subject: [PATCH 137/187] Fix _initialize on HomeBridgeErcToErc --- .../upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol b/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol index 38477bef5..179762fe5 100644 --- a/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol +++ b/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol @@ -101,7 +101,7 @@ contract HomeBridgeErcToErc is ERC677Receiver, EternalStorage, BasicBridge, Basi uint256 _foreignDailyLimit, uint256 _foreignMaxPerTx, address _owner - ) public + ) internal returns(bool) { require(!isInitialized()); From 63fbd12a65ceb9df86da873ad86bb21c4ad3d82a Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 16 Apr 2019 17:28:26 -0300 Subject: [PATCH 138/187] Move ValidatorsFeeManager constants --- contracts/upgradeable_contracts/BaseFeeManager.sol | 4 ---- contracts/upgradeable_contracts/ValidatorsFeeManager.sol | 4 ++++ 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/contracts/upgradeable_contracts/BaseFeeManager.sol b/contracts/upgradeable_contracts/BaseFeeManager.sol index 9915dc737..3b2f668d0 100644 --- a/contracts/upgradeable_contracts/BaseFeeManager.sol +++ b/contracts/upgradeable_contracts/BaseFeeManager.sol @@ -9,10 +9,6 @@ import "./FeeTypes.sol"; contract BaseFeeManager is EternalStorage, FeeTypes { using SafeMath for uint256; - bytes32 public constant REWARD_FOR_TRANSFERRING_FROM_HOME = keccak256(abi.encodePacked("reward-transferring-from-home")); - - bytes32 public constant REWARD_FOR_TRANSFERRING_FROM_FOREIGN = keccak256(abi.encodePacked("reward-transferring-from-foreign")); - event HomeFeeUpdated(uint256 fee); event ForeignFeeUpdated(uint256 fee); diff --git a/contracts/upgradeable_contracts/ValidatorsFeeManager.sol b/contracts/upgradeable_contracts/ValidatorsFeeManager.sol index c3ea01885..0f7f32b0d 100644 --- a/contracts/upgradeable_contracts/ValidatorsFeeManager.sol +++ b/contracts/upgradeable_contracts/ValidatorsFeeManager.sol @@ -5,6 +5,10 @@ import "../IRewardableValidators.sol"; contract ValidatorsFeeManager is BaseFeeManager { + bytes32 public constant REWARD_FOR_TRANSFERRING_FROM_HOME = keccak256(abi.encodePacked("reward-transferring-from-home")); + + bytes32 public constant REWARD_FOR_TRANSFERRING_FROM_FOREIGN = keccak256(abi.encodePacked("reward-transferring-from-foreign")); + function distributeFeeFromAffirmation(uint256 _fee) external { distributeFeeProportionally(_fee, REWARD_FOR_TRANSFERRING_FROM_FOREIGN); } From 8ab76b90445420da077ad096f01a2ae68cd5b7d7 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 17 Apr 2019 11:22:33 -0300 Subject: [PATCH 139/187] Add POSDAOHomeBridgeErcToErc --- .../FeeManagerErcToErcPOSDAO.sol | 16 +++++ .../erc20_to_erc20/HomeBridgeErcToErc.sol | 52 ++++++++++---- .../POSDAOHomeBridgeErcToErc.sol | 70 +++++++++++++++++++ test/erc_to_erc/home_bridge.test.js | 49 +++++++++---- 4 files changed, 158 insertions(+), 29 deletions(-) create mode 100644 contracts/upgradeable_contracts/erc20_to_erc20/POSDAOHomeBridgeErcToErc.sol diff --git a/contracts/upgradeable_contracts/erc20_to_erc20/FeeManagerErcToErcPOSDAO.sol b/contracts/upgradeable_contracts/erc20_to_erc20/FeeManagerErcToErcPOSDAO.sol index 3db72b73f..da27b4379 100644 --- a/contracts/upgradeable_contracts/erc20_to_erc20/FeeManagerErcToErcPOSDAO.sol +++ b/contracts/upgradeable_contracts/erc20_to_erc20/FeeManagerErcToErcPOSDAO.sol @@ -7,4 +7,20 @@ contract FeeManagerErcToErcPOSDAO is BlockRewardFeeManager { function getFeeManagerMode() public pure returns(bytes4) { return bytes4(keccak256(abi.encodePacked("manages-both-directions"))); } + + function blockRewardContract() public view returns(address) { + return _blockRewardContract(); + } + + function setBlockRewardContract(address _blockReward) external { + require(_blockReward != address(0) && isContract(_blockReward) && (IBlockReward(_blockReward).bridgesAllowedLength() != 0)); + addressStorage[keccak256(abi.encodePacked("blockRewardContract"))] = _blockReward; + } + + function isContract(address _addr) internal view returns (bool) + { + uint length; + assembly { length := extcodesize(_addr) } + return length > 0; + } } diff --git a/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol b/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol index 179762fe5..545617251 100644 --- a/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol +++ b/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol @@ -60,12 +60,48 @@ contract HomeBridgeErcToErc is ERC677Receiver, EternalStorage, BasicBridge, Basi uint256 _foreignDailyLimit, uint256 _foreignMaxPerTx, address _owner, - address _blockReward, address _feeManager, uint256 _homeFee, uint256 _foreignFee ) public returns(bool) + { + _rewardableInitialize ( + _validatorContract, + _dailyLimit, + _maxPerTx, + _minPerTx, + _homeGasPrice, + _requiredBlockConfirmations, + _erc677token, + _foreignDailyLimit, + _foreignMaxPerTx, + _owner, + _feeManager, + _homeFee, + _foreignFee + ); + setInitialize(true); + + return isInitialized(); + } + + function _rewardableInitialize ( + address _validatorContract, + uint256 _dailyLimit, + uint256 _maxPerTx, + uint256 _minPerTx, + uint256 _homeGasPrice, + uint256 _requiredBlockConfirmations, + address _erc677token, + uint256 _foreignDailyLimit, + uint256 _foreignMaxPerTx, + address _owner, + address _feeManager, + uint256 _homeFee, + uint256 _foreignFee + ) internal + returns(bool) { _initialize ( _validatorContract, @@ -80,14 +116,9 @@ contract HomeBridgeErcToErc is ERC677Receiver, EternalStorage, BasicBridge, Basi _owner ); require(isContract(_feeManager)); - require(_blockReward == address(0) || isContract(_blockReward)); addressStorage[keccak256(abi.encodePacked("feeManagerContract"))] = _feeManager; _setFee(_feeManager, _homeFee, HOME_FEE); _setFee(_feeManager, _foreignFee, FOREIGN_FEE); - addressStorage[keccak256(abi.encodePacked("blockRewardContract"))] = _blockReward; - setInitialize(true); - - return isInitialized(); } function _initialize ( @@ -132,15 +163,6 @@ contract HomeBridgeErcToErc is ERC677Receiver, EternalStorage, BasicBridge, Basi revert(); } - function blockRewardContract() public view returns(IBlockReward) { - return IBlockReward(addressStorage[keccak256(abi.encodePacked("blockRewardContract"))]); - } - - function setBlockRewardContract(address _blockReward) public onlyOwner { - require(_blockReward != address(0) && isContract(_blockReward) && (IBlockReward(_blockReward).bridgesAllowedLength() != 0)); - addressStorage[keccak256(abi.encodePacked("blockRewardContract"))] = _blockReward; - } - function onExecuteAffirmation(address _recipient, uint256 _value, bytes32 txHash) internal returns(bool) { setTotalExecutedPerDay(getCurrentDay(), totalExecutedPerDay(getCurrentDay()).add(_value)); uint256 valueToMint = _value; diff --git a/contracts/upgradeable_contracts/erc20_to_erc20/POSDAOHomeBridgeErcToErc.sol b/contracts/upgradeable_contracts/erc20_to_erc20/POSDAOHomeBridgeErcToErc.sol new file mode 100644 index 000000000..76b4bd409 --- /dev/null +++ b/contracts/upgradeable_contracts/erc20_to_erc20/POSDAOHomeBridgeErcToErc.sol @@ -0,0 +1,70 @@ +pragma solidity 0.4.24; + +import "./HomeBridgeErcToErc.sol"; + +contract POSDAOHomeBridgeErcToErc is HomeBridgeErcToErc { + + function rewardableInitialize ( + address _validatorContract, + uint256 _dailyLimit, + uint256 _maxPerTx, + uint256 _minPerTx, + uint256 _homeGasPrice, + uint256 _requiredBlockConfirmations, + address _erc677token, + uint256 _foreignDailyLimit, + uint256 _foreignMaxPerTx, + address _owner, + address _feeManager, + uint256 _homeFee, + uint256 _foreignFee, + address _blockReward + ) public + returns(bool) + { + _rewardableInitialize ( + _validatorContract, + _dailyLimit, + _maxPerTx, + _minPerTx, + _homeGasPrice, + _requiredBlockConfirmations, + _erc677token, + _foreignDailyLimit, + _foreignMaxPerTx, + _owner, + _feeManager, + _homeFee, + _foreignFee + ); + _setBlockRewardContract(_feeManager, _blockReward); + setInitialize(true); + + return isInitialized(); + } + + function blockRewardContract() public view returns(address) { + address blockReward; + address feeManager = feeManagerContract(); + bytes memory callData = abi.encodeWithSignature("blockRewardContract()"); + + assembly { + let result := callcode(gas, feeManager, 0x0, add(callData, 0x20), mload(callData), 0, 32) + blockReward := mload(0) + + switch result + case 0 { revert(0, 0) } + } + + return blockReward; + } + + function setBlockRewardContract(address _blockReward) public onlyOwner { + address feeManager = feeManagerContract(); + _setBlockRewardContract(feeManager, _blockReward); + } + + function _setBlockRewardContract(address _feeManager, address _blockReward) internal { + require(_feeManager.delegatecall(abi.encodeWithSignature("setBlockRewardContract(address)", _blockReward))); + } +} diff --git a/test/erc_to_erc/home_bridge.test.js b/test/erc_to_erc/home_bridge.test.js index e7cb11d7d..99da6ff33 100644 --- a/test/erc_to_erc/home_bridge.test.js +++ b/test/erc_to_erc/home_bridge.test.js @@ -1,5 +1,6 @@ const Web3Utils = require('web3-utils'); const HomeBridge = artifacts.require("HomeBridgeErcToErc.sol"); +const POSDAOHomeBridge = artifacts.require("POSDAOHomeBridgeErcToErc.sol"); const EternalStorageProxy = artifacts.require("EternalStorageProxy.sol"); const BridgeValidators = artifacts.require("BridgeValidators.sol"); const ERC677BridgeToken = artifacts.require("ERC677BridgeToken.sol"); @@ -633,7 +634,7 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); rewardableValidators = await RewardableValidators.new() await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled - homeBridge = await HomeBridge.new() + homeBridge = await POSDAOHomeBridge.new() homeFee = web3.toBigNumber(web3.toWei(0.002, "ether")) foreignFee = web3.toBigNumber(web3.toWei(0.002, "ether")) blockRewardContract = await BlockReward.new() @@ -646,11 +647,11 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { '0'.should.be.bignumber.equal(await homeBridge.maxPerTx()) false.should.be.equal(await homeBridge.isInitialized()) - await homeBridge.rewardableInitialize(ZERO_ADDRESS, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, blockRewardContract.address, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, 0, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, blockRewardContract.address, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, 0, foreignDailyLimit, token.address, foreignMaxPerTx, owner, blockRewardContract.address, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, blockRewardContract.address, ZERO_ADDRESS, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, blockRewardContract.address, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + await homeBridge.rewardableInitialize(ZERO_ADDRESS, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.rejectedWith(ERROR_MSG); + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, 0, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.rejectedWith(ERROR_MSG); + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, 0, foreignDailyLimit, token.address, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.rejectedWith(ERROR_MSG); + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, ZERO_ADDRESS, homeFee, foreignFee, blockRewardContract.address).should.be.rejectedWith(ERROR_MSG); + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.fulfilled; true.should.be.equal(await homeBridge.isInitialized()) rewardableValidators.address.should.be.equal(await homeBridge.validatorContract()); @@ -672,10 +673,12 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { bridgeHomeFee.should.be.bignumber.equal(homeFee) const bridgeForeignFee = await homeBridge.getForeignFee() bridgeForeignFee.should.be.bignumber.equal(foreignFee) + const blockReward = await homeBridge.blockRewardContract() + blockReward.should.be.equals(blockRewardContract.address) }) it('can update fee contract', async () => { const feeManager = await FeeManagerErcToErcPOSDAO.new() - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, blockRewardContract.address, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.fulfilled; // Given const newFeeManager = await FeeManagerErcToErcPOSDAO.new() @@ -689,7 +692,7 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { }) it('can update fee', async () => { const feeManager = await FeeManagerErcToErcPOSDAO.new() - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, blockRewardContract.address, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.fulfilled; // Given const newHomeFee = web3.toBigNumber(web3.toWei(0.1, "ether")) @@ -711,12 +714,29 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const bothDirectionsModeHash = '0xd7de965f' // When - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, blockRewardContract.address, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.fulfilled; // Then const feeManagerMode = await homeBridge.getFeeManagerMode() feeManagerMode.should.be.equals(bothDirectionsModeHash) }) + it('should be able to set blockReward contract', async () => { + // Given + const feeManager = await FeeManagerErcToErcPOSDAO.new() + + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.fulfilled; + + const blockReward = await homeBridge.blockRewardContract() + blockReward.should.be.equals(blockRewardContract.address) + + // When + const newBlockRewardContract = await BlockReward.new() + await homeBridge.setBlockRewardContract(newBlockRewardContract.address).should.be.fulfilled + + // Then + const newBlockReward = await homeBridge.blockRewardContract() + newBlockReward.should.be.equals(newBlockRewardContract.address) + }) }) describe('#onTokenTransfer', async () => { let homeBridge @@ -744,6 +764,7 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { }) it('should trigger UserRequestForSignature with fee subtracted', async () => { // Given + const homeBridge = await POSDAOHomeBridge.new() const owner = accounts[0] const user = accounts[4] const validators = [accounts[1]] @@ -757,7 +778,7 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const homeFee = web3.toBigNumber(web3.toWei(0.001, "ether")) const foreignFee = web3.toBigNumber(web3.toWei(0.001, "ether")) - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, blockRewardContract.address, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.fulfilled; const value = halfEther const finalValue = value.mul(web3.toBigNumber(1 - fee)) await token.mint(user, value, {from: owner}).should.be.fulfilled; @@ -779,12 +800,12 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { token = await ERC677BridgeTokenRewardable.new("Some ERC20", "RSZT", 18); rewardableValidators = await RewardableValidators.new() feeManager = await FeeManagerErcToErcPOSDAO.new() - homeBridge = await HomeBridge.new() + homeBridge = await POSDAOHomeBridge.new() fee = 0.001 homeFee = web3.toBigNumber(web3.toWei(fee, "ether")) foreignFee = web3.toBigNumber(web3.toWei(fee, "ether")) blockRewardContract = await BlockReward.new() - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, blockRewardContract.address, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.fulfilled; }) it('should distribute fee to one validator', async () => { // Given @@ -942,12 +963,12 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { token = await ERC677BridgeTokenRewardable.new("Some ERC20", "RSZT", 18); rewardableValidators = await RewardableValidators.new() feeManager = await FeeManagerErcToErcPOSDAO.new() - homeBridge = await HomeBridge.new() + homeBridge = await POSDAOHomeBridge.new() fee = 0.001 homeFee = web3.toBigNumber(web3.toWei(fee, "ether")) foreignFee = web3.toBigNumber(web3.toWei(fee, "ether")) blockRewardContract = await BlockReward.new() - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, blockRewardContract.address, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.fulfilled; }) it('should distribute fee to one validator', async () => { // Given From 851c0b92f57f33755ee9625497856f4a7875dcce Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 17 Apr 2019 15:24:02 -0300 Subject: [PATCH 140/187] Fix erc_to_erc home deploy script --- deploy/src/erc_to_erc/home.js | 27 ++++++++++++++++++--------- deploy/src/loadEnv.js | 10 ++++++++++ 2 files changed, 28 insertions(+), 9 deletions(-) diff --git a/deploy/src/erc_to_erc/home.js b/deploy/src/erc_to_erc/home.js index 98bc675b0..ca276a0bd 100644 --- a/deploy/src/erc_to_erc/home.js +++ b/deploy/src/erc_to_erc/home.js @@ -1,6 +1,7 @@ const assert = require('assert') const Web3Utils = require('web3-utils') const env = require('../loadEnv') +const { ZERO_ADDRESS } = require('../constants') const { deployContract, @@ -13,8 +14,9 @@ const { web3Home, deploymentPrivateKey, HOME_RPC_URL } = require('../web3') const EternalStorageProxy = require('../../../build/contracts/EternalStorageProxy.json') const BridgeValidators = require('../../../build/contracts/BridgeValidators.json') const RewardableValidators = require('../../../build/contracts/RewardableValidators.json') -const FeeManagerErcToErcPOSDAO = require('../../../build/contracts/FeeManagerErcToErcPOSDAO') +const FeeManagerErcToErcPOSDAO = require('../../../build/contracts/FeeManagerErcToErcPOSDAO.json') const HomeBridge = require('../../../build/contracts/HomeBridgeErcToErc.json') +const POSDAOHomeBridge = require('../../../build/contracts/POSDAOHomeBridgeErcToErc.json') const ERC677BridgeToken = require('../../../build/contracts/ERC677BridgeToken.json') const ERC677BridgeTokenRewardable = require('../../../build/contracts/ERC677BridgeTokenRewardable.json') @@ -60,7 +62,10 @@ async function deployHome() { homeNonce++ console.log('\ndeploying implementation for home validators') - const bridgeValidatorsContract = isRewardableBridge ? RewardableValidators : BridgeValidators + const bridgeValidatorsContract = + isRewardableBridge && BLOCK_REWARD_ADDRESS === ZERO_ADDRESS + ? RewardableValidators + : BridgeValidators const bridgeValidatorsHome = await deployContract(bridgeValidatorsContract, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, nonce: homeNonce @@ -87,7 +92,7 @@ async function deployHome() { let initializeData - if (isRewardableBridge) { + if (isRewardableBridge && BLOCK_REWARD_ADDRESS === ZERO_ADDRESS) { console.log( `REQUIRED_NUMBER_OF_VALIDATORS: ${REQUIRED_NUMBER_OF_VALIDATORS}, HOME_VALIDATORS_OWNER: ${HOME_VALIDATORS_OWNER}` ) @@ -141,7 +146,9 @@ async function deployHome() { console.log('[Home] HomeBridge Storage: ', homeBridgeStorage.options.address) console.log('\ndeploying homeBridge implementation\n') - const homeBridgeImplementation = await deployContract(HomeBridge, [], { + const bridgeContract = + isRewardableBridge && BLOCK_REWARD_ADDRESS !== ZERO_ADDRESS ? POSDAOHomeBridge : HomeBridge + const homeBridgeImplementation = await deployContract(bridgeContract, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, nonce: homeNonce }) @@ -164,7 +171,9 @@ async function deployHome() { console.log('\n[Home] deploying Bridgeble token') const erc677Contract = - isRewardableBridge || DEPLOY_REWARDABLE_TOKEN ? ERC677BridgeTokenRewardable : ERC677BridgeToken + (isRewardableBridge && BLOCK_REWARD_ADDRESS !== ZERO_ADDRESS) || DEPLOY_REWARDABLE_TOKEN + ? ERC677BridgeTokenRewardable + : ERC677BridgeToken const erc677token = await deployContract( erc677Contract, [BRIDGEABLE_TOKEN_NAME, BRIDGEABLE_TOKEN_SYMBOL, BRIDGEABLE_TOKEN_DECIMALS], @@ -187,7 +196,7 @@ async function deployHome() { assert.strictEqual(Web3Utils.hexToNumber(setBridgeContract.status), 1, 'Transaction Failed') homeNonce++ - if (isRewardableBridge || DEPLOY_REWARDABLE_TOKEN) { + if ((isRewardableBridge && BLOCK_REWARD_ADDRESS !== ZERO_ADDRESS) || DEPLOY_REWARDABLE_TOKEN) { console.log('\nset BlockReward contract on ERC677BridgeTokenRewardable') const setBlockRewardContractData = await erc677token.methods .setBlockRewardContract(BLOCK_REWARD_ADDRESS) @@ -240,7 +249,7 @@ async function deployHome() { let initializeHomeBridgeData homeBridgeImplementation.options.address = homeBridgeStorage.options.address - if (isRewardableBridge) { + if (isRewardableBridge && BLOCK_REWARD_ADDRESS !== ZERO_ADDRESS) { console.log('\ndeploying implementation for fee manager') const feeManager = await deployContract(FeeManagerErcToErcPOSDAO, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, @@ -277,10 +286,10 @@ async function deployHome() { FOREIGN_DAILY_LIMIT, FOREIGN_MAX_AMOUNT_PER_TX, HOME_BRIDGE_OWNER, - BLOCK_REWARD_ADDRESS, feeManager.options.address, homeFeeInWei, - foreignFeeInWei + foreignFeeInWei, + BLOCK_REWARD_ADDRESS ) .encodeABI() } else { diff --git a/deploy/src/loadEnv.js b/deploy/src/loadEnv.js index 0cfafeb0a..0e515578e 100644 --- a/deploy/src/loadEnv.js +++ b/deploy/src/loadEnv.js @@ -135,4 +135,14 @@ if (HOME_REWARDABLE === 'true' || FOREIGN_REWARDABLE === 'true') { const env = envalid.cleanEnv(process.env, validations) +if ( + env.BRIDGE_MODE === 'ERC_TO_ERC' && + env.HOME_REWARDABLE === 'true' && + env.BLOCK_REWARD_ADDRESS === ZERO_ADDRESS +) { + throw new Error( + 'Collecting fees on Home Network on ERC_TO_ERC mode without Block Reward contract is not supported.' + ) +} + module.exports = env From fd5086bb334bb279c608935431a6a32a2c803a04 Mon Sep 17 00:00:00 2001 From: Alexander Kolotov Date: Thu, 18 Apr 2019 16:47:50 +0300 Subject: [PATCH 141/187] Fee distribution events moved to the RewardableBridge contract --- contracts/upgradeable_contracts/BasicForeignBridge.sol | 4 ++-- contracts/upgradeable_contracts/RewardableBridge.sol | 9 +++++++-- .../erc20_to_erc20/ForeignBridgeErcToErc.sol | 2 +- .../erc20_to_native/ForeignBridgeErcToNative.sol | 2 +- .../erc20_to_native/HomeBridgeErcToNative.sol | 8 ++------ .../native_to_erc20/ForeignBridgeNativeToErc.sol | 4 ++-- .../native_to_erc20/HomeBridgeNativeToErc.sol | 5 +---- 7 files changed, 16 insertions(+), 18 deletions(-) diff --git a/contracts/upgradeable_contracts/BasicForeignBridge.sol b/contracts/upgradeable_contracts/BasicForeignBridge.sol index 5198a1a5f..365c4c169 100644 --- a/contracts/upgradeable_contracts/BasicForeignBridge.sol +++ b/contracts/upgradeable_contracts/BasicForeignBridge.sol @@ -21,14 +21,14 @@ contract BasicForeignBridge is EternalStorage, Validatable { require(contractAddress == address(this)); require(!relayedMessages(txHash)); setRelayedMessages(txHash, true); - require(onExecuteMessage(recipient, amount)); + require(onExecuteMessage(recipient, amount, txHash)); emit RelayedMessage(recipient, amount, txHash); } else { onFailedMessage(recipient, amount, txHash); } } - function onExecuteMessage(address, uint256) internal returns(bool); + function onExecuteMessage(address, uint256, bytes32) internal returns(bool); function setRelayedMessages(bytes32 _txHash, bool _status) internal { boolStorage[keccak256(abi.encodePacked("relayedMessages", _txHash))] = _status; diff --git a/contracts/upgradeable_contracts/RewardableBridge.sol b/contracts/upgradeable_contracts/RewardableBridge.sol index d21aeff26..295ca025c 100644 --- a/contracts/upgradeable_contracts/RewardableBridge.sol +++ b/contracts/upgradeable_contracts/RewardableBridge.sol @@ -6,6 +6,9 @@ import "./FeeTypes.sol"; contract RewardableBridge is Ownable, FeeTypes { + event FeeDistributedFromAffirmation(uint256 feeAmount, bytes32 indexed transactionHash); + event FeeDistributedFromSignatures(uint256 feeAmount, bytes32 indexed transactionHash); + function _getFee(bytes32 _feeType) internal view returns(uint256) { uint256 fee; address feeManager = feeManagerContract(); @@ -70,11 +73,13 @@ contract RewardableBridge is Ownable, FeeTypes { return fee; } - function distributeFeeFromSignatures(uint256 _fee, address _feeManager) internal { + function distributeFeeFromSignatures(uint256 _fee, address _feeManager, bytes32 _txHash) internal { require(_feeManager.delegatecall(abi.encodeWithSignature("distributeFeeFromSignatures(uint256)", _fee))); + emit FeeDistributedFromSignatures(_fee, _txHash); } - function distributeFeeFromAffirmation(uint256 _fee, address _feeManager) internal { + function distributeFeeFromAffirmation(uint256 _fee, address _feeManager, bytes32 _txHash) internal { require(_feeManager.delegatecall(abi.encodeWithSignature("distributeFeeFromAffirmation(uint256)", _fee))); + emit FeeDistributedFromAffirmation(_fee, _txHash); } } diff --git a/contracts/upgradeable_contracts/erc20_to_erc20/ForeignBridgeErcToErc.sol b/contracts/upgradeable_contracts/erc20_to_erc20/ForeignBridgeErcToErc.sol index 73a2a34ab..f609c8659 100644 --- a/contracts/upgradeable_contracts/erc20_to_erc20/ForeignBridgeErcToErc.sol +++ b/contracts/upgradeable_contracts/erc20_to_erc20/ForeignBridgeErcToErc.sol @@ -54,7 +54,7 @@ contract ForeignBridgeErcToErc is BasicBridge, BasicForeignBridge { return ERC20Basic(addressStorage[keccak256(abi.encodePacked("erc20token"))]); } - function onExecuteMessage(address _recipient, uint256 _amount) internal returns(bool){ + function onExecuteMessage(address _recipient, uint256 _amount, bytes32 _txHash) internal returns(bool){ setTotalExecutedPerDay(getCurrentDay(), totalExecutedPerDay(getCurrentDay()).add(_amount)); return erc20token().transfer(_recipient, _amount); } diff --git a/contracts/upgradeable_contracts/erc20_to_native/ForeignBridgeErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/ForeignBridgeErcToNative.sol index c64317685..aa9e292b8 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/ForeignBridgeErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/ForeignBridgeErcToNative.sol @@ -53,7 +53,7 @@ contract ForeignBridgeErcToNative is BasicBridge, BasicForeignBridge { return ERC20Basic(addressStorage[keccak256(abi.encodePacked("erc20token"))]); } - function onExecuteMessage(address _recipient, uint256 _amount) internal returns(bool) { + function onExecuteMessage(address _recipient, uint256 _amount, bytes32 _txHash) internal returns(bool) { setTotalExecutedPerDay(getCurrentDay(), totalExecutedPerDay(getCurrentDay()).add(_amount)); return erc20token().transfer(_recipient, _amount); } diff --git a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol index 7f6f8da87..223380aaa 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol @@ -14,8 +14,6 @@ import "./RewardableHomeBridgeErcToNative.sol"; contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, OverdrawManagement, RewardableHomeBridgeErcToNative { event AmountLimitExceeded(address recipient, uint256 value, bytes32 transactionHash); - event FeeDistributedFromAffirmation(uint256 feeAmount, bytes32 indexed transactionHash); - event FeeDistributedFromSignatures(uint256 feeAmount, bytes32 indexed transactionHash); function () public payable { require(msg.value > 0); @@ -162,9 +160,8 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, address feeManager = feeManagerContract(); if (feeManager != address(0)) { uint256 fee = calculateFee(valueToMint, false, feeManager, FOREIGN_FEE); - distributeFeeFromAffirmation(fee, feeManager); + distributeFeeFromAffirmation(fee, feeManager, txHash); valueToMint = valueToMint.sub(fee); - emit FeeDistributedFromAffirmation(fee, txHash); } blockReward.addExtraReceiver(valueToMint, _recipient); return true; @@ -179,8 +176,7 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, address contractAddress; (recipient, amount, txHash, contractAddress) = Message.parseMessage(_message); uint256 fee = calculateFee(amount, true, feeManager, HOME_FEE); - distributeFeeFromSignatures(fee, feeManager); - emit FeeDistributedFromSignatures(fee, txHash); + distributeFeeFromSignatures(fee, feeManager, txHash); } } diff --git a/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol index 1821b279c..8c67e76ec 100644 --- a/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol +++ b/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol @@ -114,13 +114,13 @@ contract ForeignBridgeNativeToErc is ERC677Receiver, BasicBridge, BasicForeignBr setOwner(_owner); } - function onExecuteMessage(address _recipient, uint256 _amount) internal returns(bool) { + function onExecuteMessage(address _recipient, uint256 _amount, bytes32 _txHash) internal returns(bool) { setTotalExecutedPerDay(getCurrentDay(), totalExecutedPerDay(getCurrentDay()).add(_amount)); uint256 valueToMint = _amount; address feeManager = feeManagerContract(); if (feeManager != address(0)) { uint256 fee = calculateFee(valueToMint, false, feeManager, HOME_FEE); - distributeFeeFromSignatures(fee, feeManager); + distributeFeeFromSignatures(fee, feeManager, _txHash); valueToMint = valueToMint.sub(fee); } return erc677token().mint(_recipient, valueToMint); diff --git a/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol index e235f2c2b..9c97e4ba8 100644 --- a/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol +++ b/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol @@ -10,8 +10,6 @@ import "../Sacrifice.sol"; contract HomeBridgeNativeToErc is EternalStorage, BasicBridge, BasicHomeBridge, RewardableHomeBridgeNativeToErc { - event FeeDistributedFromAffirmation(uint256 feeAmount, bytes32 indexed transactionHash); - function () public payable { require(msg.value > 0); require(msg.data.length == 0); @@ -121,9 +119,8 @@ contract HomeBridgeNativeToErc is EternalStorage, BasicBridge, BasicHomeBridge, address feeManager = feeManagerContract(); if (feeManager != address(0)) { uint256 fee = calculateFee(valueToTransfer, false, feeManager, FOREIGN_FEE); - distributeFeeFromAffirmation(fee, feeManager); + distributeFeeFromAffirmation(fee, feeManager, txHash); valueToTransfer = valueToTransfer.sub(fee); - emit FeeDistributedFromAffirmation(fee, txHash); } if (!_recipient.send(valueToTransfer)) { From 1ca930ac1db0ebe69e6c1e3652504243fdaa9522 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Thu, 18 Apr 2019 10:52:44 -0300 Subject: [PATCH 142/187] Update erc-to-erc rewards schemas --- REWARD_MANAGEMENT.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/REWARD_MANAGEMENT.md b/REWARD_MANAGEMENT.md index 9b2bb78d4..fe05a39a4 100644 --- a/REWARD_MANAGEMENT.md +++ b/REWARD_MANAGEMENT.md @@ -24,8 +24,8 @@ Fees are calculated and distributed on Home network. Validators will receive nat ### Foreign to Home transfer Fees are calculated and distributed on Home network. Validators will receive ERC20 tokens. -![ERC-ERC-ForeignToHome](https://user-images.githubusercontent.com/4614574/55352936-70752b80-5498-11e9-98ec-f2ca4d9fcb8b.png) +![ERC-ERC-ForeignToHome](https://user-images.githubusercontent.com/4614574/56365696-de735f80-61c7-11e9-9f85-9fa507aabda5.png) ### Home to Foreign transfer Fees are calculated and distributed on Home network. Validators will receive ERC20 tokens. -![ERC-ERC-HomeToForeign](https://user-images.githubusercontent.com/4614574/55352955-7d921a80-5498-11e9-92f5-8391952d1f78.png) +![ERC-ERC-HomeToForeign](https://user-images.githubusercontent.com/4614574/56365731-f0550280-61c7-11e9-8f33-ce4de1ef1ee6.png) From e605559f1727ef8dac6d75a27e2d05bba87043f3 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Thu, 18 Apr 2019 12:44:18 -0300 Subject: [PATCH 143/187] Add getAmountToBurn on erc-to-native fee manager --- .../erc20_to_native/FeeManagerErcToNative.sol | 4 ++-- .../erc20_to_native/FeeManagerErcToNativePOSDAO.sol | 4 ++-- .../erc20_to_native/HomeBridgeErcToNative.sol | 6 ++---- .../RewardableHomeBridgeErcToNative.sol | 10 +++++----- 4 files changed, 11 insertions(+), 13 deletions(-) diff --git a/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol index 00a974f4d..729a94ba4 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol @@ -26,7 +26,7 @@ contract FeeManagerErcToNative is BaseFeeManager { } } - function isPOSDAOFeeManager() public pure returns(bool) { - return false; + function getAmountToBurn(uint256 _value, uint256 _fee) public pure returns(uint256) { + return _value.sub(_fee); } } diff --git a/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNativePOSDAO.sol b/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNativePOSDAO.sol index 4658e1621..68f4adc0b 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNativePOSDAO.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNativePOSDAO.sol @@ -26,8 +26,8 @@ contract FeeManagerErcToNativePOSDAO is BaseFeeManager { blockReward.addBridgeNativeFeeReceivers(_fee); } - function isPOSDAOFeeManager() public pure returns(bool) { - return true; + function getAmountToBurn(uint256 _value, uint256 _fee) public pure returns(uint256) { + return _value; } function onAffirmationFeeDistribution(address _rewardAddress, uint256 _fee) internal {} diff --git a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol index 79af888b2..fd71c8484 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol @@ -25,13 +25,11 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, setTotalSpentPerDay(getCurrentDay(), totalSpentPerDay(getCurrentDay()).add(msg.value)); uint256 valueToTransfer = msg.value; address feeManager = feeManagerContract(); + uint256 valueToBurn = msg.value; if (feeManager != address(0)) { uint256 fee = calculateFee(valueToTransfer, false, feeManager, HOME_FEE); valueToTransfer = valueToTransfer.sub(fee); - } - uint256 valueToBurn = valueToTransfer; - if(isPOSDAOFeeManager()) { - valueToBurn = msg.value; + valueToBurn = getAmountToBurn(valueToBurn, fee); } setTotalBurntCoins(totalBurntCoins().add(valueToBurn)); address(0).transfer(valueToBurn); diff --git a/contracts/upgradeable_contracts/erc20_to_native/RewardableHomeBridgeErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/RewardableHomeBridgeErcToNative.sol index d164fbc82..e0fb9b84a 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/RewardableHomeBridgeErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/RewardableHomeBridgeErcToNative.sol @@ -21,17 +21,17 @@ contract RewardableHomeBridgeErcToNative is RewardableBridge { return _getFee(FOREIGN_FEE); } - function isPOSDAOFeeManager() public view returns(bool) { - bool mode; - bytes memory callData = abi.encodeWithSignature("isPOSDAOFeeManager()"); + function getAmountToBurn(uint256 _value, uint256 _fee) public view returns(uint256) { + uint256 amount; + bytes memory callData = abi.encodeWithSignature("getAmountToBurn(uint256,uint256)", _value, _fee); address feeManager = feeManagerContract(); assembly { let result := callcode(gas, feeManager, 0x0, add(callData, 0x20), mload(callData), 0, 32) - mode := mload(0) + amount := mload(0) switch result case 0 { revert(0, 0) } } - return mode; + return amount; } } From 4326644a2d69c64ebb2bb661721bc2bca9e100ee Mon Sep 17 00:00:00 2001 From: Alexander Kolotov Date: Fri, 19 Apr 2019 09:14:04 +0300 Subject: [PATCH 144/187] tests cover emmiting fee dsitribution event for submitSignature call in the native-to-erc mode --- test/native_to_erc/foreign_bridge_test.js | 35 +++++++++++++++-------- 1 file changed, 23 insertions(+), 12 deletions(-) diff --git a/test/native_to_erc/foreign_bridge_test.js b/test/native_to_erc/foreign_bridge_test.js index 0a1fb406f..12640adf1 100644 --- a/test/native_to_erc/foreign_bridge_test.js +++ b/test/native_to_erc/foreign_bridge_test.js @@ -637,10 +637,14 @@ contract('ForeignBridge', async (accounts) => { const vrs = signatureToVRS(signature); const { logs } = await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.fulfilled - logs[0].event.should.be.equal("RelayedMessage") - logs[0].args.recipient.should.be.equal(recipientAccount) - logs[0].args.value.should.be.bignumber.equal(value) - logs[0].args.transactionHash.should.be.equal(transactionHash); + + logs[0].event.should.be.equal("FeeDistributedFromSignatures") + logs[0].args.should.be.deep.equal({feeAmount, transactionHash}) + + logs[1].event.should.be.equal("RelayedMessage") + logs[1].args.recipient.should.be.equal(recipientAccount) + logs[1].args.value.should.be.bignumber.equal(value) + logs[1].args.transactionHash.should.be.equal(transactionHash); const balanceAfter = await token.balanceOf(recipientAccount); const totalSupplyAfter = await token.totalSupply(); @@ -657,6 +661,7 @@ contract('ForeignBridge', async (accounts) => { const feePerValidator = web3.toBigNumber(166666666666666) const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) const value = halfEther + const feeAmount = value.mul(web3.toBigNumber(fee)); const finalUserValue = value.mul(web3.toBigNumber(1-fee)); const validators = [accounts[1], accounts[2], accounts[3]] @@ -687,10 +692,13 @@ contract('ForeignBridge', async (accounts) => { const { logs } = await foreignBridge.executeSignatures([vrs.v, vrs2.v, vrs3.v], [vrs.r, vrs2.r, vrs3.r], [vrs.s, vrs2.s, vrs3.s], message).should.be.fulfilled // Then - logs[0].event.should.be.equal("RelayedMessage") - logs[0].args.recipient.should.be.equal(recipientAccount) - logs[0].args.value.should.be.bignumber.equal(value) - logs[0].args.transactionHash.should.be.equal(transactionHash); + logs[0].event.should.be.equal("FeeDistributedFromSignatures") + logs[0].args.should.be.deep.equal({feeAmount, transactionHash}) + + logs[1].event.should.be.equal("RelayedMessage") + logs[1].args.recipient.should.be.equal(recipientAccount) + logs[1].args.value.should.be.bignumber.equal(value) + logs[1].args.transactionHash.should.be.equal(transactionHash); const balanceAfter = await token.balanceOf(recipientAccount); const totalSupplyAfter = await token.totalSupply(); @@ -750,10 +758,13 @@ contract('ForeignBridge', async (accounts) => { const { logs } = await foreignBridge.executeSignatures([vrs.v, vrs2.v, vrs3.v], [vrs.r, vrs2.r, vrs3.r], [vrs.s, vrs2.s, vrs3.s], message).should.be.fulfilled // Then - logs[0].event.should.be.equal("RelayedMessage") - logs[0].args.recipient.should.be.equal(recipientAccount) - logs[0].args.value.should.be.bignumber.equal(value) - logs[0].args.transactionHash.should.be.equal(transactionHash); + logs[0].event.should.be.equal("FeeDistributedFromSignatures") + logs[0].args.should.be.deep.equal({feeAmount, transactionHash}) + + logs[1].event.should.be.equal("RelayedMessage") + logs[1].args.recipient.should.be.equal(recipientAccount) + logs[1].args.value.should.be.bignumber.equal(value) + logs[1].args.transactionHash.should.be.equal(transactionHash); const balanceAfter = await token.balanceOf(recipientAccount); const totalSupplyAfter = await token.totalSupply(); From b6df9b37fcc819b4773db44d010798b6ed69da0c Mon Sep 17 00:00:00 2001 From: Alexander Kolotov Date: Fri, 19 Apr 2019 09:15:03 +0300 Subject: [PATCH 145/187] syncronize node.js version in TravisCI with the requirements --- .travis.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.travis.yml b/.travis.yml index f26094479..77ff5d04b 100644 --- a/.travis.yml +++ b/.travis.yml @@ -3,7 +3,7 @@ sudo: required group: beta language: node_js node_js: - - "9" + - "10" cache: yarn: true env: From d5c7c5ad0aa4169b4a5145948ef7b57808dbb3ba Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 22 Apr 2019 10:26:17 -0300 Subject: [PATCH 146/187] Fix erc-to-erc reward schema text --- REWARD_MANAGEMENT.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/REWARD_MANAGEMENT.md b/REWARD_MANAGEMENT.md index fe05a39a4..0ed6b0d16 100644 --- a/REWARD_MANAGEMENT.md +++ b/REWARD_MANAGEMENT.md @@ -24,8 +24,8 @@ Fees are calculated and distributed on Home network. Validators will receive nat ### Foreign to Home transfer Fees are calculated and distributed on Home network. Validators will receive ERC20 tokens. -![ERC-ERC-ForeignToHome](https://user-images.githubusercontent.com/4614574/56365696-de735f80-61c7-11e9-9f85-9fa507aabda5.png) +![ERC-ERC-ForeignToHome (1)](https://user-images.githubusercontent.com/4614574/56502412-98c8d680-64e8-11e9-8eea-5bcd545d74d9.png) ### Home to Foreign transfer Fees are calculated and distributed on Home network. Validators will receive ERC20 tokens. -![ERC-ERC-HomeToForeign](https://user-images.githubusercontent.com/4614574/56365731-f0550280-61c7-11e9-8f33-ce4de1ef1ee6.png) +![ERC-ERC-HomeToForeign (1)](https://user-images.githubusercontent.com/4614574/56502454-b8f89580-64e8-11e9-84ae-d9a1c229e0c4.png) From 6b25ffb90c229567046c99b7f39caf3990bb8721 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 22 Apr 2019 11:09:54 -0300 Subject: [PATCH 147/187] Update fee events logic on HomeBridgeErcToErc --- .../erc20_to_erc20/HomeBridgeErcToErc.sol | 8 ++------ 1 file changed, 2 insertions(+), 6 deletions(-) diff --git a/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol b/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol index 545617251..dca16d50a 100644 --- a/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol +++ b/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol @@ -15,8 +15,6 @@ import "../../IBlockReward.sol"; contract HomeBridgeErcToErc is ERC677Receiver, EternalStorage, BasicBridge, BasicHomeBridge, ERC677Bridge, OverdrawManagement, RewardableHomeBridgeErcToErc { event AmountLimitExceeded(address recipient, uint256 value, bytes32 transactionHash); - event FeeDistributedFromAffirmation(uint256 feeAmount, bytes32 indexed transactionHash); - event FeeDistributedFromSignatures(uint256 feeAmount, bytes32 indexed transactionHash); function initialize ( address _validatorContract, @@ -169,8 +167,7 @@ contract HomeBridgeErcToErc is ERC677Receiver, EternalStorage, BasicBridge, Basi address feeManager = feeManagerContract(); if (feeManager != address(0)) { uint256 fee = calculateFee(valueToMint, false, feeManager, FOREIGN_FEE); - distributeFeeFromAffirmation(fee, feeManager); - emit FeeDistributedFromAffirmation(fee, txHash); + distributeFeeFromAffirmation(fee, feeManager, txHash); valueToMint = valueToMint.sub(fee); } return erc677token().mint(_recipient, valueToMint); @@ -195,8 +192,7 @@ contract HomeBridgeErcToErc is ERC677Receiver, EternalStorage, BasicBridge, Basi address contractAddress; (recipient, amount, txHash, contractAddress) = Message.parseMessage(_message); uint256 fee = calculateFee(amount, true, feeManager, HOME_FEE); - distributeFeeFromSignatures(fee, feeManager); - emit FeeDistributedFromSignatures(fee, txHash); + distributeFeeFromSignatures(fee, feeManager, txHash); } } From f7cb8d253e4418082a6f1230b36c6f0f4270e463 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 22 Apr 2019 11:55:11 -0300 Subject: [PATCH 148/187] Update getAmountToBurn method signature --- contracts/upgradeable_contracts/BaseFeeManager.sol | 2 +- .../erc20_to_native/FeeManagerErcToNative.sol | 5 +++-- .../erc20_to_native/FeeManagerErcToNativePOSDAO.sol | 2 +- .../erc20_to_native/HomeBridgeErcToNative.sol | 2 +- .../erc20_to_native/RewardableHomeBridgeErcToNative.sol | 4 ++-- 5 files changed, 8 insertions(+), 7 deletions(-) diff --git a/contracts/upgradeable_contracts/BaseFeeManager.sol b/contracts/upgradeable_contracts/BaseFeeManager.sol index 52eb98865..9c8aec4c6 100644 --- a/contracts/upgradeable_contracts/BaseFeeManager.sol +++ b/contracts/upgradeable_contracts/BaseFeeManager.sol @@ -16,7 +16,7 @@ contract BaseFeeManager is EternalStorage, FeeTypes { event HomeFeeUpdated(uint256 fee); event ForeignFeeUpdated(uint256 fee); - function calculateFee(uint256 _value, bool _recover, bytes32 _feeType) external view returns(uint256) { + function calculateFee(uint256 _value, bool _recover, bytes32 _feeType) public view returns(uint256) { uint256 fee = _feeType == HOME_FEE ? getHomeFee() : getForeignFee(); uint256 eth = 1 ether; if (!_recover) { diff --git a/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol index 729a94ba4..7fa49c49c 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNative.sol @@ -26,7 +26,8 @@ contract FeeManagerErcToNative is BaseFeeManager { } } - function getAmountToBurn(uint256 _value, uint256 _fee) public pure returns(uint256) { - return _value.sub(_fee); + function getAmountToBurn(uint256 _value) public view returns(uint256) { + uint256 fee = calculateFee(_value, false, HOME_FEE); + return _value.sub(fee); } } diff --git a/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNativePOSDAO.sol b/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNativePOSDAO.sol index 68f4adc0b..4e799172b 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNativePOSDAO.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNativePOSDAO.sol @@ -26,7 +26,7 @@ contract FeeManagerErcToNativePOSDAO is BaseFeeManager { blockReward.addBridgeNativeFeeReceivers(_fee); } - function getAmountToBurn(uint256 _value, uint256 _fee) public pure returns(uint256) { + function getAmountToBurn(uint256 _value) public view returns(uint256) { return _value; } diff --git a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol index fd71c8484..23598764d 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol @@ -29,7 +29,7 @@ contract HomeBridgeErcToNative is EternalStorage, BasicBridge, BasicHomeBridge, if (feeManager != address(0)) { uint256 fee = calculateFee(valueToTransfer, false, feeManager, HOME_FEE); valueToTransfer = valueToTransfer.sub(fee); - valueToBurn = getAmountToBurn(valueToBurn, fee); + valueToBurn = getAmountToBurn(valueToBurn); } setTotalBurntCoins(totalBurntCoins().add(valueToBurn)); address(0).transfer(valueToBurn); diff --git a/contracts/upgradeable_contracts/erc20_to_native/RewardableHomeBridgeErcToNative.sol b/contracts/upgradeable_contracts/erc20_to_native/RewardableHomeBridgeErcToNative.sol index e0fb9b84a..fb47621de 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/RewardableHomeBridgeErcToNative.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/RewardableHomeBridgeErcToNative.sol @@ -21,9 +21,9 @@ contract RewardableHomeBridgeErcToNative is RewardableBridge { return _getFee(FOREIGN_FEE); } - function getAmountToBurn(uint256 _value, uint256 _fee) public view returns(uint256) { + function getAmountToBurn(uint256 _value) public view returns(uint256) { uint256 amount; - bytes memory callData = abi.encodeWithSignature("getAmountToBurn(uint256,uint256)", _value, _fee); + bytes memory callData = abi.encodeWithSignature("getAmountToBurn(uint256)", _value); address feeManager = feeManagerContract(); assembly { let result := callcode(gas, feeManager, 0x0, add(callData, 0x20), mload(callData), 0, 32) From 04069bbb7e20ac13c7a1159ccd8ad22b684626fd Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 22 Apr 2019 13:49:17 -0300 Subject: [PATCH 149/187] Update FeeManagerErcToNativePOSDAO to extend BlockRewardFeeManager --- .../BlockRewardFeeManager.sol | 7 ++---- .../FeeManagerErcToErcPOSDAO.sol | 5 +++++ .../FeeManagerErcToNativePOSDAO.sol | 22 +++---------------- 3 files changed, 10 insertions(+), 24 deletions(-) diff --git a/contracts/upgradeable_contracts/BlockRewardFeeManager.sol b/contracts/upgradeable_contracts/BlockRewardFeeManager.sol index cfdeedc6f..a6414aabb 100644 --- a/contracts/upgradeable_contracts/BlockRewardFeeManager.sol +++ b/contracts/upgradeable_contracts/BlockRewardFeeManager.sol @@ -13,12 +13,9 @@ contract BlockRewardFeeManager is BaseFeeManager { distributeFeeFromBlockReward(_fee); } - function distributeFeeFromBlockReward(uint256 _fee) internal { - IBlockReward blockReward = _blockRewardContract(); - blockReward.addBridgeTokenFeeReceivers(_fee); - } - function _blockRewardContract() internal view returns(IBlockReward) { return IBlockReward(addressStorage[keccak256(abi.encodePacked("blockRewardContract"))]); } + + function distributeFeeFromBlockReward(uint256 _fee) internal; } diff --git a/contracts/upgradeable_contracts/erc20_to_erc20/FeeManagerErcToErcPOSDAO.sol b/contracts/upgradeable_contracts/erc20_to_erc20/FeeManagerErcToErcPOSDAO.sol index da27b4379..2867cbc93 100644 --- a/contracts/upgradeable_contracts/erc20_to_erc20/FeeManagerErcToErcPOSDAO.sol +++ b/contracts/upgradeable_contracts/erc20_to_erc20/FeeManagerErcToErcPOSDAO.sol @@ -17,6 +17,11 @@ contract FeeManagerErcToErcPOSDAO is BlockRewardFeeManager { addressStorage[keccak256(abi.encodePacked("blockRewardContract"))] = _blockReward; } + function distributeFeeFromBlockReward(uint256 _fee) internal { + IBlockReward blockReward = _blockRewardContract(); + blockReward.addBridgeTokenFeeReceivers(_fee); + } + function isContract(address _addr) internal view returns (bool) { uint length; diff --git a/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNativePOSDAO.sol b/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNativePOSDAO.sol index 4e799172b..cb8ea80e7 100644 --- a/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNativePOSDAO.sol +++ b/contracts/upgradeable_contracts/erc20_to_native/FeeManagerErcToNativePOSDAO.sol @@ -1,36 +1,20 @@ pragma solidity 0.4.24; -import "../BaseFeeManager.sol"; import "../../IBlockReward.sol"; +import "../BlockRewardFeeManager.sol"; -contract FeeManagerErcToNativePOSDAO is BaseFeeManager { +contract FeeManagerErcToNativePOSDAO is BlockRewardFeeManager { function getFeeManagerMode() public pure returns(bytes4) { return bytes4(keccak256(abi.encodePacked("manages-both-directions"))); } - function blockRewardContract() internal view returns(IBlockReward) { - return IBlockReward(addressStorage[keccak256(abi.encodePacked("blockRewardContract"))]); - } - - function distributeFeeFromAffirmation(uint256 _fee) external { - distributeFeeFromBlockReward(_fee); - } - - function distributeFeeFromSignatures(uint256 _fee) external { - distributeFeeFromBlockReward(_fee); - } - function distributeFeeFromBlockReward(uint256 _fee) internal { - IBlockReward blockReward = blockRewardContract(); + IBlockReward blockReward = _blockRewardContract(); blockReward.addBridgeNativeFeeReceivers(_fee); } function getAmountToBurn(uint256 _value) public view returns(uint256) { return _value; } - - function onAffirmationFeeDistribution(address _rewardAddress, uint256 _fee) internal {} - - function onSignatureFeeDistribution(address _rewardAddress, uint256 _fee) internal {} } From 39c7d392e98c32e4c61a0151bb7dfb8fa64cd8d0 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 22 Apr 2019 13:50:52 -0300 Subject: [PATCH 150/187] Fix FeeManagerErcToNativePOSDAO unit tests --- test/erc_to_native/home_bridge.test.js | 44 ++++++++++++++++++++++---- 1 file changed, 38 insertions(+), 6 deletions(-) diff --git a/test/erc_to_native/home_bridge.test.js b/test/erc_to_native/home_bridge.test.js index a7b357aae..3ad37a026 100644 --- a/test/erc_to_native/home_bridge.test.js +++ b/test/erc_to_native/home_bridge.test.js @@ -1485,8 +1485,13 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { signer: validators[0], transactionHash }); - logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); logs[1].args.should.be.deep.equal({ + feeAmount: value.mul(web3.toBigNumber(fee)), + transactionHash + }) + logs[2].event.should.be.equal("AffirmationCompleted"); + logs[2].args.should.be.deep.equal({ recipient, value, transactionHash @@ -1557,8 +1562,13 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { signer: validators[1], transactionHash }); - logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); logs[1].args.should.be.deep.equal({ + feeAmount: value.mul(web3.toBigNumber(fee)), + transactionHash + }) + logs[2].event.should.be.equal("AffirmationCompleted"); + logs[2].args.should.be.deep.equal({ recipient, value, transactionHash @@ -1643,8 +1653,13 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { signer: validators[4], transactionHash }); - logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); logs[1].args.should.be.deep.equal({ + feeAmount: value.mul(web3.toBigNumber(fee)), + transactionHash + }) + logs[2].event.should.be.equal("AffirmationCompleted"); + logs[2].args.should.be.deep.equal({ recipient, value, transactionHash @@ -1758,8 +1773,13 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const { logs } = await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled; // Then - logs.length.should.be.equal(2) + logs.length.should.be.equal(3) logs[1].event.should.be.equal('CollectedSignatures') + logs[2].event.should.be.equal("FeeDistributedFromSignatures"); + logs[2].args.should.be.deep.equal({ + feeAmount, + transactionHash + }) const finalBridgeBalance = await web3.eth.getBalance(homeBridge.address) finalBridgeBalance.should.be.bignumber.equal('0') @@ -1826,8 +1846,14 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const { logs } = await homeBridge.submitSignature(signature3, message, {from: validators[2]}).should.be.fulfilled; // Then - logs.length.should.be.equal(2) + logs.length.should.be.equal(3) logs[1].event.should.be.equal('CollectedSignatures') + logs[2].event.should.be.equal("FeeDistributedFromSignatures"); + logs[2].args.should.be.deep.equal({ + feeAmount, + transactionHash + }) + const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) @@ -1910,8 +1936,14 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const { logs } = await homeBridge.submitSignature(signature5, message, {from: validators[4]}).should.be.fulfilled; // Then - logs.length.should.be.equal(2) + logs.length.should.be.equal(3) logs[1].event.should.be.equal('CollectedSignatures') + logs[2].event.should.be.equal("FeeDistributedFromSignatures"); + logs[2].args.should.be.deep.equal({ + feeAmount, + transactionHash + }) + const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) From a448e3d5b6f996adb0ddc5b53792f5d7ae44fb56 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 22 Apr 2019 14:41:01 -0300 Subject: [PATCH 151/187] Add HOME_FEE_MANAGER_TYPE env var --- deploy/.env.example | 3 ++- deploy/README.md | 5 +++-- deploy/src/erc_to_native/home.js | 8 +++++--- deploy/src/loadEnv.js | 11 +++++++---- 4 files changed, 17 insertions(+), 10 deletions(-) diff --git a/deploy/.env.example b/deploy/.env.example index ed7acd24d..ab33dda2d 100644 --- a/deploy/.env.example +++ b/deploy/.env.example @@ -41,6 +41,8 @@ VALIDATORS=0x #for erc_to_native mode #Set to true if fee will be charged on home side HOME_REWARDABLE=false +# For erc_to_native mode BRIDGE_VALIDATORS_REWARD or POSDAO_REWARD +HOME_FEE_MANAGER_TYPE=BRIDGE_VALIDATORS_REWARD #Set to true if fee will be charged on foreign side FOREIGN_REWARDABLE=false #If HOME_REWARDABLE or FOREIGN_REWARDABLE set to true, list validators accounts were rewards should be transferred separated by space without quotes @@ -55,4 +57,3 @@ FOREIGN_TRANSACTIONS_FEE=0.001 #for bridge native_to_erc, erc_to_erc mode DEPLOY_REWARDABLE_TOKEN=false DPOS_STAKING_ADDRESS= -HOME_POSDAO=false diff --git a/deploy/README.md b/deploy/README.md index 2f862dc82..aa1ef5318 100644 --- a/deploy/README.md +++ b/deploy/README.md @@ -361,8 +361,9 @@ VALIDATORS=0x 0x 0x HOME_REWARDABLE=false # The flag defining whether to use RewardableValidators contract and set a fee manager contract on Foreign network FOREIGN_REWARDABLE=false -# Flag to define if Home network is a POSDAO and rewards are distributed by blockReward contract -HOME_POSDAO=false +# Variable to define if Home network is a POSDAO and rewards are distributed by blockReward contract to network validators or transferred directly to bridge validators. +# Supported values are BRIDGE_VALIDATORS_REWARD and POSDAO_REWARD +HOME_FEE_MANAGER_TYPE=BRIDGE_VALIDATORS_REWARD # List validators accounts were rewards should be transferred separated by space without quotes # Makes sense only when HOME_REWARDABLE=true or FOREIGN_REWARDABLE=true VALIDATORS_REWARD_ACCOUNTS=0x 0x 0x diff --git a/deploy/src/erc_to_native/home.js b/deploy/src/erc_to_native/home.js index dccbcf38d..bc29ce7db 100644 --- a/deploy/src/erc_to_native/home.js +++ b/deploy/src/erc_to_native/home.js @@ -37,13 +37,13 @@ const { HOME_REWARDABLE, HOME_TRANSACTIONS_FEE, FOREIGN_TRANSACTIONS_FEE, - HOME_POSDAO + HOME_FEE_MANAGER_TYPE } = env const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVATE_KEY) const isRewardableBridge = HOME_REWARDABLE === 'true' -const isHomePOSDAO = HOME_POSDAO === 'true' +const isFeeManagerPOSDAO = HOME_FEE_MANAGER_TYPE === 'POSDAO_REWARD' async function deployHome() { let homeNonce = await web3Home.eth.getTransactionCount(DEPLOYMENT_ACCOUNT_ADDRESS) @@ -164,7 +164,9 @@ async function deployHome() { if (isRewardableBridge) { console.log('\ndeploying implementation for fee manager') - const feeManagerContract = isHomePOSDAO ? FeeManagerErcToNativePOSDAO : FeeManagerErcToNative + const feeManagerContract = isFeeManagerPOSDAO + ? FeeManagerErcToNativePOSDAO + : FeeManagerErcToNative const feeManager = await deployContract(feeManagerContract, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, nonce: homeNonce diff --git a/deploy/src/loadEnv.js b/deploy/src/loadEnv.js index bf1ceed78..7babe1f8d 100644 --- a/deploy/src/loadEnv.js +++ b/deploy/src/loadEnv.js @@ -8,6 +8,7 @@ const { ZERO_ADDRESS } = require('./constants') // Validations and constants const validBridgeModes = ['NATIVE_TO_ERC', 'ERC_TO_ERC', 'ERC_TO_NATIVE'] +const validFeeManagerTypes = ['BRIDGE_VALIDATORS_REWARD', 'POSDAO_REWARD'] const bigNumValidator = envalid.makeValidator(x => toBN(x)) const validateAddress = address => { if (isAddress(address)) { @@ -37,7 +38,8 @@ const { FOREIGN_REWARDABLE, VALIDATORS, VALIDATORS_REWARD_ACCOUNTS, - DEPLOY_REWARDABLE_TOKEN + DEPLOY_REWARDABLE_TOKEN, + HOME_FEE_MANAGER_TYPE } = process.env if (!validBridgeModes.includes(BRIDGE_MODE)) { @@ -123,9 +125,10 @@ if (BRIDGE_MODE === 'ERC_TO_NATIVE') { } if (HOME_REWARDABLE === 'true') { - validations = { - ...validations, - HOME_POSDAO: envalid.bool() + if (!validFeeManagerTypes.includes(HOME_FEE_MANAGER_TYPE)) { + throw new Error( + `Invalid fee manager type: HOME_FEE_MANAGER_TYPE = ${HOME_FEE_MANAGER_TYPE}. Supported values are ${validFeeManagerTypes}` + ) } } } From e3d7fb9896225779c795c0687901e3b6c3879980 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 22 Apr 2019 15:43:21 -0300 Subject: [PATCH 152/187] Merge fix --- .../native_to_erc20/HomeBridgeNativeToErc.sol | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol index ec93a7add..d77fb3b62 100644 --- a/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol +++ b/contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol @@ -130,7 +130,7 @@ contract HomeBridgeNativeToErc is EternalStorage, BasicBridge, BasicHomeBridge, (recipient, amount, txHash, contractAddress) = Message.parseMessage(_message); uint256 fee = calculateFee(amount, true, feeManager, HOME_FEE); if (fee != 0) { - distributeFeeFromSignatures(fee, feeManager); + distributeFeeFromSignatures(fee, feeManager, txHash); } } } From 3f3457c278548d3612594df3281196b765c0e714 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 22 Apr 2019 16:25:36 -0300 Subject: [PATCH 153/187] Update FeeManagerNativeToErcBothDirections to extend ValidatorsFeeManager --- .../FeeManagerNativeToErcBothDirections.sol | 5 +-- test/native_to_erc/home_bridge_test.js | 42 ++++++++++++++++--- 2 files changed, 38 insertions(+), 9 deletions(-) diff --git a/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErcBothDirections.sol b/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErcBothDirections.sol index e511ecee0..049ff62c4 100644 --- a/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErcBothDirections.sol +++ b/contracts/upgradeable_contracts/native_to_erc20/FeeManagerNativeToErcBothDirections.sol @@ -1,11 +1,10 @@ pragma solidity 0.4.24; -import "../BaseFeeManager.sol"; -import "../../IBurnableMintableERC677Token.sol"; import "../Sacrifice.sol"; +import "../ValidatorsFeeManager.sol"; -contract FeeManagerNativeToErcBothDirections is BaseFeeManager { +contract FeeManagerNativeToErcBothDirections is ValidatorsFeeManager { function getFeeManagerMode() public pure returns(bytes4) { return bytes4(keccak256(abi.encodePacked("manages-both-directions"))); diff --git a/test/native_to_erc/home_bridge_test.js b/test/native_to_erc/home_bridge_test.js index 14c45e833..d3a3fb545 100644 --- a/test/native_to_erc/home_bridge_test.js +++ b/test/native_to_erc/home_bridge_test.js @@ -920,8 +920,13 @@ contract('HomeBridge', async (accounts) => { signer: validators[4], transactionHash }); - logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); logs[1].args.should.be.deep.equal({ + feeAmount, + transactionHash + }) + logs[2].event.should.be.equal("AffirmationCompleted"); + logs[2].args.should.be.deep.equal({ recipient, value, transactionHash @@ -1017,8 +1022,13 @@ contract('HomeBridge', async (accounts) => { const { logs } = await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled // Then - logs.length.should.be.equal(2) + logs.length.should.be.equal(3) logs[1].event.should.be.equal('CollectedSignatures') + logs[2].event.should.be.equal("FeeDistributedFromSignatures"); + logs[2].args.should.be.deep.equal({ + feeAmount, + transactionHash + }) const bridgeBalance = await web3.eth.getBalance(homeBridge.address) bridgeBalance.should.be.bignumber.equal(value) @@ -1070,8 +1080,13 @@ contract('HomeBridge', async (accounts) => { const { logs } = await homeBridge.submitSignature(signature3, message, {from: validators[2]}).should.be.fulfilled; // Then - logs.length.should.be.equal(2) + logs.length.should.be.equal(3) logs[1].event.should.be.equal('CollectedSignatures') + logs[2].event.should.be.equal("FeeDistributedFromSignatures"); + logs[2].args.should.be.deep.equal({ + feeAmount: initialValue.mul(web3.toBigNumber(fee)), + transactionHash + }) const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) @@ -1137,8 +1152,13 @@ contract('HomeBridge', async (accounts) => { const { logs } = await homeBridge.submitSignature(signature5, message, {from: validators[4]}).should.be.fulfilled; // Then - logs.length.should.be.equal(2) + logs.length.should.be.equal(3) logs[1].event.should.be.equal('CollectedSignatures') + logs[2].event.should.be.equal("FeeDistributedFromSignatures"); + logs[2].args.should.be.deep.equal({ + feeAmount, + transactionHash + }) const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) @@ -1195,8 +1215,13 @@ contract('HomeBridge', async (accounts) => { signer: validators[0], transactionHash }); - logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); logs[1].args.should.be.deep.equal({ + feeAmount, + transactionHash + }) + logs[2].event.should.be.equal("AffirmationCompleted"); + logs[2].args.should.be.deep.equal({ recipient, value, transactionHash @@ -1253,8 +1278,13 @@ contract('HomeBridge', async (accounts) => { signer: validators[1], transactionHash }); - logs[1].event.should.be.equal("AffirmationCompleted"); + logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); logs[1].args.should.be.deep.equal({ + feeAmount: value.mul(web3.toBigNumber(fee)), + transactionHash + }) + logs[2].event.should.be.equal("AffirmationCompleted"); + logs[2].args.should.be.deep.equal({ recipient, value, transactionHash From cad1cc5c2b436c6364d77239430e0ec0224cedc5 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 23 Apr 2019 14:16:53 -0300 Subject: [PATCH 154/187] Update .env.example --- deploy/.env.example | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/deploy/.env.example b/deploy/.env.example index ab33dda2d..5ba0843fe 100644 --- a/deploy/.env.example +++ b/deploy/.env.example @@ -41,8 +41,8 @@ VALIDATORS=0x #for erc_to_native mode #Set to true if fee will be charged on home side HOME_REWARDABLE=false -# For erc_to_native mode BRIDGE_VALIDATORS_REWARD or POSDAO_REWARD -HOME_FEE_MANAGER_TYPE=BRIDGE_VALIDATORS_REWARD +# Valid only for rewards on erc_to_native mode. Supported values are BRIDGE_VALIDATORS_REWARD and POSDAO_REWARD +HOME_FEE_MANAGER_TYPE= #Set to true if fee will be charged on foreign side FOREIGN_REWARDABLE=false #If HOME_REWARDABLE or FOREIGN_REWARDABLE set to true, list validators accounts were rewards should be transferred separated by space without quotes From bb33eec86155d4f8aee5025f54ba55ca221a40a6 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 23 Apr 2019 15:25:01 -0300 Subject: [PATCH 155/187] Merge fix --- deploy/src/erc_to_erc/home.js | 18 +++++++++--------- deploy/src/native_to_erc/foreign.js | 10 +++------- 2 files changed, 12 insertions(+), 16 deletions(-) diff --git a/deploy/src/erc_to_erc/home.js b/deploy/src/erc_to_erc/home.js index 72b08ef92..805f117dd 100644 --- a/deploy/src/erc_to_erc/home.js +++ b/deploy/src/erc_to_erc/home.js @@ -64,15 +64,15 @@ async function initializeBridge({ validatorsBridge, bridge, erc677token, initial console.log('\ndeploying implementation for fee manager') const feeManager = await deployContract(FeeManagerErcToErcPOSDAO, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, - nonce: homeNonce + nonce }) console.log('[Home] feeManager Implementation: ', feeManager.options.address) - homeNonce++ + nonce++ const homeFeeInWei = Web3Utils.toWei(HOME_TRANSACTIONS_FEE.toString(), 'ether') const foreignFeeInWei = Web3Utils.toWei(FOREIGN_TRANSACTIONS_FEE.toString(), 'ether') console.log('\ninitializing Home Bridge with fee contract:\n') - console.log(`Home Validators: ${storageValidatorsHome.options.address}, + console.log(`Home Validators: ${validatorsBridge.options.address}, HOME_DAILY_LIMIT : ${HOME_DAILY_LIMIT} which is ${Web3Utils.fromWei(HOME_DAILY_LIMIT)} in eth, HOME_MAX_AMOUNT_PER_TX: ${HOME_MAX_AMOUNT_PER_TX} which is ${Web3Utils.fromWei( HOME_MAX_AMOUNT_PER_TX @@ -85,9 +85,9 @@ async function initializeBridge({ validatorsBridge, bridge, erc677token, initial Fee Manager: ${feeManager.options.address}, Home Fee: ${homeFeeInWei} which is ${HOME_TRANSACTIONS_FEE * 100}% Foreign Fee: ${foreignFeeInWei} which is ${FOREIGN_TRANSACTIONS_FEE * 100}%`) - initializeHomeBridgeData = await homeBridgeImplementation.methods + initializeHomeBridgeData = await bridge.methods .rewardableInitialize( - storageValidatorsHome.options.address, + validatorsBridge.options.address, HOME_DAILY_LIMIT, HOME_MAX_AMOUNT_PER_TX, HOME_MIN_AMOUNT_PER_TX, @@ -262,7 +262,7 @@ async function deployHome() { .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) const setBlockRewardContract = await sendRawTxHome({ data: setBlockRewardContractData, - nonce: homeNonce, + nonce, to: erc677token.options.address, privateKey: deploymentPrivateKey, url: HOME_RPC_URL @@ -272,7 +272,7 @@ async function deployHome() { 1, 'Transaction Failed' ) - homeNonce++ + nonce++ } if (DEPLOY_REWARDABLE_TOKEN) { @@ -282,13 +282,13 @@ async function deployHome() { .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) const setStakingContract = await sendRawTxHome({ data: setStakingContractData, - nonce: homeNonce, + nonce, to: erc677token.options.address, privateKey: deploymentPrivateKey, url: HOME_RPC_URL }) assert.strictEqual(Web3Utils.hexToNumber(setStakingContract.status), 1, 'Transaction Failed') - homeNonce++ + nonce++ } console.log('transferring ownership of Bridgeble token to homeBridge contract') diff --git a/deploy/src/native_to_erc/foreign.js b/deploy/src/native_to_erc/foreign.js index 7701a8ca8..394573afc 100644 --- a/deploy/src/native_to_erc/foreign.js +++ b/deploy/src/native_to_erc/foreign.js @@ -313,16 +313,12 @@ async function deployForeign() { privateKey: deploymentPrivateKey, url: FOREIGN_RPC_URL }) - if (setValidatorSetContract.status) { - assert.strictEqual( - Web3Utils.hexToNumber(setStakingContract.status), - 1, - 'Transaction Failed' - ) + if (setStakingContract.status) { + assert.strictEqual(Web3Utils.hexToNumber(setStakingContract.status), 1, 'Transaction Failed') } else { await assertStateWithRetry( erc677bridgeToken.methods.validatorSetContract().call, - DPOS_VALIDATOR_SET_ADDRESS + DPOS_STAKING_ADDRESS ) } nonce++ From c28b5d5f287916c855774a2d72d3411537763f54 Mon Sep 17 00:00:00 2001 From: Alexander Kolotov Date: Thu, 25 Apr 2019 01:47:45 +0300 Subject: [PATCH 156/187] handle JSON RPC errors returned by the web3 provider --- deploy/src/deploymentUtils.js | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/deploy/src/deploymentUtils.js b/deploy/src/deploymentUtils.js index 3d06a86fd..3cfebd1fa 100644 --- a/deploy/src/deploymentUtils.js +++ b/deploy/src/deploymentUtils.js @@ -109,10 +109,14 @@ async function sendNodeRequest(url, method, signedData) { }) }) const json = await request.json() + if (typeof json.error === 'undefined' || json.error === null) { if (method === 'eth_sendRawTransaction') { assert.strictEqual(json.result.length, 66, `Tx wasn't sent ${json}`) } return json.result + } else { + throw new Error(`web3 RPC failed: ${JSON.stringify(json.error)}`) + } } function timeout(ms) { From 106de6408a69d7d539f3a3c5ecdee955d5e0968a Mon Sep 17 00:00:00 2001 From: Alexander Kolotov Date: Thu, 25 Apr 2019 01:53:13 +0300 Subject: [PATCH 157/187] calculate gas limit for deployment transactions instead of dealing with a constant GAS_LIMIT --- deploy/src/deploymentUtils.js | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/deploy/src/deploymentUtils.js b/deploy/src/deploymentUtils.js index 3cfebd1fa..afa649612 100644 --- a/deploy/src/deploymentUtils.js +++ b/deploy/src/deploymentUtils.js @@ -70,10 +70,18 @@ async function sendRawTxForeign(options) { async function sendRawTx({ data, nonce, to, privateKey, url, gasPrice, value }) { try { + const txToEstimateGas = { + from: privateKeyToAddress(Web3Utils.bytesToHex(privateKey)), + value: value, + to, + data + } + const estimatedGas = await sendNodeRequest(url, 'eth_estimateGas', txToEstimateGas) + const rawTx = { nonce, gasPrice: Web3Utils.toHex(gasPrice), - gasLimit: Web3Utils.toHex(GAS_LIMIT), + gasLimit: estimatedGas, to, data, value From df9cd288bf6d3307065dcd9921929dd944b18280 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 29 Apr 2019 15:48:28 -0300 Subject: [PATCH 158/187] Add ForeignBridgeExtendedErcToErc --- .../ERC20ExtendedBridge.sol | 19 +++++++ .../erc20_to_erc20/ForeignBridgeErcToErc.sol | 27 +++++++-- .../ForeignBridgeExtendedErcToErc.sol | 57 +++++++++++++++++++ 3 files changed, 99 insertions(+), 4 deletions(-) create mode 100644 contracts/upgradeable_contracts/ERC20ExtendedBridge.sol create mode 100644 contracts/upgradeable_contracts/erc20_to_erc20/ForeignBridgeExtendedErcToErc.sol diff --git a/contracts/upgradeable_contracts/ERC20ExtendedBridge.sol b/contracts/upgradeable_contracts/ERC20ExtendedBridge.sol new file mode 100644 index 000000000..94a07de37 --- /dev/null +++ b/contracts/upgradeable_contracts/ERC20ExtendedBridge.sol @@ -0,0 +1,19 @@ +pragma solidity 0.4.24; + + +import "./BasicBridge.sol"; +import "openzeppelin-solidity/contracts/token/ERC20/ERC20Basic.sol"; + +contract ERC20ExtendedBridge is BasicBridge { + function onTokenTransfer(address _from, uint256 _value, bytes /*_data*/) external returns(bool) { + require(msg.sender == address(erc20token())); + require(withinLimit(_value)); + setTotalSpentPerDay(getCurrentDay(), totalSpentPerDay(getCurrentDay()).add(_value)); + fireEventOnTokenTransfer(_from, _value); + return true; + } + + function erc20token() public view returns(ERC20Basic); + + function fireEventOnTokenTransfer(address /*_from */, uint256 /* _value */) internal; +} diff --git a/contracts/upgradeable_contracts/erc20_to_erc20/ForeignBridgeErcToErc.sol b/contracts/upgradeable_contracts/erc20_to_erc20/ForeignBridgeErcToErc.sol index 73a2a34ab..4a6342edc 100644 --- a/contracts/upgradeable_contracts/erc20_to_erc20/ForeignBridgeErcToErc.sol +++ b/contracts/upgradeable_contracts/erc20_to_erc20/ForeignBridgeErcToErc.sol @@ -9,9 +9,6 @@ import "openzeppelin-solidity/contracts/token/ERC20/ERC20Basic.sol"; contract ForeignBridgeErcToErc is BasicBridge, BasicForeignBridge { - - event RelayedMessage(address recipient, uint value, bytes32 transactionHash); - function initialize( address _validatorContract, address _erc20token, @@ -22,6 +19,29 @@ contract ForeignBridgeErcToErc is BasicBridge, BasicForeignBridge { uint256 _homeMaxPerTx, address _owner ) public returns(bool) { + _initialize( + _validatorContract, + _erc20token, + _requiredBlockConfirmations, + _gasPrice, + _maxPerTx, + _homeDailyLimit, + _homeMaxPerTx, + _owner + ); + return isInitialized(); + } + + function _initialize( + address _validatorContract, + address _erc20token, + uint256 _requiredBlockConfirmations, + uint256 _gasPrice, + uint256 _maxPerTx, + uint256 _homeDailyLimit, + uint256 _homeMaxPerTx, + address _owner + ) internal { require(!isInitialized()); require(_validatorContract != address(0) && isContract(_validatorContract)); require(_requiredBlockConfirmations != 0); @@ -38,7 +58,6 @@ contract ForeignBridgeErcToErc is BasicBridge, BasicForeignBridge { uintStorage[keccak256(abi.encodePacked("executionMaxPerTx"))] = _homeMaxPerTx; setOwner(_owner); setInitialize(true); - return isInitialized(); } function getBridgeMode() public pure returns(bytes4 _data) { diff --git a/contracts/upgradeable_contracts/erc20_to_erc20/ForeignBridgeExtendedErcToErc.sol b/contracts/upgradeable_contracts/erc20_to_erc20/ForeignBridgeExtendedErcToErc.sol new file mode 100644 index 000000000..788f16b5d --- /dev/null +++ b/contracts/upgradeable_contracts/erc20_to_erc20/ForeignBridgeExtendedErcToErc.sol @@ -0,0 +1,57 @@ +pragma solidity 0.4.24; + + +import "./ForeignBridgeErcToErc.sol"; +import "../ERC20ExtendedBridge.sol"; + + +contract ForeignBridgeExtendedErcToErc is ERC20ExtendedBridge, ForeignBridgeErcToErc { + + event UserRequestForAffirmation(address recipient, uint256 value); + + function extendedInitialize( + address _validatorContract, + address _erc20token, + uint256 _requiredBlockConfirmations, + uint256 _gasPrice, + uint256 _dailyLimit, + uint256 _maxPerTx, + uint256 _minPerTx, + uint256 _homeDailyLimit, + uint256 _homeMaxPerTx, + address _owner + ) public returns(bool) { + require(_minPerTx > 0 && _maxPerTx > _minPerTx && _dailyLimit > _maxPerTx); + uintStorage[keccak256(abi.encodePacked("dailyLimit"))] = _dailyLimit; + uintStorage[keccak256(abi.encodePacked("minPerTx"))] = _minPerTx; + + _initialize( + _validatorContract, + _erc20token, + _requiredBlockConfirmations, + _gasPrice, + _maxPerTx, + _homeDailyLimit, + _homeMaxPerTx, + _owner + ); + return isInitialized(); + } + + function initialize( + address /* _validatorContract */, + address /* _erc20token */, + uint256 /* _requiredBlockConfirmations */, + uint256 /* _gasPrice */, + uint256 /* _maxPerTx */, + uint256 /* _homeDailyLimit */, + uint256 /* _homeMaxPerTx */, + address /* _owner */ + ) public returns(bool) { + revert(); + } + + function fireEventOnTokenTransfer(address _from, uint256 _value) internal { + emit UserRequestForAffirmation(_from, _value); + } +} From 3e7c9e606f4607c704d604b39a0612b57a6e3e10 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 29 Apr 2019 15:48:59 -0300 Subject: [PATCH 159/187] Add ForeignBridgeExtendedErcToErc unit tests --- test/erc_to_erc/foreign_bridge.test.js | 127 ++++++++++++++++++++++++- 1 file changed, 124 insertions(+), 3 deletions(-) diff --git a/test/erc_to_erc/foreign_bridge.test.js b/test/erc_to_erc/foreign_bridge.test.js index a6564e59d..8a8f37941 100644 --- a/test/erc_to_erc/foreign_bridge.test.js +++ b/test/erc_to_erc/foreign_bridge.test.js @@ -1,4 +1,5 @@ const ForeignBridge = artifacts.require("ForeignBridgeErcToErc.sol"); +const ForeignBridgeExtended = artifacts.require("ForeignBridgeExtendedErcToErc.sol"); const ForeignBridgeV2 = artifacts.require("ForeignBridgeV2.sol"); const BridgeValidators = artifacts.require("BridgeValidators.sol"); const EternalStorageProxy = artifacts.require("EternalStorageProxy.sol"); @@ -13,6 +14,23 @@ const oneEther = web3.toBigNumber(web3.toWei(1, "ether")); const homeDailyLimit = oneEther const homeMaxPerTx = halfEther const maxPerTx = halfEther +const minPerTx = web3.toBigNumber(web3.toWei(0.01, "ether")); +const dailyLimit = oneEther + +const getEvents = function(contract, filter) { + return new Promise((resolve, reject) => { + var event = contract[filter.event](); + event.watch(); + event.get((error, logs) => { + if(logs.length > 0){ + resolve(logs); + } else { + throw Error("Failed to find filtered event for " + filter.event); + } + }); + event.stopWatching(); + }); +} contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { let validatorContract, authorities, owner, token; @@ -178,7 +196,6 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { await foreignBridge.executeSignatures([vrs3.v], [vrs3.r], [vrs3.s], message3).should.be.rejectedWith(ERROR_MSG) }) }) - describe('#withdraw with 2 minimum signatures', async () => { let multisigValidatorContract, twoAuthorities, ownerOfValidatorContract, foreignBridgeWithMultiSignatures var value = web3.toBigNumber(web3.toWei(0.5, "ether")); @@ -261,7 +278,6 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { true.should.be.equal(await foreignBridgeWithThreeSigs.relayedMessages(txHash)) }) }) - describe('#upgradeable', async () => { it('can be upgraded', async () => { const REQUIRED_NUMBER_OF_VALIDATORS = 1 @@ -311,7 +327,6 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { validatorsAddress.should.be.equal(await finalContract.validatorContract()) }) }) - describe('#claimTokens', async () => { it('can send erc20', async () => { const owner = accounts[0]; @@ -336,4 +351,110 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { }) }) + describe('#ForeignBridgeExtendedErcToErc_onTokenTransfer', async () => { + it('can only be called from token contract', async ()=> { + const owner = accounts[3] + const user = accounts[4] + token = await ERC677BridgeToken.new("TEST", "TST", 18, {from: owner}); + const foreignBridge = await ForeignBridgeExtended.new(); + await foreignBridge.extendedInitialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, dailyLimit, maxPerTx, minPerTx, homeDailyLimit, homeMaxPerTx, owner); + + await token.mint(user, halfEther, {from: owner }).should.be.fulfilled; + await token.transferOwnership(foreignBridge.address, {from: owner}); + await foreignBridge.onTokenTransfer(user, halfEther, '0x00', {from: owner}).should.be.rejectedWith(ERROR_MSG); + + await token.transferAndCall(foreignBridge.address, halfEther, '0x00', {from: user}).should.be.fulfilled; + halfEther.should.be.bignumber.equal(await token.totalSupply()); + '0'.should.be.bignumber.equal(await token.balanceOf(user)); + halfEther.should.be.bignumber.equal(await token.balanceOf(foreignBridge.address)); + const events = await getEvents(foreignBridge, {event: 'UserRequestForAffirmation'}); + events[0].args.should.be.deep.equal({ + recipient: user, + value: halfEther + }) + }) + it('should not allow to transfer more than maxPerTx limit', async () => { + const owner = accounts[3] + const user = accounts[4] + const valueMoreThanLimit = halfEther.add(1); + token = await ERC677BridgeToken.new("TEST", "TST", 18, {from: owner}); + const foreignBridge = await ForeignBridgeExtended.new(); + await foreignBridge.extendedInitialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, dailyLimit, maxPerTx, minPerTx, homeDailyLimit, homeMaxPerTx, owner); + + await token.mint(user, valueMoreThanLimit, {from: owner }).should.be.fulfilled; + await token.transferOwnership(foreignBridge.address, {from: owner}); + + await token.transferAndCall(foreignBridge.address, valueMoreThanLimit, '0x00', {from: user}).should.be.rejectedWith(ERROR_MSG); + valueMoreThanLimit.should.be.bignumber.equal(await token.totalSupply()); + valueMoreThanLimit.should.be.bignumber.equal(await token.balanceOf(user)); + + await token.transferAndCall(foreignBridge.address, halfEther, '0x00', {from: user}).should.be.fulfilled; + valueMoreThanLimit.should.be.bignumber.equal(await token.totalSupply()); + '1'.should.be.bignumber.equal(await token.balanceOf(user)); + halfEther.should.be.bignumber.equal(await token.balanceOf(foreignBridge.address)); + const events = await getEvents(foreignBridge, {event: 'UserRequestForAffirmation'}); + events[0].args.should.be.deep.equal({ + recipient: user, + value: halfEther + }) + }) + it('should only let to transfer within daily limit', async () => { + const owner = accounts[3] + const user = accounts[4] + const valueMoreThanLimit = halfEther.add(1); + token = await ERC677BridgeToken.new("TEST", "TST", 18, {from: owner}); + const foreignBridge = await ForeignBridgeExtended.new(); + await foreignBridge.extendedInitialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, dailyLimit, maxPerTx, minPerTx, homeDailyLimit, homeMaxPerTx, owner); + + await token.mint(user, oneEther.add(1), {from: owner }).should.be.fulfilled; + await token.transferOwnership(foreignBridge.address, {from: owner}); + + await token.transferAndCall(foreignBridge.address, valueMoreThanLimit, '0x00', {from: user}).should.be.rejectedWith(ERROR_MSG); + oneEther.add(1).should.be.bignumber.equal(await token.totalSupply()); + oneEther.add(1).should.be.bignumber.equal(await token.balanceOf(user)); + + await token.transferAndCall(foreignBridge.address, halfEther, '0x00', {from: user}).should.be.fulfilled; + oneEther.add(1).should.be.bignumber.equal(await token.totalSupply()); + valueMoreThanLimit.should.be.bignumber.equal(await token.balanceOf(user)); + const events = await getEvents(foreignBridge, {event: 'UserRequestForAffirmation'}); + events[0].args.should.be.deep.equal({ + recipient: user, + value: halfEther + }) + + + await token.transferAndCall(foreignBridge.address, halfEther, '0x00', {from: user}).should.be.fulfilled; + oneEther.add(1).should.be.bignumber.equal(await token.totalSupply()); + '1'.should.be.bignumber.equal(await token.balanceOf(user)); + oneEther.should.be.bignumber.equal(await token.balanceOf(foreignBridge.address)); + + await token.transferAndCall(foreignBridge.address, '1', '0x00', {from: user}).should.be.rejectedWith(ERROR_MSG); + }) + it('should not let to transfer less than minPerTx', async () => { + const owner = accounts[3] + const user = accounts[4] + const valueLessThanMinPerTx = minPerTx.sub(1); + token = await ERC677BridgeToken.new("TEST", "TST", 18, {from: owner}); + const foreignBridge = await ForeignBridgeExtended.new(); + await foreignBridge.extendedInitialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, dailyLimit, maxPerTx, minPerTx, homeDailyLimit, homeMaxPerTx, owner); + + await token.mint(user, oneEther, {from: owner }).should.be.fulfilled; + await token.transferOwnership(foreignBridge.address, {from: owner}); + + await token.transferAndCall(foreignBridge.address, valueLessThanMinPerTx, '0x00', {from: user}).should.be.rejectedWith(ERROR_MSG); + oneEther.should.be.bignumber.equal(await token.totalSupply()); + oneEther.should.be.bignumber.equal(await token.balanceOf(user)); + + await token.transferAndCall(foreignBridge.address, minPerTx, '0x00', {from: user}).should.be.fulfilled; + oneEther.should.be.bignumber.equal(await token.totalSupply()); + oneEther.sub(minPerTx).should.be.bignumber.equal(await token.balanceOf(user)); + minPerTx.should.be.bignumber.equal(await token.balanceOf(foreignBridge.address)); + + const events = await getEvents(foreignBridge, {event: 'UserRequestForAffirmation'}); + events[0].args.should.be.deep.equal({ + recipient: user, + value: minPerTx + }) + }) + }) }) From c4645dbd70214b687b3ccdd1725df3b9e712d9e1 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 29 Apr 2019 15:50:08 -0300 Subject: [PATCH 160/187] Add ERC20_EXTENDED_BY_ERC677 parameter for erc-to-erc deploy --- deploy/.env.example | 2 ++ deploy/README.md | 2 ++ 2 files changed, 4 insertions(+) diff --git a/deploy/.env.example b/deploy/.env.example index fd30605a8..3df300eca 100644 --- a/deploy/.env.example +++ b/deploy/.env.example @@ -33,6 +33,8 @@ FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS=8 FOREIGN_GAS_PRICE=10000000000 #for bridge erc_to_erc and erc_to_native mode ERC20_TOKEN_ADDRESS= +# Only for for erc_to_erc mode +ERC20_EXTENDED_BY_ERC677=false REQUIRED_NUMBER_OF_VALIDATORS=1 #If several validators are used, list them separated by space without quotes diff --git a/deploy/README.md b/deploy/README.md index 48579ef55..7aab7fb16 100644 --- a/deploy/README.md +++ b/deploy/README.md @@ -232,6 +232,8 @@ FOREIGN_GAS_PRICE=10000000000 # The address of the existing ERC20 compatible token in the Foreign network to # be exchanged to the ERC20/ERC677 token deployed on Home. ERC20_TOKEN_ADDRESS=0x +# Flag to specify that the existing ERC20 is also ERC677 compatible and want the Foreign bridge to use it as ERC677 to increase security. +ERC20_EXTENDED_BY_ERC677=false # The minimum number of validators required to send their signatures confirming # the relay of assets. The same number of validators is expected on both sides From 6d67fe595205dabdad2bf52970bf45a569bc91e6 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Mon, 29 Apr 2019 15:51:28 -0300 Subject: [PATCH 161/187] Add ForeignBridgeExtendedErcToErc to erc-to-erc deployment script --- deploy/deploy.js | 3 +- deploy/src/erc_to_erc/foreign.js | 53 ++++++++++++++++++++++-------- deploy/src/erc_to_erc/preDeploy.js | 18 ++++++++++ deploy/src/loadEnv.js | 14 ++++++-- 4 files changed, 71 insertions(+), 17 deletions(-) create mode 100644 deploy/src/erc_to_erc/preDeploy.js diff --git a/deploy/deploy.js b/deploy/deploy.js index a727c5d49..9af9c126e 100644 --- a/deploy/deploy.js +++ b/deploy/deploy.js @@ -42,9 +42,10 @@ async function deployNativeToErc() { } async function deployErcToErc() { + const preDeploy = require('./src/erc_to_erc/preDeploy') const deployHome = require('./src/erc_to_erc/home') const deployForeign = require('./src/erc_to_erc/foreign') - + await preDeploy() const { homeBridge, erc677 } = await deployHome() const { foreignBridge } = await deployForeign() console.log('\nDeployment has been completed.\n\n') diff --git a/deploy/src/erc_to_erc/foreign.js b/deploy/src/erc_to_erc/foreign.js index 6dc7d81f9..a65f2f276 100644 --- a/deploy/src/erc_to_erc/foreign.js +++ b/deploy/src/erc_to_erc/foreign.js @@ -8,6 +8,7 @@ const { web3Foreign, deploymentPrivateKey, FOREIGN_RPC_URL } = require('../web3' const EternalStorageProxy = require('../../../build/contracts/EternalStorageProxy.json') const BridgeValidators = require('../../../build/contracts/BridgeValidators.json') const ForeignBridge = require('../../../build/contracts/ForeignBridgeErcToErc.json') +const ForeignBridgeExtendedErcToErc = require('../../../build/contracts/ForeignBridgeExtendedErcToErc.json') const VALIDATORS = env.VALIDATORS.split(' ') @@ -22,7 +23,10 @@ const { FOREIGN_GAS_PRICE, FOREIGN_MAX_AMOUNT_PER_TX, HOME_DAILY_LIMIT, - HOME_MAX_AMOUNT_PER_TX + HOME_MAX_AMOUNT_PER_TX, + FOREIGN_MIN_AMOUNT_PER_TX, + FOREIGN_DAILY_LIMIT, + ERC20_EXTENDED_BY_ERC677 } = env const DEPLOYMENT_ACCOUNT_ADDRESS = privateKeyToAddress(DEPLOYMENT_ACCOUNT_PRIVATE_KEY) @@ -121,7 +125,8 @@ async function deployForeign() { console.log('[Foreign] ForeignBridge Storage: ', foreignBridgeStorage.options.address) console.log('\ndeploying foreignBridge implementation\n') - const foreignBridgeImplementation = await deployContract(ForeignBridge, [], { + const bridgeContract = ERC20_EXTENDED_BY_ERC677 ? ForeignBridgeExtendedErcToErc : ForeignBridge + const foreignBridgeImplementation = await deployContract(bridgeContract, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, network: 'foreign', nonce: foreignNonce @@ -154,18 +159,38 @@ async function deployForeign() { console.log(`Foreign Validators: ${storageValidatorsForeign.options.address}, `) foreignBridgeImplementation.options.address = foreignBridgeStorage.options.address - const initializeFBridgeData = await foreignBridgeImplementation.methods - .initialize( - storageValidatorsForeign.options.address, - ERC20_TOKEN_ADDRESS, - FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS, - FOREIGN_GAS_PRICE, - FOREIGN_MAX_AMOUNT_PER_TX, - HOME_DAILY_LIMIT, - HOME_MAX_AMOUNT_PER_TX, - FOREIGN_BRIDGE_OWNER - ) - .encodeABI({ from: DEPLOYMENT_ACCOUNT_ADDRESS }) + let initializeFBridgeData + + if (ERC20_EXTENDED_BY_ERC677) { + initializeFBridgeData = await foreignBridgeImplementation.methods + .extendedInitialize( + storageValidatorsForeign.options.address, + ERC20_TOKEN_ADDRESS, + FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS, + FOREIGN_GAS_PRICE, + FOREIGN_DAILY_LIMIT, + FOREIGN_MAX_AMOUNT_PER_TX, + FOREIGN_MIN_AMOUNT_PER_TX, + HOME_DAILY_LIMIT, + HOME_MAX_AMOUNT_PER_TX, + FOREIGN_BRIDGE_OWNER + ) + .encodeABI() + } else { + initializeFBridgeData = await foreignBridgeImplementation.methods + .initialize( + storageValidatorsForeign.options.address, + ERC20_TOKEN_ADDRESS, + FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS, + FOREIGN_GAS_PRICE, + FOREIGN_MAX_AMOUNT_PER_TX, + HOME_DAILY_LIMIT, + HOME_MAX_AMOUNT_PER_TX, + FOREIGN_BRIDGE_OWNER + ) + .encodeABI() + } + const txInitializeBridge = await sendRawTxForeign({ data: initializeFBridgeData, nonce: foreignNonce, diff --git a/deploy/src/erc_to_erc/preDeploy.js b/deploy/src/erc_to_erc/preDeploy.js new file mode 100644 index 000000000..5cb785774 --- /dev/null +++ b/deploy/src/erc_to_erc/preDeploy.js @@ -0,0 +1,18 @@ +const { web3Foreign } = require('../web3') +const { ERC20_TOKEN_ADDRESS, ERC20_EXTENDED_BY_ERC677 } = require('../loadEnv') +const { abi } = require('../../../build/contracts/ERC677BridgeToken.json') + +async function preDeploy() { + if (ERC20_EXTENDED_BY_ERC677) { + const tokenContract = new web3Foreign.eth.Contract(abi, ERC20_TOKEN_ADDRESS) + try { + await tokenContract.methods.bridgeContract().call() + } catch (e) { + throw new Error( + `ERC20_EXTENDED_BY_ERC677 is set to TRUE but bridgeContract method was not found on ERC677 token.` + ) + } + } +} + +module.exports = preDeploy diff --git a/deploy/src/loadEnv.js b/deploy/src/loadEnv.js index 61733c9fb..c13d01e39 100644 --- a/deploy/src/loadEnv.js +++ b/deploy/src/loadEnv.js @@ -22,7 +22,7 @@ const addressesValidator = envalid.makeValidator(addresses => { return addresses }) -const { BRIDGE_MODE } = process.env +const { BRIDGE_MODE, ERC20_EXTENDED_BY_ERC677 } = process.env if (!validBridgeModes.includes(BRIDGE_MODE)) { throw new Error(`Invalid bridge mode: ${BRIDGE_MODE}`) @@ -76,7 +76,17 @@ if (BRIDGE_MODE === 'ERC_TO_ERC') { BRIDGEABLE_TOKEN_DECIMALS: envalid.num(), DEPLOY_REWARDABLE_TOKEN: envalid.bool(), DPOS_STAKING_ADDRESS: addressValidator(), - BLOCK_REWARD_ADDRESS: addressValidator() + BLOCK_REWARD_ADDRESS: addressValidator(), + ERC20_EXTENDED_BY_ERC677: envalid.bool() + } + + if (ERC20_EXTENDED_BY_ERC677 === 'true') { + validations = { + ...validations, + FOREIGN_DAILY_LIMIT: bigNumValidator(), + FOREIGN_MAX_AMOUNT_PER_TX: bigNumValidator(), + FOREIGN_MIN_AMOUNT_PER_TX: bigNumValidator() + } } } if (BRIDGE_MODE === 'ERC_TO_NATIVE') { From 5d54ffb20bda80cf64a59529569bec4f1ef60ba5 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 30 Apr 2019 13:36:13 -0300 Subject: [PATCH 162/187] Refactor ForeignBridgeErc677ToErc677 --- .../ERC20ExtendedBridge.sol | 19 ------ .../upgradeable_contracts/ERC677Bridge.sol | 12 ++-- .../ERC677BridgeForBurnableMintableToken.sol | 13 ++++ .../BasicForeignBridgeErcToErc.sol | 63 ++++++++++++++++++ ...rc.sol => ForeignBridgeErc677ToErc677.sol} | 31 ++++----- .../erc20_to_erc20/ForeignBridgeErcToErc.sol | 64 ++----------------- .../erc20_to_erc20/HomeBridgeErcToErc.sol | 4 +- .../ForeignBridgeNativeToErc.sol | 4 +- 8 files changed, 106 insertions(+), 104 deletions(-) delete mode 100644 contracts/upgradeable_contracts/ERC20ExtendedBridge.sol create mode 100644 contracts/upgradeable_contracts/ERC677BridgeForBurnableMintableToken.sol create mode 100644 contracts/upgradeable_contracts/erc20_to_erc20/BasicForeignBridgeErcToErc.sol rename contracts/upgradeable_contracts/erc20_to_erc20/{ForeignBridgeExtendedErcToErc.sol => ForeignBridgeErc677ToErc677.sol} (67%) diff --git a/contracts/upgradeable_contracts/ERC20ExtendedBridge.sol b/contracts/upgradeable_contracts/ERC20ExtendedBridge.sol deleted file mode 100644 index 94a07de37..000000000 --- a/contracts/upgradeable_contracts/ERC20ExtendedBridge.sol +++ /dev/null @@ -1,19 +0,0 @@ -pragma solidity 0.4.24; - - -import "./BasicBridge.sol"; -import "openzeppelin-solidity/contracts/token/ERC20/ERC20Basic.sol"; - -contract ERC20ExtendedBridge is BasicBridge { - function onTokenTransfer(address _from, uint256 _value, bytes /*_data*/) external returns(bool) { - require(msg.sender == address(erc20token())); - require(withinLimit(_value)); - setTotalSpentPerDay(getCurrentDay(), totalSpentPerDay(getCurrentDay()).add(_value)); - fireEventOnTokenTransfer(_from, _value); - return true; - } - - function erc20token() public view returns(ERC20Basic); - - function fireEventOnTokenTransfer(address /*_from */, uint256 /* _value */) internal; -} diff --git a/contracts/upgradeable_contracts/ERC677Bridge.sol b/contracts/upgradeable_contracts/ERC677Bridge.sol index 8206e6669..3d99026f4 100644 --- a/contracts/upgradeable_contracts/ERC677Bridge.sol +++ b/contracts/upgradeable_contracts/ERC677Bridge.sol @@ -2,6 +2,7 @@ pragma solidity 0.4.24; import "./BasicBridge.sol"; +import "../ERC677.sol"; import "../IBurnableMintableERC677Token.sol"; contract ERC677Bridge is BasicBridge { @@ -15,16 +16,17 @@ contract ERC677Bridge is BasicBridge { } function onTokenTransfer(address _from, uint256 _value, bytes /*_data*/) external returns(bool) { - require(msg.sender == address(erc677token())); + IBurnableMintableERC677Token token = erc677token(); + require(msg.sender == address(token)); require(withinLimit(_value)); setTotalSpentPerDay(getCurrentDay(), totalSpentPerDay(getCurrentDay()).add(_value)); - erc677token().burn(_value); - fireEventOnTokenTransfer(_from, _value); + bridgeSpecificActionsOnTokenTransfer(token, _from, _value); return true; } - function fireEventOnTokenTransfer(address /*_from */, uint256 /* _value */) internal { - // has to be defined + function bridgeSpecificActionsOnTokenTransfer(IBurnableMintableERC677Token _token, address _from, uint256 _value) internal { + fireEventOnTokenTransfer(_from, _value); } + function fireEventOnTokenTransfer(address _from, uint256 _value) internal; } diff --git a/contracts/upgradeable_contracts/ERC677BridgeForBurnableMintableToken.sol b/contracts/upgradeable_contracts/ERC677BridgeForBurnableMintableToken.sol new file mode 100644 index 000000000..f93e8419a --- /dev/null +++ b/contracts/upgradeable_contracts/ERC677BridgeForBurnableMintableToken.sol @@ -0,0 +1,13 @@ +pragma solidity 0.4.24; + + +import "./ERC677Bridge.sol"; +import "../IBurnableMintableERC677Token.sol"; + + +contract ERC677BridgeForBurnableMintableToken is ERC677Bridge { + function bridgeSpecificActionsOnTokenTransfer(IBurnableMintableERC677Token _token, address _from, uint256 _value) internal { + _token.burn(_value); + fireEventOnTokenTransfer(_from, _value); + } +} diff --git a/contracts/upgradeable_contracts/erc20_to_erc20/BasicForeignBridgeErcToErc.sol b/contracts/upgradeable_contracts/erc20_to_erc20/BasicForeignBridgeErcToErc.sol new file mode 100644 index 000000000..f9238e51e --- /dev/null +++ b/contracts/upgradeable_contracts/erc20_to_erc20/BasicForeignBridgeErcToErc.sol @@ -0,0 +1,63 @@ +pragma solidity 0.4.24; + + +import "../BasicBridge.sol"; +import "../BasicForeignBridge.sol"; +import "openzeppelin-solidity/contracts/token/ERC20/ERC20Basic.sol"; + + +contract BasicForeignBridgeErcToErc is BasicBridge, BasicForeignBridge { + function _initialize( + address _validatorContract, + address _erc20token, + uint256 _requiredBlockConfirmations, + uint256 _gasPrice, + uint256 _maxPerTx, + uint256 _homeDailyLimit, + uint256 _homeMaxPerTx, + address _owner + ) internal { + require(!isInitialized()); + require(_validatorContract != address(0) && isContract(_validatorContract)); + require(_requiredBlockConfirmations != 0); + require(_gasPrice > 0); + require(_homeMaxPerTx < _homeDailyLimit); + require(_owner != address(0)); + addressStorage[keccak256(abi.encodePacked("validatorContract"))] = _validatorContract; + setErc20token(_erc20token); + uintStorage[keccak256(abi.encodePacked("deployedAtBlock"))] = block.number; + uintStorage[keccak256(abi.encodePacked("requiredBlockConfirmations"))] = _requiredBlockConfirmations; + uintStorage[keccak256(abi.encodePacked("gasPrice"))] = _gasPrice; + uintStorage[keccak256(abi.encodePacked("maxPerTx"))] = _maxPerTx; + uintStorage[keccak256(abi.encodePacked("executionDailyLimit"))] = _homeDailyLimit; + uintStorage[keccak256(abi.encodePacked("executionMaxPerTx"))] = _homeMaxPerTx; + setOwner(_owner); + setInitialize(true); + } + + function getBridgeMode() public pure returns(bytes4 _data) { + return bytes4(keccak256(abi.encodePacked("erc-to-erc-core"))); + } + + function claimTokens(address _token, address _to) public onlyIfOwnerOfProxy { + require(_token != address(erc20token())); + super.claimTokens(_token, _to); + } + + function onExecuteMessage(address _recipient, uint256 _amount) internal returns(bool){ + setTotalExecutedPerDay(getCurrentDay(), totalExecutedPerDay(getCurrentDay()).add(_amount)); + return erc20token().transfer(_recipient, _amount); + } + + function messageWithinLimits(uint256 _amount) internal view returns(bool) { + return withinExecutionLimit(_amount); + } + + function onFailedMessage(address, uint256, bytes32) internal { + revert(); + } + + function erc20token() public view returns(ERC20Basic); + + function setErc20token(address _token) internal; +} diff --git a/contracts/upgradeable_contracts/erc20_to_erc20/ForeignBridgeExtendedErcToErc.sol b/contracts/upgradeable_contracts/erc20_to_erc20/ForeignBridgeErc677ToErc677.sol similarity index 67% rename from contracts/upgradeable_contracts/erc20_to_erc20/ForeignBridgeExtendedErcToErc.sol rename to contracts/upgradeable_contracts/erc20_to_erc20/ForeignBridgeErc677ToErc677.sol index 788f16b5d..6f5bfe34d 100644 --- a/contracts/upgradeable_contracts/erc20_to_erc20/ForeignBridgeExtendedErcToErc.sol +++ b/contracts/upgradeable_contracts/erc20_to_erc20/ForeignBridgeErc677ToErc677.sol @@ -1,15 +1,15 @@ pragma solidity 0.4.24; -import "./ForeignBridgeErcToErc.sol"; -import "../ERC20ExtendedBridge.sol"; +import "./BasicForeignBridgeErcToErc.sol"; +import "../ERC677Bridge.sol"; -contract ForeignBridgeExtendedErcToErc is ERC20ExtendedBridge, ForeignBridgeErcToErc { +contract ForeignBridgeErc677ToErc677 is ERC677Bridge, BasicForeignBridgeErcToErc { event UserRequestForAffirmation(address recipient, uint256 value); - function extendedInitialize( + function initialize( address _validatorContract, address _erc20token, uint256 _requiredBlockConfirmations, @@ -22,8 +22,6 @@ contract ForeignBridgeExtendedErcToErc is ERC20ExtendedBridge, ForeignBridgeErcT address _owner ) public returns(bool) { require(_minPerTx > 0 && _maxPerTx > _minPerTx && _dailyLimit > _maxPerTx); - uintStorage[keccak256(abi.encodePacked("dailyLimit"))] = _dailyLimit; - uintStorage[keccak256(abi.encodePacked("minPerTx"))] = _minPerTx; _initialize( _validatorContract, @@ -35,20 +33,19 @@ contract ForeignBridgeExtendedErcToErc is ERC20ExtendedBridge, ForeignBridgeErcT _homeMaxPerTx, _owner ); + + uintStorage[keccak256(abi.encodePacked("dailyLimit"))] = _dailyLimit; + uintStorage[keccak256(abi.encodePacked("minPerTx"))] = _minPerTx; + return isInitialized(); } - function initialize( - address /* _validatorContract */, - address /* _erc20token */, - uint256 /* _requiredBlockConfirmations */, - uint256 /* _gasPrice */, - uint256 /* _maxPerTx */, - uint256 /* _homeDailyLimit */, - uint256 /* _homeMaxPerTx */, - address /* _owner */ - ) public returns(bool) { - revert(); + function erc20token() public view returns(ERC20Basic) { + return erc677token(); + } + + function setErc20token(address _token) internal { + setErc677token(_token); } function fireEventOnTokenTransfer(address _from, uint256 _value) internal { diff --git a/contracts/upgradeable_contracts/erc20_to_erc20/ForeignBridgeErcToErc.sol b/contracts/upgradeable_contracts/erc20_to_erc20/ForeignBridgeErcToErc.sol index 4a6342edc..57c8d1ea3 100644 --- a/contracts/upgradeable_contracts/erc20_to_erc20/ForeignBridgeErcToErc.sol +++ b/contracts/upgradeable_contracts/erc20_to_erc20/ForeignBridgeErcToErc.sol @@ -1,14 +1,10 @@ pragma solidity 0.4.24; -import "../../libraries/SafeMath.sol"; -import "../../libraries/Message.sol"; -import "../BasicBridge.sol"; -import "../BasicForeignBridge.sol"; -import "../../IBurnableMintableERC677Token.sol"; -import "../../ERC677Receiver.sol"; -import "openzeppelin-solidity/contracts/token/ERC20/ERC20Basic.sol"; -contract ForeignBridgeErcToErc is BasicBridge, BasicForeignBridge { +import "./BasicForeignBridgeErcToErc.sol"; + + +contract ForeignBridgeErcToErc is BasicForeignBridgeErcToErc { function initialize( address _validatorContract, address _erc20token, @@ -32,62 +28,12 @@ contract ForeignBridgeErcToErc is BasicBridge, BasicForeignBridge { return isInitialized(); } - function _initialize( - address _validatorContract, - address _erc20token, - uint256 _requiredBlockConfirmations, - uint256 _gasPrice, - uint256 _maxPerTx, - uint256 _homeDailyLimit, - uint256 _homeMaxPerTx, - address _owner - ) internal { - require(!isInitialized()); - require(_validatorContract != address(0) && isContract(_validatorContract)); - require(_requiredBlockConfirmations != 0); - require(_gasPrice > 0); - require(_homeMaxPerTx < _homeDailyLimit); - require(_owner != address(0)); - addressStorage[keccak256(abi.encodePacked("validatorContract"))] = _validatorContract; - setErc20token(_erc20token); - uintStorage[keccak256(abi.encodePacked("deployedAtBlock"))] = block.number; - uintStorage[keccak256(abi.encodePacked("requiredBlockConfirmations"))] = _requiredBlockConfirmations; - uintStorage[keccak256(abi.encodePacked("gasPrice"))] = _gasPrice; - uintStorage[keccak256(abi.encodePacked("maxPerTx"))] = _maxPerTx; - uintStorage[keccak256(abi.encodePacked("executionDailyLimit"))] = _homeDailyLimit; - uintStorage[keccak256(abi.encodePacked("executionMaxPerTx"))] = _homeMaxPerTx; - setOwner(_owner); - setInitialize(true); - } - - function getBridgeMode() public pure returns(bytes4 _data) { - return bytes4(keccak256(abi.encodePacked("erc-to-erc-core"))); - } - - function claimTokens(address _token, address _to) public onlyIfOwnerOfProxy { - require(_token != address(erc20token())); - super.claimTokens(_token, _to); - } - function erc20token() public view returns(ERC20Basic) { return ERC20Basic(addressStorage[keccak256(abi.encodePacked("erc20token"))]); } - function onExecuteMessage(address _recipient, uint256 _amount) internal returns(bool){ - setTotalExecutedPerDay(getCurrentDay(), totalExecutedPerDay(getCurrentDay()).add(_amount)); - return erc20token().transfer(_recipient, _amount); - } - - function setErc20token(address _token) private { + function setErc20token(address _token) internal { require(_token != address(0) && isContract(_token)); addressStorage[keccak256(abi.encodePacked("erc20token"))] = _token; } - - function messageWithinLimits(uint256 _amount) internal view returns(bool) { - return withinExecutionLimit(_amount); - } - - function onFailedMessage(address, uint256, bytes32) internal { - revert(); - } } diff --git a/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol b/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol index 51313be11..6fb99928d 100644 --- a/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol +++ b/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol @@ -6,11 +6,11 @@ import "../../upgradeability/EternalStorage.sol"; import "../../IBurnableMintableERC677Token.sol"; import "../../ERC677Receiver.sol"; import "../BasicHomeBridge.sol"; -import "../ERC677Bridge.sol"; import "../OverdrawManagement.sol"; +import "../ERC677BridgeForBurnableMintableToken.sol"; -contract HomeBridgeErcToErc is ERC677Receiver, EternalStorage, BasicBridge, BasicHomeBridge, ERC677Bridge, OverdrawManagement { +contract HomeBridgeErcToErc is ERC677Receiver, EternalStorage, BasicBridge, BasicHomeBridge, ERC677BridgeForBurnableMintableToken, OverdrawManagement { event AmountLimitExceeded(address recipient, uint256 value, bytes32 transactionHash); diff --git a/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol index 3b52049a2..7bdd35ebf 100644 --- a/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol +++ b/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol @@ -5,10 +5,10 @@ import "../../IBurnableMintableERC677Token.sol"; import "../../ERC677Receiver.sol"; import "../BasicForeignBridge.sol"; import "openzeppelin-solidity/contracts/token/ERC20/ERC20Basic.sol"; -import "../ERC677Bridge.sol"; +import "../ERC677BridgeForBurnableMintableToken.sol"; -contract ForeignBridgeNativeToErc is ERC677Receiver, BasicBridge, BasicForeignBridge, ERC677Bridge { +contract ForeignBridgeNativeToErc is ERC677Receiver, BasicBridge, BasicForeignBridge, ERC677BridgeForBurnableMintableToken { /// Event created on money withdraw. event UserRequestForAffirmation(address recipient, uint256 value); From 17b907a821c4a4f6f3f9589597f1b5c581f577d9 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 30 Apr 2019 13:57:45 -0300 Subject: [PATCH 163/187] Add FOREIGN_MAX_AMOUNT_PER_TX check for all modes in loadEnv --- deploy/src/loadEnv.js | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/deploy/src/loadEnv.js b/deploy/src/loadEnv.js index c13d01e39..c5ab7a044 100644 --- a/deploy/src/loadEnv.js +++ b/deploy/src/loadEnv.js @@ -49,6 +49,7 @@ let validations = { FOREIGN_UPGRADEABLE_ADMIN: addressValidator(), FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS: envalid.num(), FOREIGN_GAS_PRICE: bigNumValidator(), + FOREIGN_MAX_AMOUNT_PER_TX: bigNumValidator(), REQUIRED_NUMBER_OF_VALIDATORS: envalid.num(), VALIDATORS: addressesValidator() } @@ -60,7 +61,6 @@ if (BRIDGE_MODE === 'NATIVE_TO_ERC') { BRIDGEABLE_TOKEN_SYMBOL: envalid.str(), BRIDGEABLE_TOKEN_DECIMALS: envalid.num(), FOREIGN_DAILY_LIMIT: bigNumValidator(), - FOREIGN_MAX_AMOUNT_PER_TX: bigNumValidator(), FOREIGN_MIN_AMOUNT_PER_TX: bigNumValidator(), DEPLOY_REWARDABLE_TOKEN: envalid.bool(), DPOS_STAKING_ADDRESS: addressValidator(), @@ -84,7 +84,6 @@ if (BRIDGE_MODE === 'ERC_TO_ERC') { validations = { ...validations, FOREIGN_DAILY_LIMIT: bigNumValidator(), - FOREIGN_MAX_AMOUNT_PER_TX: bigNumValidator(), FOREIGN_MIN_AMOUNT_PER_TX: bigNumValidator() } } From c65f1231ffffc6b09b5e1ca94ea8e1351d240021 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 30 Apr 2019 15:15:49 -0300 Subject: [PATCH 164/187] Fix erc-to-erc foreign deploy script --- deploy/src/erc_to_erc/foreign.js | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/deploy/src/erc_to_erc/foreign.js b/deploy/src/erc_to_erc/foreign.js index a65f2f276..4e3f44b67 100644 --- a/deploy/src/erc_to_erc/foreign.js +++ b/deploy/src/erc_to_erc/foreign.js @@ -8,7 +8,7 @@ const { web3Foreign, deploymentPrivateKey, FOREIGN_RPC_URL } = require('../web3' const EternalStorageProxy = require('../../../build/contracts/EternalStorageProxy.json') const BridgeValidators = require('../../../build/contracts/BridgeValidators.json') const ForeignBridge = require('../../../build/contracts/ForeignBridgeErcToErc.json') -const ForeignBridgeExtendedErcToErc = require('../../../build/contracts/ForeignBridgeExtendedErcToErc.json') +const ForeignBridgeErc677ToErc677 = require('../../../build/contracts/ForeignBridgeErc677ToErc677.json') const VALIDATORS = env.VALIDATORS.split(' ') @@ -125,7 +125,7 @@ async function deployForeign() { console.log('[Foreign] ForeignBridge Storage: ', foreignBridgeStorage.options.address) console.log('\ndeploying foreignBridge implementation\n') - const bridgeContract = ERC20_EXTENDED_BY_ERC677 ? ForeignBridgeExtendedErcToErc : ForeignBridge + const bridgeContract = ERC20_EXTENDED_BY_ERC677 ? ForeignBridgeErc677ToErc677 : ForeignBridge const foreignBridgeImplementation = await deployContract(bridgeContract, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, network: 'foreign', @@ -163,7 +163,7 @@ async function deployForeign() { if (ERC20_EXTENDED_BY_ERC677) { initializeFBridgeData = await foreignBridgeImplementation.methods - .extendedInitialize( + .initialize( storageValidatorsForeign.options.address, ERC20_TOKEN_ADDRESS, FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS, From de9ff59ff4675c42bfb25ab0bc97c226c90066dd Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 30 Apr 2019 15:16:05 -0300 Subject: [PATCH 165/187] Fix erc-to-erc foreign unit tests --- test/erc_to_erc/foreign_bridge.test.js | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/test/erc_to_erc/foreign_bridge.test.js b/test/erc_to_erc/foreign_bridge.test.js index 8a8f37941..f62572c78 100644 --- a/test/erc_to_erc/foreign_bridge.test.js +++ b/test/erc_to_erc/foreign_bridge.test.js @@ -1,5 +1,5 @@ const ForeignBridge = artifacts.require("ForeignBridgeErcToErc.sol"); -const ForeignBridgeExtended = artifacts.require("ForeignBridgeExtendedErcToErc.sol"); +const ForeignBridgeErc677ToErc677 = artifacts.require("ForeignBridgeErc677ToErc677.sol"); const ForeignBridgeV2 = artifacts.require("ForeignBridgeV2.sol"); const BridgeValidators = artifacts.require("BridgeValidators.sol"); const EternalStorageProxy = artifacts.require("EternalStorageProxy.sol"); @@ -351,13 +351,13 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { }) }) - describe('#ForeignBridgeExtendedErcToErc_onTokenTransfer', async () => { + describe('#ForeignBridgeErc677ToErc677_onTokenTransfer', async () => { it('can only be called from token contract', async ()=> { const owner = accounts[3] const user = accounts[4] token = await ERC677BridgeToken.new("TEST", "TST", 18, {from: owner}); - const foreignBridge = await ForeignBridgeExtended.new(); - await foreignBridge.extendedInitialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, dailyLimit, maxPerTx, minPerTx, homeDailyLimit, homeMaxPerTx, owner); + const foreignBridge = await ForeignBridgeErc677ToErc677.new(); + await foreignBridge.initialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, dailyLimit, maxPerTx, minPerTx, homeDailyLimit, homeMaxPerTx, owner); await token.mint(user, halfEther, {from: owner }).should.be.fulfilled; await token.transferOwnership(foreignBridge.address, {from: owner}); @@ -378,8 +378,8 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { const user = accounts[4] const valueMoreThanLimit = halfEther.add(1); token = await ERC677BridgeToken.new("TEST", "TST", 18, {from: owner}); - const foreignBridge = await ForeignBridgeExtended.new(); - await foreignBridge.extendedInitialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, dailyLimit, maxPerTx, minPerTx, homeDailyLimit, homeMaxPerTx, owner); + const foreignBridge = await ForeignBridgeErc677ToErc677.new(); + await foreignBridge.initialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, dailyLimit, maxPerTx, minPerTx, homeDailyLimit, homeMaxPerTx, owner); await token.mint(user, valueMoreThanLimit, {from: owner }).should.be.fulfilled; await token.transferOwnership(foreignBridge.address, {from: owner}); @@ -403,8 +403,8 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { const user = accounts[4] const valueMoreThanLimit = halfEther.add(1); token = await ERC677BridgeToken.new("TEST", "TST", 18, {from: owner}); - const foreignBridge = await ForeignBridgeExtended.new(); - await foreignBridge.extendedInitialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, dailyLimit, maxPerTx, minPerTx, homeDailyLimit, homeMaxPerTx, owner); + const foreignBridge = await ForeignBridgeErc677ToErc677.new(); + await foreignBridge.initialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, dailyLimit, maxPerTx, minPerTx, homeDailyLimit, homeMaxPerTx, owner); await token.mint(user, oneEther.add(1), {from: owner }).should.be.fulfilled; await token.transferOwnership(foreignBridge.address, {from: owner}); @@ -435,8 +435,8 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { const user = accounts[4] const valueLessThanMinPerTx = minPerTx.sub(1); token = await ERC677BridgeToken.new("TEST", "TST", 18, {from: owner}); - const foreignBridge = await ForeignBridgeExtended.new(); - await foreignBridge.extendedInitialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, dailyLimit, maxPerTx, minPerTx, homeDailyLimit, homeMaxPerTx, owner); + const foreignBridge = await ForeignBridgeErc677ToErc677.new(); + await foreignBridge.initialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, dailyLimit, maxPerTx, minPerTx, homeDailyLimit, homeMaxPerTx, owner); await token.mint(user, oneEther, {from: owner }).should.be.fulfilled; await token.transferOwnership(foreignBridge.address, {from: owner}); From d92dd655faae5068c355551a7b5893ba90afb54d Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Thu, 2 May 2019 10:06:00 -0300 Subject: [PATCH 166/187] Fix initializeValidators logs --- deploy/src/deploymentUtils.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/deploy/src/deploymentUtils.js b/deploy/src/deploymentUtils.js index 583b4bf78..49b09dbeb 100644 --- a/deploy/src/deploymentUtils.js +++ b/deploy/src/deploymentUtils.js @@ -224,14 +224,14 @@ async function initializeValidators({ let data if (isRewardableBridge) { - console.log(`REQUIRED_NUMBER_OF_VALIDATORS: ${requiredNumber}, HOME_VALIDATORS_OWNER: ${owner}`) + console.log(`REQUIRED_NUMBER_OF_VALIDATORS: ${requiredNumber}, VALIDATORS_OWNER: ${owner}`) logValidatorsAndRewardAccounts(validators, rewardAccounts) data = await contract.methods .initialize(requiredNumber, validators, rewardAccounts, owner) .encodeABI() } else { console.log( - `REQUIRED_NUMBER_OF_VALIDATORS: ${requiredNumber}, VALIDATORS: ${validators}, HOME_VALIDATORS_OWNER: ${owner}` + `REQUIRED_NUMBER_OF_VALIDATORS: ${requiredNumber}, VALIDATORS: ${validators}, VALIDATORS_OWNER: ${owner}` ) data = await contract.methods.initialize(requiredNumber, validators, owner).encodeABI() } From f022bed9d19ac9126a56c8f4c5e272dfed66bdc5 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Thu, 2 May 2019 12:56:10 -0300 Subject: [PATCH 167/187] Fix sendTx method used on deploy script utils --- deploy/src/deploymentUtils.js | 20 ++++++++++++++------ 1 file changed, 14 insertions(+), 6 deletions(-) diff --git a/deploy/src/deploymentUtils.js b/deploy/src/deploymentUtils.js index 49b09dbeb..b849a21ff 100644 --- a/deploy/src/deploymentUtils.js +++ b/deploy/src/deploymentUtils.js @@ -149,7 +149,8 @@ function logValidatorsAndRewardAccounts(validators, rewards) { async function upgradeProxy({ proxy, implementationAddress, version, nonce, url }) { const data = await proxy.methods.upgradeTo(version, implementationAddress).encodeABI() - const result = await sendRawTxHome({ + const sendTx = getSendTxMethod(url) + const result = await sendTx({ data, nonce, to: proxy.options.address, @@ -165,7 +166,8 @@ async function upgradeProxy({ proxy, implementationAddress, version, nonce, url async function transferProxyOwnership({ proxy, newOwner, nonce, url }) { const data = await proxy.methods.transferProxyOwnership(newOwner).encodeABI() - const result = await sendRawTxHome({ + const sendTx = getSendTxMethod(url) + const result = await sendTx({ data, nonce, to: proxy.options.address, @@ -181,7 +183,8 @@ async function transferProxyOwnership({ proxy, newOwner, nonce, url }) { async function transferOwnership({ contract, newOwner, nonce, url }) { const data = await contract.methods.transferOwnership(newOwner).encodeABI() - const result = await sendRawTxForeign({ + const sendTx = getSendTxMethod(url) + const result = await sendTx({ data, nonce, to: contract.options.address, @@ -197,7 +200,8 @@ async function transferOwnership({ contract, newOwner, nonce, url }) { async function setBridgeContract({ contract, bridgeAddress, nonce, url }) { const data = await contract.methods.setBridgeContract(bridgeAddress).encodeABI() - const result = await sendRawTxForeign({ + const sendTx = getSendTxMethod(url) + const result = await sendTx({ data, nonce, to: contract.options.address, @@ -235,8 +239,8 @@ async function initializeValidators({ ) data = await contract.methods.initialize(requiredNumber, validators, owner).encodeABI() } - - const result = await sendRawTxHome({ + const sendTx = getSendTxMethod(url) + const result = await sendTx({ data, nonce, to: contract.options.address, @@ -259,6 +263,10 @@ async function assertStateWithRetry(fn, expected) { }) } +function getSendTxMethod(url) { + return url === HOME_RPC_URL ? sendRawTxHome : sendRawTxForeign +} + module.exports = { deployContract, sendRawTxHome, From d0ad22eb3e81a405959aa34280506bd8a8c85298 Mon Sep 17 00:00:00 2001 From: Alexander Kolotov Date: Thu, 2 May 2019 20:47:40 +0300 Subject: [PATCH 168/187] more common ERC677 type is used in ERC677Bridge --- contracts/upgradeable_contracts/ERC677Bridge.sol | 9 ++++----- .../ERC677BridgeForBurnableMintableToken.sol | 4 ++-- .../erc20_to_erc20/HomeBridgeErcToErc.sol | 2 +- .../native_to_erc20/ForeignBridgeNativeToErc.sol | 4 ++-- 4 files changed, 9 insertions(+), 10 deletions(-) diff --git a/contracts/upgradeable_contracts/ERC677Bridge.sol b/contracts/upgradeable_contracts/ERC677Bridge.sol index 3d99026f4..37777b3b7 100644 --- a/contracts/upgradeable_contracts/ERC677Bridge.sol +++ b/contracts/upgradeable_contracts/ERC677Bridge.sol @@ -3,11 +3,10 @@ pragma solidity 0.4.24; import "./BasicBridge.sol"; import "../ERC677.sol"; -import "../IBurnableMintableERC677Token.sol"; contract ERC677Bridge is BasicBridge { - function erc677token() public view returns(IBurnableMintableERC677Token) { - return IBurnableMintableERC677Token(addressStorage[keccak256(abi.encodePacked("erc677token"))]); + function erc677token() public view returns(ERC677) { + return ERC677(addressStorage[keccak256(abi.encodePacked("erc677token"))]); } function setErc677token(address _token) internal { @@ -16,7 +15,7 @@ contract ERC677Bridge is BasicBridge { } function onTokenTransfer(address _from, uint256 _value, bytes /*_data*/) external returns(bool) { - IBurnableMintableERC677Token token = erc677token(); + ERC677 token = erc677token(); require(msg.sender == address(token)); require(withinLimit(_value)); setTotalSpentPerDay(getCurrentDay(), totalSpentPerDay(getCurrentDay()).add(_value)); @@ -24,7 +23,7 @@ contract ERC677Bridge is BasicBridge { return true; } - function bridgeSpecificActionsOnTokenTransfer(IBurnableMintableERC677Token _token, address _from, uint256 _value) internal { + function bridgeSpecificActionsOnTokenTransfer(ERC677 _token, address _from, uint256 _value) internal { fireEventOnTokenTransfer(_from, _value); } diff --git a/contracts/upgradeable_contracts/ERC677BridgeForBurnableMintableToken.sol b/contracts/upgradeable_contracts/ERC677BridgeForBurnableMintableToken.sol index f93e8419a..3483626e9 100644 --- a/contracts/upgradeable_contracts/ERC677BridgeForBurnableMintableToken.sol +++ b/contracts/upgradeable_contracts/ERC677BridgeForBurnableMintableToken.sol @@ -6,8 +6,8 @@ import "../IBurnableMintableERC677Token.sol"; contract ERC677BridgeForBurnableMintableToken is ERC677Bridge { - function bridgeSpecificActionsOnTokenTransfer(IBurnableMintableERC677Token _token, address _from, uint256 _value) internal { - _token.burn(_value); + function bridgeSpecificActionsOnTokenTransfer(ERC677 _token, address _from, uint256 _value) internal { + IBurnableMintableERC677Token(_token).burn(_value); fireEventOnTokenTransfer(_from, _value); } } diff --git a/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol b/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol index 6fb99928d..af2b3dbda 100644 --- a/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol +++ b/contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol @@ -61,7 +61,7 @@ contract HomeBridgeErcToErc is ERC677Receiver, EternalStorage, BasicBridge, Basi function onExecuteAffirmation(address _recipient, uint256 _value) internal returns(bool) { setTotalExecutedPerDay(getCurrentDay(), totalExecutedPerDay(getCurrentDay()).add(_value)); - return erc677token().mint(_recipient, _value); + return IBurnableMintableERC677Token(erc677token()).mint(_recipient, _value); } function fireEventOnTokenTransfer(address _from, uint256 _value) internal { diff --git a/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol index 7bdd35ebf..70f1d0c6f 100644 --- a/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol +++ b/contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol @@ -51,12 +51,12 @@ contract ForeignBridgeNativeToErc is ERC677Receiver, BasicBridge, BasicForeignBr } function claimTokensFromErc677(address _token, address _to) external onlyIfOwnerOfProxy { - erc677token().claimTokens(_token, _to); + IBurnableMintableERC677Token(erc677token()).claimTokens(_token, _to); } function onExecuteMessage(address _recipient, uint256 _amount) internal returns(bool){ setTotalExecutedPerDay(getCurrentDay(), totalExecutedPerDay(getCurrentDay()).add(_amount)); - return erc677token().mint(_recipient, _amount); + return IBurnableMintableERC677Token(erc677token()).mint(_recipient, _amount); } function fireEventOnTokenTransfer(address _from, uint256 _value) internal { From be3e9e7928003a13507350f375e0cf15c8653713 Mon Sep 17 00:00:00 2001 From: Alexander Kolotov Date: Fri, 3 May 2019 03:25:00 +0300 Subject: [PATCH 169/187] DEPLOYMENT_GAS_LIMIT_EXTRA is used to calculate a transaction gas limit --- deploy/package.json | 1 + deploy/src/deploymentUtils.js | 24 ++++++++++++++++++++---- deploy/src/loadEnv.js | 2 +- deploy/src/web3.js | 4 ++-- 4 files changed, 24 insertions(+), 7 deletions(-) diff --git a/deploy/package.json b/deploy/package.json index 831552c7e..a37a057b8 100644 --- a/deploy/package.json +++ b/deploy/package.json @@ -10,6 +10,7 @@ "author": "", "license": "ISC", "dependencies": { + "bignumber.js": "^7.2.1", "dotenv": "^5.0.1", "envalid": "^4.1.4", "ethereumjs-tx": "^1.3.4", diff --git a/deploy/src/deploymentUtils.js b/deploy/src/deploymentUtils.js index afa649612..4c5bad926 100644 --- a/deploy/src/deploymentUtils.js +++ b/deploy/src/deploymentUtils.js @@ -1,3 +1,4 @@ +const BigNumber = require('bignumber.js') const Web3 = require('web3') const Tx = require('ethereumjs-tx') const Web3Utils = require('web3-utils') @@ -9,7 +10,7 @@ const { deploymentPrivateKey, FOREIGN_RPC_URL, HOME_RPC_URL, - GAS_LIMIT, + GAS_LIMIT_EXTRA, HOME_DEPLOYMENT_GAS_PRICE, FOREIGN_DEPLOYMENT_GAS_PRICE, GET_RECEIPT_INTERVAL_IN_MILLISECONDS @@ -76,12 +77,24 @@ async function sendRawTx({ data, nonce, to, privateKey, url, gasPrice, value }) to, data } - const estimatedGas = await sendNodeRequest(url, 'eth_estimateGas', txToEstimateGas) + const estimatedGas = BigNumber(await sendNodeRequest(url, 'eth_estimateGas', txToEstimateGas)) + + const blockData = await sendNodeRequest(url, 'eth_getBlockByNumber', ["latest", false]) + const blockGasLimit = BigNumber(blockData.gasLimit) + if (estimatedGas.isGreaterThan(blockGasLimit)) { + throw new Error(`estimated gas greater (${estimatedGas.toString()}) than the block gas limit (${blockGasLimit.toString()})`) + } + let gas = estimatedGas.multipliedBy(BigNumber(1 + GAS_LIMIT_EXTRA)) + if (gas.isGreaterThan(blockGasLimit)) { + gas = blockGasLimit + } else { + gas = gas.toFixed(0) + } const rawTx = { nonce, gasPrice: Web3Utils.toHex(gasPrice), - gasLimit: estimatedGas, + gasLimit: Web3Utils.toHex(gas), to, data, value @@ -104,6 +117,9 @@ async function sendRawTx({ data, nonce, to, privateKey, url, gasPrice, value }) } async function sendNodeRequest(url, method, signedData) { + if (! Array.isArray(signedData)) { + signedData = [signedData] + } const request = await fetch(url, { headers: { 'Content-type': 'application/json' @@ -112,7 +128,7 @@ async function sendNodeRequest(url, method, signedData) { body: JSON.stringify({ jsonrpc: '2.0', method, - params: [signedData], + params: signedData, id: 1 }) }) diff --git a/deploy/src/loadEnv.js b/deploy/src/loadEnv.js index 61733c9fb..93719b5ff 100644 --- a/deploy/src/loadEnv.js +++ b/deploy/src/loadEnv.js @@ -30,7 +30,7 @@ if (!validBridgeModes.includes(BRIDGE_MODE)) { let validations = { DEPLOYMENT_ACCOUNT_PRIVATE_KEY: envalid.str(), - DEPLOYMENT_GAS_LIMIT: bigNumValidator(), + DEPLOYMENT_GAS_LIMIT_EXTRA: envalid.num(), HOME_DEPLOYMENT_GAS_PRICE: bigNumValidator(), FOREIGN_DEPLOYMENT_GAS_PRICE: bigNumValidator(), GET_RECEIPT_INTERVAL_IN_MILLISECONDS: bigNumValidator(), diff --git a/deploy/src/web3.js b/deploy/src/web3.js index b475a1646..685a9daba 100644 --- a/deploy/src/web3.js +++ b/deploy/src/web3.js @@ -15,7 +15,7 @@ const foreignProvider = new Web3.providers.HttpProvider(FOREIGN_RPC_URL) const web3Foreign = new Web3(foreignProvider) const { HOME_DEPLOYMENT_GAS_PRICE, FOREIGN_DEPLOYMENT_GAS_PRICE } = env -const GAS_LIMIT = env.DEPLOYMENT_GAS_LIMIT +const GAS_LIMIT_EXTRA = env.DEPLOYMENT_GAS_LIMIT_EXTRA const deploymentPrivateKey = Buffer.from(DEPLOYMENT_ACCOUNT_PRIVATE_KEY, 'hex') @@ -25,7 +25,7 @@ module.exports = { deploymentPrivateKey, HOME_RPC_URL, FOREIGN_RPC_URL, - GAS_LIMIT, + GAS_LIMIT_EXTRA, HOME_DEPLOYMENT_GAS_PRICE, FOREIGN_DEPLOYMENT_GAS_PRICE, GET_RECEIPT_INTERVAL_IN_MILLISECONDS From f9db683f1cd8f87108d5ec335eb07bc53988bf72 Mon Sep 17 00:00:00 2001 From: Alexander Kolotov Date: Fri, 3 May 2019 03:34:01 +0300 Subject: [PATCH 170/187] documentation update to reflect usage of DEPLOYMENT_GAS_LIMIT_EXTRA --- deploy/.env.example | 2 +- deploy/README.md | 18 ++++++++++++------ 2 files changed, 13 insertions(+), 7 deletions(-) diff --git a/deploy/.env.example b/deploy/.env.example index fd30605a8..e7a05c610 100644 --- a/deploy/.env.example +++ b/deploy/.env.example @@ -1,7 +1,7 @@ #BRIDGE_MODE=ERC_TO_ERC BRIDGE_MODE=NATIVE_TO_ERC DEPLOYMENT_ACCOUNT_PRIVATE_KEY=67..14 -DEPLOYMENT_GAS_LIMIT=5000000 +DEPLOYMENT_GAS_LIMIT_EXTRA=0.2 HOME_DEPLOYMENT_GAS_PRICE=10000000000 FOREIGN_DEPLOYMENT_GAS_PRICE=10000000000 GET_RECEIPT_INTERVAL_IN_MILLISECONDS=3000 diff --git a/deploy/README.md b/deploy/README.md index 48579ef55..442c407ab 100644 --- a/deploy/README.md +++ b/deploy/README.md @@ -36,8 +36,10 @@ BRIDGE_MODE=NATIVE_TO_ERC # deployments and initial configuration. The account's balance must contain # funds from both networks. DEPLOYMENT_ACCOUNT_PRIVATE_KEY=67..14 -# The "gas" parameter set in every deployment/configuration transaction. -DEPLOYMENT_GAS_LIMIT=4000000 +# Extra gas added to the estimated gas of a particular deployment/configuration transaction +# E.g. if estimated gas returns 100000 and the parameter is 0.2, +# the transaction gas limit will be (100000 + 100000 * 0.2) = 120000 +DEPLOYMENT_GAS_LIMIT_EXTRA=0.2 # The "gasPrice" parameter set in every deployment/configuration transaction on # Home network (in Wei). HOME_DEPLOYMENT_GAS_PRICE=10000000000 @@ -152,8 +154,10 @@ BRIDGE_MODE=ERC_TO_ERC # deployments and initial configuration. The account's balance must contain # funds from both networks. DEPLOYMENT_ACCOUNT_PRIVATE_KEY=67..14 -# The "gas" parameter set in every deployment/configuration transaction. -DEPLOYMENT_GAS_LIMIT=4000000 +# Extra gas added to the estimated gas of a particular deployment/configuration transaction +# E.g. if estimated gas returns 100000 and the parameter is 0.2, +# the transaction gas limit will be (100000 + 100000 * 0.2) = 120000 +DEPLOYMENT_GAS_LIMIT_EXTRA=0.2 # The "gasPrice" parameter set in every deployment/configuration transaction on # Home network (in Wei). HOME_DEPLOYMENT_GAS_PRICE=10000000000 @@ -266,8 +270,10 @@ BRIDGE_MODE=ERC_TO_NATIVE # deployments and initial configuration. The account's balance must contain # funds from both networks. DEPLOYMENT_ACCOUNT_PRIVATE_KEY=67..14 -# The "gas" parameter set in every deployment/configuration transaction. -DEPLOYMENT_GAS_LIMIT=4000000 +# Extra gas added to the estimated gas of a particular deployment/configuration transaction +# E.g. if estimated gas returns 100000 and the parameter is 0.2, +# the transaction gas limit will be (100000 + 100000 * 0.2) = 120000 +DEPLOYMENT_GAS_LIMIT_EXTRA=0.2 # The "gasPrice" parameter set in every deployment/configuration transaction on # Home network (in Wei). HOME_DEPLOYMENT_GAS_PRICE=10000000000 From d51914ddfea78bc1f2d84c364566aa4781a092b9 Mon Sep 17 00:00:00 2001 From: varasev <33550681+varasev@users.noreply.github.com> Date: Fri, 3 May 2019 10:34:56 +0300 Subject: [PATCH 171/187] Update ERC677BridgeTokenRewardable.sol Now the `mintReward` function ignores zero amount. --- contracts/ERC677BridgeTokenRewardable.sol | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/contracts/ERC677BridgeTokenRewardable.sol b/contracts/ERC677BridgeTokenRewardable.sol index d12c93482..39155fb38 100644 --- a/contracts/ERC677BridgeTokenRewardable.sol +++ b/contracts/ERC677BridgeTokenRewardable.sol @@ -36,9 +36,12 @@ contract ERC677BridgeTokenRewardable is ERC677BridgeToken { function mintReward(address[] _receivers, uint256[] _rewards) external onlyBlockRewardContract { for (uint256 i = 0; i < _receivers.length; i++) { - address to = _receivers[i]; uint256 amount = _rewards[i]; + if (amount == 0) continue; + + address to = _receivers[i]; + // Mint `amount` for `to` totalSupply_ = totalSupply_.add(amount); balances[to] = balances[to].add(amount); From fb6b0d782199d1d413073479e3b43f72c9199ba9 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Fri, 3 May 2019 14:04:23 -0300 Subject: [PATCH 172/187] Fix merge --- .../erc20_to_erc20/BasicForeignBridgeErcToErc.sol | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/contracts/upgradeable_contracts/erc20_to_erc20/BasicForeignBridgeErcToErc.sol b/contracts/upgradeable_contracts/erc20_to_erc20/BasicForeignBridgeErcToErc.sol index f9238e51e..c59d85748 100644 --- a/contracts/upgradeable_contracts/erc20_to_erc20/BasicForeignBridgeErcToErc.sol +++ b/contracts/upgradeable_contracts/erc20_to_erc20/BasicForeignBridgeErcToErc.sol @@ -44,7 +44,7 @@ contract BasicForeignBridgeErcToErc is BasicBridge, BasicForeignBridge { super.claimTokens(_token, _to); } - function onExecuteMessage(address _recipient, uint256 _amount) internal returns(bool){ + function onExecuteMessage(address _recipient, uint256 _amount, bytes32 _txHash) internal returns(bool){ setTotalExecutedPerDay(getCurrentDay(), totalExecutedPerDay(getCurrentDay()).add(_amount)); return erc20token().transfer(_recipient, _amount); } From f30a1da139ef64d115de574d4c278d7a7c18edc4 Mon Sep 17 00:00:00 2001 From: Alexander Kolotov Date: Fri, 3 May 2019 20:14:06 +0300 Subject: [PATCH 173/187] flattening sources of the new set of contracts --- flatten.sh | 39 ++++++++++++++++++++++++++++++--------- 1 file changed, 30 insertions(+), 9 deletions(-) diff --git a/flatten.sh b/flatten.sh index 1f1fe20da..0b3fc9241 100755 --- a/flatten.sh +++ b/flatten.sh @@ -7,16 +7,37 @@ fi mkdir -p flats/native_to_erc20 mkdir -p flats/erc20_to_erc20 mkdir -p flats/erc20_to_native +mkdir -p flats/validators -./node_modules/.bin/truffle-flattener contracts/upgradeable_contracts/native_to_erc20/ForeignBridgeNativeToErc.sol > flats/native_to_erc20/ForeignBridgeNativeToErc_flat.sol -./node_modules/.bin/truffle-flattener contracts/upgradeable_contracts/native_to_erc20/HomeBridgeNativeToErc.sol > flats/native_to_erc20/HomeBridgeNativeToErc_flat.sol +FLATTENER=./node_modules/.bin/truffle-flattener +BRIDGE_CONTRACTS_DIR=contracts/upgradeable_contracts +VALIDATOR_CONTRACTS_DIR=contracts/upgradeable_contracts -./node_modules/.bin/truffle-flattener contracts/upgradeable_contracts/erc20_to_erc20/HomeBridgeErcToErc.sol > flats/erc20_to_erc20/HomeBridgeErcToErc_flat.sol -./node_modules/.bin/truffle-flattener contracts/upgradeable_contracts/erc20_to_erc20/ForeignBridgeErcToErc.sol > flats/erc20_to_erc20/ForeignBridgeErcToErc_flat.sol +echo "Flattening common bridge contracts" +${FLATTENER} contracts/upgradeability/EternalStorageProxy.sol > flats/EternalStorageProxy_flat.sol +${FLATTENER} contracts/ERC677BridgeToken.sol > flats/ERC677BridgeToken_flat.sol +${FLATTENER} contracts/ERC677BridgeTokenRewardable.sol > flats/ERC677BridgeTokenRewardable_flat.sol + +echo "Flattening bridge validators contracts" +${FLATTENER} ${VALIDATOR_CONTRACTS_DIR}/BridgeValidators.sol > flats/validators/BridgeValidators_flat.sol +${FLATTENER} ${VALIDATOR_CONTRACTS_DIR}/RewardableValidators.sol > flats/validators/RewardableValidators_flat.sol + +echo "Flattening contracts related to native-to-erc bridge" +${FLATTENER} ${BRIDGE_CONTRACTS_DIR}/native_to_erc20/ForeignBridgeNativeToErc.sol > flats/native_to_erc20/ForeignBridgeNativeToErc_flat.sol +${FLATTENER} ${BRIDGE_CONTRACTS_DIR}/native_to_erc20/HomeBridgeNativeToErc.sol > flats/native_to_erc20/HomeBridgeNativeToErc_flat.sol +${FLATTENER} ${BRIDGE_CONTRACTS_DIR}/native_to_erc20/FeeManagerNativeToErc.sol > flats/native_to_erc20/FeeManagerNativeToErc_flat.sol +${FLATTENER} ${BRIDGE_CONTRACTS_DIR}/native_to_erc20/FeeManagerNativeToErcBothDirections.sol > flats/native_to_erc20/FeeManagerNativeToErcBothDirections_flat.sol + +echo "Flattening contracts related to erc-to-erc bridge" +${FLATTENER} ${BRIDGE_CONTRACTS_DIR}/erc20_to_erc20/HomeBridgeErcToErc.sol > flats/erc20_to_erc20/HomeBridgeErcToErc_flat.sol +${FLATTENER} ${BRIDGE_CONTRACTS_DIR}/erc20_to_erc20/POSDAOHomeBridgeErcToErc.sol > flats/erc20_to_erc20/POSDAOHomeBridgeErcToErc_flat.sol +${FLATTENER} ${BRIDGE_CONTRACTS_DIR}/erc20_to_erc20/ForeignBridgeErcToErc.sol > flats/erc20_to_erc20/ForeignBridgeErcToErc_flat.sol +${FLATTENER} ${BRIDGE_CONTRACTS_DIR}/erc20_to_erc20/FeeManagerErcToErcPOSDAO.sol > flats/erc20_to_erc20/FeeManagerErcToErcPOSDAO_flat.sol + +echo "Flattening contracts related to erc-to-native bridge" +${FLATTENER} ${BRIDGE_CONTRACTS_DIR}/erc20_to_native/HomeBridgeErcToNative.sol > flats/erc20_to_native/HomeBridgeErcToNative_flat.sol +${FLATTENER} ${BRIDGE_CONTRACTS_DIR}/erc20_to_native/ForeignBridgeErcToNative.sol > flats/erc20_to_native/ForeignBridgeErcToNative_flat.sol +${FLATTENER} ${BRIDGE_CONTRACTS_DIR}/erc20_to_native/FeeManagerErcToNative.sol > flats/erc20_to_native/FeeManagerErcToNative_flat.sol +${FLATTENER} ${BRIDGE_CONTRACTS_DIR}/erc20_to_native/FeeManagerErcToNativePOSDAO.sol > flats/erc20_to_native/FeeManagerErcToNativePOSDAO_flat.sol -./node_modules/.bin/truffle-flattener contracts/upgradeable_contracts/erc20_to_native/HomeBridgeErcToNative.sol > flats/erc20_to_native/HomeBridgeErcToNative_flat.sol -./node_modules/.bin/truffle-flattener contracts/upgradeable_contracts/erc20_to_native/ForeignBridgeErcToNative.sol > flats/erc20_to_native/ForeignBridgeErcToNative_flat.sol -./node_modules/.bin/truffle-flattener contracts/upgradeability/EternalStorageProxy.sol > flats/EternalStorageProxy_flat.sol -./node_modules/.bin/truffle-flattener contracts/upgradeable_contracts/BridgeValidators.sol > flats/BridgeValidators_flat.sol -./node_modules/.bin/truffle-flattener contracts/ERC677BridgeToken.sol > flats/ERC677BridgeToken_flat.sol From 92be48b052c648e2d7975eb32622a0fe600c171d Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Fri, 3 May 2019 14:20:23 -0300 Subject: [PATCH 174/187] Fix merge deploy script --- deploy/src/deploymentUtils.js | 31 ++++++++++++++++--------------- deploy/src/erc_to_erc/foreign.js | 8 ++++---- 2 files changed, 20 insertions(+), 19 deletions(-) diff --git a/deploy/src/deploymentUtils.js b/deploy/src/deploymentUtils.js index 32b825698..c08b48368 100644 --- a/deploy/src/deploymentUtils.js +++ b/deploy/src/deploymentUtils.js @@ -72,18 +72,20 @@ async function sendRawTxForeign(options) { async function sendRawTx({ data, nonce, to, privateKey, url, gasPrice, value }) { try { - const txToEstimateGas = { - from: privateKeyToAddress(Web3Utils.bytesToHex(privateKey)), - value: value, - to, - data + const txToEstimateGas = { + from: privateKeyToAddress(Web3Utils.bytesToHex(privateKey)), + value, + to, + data } const estimatedGas = BigNumber(await sendNodeRequest(url, 'eth_estimateGas', txToEstimateGas)) - - const blockData = await sendNodeRequest(url, 'eth_getBlockByNumber', ["latest", false]) + + const blockData = await sendNodeRequest(url, 'eth_getBlockByNumber', ['latest', false]) const blockGasLimit = BigNumber(blockData.gasLimit) if (estimatedGas.isGreaterThan(blockGasLimit)) { - throw new Error(`estimated gas greater (${estimatedGas.toString()}) than the block gas limit (${blockGasLimit.toString()})`) + throw new Error( + `estimated gas greater (${estimatedGas.toString()}) than the block gas limit (${blockGasLimit.toString()})` + ) } let gas = estimatedGas.multipliedBy(BigNumber(1 + GAS_LIMIT_EXTRA)) if (gas.isGreaterThan(blockGasLimit)) { @@ -117,7 +119,7 @@ async function sendRawTx({ data, nonce, to, privateKey, url, gasPrice, value }) } async function sendNodeRequest(url, method, signedData) { - if (! Array.isArray(signedData)) { + if (!Array.isArray(signedData)) { signedData = [signedData] } const request = await fetch(url, { @@ -134,13 +136,12 @@ async function sendNodeRequest(url, method, signedData) { }) const json = await request.json() if (typeof json.error === 'undefined' || json.error === null) { - if (method === 'eth_sendRawTransaction') { - assert.strictEqual(json.result.length, 66, `Tx wasn't sent ${json}`) - } - return json.result - } else { - throw new Error(`web3 RPC failed: ${JSON.stringify(json.error)}`) + if (method === 'eth_sendRawTransaction') { + assert.strictEqual(json.result.length, 66, `Tx wasn't sent ${json}`) + } + return json.result } + throw new Error(`web3 RPC failed: ${JSON.stringify(json.error)}`) } function timeout(ms) { diff --git a/deploy/src/erc_to_erc/foreign.js b/deploy/src/erc_to_erc/foreign.js index ce9704c4b..c66fbf6dc 100644 --- a/deploy/src/erc_to_erc/foreign.js +++ b/deploy/src/erc_to_erc/foreign.js @@ -55,9 +55,9 @@ async function initializeBridge({ validatorsBridge, bridge, nonce }) { let initializeFBridgeData if (ERC20_EXTENDED_BY_ERC677) { - initializeFBridgeData = await foreignBridgeImplementation.methods + initializeFBridgeData = await bridge.methods .initialize( - storageValidatorsForeign.options.address, + validatorsBridge.options.address, ERC20_TOKEN_ADDRESS, FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS, FOREIGN_GAS_PRICE, @@ -70,9 +70,9 @@ async function initializeBridge({ validatorsBridge, bridge, nonce }) { ) .encodeABI() } else { - initializeFBridgeData = await foreignBridgeImplementation.methods + initializeFBridgeData = await bridge.methods .initialize( - storageValidatorsForeign.options.address, + validatorsBridge.options.address, ERC20_TOKEN_ADDRESS, FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS, FOREIGN_GAS_PRICE, From d69f8f48ecb3e252b969e08985a1d3f66c6ff088 Mon Sep 17 00:00:00 2001 From: Alexander Kolotov Date: Fri, 3 May 2019 20:38:46 +0300 Subject: [PATCH 175/187] flattening of the new contract related to erc677-to-erc677 bridge mode --- flatten.sh | 1 + 1 file changed, 1 insertion(+) diff --git a/flatten.sh b/flatten.sh index 0b3fc9241..532f90e2d 100755 --- a/flatten.sh +++ b/flatten.sh @@ -32,6 +32,7 @@ echo "Flattening contracts related to erc-to-erc bridge" ${FLATTENER} ${BRIDGE_CONTRACTS_DIR}/erc20_to_erc20/HomeBridgeErcToErc.sol > flats/erc20_to_erc20/HomeBridgeErcToErc_flat.sol ${FLATTENER} ${BRIDGE_CONTRACTS_DIR}/erc20_to_erc20/POSDAOHomeBridgeErcToErc.sol > flats/erc20_to_erc20/POSDAOHomeBridgeErcToErc_flat.sol ${FLATTENER} ${BRIDGE_CONTRACTS_DIR}/erc20_to_erc20/ForeignBridgeErcToErc.sol > flats/erc20_to_erc20/ForeignBridgeErcToErc_flat.sol +${FLATTENER} ${BRIDGE_CONTRACTS_DIR}/erc20_to_erc20/ForeignBridgeErc677ToErc677.sol > flats/erc20_to_erc20/ForeignBridgeErc677ToErc677_flat.sol ${FLATTENER} ${BRIDGE_CONTRACTS_DIR}/erc20_to_erc20/FeeManagerErcToErcPOSDAO.sol > flats/erc20_to_erc20/FeeManagerErcToErcPOSDAO_flat.sol echo "Flattening contracts related to erc-to-native bridge" From 964d1049584ea84f5cabc92a7bbd3a6d1daa4e1d Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 8 May 2019 09:09:10 -0300 Subject: [PATCH 176/187] Apply contract changes from `develop-for-classic` --- contracts/IRewardableValidators.sol | 2 ++ .../ClassicEternalStorageProxy.sol | 31 +++++++++++++++++ .../ValidatorsFeeManager.sol | 23 +++++++++---- .../ClassicHomeBridgeNativeToErc.sol | 34 +++++++++++++++++++ 4 files changed, 84 insertions(+), 6 deletions(-) create mode 100644 contracts/upgradeability/ClassicEternalStorageProxy.sol create mode 100644 contracts/upgradeable_contracts/native_to_erc20/ClassicHomeBridgeNativeToErc.sol diff --git a/contracts/IRewardableValidators.sol b/contracts/IRewardableValidators.sol index 5240c5d0a..4c753f338 100644 --- a/contracts/IRewardableValidators.sol +++ b/contracts/IRewardableValidators.sol @@ -7,4 +7,6 @@ interface IRewardableValidators { function owner() public view returns(address); function validatorList() public view returns (address[]); function getValidatorRewardAddress(address _validator) public view returns(address); + function validatorCount() public view returns (uint256); + function getNextValidator(address _address) public view returns (address); } diff --git a/contracts/upgradeability/ClassicEternalStorageProxy.sol b/contracts/upgradeability/ClassicEternalStorageProxy.sol new file mode 100644 index 000000000..d01770389 --- /dev/null +++ b/contracts/upgradeability/ClassicEternalStorageProxy.sol @@ -0,0 +1,31 @@ +pragma solidity 0.4.24; + +import "./EternalStorage.sol"; +import "./OwnedUpgradeabilityProxy.sol"; + + +contract ClassicEternalStorageProxy is EternalStorage, OwnedUpgradeabilityProxy { + + function () payable public { + address _impl = implementation(); + require(_impl != address(0)); + uint256 len = getSize(msg.sig); + assembly { + let ptr := mload(0x40) + calldatacopy(ptr, 0, calldatasize) + let result := delegatecall(gas, _impl, ptr, calldatasize, 0, len) + + switch result + case 0 { revert(0, len) } + default { return(0, len) } + } + } + + function getSize(bytes4 sig) public view returns(uint256) { + uint256 ret = uintStorage[keccak256(abi.encodePacked("dataSizes", sig))]; + if (ret == 0) { + ret = 32; + } + return ret; + } +} diff --git a/contracts/upgradeable_contracts/ValidatorsFeeManager.sol b/contracts/upgradeable_contracts/ValidatorsFeeManager.sol index 0f7f32b0d..705d99b3c 100644 --- a/contracts/upgradeable_contracts/ValidatorsFeeManager.sol +++ b/contracts/upgradeable_contracts/ValidatorsFeeManager.sol @@ -23,22 +23,33 @@ contract ValidatorsFeeManager is BaseFeeManager { function distributeFeeProportionally(uint256 _fee, bytes32 _direction) internal { IRewardableValidators validators = rewardableValidatorContract(); - address[] memory validatorList = validators.validatorList(); - uint256 feePerValidator = _fee.div(validatorList.length); + address F_ADDR = 0xFFfFfFffFFfffFFfFFfFFFFFffFFFffffFfFFFfF; + uint256 numOfValidators = validators.validatorCount(); + + uint256 feePerValidator = _fee.div(numOfValidators); uint256 randomValidatorIndex; - uint256 diff = _fee.sub(feePerValidator.mul(validatorList.length)); + uint256 diff = _fee.sub(feePerValidator.mul(numOfValidators)); if (diff > 0) { - randomValidatorIndex = random(validatorList.length); + randomValidatorIndex = random(numOfValidators); } - for (uint256 i = 0; i < validatorList.length; i++) { + address nextValidator = validators.getNextValidator(F_ADDR); + require((nextValidator != F_ADDR) && (nextValidator != address(0))); + + uint256 i = 0; + while (nextValidator != F_ADDR) { uint256 feeToDistribute = feePerValidator; if (diff > 0 && randomValidatorIndex == i) { feeToDistribute = feeToDistribute.add(diff); } - address rewardAddress = validators.getValidatorRewardAddress(validatorList[i]); + + address rewardAddress = validators.getValidatorRewardAddress(nextValidator); onFeeDistribution(rewardAddress, feeToDistribute, _direction); + + nextValidator = validators.getNextValidator(nextValidator); + require(nextValidator != address(0)); + i = i + 1; } } diff --git a/contracts/upgradeable_contracts/native_to_erc20/ClassicHomeBridgeNativeToErc.sol b/contracts/upgradeable_contracts/native_to_erc20/ClassicHomeBridgeNativeToErc.sol new file mode 100644 index 000000000..cea6ba5c3 --- /dev/null +++ b/contracts/upgradeable_contracts/native_to_erc20/ClassicHomeBridgeNativeToErc.sol @@ -0,0 +1,34 @@ +pragma solidity 0.4.24; + +import "./HomeBridgeNativeToErc.sol"; + + +contract ClassicHomeBridgeNativeToErc is HomeBridgeNativeToErc { + + function _initialize ( + address _validatorContract, + uint256 _dailyLimit, + uint256 _maxPerTx, + uint256 _minPerTx, + uint256 _homeGasPrice, + uint256 _requiredBlockConfirmations, + uint256 _foreignDailyLimit, + uint256 _foreignMaxPerTx, + address _owner + ) internal + { + super._initialize( + _validatorContract, + _dailyLimit, + _maxPerTx, + _minPerTx, + _homeGasPrice, + _requiredBlockConfirmations, + _foreignDailyLimit, + _foreignMaxPerTx, + _owner + ); + uintStorage[keccak256(abi.encodePacked("dataSizes", bytes4(keccak256("signature(bytes32,uint256)"))))] = 132; + uintStorage[keccak256(abi.encodePacked("dataSizes", bytes4(keccak256("message(bytes32)"))))] = 210; + } +} From d5139e164a4c66cb1641806b17f53424a69f1af3 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 8 May 2019 10:42:57 -0300 Subject: [PATCH 177/187] Upgrade truffle version --- package-lock.json | 272 +++++++++++++++++++++++++++++++++++----------- package.json | 2 +- truffle-config.js | 36 +++++- truffle.js | 63 ----------- 4 files changed, 245 insertions(+), 128 deletions(-) delete mode 100644 truffle.js diff --git a/package-lock.json b/package-lock.json index 8301e96f5..988489394 100644 --- a/package-lock.json +++ b/package-lock.json @@ -195,6 +195,11 @@ } } }, + "app-module-path": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/app-module-path/-/app-module-path-2.2.0.tgz", + "integrity": "sha1-ZBqlXft9am8KgUHEucCqULbCTdU=" + }, "argparse": { "version": "1.0.10", "resolved": "https://registry.npmjs.org/argparse/-/argparse-1.0.10.tgz", @@ -381,6 +386,14 @@ "integrity": "sha512-Un7MIEDdUC5gNpcGDV97op1Ywk748MpHcFTHoYs6qnj1Z3j7I53VG3nwZhKzoBZmbdRNnb6WRdFlwl7tSDuZGw==", "dev": true }, + "bindings": { + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/bindings/-/bindings-1.5.0.tgz", + "integrity": "sha512-p2q/t/mhvuOj/UeLlV6566GD/guowlr0hHxClI0W9m7MWYkL1F0hLo+0Aexs9HSPCtR1SXQ0TD3MMKrXZajbiQ==", + "requires": { + "file-uri-to-path": "1.0.0" + } + }, "bn.js": { "version": "4.11.6", "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.11.6.tgz", @@ -560,7 +573,8 @@ "camelcase": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-3.0.0.tgz", - "integrity": "sha1-MvxLn82vhF/N9+c7uXysImHwqwo=" + "integrity": "sha1-MvxLn82vhF/N9+c7uXysImHwqwo=", + "dev": true }, "capture-stack-trace": { "version": "1.0.1", @@ -745,6 +759,7 @@ "version": "3.2.0", "resolved": "https://registry.npmjs.org/cliui/-/cliui-3.2.0.tgz", "integrity": "sha1-EgYBU3qRbSmUD5NNo7SNWFo5IT0=", + "dev": true, "requires": { "string-width": "^1.0.1", "strip-ansi": "^3.0.1", @@ -890,7 +905,6 @@ "version": "5.1.0", "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-5.1.0.tgz", "integrity": "sha1-6L0O/uWPz/b4+UUQoKVUu/ojVEk=", - "dev": true, "requires": { "lru-cache": "^4.0.1", "shebang-command": "^1.2.0", @@ -1102,6 +1116,7 @@ "version": "1.3.2", "resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.2.tgz", "integrity": "sha512-7dFHNmqeFSEt2ZBsCriorKnn3Z2pj+fd9kmI6QoWw4//DL+icEBfc0U7qJCisqrTsKTjw4fNFy2pW9OqStD84g==", + "dev": true, "requires": { "is-arrayish": "^0.2.1" } @@ -1243,7 +1258,6 @@ "version": "0.7.0", "resolved": "https://registry.npmjs.org/execa/-/execa-0.7.0.tgz", "integrity": "sha1-lEvs00zEHuMqY6n68nrVpl/Fl3c=", - "dev": true, "requires": { "cross-spawn": "^5.0.1", "get-stream": "^3.0.0", @@ -1462,6 +1476,11 @@ "integrity": "sha1-PYpcZog6FqMMqGQ+hR8Zuqd5eRc=", "dev": true }, + "file-uri-to-path": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/file-uri-to-path/-/file-uri-to-path-1.0.0.tgz", + "integrity": "sha512-0Zt+s3L7Vf1biwWZ29aARiVYLx7iMGnEUl9x33fbB/j3jR81u/O2LbqK+Bm1CDSNDKVtJ/YjwY7TUd5SkeLQLw==" + }, "fill-range": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/fill-range/-/fill-range-4.0.0.tgz", @@ -1518,6 +1537,7 @@ "version": "1.1.2", "resolved": "https://registry.npmjs.org/find-up/-/find-up-1.1.2.tgz", "integrity": "sha1-ay6YIrGizgpgq2TWEOzK1TyyTQ8=", + "dev": true, "requires": { "path-exists": "^2.0.0", "pinkie-promise": "^2.0.0" @@ -2520,8 +2540,7 @@ "get-stream": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-3.0.0.tgz", - "integrity": "sha1-jpQ9E1jcN1VQVOy+LtsFqhdO3hQ=", - "dev": true + "integrity": "sha1-jpQ9E1jcN1VQVOy+LtsFqhdO3hQ=" }, "get-value": { "version": "2.0.6", @@ -2729,7 +2748,8 @@ "hosted-git-info": { "version": "2.7.1", "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-2.7.1.tgz", - "integrity": "sha512-7T/BxH19zbcCTa8XkMlbK5lTo1WtgkFi3GvdWEyNuc4Vex7/9Dqbnpsf4JMydcfj9HCg4zUWFTL3Za6lapg5/w==" + "integrity": "sha512-7T/BxH19zbcCTa8XkMlbK5lTo1WtgkFi3GvdWEyNuc4Vex7/9Dqbnpsf4JMydcfj9HCg4zUWFTL3Za6lapg5/w==", + "dev": true }, "http-basic": { "version": "8.1.1", @@ -2858,7 +2878,8 @@ "is-arrayish": { "version": "0.2.1", "resolved": "https://registry.npmjs.org/is-arrayish/-/is-arrayish-0.2.1.tgz", - "integrity": "sha1-d8mYQFJ6qOyxqLppe4BkWnqSap0=" + "integrity": "sha1-d8mYQFJ6qOyxqLppe4BkWnqSap0=", + "dev": true }, "is-binary-path": { "version": "1.0.1", @@ -3055,8 +3076,7 @@ "is-stream": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-1.1.0.tgz", - "integrity": "sha1-EtSj3U5o4Lec6428hBc66A2RykQ=", - "dev": true + "integrity": "sha1-EtSj3U5o4Lec6428hBc66A2RykQ=" }, "is-symbol": { "version": "1.0.2", @@ -3074,7 +3094,8 @@ "is-utf8": { "version": "0.2.1", "resolved": "https://registry.npmjs.org/is-utf8/-/is-utf8-0.2.1.tgz", - "integrity": "sha1-Sw2hRCEE0bM2NA6AeX6GXPOffXI=" + "integrity": "sha1-Sw2hRCEE0bM2NA6AeX6GXPOffXI=", + "dev": true }, "is-windows": { "version": "1.0.2", @@ -3091,8 +3112,7 @@ "isexe": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", - "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=", - "dev": true + "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=" }, "isobject": { "version": "3.0.1", @@ -3240,6 +3260,17 @@ "verror": "1.10.0" } }, + "keccak": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/keccak/-/keccak-1.4.0.tgz", + "integrity": "sha512-eZVaCpblK5formjPjeTBik7TAg+pqnDrMHIffSvi9Lh7PQgM1+hSzakUeZFCk9DVVG0dacZJuaz2ntwlzZUIBw==", + "requires": { + "bindings": "^1.2.1", + "inherits": "^2.0.3", + "nan": "^2.2.1", + "safe-buffer": "^5.1.0" + } + }, "keccakjs": { "version": "0.2.3", "resolved": "https://registry.npmjs.org/keccakjs/-/keccakjs-0.2.3.tgz", @@ -3294,6 +3325,7 @@ "version": "1.1.0", "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-1.1.0.tgz", "integrity": "sha1-lWkFcI1YtLq0wiYbBPWfMcmTdMA=", + "dev": true, "requires": { "graceful-fs": "^4.1.2", "parse-json": "^2.2.0", @@ -3306,7 +3338,6 @@ "version": "2.0.0", "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-2.0.0.tgz", "integrity": "sha1-K1aLJl7slExtnA3pw9u7ygNUzY4=", - "dev": true, "requires": { "p-locate": "^2.0.0", "path-exists": "^3.0.0" @@ -3315,8 +3346,7 @@ "path-exists": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", - "integrity": "sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=", - "dev": true + "integrity": "sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=" } } }, @@ -3329,7 +3359,8 @@ "lodash.assign": { "version": "4.2.0", "resolved": "https://registry.npmjs.org/lodash.assign/-/lodash.assign-4.2.0.tgz", - "integrity": "sha1-DZnzzNem0mHRm9rrkkUAXShYCOc=" + "integrity": "sha1-DZnzzNem0mHRm9rrkkUAXShYCOc=", + "dev": true }, "lowercase-keys": { "version": "1.0.1", @@ -3341,7 +3372,6 @@ "version": "4.1.5", "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-4.1.5.tgz", "integrity": "sha512-sWZlbEP2OsHNkXrMl5GYk/jKk70MBng6UU4YI/qGDYbgf6YbP4EvmqISbXCoJiRKs+1bSpFHVgQxvJ17F2li5g==", - "dev": true, "requires": { "pseudomap": "^1.0.2", "yallist": "^2.1.2" @@ -3384,6 +3414,14 @@ "resolved": "https://registry.npmjs.org/media-typer/-/media-typer-0.3.0.tgz", "integrity": "sha1-hxDXrwqmJvj/+hzgAWhUUmMlV0g=" }, + "mem": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/mem/-/mem-1.1.0.tgz", + "integrity": "sha1-Xt1StIXKHZAP5kiVUFOZoN+kX3Y=", + "requires": { + "mimic-fn": "^1.0.0" + } + }, "memorystream": { "version": "0.3.1", "resolved": "https://registry.npmjs.org/memorystream/-/memorystream-0.3.1.tgz", @@ -3438,6 +3476,11 @@ "mime-db": "~1.38.0" } }, + "mimic-fn": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-1.2.0.tgz", + "integrity": "sha512-jf84uxzwiuiIVKiOLpfYk7N46TSy8ubTonmneY9vrpHNAnp0QBt2BxWV9dO3/j+BoVAb+a5G6YDPW3M5HOdMWQ==" + }, "mimic-response": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-1.0.1.tgz", @@ -3613,6 +3656,7 @@ "version": "2.5.0", "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-2.5.0.tgz", "integrity": "sha512-/5CMN3T0R4XTj4DcGaexo+roZSdSFW/0AOOTROrjxzCG1wrWXEsGbRKevjlIL+ZDE4sZlJr5ED4YW0yqmkK+eA==", + "dev": true, "requires": { "hosted-git-info": "^2.1.4", "resolve": "^1.10.0", @@ -3630,7 +3674,6 @@ "version": "2.0.2", "resolved": "https://registry.npmjs.org/npm-run-path/-/npm-run-path-2.0.2.tgz", "integrity": "sha1-NakjLfo11wZ7TLLd8jV7GHFTbF8=", - "dev": true, "requires": { "path-key": "^2.0.0" } @@ -3775,6 +3818,7 @@ "version": "1.4.0", "resolved": "https://registry.npmjs.org/os-locale/-/os-locale-1.4.0.tgz", "integrity": "sha1-IPnxeuKe00XoveWDsT0gCYA8FNk=", + "dev": true, "requires": { "lcid": "^1.0.0" } @@ -3782,14 +3826,12 @@ "p-finally": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/p-finally/-/p-finally-1.0.0.tgz", - "integrity": "sha1-P7z7FbiZpEEjs0ttzBi3JDNqLK4=", - "dev": true + "integrity": "sha1-P7z7FbiZpEEjs0ttzBi3JDNqLK4=" }, "p-limit": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-1.3.0.tgz", "integrity": "sha512-vvcXsLAJ9Dr5rQOPk7toZQZJApBl2K4J6dANSsEuh6QI41JYcsS/qhTGa9ErIUUgK3WNQoJYvylxvjqmiqEA9Q==", - "dev": true, "requires": { "p-try": "^1.0.0" } @@ -3798,7 +3840,6 @@ "version": "2.0.0", "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-2.0.0.tgz", "integrity": "sha1-IKAQOyIqcMj9OcwuWAaA893l7EM=", - "dev": true, "requires": { "p-limit": "^1.1.0" } @@ -3806,8 +3847,7 @@ "p-try": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/p-try/-/p-try-1.0.0.tgz", - "integrity": "sha1-y8ec26+P1CKOE/Yh8rGiN8GyB7M=", - "dev": true + "integrity": "sha1-y8ec26+P1CKOE/Yh8rGiN8GyB7M=" }, "package-json": { "version": "4.0.1", @@ -3840,6 +3880,7 @@ "version": "2.2.0", "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-2.2.0.tgz", "integrity": "sha1-9ID0BDTvgHQfhGkJn43qGPVaTck=", + "dev": true, "requires": { "error-ex": "^1.2.0" } @@ -3865,6 +3906,7 @@ "version": "2.1.0", "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-2.1.0.tgz", "integrity": "sha1-D+tsZPD8UY2adU3V77YscCJ2H0s=", + "dev": true, "requires": { "pinkie-promise": "^2.0.0" } @@ -3883,13 +3925,13 @@ "path-key": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/path-key/-/path-key-2.0.1.tgz", - "integrity": "sha1-QRyttXTFoUDTpLGRDUDYDMn0C0A=", - "dev": true + "integrity": "sha1-QRyttXTFoUDTpLGRDUDYDMn0C0A=" }, "path-parse": { "version": "1.0.6", "resolved": "https://registry.npmjs.org/path-parse/-/path-parse-1.0.6.tgz", - "integrity": "sha512-GSmOT2EbHrINBf9SR7CDELwlJ8AENk3Qn7OikK4nFYAu3Ote2+JYNVvkpAEQm3/TLNEJFD/xZJjzyxg3KBWOzw==" + "integrity": "sha512-GSmOT2EbHrINBf9SR7CDELwlJ8AENk3Qn7OikK4nFYAu3Ote2+JYNVvkpAEQm3/TLNEJFD/xZJjzyxg3KBWOzw==", + "dev": true }, "path-to-regexp": { "version": "0.1.7", @@ -3900,6 +3942,7 @@ "version": "1.1.0", "resolved": "https://registry.npmjs.org/path-type/-/path-type-1.1.0.tgz", "integrity": "sha1-WcRPfuSR2nBNpBXaWkBwuk+P5EE=", + "dev": true, "requires": { "graceful-fs": "^4.1.2", "pify": "^2.0.0", @@ -3926,17 +3969,20 @@ "pify": { "version": "2.3.0", "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", - "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=" + "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=", + "dev": true }, "pinkie": { "version": "2.0.4", "resolved": "https://registry.npmjs.org/pinkie/-/pinkie-2.0.4.tgz", - "integrity": "sha1-clVrgM+g1IqXToDnckjoDtT3+HA=" + "integrity": "sha1-clVrgM+g1IqXToDnckjoDtT3+HA=", + "dev": true }, "pinkie-promise": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/pinkie-promise/-/pinkie-promise-2.0.1.tgz", "integrity": "sha1-ITXW36ejWMBprJsXh3YogihFD/o=", + "dev": true, "requires": { "pinkie": "^2.0.0" } @@ -3991,8 +4037,7 @@ "pseudomap": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/pseudomap/-/pseudomap-1.0.2.tgz", - "integrity": "sha1-8FKijacOYYkX7wqKw0wa5aaChrM=", - "dev": true + "integrity": "sha1-8FKijacOYYkX7wqKw0wa5aaChrM=" }, "psl": { "version": "1.1.31", @@ -4070,6 +4115,7 @@ "version": "1.1.0", "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-1.1.0.tgz", "integrity": "sha1-9f+qXs0pyzHAR0vKfXVra7KePyg=", + "dev": true, "requires": { "load-json-file": "^1.0.0", "normalize-package-data": "^2.3.2", @@ -4080,6 +4126,7 @@ "version": "1.0.1", "resolved": "https://registry.npmjs.org/read-pkg-up/-/read-pkg-up-1.0.1.tgz", "integrity": "sha1-nWPBMnbAZZGNV/ACpX9AobZD+wI=", + "dev": true, "requires": { "find-up": "^1.0.0", "read-pkg": "^1.0.0" @@ -4238,9 +4285,9 @@ "integrity": "sha1-jGStX9MNqxyXbiNE/+f3kqam30I=" }, "require-from-string": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/require-from-string/-/require-from-string-1.2.1.tgz", - "integrity": "sha1-UpyczvJzgK3+yaL5ZbZJu+5jZBg=" + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/require-from-string/-/require-from-string-2.0.2.tgz", + "integrity": "sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==" }, "require-main-filename": { "version": "1.0.1", @@ -4251,6 +4298,7 @@ "version": "1.10.0", "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.10.0.tgz", "integrity": "sha512-3sUr9aq5OfSg2S9pNtPA9hL1FVEAjvfOC4leW0SNf/mpnaakz2a9femSd6LqAww2RaFctwyf1lCqnTHuF1rxDg==", + "dev": true, "requires": { "path-parse": "^1.0.6" } @@ -4282,9 +4330,9 @@ }, "dependencies": { "glob": { - "version": "7.1.3", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.3.tgz", - "integrity": "sha512-vcfuiIxogLV4DlGBHIUOwI0IbrJ8HWPc4MU7HzviGeNho/UJDfi6B5p3sHeWIQ0KGIU0Jpxi5ZHxemQfLkkAwQ==", + "version": "7.1.4", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.4.tgz", + "integrity": "sha512-hkLPepehmnKk41pUGm3sYxoFs/umurYfYJCerbXEyFIWcAzvpipAgVkBqqT9RBKMGjnq6kMuyYwha6csxbiM1A==", "requires": { "fs.realpath": "^1.0.0", "inflight": "^1.0.4", @@ -4442,7 +4490,6 @@ "version": "1.2.0", "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-1.2.0.tgz", "integrity": "sha1-RKrGW2lbAzmJaMOfNj/uXer98eo=", - "dev": true, "requires": { "shebang-regex": "^1.0.0" } @@ -4450,8 +4497,7 @@ "shebang-regex": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-1.0.0.tgz", - "integrity": "sha1-2kL0l0DAtC2yypcoVxyxkMmO/qM=", - "dev": true + "integrity": "sha1-2kL0l0DAtC2yypcoVxyxkMmO/qM=" }, "shelljs": { "version": "0.7.8", @@ -4467,8 +4513,7 @@ "signal-exit": { "version": "3.0.2", "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.2.tgz", - "integrity": "sha1-tf3AjxKH6hF4Yo5BXiUTK3NkbG0=", - "dev": true + "integrity": "sha1-tf3AjxKH6hF4Yo5BXiUTK3NkbG0=" }, "simple-concat": { "version": "1.0.0", @@ -4608,15 +4653,110 @@ "dev": true }, "solc": { - "version": "0.4.24", - "resolved": "https://registry.npmjs.org/solc/-/solc-0.4.24.tgz", - "integrity": "sha512-2xd7Cf1HeVwrIb6Bu1cwY2/TaLRodrppCq3l7rhLimFQgmxptXhTC3+/wesVLpB09F1A2kZgvbMOgH7wvhFnBQ==", + "version": "0.5.0", + "resolved": "https://registry.npmjs.org/solc/-/solc-0.5.0.tgz", + "integrity": "sha512-mdLHDl9WeYrN+FIKcMc9PlPfnA9DG9ur5QpCDKcv6VC4RINAsTF4EMuXMZMKoQTvZhtLyJIVH/BZ+KU830Z8Xg==", "requires": { "fs-extra": "^0.30.0", + "keccak": "^1.0.2", "memorystream": "^0.3.1", - "require-from-string": "^1.1.0", - "semver": "^5.3.0", - "yargs": "^4.7.1" + "require-from-string": "^2.0.0", + "semver": "^5.5.0", + "yargs": "^11.0.0" + }, + "dependencies": { + "ansi-regex": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", + "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=" + }, + "camelcase": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-4.1.0.tgz", + "integrity": "sha1-1UVjW+HjPFQmScaRc+Xeas+uNN0=" + }, + "cliui": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/cliui/-/cliui-4.1.0.tgz", + "integrity": "sha512-4FG+RSG9DL7uEwRUZXZn3SS34DiDPfzP0VOiEwtUWlE+AR2EIg+hSyvrIgUUfhdgR/UkAeW2QHgeP+hWrXs7jQ==", + "requires": { + "string-width": "^2.1.1", + "strip-ansi": "^4.0.0", + "wrap-ansi": "^2.0.0" + } + }, + "find-up": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", + "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", + "requires": { + "locate-path": "^2.0.0" + } + }, + "is-fullwidth-code-point": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", + "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=" + }, + "os-locale": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/os-locale/-/os-locale-2.1.0.tgz", + "integrity": "sha512-3sslG3zJbEYcaC4YVAvDorjGxc7tv6KVATnLPZONiljsUncvihe9BQoVCEs0RZ1kmf4Hk9OBqlZfJZWI4GanKA==", + "requires": { + "execa": "^0.7.0", + "lcid": "^1.0.0", + "mem": "^1.1.0" + } + }, + "string-width": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", + "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", + "requires": { + "is-fullwidth-code-point": "^2.0.0", + "strip-ansi": "^4.0.0" + } + }, + "strip-ansi": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", + "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", + "requires": { + "ansi-regex": "^3.0.0" + } + }, + "which-module": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/which-module/-/which-module-2.0.0.tgz", + "integrity": "sha1-2e8H3Od7mQK4o6j6SzHD4/fm6Ho=" + }, + "yargs": { + "version": "11.1.0", + "resolved": "https://registry.npmjs.org/yargs/-/yargs-11.1.0.tgz", + "integrity": "sha512-NwW69J42EsCSanF8kyn5upxvjp5ds+t3+udGBeTbFnERA+lF541DDpMawzo4z6W/QrzNM18D+BPMiOBibnFV5A==", + "requires": { + "cliui": "^4.0.0", + "decamelize": "^1.1.1", + "find-up": "^2.1.0", + "get-caller-file": "^1.0.1", + "os-locale": "^2.0.0", + "require-directory": "^2.1.1", + "require-main-filename": "^1.0.1", + "set-blocking": "^2.0.0", + "string-width": "^2.0.0", + "which-module": "^2.0.0", + "y18n": "^3.2.1", + "yargs-parser": "^9.0.2" + } + }, + "yargs-parser": { + "version": "9.0.2", + "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-9.0.2.tgz", + "integrity": "sha1-nM9qQ0YP5O1Aqbto9I1DuKaMwHc=", + "requires": { + "camelcase": "^4.1.0" + } + } } }, "solidity-coverage": { @@ -4727,6 +4867,7 @@ "version": "3.1.0", "resolved": "https://registry.npmjs.org/spdx-correct/-/spdx-correct-3.1.0.tgz", "integrity": "sha512-lr2EZCctC2BNR7j7WzJ2FpDznxky1sjfxvvYEyzxNyb6lZXHODmEoJeFu4JupYlkfha1KZpJyoqiJ7pgA1qq8Q==", + "dev": true, "requires": { "spdx-expression-parse": "^3.0.0", "spdx-license-ids": "^3.0.0" @@ -4735,12 +4876,14 @@ "spdx-exceptions": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/spdx-exceptions/-/spdx-exceptions-2.2.0.tgz", - "integrity": "sha512-2XQACfElKi9SlVb1CYadKDXvoajPgBVPn/gOQLrTvHdElaVhr7ZEbqJaRnJLVNeaI4cMEAgVCeBMKF6MWRDCRA==" + "integrity": "sha512-2XQACfElKi9SlVb1CYadKDXvoajPgBVPn/gOQLrTvHdElaVhr7ZEbqJaRnJLVNeaI4cMEAgVCeBMKF6MWRDCRA==", + "dev": true }, "spdx-expression-parse": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/spdx-expression-parse/-/spdx-expression-parse-3.0.0.tgz", "integrity": "sha512-Yg6D3XpRD4kkOmTpdgbUiEJFKghJH03fiC1OPll5h/0sO6neh2jqRDVHOQ4o/LMea0tgCkbMgea5ip/e+MkWyg==", + "dev": true, "requires": { "spdx-exceptions": "^2.1.0", "spdx-license-ids": "^3.0.0" @@ -4749,7 +4892,8 @@ "spdx-license-ids": { "version": "3.0.3", "resolved": "https://registry.npmjs.org/spdx-license-ids/-/spdx-license-ids-3.0.3.tgz", - "integrity": "sha512-uBIcIl3Ih6Phe3XHK1NqboJLdGfwr1UN3k6wSD1dZpmPsIkb8AGNbZYJ1fOBk834+Gxy8rpfDxrS6XLEMZMY2g==" + "integrity": "sha512-uBIcIl3Ih6Phe3XHK1NqboJLdGfwr1UN3k6wSD1dZpmPsIkb8AGNbZYJ1fOBk834+Gxy8rpfDxrS6XLEMZMY2g==", + "dev": true }, "split-string": { "version": "3.1.0", @@ -4860,6 +5004,7 @@ "version": "2.0.0", "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-2.0.0.tgz", "integrity": "sha1-YhmoVhZSBJHzV4i9vxRHqZx+aw4=", + "dev": true, "requires": { "is-utf8": "^0.2.0" } @@ -4867,8 +5012,7 @@ "strip-eof": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/strip-eof/-/strip-eof-1.0.0.tgz", - "integrity": "sha1-u0P/VZim6wXYm1n80SnJgzE2Br8=", - "dev": true + "integrity": "sha1-u0P/VZim6wXYm1n80SnJgzE2Br8=" }, "strip-hex-prefix": { "version": "1.0.0", @@ -5027,13 +5171,14 @@ "dev": true }, "truffle": { - "version": "4.1.11", - "resolved": "https://registry.npmjs.org/truffle/-/truffle-4.1.11.tgz", - "integrity": "sha512-VNhc6jexZeM92sNJJr4U8ln3uJ/mJEQO/0y9ZLYc4pccyIskPtl+3r4mzymgGM/Mq5v6MpoQVD6NZgHUVKX+Dw==", + "version": "5.0.15", + "resolved": "https://registry.npmjs.org/truffle/-/truffle-5.0.15.tgz", + "integrity": "sha512-/FAabG/+xv4mADQvm4YXTMWThXrc9Z4MsMCqWixrd6DlQMPBQIV5F86DeYHgkKbp8hRM3oGUdBVfpWRaha6YKg==", "requires": { + "app-module-path": "^2.2.0", "mocha": "^4.1.0", - "original-require": "^1.0.1", - "solc": "0.4.24" + "original-require": "1.0.1", + "solc": "0.5.0" } }, "truffle-flattener": { @@ -5350,6 +5495,7 @@ "version": "3.0.4", "resolved": "https://registry.npmjs.org/validate-npm-package-license/-/validate-npm-package-license-3.0.4.tgz", "integrity": "sha512-DpKm2Ui/xN7/HQKCtpZxoRWBhZ9Z0kqtygG8XCgNQ8ZlDnxuQmWhj566j8fN4Cu3/JmbhsDo7fcAJq4s9h27Ew==", + "dev": true, "requires": { "spdx-correct": "^3.0.0", "spdx-expression-parse": "^3.0.0" @@ -5401,7 +5547,6 @@ "version": "1.3.1", "resolved": "https://registry.npmjs.org/which/-/which-1.3.1.tgz", "integrity": "sha512-HxJdYWq1MTIQbJ3nw0cqssHoTNU267KlrDuGZ1WYlxDStUtKUhOaJmh112/TZmHxxUfuJqPXSOm7tDyas0OSIQ==", - "dev": true, "requires": { "isexe": "^2.0.0" } @@ -5409,7 +5554,8 @@ "which-module": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/which-module/-/which-module-1.0.0.tgz", - "integrity": "sha1-u6Y8qGGUiZT/MHc2CJ47lgJsKk8=" + "integrity": "sha1-u6Y8qGGUiZT/MHc2CJ47lgJsKk8=", + "dev": true }, "widest-line": { "version": "2.0.1", @@ -5456,7 +5602,8 @@ "window-size": { "version": "0.2.0", "resolved": "https://registry.npmjs.org/window-size/-/window-size-0.2.0.tgz", - "integrity": "sha1-tDFbtCFKPXBY6+7okuE/ok2YsHU=" + "integrity": "sha1-tDFbtCFKPXBY6+7okuE/ok2YsHU=", + "dev": true }, "wordwrap": { "version": "1.0.0", @@ -5563,13 +5710,13 @@ "yallist": { "version": "2.1.2", "resolved": "https://registry.npmjs.org/yallist/-/yallist-2.1.2.tgz", - "integrity": "sha1-HBH5IY8HYImkfdUS+TxmmaaoHVI=", - "dev": true + "integrity": "sha1-HBH5IY8HYImkfdUS+TxmmaaoHVI=" }, "yargs": { "version": "4.8.1", "resolved": "https://registry.npmjs.org/yargs/-/yargs-4.8.1.tgz", "integrity": "sha1-wMQpJMpKqmsObaFznfshZDn53cA=", + "dev": true, "requires": { "cliui": "^3.2.0", "decamelize": "^1.1.1", @@ -5591,6 +5738,7 @@ "version": "2.4.1", "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-2.4.1.tgz", "integrity": "sha1-hVaN488VD/SfpRgl8DqMiA3cxcQ=", + "dev": true, "requires": { "camelcase": "^3.0.0", "lodash.assign": "^4.0.6" diff --git a/package.json b/package.json index 86e6d2e89..07d969e7d 100644 --- a/package.json +++ b/package.json @@ -15,7 +15,7 @@ "dependencies": { "ganache-cli": "^6.1.0", "openzeppelin-solidity": "^1.10.0", - "truffle": "4.1.11", + "truffle": "^5.0.15", "web3-utils": "1.0.0-beta.34" }, "devDependencies": { diff --git a/truffle-config.js b/truffle-config.js index a6330d6d5..39fc849ca 100644 --- a/truffle-config.js +++ b/truffle-config.js @@ -1,4 +1,36 @@ module.exports = { - // See - // to customize your Truffle configuration! + networks: { + coverage: { + host: 'localhost', + network_id: '*', // eslint-disable-line camelcase + port: 8555, + gas: 0xfffffffffff, + gasPrice: 0x01, + }, + ganache: { + host: '127.0.0.1', + port: 8545, + network_id: '*', // eslint-disable-line camelcase + gasPrice: 100000000000 + } + }, + compilers: { + solc: { + version: "0.4.24", + settings: { + optimizer: { + enabled: true, + runs: 200 + }, + evmVersion: "byzantium" + } + } + }, + mocha: { + reporter: 'eth-gas-reporter', + reporterOptions : { + currency: 'USD', + gasPrice: 1 + } + } }; diff --git a/truffle.js b/truffle.js deleted file mode 100644 index 3468c855d..000000000 --- a/truffle.js +++ /dev/null @@ -1,63 +0,0 @@ -module.exports = { - networks: { - development: { - host: "localhost", - port: 7545, - network_id: "*", - gasPrice: 1000000000 - }, - test: { - host: "localhost", - port: 7545, - network_id: "*", - gasPrice: 1000000000 - }, - kovan: { - host: "localhost", - port: "8591", - network_id: "*", - gas: 4700000, - gasPrice: 1000000000 - }, - core: { - host: "localhost", - port: "8777", - network_id: "*", - gas: 4700000, - gasPrice: 1000000000 - }, - sokol: { - host: "localhost", - port: "8545", - network_id: "*", - gas: 4700000, - gasPrice: 1000000000 - }, - coverage: { - host: 'localhost', - network_id: '*', // eslint-disable-line camelcase - port: 8555, - gas: 0xfffffffffff, - gasPrice: 0x01, - }, - ganache: { - host: 'localhost', - port: 8545, - network_id: '*', // eslint-disable-line camelcase - gasPrice: 1000000000 - } - }, - solc: { - optimizer: { - enabled: true, - runs: 200 - } - }, - mocha: { - reporter: 'eth-gas-reporter', - reporterOptions : { - currency: 'USD', - gasPrice: 1 - } - } -}; From a682bd65e945ece1e816997aaf9ab597788afd58 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 8 May 2019 11:05:30 -0300 Subject: [PATCH 178/187] compile contracts for byzantium and spuriousDragon --- package.json | 2 +- truffle-config.js | 7 ++++++- 2 files changed, 7 insertions(+), 2 deletions(-) diff --git a/package.json b/package.json index 07d969e7d..5d94fdb2b 100644 --- a/package.json +++ b/package.json @@ -6,7 +6,7 @@ "scripts": { "test": "scripts/test.sh", "deploy": "truffle migrate --reset --network $NETWORK", - "compile": "truffle compile", + "compile": "truffle compile && truffle compile spuriousDragon", "flatten": "bash flatten.sh", "watch-tests": "./node_modules/.bin/nodemon ./node_modules/.bin/truffle test --network test" }, diff --git a/truffle-config.js b/truffle-config.js index 39fc849ca..3fa52333e 100644 --- a/truffle-config.js +++ b/truffle-config.js @@ -1,4 +1,9 @@ +const spuriousDragonVersion = process.argv[3] === 'spuriousDragon' +const contractsBuildDirectory = spuriousDragonVersion ? './build/spuriousDragon' : './build/contracts' +const evmVersion = spuriousDragonVersion ? 'spuriousDragon' : 'byzantium' + module.exports = { + contracts_build_directory: contractsBuildDirectory, networks: { coverage: { host: 'localhost', @@ -22,7 +27,7 @@ module.exports = { enabled: true, runs: 200 }, - evmVersion: "byzantium" + evmVersion: evmVersion } } }, From de536a3781254d8e5256150cebde08d327d2e31e Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 8 May 2019 11:29:26 -0300 Subject: [PATCH 179/187] Remove unused migrations files --- migrations/.gitkeep | 0 migrations/1_initial_migration.js | 6 -- migrations/2_bridge_deployment.js | 27 ------- migrations/3_upgradeable_deployment.js | 98 -------------------------- package.json | 1 - scripts/test.sh | 2 +- 6 files changed, 1 insertion(+), 133 deletions(-) create mode 100644 migrations/.gitkeep delete mode 100644 migrations/1_initial_migration.js delete mode 100644 migrations/2_bridge_deployment.js delete mode 100644 migrations/3_upgradeable_deployment.js diff --git a/migrations/.gitkeep b/migrations/.gitkeep new file mode 100644 index 000000000..e69de29bb diff --git a/migrations/1_initial_migration.js b/migrations/1_initial_migration.js deleted file mode 100644 index 09b416e01..000000000 --- a/migrations/1_initial_migration.js +++ /dev/null @@ -1,6 +0,0 @@ -var Migrations = artifacts.require("./Migrations.sol"); - -module.exports = async function(deployer, network, accounts) { - const PROXY_OWNER = process.env.PROXY_OWNER || accounts[0]; - await deployer.deploy(Migrations, {from: PROXY_OWNER}); -}; diff --git a/migrations/2_bridge_deployment.js b/migrations/2_bridge_deployment.js deleted file mode 100644 index e2d53ea79..000000000 --- a/migrations/2_bridge_deployment.js +++ /dev/null @@ -1,27 +0,0 @@ -const POA20 = artifacts.require("./ERC677BridgeToken.sol"); -const BridgeValidators = artifacts.require("./BridgeValidators.sol"); -const HomeBridge = artifacts.require("./HomeBridgeNativeToErc.sol"); -const ForeignBridge = artifacts.require("./ForeignBridgeNativeToErc.sol"); - -module.exports = async function(deployer, network, accounts) { - if(process.env.DEPLOY_NORMAL === true){ - let validators = ["0xb8988b690910913c97a090c3a6f80fad8b3a4683"] - const homeDailyLimit = '1000000000000000000' // 1 ether - const foreignDailyLimit = '1000000000000000000' // 1 ether - console.log('deploying token') - await deployer.deploy(POA20, "POA ERC20 on Foundation", "POA20", 18) - const erc677token = await POA20.deployed() - console.log('deploying validators') - await deployer.deploy(BridgeValidators, '1', validators); - const validatorContract = await BridgeValidators.deployed(); - console.log('deploying home') - await deployer.deploy(HomeBridge, validatorContract.address, homeDailyLimit); - console.log('deploying ForeignBridge') - await deployer.deploy(ForeignBridge, validatorContract.address, erc677token.address, foreignDailyLimit); - const foreignBridge = await ForeignBridge.deployed(); - - await erc677token.transferOwnership(foreignBridge.address) - console.log('all is done') - } - -}; diff --git a/migrations/3_upgradeable_deployment.js b/migrations/3_upgradeable_deployment.js deleted file mode 100644 index 3d94ba4f5..000000000 --- a/migrations/3_upgradeable_deployment.js +++ /dev/null @@ -1,98 +0,0 @@ -const POA20 = artifacts.require("./ERC677BridgeToken.sol"); -const BridgeValidators = artifacts.require("./BridgeValidators.sol"); -const HomeBridge = artifacts.require("./HomeBridgeNativeToErc.sol"); -const ForeignBridge = artifacts.require("./ForeignBridgeNativeToErc.sol"); -const EternalStorageProxy = artifacts.require('EternalStorageProxy') - -module.exports = async function(deployer, network, accounts) { - if(network !== 'test' && network !== 'ganache'){ - const VALIDATORS = process.env.VALIDATORS ? process.env.VALIDATORS.split(" ") : [accounts[0]]; - const REQUIRED_NUMBER_OF_VALIDATORS = process.env.REQUIRED_VALIDATORS || VALIDATORS.length - const PROXY_OWNER = process.env.PROXY_OWNER || accounts[0]; - const homeDailyLimit = process.env.HOME_LIMIT || '1000000000000000000' // 1 ether - const foreignDailyLimit = process.env.FOREIGN_LIMIT || '1000000000000000000' // 1 ether - const MAX_AMOUNT_PER_TX = process.env.MAX_AMOUNT_PER_TX || '100000000000000000' // 0.1 ether - const MIN_AMOUNT_PER_TX = process.env.MIN_AMOUNT_PER_TX || '10000000000000000' // 0.01 ether - const HOME_REQUIRED_BLOCK_CONFIRMATIONS = process.env.HOME_REQUIRED_BLOCK_CONFIRMATIONS || '1' - const HOME_GAS_PRICE = process.env.HOME_GAS_PRICE || '1000000000'; - const FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS = process.env.FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS || '8'; - const FOREIGN_GAS_PRICE = process.env.FOREIGN_GAS_PRICE || '1000000000'; - - console.log('storage for home validators') - await deployer.deploy(EternalStorageProxy, {from: PROXY_OWNER}); - const storageBridgeValidators = await EternalStorageProxy.deployed() - - console.log('deploying token') - await deployer.deploy(POA20, "POA ERC20 on Foundation", "POA20", 18) - const erc677token = await POA20.deployed() - - console.log('deploying validators') - await deployer.deploy(BridgeValidators); - const validatorContract = await BridgeValidators.deployed(); - - console.log('hooking up eternal storage to BridgeValidators') - //truffle sucks, it uses web3 0.20, hence I need to work around in order to generate data param - var bridgeValidatorsWeb3 = web3.eth.contract(BridgeValidators.abi); - var bridgeValidatorsWeb3Instance = bridgeValidatorsWeb3.at(validatorContract.address); - var initializeDataValidators = bridgeValidatorsWeb3Instance.initialize.getData(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, PROXY_OWNER); - await storageBridgeValidators.upgradeTo('1', validatorContract.address, {from: PROXY_OWNER}); - await web3.eth.sendTransaction({ - from: PROXY_OWNER, - to: storageBridgeValidators.address, - data: initializeDataValidators, - value: 0, - gas: 4700000 - }) - - console.log('deploying home storage on home network') - await deployer.deploy(EternalStorageProxy, {from: PROXY_OWNER}); - const homeBridgeUpgradeable = await EternalStorageProxy.deployed() - await deployer.deploy(HomeBridge); - const homeBridgeImplementation = await HomeBridge.deployed(); - var homeBridgeWeb3 = web3.eth.contract(HomeBridge.abi); - var homeBridgeWeb3Instance = homeBridgeWeb3.at(homeBridgeImplementation.address); - var initializeDataHome = homeBridgeWeb3Instance.initialize.getData( - storageBridgeValidators.address, - homeDailyLimit, - MAX_AMOUNT_PER_TX, - MIN_AMOUNT_PER_TX, - HOME_GAS_PRICE, - HOME_REQUIRED_BLOCK_CONFIRMATIONS); - await homeBridgeUpgradeable.upgradeTo('1', homeBridgeImplementation.address, {from: PROXY_OWNER}); - await web3.eth.sendTransaction({ - from: PROXY_OWNER, - to: homeBridgeUpgradeable.address, - data: initializeDataHome, - value: 0, - gas: 4700000 - }) - - console.log('deploying ForeignBridge') - await deployer.deploy(EternalStorageProxy, {from: PROXY_OWNER}); - const foreignBridgeUpgradeable = await EternalStorageProxy.deployed() - await deployer.deploy(ForeignBridge); - const foreignBridgeImplementation = await ForeignBridge.deployed(); - var foreignBridgeWeb3 = web3.eth.contract(ForeignBridge.abi); - var foreignBridgeWeb3Instance = foreignBridgeWeb3.at(foreignBridgeImplementation.address); - var initializeDataForeign = foreignBridgeWeb3Instance.initialize - .getData(storageBridgeValidators.address, erc677token.address, foreignDailyLimit, MAX_AMOUNT_PER_TX, MIN_AMOUNT_PER_TX, FOREIGN_GAS_PRICE, FOREIGN_REQUIRED_BLOCK_CONFIRMATIONS); - await foreignBridgeUpgradeable.upgradeTo('1', foreignBridgeImplementation.address, {from: PROXY_OWNER}); - - await web3.eth.sendTransaction({ - from: PROXY_OWNER, - to: foreignBridgeUpgradeable.address, - data: initializeDataForeign, - value: 0, - gas: 4700000 - }) - - await erc677token.transferOwnership(foreignBridgeUpgradeable.address) - console.log('all is done', ` - validators: ${VALIDATORS} - Owner: ${PROXY_OWNER} - Foreign Bridge: ${foreignBridgeUpgradeable.address} - Home Bridge: ${homeBridgeUpgradeable.address} - POA20: ${erc677token.address}`) - } - -}; diff --git a/package.json b/package.json index 5d94fdb2b..649b6960b 100644 --- a/package.json +++ b/package.json @@ -5,7 +5,6 @@ "main": "index.js", "scripts": { "test": "scripts/test.sh", - "deploy": "truffle migrate --reset --network $NETWORK", "compile": "truffle compile && truffle compile spuriousDragon", "flatten": "bash flatten.sh", "watch-tests": "./node_modules/.bin/nodemon ./node_modules/.bin/truffle test --network test" diff --git a/scripts/test.sh b/scripts/test.sh index ee231fc30..7b133245a 100755 --- a/scripts/test.sh +++ b/scripts/test.sh @@ -61,5 +61,5 @@ if [ "$SOLIDITY_COVERAGE" = true ]; then cat coverage/lcov.info | node_modules/.bin/coveralls fi else - node_modules/.bin/truffle test "$@" --network ganache + node_modules/.bin/truffle test "$@" fi From b73661317e6b7cabd01de2bc08701cbfc67924af Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 8 May 2019 14:56:40 -0300 Subject: [PATCH 180/187] Update deploy script to use correct evm build --- deploy/.env.example | 7 +++++ deploy/README.md | 24 +++++++++++++++++ deploy/src/constants.js | 7 ++++- deploy/src/erc_to_erc/foreign.js | 13 +++++---- deploy/src/erc_to_erc/home.js | 24 ++++++++++------- deploy/src/erc_to_erc/preDeploy.js | 6 ++++- deploy/src/erc_to_native/foreign.js | 11 +++++--- deploy/src/erc_to_native/home.js | 17 +++++++----- deploy/src/loadContracts.js | 39 +++++++++++++++++++++++++++ deploy/src/loadEnv.js | 23 ++++++++++++++-- deploy/src/native_to_erc/foreign.js | 19 +++++++------ deploy/src/native_to_erc/home.js | 17 +++++++----- deploy/src/utils/deployBlockReward.js | 4 ++- deploy/src/utils/deployERC20Token.js | 4 ++- deploy/src/utils/setBlockReward.js | 4 ++- 15 files changed, 172 insertions(+), 47 deletions(-) create mode 100644 deploy/src/loadContracts.js diff --git a/deploy/.env.example b/deploy/.env.example index 68c8e2fd1..dd9ea4773 100644 --- a/deploy/.env.example +++ b/deploy/.env.example @@ -1,5 +1,12 @@ #BRIDGE_MODE=ERC_TO_ERC BRIDGE_MODE=NATIVE_TO_ERC + +# If Home network does not support byzantium fork, should use contracts compiled for spuriousDragon +#HOME_EVM_VERSION=spuriousDragon + +# If Foreign network does not support byzantium fork, should use contracts compiled for spuriousDragon +#FOREIGN_EVM_VERSION=spuriousDragon + DEPLOYMENT_ACCOUNT_PRIVATE_KEY=67..14 DEPLOYMENT_GAS_LIMIT_EXTRA=0.2 HOME_DEPLOYMENT_GAS_PRICE=10000000000 diff --git a/deploy/README.md b/deploy/README.md index 8ace66325..895307237 100644 --- a/deploy/README.md +++ b/deploy/README.md @@ -32,6 +32,14 @@ This example of an `.env` file for the `native-to-erc` bridge mode includes comm # The type of bridge. Defines set of contracts to be deployed. BRIDGE_MODE=NATIVE_TO_ERC +# If Home network does not support byzantium fork, should use contracts compiled for spuriousDragon +# Default value is byzantium +#HOME_EVM_VERSION=spuriousDragon + +# If Foreign network does not support byzantium fork, should use contracts compiled for spuriousDragon +# Default value is byzantium +#FOREIGN_EVM_VERSION=spuriousDragon + # The private key hex value of the account responsible for contracts # deployments and initial configuration. The account's balance must contain # funds from both networks. @@ -169,6 +177,14 @@ This example of an `.env` file for the `erc-to-erc` bridge mode includes comment # The type of bridge. Defines set of contracts to be deployed. BRIDGE_MODE=ERC_TO_ERC +# If Home network does not support byzantium fork, should use contracts compiled for spuriousDragon +# Default value is byzantium +#HOME_EVM_VERSION=spuriousDragon + +# If Foreign network does not support byzantium fork, should use contracts compiled for spuriousDragon +# Default value is byzantium +#FOREIGN_EVM_VERSION=spuriousDragon + # The private key hex value of the account responsible for contracts # deployments and initial configuration. The account's balance must contain # funds from both networks. @@ -287,6 +303,14 @@ This example of an `.env` file for the `erc-to-native` bridge mode includes comm # The type of bridge. Defines set of contracts to be deployed. BRIDGE_MODE=ERC_TO_NATIVE +# If Home network does not support byzantium fork, should use contracts compiled for spuriousDragon +# Default value is byzantium +#HOME_EVM_VERSION=spuriousDragon + +# If Foreign network does not support byzantium fork, should use contracts compiled for spuriousDragon +# Default value is byzantium +#FOREIGN_EVM_VERSION=spuriousDragon + # The private key hex value of the account responsible for contracts # deployments and initial configuration. The account's balance must contain # funds from both networks. diff --git a/deploy/src/constants.js b/deploy/src/constants.js index 362c403bb..6f05af970 100644 --- a/deploy/src/constants.js +++ b/deploy/src/constants.js @@ -1,5 +1,10 @@ const ZERO_ADDRESS = '0x0000000000000000000000000000000000000000' +const EVM_TYPES = { + BYZANTIUM: 'byzantium', + SPURIOUSDRAGON: 'spuriousDragon' +} module.exports = { - ZERO_ADDRESS + ZERO_ADDRESS, + EVM_TYPES } diff --git a/deploy/src/erc_to_erc/foreign.js b/deploy/src/erc_to_erc/foreign.js index c66fbf6dc..1daa1b215 100644 --- a/deploy/src/erc_to_erc/foreign.js +++ b/deploy/src/erc_to_erc/foreign.js @@ -12,11 +12,14 @@ const { assertStateWithRetry } = require('../deploymentUtils') const { web3Foreign, deploymentPrivateKey, FOREIGN_RPC_URL } = require('../web3') - -const EternalStorageProxy = require('../../../build/contracts/EternalStorageProxy.json') -const BridgeValidators = require('../../../build/contracts/BridgeValidators.json') -const ForeignBridge = require('../../../build/contracts/ForeignBridgeErcToErc.json') -const ForeignBridgeErc677ToErc677 = require('../../../build/contracts/ForeignBridgeErc677ToErc677.json') +const { + foreignContracts: { + EternalStorageProxy, + BridgeValidators, + ForeignBridgeErcToErc: ForeignBridge, + ForeignBridgeErc677ToErc677 + } +} = require('../loadContracts') const VALIDATORS = env.VALIDATORS.split(' ') diff --git a/deploy/src/erc_to_erc/home.js b/deploy/src/erc_to_erc/home.js index 805f117dd..d19bf6a38 100644 --- a/deploy/src/erc_to_erc/home.js +++ b/deploy/src/erc_to_erc/home.js @@ -16,14 +16,18 @@ const { } = require('../deploymentUtils') const { web3Home, deploymentPrivateKey, HOME_RPC_URL } = require('../web3') -const EternalStorageProxy = require('../../../build/contracts/EternalStorageProxy.json') -const BridgeValidators = require('../../../build/contracts/BridgeValidators.json') -const RewardableValidators = require('../../../build/contracts/RewardableValidators.json') -const FeeManagerErcToErcPOSDAO = require('../../../build/contracts/FeeManagerErcToErcPOSDAO.json') -const HomeBridge = require('../../../build/contracts/HomeBridgeErcToErc.json') -const POSDAOHomeBridge = require('../../../build/contracts/POSDAOHomeBridgeErcToErc.json') -const ERC677BridgeToken = require('../../../build/contracts/ERC677BridgeToken.json') -const ERC677BridgeTokenRewardable = require('../../../build/contracts/ERC677BridgeTokenRewardable.json') +const { + homeContracts: { + EternalStorageProxy, + BridgeValidators, + RewardableValidators, + FeeManagerErcToErcPOSDAO, + HomeBridgeErcToErc: HomeBridge, + POSDAOHomeBridgeErcToErc, + ERC677BridgeToken, + ERC677BridgeTokenRewardable + } +} = require('../loadContracts') const VALIDATORS = env.VALIDATORS.split(' ') const VALIDATORS_REWARD_ACCOUNTS = env.VALIDATORS_REWARD_ACCOUNTS.split(' ') @@ -215,7 +219,9 @@ async function deployHome() { console.log('\ndeploying homeBridge implementation\n') const bridgeContract = - isRewardableBridge && BLOCK_REWARD_ADDRESS !== ZERO_ADDRESS ? POSDAOHomeBridge : HomeBridge + isRewardableBridge && BLOCK_REWARD_ADDRESS !== ZERO_ADDRESS + ? POSDAOHomeBridgeErcToErc + : HomeBridge const homeBridgeImplementation = await deployContract(bridgeContract, [], { from: DEPLOYMENT_ACCOUNT_ADDRESS, nonce diff --git a/deploy/src/erc_to_erc/preDeploy.js b/deploy/src/erc_to_erc/preDeploy.js index 5cb785774..3df6f18b2 100644 --- a/deploy/src/erc_to_erc/preDeploy.js +++ b/deploy/src/erc_to_erc/preDeploy.js @@ -1,6 +1,10 @@ const { web3Foreign } = require('../web3') const { ERC20_TOKEN_ADDRESS, ERC20_EXTENDED_BY_ERC677 } = require('../loadEnv') -const { abi } = require('../../../build/contracts/ERC677BridgeToken.json') +const { + foreignContracts: { + ERC677BridgeToken: { abi } + } +} = require('../loadContracts') async function preDeploy() { if (ERC20_EXTENDED_BY_ERC677) { diff --git a/deploy/src/erc_to_native/foreign.js b/deploy/src/erc_to_native/foreign.js index b08fc3363..87a2f1a6e 100644 --- a/deploy/src/erc_to_native/foreign.js +++ b/deploy/src/erc_to_native/foreign.js @@ -12,10 +12,13 @@ const { assertStateWithRetry } = require('../deploymentUtils') const { web3Foreign, deploymentPrivateKey, FOREIGN_RPC_URL } = require('../web3') - -const EternalStorageProxy = require('../../../build/contracts/EternalStorageProxy.json') -const BridgeValidators = require('../../../build/contracts/BridgeValidators.json') -const ForeignBridge = require('../../../build/contracts/ForeignBridgeErcToNative.json') +const { + foreignContracts: { + EternalStorageProxy, + BridgeValidators, + ForeignBridgeErcToNative: ForeignBridge + } +} = require('../loadContracts') const VALIDATORS = env.VALIDATORS.split(' ') diff --git a/deploy/src/erc_to_native/home.js b/deploy/src/erc_to_native/home.js index 7a122ab4f..963fe8f6e 100644 --- a/deploy/src/erc_to_native/home.js +++ b/deploy/src/erc_to_native/home.js @@ -12,13 +12,16 @@ const { assertStateWithRetry } = require('../deploymentUtils') const { web3Home, deploymentPrivateKey, HOME_RPC_URL } = require('../web3') - -const EternalStorageProxy = require('../../../build/contracts/EternalStorageProxy.json') -const BridgeValidators = require('../../../build/contracts/BridgeValidators.json') -const RewardableValidators = require('../../../build/contracts/RewardableValidators.json') -const FeeManagerErcToNative = require('../../../build/contracts/FeeManagerErcToNative.json') -const FeeManagerErcToNativePOSDAO = require('../../../build/contracts/FeeManagerErcToNativePOSDAO.json') -const HomeBridge = require('../../../build/contracts/HomeBridgeErcToNative.json') +const { + homeContracts: { + EternalStorageProxy, + BridgeValidators, + RewardableValidators, + FeeManagerErcToNative, + HomeBridgeErcToNative: HomeBridge, + FeeManagerErcToNativePOSDAO + } +} = require('../loadContracts') const VALIDATORS = env.VALIDATORS.split(' ') const VALIDATORS_REWARD_ACCOUNTS = env.VALIDATORS_REWARD_ACCOUNTS.split(' ') diff --git a/deploy/src/loadContracts.js b/deploy/src/loadContracts.js new file mode 100644 index 000000000..e7c56499f --- /dev/null +++ b/deploy/src/loadContracts.js @@ -0,0 +1,39 @@ +/* eslint import/no-dynamic-require: 0 */ +const { HOME_EVM_VERSION, FOREIGN_EVM_VERSION } = require('./loadEnv') +const { EVM_TYPES } = require('./constants') + +const homeContracts = getContracts(HOME_EVM_VERSION) +const foreignContracts = getContracts(FOREIGN_EVM_VERSION) + +function getContracts(evmVersion) { + const buildPath = evmVersion === EVM_TYPES.SPURIOUSDRAGON ? 'spuriousDragon' : 'contracts' + const useClassicProxy = evmVersion === EVM_TYPES.SPURIOUSDRAGON + return { + EternalStorageProxy: useClassicProxy + ? require(`../../build/${buildPath}/ClassicEternalStorageProxy.json`) + : require(`../../build/${buildPath}/EternalStorageProxy.json`), + BridgeValidators: require(`../../build/${buildPath}/BridgeValidators.json`), + RewardableValidators: require(`../../build/${buildPath}/RewardableValidators.json`), + FeeManagerErcToErcPOSDAO: require(`../../build/${buildPath}/FeeManagerErcToErcPOSDAO.json`), + HomeBridgeErcToErc: require(`../../build/${buildPath}/HomeBridgeErcToErc.json`), + ForeignBridgeErcToErc: require(`../../build/${buildPath}/ForeignBridgeErcToErc.json`), + ForeignBridgeErc677ToErc677: require(`../../build/${buildPath}/ForeignBridgeErc677ToErc677.json`), + POSDAOHomeBridgeErcToErc: require(`../../build/${buildPath}/POSDAOHomeBridgeErcToErc.json`), + ERC677BridgeToken: require(`../../build/${buildPath}/ERC677BridgeToken.json`), + ERC677BridgeTokenRewardable: require(`../../build/${buildPath}/ERC677BridgeTokenRewardable.json`), + ForeignBridgeErcToNative: require(`../../build/${buildPath}/ForeignBridgeErcToNative.json`), + FeeManagerErcToNative: require(`../../build/${buildPath}/FeeManagerErcToNative.json`), + FeeManagerErcToNativePOSDAO: require(`../../build/${buildPath}/FeeManagerErcToNativePOSDAO.json`), + HomeBridgeErcToNative: require(`../../build/${buildPath}/HomeBridgeErcToNative.json`), + FeeManagerNativeToErc: require(`../../build/${buildPath}/FeeManagerNativeToErc.json`), + ForeignBridgeNativeToErc: require(`../../build/${buildPath}/ForeignBridgeNativeToErc.json`), + FeeManagerNativeToErcBothDirections: require(`../../build/${buildPath}/FeeManagerNativeToErcBothDirections.json`), + HomeBridgeNativeToErc: require(`../../build/${buildPath}/HomeBridgeNativeToErc.json`), + BlockReward: require(`../../build/${buildPath}/BlockReward.json`) + } +} + +module.exports = { + homeContracts, + foreignContracts +} diff --git a/deploy/src/loadEnv.js b/deploy/src/loadEnv.js index 3f36d60e4..3d08d9775 100644 --- a/deploy/src/loadEnv.js +++ b/deploy/src/loadEnv.js @@ -4,9 +4,10 @@ require('dotenv').config({ }) const { isAddress, toBN } = require('web3').utils const envalid = require('envalid') -const { ZERO_ADDRESS } = require('./constants') +const { ZERO_ADDRESS, EVM_TYPES } = require('./constants') // Validations and constants +const evmVersions = [EVM_TYPES.BYZANTIUM, EVM_TYPES.SPURIOUSDRAGON] const validBridgeModes = ['NATIVE_TO_ERC', 'ERC_TO_ERC', 'ERC_TO_NATIVE'] const validRewardModes = ['false', 'ONE_DIRECTION', 'BOTH_DIRECTIONS'] const validFeeManagerTypes = ['BRIDGE_VALIDATORS_REWARD', 'POSDAO_REWARD'] @@ -41,9 +42,27 @@ const { VALIDATORS_REWARD_ACCOUNTS, DEPLOY_REWARDABLE_TOKEN, HOME_FEE_MANAGER_TYPE, - ERC20_EXTENDED_BY_ERC677 + ERC20_EXTENDED_BY_ERC677, + HOME_EVM_VERSION, + FOREIGN_EVM_VERSION } = process.env +if (HOME_EVM_VERSION) { + if (!evmVersions.includes(HOME_EVM_VERSION)) { + throw new Error( + `Invalid Home EVM Version: ${HOME_EVM_VERSION}. Supported values are ${evmVersions}` + ) + } +} + +if (FOREIGN_EVM_VERSION) { + if (!evmVersions.includes(FOREIGN_EVM_VERSION)) { + throw new Error( + `Invalid Foreign EVM Version: ${FOREIGN_EVM_VERSION}. Supported values are ${evmVersions}` + ) + } +} + if (!validBridgeModes.includes(BRIDGE_MODE)) { throw new Error(`Invalid bridge mode: ${BRIDGE_MODE}`) } diff --git a/deploy/src/native_to_erc/foreign.js b/deploy/src/native_to_erc/foreign.js index 394573afc..1d7ee002e 100644 --- a/deploy/src/native_to_erc/foreign.js +++ b/deploy/src/native_to_erc/foreign.js @@ -14,14 +14,17 @@ const { assertStateWithRetry } = require('../deploymentUtils') const { web3Foreign, deploymentPrivateKey, FOREIGN_RPC_URL } = require('../web3') - -const ERC677BridgeToken = require('../../../build/contracts/ERC677BridgeToken.json') -const ERC677BridgeTokenRewardable = require('../../../build/contracts/ERC677BridgeTokenRewardable.json') -const EternalStorageProxy = require('../../../build/contracts/EternalStorageProxy.json') -const BridgeValidators = require('../../../build/contracts/BridgeValidators.json') -const RewardableValidators = require('../../../build/contracts/RewardableValidators.json') -const FeeManagerNativeToErc = require('../../../build/contracts/FeeManagerNativeToErc.json') -const ForeignBridge = require('../../../build/contracts/ForeignBridgeNativeToErc.json') +const { + foreignContracts: { + EternalStorageProxy, + BridgeValidators, + RewardableValidators, + ForeignBridgeNativeToErc: ForeignBridge, + ERC677BridgeToken, + ERC677BridgeTokenRewardable, + FeeManagerNativeToErc + } +} = require('../loadContracts') const VALIDATORS = env.VALIDATORS.split(' ') const VALIDATORS_REWARD_ACCOUNTS = env.VALIDATORS_REWARD_ACCOUNTS.split(' ') diff --git a/deploy/src/native_to_erc/home.js b/deploy/src/native_to_erc/home.js index 414dca095..65eb4c907 100644 --- a/deploy/src/native_to_erc/home.js +++ b/deploy/src/native_to_erc/home.js @@ -12,13 +12,16 @@ const { assertStateWithRetry } = require('../deploymentUtils') const { web3Home, deploymentPrivateKey, HOME_RPC_URL } = require('../web3') - -const EternalStorageProxy = require('../../../build/contracts/EternalStorageProxy.json') -const BridgeValidators = require('../../../build/contracts/BridgeValidators.json') -const RewardableValidators = require('../../../build/contracts/RewardableValidators.json') -const FeeManagerNativeToErc = require('../../../build/contracts/FeeManagerNativeToErc.json') -const FeeManagerNativeToErcBothDirections = require('../../../build/contracts/FeeManagerNativeToErcBothDirections.json') -const HomeBridge = require('../../../build/contracts/HomeBridgeNativeToErc.json') +const { + homeContracts: { + EternalStorageProxy, + BridgeValidators, + RewardableValidators, + FeeManagerNativeToErc, + HomeBridgeNativeToErc: HomeBridge, + FeeManagerNativeToErcBothDirections + } +} = require('../loadContracts') const VALIDATORS = env.VALIDATORS.split(' ') const VALIDATORS_REWARD_ACCOUNTS = env.VALIDATORS_REWARD_ACCOUNTS.split(' ') diff --git a/deploy/src/utils/deployBlockReward.js b/deploy/src/utils/deployBlockReward.js index 4c0d9a3dc..aa38edaeb 100644 --- a/deploy/src/utils/deployBlockReward.js +++ b/deploy/src/utils/deployBlockReward.js @@ -1,7 +1,9 @@ const Web3Utils = require('web3-utils') const { web3Home, deploymentPrivateKey, HOME_RPC_URL } = require('../web3') const { deployContract, privateKeyToAddress, sendRawTxHome } = require('../deploymentUtils') -const BlockReward = require('../../../build/contracts/BlockReward.json') +const { + homeContracts: { BlockReward } +} = require('../loadContracts') const env = require('../loadEnv') const { DEPLOYMENT_ACCOUNT_PRIVATE_KEY } = env diff --git a/deploy/src/utils/deployERC20Token.js b/deploy/src/utils/deployERC20Token.js index f18922397..ff798943c 100644 --- a/deploy/src/utils/deployERC20Token.js +++ b/deploy/src/utils/deployERC20Token.js @@ -5,7 +5,9 @@ const env = require('../loadEnv') const { deployContract, privateKeyToAddress, sendRawTxForeign } = require('../deploymentUtils') const { web3Foreign, deploymentPrivateKey, FOREIGN_RPC_URL } = require('../web3') -const ERC677BridgeToken = require('../../../build/contracts/ERC677BridgeToken.json') +const { + foreignContracts: { ERC677BridgeToken } +} = require('../loadContracts') const { DEPLOYMENT_ACCOUNT_PRIVATE_KEY, diff --git a/deploy/src/utils/setBlockReward.js b/deploy/src/utils/setBlockReward.js index 4709361c8..7bfe88dcb 100644 --- a/deploy/src/utils/setBlockReward.js +++ b/deploy/src/utils/setBlockReward.js @@ -1,6 +1,8 @@ const { web3Home, deploymentPrivateKey, HOME_RPC_URL } = require('../web3') const { privateKeyToAddress, sendRawTxHome } = require('../deploymentUtils') -const HomeBridge = require('../../../build/contracts/HomeBridgeErcToNative.json') +const { + homeContracts: { HomeBridgeErcToNative: HomeBridge } +} = require('../loadContracts') const env = require('../loadEnv') const { BLOCK_REWARD_ADDRESS, DEPLOYMENT_ACCOUNT_PRIVATE_KEY, HOME_BRIDGE_ADDRESS } = env From 20e7cefdf8dd5761765a053829f1781a1fab1ded Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 8 May 2019 15:21:05 -0300 Subject: [PATCH 181/187] Add specific script for gas report on tests --- package.json | 1 + truffle-config.js | 17 ++++++++++------- 2 files changed, 11 insertions(+), 7 deletions(-) diff --git a/package.json b/package.json index 649b6960b..d72488cf6 100644 --- a/package.json +++ b/package.json @@ -5,6 +5,7 @@ "main": "index.js", "scripts": { "test": "scripts/test.sh", + "test:gasreport": "GASREPORT=true npm run test", "compile": "truffle compile && truffle compile spuriousDragon", "flatten": "bash flatten.sh", "watch-tests": "./node_modules/.bin/nodemon ./node_modules/.bin/truffle test --network test" diff --git a/truffle-config.js b/truffle-config.js index 3fa52333e..a3c510631 100644 --- a/truffle-config.js +++ b/truffle-config.js @@ -1,6 +1,15 @@ const spuriousDragonVersion = process.argv[3] === 'spuriousDragon' const contractsBuildDirectory = spuriousDragonVersion ? './build/spuriousDragon' : './build/contracts' const evmVersion = spuriousDragonVersion ? 'spuriousDragon' : 'byzantium' +const mochaOptions = process.env.GASREPORT === 'true' + ? { + reporter: 'eth-gas-reporter', + reporterOptions : { + currency: 'USD', + gasPrice: 1 + } + } + : {} module.exports = { contracts_build_directory: contractsBuildDirectory, @@ -31,11 +40,5 @@ module.exports = { } } }, - mocha: { - reporter: 'eth-gas-reporter', - reporterOptions : { - currency: 'USD', - gasPrice: 1 - } - } + mocha: mochaOptions }; From f937e507036989e8020fa74a25df1dc6a56ba716 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Wed, 8 May 2019 15:49:02 -0300 Subject: [PATCH 182/187] Update test dependencies --- package-lock.json | 427 ++++++++++++++++++++++++++-------------------- package.json | 8 +- test/setup.js | 8 +- 3 files changed, 253 insertions(+), 190 deletions(-) diff --git a/package-lock.json b/package-lock.json index 988489394..ad3b00891 100644 --- a/package-lock.json +++ b/package-lock.json @@ -92,12 +92,27 @@ } }, "accepts": { - "version": "1.3.5", - "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.5.tgz", - "integrity": "sha1-63d99gEXI6OxTopywIBcjoZ0a9I=", + "version": "1.3.7", + "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.7.tgz", + "integrity": "sha512-Il80Qs2WjYlJIBNzNkK6KYqlVMTbZLXgHx2oT0pU/fjRHyEp+PEfEPY0R3WCwAGVOtauxh1hOxNgIf5bv7dQpA==", "requires": { - "mime-types": "~2.1.18", - "negotiator": "0.6.1" + "mime-types": "~2.1.24", + "negotiator": "0.6.2" + }, + "dependencies": { + "mime-db": { + "version": "1.40.0", + "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.40.0.tgz", + "integrity": "sha512-jYdeOMPy9vnxEqFRRo6ZvTZ8d9oPb+k18PKoYNYUe2stVEBPPwsln/qWzdbmaIvnhZ9v2P+CuecK+fpUfsV2mA==" + }, + "mime-types": { + "version": "2.1.24", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.24.tgz", + "integrity": "sha512-WaFHS3MCl5fapm3oLxU4eYDw77IQM2ACcxQ9RIxfaC3ooc6PFuBMGZZsYpvoXS5D5QTWPieo1jjLdAm3TBP3cQ==", + "requires": { + "mime-db": "1.40.0" + } + } } }, "ajv": { @@ -400,20 +415,20 @@ "integrity": "sha1-UzRK2xRhehP26N0s4okF0cC6MhU=" }, "body-parser": { - "version": "1.18.3", - "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.18.3.tgz", - "integrity": "sha1-WykhmP/dVTs6DyDe0FkrlWlVyLQ=", + "version": "1.19.0", + "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.19.0.tgz", + "integrity": "sha512-dhEPs72UPbDnAQJ9ZKMNTP6ptJaionhP5cBb541nXPlW60Jepo9RV/a4fX4XWW9CuFNK22krhrj1+rgzifNCsw==", "requires": { - "bytes": "3.0.0", + "bytes": "3.1.0", "content-type": "~1.0.4", "debug": "2.6.9", "depd": "~1.1.2", - "http-errors": "~1.6.3", - "iconv-lite": "0.4.23", + "http-errors": "1.7.2", + "iconv-lite": "0.4.24", "on-finished": "~2.3.0", - "qs": "6.5.2", - "raw-body": "2.3.3", - "type-is": "~1.6.16" + "qs": "6.7.0", + "raw-body": "2.4.0", + "type-is": "~1.6.17" }, "dependencies": { "debug": { @@ -423,6 +438,11 @@ "requires": { "ms": "2.0.0" } + }, + "qs": { + "version": "6.7.0", + "resolved": "https://registry.npmjs.org/qs/-/qs-6.7.0.tgz", + "integrity": "sha512-VCdBRNFTX1fyE7Nb6FYoURo/SPe62QCaAyzJvUjwRaIsc+NePBEniHlvxFmmX56+HZphIGtV0XeCirBtpDrTyQ==" } } }, @@ -549,9 +569,9 @@ "integrity": "sha1-YGSkD6dutDxyOrqe+PbhIW0QURo=" }, "bytes": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.0.0.tgz", - "integrity": "sha1-0ygVQE1olpn4Wk6k+odV3ROpYEg=" + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.0.tgz", + "integrity": "sha512-zauLjrfCG+xvoyaqLoV8bLVXXNGC4JqlxFCutSDWA6fJrTo2ZuvLYTqZ7aHBLZSMOopbzwv8f+wZcVzfVTI2Dg==" }, "cache-base": { "version": "1.0.1", @@ -610,10 +630,10 @@ "check-error": "^1.0.2" } }, - "chai-bignumber": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/chai-bignumber/-/chai-bignumber-2.0.2.tgz", - "integrity": "sha512-BIdRNjRaoRj4bMsZLKbIZPMNKqmwnzNiyxqBYDSs6dFOCs9w8OHPuUE8e1bH60i1IhOzT0NjLtCD+lKEWB1KTQ==", + "chai-bn": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/chai-bn/-/chai-bn-0.1.1.tgz", + "integrity": "sha512-e1npVXt3cQfZ6oQET9oP38vNj/4HeJ4ojeUpuC8YzhVbTJpIDqANVt7TKi7Dq9yKlHySk2FqbmiMih35iT4DYg==", "dev": true }, "chalk": { @@ -1349,6 +1369,28 @@ "vary": "~1.1.2" }, "dependencies": { + "body-parser": { + "version": "1.18.3", + "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.18.3.tgz", + "integrity": "sha1-WykhmP/dVTs6DyDe0FkrlWlVyLQ=", + "requires": { + "bytes": "3.0.0", + "content-type": "~1.0.4", + "debug": "2.6.9", + "depd": "~1.1.2", + "http-errors": "~1.6.3", + "iconv-lite": "0.4.23", + "on-finished": "~2.3.0", + "qs": "6.5.2", + "raw-body": "2.3.3", + "type-is": "~1.6.16" + } + }, + "bytes": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.0.0.tgz", + "integrity": "sha1-0ygVQE1olpn4Wk6k+odV3ROpYEg=" + }, "debug": { "version": "2.6.9", "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", @@ -1357,6 +1399,41 @@ "ms": "2.0.0" } }, + "http-errors": { + "version": "1.6.3", + "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.6.3.tgz", + "integrity": "sha1-i1VoC7S+KDoLW/TqLjhYC+HZMg0=", + "requires": { + "depd": "~1.1.2", + "inherits": "2.0.3", + "setprototypeof": "1.1.0", + "statuses": ">= 1.4.0 < 2" + } + }, + "iconv-lite": { + "version": "0.4.23", + "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.23.tgz", + "integrity": "sha512-neyTUVFtahjf0mB3dZT77u+8O0QB89jFdnBkd5P1JgYPbPaia3gXXOVL2fq8VyU2gMMD7SaN7QukTB/pmXYvDA==", + "requires": { + "safer-buffer": ">= 2.1.2 < 3" + } + }, + "raw-body": { + "version": "2.3.3", + "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-2.3.3.tgz", + "integrity": "sha512-9esiElv1BrZoI3rCDuOuKCBRbuApGGaDPQfjSflGxdy4oyzqghxu6klEkkVIvBje+FF0BX9coEv8KqW6X/7njw==", + "requires": { + "bytes": "3.0.0", + "http-errors": "1.6.3", + "iconv-lite": "0.4.23", + "unpipe": "1.0.0" + } + }, + "setprototypeof": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.1.0.tgz", + "integrity": "sha512-BvE/TwpZX4FXExxOxZyRGQQv651MSwmWKZGqvmPcRIjDqWub67kTKuIMx43cZZrS/cBBzwBcNDWoFxt2XEFIpQ==" + }, "statuses": { "version": "1.4.0", "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.4.0.tgz", @@ -2143,9 +2220,9 @@ "integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==" }, "ganache-cli": { - "version": "6.4.1", - "resolved": "https://registry.npmjs.org/ganache-cli/-/ganache-cli-6.4.1.tgz", - "integrity": "sha512-MUZ1DNnmlTrXnH6EuINuew75AI9d/wbIC0WpZCJo5Endsf6ZwEvfnfxGMpEnVizRri1mon2WWxLGAmALDxVcRQ==", + "version": "6.4.3", + "resolved": "https://registry.npmjs.org/ganache-cli/-/ganache-cli-6.4.3.tgz", + "integrity": "sha512-3G+CK4ojipDvxQHlpX8PjqaOMRWVcaLZZSW97Bv7fdcPTXQwkji2yY5CY6J12Atiub4M4aJc0va+q3HXeerbIA==", "requires": { "bn.js": "4.11.8", "source-map-support": "0.5.9", @@ -2154,28 +2231,23 @@ "dependencies": { "ansi-regex": { "version": "3.0.0", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", - "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=" + "bundled": true }, "bn.js": { "version": "4.11.8", - "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.11.8.tgz", - "integrity": "sha512-ItfYfPLkWHUjckQCk8xC+LwxgK8NYcXywGigJgSwOP8Y2iyWT4f2vsZnoOXTTbo+o5yXmIUJ4gn5538SO5S3gA==" + "bundled": true }, "buffer-from": { "version": "1.1.1", - "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.1.tgz", - "integrity": "sha512-MQcXEUbCKtEo7bhqEs6560Hyd4XaovZlO/k9V3hjVUF/zwW7KBVdSK4gIt/bzwS9MbR5qob+F5jusZsb0YQK2A==" + "bundled": true }, "camelcase": { "version": "4.1.0", - "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-4.1.0.tgz", - "integrity": "sha1-1UVjW+HjPFQmScaRc+Xeas+uNN0=" + "bundled": true }, "cliui": { "version": "4.1.0", - "resolved": "https://registry.npmjs.org/cliui/-/cliui-4.1.0.tgz", - "integrity": "sha512-4FG+RSG9DL7uEwRUZXZn3SS34DiDPfzP0VOiEwtUWlE+AR2EIg+hSyvrIgUUfhdgR/UkAeW2QHgeP+hWrXs7jQ==", + "bundled": true, "requires": { "string-width": "^2.1.1", "strip-ansi": "^4.0.0", @@ -2184,13 +2256,11 @@ }, "code-point-at": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/code-point-at/-/code-point-at-1.1.0.tgz", - "integrity": "sha1-DQcLTQQ6W+ozovGkDi7bPZpMz3c=" + "bundled": true }, "cross-spawn": { "version": "5.1.0", - "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-5.1.0.tgz", - "integrity": "sha1-6L0O/uWPz/b4+UUQoKVUu/ojVEk=", + "bundled": true, "requires": { "lru-cache": "^4.0.1", "shebang-command": "^1.2.0", @@ -2199,13 +2269,11 @@ }, "decamelize": { "version": "1.2.0", - "resolved": "https://registry.npmjs.org/decamelize/-/decamelize-1.2.0.tgz", - "integrity": "sha1-9lNNFRSCabIDUue+4m9QH5oZEpA=" + "bundled": true }, "execa": { "version": "0.7.0", - "resolved": "https://registry.npmjs.org/execa/-/execa-0.7.0.tgz", - "integrity": "sha1-lEvs00zEHuMqY6n68nrVpl/Fl3c=", + "bundled": true, "requires": { "cross-spawn": "^5.0.1", "get-stream": "^3.0.0", @@ -2218,54 +2286,45 @@ }, "find-up": { "version": "2.1.0", - "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", - "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", + "bundled": true, "requires": { "locate-path": "^2.0.0" } }, "get-caller-file": { "version": "1.0.3", - "resolved": "https://registry.npmjs.org/get-caller-file/-/get-caller-file-1.0.3.tgz", - "integrity": "sha512-3t6rVToeoZfYSGd8YoLFR2DJkiQrIiUrGcjvFX2mDw3bn6k2OtwHN0TNCLbBO+w8qTvimhDkv+LSscbJY1vE6w==" + "bundled": true }, "get-stream": { "version": "3.0.0", - "resolved": "http://registry.npmjs.org/get-stream/-/get-stream-3.0.0.tgz", - "integrity": "sha1-jpQ9E1jcN1VQVOy+LtsFqhdO3hQ=" + "bundled": true }, "invert-kv": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/invert-kv/-/invert-kv-1.0.0.tgz", - "integrity": "sha1-EEqOSqym09jNFXqO+L+rLXo//bY=" + "bundled": true }, "is-fullwidth-code-point": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", - "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=" + "bundled": true }, "is-stream": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-1.1.0.tgz", - "integrity": "sha1-EtSj3U5o4Lec6428hBc66A2RykQ=" + "bundled": true }, "isexe": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", - "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=" + "bundled": true }, "lcid": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/lcid/-/lcid-1.0.0.tgz", - "integrity": "sha1-MIrMr6C8SDo4Z7S28rlQYlHRuDU=", + "bundled": true, "requires": { "invert-kv": "^1.0.0" } }, "locate-path": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-2.0.0.tgz", - "integrity": "sha1-K1aLJl7slExtnA3pw9u7ygNUzY4=", + "bundled": true, "requires": { "p-locate": "^2.0.0", "path-exists": "^3.0.0" @@ -2273,8 +2332,7 @@ }, "lru-cache": { "version": "4.1.4", - "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-4.1.4.tgz", - "integrity": "sha512-EPstzZ23znHUVLKj+lcXO1KvZkrlw+ZirdwvOmnAnA/1PB4ggyXJ77LRkCqkff+ShQ+cqoxCxLQOh4cKITO5iA==", + "bundled": true, "requires": { "pseudomap": "^1.0.2", "yallist": "^3.0.2" @@ -2282,34 +2340,29 @@ }, "mem": { "version": "1.1.0", - "resolved": "https://registry.npmjs.org/mem/-/mem-1.1.0.tgz", - "integrity": "sha1-Xt1StIXKHZAP5kiVUFOZoN+kX3Y=", + "bundled": true, "requires": { "mimic-fn": "^1.0.0" } }, "mimic-fn": { "version": "1.2.0", - "resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-1.2.0.tgz", - "integrity": "sha512-jf84uxzwiuiIVKiOLpfYk7N46TSy8ubTonmneY9vrpHNAnp0QBt2BxWV9dO3/j+BoVAb+a5G6YDPW3M5HOdMWQ==" + "bundled": true }, "npm-run-path": { "version": "2.0.2", - "resolved": "https://registry.npmjs.org/npm-run-path/-/npm-run-path-2.0.2.tgz", - "integrity": "sha1-NakjLfo11wZ7TLLd8jV7GHFTbF8=", + "bundled": true, "requires": { "path-key": "^2.0.0" } }, "number-is-nan": { "version": "1.0.1", - "resolved": "https://registry.npmjs.org/number-is-nan/-/number-is-nan-1.0.1.tgz", - "integrity": "sha1-CXtgK1NCKlIsGvuHkDGDNpQaAR0=" + "bundled": true }, "os-locale": { "version": "2.1.0", - "resolved": "https://registry.npmjs.org/os-locale/-/os-locale-2.1.0.tgz", - "integrity": "sha512-3sslG3zJbEYcaC4YVAvDorjGxc7tv6KVATnLPZONiljsUncvihe9BQoVCEs0RZ1kmf4Hk9OBqlZfJZWI4GanKA==", + "bundled": true, "requires": { "execa": "^0.7.0", "lcid": "^1.0.0", @@ -2318,87 +2371,72 @@ }, "p-finally": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/p-finally/-/p-finally-1.0.0.tgz", - "integrity": "sha1-P7z7FbiZpEEjs0ttzBi3JDNqLK4=" + "bundled": true }, "p-limit": { "version": "1.3.0", - "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-1.3.0.tgz", - "integrity": "sha512-vvcXsLAJ9Dr5rQOPk7toZQZJApBl2K4J6dANSsEuh6QI41JYcsS/qhTGa9ErIUUgK3WNQoJYvylxvjqmiqEA9Q==", + "bundled": true, "requires": { "p-try": "^1.0.0" } }, "p-locate": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-2.0.0.tgz", - "integrity": "sha1-IKAQOyIqcMj9OcwuWAaA893l7EM=", + "bundled": true, "requires": { "p-limit": "^1.1.0" } }, "p-try": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/p-try/-/p-try-1.0.0.tgz", - "integrity": "sha1-y8ec26+P1CKOE/Yh8rGiN8GyB7M=" + "bundled": true }, "path-exists": { "version": "3.0.0", - "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", - "integrity": "sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=" + "bundled": true }, "path-key": { "version": "2.0.1", - "resolved": "https://registry.npmjs.org/path-key/-/path-key-2.0.1.tgz", - "integrity": "sha1-QRyttXTFoUDTpLGRDUDYDMn0C0A=" + "bundled": true }, "pseudomap": { "version": "1.0.2", - "resolved": "https://registry.npmjs.org/pseudomap/-/pseudomap-1.0.2.tgz", - "integrity": "sha1-8FKijacOYYkX7wqKw0wa5aaChrM=" + "bundled": true }, "require-directory": { "version": "2.1.1", - "resolved": "https://registry.npmjs.org/require-directory/-/require-directory-2.1.1.tgz", - "integrity": "sha1-jGStX9MNqxyXbiNE/+f3kqam30I=" + "bundled": true }, "require-main-filename": { "version": "1.0.1", - "resolved": "https://registry.npmjs.org/require-main-filename/-/require-main-filename-1.0.1.tgz", - "integrity": "sha1-l/cXtp1IeE9fUmpsWqj/3aBVpNE=" + "bundled": true }, "set-blocking": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/set-blocking/-/set-blocking-2.0.0.tgz", - "integrity": "sha1-BF+XgtARrppoA93TgrJDkrPYkPc=" + "bundled": true }, "shebang-command": { "version": "1.2.0", - "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-1.2.0.tgz", - "integrity": "sha1-RKrGW2lbAzmJaMOfNj/uXer98eo=", + "bundled": true, "requires": { "shebang-regex": "^1.0.0" } }, "shebang-regex": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-1.0.0.tgz", - "integrity": "sha1-2kL0l0DAtC2yypcoVxyxkMmO/qM=" + "bundled": true }, "signal-exit": { "version": "3.0.2", - "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.2.tgz", - "integrity": "sha1-tf3AjxKH6hF4Yo5BXiUTK3NkbG0=" + "bundled": true }, "source-map": { "version": "0.6.1", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", - "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==" + "bundled": true }, "source-map-support": { "version": "0.5.9", - "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.9.tgz", - "integrity": "sha512-gR6Rw4MvUlYy83vP0vxoVNzM6t8MUXqNuRsuBmBHQDu1Fh6X015FrLdgoDKcNdkwGubozq0P4N0Q37UyFVr1EA==", + "bundled": true, "requires": { "buffer-from": "^1.0.0", "source-map": "^0.6.0" @@ -2406,8 +2444,7 @@ }, "string-width": { "version": "2.1.1", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", - "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", + "bundled": true, "requires": { "is-fullwidth-code-point": "^2.0.0", "strip-ansi": "^4.0.0" @@ -2415,34 +2452,29 @@ }, "strip-ansi": { "version": "4.0.0", - "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", - "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", + "bundled": true, "requires": { "ansi-regex": "^3.0.0" } }, "strip-eof": { "version": "1.0.0", - "resolved": "http://registry.npmjs.org/strip-eof/-/strip-eof-1.0.0.tgz", - "integrity": "sha1-u0P/VZim6wXYm1n80SnJgzE2Br8=" + "bundled": true }, "which": { "version": "1.3.1", - "resolved": "https://registry.npmjs.org/which/-/which-1.3.1.tgz", - "integrity": "sha512-HxJdYWq1MTIQbJ3nw0cqssHoTNU267KlrDuGZ1WYlxDStUtKUhOaJmh112/TZmHxxUfuJqPXSOm7tDyas0OSIQ==", + "bundled": true, "requires": { "isexe": "^2.0.0" } }, "which-module": { "version": "2.0.0", - "resolved": "https://registry.npmjs.org/which-module/-/which-module-2.0.0.tgz", - "integrity": "sha1-2e8H3Od7mQK4o6j6SzHD4/fm6Ho=" + "bundled": true }, "wrap-ansi": { "version": "2.1.0", - "resolved": "http://registry.npmjs.org/wrap-ansi/-/wrap-ansi-2.1.0.tgz", - "integrity": "sha1-2Pw9KE3QV5T+hJc8rs3Rz4JP3YU=", + "bundled": true, "requires": { "string-width": "^1.0.1", "strip-ansi": "^3.0.1" @@ -2450,21 +2482,18 @@ "dependencies": { "ansi-regex": { "version": "2.1.1", - "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz", - "integrity": "sha1-w7M6te42DYbg5ijwRorn7yfWVN8=" + "bundled": true }, "is-fullwidth-code-point": { "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz", - "integrity": "sha1-754xOG8DGn8NZDr4L95QxFfvAMs=", + "bundled": true, "requires": { "number-is-nan": "^1.0.0" } }, "string-width": { "version": "1.0.2", - "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz", - "integrity": "sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=", + "bundled": true, "requires": { "code-point-at": "^1.0.0", "is-fullwidth-code-point": "^1.0.0", @@ -2473,8 +2502,7 @@ }, "strip-ansi": { "version": "3.0.1", - "resolved": "http://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", - "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", + "bundled": true, "requires": { "ansi-regex": "^2.0.0" } @@ -2483,18 +2511,15 @@ }, "y18n": { "version": "3.2.1", - "resolved": "https://registry.npmjs.org/y18n/-/y18n-3.2.1.tgz", - "integrity": "sha1-bRX7qITAhnnA136I53WegR4H+kE=" + "bundled": true }, "yallist": { "version": "3.0.2", - "resolved": "https://registry.npmjs.org/yallist/-/yallist-3.0.2.tgz", - "integrity": "sha1-hFK0u36Dx8GI2AQcGoN8dz1ti7k=" + "bundled": true }, "yargs": { "version": "11.1.0", - "resolved": "http://registry.npmjs.org/yargs/-/yargs-11.1.0.tgz", - "integrity": "sha512-NwW69J42EsCSanF8kyn5upxvjp5ds+t3+udGBeTbFnERA+lF541DDpMawzo4z6W/QrzNM18D+BPMiOBibnFV5A==", + "bundled": true, "requires": { "cliui": "^4.0.0", "decamelize": "^1.1.1", @@ -2512,8 +2537,7 @@ }, "yargs-parser": { "version": "9.0.2", - "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-9.0.2.tgz", - "integrity": "sha1-nM9qQ0YP5O1Aqbto9I1DuKaMwHc=", + "bundled": true, "requires": { "camelcase": "^4.1.0" } @@ -2638,9 +2662,9 @@ "integrity": "sha512-hKlsbA5Vu3xsh1Cg3J7jSmX/WaW6A5oBeqzM88oNbCRQFz+zUaXm6yxS4RVytp1scBoJzSYl4YAEOQIt6O8V1Q==" }, "handlebars": { - "version": "4.1.1", - "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.1.1.tgz", - "integrity": "sha512-3Zhi6C0euYZL5sM0Zcy7lInLXKQ+YLcF/olbN010mzGQ4XVm50JeyBnMqofHh696GrciGruC7kCcApPDJvVgwA==", + "version": "4.1.2", + "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.1.2.tgz", + "integrity": "sha512-nvfrjqvt9xQ8Z/w0ijewdD/vvWDTOweBUm96NTr66Wfvo1mJenBLwcYmPs3TIBP5ruzYGD7Hx/DaM9RmhroGPw==", "dev": true, "requires": { "neo-async": "^2.6.0", @@ -2764,14 +2788,15 @@ } }, "http-errors": { - "version": "1.6.3", - "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.6.3.tgz", - "integrity": "sha1-i1VoC7S+KDoLW/TqLjhYC+HZMg0=", + "version": "1.7.2", + "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.7.2.tgz", + "integrity": "sha512-uUQBt3H/cSIVfch6i1EuPNy/YsRSOUBXTVfZ+yR7Zjez3qjBz6i9+i4zjNaoqcoFVI4lQJ5plg63TvGfRSDCRg==", "requires": { "depd": "~1.1.2", "inherits": "2.0.3", - "setprototypeof": "1.1.0", - "statuses": ">= 1.4.0 < 2" + "setprototypeof": "1.1.1", + "statuses": ">= 1.5.0 < 2", + "toidentifier": "1.0.0" } }, "http-response-object": { @@ -2794,9 +2819,9 @@ } }, "iconv-lite": { - "version": "0.4.23", - "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.23.tgz", - "integrity": "sha512-neyTUVFtahjf0mB3dZT77u+8O0QB89jFdnBkd5P1JgYPbPaia3gXXOVL2fq8VyU2gMMD7SaN7QukTB/pmXYvDA==", + "version": "0.4.24", + "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.24.tgz", + "integrity": "sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==", "requires": { "safer-buffer": ">= 2.1.2 < 3" } @@ -2851,9 +2876,9 @@ "integrity": "sha1-EEqOSqym09jNFXqO+L+rLXo//bY=" }, "ipaddr.js": { - "version": "1.8.0", - "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.8.0.tgz", - "integrity": "sha1-6qM9bd16zo9/b+DJygRA5wZzix4=" + "version": "1.9.0", + "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.9.0.tgz", + "integrity": "sha512-M4Sjn6N/+O6/IXSJseKqHoFc+5FdGJ22sXqnjTpdZweHK64MzEPAyQZyEU3R/KRv2GLoa7nNtg/C2Ev6m7z+eA==" }, "is-accessor-descriptor": { "version": "0.1.6", @@ -3204,9 +3229,9 @@ "integrity": "sha1-W4n3enR3Z5h39YxKB1JAk0sflcA=" }, "js-yaml": { - "version": "3.13.0", - "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.13.0.tgz", - "integrity": "sha512-pZZoSxcCYco+DIKBTimr67J6Hy+EYGZDY/HCWC+iAEA9h1ByhMXAIVUXMcMFpOCxQ/xjXmPI2MkDL5HRm5eFrQ==", + "version": "3.13.1", + "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.13.1.tgz", + "integrity": "sha512-YfbcO7jXDdyj0DGxYVSlSeQNHbD7XPWvrVWeVUujrQEoZzWJIRrCPoyk6kL6IAjAG2IolMK4T0hNUe0HOUs5Jw==", "dev": true, "requires": { "argparse": "^1.0.7", @@ -3598,9 +3623,9 @@ } }, "negotiator": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-0.6.1.tgz", - "integrity": "sha1-KzJxhOiZIQEXeyhWP7XnECrNDKk=" + "version": "0.6.2", + "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-0.6.2.tgz", + "integrity": "sha512-hZXc7K2e+PgeI1eDBe/10Ard4ekbfrrqG8Ep+8Jmf4JID2bNg7NvCPOZN+kfF574pFQI7mum2AUqDidoKqcTOw==" }, "neo-async": { "version": "2.6.0", @@ -3734,9 +3759,9 @@ } }, "object-keys": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/object-keys/-/object-keys-1.1.0.tgz", - "integrity": "sha512-6OO5X1+2tYkNyNEx6TsCxEqFfRWaqx6EtMiSbGrw8Ob8v9Ne+Hl8rBAgLBZn5wjEz3s/s6U1WXFUFOcxxAwUpg==" + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/object-keys/-/object-keys-1.1.1.tgz", + "integrity": "sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==" }, "object-visit": { "version": "1.0.1", @@ -3886,9 +3911,9 @@ } }, "parseurl": { - "version": "1.3.2", - "resolved": "https://registry.npmjs.org/parseurl/-/parseurl-1.3.2.tgz", - "integrity": "sha1-/CidTtiZMRlGDBViUyYs3I3mW/M=" + "version": "1.3.3", + "resolved": "https://registry.npmjs.org/parseurl/-/parseurl-1.3.3.tgz", + "integrity": "sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==" }, "pascalcase": { "version": "0.1.1", @@ -4026,12 +4051,12 @@ } }, "proxy-addr": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.4.tgz", - "integrity": "sha512-5erio2h9jp5CHGwcybmxmVqHmnCBZeewlfJ0pex+UW7Qny7OOZXTtH56TGNyBizkgiOwhJtMKrVzDTeKcySZwA==", + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.5.tgz", + "integrity": "sha512-t/7RxHXPH6cJtP0pRG6smSr9QJidhB+3kXu0KgXnbGYMgzEnUxRQ4/LDdfOwZEMyIh3/xHb8PX3t+lfL9z+YVQ==", "requires": { "forwarded": "~0.1.2", - "ipaddr.js": "1.8.0" + "ipaddr.js": "1.9.0" } }, "pseudomap": { @@ -4081,13 +4106,13 @@ "integrity": "sha1-9JvmtIeJTdxA3MlKMi9hEJLgDV4=" }, "raw-body": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-2.3.3.tgz", - "integrity": "sha512-9esiElv1BrZoI3rCDuOuKCBRbuApGGaDPQfjSflGxdy4oyzqghxu6klEkkVIvBje+FF0BX9coEv8KqW6X/7njw==", + "version": "2.4.0", + "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-2.4.0.tgz", + "integrity": "sha512-4Oz8DUIwdvoa5qMJelxipzi/iJIi40O5cGV1wNYp5hvZP8ZN0T+jiNkL0QepXs+EsQ9XJ8ipEDoiH70ySUJP3Q==", "requires": { - "bytes": "3.0.0", - "http-errors": "1.6.3", - "iconv-lite": "0.4.23", + "bytes": "3.1.0", + "http-errors": "1.7.2", + "iconv-lite": "0.4.24", "unpipe": "1.0.0" } }, @@ -4405,6 +4430,22 @@ "ms": "2.0.0" } }, + "http-errors": { + "version": "1.6.3", + "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.6.3.tgz", + "integrity": "sha1-i1VoC7S+KDoLW/TqLjhYC+HZMg0=", + "requires": { + "depd": "~1.1.2", + "inherits": "2.0.3", + "setprototypeof": "1.1.0", + "statuses": ">= 1.4.0 < 2" + } + }, + "setprototypeof": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.1.0.tgz", + "integrity": "sha512-BvE/TwpZX4FXExxOxZyRGQQv651MSwmWKZGqvmPcRIjDqWub67kTKuIMx43cZZrS/cBBzwBcNDWoFxt2XEFIpQ==" + }, "statuses": { "version": "1.4.0", "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.4.0.tgz", @@ -4464,9 +4505,9 @@ } }, "setprototypeof": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.1.0.tgz", - "integrity": "sha512-BvE/TwpZX4FXExxOxZyRGQQv651MSwmWKZGqvmPcRIjDqWub67kTKuIMx43cZZrS/cBBzwBcNDWoFxt2XEFIpQ==" + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.1.1.tgz", + "integrity": "sha512-JvdAWfbXeIGaZ9cILp38HntZSFSo3mWg6xGcJJsd+d4aRMOqauag1C63dJfDw7OaMYwEbHMOxEZ1lqVRYP2OAw==" }, "sha1": { "version": "1.1.1", @@ -5139,6 +5180,11 @@ "repeat-string": "^1.6.1" } }, + "toidentifier": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/toidentifier/-/toidentifier-1.0.0.tgz", + "integrity": "sha512-yaOH/Pk/VEhBWWTlhI+qXxDFXlejDGcQipMlyxda9nthulaxLZUNcUqFxokp0vcYnvteJln5FNQDRrxj3YcbVw==" + }, "touch": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/touch/-/touch-3.1.0.tgz", @@ -5246,12 +5292,27 @@ "dev": true }, "type-is": { - "version": "1.6.16", - "resolved": "https://registry.npmjs.org/type-is/-/type-is-1.6.16.tgz", - "integrity": "sha512-HRkVv/5qY2G6I8iab9cI7v1bOIdhm94dVjQCPFElW9W+3GeDOSHmy2EBYe4VTApuzolPcmgFTN3ftVJRKR2J9Q==", + "version": "1.6.18", + "resolved": "https://registry.npmjs.org/type-is/-/type-is-1.6.18.tgz", + "integrity": "sha512-TkRKr9sUTxEH8MdfuCSP7VizJyzRNMjj2J2do2Jr3Kym598JVdEksuzPQCnlFPW4ky9Q+iA+ma9BGm06XQBy8g==", "requires": { "media-typer": "0.3.0", - "mime-types": "~2.1.18" + "mime-types": "~2.1.24" + }, + "dependencies": { + "mime-db": { + "version": "1.40.0", + "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.40.0.tgz", + "integrity": "sha512-jYdeOMPy9vnxEqFRRo6ZvTZ8d9oPb+k18PKoYNYUe2stVEBPPwsln/qWzdbmaIvnhZ9v2P+CuecK+fpUfsV2mA==" + }, + "mime-types": { + "version": "2.1.24", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.24.tgz", + "integrity": "sha512-WaFHS3MCl5fapm3oLxU4eYDw77IQM2ACcxQ9RIxfaC3ooc6PFuBMGZZsYpvoXS5D5QTWPieo1jjLdAm3TBP3cQ==", + "requires": { + "mime-db": "1.40.0" + } + } } }, "typedarray": { @@ -5261,20 +5322,20 @@ "dev": true }, "uglify-js": { - "version": "3.5.3", - "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-3.5.3.tgz", - "integrity": "sha512-rIQPT2UMDnk4jRX+w4WO84/pebU2jiLsjgIyrCktYgSvx28enOE3iYQMr+BD1rHiitWnDmpu0cY/LfIEpKcjcw==", + "version": "3.5.11", + "resolved": "https://registry.npmjs.org/uglify-js/-/uglify-js-3.5.11.tgz", + "integrity": "sha512-izPJg8RsSyqxbdnqX36ExpbH3K7tDBsAU/VfNv89VkMFy3z39zFjunQGsSHOlGlyIfGLGprGeosgQno3bo2/Kg==", "dev": true, "optional": true, "requires": { - "commander": "~2.19.0", + "commander": "~2.20.0", "source-map": "~0.6.1" }, "dependencies": { "commander": { - "version": "2.19.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-2.19.0.tgz", - "integrity": "sha512-6tvAOO+D6OENvRAh524Dh9jcfKTYDQAqvqezbCW82xj5X0pSrcpxtvRKHLG0yBY6SD7PSDrJaj+0AiOcKVd1Xg==", + "version": "2.20.0", + "resolved": "https://registry.npmjs.org/commander/-/commander-2.20.0.tgz", + "integrity": "sha512-7j2y+40w61zy6YC2iRNpUe/NwhNyoXrYpHMrSunaMG64nRnaf96zO/KMQR4OyN/UnE5KLyEBnKHd4aG3rskjpQ==", "dev": true, "optional": true }, @@ -5530,9 +5591,9 @@ } }, "web3-utils": { - "version": "1.0.0-beta.34", - "resolved": "https://registry.npmjs.org/web3-utils/-/web3-utils-1.0.0-beta.34.tgz", - "integrity": "sha1-lBH8OarvOcpOBhafdiKX2f8CCXA=", + "version": "1.0.0-beta.37", + "resolved": "https://registry.npmjs.org/web3-utils/-/web3-utils-1.0.0-beta.37.tgz", + "integrity": "sha512-kA1fyhO8nKgU21wi30oJQ/ssvu+9srMdjOTKbHYbQe4ATPcr5YNwwrxG3Bcpbu1bEwRUVKHCkqi+wTvcAWBdlQ==", "requires": { "bn.js": "4.11.6", "eth-lib": "0.1.27", diff --git a/package.json b/package.json index d72488cf6..8e4c88b4e 100644 --- a/package.json +++ b/package.json @@ -13,15 +13,15 @@ "author": "POA network", "license": "GPLv3", "dependencies": { - "ganache-cli": "^6.1.0", + "ganache-cli": "^6.4.3", "openzeppelin-solidity": "^1.10.0", "truffle": "^5.0.15", - "web3-utils": "1.0.0-beta.34" + "web3-utils": "1.0.0-beta.37" }, "devDependencies": { - "chai": "^4.1.2", + "chai": "^4.2.0", "chai-as-promised": "^7.1.1", - "chai-bignumber": "^2.0.2", + "chai-bn": "^0.1.1", "eth-gas-reporter": "^0.1.12", "nodemon": "^1.17.3", "solidity-coverage": "^0.5.11", diff --git a/test/setup.js b/test/setup.js index 2e713af02..3ede476e6 100644 --- a/test/setup.js +++ b/test/setup.js @@ -1,10 +1,12 @@ -var BigNumber = web3.BigNumber; +const BN = web3.utils.BN; require('chai') .use(require('chai-as-promised')) - .use(require('chai-bignumber')(BigNumber)) - .should(); + .use(require('chai-bn')(BN)) +require('chai/register-should'); + +exports.BN = BN exports.ERROR_MSG = 'VM Exception while processing transaction: revert'; exports.ERROR_MSG_OPCODE = 'VM Exception while processing transaction: invalid opcode'; exports.ZERO_ADDRESS = '0x0000000000000000000000000000000000000000' From 9538a7866597c71d68597e4f71c97cff9f31eede Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Thu, 9 May 2019 10:20:31 -0300 Subject: [PATCH 183/187] remove web3-utils --- package-lock.json | 994 +++++----------------------------------------- package.json | 3 +- 2 files changed, 90 insertions(+), 907 deletions(-) diff --git a/package-lock.json b/package-lock.json index ad3b00891..fdb49d629 100644 --- a/package-lock.json +++ b/package-lock.json @@ -91,34 +91,11 @@ "web3": "^0.18.4" } }, - "accepts": { - "version": "1.3.7", - "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.7.tgz", - "integrity": "sha512-Il80Qs2WjYlJIBNzNkK6KYqlVMTbZLXgHx2oT0pU/fjRHyEp+PEfEPY0R3WCwAGVOtauxh1hOxNgIf5bv7dQpA==", - "requires": { - "mime-types": "~2.1.24", - "negotiator": "0.6.2" - }, - "dependencies": { - "mime-db": { - "version": "1.40.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.40.0.tgz", - "integrity": "sha512-jYdeOMPy9vnxEqFRRo6ZvTZ8d9oPb+k18PKoYNYUe2stVEBPPwsln/qWzdbmaIvnhZ9v2P+CuecK+fpUfsV2mA==" - }, - "mime-types": { - "version": "2.1.24", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.24.tgz", - "integrity": "sha512-WaFHS3MCl5fapm3oLxU4eYDw77IQM2ACcxQ9RIxfaC3ooc6PFuBMGZZsYpvoXS5D5QTWPieo1jjLdAm3TBP3cQ==", - "requires": { - "mime-db": "1.40.0" - } - } - } - }, "ajv": { "version": "6.10.0", "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.10.0.tgz", "integrity": "sha512-nffhOpkymDECQyR0mnsUtoCE8RlX38G0rYP+wgLWFyZuUyuuojSSvi/+euOiQBIn63whYwYVIIH1TvE3tu4OEg==", + "dev": true, "requires": { "fast-deep-equal": "^2.0.1", "fast-json-stable-stringify": "^2.0.0", @@ -242,11 +219,6 @@ "integrity": "sha1-45sJrqne+Gao8gbiiK9jkZuuOcQ=", "dev": true }, - "array-flatten": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-1.1.1.tgz", - "integrity": "sha1-ml9pkFGx5wczKPKgCJaLZOopVdI=" - }, "array-unique": { "version": "0.3.2", "resolved": "https://registry.npmjs.org/array-unique/-/array-unique-0.3.2.tgz", @@ -263,6 +235,7 @@ "version": "0.2.4", "resolved": "https://registry.npmjs.org/asn1/-/asn1-0.2.4.tgz", "integrity": "sha512-jxwzQpLQjSmWXgwaCZE9Nz+glAG01yF1QnWgbhGwHI5A6FRIEY6IVqtHhIepHqI7/kyEyQEagBC5mBEFlIYvdg==", + "dev": true, "requires": { "safer-buffer": "~2.1.0" } @@ -270,7 +243,8 @@ "assert-plus": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", - "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=" + "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=", + "dev": true }, "assertion-error": { "version": "1.1.0", @@ -296,15 +270,11 @@ "integrity": "sha512-6xrbvN0MOBKSJDdonmSSz2OwFSgxRaVtBDes26mj9KIGtDo+g9xosFRSC+i1gQh2oAN/tQ62AI/pGZGQjVOiRg==", "dev": true }, - "async-limiter": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/async-limiter/-/async-limiter-1.0.0.tgz", - "integrity": "sha512-jp/uFnooOiO+L211eZOoSyzpOITMXx1rBITauYykG3BRYPu8h0UcxsPNB04RR5vo4Tyz3+ay17tR6JVf9qzYWg==" - }, "asynckit": { "version": "0.4.0", "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", - "integrity": "sha1-x57Zf380y48robyXkLzDZkdLS3k=" + "integrity": "sha1-x57Zf380y48robyXkLzDZkdLS3k=", + "dev": true }, "atob": { "version": "2.1.2", @@ -315,12 +285,14 @@ "aws-sign2": { "version": "0.7.0", "resolved": "https://registry.npmjs.org/aws-sign2/-/aws-sign2-0.7.0.tgz", - "integrity": "sha1-tG6JCTSpWR8tL2+G1+ap8bP+dqg=" + "integrity": "sha1-tG6JCTSpWR8tL2+G1+ap8bP+dqg=", + "dev": true }, "aws4": { "version": "1.8.0", "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.8.0.tgz", - "integrity": "sha512-ReZxvNHIOv88FlT7rxcXIIC0fPt4KZqZbOlivyWtXLt8ESx84zd3kMC6iK5jVeS2qt+g7ftS7ye4fi06X5rtRQ==" + "integrity": "sha512-ReZxvNHIOv88FlT7rxcXIIC0fPt4KZqZbOlivyWtXLt8ESx84zd3kMC6iK5jVeS2qt+g7ftS7ye4fi06X5rtRQ==", + "dev": true }, "balanced-match": { "version": "1.0.0", @@ -386,6 +358,7 @@ "version": "1.0.2", "resolved": "https://registry.npmjs.org/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.2.tgz", "integrity": "sha1-pDAdOJtqQ/m2f/PKEaP2Y342Dp4=", + "dev": true, "requires": { "tweetnacl": "^0.14.3" } @@ -409,43 +382,6 @@ "file-uri-to-path": "1.0.0" } }, - "bn.js": { - "version": "4.11.6", - "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.11.6.tgz", - "integrity": "sha1-UzRK2xRhehP26N0s4okF0cC6MhU=" - }, - "body-parser": { - "version": "1.19.0", - "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.19.0.tgz", - "integrity": "sha512-dhEPs72UPbDnAQJ9ZKMNTP6ptJaionhP5cBb541nXPlW60Jepo9RV/a4fX4XWW9CuFNK22krhrj1+rgzifNCsw==", - "requires": { - "bytes": "3.1.0", - "content-type": "~1.0.4", - "debug": "2.6.9", - "depd": "~1.1.2", - "http-errors": "1.7.2", - "iconv-lite": "0.4.24", - "on-finished": "~2.3.0", - "qs": "6.7.0", - "raw-body": "2.4.0", - "type-is": "~1.6.17" - }, - "dependencies": { - "debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "requires": { - "ms": "2.0.0" - } - }, - "qs": { - "version": "6.7.0", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.7.0.tgz", - "integrity": "sha512-VCdBRNFTX1fyE7Nb6FYoURo/SPe62QCaAyzJvUjwRaIsc+NePBEniHlvxFmmX56+HZphIGtV0XeCirBtpDrTyQ==" - } - } - }, "boxen": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/boxen/-/boxen-1.3.0.tgz", @@ -538,11 +474,6 @@ } } }, - "brorand": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/brorand/-/brorand-1.1.0.tgz", - "integrity": "sha1-EsJe/kCkXjwyPrhnWgoM5XsiNx8=" - }, "browser-stdout": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/browser-stdout/-/browser-stdout-1.3.0.tgz", @@ -552,6 +483,7 @@ "version": "0.0.4", "resolved": "https://registry.npmjs.org/browserify-sha3/-/browserify-sha3-0.0.4.tgz", "integrity": "sha1-CGxHuMgjFsnUcCLCYYWVRXbdjiY=", + "dev": true, "requires": { "js-sha3": "^0.6.1", "safe-buffer": "^5.1.1" @@ -563,16 +495,6 @@ "integrity": "sha512-MQcXEUbCKtEo7bhqEs6560Hyd4XaovZlO/k9V3hjVUF/zwW7KBVdSK4gIt/bzwS9MbR5qob+F5jusZsb0YQK2A==", "dev": true }, - "buffer-to-arraybuffer": { - "version": "0.0.5", - "resolved": "https://registry.npmjs.org/buffer-to-arraybuffer/-/buffer-to-arraybuffer-0.0.5.tgz", - "integrity": "sha1-YGSkD6dutDxyOrqe+PbhIW0QURo=" - }, - "bytes": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.0.tgz", - "integrity": "sha512-zauLjrfCG+xvoyaqLoV8bLVXXNGC4JqlxFCutSDWA6fJrTo2ZuvLYTqZ7aHBLZSMOopbzwv8f+wZcVzfVTI2Dg==" - }, "cache-base": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/cache-base/-/cache-base-1.0.1.tgz", @@ -605,7 +527,8 @@ "caseless": { "version": "0.12.0", "resolved": "https://registry.npmjs.org/caseless/-/caseless-0.12.0.tgz", - "integrity": "sha1-G2gcIf+EAzyCZUMJBolCDRhxUdw=" + "integrity": "sha1-G2gcIf+EAzyCZUMJBolCDRhxUdw=", + "dev": true }, "chai": { "version": "4.2.0", @@ -826,6 +749,7 @@ "version": "1.0.7", "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.7.tgz", "integrity": "sha512-brWl9y6vOB1xYPZcpZde3N9zDByXTosAeMDo4p1wzo6UMOX4vumB+TP1RZ76sfE6Md68Q0NJSrE/gbezd4Ul+w==", + "dev": true, "requires": { "delayed-stream": "~1.0.0" } @@ -872,26 +796,6 @@ "xdg-basedir": "^3.0.0" } }, - "content-disposition": { - "version": "0.5.2", - "resolved": "https://registry.npmjs.org/content-disposition/-/content-disposition-0.5.2.tgz", - "integrity": "sha1-DPaLud318r55YcOoUXjLhdunjLQ=" - }, - "content-type": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/content-type/-/content-type-1.0.4.tgz", - "integrity": "sha512-hIP3EEPs8tB9AT1L+NUqtwOAps4mk2Zob89MWXMHjHWg9milF/j4osnnQLXBCBFBk/tvIG/tUc9mOUJiPBhPXA==" - }, - "cookie": { - "version": "0.3.1", - "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.3.1.tgz", - "integrity": "sha1-5+Ch+e9DtMi6klxcWpboBtFoc7s=" - }, - "cookie-signature": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz", - "integrity": "sha1-4wOogrNCzD7oylE6eZmXNNqzriw=" - }, "copy-descriptor": { "version": "0.1.1", "resolved": "https://registry.npmjs.org/copy-descriptor/-/copy-descriptor-0.1.1.tgz", @@ -901,16 +805,8 @@ "core-util-is": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz", - "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=" - }, - "cors": { - "version": "2.8.5", - "resolved": "https://registry.npmjs.org/cors/-/cors-2.8.5.tgz", - "integrity": "sha512-KIHbLJqu73RGr/hnbrO9uBeixNGuvSQjul/jdFvS/KFSIH1hWVd1ng7zOHx+YrEfInLG7q4n6GHQ9cDtxv/P6g==", - "requires": { - "object-assign": "^4", - "vary": "^1" - } + "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=", + "dev": true }, "create-error-class": { "version": "3.0.2", @@ -953,6 +849,7 @@ "version": "1.14.1", "resolved": "https://registry.npmjs.org/dashdash/-/dashdash-1.14.1.tgz", "integrity": "sha1-hTz6D3y+L+1d4gMmuN1YEDX24vA=", + "dev": true, "requires": { "assert-plus": "^1.0.0" } @@ -979,15 +876,8 @@ "decode-uri-component": { "version": "0.2.0", "resolved": "https://registry.npmjs.org/decode-uri-component/-/decode-uri-component-0.2.0.tgz", - "integrity": "sha1-6zkTMzRYd1y4TNGh+uBiEGu4dUU=" - }, - "decompress-response": { - "version": "3.3.0", - "resolved": "https://registry.npmjs.org/decompress-response/-/decompress-response-3.3.0.tgz", - "integrity": "sha1-gKTdMjdIOEv6JICDYirt7Jgq3/M=", - "requires": { - "mimic-response": "^1.0.0" - } + "integrity": "sha1-6zkTMzRYd1y4TNGh+uBiEGu4dUU=", + "dev": true }, "deep-eql": { "version": "3.0.1", @@ -1010,14 +900,6 @@ "integrity": "sha1-s2nW+128E+7PUk+RsHD+7cNXzzQ=", "dev": true }, - "define-properties": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/define-properties/-/define-properties-1.1.3.tgz", - "integrity": "sha512-3MqfYKj2lLzdMSf8ZIZE/V+Zuy+BgD6f164e8K2w7dgnpKArBDerGYpM46IYYcjnkdPNMjPk9A6VFB8+3SKlXQ==", - "requires": { - "object-keys": "^1.0.12" - } - }, "define-property": { "version": "2.0.2", "resolved": "https://registry.npmjs.org/define-property/-/define-property-2.0.2.tgz", @@ -1062,28 +944,14 @@ "delayed-stream": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", - "integrity": "sha1-3zrhmayt+31ECqrgsp4icrJOxhk=" - }, - "depd": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/depd/-/depd-1.1.2.tgz", - "integrity": "sha1-m81S4UwJd2PnSbJ0xDRu0uVgtak=" - }, - "destroy": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/destroy/-/destroy-1.0.4.tgz", - "integrity": "sha1-l4hXRCxEdJ5CBmE+N5RiBYJqvYA=" + "integrity": "sha1-3zrhmayt+31ECqrgsp4icrJOxhk=", + "dev": true }, "diff": { "version": "3.3.1", "resolved": "https://registry.npmjs.org/diff/-/diff-3.3.1.tgz", "integrity": "sha512-MKPHZDMB0o6yHyDryUOScqZibp914ksXwAMYMTHj6KO8UeKsRYNJD3oNCKjTqZon+V488P7N/HzXF8t7ZR95ww==" }, - "dom-walk": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/dom-walk/-/dom-walk-0.1.1.tgz", - "integrity": "sha1-ZyIm3HTI95mtNTB9+TaroRrNYBg=" - }, "dot-prop": { "version": "4.2.0", "resolved": "https://registry.npmjs.org/dot-prop/-/dot-prop-4.2.0.tgz", @@ -1103,35 +971,12 @@ "version": "0.1.2", "resolved": "https://registry.npmjs.org/ecc-jsbn/-/ecc-jsbn-0.1.2.tgz", "integrity": "sha1-OoOpBOVDUyh4dMVkt1SThoSamMk=", + "dev": true, "requires": { "jsbn": "~0.1.0", "safer-buffer": "^2.1.0" } }, - "ee-first": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/ee-first/-/ee-first-1.1.1.tgz", - "integrity": "sha1-WQxhFWsK4vTwJVcyoViyZrxWsh0=" - }, - "elliptic": { - "version": "6.4.1", - "resolved": "https://registry.npmjs.org/elliptic/-/elliptic-6.4.1.tgz", - "integrity": "sha512-BsXLz5sqX8OHcsh7CqBMztyXARmGQ3LWPtGjJi6DiJHq5C/qvi9P3OqgswKSDftbu8+IoI/QDTAm2fFnQ9SZSQ==", - "requires": { - "bn.js": "^4.4.0", - "brorand": "^1.0.1", - "hash.js": "^1.0.0", - "hmac-drbg": "^1.0.0", - "inherits": "^2.0.1", - "minimalistic-assert": "^1.0.0", - "minimalistic-crypto-utils": "^1.0.0" - } - }, - "encodeurl": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-1.0.2.tgz", - "integrity": "sha1-rT/0yG7C0CkyL1oCw6mmBslbP1k=" - }, "error-ex": { "version": "1.3.2", "resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.2.tgz", @@ -1141,34 +986,6 @@ "is-arrayish": "^0.2.1" } }, - "es-abstract": { - "version": "1.13.0", - "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.13.0.tgz", - "integrity": "sha512-vDZfg/ykNxQVwup/8E1BZhVzFfBxs9NqMzGcvIJrqg5k2/5Za2bWo40dK2J1pgLngZ7c+Shh8lwYtLGyrwPutg==", - "requires": { - "es-to-primitive": "^1.2.0", - "function-bind": "^1.1.1", - "has": "^1.0.3", - "is-callable": "^1.1.4", - "is-regex": "^1.0.4", - "object-keys": "^1.0.12" - } - }, - "es-to-primitive": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/es-to-primitive/-/es-to-primitive-1.2.0.tgz", - "integrity": "sha512-qZryBOJjV//LaxLTV6UC//WewneB3LcXOL9NP++ozKVXsIIIpm/2c13UDiD9Jp2eThsecw9m3jPqDwTyobcdbg==", - "requires": { - "is-callable": "^1.1.4", - "is-date-object": "^1.0.1", - "is-symbol": "^1.0.2" - } - }, - "escape-html": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/escape-html/-/escape-html-1.0.3.tgz", - "integrity": "sha1-Aljq5NPQwJdN4cFpGI7wBR0dGYg=" - }, "escape-string-regexp": { "version": "1.0.5", "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", @@ -1217,11 +1034,6 @@ "integrity": "sha1-Cr9PHKpbyx96nYrMbepPqqBLrJs=", "dev": true }, - "etag": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/etag/-/etag-1.8.1.tgz", - "integrity": "sha1-Qa4u62XvpiJorr/qg6x9eSmbCIc=" - }, "eth-gas-reporter": { "version": "0.1.12", "resolved": "https://registry.npmjs.org/eth-gas-reporter/-/eth-gas-reporter-0.1.12.tgz", @@ -1242,20 +1054,6 @@ "sync-request": "^6.0.0" } }, - "eth-lib": { - "version": "0.1.27", - "resolved": "https://registry.npmjs.org/eth-lib/-/eth-lib-0.1.27.tgz", - "integrity": "sha512-B8czsfkJYzn2UIEMwjc7Mbj+Cy72V+/OXH/tb44LV8jhrjizQJJ325xMOMyk3+ETa6r6oi0jsUY14+om8mQMWA==", - "requires": { - "bn.js": "^4.11.6", - "elliptic": "^6.4.0", - "keccakjs": "^0.2.1", - "nano-json-stream-parser": "^0.1.2", - "servify": "^0.1.12", - "ws": "^3.0.0", - "xhr-request-promise": "^0.1.2" - } - }, "ethereumjs-testrpc-sc": { "version": "6.1.6", "resolved": "https://registry.npmjs.org/ethereumjs-testrpc-sc/-/ethereumjs-testrpc-sc-6.1.6.tgz", @@ -1265,15 +1063,6 @@ "source-map-support": "^0.5.3" } }, - "ethjs-unit": { - "version": "0.1.6", - "resolved": "https://registry.npmjs.org/ethjs-unit/-/ethjs-unit-0.1.6.tgz", - "integrity": "sha1-xmWSHkduh7ziqdWIpv4EBbLEFpk=", - "requires": { - "bn.js": "4.11.6", - "number-to-bn": "1.7.0" - } - }, "execa": { "version": "0.7.0", "resolved": "https://registry.npmjs.org/execa/-/execa-0.7.0.tgz", @@ -1332,119 +1121,11 @@ } } }, - "express": { - "version": "4.16.4", - "resolved": "https://registry.npmjs.org/express/-/express-4.16.4.tgz", - "integrity": "sha512-j12Uuyb4FMrd/qQAm6uCHAkPtO8FDTRJZBDd5D2KOL2eLaz1yUNdUB/NOIyq0iU4q4cFarsUCrnFDPBcnksuOg==", - "requires": { - "accepts": "~1.3.5", - "array-flatten": "1.1.1", - "body-parser": "1.18.3", - "content-disposition": "0.5.2", - "content-type": "~1.0.4", - "cookie": "0.3.1", - "cookie-signature": "1.0.6", - "debug": "2.6.9", - "depd": "~1.1.2", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "etag": "~1.8.1", - "finalhandler": "1.1.1", - "fresh": "0.5.2", - "merge-descriptors": "1.0.1", - "methods": "~1.1.2", - "on-finished": "~2.3.0", - "parseurl": "~1.3.2", - "path-to-regexp": "0.1.7", - "proxy-addr": "~2.0.4", - "qs": "6.5.2", - "range-parser": "~1.2.0", - "safe-buffer": "5.1.2", - "send": "0.16.2", - "serve-static": "1.13.2", - "setprototypeof": "1.1.0", - "statuses": "~1.4.0", - "type-is": "~1.6.16", - "utils-merge": "1.0.1", - "vary": "~1.1.2" - }, - "dependencies": { - "body-parser": { - "version": "1.18.3", - "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.18.3.tgz", - "integrity": "sha1-WykhmP/dVTs6DyDe0FkrlWlVyLQ=", - "requires": { - "bytes": "3.0.0", - "content-type": "~1.0.4", - "debug": "2.6.9", - "depd": "~1.1.2", - "http-errors": "~1.6.3", - "iconv-lite": "0.4.23", - "on-finished": "~2.3.0", - "qs": "6.5.2", - "raw-body": "2.3.3", - "type-is": "~1.6.16" - } - }, - "bytes": { - "version": "3.0.0", - "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.0.0.tgz", - "integrity": "sha1-0ygVQE1olpn4Wk6k+odV3ROpYEg=" - }, - "debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "requires": { - "ms": "2.0.0" - } - }, - "http-errors": { - "version": "1.6.3", - "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.6.3.tgz", - "integrity": "sha1-i1VoC7S+KDoLW/TqLjhYC+HZMg0=", - "requires": { - "depd": "~1.1.2", - "inherits": "2.0.3", - "setprototypeof": "1.1.0", - "statuses": ">= 1.4.0 < 2" - } - }, - "iconv-lite": { - "version": "0.4.23", - "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.23.tgz", - "integrity": "sha512-neyTUVFtahjf0mB3dZT77u+8O0QB89jFdnBkd5P1JgYPbPaia3gXXOVL2fq8VyU2gMMD7SaN7QukTB/pmXYvDA==", - "requires": { - "safer-buffer": ">= 2.1.2 < 3" - } - }, - "raw-body": { - "version": "2.3.3", - "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-2.3.3.tgz", - "integrity": "sha512-9esiElv1BrZoI3rCDuOuKCBRbuApGGaDPQfjSflGxdy4oyzqghxu6klEkkVIvBje+FF0BX9coEv8KqW6X/7njw==", - "requires": { - "bytes": "3.0.0", - "http-errors": "1.6.3", - "iconv-lite": "0.4.23", - "unpipe": "1.0.0" - } - }, - "setprototypeof": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.1.0.tgz", - "integrity": "sha512-BvE/TwpZX4FXExxOxZyRGQQv651MSwmWKZGqvmPcRIjDqWub67kTKuIMx43cZZrS/cBBzwBcNDWoFxt2XEFIpQ==" - }, - "statuses": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.4.0.tgz", - "integrity": "sha512-zhSCtt8v2NDrRlPQpCNtw/heZLtfUDqxBM1udqikb/Hbk52LK4nQSwr10u77iopCW5LsyHpuXS0GnEc48mLeew==" - } - } - }, "extend": { "version": "3.0.2", "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.2.tgz", - "integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==" + "integrity": "sha512-fjquC59cD7CyW6urNXK0FBufkZcoiGG80wTuPujX590cB5Ttln20E2UB4S/WARVqhXffZl2LNgS+gQdPIIim/g==", + "dev": true }, "extend-shallow": { "version": "3.0.2", @@ -1535,17 +1216,20 @@ "extsprintf": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/extsprintf/-/extsprintf-1.3.0.tgz", - "integrity": "sha1-lpGEQOMEGnpBT4xS48V06zw+HgU=" + "integrity": "sha1-lpGEQOMEGnpBT4xS48V06zw+HgU=", + "dev": true }, "fast-deep-equal": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-2.0.1.tgz", - "integrity": "sha1-ewUhjd+WZ79/Nwv3/bLLFf3Qqkk=" + "integrity": "sha1-ewUhjd+WZ79/Nwv3/bLLFf3Qqkk=", + "dev": true }, "fast-json-stable-stringify": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.0.0.tgz", - "integrity": "sha1-1RQsDK7msRifh9OnYREGT4bIu/I=" + "integrity": "sha1-1RQsDK7msRifh9OnYREGT4bIu/I=", + "dev": true }, "fast-levenshtein": { "version": "2.0.6", @@ -1581,35 +1265,6 @@ } } }, - "finalhandler": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/finalhandler/-/finalhandler-1.1.1.tgz", - "integrity": "sha512-Y1GUDo39ez4aHAw7MysnUD5JzYX+WaIj8I57kO3aEPT1fFRL4sr7mjei97FgnwhAyyzRYmQZaTHb2+9uZ1dPtg==", - "requires": { - "debug": "2.6.9", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "on-finished": "~2.3.0", - "parseurl": "~1.3.2", - "statuses": "~1.4.0", - "unpipe": "~1.0.0" - }, - "dependencies": { - "debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "requires": { - "ms": "2.0.0" - } - }, - "statuses": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.4.0.tgz", - "integrity": "sha512-zhSCtt8v2NDrRlPQpCNtw/heZLtfUDqxBM1udqikb/Hbk52LK4nQSwr10u77iopCW5LsyHpuXS0GnEc48mLeew==" - } - } - }, "find-up": { "version": "1.1.2", "resolved": "https://registry.npmjs.org/find-up/-/find-up-1.1.2.tgz", @@ -1620,14 +1275,6 @@ "pinkie-promise": "^2.0.0" } }, - "for-each": { - "version": "0.3.3", - "resolved": "https://registry.npmjs.org/for-each/-/for-each-0.3.3.tgz", - "integrity": "sha512-jqYfLp7mo9vIyQf8ykW2v7A+2N4QjeCeI5+Dz9XraiO1ign81wjiH7Fb9vSOWvQfNtmSa4H2RoQTrrXivdUZmw==", - "requires": { - "is-callable": "^1.1.3" - } - }, "for-in": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/for-in/-/for-in-1.0.2.tgz", @@ -1637,23 +1284,20 @@ "forever-agent": { "version": "0.6.1", "resolved": "https://registry.npmjs.org/forever-agent/-/forever-agent-0.6.1.tgz", - "integrity": "sha1-+8cfDEGt6zf5bFd60e1C2P2sypE=" + "integrity": "sha1-+8cfDEGt6zf5bFd60e1C2P2sypE=", + "dev": true }, "form-data": { "version": "2.3.3", "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.3.3.tgz", "integrity": "sha512-1lLKB2Mu3aGP1Q/2eCOx0fNbRMe7XdwktwOruhfqqd0rIJWwN4Dh+E3hrPSlDCXnSR7UtZ1N38rVXm+6+MEhJQ==", + "dev": true, "requires": { "asynckit": "^0.4.0", "combined-stream": "^1.0.6", "mime-types": "^2.1.12" } }, - "forwarded": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.1.2.tgz", - "integrity": "sha1-mMI9qxF1ZXuMBXPozszZGw/xjIQ=" - }, "fragment-cache": { "version": "0.2.1", "resolved": "https://registry.npmjs.org/fragment-cache/-/fragment-cache-0.2.1.tgz", @@ -1663,11 +1307,6 @@ "map-cache": "^0.2.2" } }, - "fresh": { - "version": "0.5.2", - "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.5.2.tgz", - "integrity": "sha1-PYyt2Q2XZWn6g1qx+OSyOhBWBac=" - }, "fs-extra": { "version": "0.30.0", "resolved": "https://registry.npmjs.org/fs-extra/-/fs-extra-0.30.0.tgz", @@ -2214,11 +1853,6 @@ } } }, - "function-bind": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz", - "integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==" - }, "ganache-cli": { "version": "6.4.3", "resolved": "https://registry.npmjs.org/ganache-cli/-/ganache-cli-6.4.3.tgz", @@ -2576,6 +2210,7 @@ "version": "0.1.7", "resolved": "https://registry.npmjs.org/getpass/-/getpass-0.1.7.tgz", "integrity": "sha1-Xv+OPmhNVprkyysSgmBOi6YhSfo=", + "dev": true, "requires": { "assert-plus": "^1.0.0" } @@ -2614,15 +2249,6 @@ } } }, - "global": { - "version": "4.3.2", - "resolved": "https://registry.npmjs.org/global/-/global-4.3.2.tgz", - "integrity": "sha1-52mJJopsdMOJCLEwWxD8DjlOnQ8=", - "requires": { - "min-document": "^2.19.0", - "process": "~0.5.1" - } - }, "global-dirs": { "version": "0.1.1", "resolved": "https://registry.npmjs.org/global-dirs/-/global-dirs-0.1.1.tgz", @@ -2684,35 +2310,24 @@ "har-schema": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/har-schema/-/har-schema-2.0.0.tgz", - "integrity": "sha1-qUwiJOvKwEeCoNkDVSHyRzW37JI=" + "integrity": "sha1-qUwiJOvKwEeCoNkDVSHyRzW37JI=", + "dev": true }, "har-validator": { "version": "5.1.3", "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-5.1.3.tgz", "integrity": "sha512-sNvOCzEQNr/qrvJgc3UG/kD4QtlHycrzwS+6mfTrrSq97BvaYcPZZI1ZSqGSPR73Cxn4LKTD4PttRwfU7jWq5g==", + "dev": true, "requires": { "ajv": "^6.5.5", "har-schema": "^2.0.0" } }, - "has": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/has/-/has-1.0.3.tgz", - "integrity": "sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw==", - "requires": { - "function-bind": "^1.1.1" - } - }, "has-flag": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-2.0.0.tgz", "integrity": "sha1-6CB68cx7MNRGzHC3NLXovhj4jVE=" }, - "has-symbols": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.0.0.tgz", - "integrity": "sha1-uhqPGvKg/DllD1yFA2dwQSIGO0Q=" - }, "has-value": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/has-value/-/has-value-1.0.0.tgz", @@ -2745,30 +2360,11 @@ } } }, - "hash.js": { - "version": "1.1.7", - "resolved": "https://registry.npmjs.org/hash.js/-/hash.js-1.1.7.tgz", - "integrity": "sha512-taOaskGt4z4SOANNseOviYDvjEJinIkRgmp7LbKP2YTTmVxWBl87s/uzK9r+44BclBSp2X7K1hqeNfz9JbBeXA==", - "requires": { - "inherits": "^2.0.3", - "minimalistic-assert": "^1.0.1" - } - }, "he": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/he/-/he-1.1.1.tgz", "integrity": "sha1-k0EP0hsAlzUVH4howvJx80J+I/0=" }, - "hmac-drbg": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/hmac-drbg/-/hmac-drbg-1.0.1.tgz", - "integrity": "sha1-0nRXAQJabHdabFRXk+1QL8DGSaE=", - "requires": { - "hash.js": "^1.0.3", - "minimalistic-assert": "^1.0.0", - "minimalistic-crypto-utils": "^1.0.1" - } - }, "hosted-git-info": { "version": "2.7.1", "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-2.7.1.tgz", @@ -2787,18 +2383,6 @@ "parse-cache-control": "^1.0.1" } }, - "http-errors": { - "version": "1.7.2", - "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.7.2.tgz", - "integrity": "sha512-uUQBt3H/cSIVfch6i1EuPNy/YsRSOUBXTVfZ+yR7Zjez3qjBz6i9+i4zjNaoqcoFVI4lQJ5plg63TvGfRSDCRg==", - "requires": { - "depd": "~1.1.2", - "inherits": "2.0.3", - "setprototypeof": "1.1.1", - "statuses": ">= 1.5.0 < 2", - "toidentifier": "1.0.0" - } - }, "http-response-object": { "version": "3.0.2", "resolved": "https://registry.npmjs.org/http-response-object/-/http-response-object-3.0.2.tgz", @@ -2812,20 +2396,13 @@ "version": "1.2.0", "resolved": "https://registry.npmjs.org/http-signature/-/http-signature-1.2.0.tgz", "integrity": "sha1-muzZJRFHcvPZW2WmCruPfBj7rOE=", + "dev": true, "requires": { "assert-plus": "^1.0.0", "jsprim": "^1.2.2", "sshpk": "^1.7.0" } }, - "iconv-lite": { - "version": "0.4.24", - "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.24.tgz", - "integrity": "sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==", - "requires": { - "safer-buffer": ">= 2.1.2 < 3" - } - }, "ignore-by-default": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/ignore-by-default/-/ignore-by-default-1.0.1.tgz", @@ -2875,11 +2452,6 @@ "resolved": "https://registry.npmjs.org/invert-kv/-/invert-kv-1.0.0.tgz", "integrity": "sha1-EEqOSqym09jNFXqO+L+rLXo//bY=" }, - "ipaddr.js": { - "version": "1.9.0", - "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.9.0.tgz", - "integrity": "sha512-M4Sjn6N/+O6/IXSJseKqHoFc+5FdGJ22sXqnjTpdZweHK64MzEPAyQZyEU3R/KRv2GLoa7nNtg/C2Ev6m7z+eA==" - }, "is-accessor-descriptor": { "version": "0.1.6", "resolved": "https://registry.npmjs.org/is-accessor-descriptor/-/is-accessor-descriptor-0.1.6.tgz", @@ -2921,11 +2493,6 @@ "integrity": "sha512-NcdALwpXkTm5Zvvbk7owOUSvVvBKDgKP5/ewfXEznmQFfs4ZRmanOeKBTjRVjka3QFoN6XJ+9F3USqfHqTaU5w==", "dev": true }, - "is-callable": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/is-callable/-/is-callable-1.1.4.tgz", - "integrity": "sha512-r5p9sxJjYnArLjObpjA4xu5EKI3CuKHkJXMhT7kwbpUyIFD1n5PMAsoPvWnvtZiNz7LjkYDRZhd7FlI0eMijEA==" - }, "is-ci": { "version": "1.2.1", "resolved": "https://registry.npmjs.org/is-ci/-/is-ci-1.2.1.tgz", @@ -2955,11 +2522,6 @@ } } }, - "is-date-object": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-date-object/-/is-date-object-1.0.1.tgz", - "integrity": "sha1-mqIOtq7rv/d/vTPnTKAbM1gdOhY=" - }, "is-descriptor": { "version": "0.1.6", "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-0.1.6.tgz", @@ -2999,11 +2561,6 @@ "number-is-nan": "^1.0.0" } }, - "is-function": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/is-function/-/is-function-1.0.1.tgz", - "integrity": "sha1-Es+5i2W1fdPRk6MSH19uL0N2ArU=" - }, "is-glob": { "version": "4.0.1", "resolved": "https://registry.npmjs.org/is-glob/-/is-glob-4.0.1.tgz", @@ -3013,11 +2570,6 @@ "is-extglob": "^2.1.1" } }, - "is-hex-prefixed": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-hex-prefixed/-/is-hex-prefixed-1.0.0.tgz", - "integrity": "sha1-fY035q135dEnFIkTxXPggtd39VQ=" - }, "is-installed-globally": { "version": "0.1.0", "resolved": "https://registry.npmjs.org/is-installed-globally/-/is-installed-globally-0.1.0.tgz", @@ -3084,14 +2636,6 @@ "integrity": "sha1-HQPd7VO9jbDzDCbk+V02/HyH3CQ=", "dev": true }, - "is-regex": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/is-regex/-/is-regex-1.0.4.tgz", - "integrity": "sha1-VRdIm1RwkbCTDglWVM7SXul+lJE=", - "requires": { - "has": "^1.0.1" - } - }, "is-retry-allowed": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/is-retry-allowed/-/is-retry-allowed-1.1.0.tgz", @@ -3103,18 +2647,11 @@ "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-1.1.0.tgz", "integrity": "sha1-EtSj3U5o4Lec6428hBc66A2RykQ=" }, - "is-symbol": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/is-symbol/-/is-symbol-1.0.2.tgz", - "integrity": "sha512-HS8bZ9ox60yCJLH9snBpIwv9pYUAkcuLhSA1oero1UB5y9aiQpRA8y2ex945AOtCZL1lJDeIk3G5LthswI46Lw==", - "requires": { - "has-symbols": "^1.0.0" - } - }, "is-typedarray": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/is-typedarray/-/is-typedarray-1.0.0.tgz", - "integrity": "sha1-5HnICFjfDBsR3dppQPlgEfzaSpo=" + "integrity": "sha1-5HnICFjfDBsR3dppQPlgEfzaSpo=", + "dev": true }, "is-utf8": { "version": "0.2.1", @@ -3148,7 +2685,8 @@ "isstream": { "version": "0.1.2", "resolved": "https://registry.npmjs.org/isstream/-/isstream-0.1.2.tgz", - "integrity": "sha1-R+Y/evVa+m+S4VAOaQ64uFKcCZo=" + "integrity": "sha1-R+Y/evVa+m+S4VAOaQ64uFKcCZo=", + "dev": true }, "istanbul": { "version": "0.4.5", @@ -3226,7 +2764,8 @@ "js-sha3": { "version": "0.6.1", "resolved": "https://registry.npmjs.org/js-sha3/-/js-sha3-0.6.1.tgz", - "integrity": "sha1-W4n3enR3Z5h39YxKB1JAk0sflcA=" + "integrity": "sha1-W4n3enR3Z5h39YxKB1JAk0sflcA=", + "dev": true }, "js-yaml": { "version": "3.13.1", @@ -3249,22 +2788,26 @@ "jsbn": { "version": "0.1.1", "resolved": "https://registry.npmjs.org/jsbn/-/jsbn-0.1.1.tgz", - "integrity": "sha1-peZUwuWi3rXyAdls77yoDA7y9RM=" + "integrity": "sha1-peZUwuWi3rXyAdls77yoDA7y9RM=", + "dev": true }, "json-schema": { "version": "0.2.3", "resolved": "https://registry.npmjs.org/json-schema/-/json-schema-0.2.3.tgz", - "integrity": "sha1-tIDIkuWaLwWVTOcnvT8qTogvnhM=" + "integrity": "sha1-tIDIkuWaLwWVTOcnvT8qTogvnhM=", + "dev": true }, "json-schema-traverse": { "version": "0.4.1", "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", - "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==" + "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", + "dev": true }, "json-stringify-safe": { "version": "5.0.1", "resolved": "https://registry.npmjs.org/json-stringify-safe/-/json-stringify-safe-5.0.1.tgz", - "integrity": "sha1-Epai1Y/UXxmg9s4B1lcB4sc1tus=" + "integrity": "sha1-Epai1Y/UXxmg9s4B1lcB4sc1tus=", + "dev": true }, "jsonfile": { "version": "2.4.0", @@ -3278,6 +2821,7 @@ "version": "1.4.1", "resolved": "https://registry.npmjs.org/jsprim/-/jsprim-1.4.1.tgz", "integrity": "sha1-MT5mvB5cwG5Di8G3SZwuXFastqI=", + "dev": true, "requires": { "assert-plus": "1.0.0", "extsprintf": "1.3.0", @@ -3300,6 +2844,7 @@ "version": "0.2.3", "resolved": "https://registry.npmjs.org/keccakjs/-/keccakjs-0.2.3.tgz", "integrity": "sha512-BjLkNDcfaZ6l8HBG9tH0tpmDv3sS2mA7FNQxFHpCdzP3Gb2MVruXBSuoM66SnVxKJpAr5dKGdkHD+bDokt8fTg==", + "dev": true, "requires": { "browserify-sha3": "^0.0.4", "sha3": "^1.2.2" @@ -3434,11 +2979,6 @@ "object-visit": "^1.0.0" } }, - "media-typer": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/media-typer/-/media-typer-0.3.0.tgz", - "integrity": "sha1-hxDXrwqmJvj/+hzgAWhUUmMlV0g=" - }, "mem": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/mem/-/mem-1.1.0.tgz", @@ -3452,16 +2992,6 @@ "resolved": "https://registry.npmjs.org/memorystream/-/memorystream-0.3.1.tgz", "integrity": "sha1-htcJCzDORV1j+64S3aUaR93K+bI=" }, - "merge-descriptors": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/merge-descriptors/-/merge-descriptors-1.0.1.tgz", - "integrity": "sha1-sAqqVW3YtEVoFQ7J0blT8/kMu2E=" - }, - "methods": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/methods/-/methods-1.1.2.tgz", - "integrity": "sha1-VSmk1nZUE07cxSZmVoNbD4Ua/O4=" - }, "micromatch": { "version": "3.1.10", "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-3.1.10.tgz", @@ -3483,20 +3013,17 @@ "to-regex": "^3.0.2" } }, - "mime": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/mime/-/mime-1.4.1.tgz", - "integrity": "sha512-KI1+qOZu5DcW6wayYHSzR/tXKCDC5Om4s1z2QJjDULzLcmf3DvzS7oluY4HCTrc+9FiKmWUgeNLg7W3uIQvxtQ==" - }, "mime-db": { "version": "1.38.0", "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.38.0.tgz", - "integrity": "sha512-bqVioMFFzc2awcdJZIzR3HjZFX20QhilVS7hytkKrv7xFAn8bM1gzc/FOX2awLISvWe0PV8ptFKcon+wZ5qYkg==" + "integrity": "sha512-bqVioMFFzc2awcdJZIzR3HjZFX20QhilVS7hytkKrv7xFAn8bM1gzc/FOX2awLISvWe0PV8ptFKcon+wZ5qYkg==", + "dev": true }, "mime-types": { "version": "2.1.22", "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.22.tgz", "integrity": "sha512-aGl6TZGnhm/li6F7yx82bJiBZwgiEa4Hf6CNr8YO+r5UHr53tSTYZb102zyU50DOWWKeOv0uQLRL0/9EiKWCog==", + "dev": true, "requires": { "mime-db": "~1.38.0" } @@ -3506,29 +3033,6 @@ "resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-1.2.0.tgz", "integrity": "sha512-jf84uxzwiuiIVKiOLpfYk7N46TSy8ubTonmneY9vrpHNAnp0QBt2BxWV9dO3/j+BoVAb+a5G6YDPW3M5HOdMWQ==" }, - "mimic-response": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/mimic-response/-/mimic-response-1.0.1.tgz", - "integrity": "sha512-j5EctnkH7amfV/q5Hgmoal1g2QHFJRraOtmx0JpIqkxhBhI/lJSl1nMpQ45hVarwNETOoWEimndZ4QK0RHxuxQ==" - }, - "min-document": { - "version": "2.19.0", - "resolved": "https://registry.npmjs.org/min-document/-/min-document-2.19.0.tgz", - "integrity": "sha1-e9KC4/WELtKVu3SM3Z8f+iyCRoU=", - "requires": { - "dom-walk": "^0.1.0" - } - }, - "minimalistic-assert": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/minimalistic-assert/-/minimalistic-assert-1.0.1.tgz", - "integrity": "sha512-UtJcAD4yEaGtjPezWuO9wC4nwUnVH/8/Im3yEHQP4b67cXlD/Qr9hdITCU1xDbSEXg2XKNaP8jsReV7vQd00/A==" - }, - "minimalistic-crypto-utils": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/minimalistic-crypto-utils/-/minimalistic-crypto-utils-1.0.1.tgz", - "integrity": "sha1-9sAMHAsIIkblxNmd+4x8CDsrWCo=" - }, "minimatch": { "version": "3.0.4", "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", @@ -3598,11 +3102,6 @@ "resolved": "https://registry.npmjs.org/nan/-/nan-2.10.0.tgz", "integrity": "sha512-bAdJv7fBLhWC+/Bls0Oza+mvTaNQtP+1RyhhhvD95pgUJz6XM5IzgmxOkItJ9tkoCiplvAnXI1tNmmUD/eScyA==" }, - "nano-json-stream-parser": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/nano-json-stream-parser/-/nano-json-stream-parser-0.1.2.tgz", - "integrity": "sha1-DMj20OK2IrR5xA1JnEbWS3Vcb18=" - }, "nanomatch": { "version": "1.2.13", "resolved": "https://registry.npmjs.org/nanomatch/-/nanomatch-1.2.13.tgz", @@ -3622,11 +3121,6 @@ "to-regex": "^3.0.1" } }, - "negotiator": { - "version": "0.6.2", - "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-0.6.2.tgz", - "integrity": "sha512-hZXc7K2e+PgeI1eDBe/10Ard4ekbfrrqG8Ep+8Jmf4JID2bNg7NvCPOZN+kfF574pFQI7mum2AUqDidoKqcTOw==" - }, "neo-async": { "version": "2.6.0", "resolved": "https://registry.npmjs.org/neo-async/-/neo-async-2.6.0.tgz", @@ -3708,24 +3202,17 @@ "resolved": "https://registry.npmjs.org/number-is-nan/-/number-is-nan-1.0.1.tgz", "integrity": "sha1-CXtgK1NCKlIsGvuHkDGDNpQaAR0=" }, - "number-to-bn": { - "version": "1.7.0", - "resolved": "https://registry.npmjs.org/number-to-bn/-/number-to-bn-1.7.0.tgz", - "integrity": "sha1-uzYjWS9+X54AMLGXe9QaDFP+HqA=", - "requires": { - "bn.js": "4.11.6", - "strip-hex-prefix": "1.0.0" - } - }, "oauth-sign": { "version": "0.9.0", "resolved": "https://registry.npmjs.org/oauth-sign/-/oauth-sign-0.9.0.tgz", - "integrity": "sha512-fexhUFFPTGV8ybAtSIGbV6gOkSv8UtRbDBnAyLQw4QPKkgNlsH2ByPGtMUqdWkos6YCRmAqViwgZrJc/mRDzZQ==" + "integrity": "sha512-fexhUFFPTGV8ybAtSIGbV6gOkSv8UtRbDBnAyLQw4QPKkgNlsH2ByPGtMUqdWkos6YCRmAqViwgZrJc/mRDzZQ==", + "dev": true }, "object-assign": { "version": "4.1.1", "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", - "integrity": "sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM=" + "integrity": "sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM=", + "dev": true }, "object-copy": { "version": "0.1.0", @@ -3758,11 +3245,6 @@ } } }, - "object-keys": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/object-keys/-/object-keys-1.1.1.tgz", - "integrity": "sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==" - }, "object-visit": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/object-visit/-/object-visit-1.0.1.tgz", @@ -3781,14 +3263,6 @@ "isobject": "^3.0.1" } }, - "on-finished": { - "version": "2.3.0", - "resolved": "https://registry.npmjs.org/on-finished/-/on-finished-2.3.0.tgz", - "integrity": "sha1-IPEzZIGwg811M3mSoWlxqi2QaUc=", - "requires": { - "ee-first": "1.1.1" - } - }, "once": { "version": "1.4.0", "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", @@ -3892,15 +3366,6 @@ "integrity": "sha1-juqz5U+laSD+Fro493+iGqzC104=", "dev": true }, - "parse-headers": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/parse-headers/-/parse-headers-2.0.2.tgz", - "integrity": "sha512-/LypJhzFmyBIDYP9aDVgeyEb5sQfbfY5mnDq4hVhlQ69js87wXfmEI5V3xI6vvXasqebp0oCytYFLxsBVfCzSg==", - "requires": { - "for-each": "^0.3.3", - "string.prototype.trim": "^1.1.2" - } - }, "parse-json": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-2.2.0.tgz", @@ -3910,11 +3375,6 @@ "error-ex": "^1.2.0" } }, - "parseurl": { - "version": "1.3.3", - "resolved": "https://registry.npmjs.org/parseurl/-/parseurl-1.3.3.tgz", - "integrity": "sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==" - }, "pascalcase": { "version": "0.1.1", "resolved": "https://registry.npmjs.org/pascalcase/-/pascalcase-0.1.1.tgz", @@ -3958,11 +3418,6 @@ "integrity": "sha512-GSmOT2EbHrINBf9SR7CDELwlJ8AENk3Qn7OikK4nFYAu3Ote2+JYNVvkpAEQm3/TLNEJFD/xZJjzyxg3KBWOzw==", "dev": true }, - "path-to-regexp": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-0.1.7.tgz", - "integrity": "sha1-32BBeABfUi8V60SQ5yR6G/qmf4w=" - }, "path-type": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/path-type/-/path-type-1.1.0.tgz", @@ -3989,7 +3444,8 @@ "performance-now": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/performance-now/-/performance-now-2.1.0.tgz", - "integrity": "sha1-Ywn04OX6kT7BxpMHrjZLSzd8nns=" + "integrity": "sha1-Ywn04OX6kT7BxpMHrjZLSzd8nns=", + "dev": true }, "pify": { "version": "2.3.0", @@ -4030,11 +3486,6 @@ "integrity": "sha1-1PRWKwzjaW5BrFLQ4ALlemNdxtw=", "dev": true }, - "process": { - "version": "0.5.2", - "resolved": "https://registry.npmjs.org/process/-/process-0.5.2.tgz", - "integrity": "sha1-FjjYqONML0QKkduVq5rrZ3/Bhc8=" - }, "process-nextick-args": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.0.tgz", @@ -4050,15 +3501,6 @@ "asap": "~2.0.6" } }, - "proxy-addr": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.5.tgz", - "integrity": "sha512-t/7RxHXPH6cJtP0pRG6smSr9QJidhB+3kXu0KgXnbGYMgzEnUxRQ4/LDdfOwZEMyIh3/xHb8PX3t+lfL9z+YVQ==", - "requires": { - "forwarded": "~0.1.2", - "ipaddr.js": "1.9.0" - } - }, "pseudomap": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/pseudomap/-/pseudomap-1.0.2.tgz", @@ -4067,7 +3509,8 @@ "psl": { "version": "1.1.31", "resolved": "https://registry.npmjs.org/psl/-/psl-1.1.31.tgz", - "integrity": "sha512-/6pt4+C+T+wZUieKR620OpzN/LlnNKuWjy1iFLQ/UG35JqHlR/89MP1d96dUfkf6Dne3TuLQzOYEYshJ+Hx8mw==" + "integrity": "sha512-/6pt4+C+T+wZUieKR620OpzN/LlnNKuWjy1iFLQ/UG35JqHlR/89MP1d96dUfkf6Dne3TuLQzOYEYshJ+Hx8mw==", + "dev": true }, "pstree.remy": { "version": "1.1.6", @@ -4078,43 +3521,14 @@ "punycode": { "version": "2.1.1", "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.1.1.tgz", - "integrity": "sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A==" + "integrity": "sha512-XRsRjdf+j5ml+y/6GKHPZbrF/8p2Yga0JPtdqTIY2Xe5ohJPD9saDJJLPvp9+NSBprVvevdXZybnj2cv8OEd0A==", + "dev": true }, "qs": { "version": "6.5.2", "resolved": "https://registry.npmjs.org/qs/-/qs-6.5.2.tgz", - "integrity": "sha512-N5ZAX4/LxJmF+7wN74pUD6qAh9/wnvdQcjq9TZjevvXzSUo7bfmw91saqMjzGS2xq91/odN2dW/WOl7qQHNDGA==" - }, - "query-string": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/query-string/-/query-string-5.1.1.tgz", - "integrity": "sha512-gjWOsm2SoGlgLEdAGt7a6slVOk9mGiXmPFMqrEhLQ68rhQuBnpfs3+EmlvqKyxnCo9/PPlF+9MtY02S1aFg+Jw==", - "requires": { - "decode-uri-component": "^0.2.0", - "object-assign": "^4.1.0", - "strict-uri-encode": "^1.0.0" - } - }, - "randomhex": { - "version": "0.1.5", - "resolved": "https://registry.npmjs.org/randomhex/-/randomhex-0.1.5.tgz", - "integrity": "sha1-us7vmCMpCRQA8qKRLGzQLxCU9YU=" - }, - "range-parser": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/range-parser/-/range-parser-1.2.0.tgz", - "integrity": "sha1-9JvmtIeJTdxA3MlKMi9hEJLgDV4=" - }, - "raw-body": { - "version": "2.4.0", - "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-2.4.0.tgz", - "integrity": "sha512-4Oz8DUIwdvoa5qMJelxipzi/iJIi40O5cGV1wNYp5hvZP8ZN0T+jiNkL0QepXs+EsQ9XJ8ipEDoiH70ySUJP3Q==", - "requires": { - "bytes": "3.1.0", - "http-errors": "1.7.2", - "iconv-lite": "0.4.24", - "unpipe": "1.0.0" - } + "integrity": "sha512-N5ZAX4/LxJmF+7wN74pUD6qAh9/wnvdQcjq9TZjevvXzSUo7bfmw91saqMjzGS2xq91/odN2dW/WOl7qQHNDGA==", + "dev": true }, "rc": { "version": "1.2.8", @@ -4261,6 +3675,7 @@ "version": "2.88.0", "resolved": "https://registry.npmjs.org/request/-/request-2.88.0.tgz", "integrity": "sha512-NAqBSrijGLZdM0WZNsInLJpkJokL72XYjUpnB0iwsRgxh7dB6COrHnTBNwN0E+lHDAJzu7kLAkDeY08z2/A0hg==", + "dev": true, "requires": { "aws-sign2": "~0.7.0", "aws4": "^1.8.0", @@ -4386,7 +3801,8 @@ "safer-buffer": { "version": "2.1.2", "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", - "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==" + "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==", + "dev": true }, "semver": { "version": "5.7.0", @@ -4402,80 +3818,6 @@ "semver": "^5.0.3" } }, - "send": { - "version": "0.16.2", - "resolved": "https://registry.npmjs.org/send/-/send-0.16.2.tgz", - "integrity": "sha512-E64YFPUssFHEFBvpbbjr44NCLtI1AohxQ8ZSiJjQLskAdKuriYEP6VyGEsRDH8ScozGpkaX1BGvhanqCwkcEZw==", - "requires": { - "debug": "2.6.9", - "depd": "~1.1.2", - "destroy": "~1.0.4", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "etag": "~1.8.1", - "fresh": "0.5.2", - "http-errors": "~1.6.2", - "mime": "1.4.1", - "ms": "2.0.0", - "on-finished": "~2.3.0", - "range-parser": "~1.2.0", - "statuses": "~1.4.0" - }, - "dependencies": { - "debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "requires": { - "ms": "2.0.0" - } - }, - "http-errors": { - "version": "1.6.3", - "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-1.6.3.tgz", - "integrity": "sha1-i1VoC7S+KDoLW/TqLjhYC+HZMg0=", - "requires": { - "depd": "~1.1.2", - "inherits": "2.0.3", - "setprototypeof": "1.1.0", - "statuses": ">= 1.4.0 < 2" - } - }, - "setprototypeof": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.1.0.tgz", - "integrity": "sha512-BvE/TwpZX4FXExxOxZyRGQQv651MSwmWKZGqvmPcRIjDqWub67kTKuIMx43cZZrS/cBBzwBcNDWoFxt2XEFIpQ==" - }, - "statuses": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.4.0.tgz", - "integrity": "sha512-zhSCtt8v2NDrRlPQpCNtw/heZLtfUDqxBM1udqikb/Hbk52LK4nQSwr10u77iopCW5LsyHpuXS0GnEc48mLeew==" - } - } - }, - "serve-static": { - "version": "1.13.2", - "resolved": "https://registry.npmjs.org/serve-static/-/serve-static-1.13.2.tgz", - "integrity": "sha512-p/tdJrO4U387R9oMjb1oj7qSMaMfmOyd4j9hOFoxZe2baQszgHcSWjuya/CiT5kgZZKRudHNOA0pYXOl8rQ5nw==", - "requires": { - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "parseurl": "~1.3.2", - "send": "0.16.2" - } - }, - "servify": { - "version": "0.1.12", - "resolved": "https://registry.npmjs.org/servify/-/servify-0.1.12.tgz", - "integrity": "sha512-/xE6GvsKKqyo1BAY+KxOWXcLpPsUUyji7Qg3bVD7hh1eRze5bR1uYiuDA/k3Gof1s9BTzQZEJK8sNcNGFIzeWw==", - "requires": { - "body-parser": "^1.16.0", - "cors": "^2.8.1", - "express": "^4.14.0", - "request": "^2.79.0", - "xhr": "^2.3.3" - } - }, "set-blocking": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/set-blocking/-/set-blocking-2.0.0.tgz", @@ -4504,11 +3846,6 @@ } } }, - "setprototypeof": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.1.1.tgz", - "integrity": "sha512-JvdAWfbXeIGaZ9cILp38HntZSFSo3mWg6xGcJJsd+d4aRMOqauag1C63dJfDw7OaMYwEbHMOxEZ1lqVRYP2OAw==" - }, "sha1": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/sha1/-/sha1-1.1.1.tgz", @@ -4523,6 +3860,7 @@ "version": "1.2.2", "resolved": "https://registry.npmjs.org/sha3/-/sha3-1.2.2.tgz", "integrity": "sha1-pmxQmN5MJbyIM27ItIF9AFvKe6k=", + "dev": true, "requires": { "nan": "2.10.0" } @@ -4556,21 +3894,6 @@ "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.2.tgz", "integrity": "sha1-tf3AjxKH6hF4Yo5BXiUTK3NkbG0=" }, - "simple-concat": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/simple-concat/-/simple-concat-1.0.0.tgz", - "integrity": "sha1-c0TLuLbib7J9ZrL8hvn21Zl1IcY=" - }, - "simple-get": { - "version": "2.8.1", - "resolved": "https://registry.npmjs.org/simple-get/-/simple-get-2.8.1.tgz", - "integrity": "sha512-lSSHRSw3mQNUGPAYRqo7xy9dhKmxFXIjLjp4KHpf99GEH2VH7C3AM+Qfx6du6jhfUi6Vm7XnbEVEf7Wb6N8jRw==", - "requires": { - "decompress-response": "^3.3.0", - "once": "^1.3.1", - "simple-concat": "^1.0.0" - } - }, "snapdragon": { "version": "0.8.2", "resolved": "https://registry.npmjs.org/snapdragon/-/snapdragon-0.8.2.tgz", @@ -4955,6 +4278,7 @@ "version": "1.16.1", "resolved": "https://registry.npmjs.org/sshpk/-/sshpk-1.16.1.tgz", "integrity": "sha512-HXXqVUq7+pcKeLqqZj6mHFUMvXtOJt1uoUx09pFW6011inTMxqI8BA8PM95myrIyyKwdnzjdFjLiE6KBPVtJIg==", + "dev": true, "requires": { "asn1": "~0.2.3", "assert-plus": "^1.0.0", @@ -4988,22 +4312,12 @@ } } }, - "statuses": { - "version": "1.5.0", - "resolved": "https://registry.npmjs.org/statuses/-/statuses-1.5.0.tgz", - "integrity": "sha1-Fhx9rBd2Wf2YEfQ3cfqZOBR4Yow=" - }, "stealthy-require": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/stealthy-require/-/stealthy-require-1.1.1.tgz", "integrity": "sha1-NbCYdbT/SfJqd35QmzCQoyJr8ks=", "dev": true }, - "strict-uri-encode": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/strict-uri-encode/-/strict-uri-encode-1.1.0.tgz", - "integrity": "sha1-J5siXfHVgrH1TmWt3UNS4Y+qBxM=" - }, "string-width": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz", @@ -5014,16 +4328,6 @@ "strip-ansi": "^3.0.0" } }, - "string.prototype.trim": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/string.prototype.trim/-/string.prototype.trim-1.1.2.tgz", - "integrity": "sha1-0E3iyJ4Tf019IG8Ia17S+ua+jOo=", - "requires": { - "define-properties": "^1.1.2", - "es-abstract": "^1.5.0", - "function-bind": "^1.0.2" - } - }, "string_decoder": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", @@ -5055,14 +4359,6 @@ "resolved": "https://registry.npmjs.org/strip-eof/-/strip-eof-1.0.0.tgz", "integrity": "sha1-u0P/VZim6wXYm1n80SnJgzE2Br8=" }, - "strip-hex-prefix": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/strip-hex-prefix/-/strip-hex-prefix-1.0.0.tgz", - "integrity": "sha1-DF8VX+8RUTczd96du1iNoFUA428=", - "requires": { - "is-hex-prefixed": "1.0.0" - } - }, "strip-json-comments": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", @@ -5136,7 +4432,8 @@ "timed-out": { "version": "4.0.1", "resolved": "https://registry.npmjs.org/timed-out/-/timed-out-4.0.1.tgz", - "integrity": "sha1-8y6srFoXW+ol1/q1Zas+2HQe9W8=" + "integrity": "sha1-8y6srFoXW+ol1/q1Zas+2HQe9W8=", + "dev": true }, "to-object-path": { "version": "0.3.0", @@ -5180,11 +4477,6 @@ "repeat-string": "^1.6.1" } }, - "toidentifier": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/toidentifier/-/toidentifier-1.0.0.tgz", - "integrity": "sha512-yaOH/Pk/VEhBWWTlhI+qXxDFXlejDGcQipMlyxda9nthulaxLZUNcUqFxokp0vcYnvteJln5FNQDRrxj3YcbVw==" - }, "touch": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/touch/-/touch-3.1.0.tgz", @@ -5198,6 +4490,7 @@ "version": "2.4.3", "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.4.3.tgz", "integrity": "sha512-Q5srk/4vDM54WJsJio3XNn6K2sCG+CQ8G5Wz6bZhRZoAe/+TxjWB/GlFAnYEbkYVlON9FMk/fE3h2RLpPXo4lQ==", + "dev": true, "requires": { "psl": "^1.1.24", "punycode": "^1.4.1" @@ -5206,7 +4499,8 @@ "punycode": { "version": "1.4.1", "resolved": "https://registry.npmjs.org/punycode/-/punycode-1.4.1.tgz", - "integrity": "sha1-wNWmOycYgArY4esPpSachN1BhF4=" + "integrity": "sha1-wNWmOycYgArY4esPpSachN1BhF4=", + "dev": true } } }, @@ -5267,6 +4561,7 @@ "version": "0.6.0", "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.6.0.tgz", "integrity": "sha1-J6XeoGs2sEoKmWZ3SykIaPD8QP0=", + "dev": true, "requires": { "safe-buffer": "^5.0.1" } @@ -5274,7 +4569,8 @@ "tweetnacl": { "version": "0.14.5", "resolved": "https://registry.npmjs.org/tweetnacl/-/tweetnacl-0.14.5.tgz", - "integrity": "sha1-WuaBd/GS1EViadEIr6k/+HQ/T2Q=" + "integrity": "sha1-WuaBd/GS1EViadEIr6k/+HQ/T2Q=", + "dev": true }, "type-check": { "version": "0.3.2", @@ -5291,30 +4587,6 @@ "integrity": "sha512-0fr/mIH1dlO+x7TlcMy+bIDqKPsw/70tVyeHW787goQjhmqaZe10uwLujubK9q9Lg6Fiho1KUKDYz0Z7k7g5/g==", "dev": true }, - "type-is": { - "version": "1.6.18", - "resolved": "https://registry.npmjs.org/type-is/-/type-is-1.6.18.tgz", - "integrity": "sha512-TkRKr9sUTxEH8MdfuCSP7VizJyzRNMjj2J2do2Jr3Kym598JVdEksuzPQCnlFPW4ky9Q+iA+ma9BGm06XQBy8g==", - "requires": { - "media-typer": "0.3.0", - "mime-types": "~2.1.24" - }, - "dependencies": { - "mime-db": { - "version": "1.40.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.40.0.tgz", - "integrity": "sha512-jYdeOMPy9vnxEqFRRo6ZvTZ8d9oPb+k18PKoYNYUe2stVEBPPwsln/qWzdbmaIvnhZ9v2P+CuecK+fpUfsV2mA==" - }, - "mime-types": { - "version": "2.1.24", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.24.tgz", - "integrity": "sha512-WaFHS3MCl5fapm3oLxU4eYDw77IQM2ACcxQ9RIxfaC3ooc6PFuBMGZZsYpvoXS5D5QTWPieo1jjLdAm3TBP3cQ==", - "requires": { - "mime-db": "1.40.0" - } - } - } - }, "typedarray": { "version": "0.0.6", "resolved": "https://registry.npmjs.org/typedarray/-/typedarray-0.0.6.tgz", @@ -5348,11 +4620,6 @@ } } }, - "ultron": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/ultron/-/ultron-1.1.1.tgz", - "integrity": "sha512-UIEXBNeYmKptWH6z8ZnqTeS8fV74zG0/eRU9VGkpzz+LIJNs8W/zM/L+7ctCkRrgbNnnR0xxw4bKOr0cW0N0Og==" - }, "undefsafe": { "version": "2.0.2", "resolved": "https://registry.npmjs.org/undefsafe/-/undefsafe-2.0.2.tgz", @@ -5373,11 +4640,6 @@ } } }, - "underscore": { - "version": "1.8.3", - "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.8.3.tgz", - "integrity": "sha1-Tz+1OxBuYJf8+ctBCfKl6b36UCI=" - }, "union-value": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/union-value/-/union-value-1.0.0.tgz", @@ -5422,11 +4684,6 @@ "crypto-random-string": "^1.0.0" } }, - "unpipe": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/unpipe/-/unpipe-1.0.0.tgz", - "integrity": "sha1-sr9O6FFKrmFltIF4KdIbLvSZBOw=" - }, "unset-value": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/unset-value/-/unset-value-1.0.0.tgz", @@ -5501,6 +4758,7 @@ "version": "4.2.2", "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.2.2.tgz", "integrity": "sha512-KY9Frmirql91X2Qgjry0Wd4Y+YTdrdZheS8TFwvkbLWf/G5KNJDCh6pKL5OZctEW4+0Baa5idK2ZQuELRwPznQ==", + "dev": true, "requires": { "punycode": "^2.1.0" } @@ -5520,11 +4778,6 @@ "prepend-http": "^1.0.1" } }, - "url-set-query": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/url-set-query/-/url-set-query-1.0.0.tgz", - "integrity": "sha1-AW6M/Xwg7gXK/neV6JK9BwL6ozk=" - }, "use": { "version": "3.1.1", "resolved": "https://registry.npmjs.org/use/-/use-3.1.1.tgz", @@ -5534,7 +4787,8 @@ "utf8": { "version": "2.1.1", "resolved": "https://registry.npmjs.org/utf8/-/utf8-2.1.1.tgz", - "integrity": "sha1-LgHbAvfY0JRPdxBPFgnrDDBM92g=" + "integrity": "sha1-LgHbAvfY0JRPdxBPFgnrDDBM92g=", + "dev": true }, "util-deprecate": { "version": "1.0.2", @@ -5542,15 +4796,11 @@ "integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=", "dev": true }, - "utils-merge": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/utils-merge/-/utils-merge-1.0.1.tgz", - "integrity": "sha1-n5VxD1CiZ5R7LMwSR0HBAoQn5xM=" - }, "uuid": { "version": "3.3.2", "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.3.2.tgz", - "integrity": "sha512-yXJmeNaw3DnnKAOKJE51sL/ZaYfWJRl1pK9dr19YFCu0ObS231AB1/LbqTKRAQ5kw8A90rA6fr4riOUpTZvQZA==" + "integrity": "sha512-yXJmeNaw3DnnKAOKJE51sL/ZaYfWJRl1pK9dr19YFCu0ObS231AB1/LbqTKRAQ5kw8A90rA6fr4riOUpTZvQZA==", + "dev": true }, "validate-npm-package-license": { "version": "3.0.4", @@ -5562,15 +4812,11 @@ "spdx-expression-parse": "^3.0.0" } }, - "vary": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz", - "integrity": "sha1-IpnwLG3tMNSllhsLn3RSShj2NPw=" - }, "verror": { "version": "1.10.0", "resolved": "https://registry.npmjs.org/verror/-/verror-1.10.0.tgz", "integrity": "sha1-OhBcoXBTr1XW4nDB+CiGguGNpAA=", + "dev": true, "requires": { "assert-plus": "^1.0.0", "core-util-is": "1.0.2", @@ -5590,20 +4836,6 @@ "xmlhttprequest": "*" } }, - "web3-utils": { - "version": "1.0.0-beta.37", - "resolved": "https://registry.npmjs.org/web3-utils/-/web3-utils-1.0.0-beta.37.tgz", - "integrity": "sha512-kA1fyhO8nKgU21wi30oJQ/ssvu+9srMdjOTKbHYbQe4ATPcr5YNwwrxG3Bcpbu1bEwRUVKHCkqi+wTvcAWBdlQ==", - "requires": { - "bn.js": "4.11.6", - "eth-lib": "0.1.27", - "ethjs-unit": "0.1.6", - "number-to-bn": "1.7.0", - "randomhex": "0.1.5", - "underscore": "1.8.3", - "utf8": "2.1.1" - } - }, "which": { "version": "1.3.1", "resolved": "https://registry.npmjs.org/which/-/which-1.3.1.tgz", @@ -5697,55 +4929,12 @@ "signal-exit": "^3.0.2" } }, - "ws": { - "version": "3.3.3", - "resolved": "https://registry.npmjs.org/ws/-/ws-3.3.3.tgz", - "integrity": "sha512-nnWLa/NwZSt4KQJu51MYlCcSQ5g7INpOrOMt4XV8j4dqTXdmlUmSHQ8/oLC069ckre0fRsgfvsKwbTdtKLCDkA==", - "requires": { - "async-limiter": "~1.0.0", - "safe-buffer": "~5.1.0", - "ultron": "~1.1.0" - } - }, "xdg-basedir": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/xdg-basedir/-/xdg-basedir-3.0.0.tgz", "integrity": "sha1-SWsswQnsqNus/i3HK2A8F8WHCtQ=", "dev": true }, - "xhr": { - "version": "2.5.0", - "resolved": "https://registry.npmjs.org/xhr/-/xhr-2.5.0.tgz", - "integrity": "sha512-4nlO/14t3BNUZRXIXfXe+3N6w3s1KoxcJUUURctd64BLRe67E4gRwp4PjywtDY72fXpZ1y6Ch0VZQRY/gMPzzQ==", - "requires": { - "global": "~4.3.0", - "is-function": "^1.0.1", - "parse-headers": "^2.0.0", - "xtend": "^4.0.0" - } - }, - "xhr-request": { - "version": "1.1.0", - "resolved": "https://registry.npmjs.org/xhr-request/-/xhr-request-1.1.0.tgz", - "integrity": "sha512-Y7qzEaR3FDtL3fP30k9wO/e+FBnBByZeybKOhASsGP30NIkRAAkKD/sCnLvgEfAIEC1rcmK7YG8f4oEnIrrWzA==", - "requires": { - "buffer-to-arraybuffer": "^0.0.5", - "object-assign": "^4.1.1", - "query-string": "^5.0.1", - "simple-get": "^2.7.0", - "timed-out": "^4.0.1", - "url-set-query": "^1.0.0", - "xhr": "^2.0.4" - } - }, - "xhr-request-promise": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/xhr-request-promise/-/xhr-request-promise-0.1.2.tgz", - "integrity": "sha1-NDxE0e53JrhkgGloLQ+EDIO0Jh0=", - "requires": { - "xhr-request": "^1.0.1" - } - }, "xhr2": { "version": "0.1.4", "resolved": "https://registry.npmjs.org/xhr2/-/xhr2-0.1.4.tgz", @@ -5758,11 +4947,6 @@ "integrity": "sha1-Z/4HXFwk/vOfnWX197f+dRcZaPw=", "dev": true }, - "xtend": { - "version": "4.0.1", - "resolved": "https://registry.npmjs.org/xtend/-/xtend-4.0.1.tgz", - "integrity": "sha1-pcbVMr5lbiPbgg77lDofBJmNY68=" - }, "y18n": { "version": "3.2.1", "resolved": "https://registry.npmjs.org/y18n/-/y18n-3.2.1.tgz", diff --git a/package.json b/package.json index 8e4c88b4e..abde3d9fe 100644 --- a/package.json +++ b/package.json @@ -15,8 +15,7 @@ "dependencies": { "ganache-cli": "^6.4.3", "openzeppelin-solidity": "^1.10.0", - "truffle": "^5.0.15", - "web3-utils": "1.0.0-beta.37" + "truffle": "^5.0.15" }, "devDependencies": { "chai": "^4.2.0", From 6bad8be39d71d5ebac0fbe1fbad70567adb4d2a3 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 14 May 2019 11:22:31 -0300 Subject: [PATCH 184/187] Fix unit tests --- test/erc_to_erc/foreign_bridge.test.js | 244 +++---- test/erc_to_erc/home_bridge.test.js | 449 ++++++------- test/erc_to_native/foreign_bridge.test.js | 90 +-- test/erc_to_native/home_bridge.test.js | 779 +++++++++++----------- test/helpers/helpers.js | 68 +- test/native_to_erc/foreign_bridge_test.js | 369 +++++----- test/native_to_erc/home_bridge_test.js | 699 ++++++++++--------- test/poa20_test.js | 262 ++++---- test/rewardable_validators_test.js | 123 ++-- test/setup.js | 1 + test/validators_test.js | 112 ++-- 11 files changed, 1593 insertions(+), 1603 deletions(-) diff --git a/test/erc_to_erc/foreign_bridge.test.js b/test/erc_to_erc/foreign_bridge.test.js index 94a07bde4..ff50ca026 100644 --- a/test/erc_to_erc/foreign_bridge.test.js +++ b/test/erc_to_erc/foreign_bridge.test.js @@ -3,34 +3,23 @@ const ForeignBridgeErc677ToErc677 = artifacts.require("ForeignBridgeErc677ToErc6 const ForeignBridgeV2 = artifacts.require("ForeignBridgeV2.sol"); const BridgeValidators = artifacts.require("BridgeValidators.sol"); const EternalStorageProxy = artifacts.require("EternalStorageProxy.sol"); - const ERC677BridgeToken = artifacts.require("ERC677BridgeToken.sol"); -const {ERROR_MSG, ZERO_ADDRESS, INVALID_ARGUMENTS} = require('../setup'); -const {createMessage, sign, signatureToVRS} = require('../helpers/helpers'); -const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")); + +const { expect } = require('chai'); +const { ERROR_MSG, ZERO_ADDRESS, toBN } = require('../setup'); +const { createMessage, sign, signatureToVRS, ether, getEvents } = require('../helpers/helpers'); + +const oneEther = ether('1'); +const halfEther = ether('0.5'); const requireBlockConfirmations = 8; -const gasPrice = web3.toWei('1', 'gwei') -const oneEther = web3.toBigNumber(web3.toWei(1, "ether")); +const gasPrice = web3.utils.toWei('1', 'gwei') const homeDailyLimit = oneEther const homeMaxPerTx = halfEther const maxPerTx = halfEther -const minPerTx = web3.toBigNumber(web3.toWei(0.01, "ether")); +const minPerTx = ether('0.01'); const dailyLimit = oneEther +const ZERO = toBN(0) -const getEvents = function(contract, filter) { - return new Promise((resolve, reject) => { - var event = contract[filter.event](); - event.watch(); - event.get((error, logs) => { - if(logs.length > 0){ - resolve(logs); - } else { - throw Error("Failed to find filtered event for " + filter.event); - } - }); - event.stopWatching(); - }); -} contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { let validatorContract, authorities, owner, token; @@ -46,13 +35,11 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); let foreignBridge = await ForeignBridge.new(); - ZERO_ADDRESS.should.be.equal(await foreignBridge.erc20token()); - ZERO_ADDRESS.should.be.equal(await foreignBridge.validatorContract()) - '0'.should.be.bignumber.equal(await foreignBridge.deployedAtBlock()) - false.should.be.equal(await foreignBridge.isInitialized()) - '0'.should.be.bignumber.equal(await foreignBridge.requiredBlockConfirmations()) - - await foreignBridge.initialize(validatorContract.address, token.address, requireBlockConfirmations, owner).should.be.rejectedWith(INVALID_ARGUMENTS); + expect(await foreignBridge.erc20token()).to.be.equal(ZERO_ADDRESS) + expect(await foreignBridge.validatorContract()).to.be.equal(ZERO_ADDRESS) + expect(await foreignBridge.deployedAtBlock()).to.be.bignumber.equal(ZERO) + expect(await foreignBridge.isInitialized()).to.be.equal(false) + expect(await foreignBridge.requiredBlockConfirmations()).to.be.bignumber.equal(ZERO) await foreignBridge.initialize(ZERO_ADDRESS, token.address, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); await foreignBridge.initialize(validatorContract.address, ZERO_ADDRESS, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); @@ -63,26 +50,23 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { await foreignBridge.initialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner); - token.address.should.be.equal(await foreignBridge.erc20token()); - true.should.be.equal(await foreignBridge.isInitialized()) - validatorContract.address.should.be.equal(await foreignBridge.validatorContract()); - token.address.should.be.equal(await foreignBridge.erc20token()); - (await foreignBridge.deployedAtBlock()).should.be.bignumber.above(0); - requireBlockConfirmations.should.be.bignumber.equal(await foreignBridge.requiredBlockConfirmations()) - const contractGasPrice = await foreignBridge.gasPrice() - contractGasPrice.should.be.bignumber.equal(gasPrice) + expect(await foreignBridge.erc20token()).to.be.equal(token.address) + expect(await foreignBridge.isInitialized()).to.be.equal(true) + expect(await foreignBridge.validatorContract()).to.be.equal(validatorContract.address) + expect(await foreignBridge.deployedAtBlock()).to.be.bignumber.above(ZERO) + expect(await foreignBridge.requiredBlockConfirmations()).to.be.bignumber.equal(requireBlockConfirmations.toString()) + expect(await foreignBridge.gasPrice()).to.be.bignumber.equal(gasPrice) const bridgeMode = '0xba4690f5' // 4 bytes of keccak256('erc-to-erc-core') - const mode = await foreignBridge.getBridgeMode(); - mode.should.be.equal(bridgeMode) - const [major, minor, patch] = await foreignBridge.getBridgeInterfacesVersion() - major.should.be.bignumber.gte(0) - minor.should.be.bignumber.gte(0) - patch.should.be.bignumber.gte(0) + expect(await foreignBridge.getBridgeMode()).to.be.equal(bridgeMode) + const { major, minor, patch } = await foreignBridge.getBridgeInterfacesVersion() + expect(major).to.be.bignumber.gte(ZERO) + expect(minor).to.be.bignumber.gte(ZERO) + expect(patch).to.be.bignumber.gte(ZERO) }) }) describe('#executeSignatures', async () => { - var value = web3.toBigNumber(web3.toWei(0.25, "ether")); + const value = ether('0.25'); let foreignBridge beforeEach(async () => { foreignBridge = await ForeignBridge.new() @@ -91,13 +75,13 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { await token.mint(foreignBridge.address,value); }) it('should allow to executeSignatures', async () => { - var recipientAccount = accounts[3]; + const recipientAccount = accounts[3]; const balanceBefore = await token.balanceOf(recipientAccount) - var transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - var message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); - var signature = await sign(authorities[0], message) - var vrs = signatureToVRS(signature); + const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; + const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); + const signature = await sign(authorities[0], message) + const vrs = signatureToVRS(signature); false.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) const {logs} = await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.fulfilled logs[0].event.should.be.equal("RelayedMessage") @@ -107,26 +91,25 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { const balanceAfter = await token.balanceOf(recipientAccount); const balanceAfterBridge = await token.balanceOf(foreignBridge.address); balanceAfter.should.be.bignumber.equal(balanceBefore.add(value)) - balanceAfterBridge.should.be.bignumber.equal(0) + balanceAfterBridge.should.be.bignumber.equal(ZERO) true.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) }) it('should allow second withdrawal with different transactionHash but same recipient and value', async ()=> { - var recipientAccount = accounts[3]; + const recipientAccount = accounts[3]; const balanceBefore = await token.balanceOf(recipientAccount) // tx 1 - var value = web3.toBigNumber(web3.toWei(0.25, "ether")); - var transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - var message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); - var signature = await sign(authorities[0], message) - var vrs = signatureToVRS(signature); + const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; + const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); + const signature = await sign(authorities[0], message) + const vrs = signatureToVRS(signature); false.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.fulfilled // tx 2 await token.mint(foreignBridge.address,value); - var transactionHash2 = "0x77a496628a776a03d58d7e6059a5937f04bebd8ba4ff89f76dd4bb8ba7e291ee"; - var message2 = createMessage(recipientAccount, value, transactionHash2, foreignBridge.address); - var signature2 = await sign(authorities[0], message2) - var vrs2 = signatureToVRS(signature2); + const transactionHash2 = "0x77a496628a776a03d58d7e6059a5937f04bebd8ba4ff89f76dd4bb8ba7e291ee"; + const message2 = createMessage(recipientAccount, value, transactionHash2, foreignBridge.address); + const signature2 = await sign(authorities[0], message2) + const vrs2 = signatureToVRS(signature2); false.should.be.equal(await foreignBridge.relayedMessages(transactionHash2)) const {logs} = await foreignBridge.executeSignatures([vrs2.v], [vrs2.r], [vrs2.s], message2).should.be.fulfilled @@ -134,34 +117,33 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { logs[0].args.recipient.should.be.equal(recipientAccount) logs[0].args.value.should.be.bignumber.equal(value) const balanceAfter = await token.balanceOf(recipientAccount) - balanceAfter.should.be.bignumber.equal(balanceBefore.add(value.mul(2))) + balanceAfter.should.be.bignumber.equal(balanceBefore.add(value.mul(toBN(2)))) true.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) true.should.be.equal(await foreignBridge.relayedMessages(transactionHash2)) }) it('should not allow second withdraw (replay attack) with same transactionHash but different recipient', async () => { - var recipientAccount = accounts[3]; - const balanceBefore = await token.balanceOf(recipientAccount) + const recipientAccount = accounts[3]; // tx 1 - var transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - var message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); - var signature = await sign(authorities[0], message) - var vrs = signatureToVRS(signature); + const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; + const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); + const signature = await sign(authorities[0], message) + const vrs = signatureToVRS(signature); false.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.fulfilled // tx 2 await token.mint(foreignBridge.address,value); - var message2 = createMessage(accounts[4], value, transactionHash, foreignBridge.address); - var signature2 = await sign(authorities[0], message2) - var vrs = signatureToVRS(signature2); + const message2 = createMessage(accounts[4], value, transactionHash, foreignBridge.address); + const signature2 = await sign(authorities[0], message2) + const vrs2 = signatureToVRS(signature2); true.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) - await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message2).should.be.rejectedWith(ERROR_MSG) + await foreignBridge.executeSignatures([vrs2.v], [vrs2.r], [vrs2.s], message2).should.be.rejectedWith(ERROR_MSG) }) it('should not allow withdraw over home max tx limit', async () => { const recipientAccount = accounts[3]; - const invalidValue = web3.toBigNumber(web3.toWei(0.75, "ether")); - await token.mint(foreignBridge.address, web3.toBigNumber(web3.toWei(5, "ether"))); + const invalidValue = ether('0.75'); + await token.mint(foreignBridge.address, ether('5')); const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; const message = createMessage(recipientAccount, invalidValue, transactionHash, foreignBridge.address); @@ -173,7 +155,7 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { it('should not allow withdraw over daily home limit', async () => { const recipientAccount = accounts[3]; - await token.mint(foreignBridge.address, web3.toBigNumber(web3.toWei(5, "ether"))); + await token.mint(foreignBridge.address, ether('5')); const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; const message = createMessage(recipientAccount, halfEther, transactionHash, foreignBridge.address); @@ -199,32 +181,30 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { }) describe('#withdraw with 2 minimum signatures', async () => { let multisigValidatorContract, twoAuthorities, ownerOfValidatorContract, foreignBridgeWithMultiSignatures - var value = web3.toBigNumber(web3.toWei(0.5, "ether")); + const value = halfEther beforeEach(async () => { multisigValidatorContract = await BridgeValidators.new() token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); twoAuthorities = [accounts[0], accounts[1]]; ownerOfValidatorContract = accounts[3] - const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")); await multisigValidatorContract.initialize(2, twoAuthorities, ownerOfValidatorContract, {from: ownerOfValidatorContract}) foreignBridgeWithMultiSignatures = await ForeignBridge.new() - const oneEther = web3.toBigNumber(web3.toWei(1, "ether")); await foreignBridgeWithMultiSignatures.initialize(multisigValidatorContract.address, token.address, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner, {from: ownerOfValidatorContract}); await token.mint(foreignBridgeWithMultiSignatures.address,value); }) it('withdraw should fail if not enough signatures are provided', async () => { - var recipientAccount = accounts[4]; + const recipientAccount = accounts[4]; // msg 1 - var transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - var message = createMessage(recipientAccount, value, transactionHash, foreignBridgeWithMultiSignatures.address); - var signature = await sign(twoAuthorities[0], message) - var vrs = signatureToVRS(signature); + const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; + const message = createMessage(recipientAccount, value, transactionHash, foreignBridgeWithMultiSignatures.address); + const signature = await sign(twoAuthorities[0], message) + const vrs = signatureToVRS(signature); false.should.be.equal(await foreignBridgeWithMultiSignatures.relayedMessages(transactionHash)) await foreignBridgeWithMultiSignatures.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.rejectedWith(ERROR_MSG) // msg 2 - var signature2 = await sign(twoAuthorities[1], message) - var vrs2 = signatureToVRS(signature2); + const signature2 = await sign(twoAuthorities[1], message) + const vrs2 = signatureToVRS(signature2); const {logs} = await foreignBridgeWithMultiSignatures.executeSignatures([vrs.v, vrs2.v], [vrs.r, vrs2.r], [vrs.s, vrs2.s], message).should.be.fulfilled; logs[0].event.should.be.equal("RelayedMessage") @@ -234,11 +214,11 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { }) it('withdraw should fail if duplicate signature is provided', async () => { - var recipientAccount = accounts[4]; - var transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - var message = createMessage(recipientAccount, value, transactionHash, foreignBridgeWithMultiSignatures.address); - var signature = await sign(twoAuthorities[0], message) - var vrs = signatureToVRS(signature); + const recipientAccount = accounts[4]; + const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; + const message = createMessage(recipientAccount, value, transactionHash, foreignBridgeWithMultiSignatures.address); + const signature = await sign(twoAuthorities[0], message) + const vrs = signatureToVRS(signature); false.should.be.equal(await foreignBridgeWithMultiSignatures.relayedMessages(transactionHash)) await foreignBridgeWithMultiSignatures.executeSignatures([vrs.v, vrs.v], [vrs.r, vrs.r], [vrs.s, vrs.s], message).should.be.rejectedWith(ERROR_MSG) }) @@ -250,7 +230,7 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { const validatorContractWith3Signatures = await BridgeValidators.new() await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) const erc20Token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); - const value = web3.toBigNumber(web3.toWei(0.5, "ether")); + const value = halfEther const foreignBridgeWithThreeSigs = await ForeignBridge.new() await foreignBridgeWithThreeSigs.initialize(validatorContractWith3Signatures.address, erc20Token.address, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner); @@ -320,8 +300,8 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { let storageProxy = await EternalStorageProxy.new().should.be.fulfilled; let foreignBridge = await ForeignBridge.new(); - let data = foreignBridge.initialize.request( - validatorsAddress, tokenAddress, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner).params[0].data + const data = foreignBridge.contract.methods.initialize( + validatorsAddress, tokenAddress, requireBlockConfirmations, gasPrice, '2', '3', '2', owner).encodeABI() await storageProxy.upgradeToAndCall('1', foreignBridge.address, data).should.be.fulfilled; let finalContract = await ForeignBridge.at(storageProxy.address); true.should.be.equal(await finalContract.isInitialized()); @@ -341,15 +321,15 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { let tokenSecond = await ERC677BridgeToken.new("Roman Token", "RST", 18); await tokenSecond.mint(accounts[0], halfEther).should.be.fulfilled; - halfEther.should.be.bignumber.equal(await tokenSecond.balanceOf(accounts[0])) + expect(await tokenSecond.balanceOf(accounts[0])).to.be.bignumber.equal(halfEther) + await tokenSecond.transfer(foreignBridge.address, halfEther); - '0'.should.be.bignumber.equal(await tokenSecond.balanceOf(accounts[0])) - halfEther.should.be.bignumber.equal(await tokenSecond.balanceOf(foreignBridge.address)) + expect(await tokenSecond.balanceOf(accounts[0])).to.be.bignumber.equal(ZERO) + expect(await tokenSecond.balanceOf(foreignBridge.address)).to.be.bignumber.equal(halfEther) await foreignBridge.claimTokens(tokenSecond.address, accounts[3], {from: owner}); - '0'.should.be.bignumber.equal(await tokenSecond.balanceOf(foreignBridge.address)) - halfEther.should.be.bignumber.equal(await tokenSecond.balanceOf(accounts[3])) - + expect(await tokenSecond.balanceOf(foreignBridge.address)).to.be.bignumber.equal(ZERO) + expect(await tokenSecond.balanceOf(accounts[3])).to.be.bignumber.equal(halfEther) }) }) describe('#ForeignBridgeErc677ToErc677_onTokenTransfer', async () => { @@ -365,19 +345,18 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { await foreignBridge.onTokenTransfer(user, halfEther, '0x00', {from: owner}).should.be.rejectedWith(ERROR_MSG); await token.transferAndCall(foreignBridge.address, halfEther, '0x00', {from: user}).should.be.fulfilled; - halfEther.should.be.bignumber.equal(await token.totalSupply()); - '0'.should.be.bignumber.equal(await token.balanceOf(user)); - halfEther.should.be.bignumber.equal(await token.balanceOf(foreignBridge.address)); + expect(await token.totalSupply()).to.be.bignumber.equal(halfEther) + expect(await token.balanceOf(user)).to.be.bignumber.equal(ZERO) + expect(await token.balanceOf(foreignBridge.address)).to.be.bignumber.equal(halfEther) + const events = await getEvents(foreignBridge, {event: 'UserRequestForAffirmation'}); - events[0].args.should.be.deep.equal({ - recipient: user, - value: halfEther - }) + expect(events[0].returnValues.recipient).to.be.equal(user) + expect(toBN(events[0].returnValues.value)).to.be.bignumber.equal(halfEther) }) it('should not allow to transfer more than maxPerTx limit', async () => { const owner = accounts[3] const user = accounts[4] - const valueMoreThanLimit = halfEther.add(1); + const valueMoreThanLimit = halfEther.add(toBN(1)); token = await ERC677BridgeToken.new("TEST", "TST", 18, {from: owner}); const foreignBridge = await ForeignBridgeErc677ToErc677.new(); await foreignBridge.initialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, dailyLimit, maxPerTx, minPerTx, homeDailyLimit, homeMaxPerTx, owner); @@ -390,51 +369,49 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { valueMoreThanLimit.should.be.bignumber.equal(await token.balanceOf(user)); await token.transferAndCall(foreignBridge.address, halfEther, '0x00', {from: user}).should.be.fulfilled; - valueMoreThanLimit.should.be.bignumber.equal(await token.totalSupply()); - '1'.should.be.bignumber.equal(await token.balanceOf(user)); - halfEther.should.be.bignumber.equal(await token.balanceOf(foreignBridge.address)); + + expect(await token.totalSupply()).to.be.bignumber.equal(valueMoreThanLimit) + expect(await token.balanceOf(user)).to.be.bignumber.equal('1') + expect(await token.balanceOf(foreignBridge.address)).to.be.bignumber.equal(halfEther) const events = await getEvents(foreignBridge, {event: 'UserRequestForAffirmation'}); - events[0].args.should.be.deep.equal({ - recipient: user, - value: halfEther - }) + expect(events[0].returnValues.recipient).to.be.equal(user) + expect(toBN(events[0].returnValues.value)).to.be.bignumber.equal(halfEther) }) it('should only let to transfer within daily limit', async () => { const owner = accounts[3] const user = accounts[4] - const valueMoreThanLimit = halfEther.add(1); + const valueMoreThanLimit = halfEther.add(toBN(1)); token = await ERC677BridgeToken.new("TEST", "TST", 18, {from: owner}); const foreignBridge = await ForeignBridgeErc677ToErc677.new(); await foreignBridge.initialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, dailyLimit, maxPerTx, minPerTx, homeDailyLimit, homeMaxPerTx, owner); - await token.mint(user, oneEther.add(1), {from: owner }).should.be.fulfilled; + await token.mint(user, oneEther.add(toBN(1)), {from: owner }).should.be.fulfilled; await token.transferOwnership(foreignBridge.address, {from: owner}); await token.transferAndCall(foreignBridge.address, valueMoreThanLimit, '0x00', {from: user}).should.be.rejectedWith(ERROR_MSG); - oneEther.add(1).should.be.bignumber.equal(await token.totalSupply()); - oneEther.add(1).should.be.bignumber.equal(await token.balanceOf(user)); + oneEther.add(toBN(1)).should.be.bignumber.equal(await token.totalSupply()); + oneEther.add(toBN(1)).should.be.bignumber.equal(await token.balanceOf(user)); await token.transferAndCall(foreignBridge.address, halfEther, '0x00', {from: user}).should.be.fulfilled; - oneEther.add(1).should.be.bignumber.equal(await token.totalSupply()); + oneEther.add(toBN(1)).should.be.bignumber.equal(await token.totalSupply()); valueMoreThanLimit.should.be.bignumber.equal(await token.balanceOf(user)); const events = await getEvents(foreignBridge, {event: 'UserRequestForAffirmation'}); - events[0].args.should.be.deep.equal({ - recipient: user, - value: halfEther - }) + expect(events[0].returnValues.recipient).to.be.equal(user) + expect(toBN(events[0].returnValues.value)).to.be.bignumber.equal(halfEther) await token.transferAndCall(foreignBridge.address, halfEther, '0x00', {from: user}).should.be.fulfilled; - oneEther.add(1).should.be.bignumber.equal(await token.totalSupply()); - '1'.should.be.bignumber.equal(await token.balanceOf(user)); - oneEther.should.be.bignumber.equal(await token.balanceOf(foreignBridge.address)); + + expect(await token.totalSupply()).to.be.bignumber.equal(oneEther.add(toBN(1))) + expect(await token.balanceOf(user)).to.be.bignumber.equal('1') + expect(await token.balanceOf(foreignBridge.address)).to.be.bignumber.equal(oneEther) await token.transferAndCall(foreignBridge.address, '1', '0x00', {from: user}).should.be.rejectedWith(ERROR_MSG); }) it('should not let to transfer less than minPerTx', async () => { const owner = accounts[3] const user = accounts[4] - const valueLessThanMinPerTx = minPerTx.sub(1); + const valueLessThanMinPerTx = minPerTx.sub(toBN(1)); token = await ERC677BridgeToken.new("TEST", "TST", 18, {from: owner}); const foreignBridge = await ForeignBridgeErc677ToErc677.new(); await foreignBridge.initialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, dailyLimit, maxPerTx, minPerTx, homeDailyLimit, homeMaxPerTx, owner); @@ -443,19 +420,18 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { await token.transferOwnership(foreignBridge.address, {from: owner}); await token.transferAndCall(foreignBridge.address, valueLessThanMinPerTx, '0x00', {from: user}).should.be.rejectedWith(ERROR_MSG); - oneEther.should.be.bignumber.equal(await token.totalSupply()); - oneEther.should.be.bignumber.equal(await token.balanceOf(user)); + expect(await token.totalSupply()).to.be.bignumber.equal(oneEther) + expect(await token.balanceOf(user)).to.be.bignumber.equal(oneEther) await token.transferAndCall(foreignBridge.address, minPerTx, '0x00', {from: user}).should.be.fulfilled; - oneEther.should.be.bignumber.equal(await token.totalSupply()); - oneEther.sub(minPerTx).should.be.bignumber.equal(await token.balanceOf(user)); - minPerTx.should.be.bignumber.equal(await token.balanceOf(foreignBridge.address)); + + expect(await token.totalSupply()).to.be.bignumber.equal(oneEther) + expect(await token.balanceOf(user)).to.be.bignumber.equal(oneEther.sub(minPerTx)) + expect(await token.balanceOf(foreignBridge.address)).to.be.bignumber.equal(minPerTx) const events = await getEvents(foreignBridge, {event: 'UserRequestForAffirmation'}); - events[0].args.should.be.deep.equal({ - recipient: user, - value: minPerTx - }) + expect(events[0].returnValues.recipient).to.be.equal(user) + expect(toBN(events[0].returnValues.value)).to.be.bignumber.equal(minPerTx) }) }) }) diff --git a/test/erc_to_erc/home_bridge.test.js b/test/erc_to_erc/home_bridge.test.js index 5a52a5435..f608ff394 100644 --- a/test/erc_to_erc/home_bridge.test.js +++ b/test/erc_to_erc/home_bridge.test.js @@ -1,4 +1,3 @@ -const Web3Utils = require('web3-utils'); const HomeBridge = artifacts.require("HomeBridgeErcToErc.sol"); const POSDAOHomeBridge = artifacts.require("POSDAOHomeBridgeErcToErc.sol"); const EternalStorageProxy = artifacts.require("EternalStorageProxy.sol"); @@ -8,15 +7,20 @@ const ERC677BridgeTokenRewardable = artifacts.require("ERC677BridgeTokenRewardab const FeeManagerErcToErcPOSDAO = artifacts.require("FeeManagerErcToErcPOSDAO.sol"); const RewardableValidators = artifacts.require("RewardableValidators.sol"); const BlockReward = artifacts.require('BlockReward') -const {ERROR_MSG, ZERO_ADDRESS} = require('../setup'); -const {createMessage, sign, getEvents} = require('../helpers/helpers'); -const minPerTx = web3.toBigNumber(web3.toWei(0.01, "ether")); + +const { expect } = require('chai'); +const { ERROR_MSG, ZERO_ADDRESS, toBN } = require('../setup'); +const { createMessage, sign, getEvents, ether, expectEventInLogs } = require('../helpers/helpers'); + +const minPerTx = ether('0.01'); const requireBlockConfirmations = 8; -const gasPrice = Web3Utils.toWei('1', 'gwei'); -const oneEther = web3.toBigNumber(web3.toWei(1, "ether")); -const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")); +const gasPrice = web3.utils.toWei('1', 'gwei'); +const oneEther = ether('1'); +const halfEther = ether('0.5'); const foreignDailyLimit = oneEther const foreignMaxPerTx = halfEther +const ZERO = toBN(0) +const markedAsProcessed = (toBN(2)).pow(toBN(255)).add(toBN(1)) contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { @@ -33,47 +37,52 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); }) it('sets variables', async () => { - ZERO_ADDRESS.should.be.equal(await homeContract.validatorContract()) - '0'.should.be.bignumber.equal(await homeContract.deployedAtBlock()) - '0'.should.be.bignumber.equal(await homeContract.dailyLimit()) - '0'.should.be.bignumber.equal(await homeContract.maxPerTx()) - false.should.be.equal(await homeContract.isInitialized()) + expect(await homeContract.validatorContract()).to.be.equal(ZERO_ADDRESS) + expect(await homeContract.deployedAtBlock()).to.be.bignumber.equal(ZERO) + expect(await homeContract.dailyLimit()).to.be.bignumber.equal(ZERO) + expect(await homeContract.maxPerTx()).to.be.bignumber.equal(ZERO) + expect(await homeContract.isInitialized()).to.be.equal(false) + await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled; - true.should.be.equal(await homeContract.isInitialized()) - validatorContract.address.should.be.equal(await homeContract.validatorContract()); - (await homeContract.deployedAtBlock()).should.be.bignumber.above(0); - '3'.should.be.bignumber.equal(await homeContract.dailyLimit()) - '2'.should.be.bignumber.equal(await homeContract.maxPerTx()) - '1'.should.be.bignumber.equal(await homeContract.minPerTx()) + + expect(await homeContract.isInitialized()).to.be.equal(true) + expect(await homeContract.validatorContract()).to.be.equal(validatorContract.address) + expect(await homeContract.deployedAtBlock()).to.be.bignumber.above(ZERO) + expect(await homeContract.dailyLimit()).to.be.bignumber.equal('3') + expect(await homeContract.maxPerTx()).to.be.bignumber.equal('2') + expect(await homeContract.minPerTx()).to.be.bignumber.equal('1') const bridgeMode = '0xba4690f5' // 4 bytes of keccak256('erc-to-erc-core') - const mode = await homeContract.getBridgeMode(); - mode.should.be.equal(bridgeMode) - const [major, minor, patch] = await homeContract.getBridgeInterfacesVersion() - major.should.be.bignumber.gte(0) - minor.should.be.bignumber.gte(0) - patch.should.be.bignumber.gte(0) + expect(await homeContract.getBridgeMode()).to.be.equal(bridgeMode) + const { major, minor, patch } = await homeContract.getBridgeInterfacesVersion() + expect(major).to.be.bignumber.gte(ZERO) + expect(minor).to.be.bignumber.gte(ZERO) + expect(patch).to.be.bignumber.gte(ZERO) }) it('cant set maxPerTx > dailyLimit', async () => { - false.should.be.equal(await homeContract.isInitialized()) + expect(await homeContract.isInitialized()).to.be.equal(false) + await homeContract.initialize(validatorContract.address, '1', '2', '1', gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); await homeContract.initialize(validatorContract.address, '3', '2', '2', gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - false.should.be.equal(await homeContract.isInitialized()) + + expect(await homeContract.isInitialized()).to.be.equal(false) }) it('can be deployed via upgradeToAndCall', async () => { let storageProxy = await EternalStorageProxy.new().should.be.fulfilled; - let data = homeContract.initialize.request(validatorContract.address, "3", "2", "1", gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner).params[0].data + const data = homeContract.contract.methods.initialize(validatorContract.address, "3", "2", "1", gasPrice, requireBlockConfirmations, token.address, '3', '2', owner).encodeABI() await storageProxy.upgradeToAndCall('1', homeContract.address, data).should.be.fulfilled; let finalContract = await HomeBridge.at(storageProxy.address); - true.should.be.equal(await finalContract.isInitialized()); - validatorContract.address.should.be.equal(await finalContract.validatorContract()) - "3".should.be.bignumber.equal(await finalContract.dailyLimit()) - "2".should.be.bignumber.equal(await finalContract.maxPerTx()) - "1".should.be.bignumber.equal(await finalContract.minPerTx()) + + expect(await finalContract.isInitialized()).to.be.equal(true) + expect(await finalContract.validatorContract()).to.be.equal(validatorContract.address) + expect(await finalContract.dailyLimit()).to.be.bignumber.equal('3') + expect(await finalContract.maxPerTx()).to.be.bignumber.equal('2') + expect(await finalContract.minPerTx()).to.be.bignumber.equal('1') }) it('cant initialize with invalid arguments', async () => { - false.should.be.equal(await homeContract.isInitialized()) + expect(await homeContract.isInitialized()).to.be.equal(false) + await homeContract.initialize(validatorContract.address, '3', '2', '1', 0, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, 0, token.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); await homeContract.initialize(owner, '3', '2', '1', gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); @@ -82,7 +91,8 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, owner, foreignDailyLimit, foreignMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, token.address, halfEther, oneEther, owner).should.be.rejectedWith(ERROR_MSG); await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled; - true.should.be.equal(await homeContract.isInitialized()) + + expect(await homeContract.isInitialized()).to.be.equal(true) }) }) @@ -93,7 +103,7 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner) }) it('reverts', async () => { - const {logs} = await homeContract.sendTransaction({ + await homeContract.sendTransaction({ from: accounts[1], value: 1 }).should.be.rejectedWith(ERROR_MSG) @@ -136,56 +146,54 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const balanceBefore = await token.balanceOf(recipient) const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; const {logs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}) - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ + expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], transactionHash - }); - logs[1].event.should.be.equal("AffirmationCompleted"); - logs[1].args.should.be.deep.equal({ + }) + expectEventInLogs(logs, 'AffirmationCompleted', { recipient, value, transactionHash }) + const totalSupply = await token.totalSupply() const balanceAfter = await token.balanceOf(recipient) balanceAfter.should.be.bignumber.equal(balanceBefore.add(value)) totalSupply.should.be.bignumber.equal(value) - const msgHash = Web3Utils.soliditySha3(recipient, value, transactionHash); - const senderHash = Web3Utils.soliditySha3(authorities[0], msgHash) + const msgHash = web3.utils.soliditySha3(recipient, value, transactionHash); + const senderHash = web3.utils.soliditySha3(authorities[0], msgHash) true.should.be.equal(await homeBridge.affirmationsSigned(senderHash)) - const markedAsProcessed = new web3.BigNumber(2).pow(255).add(1); markedAsProcessed.should.be.bignumber.equal(await homeBridge.numAffirmationsSigned(msgHash)); await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG) }) it('should allow validator to withdraw with zero value', async () => { const recipient = accounts[5]; - const value = web3.toBigNumber(web3.toWei(0, "ether")); + const value = ZERO const balanceBefore = await token.balanceOf(recipient) const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const {logs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}) - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ + + expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], transactionHash - }); - logs[1].event.should.be.equal("AffirmationCompleted"); - logs[1].args.should.be.deep.equal({ + }) + expectEventInLogs(logs, 'AffirmationCompleted', { recipient, value, transactionHash }) + const totalSupply = await token.totalSupply() const balanceAfter = await token.balanceOf(recipient) balanceAfter.should.be.bignumber.equal(balanceBefore.add(value)) totalSupply.should.be.bignumber.equal(value) - const msgHash = Web3Utils.soliditySha3(recipient, value, transactionHash); - const senderHash = Web3Utils.soliditySha3(authorities[0], msgHash) + const msgHash = web3.utils.soliditySha3(recipient, value, transactionHash); + const senderHash = web3.utils.soliditySha3(authorities[0], msgHash) true.should.be.equal(await homeBridge.affirmationsSigned(senderHash)) - const markedAsProcessed = new web3.BigNumber(2).pow(255).add(1); markedAsProcessed.should.be.bignumber.equal(await homeBridge.numAffirmationsSigned(msgHash)); await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG) }) @@ -203,17 +211,18 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const value = halfEther; const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; const balanceBefore = await token2sig.balanceOf(recipient) - const msgHash = Web3Utils.soliditySha3(recipient, value, transactionHash); + const msgHash = web3.utils.soliditySha3(recipient, value, transactionHash); const {logs} = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ + + expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], transactionHash - }); - '0'.should.be.bignumber.equal(await token2sig.totalSupply()) + }) + + expect(await token2sig.totalSupply()).to.be.bignumber.equal(ZERO) const notProcessed = await homeBridgeWithTwoSigs.numAffirmationsSigned(msgHash); - notProcessed.should.be.bignumber.equal(1); + notProcessed.should.be.bignumber.equal('1'); await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[0]}).should.be.rejectedWith(ERROR_MSG); const secondSignature = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; @@ -221,22 +230,20 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const balanceAfter = await token2sig.balanceOf(recipient) balanceAfter.should.be.bignumber.equal(balanceBefore.add(value)) - secondSignature.logs[1].event.should.be.equal("AffirmationCompleted"); - secondSignature.logs[1].args.should.be.deep.equal({ + expectEventInLogs(secondSignature.logs, 'AffirmationCompleted', { recipient, value, transactionHash }) - const senderHash = Web3Utils.soliditySha3(authoritiesThreeAccs[0], msgHash) + const senderHash = web3.utils.soliditySha3(authoritiesThreeAccs[0], msgHash) true.should.be.equal(await homeBridgeWithTwoSigs.affirmationsSigned(senderHash)) - const senderHash2 = Web3Utils.soliditySha3(authoritiesThreeAccs[1], msgHash); + const senderHash2 = web3.utils.soliditySha3(authoritiesThreeAccs[1], msgHash); true.should.be.equal(await homeBridgeWithTwoSigs.affirmationsSigned(senderHash2)) - const markedAsProcessed = await homeBridgeWithTwoSigs.numAffirmationsSigned(msgHash); - const processed = new web3.BigNumber(2).pow(255).add(2); - markedAsProcessed.should.be.bignumber.equal(processed) + const processed = toBN(2).pow(toBN(255)).add(toBN(2)); + expect(await homeBridgeWithTwoSigs.numAffirmationsSigned(msgHash)).to.be.bignumber.equal(processed) }) it('should not allow to double submit', async () => { const recipient = accounts[5]; @@ -263,10 +270,9 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { await homeBridgeWithTwoSigs.initialize(validatorContractWith2Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token2sig.address, foreignDailyLimit, foreignMaxPerTx, owner); await token2sig.transferOwnership(homeBridgeWithTwoSigs.address); const recipient = accounts[5]; - const value = halfEther.div(2); + const value = halfEther.div(toBN(2)); const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; const balanceBefore = await token.balanceOf(recipient) - const msgHash = Web3Utils.soliditySha3(recipient, value, transactionHash); await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; @@ -290,21 +296,19 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { await homeBridgeWithThreeSigs.initialize(validatorContractWith3Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner); await token.transferOwnership(homeBridgeWithThreeSigs.address); - const value = web3.toBigNumber(web3.toWei(0.5, "ether")); + const value = ether('0.5'); const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; const {logs} = await homeBridgeWithThreeSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesFiveAccs[0]}).should.be.fulfilled; - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ + expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], transactionHash - }); + }) await homeBridgeWithThreeSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesFiveAccs[1]}).should.be.fulfilled; const thirdSignature = await homeBridgeWithThreeSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesFiveAccs[2]}).should.be.fulfilled; - thirdSignature.logs[1].event.should.be.equal("AffirmationCompleted"); - thirdSignature.logs[1].args.should.be.deep.equal({ + expectEventInLogs(thirdSignature.logs, 'AffirmationCompleted', { recipient, value, transactionHash @@ -316,12 +320,11 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; const {logs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.fulfilled; - logs[0].event.should.be.equal("AmountLimitExceeded"); - logs[0].args.should.be.deep.equal({ + expectEventInLogs(logs, 'AmountLimitExceeded', { recipient, value, transactionHash - }); + }) }) it('should fail if txHash already set as above of limits', async () => { const recipient = accounts[5]; @@ -329,12 +332,11 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; const {logs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.fulfilled; - logs[0].event.should.be.equal("AmountLimitExceeded"); - logs[0].args.should.be.deep.equal({ + expectEventInLogs(logs, 'AmountLimitExceeded', { recipient, value, transactionHash - }); + }) await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG) await homeBridge.executeAffirmation(accounts[6], value, transactionHash, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG) @@ -345,13 +347,11 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.fulfilled; - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ + expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], transactionHash - }); - logs[1].event.should.be.equal("AffirmationCompleted"); - logs[1].args.should.be.deep.equal({ + }) + expectEventInLogs(logs, 'AffirmationCompleted', { recipient, value, transactionHash @@ -360,13 +360,11 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const transactionHash2 = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; const { logs: logs2 } = await homeBridge.executeAffirmation(recipient, value, transactionHash2, {from: authorities[0]}).should.be.fulfilled; - logs2[0].event.should.be.equal("SignedForAffirmation"); - logs2[0].args.should.be.deep.equal({ + expectEventInLogs(logs2, 'SignedForAffirmation', { signer: authorities[0], transactionHash: transactionHash2 - }); - logs2[1].event.should.be.equal("AffirmationCompleted"); - logs2[1].args.should.be.deep.equal({ + }) + expectEventInLogs(logs2, 'AffirmationCompleted', { recipient, value, transactionHash: transactionHash2 @@ -375,12 +373,11 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const transactionHash3 = "0x69debd8fd1923c9cb3cd8ef6461e2740b2d037943b941729d5a47671a2bb8712"; const { logs: logs3 } = await homeBridge.executeAffirmation(recipient, value, transactionHash3, {from: authorities[0]}).should.be.fulfilled; - logs3[0].event.should.be.equal("AmountLimitExceeded"); - logs3[0].args.should.be.deep.equal({ + expectEventInLogs(logs3, 'AmountLimitExceeded', { recipient, value, transactionHash: transactionHash3 - }); + }) const outOfLimitAmount = await homeBridge.outOfLimitAmount() @@ -389,22 +386,20 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const transactionHash4 = "0xc9ffe298d85ec5c515153608924b7bdcf1835539813dcc82cdbcc071170c3196"; const { logs: logs4 } = await homeBridge.executeAffirmation(recipient, value, transactionHash4, {from: authorities[0]}).should.be.fulfilled; - logs4[0].event.should.be.equal("AmountLimitExceeded"); - logs4[0].args.should.be.deep.equal({ + expectEventInLogs(logs4, 'AmountLimitExceeded', { recipient, value, transactionHash: transactionHash4 - }); + }) - const newOutOfLimitAmount = await homeBridge.outOfLimitAmount() - newOutOfLimitAmount.should.be.bignumber.equal(oneEther) + expect(await homeBridge.outOfLimitAmount()).to.be.bignumber.equal(oneEther) }) }) describe('#isAlreadyProcessed', async () => { it('returns ', async () => { homeBridge = await HomeBridge.new(); - const bn = new web3.BigNumber(2).pow(255); - const processedNumbers = [bn.add(1).toString(10), bn.add(100).toString(10)]; + const bn = toBN(2).pow(toBN(255)); + const processedNumbers = [bn.add(toBN(1)).toString(10), bn.add(toBN(100)).toString(10)]; true.should.be.equal(await homeBridge.isAlreadyProcessed(processedNumbers[0])); true.should.be.equal(await homeBridge.isAlreadyProcessed(processedNumbers[1])); false.should.be.equal(await homeBridge.isAlreadyProcessed(10)); @@ -412,7 +407,7 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { }) describe('#submitSignature', async () => { - let validatorContractWith2Signatures,authoritiesThreeAccs,ownerOfValidators,tokenPOA20,homeBridgeWithTwoSigs + let validatorContractWith2Signatures,authoritiesThreeAccs,ownerOfValidators,homeBridgeWithTwoSigs beforeEach(async () => { let token2sig = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); validatorContractWith2Signatures = await BridgeValidators.new() @@ -424,11 +419,11 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { await token2sig.transferOwnership(homeBridgeWithTwoSigs.address); }) it('allows a validator to submit a signature', async () => { - var recipientAccount = accounts[8] - var value = web3.toBigNumber(web3.toWei(0.5, "ether")); - var transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - var message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); - var signature = await sign(authoritiesThreeAccs[0], message) + const recipientAccount = accounts[8] + const value = ether('0.5'); + const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; + const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); + const signature = await sign(authoritiesThreeAccs[0], message) const {logs} = await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authorities[0]}).should.be.fulfilled; logs[0].event.should.be.equal('SignedForUserRequest') const msgHashFromLog = logs[0].args.messageHash @@ -437,21 +432,20 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { signature.should.be.equal(signatureFromContract); messageFromContract.should.be.equal(messageFromContract); - const hashMsg = Web3Utils.soliditySha3(message); - '1'.should.be.bignumber.equal(await homeBridgeWithTwoSigs.numMessagesSigned(hashMsg)) - const hashSenderMsg = Web3Utils.soliditySha3(authorities[0], hashMsg) + const hashMsg = web3.utils.soliditySha3(message); + expect(await homeBridgeWithTwoSigs.numMessagesSigned(hashMsg)).to.be.bignumber.equal('1') + const hashSenderMsg = web3.utils.soliditySha3(authorities[0], hashMsg) true.should.be.equal(await homeBridgeWithTwoSigs.messagesSigned(hashSenderMsg)); }) it('when enough requiredSignatures are collected, CollectedSignatures event is emitted', async () => { - var recipientAccount = accounts[8] - var value = web3.toBigNumber(web3.toWei(0.5, "ether")); - var homeGasPrice = web3.toBigNumber(0); - var transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - var message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); - const hashMsg = Web3Utils.soliditySha3(message); - var signature = await sign(authoritiesThreeAccs[0], message) - var signature2 = await sign(authoritiesThreeAccs[1], message) - '2'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); + const recipientAccount = accounts[8] + const value = ether('0.5'); + const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; + const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); + const hashMsg = web3.utils.soliditySha3(message); + const signature = await sign(authoritiesThreeAccs[0], message) + const signature2 = await sign(authoritiesThreeAccs[1], message) + expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('2') await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.rejectedWith(ERROR_MSG); await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[1]}).should.be.rejectedWith(ERROR_MSG); @@ -459,7 +453,7 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { logs.length.should.be.equal(2) logs[1].event.should.be.equal('CollectedSignatures') logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesThreeAccs[1]) - const markedAsProcessed = new web3.BigNumber(2).pow(255).add(2); + const markedAsProcessed = toBN(2).pow(toBN(255)).add(toBN(2)); markedAsProcessed.should.be.bignumber.equal(await homeBridgeWithTwoSigs.numMessagesSigned(hashMsg)) }) it('works with 5 validators and 3 required signatures', async () => { @@ -472,13 +466,13 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const homeBridgeWithThreeSigs = await HomeBridge.new(); await homeBridgeWithThreeSigs.initialize(validatorContractWith3Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner); - const value = web3.toBigNumber(web3.toWei(0.5, "ether")); + const value = ether('0.5'); const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithThreeSigs.address); const signature = await sign(authoritiesFiveAccs[0], message) const signature2 = await sign(authoritiesFiveAccs[1], message) const signature3 = await sign(authoritiesFiveAccs[2], message) - '3'.should.be.bignumber.equal(await validatorContractWith3Signatures.requiredSignatures()); + expect(await validatorContractWith3Signatures.requiredSignatures()).to.be.bignumber.equal('3') await homeBridgeWithThreeSigs.submitSignature(signature, message, {from: authoritiesFiveAccs[0]}).should.be.fulfilled; await homeBridgeWithThreeSigs.submitSignature(signature2, message, {from: authoritiesFiveAccs[1]}).should.be.fulfilled; @@ -488,15 +482,15 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesFiveAccs[2]) }) it('attack when increasing requiredSignatures', async () => { - var recipientAccount = accounts[8] - var value = web3.toBigNumber(web3.toWei(0.5, "ether")); - var homeGasPrice = web3.toBigNumber(0); - var transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - var message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); - var signature = await sign(authoritiesThreeAccs[0], message) - var signature2 = await sign(authoritiesThreeAccs[1], message) - var signature3 = await sign(authoritiesThreeAccs[2], message) - '2'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); + const recipientAccount = accounts[8] + const value = ether('0.5'); + const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; + const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); + const signature = await sign(authoritiesThreeAccs[0], message) + const signature2 = await sign(authoritiesThreeAccs[1], message) + const signature3 = await sign(authoritiesThreeAccs[2], message) + expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('2') + await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.rejectedWith(ERROR_MSG); await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[1]}).should.be.rejectedWith(ERROR_MSG); @@ -505,22 +499,24 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { logs[1].event.should.be.equal('CollectedSignatures') logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesThreeAccs[1]) await validatorContractWith2Signatures.setRequiredSignatures(3).should.be.fulfilled; - '3'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); - const attackerTx = await homeBridgeWithTwoSigs.submitSignature(signature3, message, {from: authoritiesThreeAccs[2]}).should.be.rejectedWith(ERROR_MSG); + expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('3') + + await homeBridgeWithTwoSigs.submitSignature(signature3, message, {from: authoritiesThreeAccs[2]}).should.be.rejectedWith(ERROR_MSG); }) it('attack when decreasing requiredSignatures', async () => { - var recipientAccount = accounts[8] - var value = web3.toBigNumber(web3.toWei(0.5, "ether")); - var homeGasPrice = web3.toBigNumber(0); - var transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - var message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); - var signature = await sign(authoritiesThreeAccs[0], message) - var signature2 = await sign(authoritiesThreeAccs[1], message) - var signature3 = await sign(authoritiesThreeAccs[2], message) - '2'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); + const recipientAccount = accounts[8] + const value = ether('0.5'); + const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; + const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); + const signature = await sign(authoritiesThreeAccs[0], message) + const signature2 = await sign(authoritiesThreeAccs[1], message) + + expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('2') + await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; await validatorContractWith2Signatures.setRequiredSignatures(1).should.be.fulfilled; - '1'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); + + expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('1') const {logs} = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; logs.length.should.be.equal(2) logs[1].event.should.be.equal('CollectedSignatures') @@ -535,13 +531,12 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { it('should return the required message length', async () => { const requiredMessageLength = await homeContract.requiredMessageLength() - '104'.should.be.bignumber.equal(requiredMessageLength) + expect(requiredMessageLength).to.be.bignumber.equal('104') }) }) describe('#fixAssetsAboveLimits', async () => { let homeBridge; - const zeroValue = web3.toBigNumber(web3.toWei(0, "ether")) beforeEach(async () => { const homeBridgeImpl = await HomeBridge.new(); const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; @@ -565,7 +560,7 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { logs.length.should.be.equal(0) const newOutOfLimitAmount = await homeBridge.outOfLimitAmount() - newOutOfLimitAmount.should.be.bignumber.equal(zeroValue) + newOutOfLimitAmount.should.be.bignumber.equal(ZERO) }) it('Should reduce outOfLimitAmount and emit UserRequestForSignature', async () => { const recipient = accounts[5]; @@ -581,14 +576,13 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const { logs } = await homeBridge.fixAssetsAboveLimits(transactionHash, true).should.be.fulfilled logs.length.should.be.equal(1) - logs[0].event.should.be.equal('UserRequestForSignature') - logs[0].args.should.be.deep.equal({ + expectEventInLogs(logs, 'UserRequestForSignature', { recipient, value }) const newOutOfLimitAmount = await homeBridge.outOfLimitAmount() - newOutOfLimitAmount.should.be.bignumber.equal(zeroValue) + newOutOfLimitAmount.should.be.bignumber.equal(ZERO) }) it('Should not be allow to be called by an already fixed txHash', async () => { const recipient = accounts[5]; @@ -611,7 +605,7 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { await homeBridge.fixAssetsAboveLimits(transactionHash2, false).should.be.fulfilled const updatedOutOfLimitAmount = await homeBridge.outOfLimitAmount() - updatedOutOfLimitAmount.should.be.bignumber.equal(zeroValue) + updatedOutOfLimitAmount.should.be.bignumber.equal(ZERO) await homeBridge.fixAssetsAboveLimits(transactionHash2, false).should.be.rejectedWith(ERROR_MSG) }) @@ -665,37 +659,36 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { rewardableValidators = await RewardableValidators.new() await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled homeBridge = await POSDAOHomeBridge.new() - homeFee = web3.toBigNumber(web3.toWei(0.002, "ether")) - foreignFee = web3.toBigNumber(web3.toWei(0.002, "ether")) + homeFee = ether('0.002') + foreignFee = ether('0.002') blockRewardContract = await BlockReward.new() }) it('sets variables', async () => { const feeManager = await FeeManagerErcToErcPOSDAO.new() - ZERO_ADDRESS.should.be.equal(await homeBridge.validatorContract()) - '0'.should.be.bignumber.equal(await homeBridge.deployedAtBlock()) - '0'.should.be.bignumber.equal(await homeBridge.dailyLimit()) - '0'.should.be.bignumber.equal(await homeBridge.maxPerTx()) - false.should.be.equal(await homeBridge.isInitialized()) - - await homeBridge.rewardableInitialize(ZERO_ADDRESS, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.rejectedWith(ERROR_MSG); - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, 0, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.rejectedWith(ERROR_MSG); - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, 0, foreignDailyLimit, token.address, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.rejectedWith(ERROR_MSG); - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, ZERO_ADDRESS, homeFee, foreignFee, blockRewardContract.address).should.be.rejectedWith(ERROR_MSG); + expect(await homeBridge.validatorContract()).to.be.equal(ZERO_ADDRESS) + expect(await homeBridge.deployedAtBlock()).to.be.bignumber.equal(ZERO) + expect(await homeBridge.dailyLimit()).to.be.bignumber.equal(ZERO) + expect(await homeBridge.maxPerTx()).to.be.bignumber.equal(ZERO) + expect(await homeBridge.isInitialized()).to.be.equal(false) + + await homeBridge.rewardableInitialize(ZERO_ADDRESS, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.rejected; + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, 0, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.rejected; + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, 0, foreignDailyLimit, token.address, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.rejected; + await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, ZERO_ADDRESS, homeFee, foreignFee, blockRewardContract.address).should.be.rejected; await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.fulfilled; - true.should.be.equal(await homeBridge.isInitialized()) - rewardableValidators.address.should.be.equal(await homeBridge.validatorContract()); - (await homeBridge.deployedAtBlock()).should.be.bignumber.above(0); - oneEther.should.be.bignumber.equal(await homeBridge.dailyLimit()) - halfEther.should.be.bignumber.equal(await homeBridge.maxPerTx()) - minPerTx.should.be.bignumber.equal(await homeBridge.minPerTx()) + expect(await homeBridge.isInitialized()).to.be.equal(true) + expect(await homeBridge.validatorContract()).to.be.equal(rewardableValidators.address) + expect(await homeBridge.deployedAtBlock()).to.be.bignumber.above(ZERO) + expect(await homeBridge.dailyLimit()).to.be.bignumber.equal(oneEther) + expect(await homeBridge.maxPerTx()).to.be.bignumber.equal(halfEther) + expect(await homeBridge.minPerTx()).to.be.bignumber.equal(minPerTx) const bridgeMode = '0xba4690f5' // 4 bytes of keccak256('erc-to-erc-core') - const mode = await homeBridge.getBridgeMode(); - mode.should.be.equal(bridgeMode) - const [major, minor, patch] = await homeBridge.getBridgeInterfacesVersion() - major.should.be.bignumber.gte(0) - minor.should.be.bignumber.gte(0) - patch.should.be.bignumber.gte(0) + expect(await homeBridge.getBridgeMode()).to.be.equal(bridgeMode) + const { major, minor, patch } = await homeBridge.getBridgeInterfacesVersion() + expect(major).to.be.bignumber.gte(ZERO) + expect(minor).to.be.bignumber.gte(ZERO) + expect(patch).to.be.bignumber.gte(ZERO) const feeManagerContract = await homeBridge.feeManagerContract() feeManagerContract.should.be.equals(feeManager.address) @@ -725,8 +718,8 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.fulfilled; // Given - const newHomeFee = web3.toBigNumber(web3.toWei(0.1, "ether")) - const newForeignFee = web3.toBigNumber(web3.toWei(0.4, "ether")) + const newHomeFee = ether('0.1') + const newForeignFee = ether('0.4') // When await homeBridge.setHomeFee(newHomeFee, {from: owner}).should.be.fulfilled @@ -787,10 +780,8 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { // Then const events = await getEvents(homeBridge, {event: 'UserRequestForSignature'}); - events[0].args.should.be.deep.equal({ - recipient: user, - value - }) + expect(events[0].returnValues.recipient).to.be.equal(user) + expect(toBN(events[0].returnValues.value)).to.be.bignumber.equal(value) }) it('should trigger UserRequestForSignature with fee subtracted', async () => { // Given @@ -805,12 +796,13 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled const feeManager = await FeeManagerErcToErcPOSDAO.new() const fee = 0.001 - const homeFee = web3.toBigNumber(web3.toWei(0.001, "ether")) - const foreignFee = web3.toBigNumber(web3.toWei(0.001, "ether")) + const homeFee = ether('0.001') + const foreignFee = ether('0.001') await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.fulfilled; const value = halfEther - const finalValue = value.mul(web3.toBigNumber(1 - fee)) + const finalValueCalc = 0.5 * (1 - fee) + const finalValue = ether(finalValueCalc.toString()) await token.mint(user, value, {from: owner}).should.be.fulfilled; // When @@ -818,10 +810,8 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { // Then const events = await getEvents(homeBridge, {event: 'UserRequestForSignature'}); - events[0].args.should.be.deep.equal({ - recipient: user, - value: finalValue - }) + expect(events[0].returnValues.recipient).to.be.equal(user) + expect(toBN(events[0].returnValues.value)).to.be.bignumber.equal(finalValue) }) }) describe('#rewardable_submitSignatures', () => { @@ -832,8 +822,8 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { feeManager = await FeeManagerErcToErcPOSDAO.new() homeBridge = await POSDAOHomeBridge.new() fee = 0.001 - homeFee = web3.toBigNumber(web3.toWei(fee, "ether")) - foreignFee = web3.toBigNumber(web3.toWei(fee, "ether")) + homeFee = ether(fee.toString()) + foreignFee = ether(fee.toString()) blockRewardContract = await BlockReward.new() await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.fulfilled; }) @@ -850,9 +840,10 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { await token.setBlockRewardContract(blockRewardContract.address, {from: owner}) await token.transferOwnership(homeBridge.address, {from: owner}) - const initialValue = halfEther - const value = initialValue.mul(web3.toBigNumber(1 - fee)) - const feeAmount = initialValue.mul(web3.toBigNumber(fee)) + const valueCalc = 0.5 * (1 - fee) + const value = ether(valueCalc.toString()) + const feeAmountCalc = 0.5 * fee + const feeAmount = ether(feeAmountCalc.toString()) const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; const message = createMessage(recipient, value, transactionHash, homeBridge.address); const signature = await sign(validators[0], message) @@ -866,8 +857,7 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { // Then logs.length.should.be.equal(3) logs[1].event.should.be.equal('CollectedSignatures') - logs[2].event.should.be.equal("FeeDistributedFromSignatures"); - logs[2].args.should.be.deep.equal({ + expectEventInLogs(logs, 'FeeDistributedFromSignatures', { feeAmount, transactionHash }) @@ -894,11 +884,12 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { await token.setBlockRewardContract(blockRewardContract.address) await token.transferOwnership(homeBridge.address) - const initialValue = halfEther - const value = initialValue.mul(web3.toBigNumber(1 - fee)) - const feeAmount = initialValue.mul(web3.toBigNumber(fee)) - const feePerValidator = web3.toBigNumber(166666666666666) - const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) + const calcValue = 0.5 * (1- fee) + const value = ether(calcValue.toString()) + const calcFeeAmount = 0.5 * fee + const feeAmount = ether(calcFeeAmount.toString()) + const feePerValidator = toBN(166666666666666) + const feePerValidatorPlusDiff = toBN(166666666666668) const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; const message = createMessage(recipient, value, transactionHash, homeBridge.address); const signature = await sign(validators[0], message) @@ -911,8 +902,7 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { // Then logs.length.should.be.equal(3) logs[1].event.should.be.equal('CollectedSignatures') - logs[2].event.should.be.equal("FeeDistributedFromSignatures"); - logs[2].args.should.be.deep.equal({ + expectEventInLogs(logs, 'FeeDistributedFromSignatures', { feeAmount, transactionHash }) @@ -944,10 +934,11 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { await token.setBlockRewardContract(blockRewardContract.address) await token.transferOwnership(homeBridge.address) - const initialValue = halfEther - const value = initialValue.mul(web3.toBigNumber(1 - fee)) - const feeAmount = initialValue.mul(web3.toBigNumber(fee)) - const feePerValidator = feeAmount.div(web3.toBigNumber(5)) + const valueCalc = 0.5 * (1 - fee) + const value = ether(valueCalc.toString()) + const feeAmountCalc = 0.5 * fee + const feeAmount = ether(feeAmountCalc.toString()) + const feePerValidator = feeAmount.div(toBN(5)) const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; const message = createMessage(recipient, value, transactionHash, homeBridge.address); const signature = await sign(validators[0], message) @@ -962,8 +953,7 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { // Then logs.length.should.be.equal(3) logs[1].event.should.be.equal('CollectedSignatures') - logs[2].event.should.be.equal("FeeDistributedFromSignatures"); - logs[2].args.should.be.deep.equal({ + expectEventInLogs(logs, 'FeeDistributedFromSignatures', { feeAmount, transactionHash }) @@ -995,8 +985,8 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { feeManager = await FeeManagerErcToErcPOSDAO.new() homeBridge = await POSDAOHomeBridge.new() fee = 0.001 - homeFee = web3.toBigNumber(web3.toWei(fee, "ether")) - foreignFee = web3.toBigNumber(web3.toWei(fee, "ether")) + homeFee = ether(fee.toString()) + foreignFee = ether(fee.toString()) blockRewardContract = await BlockReward.new() await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.fulfilled; }) @@ -1014,8 +1004,10 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { await token.transferOwnership(homeBridge.address) const initialValue = halfEther - const value = initialValue.mul(web3.toBigNumber(1 - fee)) - const feeAmount = initialValue.mul(web3.toBigNumber(fee)) + const valueCalc = 0.5 * (1 - fee) + const value = ether(valueCalc.toString()) + const feeAmountCalc = 0.5 * fee + const feeAmount = ether(feeAmountCalc.toString()) const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; const rewardAddressBalanceBefore = await token.balanceOf(rewards[0]) @@ -1025,13 +1017,12 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const { logs } = await homeBridge.executeAffirmation(recipient, initialValue, transactionHash, {from: validators[0]}).should.be.fulfilled; // Then - logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); - logs[1].args.should.be.deep.equal({ + expectEventInLogs(logs, 'FeeDistributedFromAffirmation', { feeAmount, transactionHash }) - logs[2].event.should.be.equal("AffirmationCompleted"); - logs[2].args.should.be.deep.equal({ + + expectEventInLogs(logs, 'AffirmationCompleted', { recipient, value: initialValue, transactionHash @@ -1060,10 +1051,12 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { await token.transferOwnership(homeBridge.address) const initialValue = halfEther - const value = initialValue.mul(web3.toBigNumber(1 - fee)) - const feeAmount = initialValue.mul(web3.toBigNumber(fee)) - const feePerValidator = web3.toBigNumber(166666666666666) - const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) + const valueCalc = 0.5 * (1 - fee) + const value = ether(valueCalc.toString()) + const feeAmountCalc = 0.5 * fee + const feeAmount = ether(feeAmountCalc.toString()) + const feePerValidator = toBN(166666666666666) + const feePerValidatorPlusDiff = toBN(166666666666668) const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80" const rewardAddressBalanceBefore = await token.balanceOf(rewards[0]) @@ -1074,13 +1067,12 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const { logs } = await homeBridge.executeAffirmation(recipient, initialValue, transactionHash, {from: validators[1]}).should.be.fulfilled // Then - logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); - logs[1].args.should.be.deep.equal({ + expectEventInLogs(logs, 'FeeDistributedFromAffirmation', { feeAmount, transactionHash }) - logs[2].event.should.be.equal("AffirmationCompleted"); - logs[2].args.should.be.deep.equal({ + + expectEventInLogs(logs, 'AffirmationCompleted', { recipient, value: initialValue, transactionHash @@ -1114,9 +1106,11 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { await token.transferOwnership(homeBridge.address) const initialValue = halfEther - const value = initialValue.mul(web3.toBigNumber(1 - fee)) - const feeAmount = initialValue.mul(web3.toBigNumber(fee)) - const feePerValidator = feeAmount.div(web3.toBigNumber(5)) + const valueCalc = 0.5 * (1 - fee) + const value = ether(valueCalc.toString()) + const feeAmountCalc = 0.5 * fee + const feeAmount = ether(feeAmountCalc.toString()) + const feePerValidator = feeAmount.div(toBN(5)) const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80" const rewardAddressBalanceBefore = await token.balanceOf(rewards[0]) @@ -1128,13 +1122,12 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const { logs } = await homeBridge.executeAffirmation(recipient, initialValue, transactionHash, {from: validators[2]}).should.be.fulfilled // Then - logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); - logs[1].args.should.be.deep.equal({ + expectEventInLogs(logs, 'FeeDistributedFromAffirmation', { feeAmount, transactionHash }) - logs[2].event.should.be.equal("AffirmationCompleted"); - logs[2].args.should.be.deep.equal({ + + expectEventInLogs(logs, 'AffirmationCompleted', { recipient, value: initialValue, transactionHash diff --git a/test/erc_to_native/foreign_bridge.test.js b/test/erc_to_native/foreign_bridge.test.js index b11a783e1..f6708c74f 100644 --- a/test/erc_to_native/foreign_bridge.test.js +++ b/test/erc_to_native/foreign_bridge.test.js @@ -2,17 +2,20 @@ const ForeignBridge = artifacts.require("ForeignBridgeErcToNative.sol"); const ForeignBridgeV2 = artifacts.require("ForeignBridgeV2.sol"); const BridgeValidators = artifacts.require("BridgeValidators.sol"); const EternalStorageProxy = artifacts.require("EternalStorageProxy.sol"); - const ERC677BridgeToken = artifacts.require("ERC677BridgeToken.sol"); -const { ERROR_MSG, ZERO_ADDRESS } = require('../setup'); -const { createMessage, sign, signatureToVRS } = require('../helpers/helpers'); -const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")); + +const { expect } = require('chai'); +const { ERROR_MSG, ZERO_ADDRESS, toBN } = require('../setup'); +const { createMessage, sign, signatureToVRS, ether } = require('../helpers/helpers'); + +const halfEther = ether('0.5'); const requireBlockConfirmations = 8; -const gasPrice = web3.toWei('1', 'gwei'); -const oneEther = web3.toBigNumber(web3.toWei(1, "ether")); +const gasPrice = web3.utils.toWei('1', 'gwei'); +const oneEther = ether('1'); const homeDailyLimit = oneEther const homeMaxPerTx = halfEther const maxPerTx = halfEther +const ZERO = toBN(0) contract('ForeignBridge_ERC20_to_Native', async (accounts) => { let validatorContract, authorities, owner, token; @@ -28,11 +31,11 @@ contract('ForeignBridge_ERC20_to_Native', async (accounts) => { token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); let foreignBridge = await ForeignBridge.new(); - ZERO_ADDRESS.should.be.equal(await foreignBridge.erc20token()); - ZERO_ADDRESS.should.be.equal(await foreignBridge.validatorContract()) - '0'.should.be.bignumber.equal(await foreignBridge.deployedAtBlock()) - false.should.be.equal(await foreignBridge.isInitialized()) - '0'.should.be.bignumber.equal(await foreignBridge.requiredBlockConfirmations()) + expect(await foreignBridge.erc20token()).to.be.equal(ZERO_ADDRESS) + expect(await foreignBridge.validatorContract()).to.be.equal(ZERO_ADDRESS) + expect(await foreignBridge.deployedAtBlock()).to.be.bignumber.equal(ZERO) + expect(await foreignBridge.isInitialized()).to.be.equal(false) + expect(await foreignBridge.requiredBlockConfirmations()).to.be.bignumber.equal(ZERO) await foreignBridge.initialize(ZERO_ADDRESS, token.address, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); await foreignBridge.initialize(validatorContract.address, ZERO_ADDRESS, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); @@ -44,26 +47,23 @@ contract('ForeignBridge_ERC20_to_Native', async (accounts) => { await foreignBridge.initialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner); - token.address.should.be.equal(await foreignBridge.erc20token()); - true.should.be.equal(await foreignBridge.isInitialized()) - validatorContract.address.should.be.equal(await foreignBridge.validatorContract()); - token.address.should.be.equal(await foreignBridge.erc20token()); - (await foreignBridge.deployedAtBlock()).should.be.bignumber.above(0); - requireBlockConfirmations.should.be.bignumber.equal(await foreignBridge.requiredBlockConfirmations()) - const contractGasPrice = await foreignBridge.gasPrice() - contractGasPrice.should.be.bignumber.equal(gasPrice) - const bridgeMode = '0x18762d46' // 4 bytes of keccak256('erc-to-erc-core') - const mode = await foreignBridge.getBridgeMode(); - mode.should.be.equal(bridgeMode) - const [major, minor, patch] = await foreignBridge.getBridgeInterfacesVersion() - major.should.be.bignumber.gte(0) - minor.should.be.bignumber.gte(0) - patch.should.be.bignumber.gte(0) + expect(await foreignBridge.erc20token()).to.be.equal(token.address) + expect(await foreignBridge.isInitialized()).to.be.equal(true) + expect(await foreignBridge.validatorContract()).to.be.equal(validatorContract.address) + expect(await foreignBridge.deployedAtBlock()).to.be.bignumber.above(ZERO) + expect(await foreignBridge.requiredBlockConfirmations()).to.be.bignumber.equal(requireBlockConfirmations.toString()) + expect(await foreignBridge.gasPrice()).to.be.bignumber.equal(gasPrice) + const bridgeMode = '0x18762d46' // 4 bytes of keccak256('erc-to-native-core') + expect(await foreignBridge.getBridgeMode()).to.be.equal(bridgeMode) + const { major, minor, patch } = await foreignBridge.getBridgeInterfacesVersion() + expect(major).to.be.bignumber.gte(ZERO) + expect(minor).to.be.bignumber.gte(ZERO) + expect(patch).to.be.bignumber.gte(ZERO) }) }) describe('#executeSignatures', async () => { - const value = web3.toBigNumber(web3.toWei(0.25, "ether")); + const value = ether('0.25'); let foreignBridge beforeEach(async () => { foreignBridge = await ForeignBridge.new() @@ -90,7 +90,7 @@ contract('ForeignBridge_ERC20_to_Native', async (accounts) => { const balanceAfter = await token.balanceOf(recipientAccount); const balanceAfterBridge = await token.balanceOf(foreignBridge.address); balanceAfter.should.be.bignumber.equal(balanceBefore.add(value)) - balanceAfterBridge.should.be.bignumber.equal(0) + balanceAfterBridge.should.be.bignumber.equal(ZERO) true.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) }) @@ -99,7 +99,7 @@ contract('ForeignBridge_ERC20_to_Native', async (accounts) => { const balanceBefore = await token.balanceOf(recipientAccount) // tx 1 - const value = web3.toBigNumber(web3.toWei(0.25, "ether")); + const value = ether('0.25'); const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); const signature = await sign(authorities[0], message) @@ -110,10 +110,10 @@ contract('ForeignBridge_ERC20_to_Native', async (accounts) => { // tx 2 await token.mint(foreignBridge.address,value); - var transactionHash2 = "0x77a496628a776a03d58d7e6059a5937f04bebd8ba4ff89f76dd4bb8ba7e291ee"; - var message2 = createMessage(recipientAccount, value, transactionHash2, foreignBridge.address); - var signature2 = await sign(authorities[0], message2) - var vrs2 = signatureToVRS(signature2); + const transactionHash2 = "0x77a496628a776a03d58d7e6059a5937f04bebd8ba4ff89f76dd4bb8ba7e291ee"; + const message2 = createMessage(recipientAccount, value, transactionHash2, foreignBridge.address); + const signature2 = await sign(authorities[0], message2) + const vrs2 = signatureToVRS(signature2); false.should.be.equal(await foreignBridge.relayedMessages(transactionHash2)) const {logs} = await foreignBridge.executeSignatures([vrs2.v], [vrs2.r], [vrs2.s], message2).should.be.fulfilled @@ -122,7 +122,7 @@ contract('ForeignBridge_ERC20_to_Native', async (accounts) => { logs[0].args.recipient.should.be.equal(recipientAccount) logs[0].args.value.should.be.bignumber.equal(value) const balanceAfter = await token.balanceOf(recipientAccount) - balanceAfter.should.be.bignumber.equal(balanceBefore.add(value.mul(2))) + balanceAfter.should.be.bignumber.equal(balanceBefore.add(value.mul(toBN(2)))) true.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) true.should.be.equal(await foreignBridge.relayedMessages(transactionHash2)) }) @@ -151,8 +151,8 @@ contract('ForeignBridge_ERC20_to_Native', async (accounts) => { it('should not allow withdraw over home max tx limit', async () => { const recipientAccount = accounts[3]; - const invalidValue = web3.toBigNumber(web3.toWei(0.75, "ether")); - await token.mint(foreignBridge.address, web3.toBigNumber(web3.toWei(5, "ether"))); + const invalidValue = ether('0.75'); + await token.mint(foreignBridge.address, ether('5')); const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; const message = createMessage(recipientAccount, invalidValue, transactionHash, foreignBridge.address); @@ -164,7 +164,7 @@ contract('ForeignBridge_ERC20_to_Native', async (accounts) => { it('should not allow withdraw over daily home limit', async () => { const recipientAccount = accounts[3]; - await token.mint(foreignBridge.address, web3.toBigNumber(web3.toWei(5, "ether"))); + await token.mint(foreignBridge.address, ether('5')); const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; const message = createMessage(recipientAccount, halfEther, transactionHash, foreignBridge.address); @@ -191,7 +191,7 @@ contract('ForeignBridge_ERC20_to_Native', async (accounts) => { describe('#withdraw with 2 minimum signatures', async () => { let multisigValidatorContract, twoAuthorities, ownerOfValidatorContract, foreignBridgeWithMultiSignatures - const value = web3.toBigNumber(web3.toWei(0.5, "ether")); + const value = halfEther beforeEach(async () => { multisigValidatorContract = await BridgeValidators.new() token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); @@ -244,7 +244,7 @@ contract('ForeignBridge_ERC20_to_Native', async (accounts) => { const validatorContractWith3Signatures = await BridgeValidators.new() await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) const erc20Token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); - const value = web3.toBigNumber(web3.toWei(0.5, "ether")); + const value = halfEther const foreignBridgeWithThreeSigs = await ForeignBridge.new() await foreignBridgeWithThreeSigs.initialize(validatorContractWith3Signatures.address, erc20Token.address, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner); @@ -311,7 +311,7 @@ contract('ForeignBridge_ERC20_to_Native', async (accounts) => { const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; const foreignBridge = await ForeignBridge.new(); - const data = foreignBridge.initialize.request(validatorsAddress, tokenAddress, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner).params[0].data + const data = foreignBridge.contract.methods.initialize(validatorsAddress, tokenAddress, requireBlockConfirmations, gasPrice, '2', '3', '2', owner).encodeABI() await storageProxy.upgradeToAndCall('1', foreignBridge.address, data).should.be.fulfilled; @@ -334,15 +334,15 @@ contract('ForeignBridge_ERC20_to_Native', async (accounts) => { const tokenSecond = await ERC677BridgeToken.new("Roman Token", "RST", 18); await tokenSecond.mint(accounts[0], halfEther).should.be.fulfilled; - halfEther.should.be.bignumber.equal(await tokenSecond.balanceOf(accounts[0])) + expect(await tokenSecond.balanceOf(accounts[0])).to.be.bignumber.equal(halfEther) await tokenSecond.transfer(foreignBridge.address, halfEther); - '0'.should.be.bignumber.equal(await tokenSecond.balanceOf(accounts[0])) - halfEther.should.be.bignumber.equal(await tokenSecond.balanceOf(foreignBridge.address)) + expect(await tokenSecond.balanceOf(accounts[0])).to.be.bignumber.equal(ZERO) + expect(await tokenSecond.balanceOf(foreignBridge.address)).to.be.bignumber.equal(halfEther) await foreignBridge.claimTokens(tokenSecond.address, accounts[3], {from: owner}); - '0'.should.be.bignumber.equal(await tokenSecond.balanceOf(foreignBridge.address)) - halfEther.should.be.bignumber.equal(await tokenSecond.balanceOf(accounts[3])) + expect(await tokenSecond.balanceOf(foreignBridge.address)).to.be.bignumber.equal(ZERO) + expect(await tokenSecond.balanceOf(accounts[3])).to.be.bignumber.equal(halfEther) }) }) }) diff --git a/test/erc_to_native/home_bridge.test.js b/test/erc_to_native/home_bridge.test.js index 0db324fe9..55d3c803a 100644 --- a/test/erc_to_native/home_bridge.test.js +++ b/test/erc_to_native/home_bridge.test.js @@ -1,4 +1,3 @@ -const Web3Utils = require('web3-utils') const HomeBridge = artifacts.require('HomeBridgeErcToNative.sol') const EternalStorageProxy = artifacts.require('EternalStorageProxy.sol') const BridgeValidators = artifacts.require('BridgeValidators.sol') @@ -6,15 +5,19 @@ const BlockReward = artifacts.require('BlockReward') const RewardableValidators = artifacts.require("RewardableValidators.sol"); const FeeManagerErcToNative = artifacts.require("FeeManagerErcToNative.sol"); const FeeManagerErcToNativePOSDAO = artifacts.require("FeeManagerErcToNativePOSDAO"); -const {ERROR_MSG, ZERO_ADDRESS} = require('../setup'); -const {createMessage, sign } = require('../helpers/helpers'); -const minPerTx = web3.toBigNumber(web3.toWei(0.01, "ether")); + +const { expect } = require('chai'); +const { ERROR_MSG, ZERO_ADDRESS, toBN } = require('../setup'); +const {createMessage, sign, ether, expectEventInLogs } = require('../helpers/helpers'); + +const minPerTx = ether('0.01'); const requireBlockConfirmations = 8; -const gasPrice = Web3Utils.toWei('1', 'gwei'); -const oneEther = web3.toBigNumber(web3.toWei(1, "ether")); -const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")); +const gasPrice = web3.utils.toWei('1', 'gwei'); +const oneEther = ether('1'); +const halfEther = ether('0.5'); const foreignDailyLimit = oneEther const foreignMaxPerTx = halfEther +const ZERO = toBN(0) contract('HomeBridge_ERC20_to_Native', async (accounts) => { @@ -32,31 +35,29 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { homeContract = await HomeBridge.new() }) it('sets variables', async () => { - ZERO_ADDRESS.should.be.equal(await homeContract.validatorContract()) - '0'.should.be.bignumber.equal(await homeContract.deployedAtBlock()) - '0'.should.be.bignumber.equal(await homeContract.dailyLimit()) - '0'.should.be.bignumber.equal(await homeContract.maxPerTx()) - false.should.be.equal(await homeContract.isInitialized()) - ZERO_ADDRESS.should.be.equal(await homeContract.blockRewardContract()) + expect(await homeContract.validatorContract()).to.be.equal(ZERO_ADDRESS) + expect(await homeContract.deployedAtBlock()).to.be.bignumber.equal(ZERO) + expect(await homeContract.dailyLimit()).to.be.bignumber.equal(ZERO) + expect(await homeContract.maxPerTx()).to.be.bignumber.equal(ZERO) + expect(await homeContract.isInitialized()).to.be.equal(false) + expect(await homeContract.blockRewardContract()).to.be.equal(ZERO_ADDRESS) await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled - true.should.be.equal(await homeContract.isInitialized()) - validatorContract.address.should.be.equal(await homeContract.validatorContract()) - blockRewardContract.address.should.be.equal(await homeContract.blockRewardContract()); - (await homeContract.deployedAtBlock()).should.be.bignumber.above(0) - '3'.should.be.bignumber.equal(await homeContract.dailyLimit()) - '2'.should.be.bignumber.equal(await homeContract.maxPerTx()) - '1'.should.be.bignumber.equal(await homeContract.minPerTx()) - const contractGasPrice = await homeContract.gasPrice() - contractGasPrice.should.be.bignumber.equal(gasPrice) + expect(await homeContract.isInitialized()).to.be.equal(true) + expect(await homeContract.validatorContract()).to.be.equal(validatorContract.address) + expect(await homeContract.deployedAtBlock()).to.be.bignumber.above(ZERO) + expect(await homeContract.dailyLimit()).to.be.bignumber.equal('3') + expect(await homeContract.maxPerTx()).to.be.bignumber.equal('2') + expect(await homeContract.minPerTx()).to.be.bignumber.equal('1') + expect(await homeContract.blockRewardContract()).to.be.equal(blockRewardContract.address) + expect(await homeContract.gasPrice()).to.be.bignumber.equal(gasPrice) const bridgeMode = '0x18762d46' // 4 bytes of keccak256('erc-to-native-core') - const mode = await homeContract.getBridgeMode(); - mode.should.be.equal(bridgeMode) - const [major, minor, patch] = await homeContract.getBridgeInterfacesVersion() - major.should.be.bignumber.gte(0) - minor.should.be.bignumber.gte(0) - patch.should.be.bignumber.gte(0) + expect(await homeContract.getBridgeMode()).to.be.equal(bridgeMode) + const { major, minor, patch } = await homeContract.getBridgeInterfacesVersion() + expect(major).to.be.bignumber.gte(ZERO) + expect(minor).to.be.bignumber.gte(ZERO) + expect(patch).to.be.bignumber.gte(ZERO) }) it('can update block reward contract', async () => { @@ -93,47 +94,46 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { it('can be deployed via upgradeToAndCall', async () => { let storageProxy = await EternalStorageProxy.new().should.be.fulfilled; - let data = homeContract.initialize.request(validatorContract.address, "3", "2", "1", gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).params[0].data + let data = homeContract.contract.methods.initialize(validatorContract.address, "3", "2", "1", gasPrice, requireBlockConfirmations, blockRewardContract.address, '3', '2', owner).encodeABI() await storageProxy.upgradeToAndCall('1', homeContract.address, data).should.be.fulfilled let finalContract = await HomeBridge.at(storageProxy.address); - true.should.be.equal(await finalContract.isInitialized()) - validatorContract.address.should.be.equal(await finalContract.validatorContract()) - blockRewardContract.address.should.be.equal(await finalContract.blockRewardContract()) - "3".should.be.bignumber.equal(await finalContract.dailyLimit()) - "2".should.be.bignumber.equal(await finalContract.maxPerTx()) - "1".should.be.bignumber.equal(await finalContract.minPerTx()) + expect(await finalContract.isInitialized()).to.be.equal(true) + expect(await finalContract.validatorContract()).to.be.equal(validatorContract.address) + expect(await finalContract.dailyLimit()).to.be.bignumber.equal('3') + expect(await finalContract.maxPerTx()).to.be.bignumber.equal('2') + expect(await finalContract.minPerTx()).to.be.bignumber.equal('1') + expect(await finalContract.blockRewardContract()).to.be.equal(blockRewardContract.address) }) it('can be upgraded keeping the state', async () => { const homeOwner = accounts[8] const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; const proxyOwner = await storageProxy.proxyOwner() - const data = homeContract.initialize.request(validatorContract.address, "3", "2", "1", gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, homeOwner).params[0].data + const data = homeContract.contract.methods.initialize(validatorContract.address, "3", "2", "1", gasPrice, requireBlockConfirmations, blockRewardContract.address, '3', '2', homeOwner).encodeABI() await storageProxy.upgradeToAndCall('1', homeContract.address, data).should.be.fulfilled const finalContract = await HomeBridge.at(storageProxy.address); - true.should.be.equal(await finalContract.isInitialized()) - validatorContract.address.should.be.equal(await finalContract.validatorContract()) - blockRewardContract.address.should.be.equal(await finalContract.blockRewardContract()) - "3".should.be.bignumber.equal(await finalContract.dailyLimit()) - "2".should.be.bignumber.equal(await finalContract.maxPerTx()) - "1".should.be.bignumber.equal(await finalContract.minPerTx()) - const upgradeabilityAdmin = await finalContract.upgradeabilityAdmin() - upgradeabilityAdmin.should.be.equal(proxyOwner) + expect(await finalContract.isInitialized()).to.be.equal(true) + expect(await finalContract.validatorContract()).to.be.equal(validatorContract.address) + expect(await finalContract.dailyLimit()).to.be.bignumber.equal('3') + expect(await finalContract.maxPerTx()).to.be.bignumber.equal('2') + expect(await finalContract.minPerTx()).to.be.bignumber.equal('1') + expect(await finalContract.blockRewardContract()).to.be.equal(blockRewardContract.address) + expect(await finalContract.upgradeabilityAdmin()).to.be.equal(proxyOwner) const homeContractV2 = await HomeBridge.new() await storageProxy.upgradeTo('2', homeContractV2.address).should.be.fulfilled const finalContractV2 = await HomeBridge.at(storageProxy.address); - validatorContract.address.should.be.equal(await finalContractV2.validatorContract()) - blockRewardContract.address.should.be.equal(await finalContractV2.blockRewardContract()) - "3".should.be.bignumber.equal(await finalContractV2.dailyLimit()) - "2".should.be.bignumber.equal(await finalContractV2.maxPerTx()) - "1".should.be.bignumber.equal(await finalContractV2.minPerTx()) - const upgradeabilityAdminV2 = await finalContractV2.upgradeabilityAdmin() - upgradeabilityAdminV2.should.be.equal(proxyOwner) + expect(await finalContractV2.isInitialized()).to.be.equal(true) + expect(await finalContractV2.validatorContract()).to.be.equal(validatorContract.address) + expect(await finalContractV2.dailyLimit()).to.be.bignumber.equal('3') + expect(await finalContractV2.maxPerTx()).to.be.bignumber.equal('2') + expect(await finalContractV2.minPerTx()).to.be.bignumber.equal('1') + expect(await finalContractV2.blockRewardContract()).to.be.equal(blockRewardContract.address) + expect(await finalContractV2.upgradeabilityAdmin()).to.be.equal(proxyOwner) }) it('cant initialize with invalid arguments', async () => { false.should.be.equal(await homeContract.isInitialized()) @@ -152,35 +152,33 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { beforeEach(async () => { feeManager = await FeeManagerErcToNative.new() homeContract = await HomeBridge.new() - homeFee = web3.toBigNumber(web3.toWei(0.001, "ether")) - foreignFee = web3.toBigNumber(web3.toWei(0.002, "ether")) + homeFee = ether('0.001') + foreignFee = ether('0.002') }) it('sets variables', async () => { - ZERO_ADDRESS.should.be.equal(await homeContract.validatorContract()) - '0'.should.be.bignumber.equal(await homeContract.deployedAtBlock()) - '0'.should.be.bignumber.equal(await homeContract.dailyLimit()) - '0'.should.be.bignumber.equal(await homeContract.maxPerTx()) - false.should.be.equal(await homeContract.isInitialized()) - ZERO_ADDRESS.should.be.equal(await homeContract.blockRewardContract()) + expect(await homeContract.validatorContract()).to.be.equal(ZERO_ADDRESS) + expect(await homeContract.deployedAtBlock()).to.be.bignumber.equal(ZERO) + expect(await homeContract.dailyLimit()).to.be.bignumber.equal(ZERO) + expect(await homeContract.maxPerTx()).to.be.bignumber.equal(ZERO) + expect(await homeContract.isInitialized()).to.be.equal(false) + expect(await homeContract.blockRewardContract()).to.be.equal(ZERO_ADDRESS) await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled - true.should.be.equal(await homeContract.isInitialized()) - validatorContract.address.should.be.equal(await homeContract.validatorContract()) - blockRewardContract.address.should.be.equal(await homeContract.blockRewardContract()); - (await homeContract.deployedAtBlock()).should.be.bignumber.above(0) - '3'.should.be.bignumber.equal(await homeContract.dailyLimit()) - '2'.should.be.bignumber.equal(await homeContract.maxPerTx()) - '1'.should.be.bignumber.equal(await homeContract.minPerTx()) - const contractGasPrice = await homeContract.gasPrice() - contractGasPrice.should.be.bignumber.equal(gasPrice) + expect(await homeContract.isInitialized()).to.be.equal(true) + expect(await homeContract.validatorContract()).to.be.equal(validatorContract.address) + expect(await homeContract.deployedAtBlock()).to.be.bignumber.above(ZERO) + expect(await homeContract.dailyLimit()).to.be.bignumber.equal('3') + expect(await homeContract.maxPerTx()).to.be.bignumber.equal('2') + expect(await homeContract.minPerTx()).to.be.bignumber.equal('1') + expect(await homeContract.blockRewardContract()).to.be.equal(blockRewardContract.address) + expect(await homeContract.gasPrice()).to.be.bignumber.equal(gasPrice) const bridgeMode = '0x18762d46' // 4 bytes of keccak256('erc-to-native-core') - const mode = await homeContract.getBridgeMode(); - mode.should.be.equal(bridgeMode) - const [major, minor, patch] = await homeContract.getBridgeInterfacesVersion() - major.should.be.bignumber.gte(0) - minor.should.be.bignumber.gte(0) - patch.should.be.bignumber.gte(0) + expect(await homeContract.getBridgeMode()).to.be.equal(bridgeMode) + const { major, minor, patch } = await homeContract.getBridgeInterfacesVersion() + expect(major).to.be.bignumber.gte(ZERO) + expect(minor).to.be.bignumber.gte(ZERO) + expect(patch).to.be.bignumber.gte(ZERO) const feeManagerContract = await homeContract.feeManagerContract() feeManagerContract.should.be.equals(feeManager.address) @@ -220,8 +218,8 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; // Given - const newHomeFee = web3.toBigNumber(web3.toWei(0.1, "ether")) - const newForeignFee = web3.toBigNumber(web3.toWei(0.2, "ether")) + const newHomeFee = ether('0.1') + const newForeignFee = ether('0.2') // When await homeContract.setHomeFee(newHomeFee, { from: owner }).should.be.fulfilled @@ -243,61 +241,61 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { it('should accept native coins', async () => { const currentDay = await homeContract.getCurrentDay() - '0'.should.be.bignumber.equal(await homeContract.totalSpentPerDay(currentDay)) + expect(await homeContract.totalSpentPerDay(currentDay)).to.be.bignumber.equal(ZERO) await blockRewardContract.addMintedTotallyByBridge(10, homeContract.address) const minted = await blockRewardContract.mintedTotallyByBridge(homeContract.address) - minted.should.be.bignumber.equal(10) + minted.should.be.bignumber.equal('10') const {logs} = await homeContract.sendTransaction({ from: accounts[1], value: 1 }).should.be.fulfilled - logs[0].event.should.be.equal('UserRequestForSignature') - logs[0].args.should.be.deep.equal({ recipient: accounts[1], value: new web3.BigNumber(1) }) - '1'.should.be.bignumber.equal(await homeContract.totalSpentPerDay(currentDay)) - '1'.should.be.bignumber.equal(await homeContract.totalBurntCoins()) - const homeContractBalance = await web3.eth.getBalance(homeContract.address) - homeContractBalance.should.be.bignumber.equal('0') + expectEventInLogs(logs, 'UserRequestForSignature', { recipient: accounts[1], value: toBN(1) }) + expect(await homeContract.totalSpentPerDay(currentDay)).to.be.bignumber.equal('1') + expect(await homeContract.totalBurntCoins()).to.be.bignumber.equal('1') + + const homeContractBalance = toBN(await web3.eth.getBalance(homeContract.address)) + homeContractBalance.should.be.bignumber.equal(ZERO) }) it('should accumulate burnt coins', async () => { await blockRewardContract.addMintedTotallyByBridge(10, homeContract.address) const currentDay = await homeContract.getCurrentDay() - '0'.should.be.bignumber.equal(await homeContract.totalSpentPerDay(currentDay)) + expect(await homeContract.totalSpentPerDay(currentDay)).to.be.bignumber.equal(ZERO) await homeContract.sendTransaction({ from: accounts[1], value: 1 }).should.be.fulfilled - '1'.should.be.bignumber.equal(await homeContract.totalBurntCoins()) + expect(await homeContract.totalBurntCoins()).to.be.bignumber.equal('1') await homeContract.sendTransaction({ from: accounts[1], value: 1 }).should.be.fulfilled - '2'.should.be.bignumber.equal(await homeContract.totalBurntCoins()) + expect(await homeContract.totalBurntCoins()).to.be.bignumber.equal('2') await homeContract.sendTransaction({ from: accounts[1], value: 1 }).should.be.fulfilled - '3'.should.be.bignumber.equal(await homeContract.totalBurntCoins()) + expect(await homeContract.totalBurntCoins()).to.be.bignumber.equal('3') - const homeContractBalance = await web3.eth.getBalance(homeContract.address) - homeContractBalance.should.be.bignumber.equal('0') + const homeContractBalance = toBN(await web3.eth.getBalance(homeContract.address)) + homeContractBalance.should.be.bignumber.equal(ZERO) }) it('doesnt let you send more than daily limit', async () => { await blockRewardContract.addMintedTotallyByBridge(10, homeContract.address) const currentDay = await homeContract.getCurrentDay() - '0'.should.be.bignumber.equal(await homeContract.totalSpentPerDay(currentDay)) + expect(await homeContract.totalSpentPerDay(currentDay)).to.be.bignumber.equal(ZERO) await homeContract.sendTransaction({ from: accounts[1], value: 1 }).should.be.fulfilled - '1'.should.be.bignumber.equal(await homeContract.totalSpentPerDay(currentDay)) - '1'.should.be.bignumber.equal(await homeContract.totalBurntCoins()) + expect(await homeContract.totalSpentPerDay(currentDay)).to.be.bignumber.equal('1') + expect(await homeContract.totalBurntCoins()).to.be.bignumber.equal('1') await homeContract.sendTransaction({ from: accounts[1], value: 1 }).should.be.fulfilled; - '2'.should.be.bignumber.equal(await homeContract.totalSpentPerDay(currentDay)) + expect(await homeContract.totalSpentPerDay(currentDay)).to.be.bignumber.equal('2') await homeContract.sendTransaction({ from: accounts[1], value: 2 }).should.be.rejectedWith(ERROR_MSG); await homeContract.setDailyLimit(4).should.be.fulfilled; await homeContract.sendTransaction({ from: accounts[1], value: 2 }).should.be.fulfilled; - '4'.should.be.bignumber.equal(await homeContract.totalSpentPerDay(currentDay)) - '4'.should.be.bignumber.equal(await homeContract.totalBurntCoins()) + expect(await homeContract.totalSpentPerDay(currentDay)).to.be.bignumber.equal('4') + expect(await homeContract.totalBurntCoins()).to.be.bignumber.equal('4') }) it('doesnt let you send more than max amount per tx', async () => { @@ -345,7 +343,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { it('should fail if not enough bridged tokens', async () => { const initiallyMinted = await blockRewardContract.mintedTotallyByBridge(homeContract.address) - initiallyMinted.should.be.bignumber.equal(0) + initiallyMinted.should.be.bignumber.equal(ZERO) await homeContract.sendTransaction({ from: accounts[1], value: 1 }).should.be.rejectedWith(ERROR_MSG) @@ -360,8 +358,8 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const minted = await blockRewardContract.mintedTotallyByBridge(homeContract.address) const burnt = await homeContract.totalBurntCoins() - minted.should.be.bignumber.equal(2) - burnt.should.be.bignumber.equal(2) + minted.should.be.bignumber.equal('2') + burnt.should.be.bignumber.equal('2') }) }) @@ -377,7 +375,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { await homeContract.setMaxPerTx(3, {from: owner}).should.be.rejectedWith(ERROR_MSG); const maxPerTx = await homeContract.maxPerTx() - maxPerTx.should.be.bignumber.equal(web3.toBigNumber(2)) + maxPerTx.should.be.bignumber.equal(toBN(2)) }) it('setMinPerTx allows to set only to owner and cannot be more than daily limit and should be less than maxPerTx', async () => { @@ -386,11 +384,11 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { await homeContract.setMinPerTx(2, {from: owner}).should.be.rejectedWith(ERROR_MSG); const minPerTx = await homeContract.minPerTx() - minPerTx.should.be.bignumber.equal(web3.toBigNumber(1)) + minPerTx.should.be.bignumber.equal(toBN(1)) }) it('setExecutionMaxPerTx allows to set only to owner and cannot be more than execution daily limit', async () => { - const newValue = web3.toBigNumber(web3.toWei(0.3, "ether")); + const newValue = ether('0.3'); const initialExecutionMaxPerTx = await homeContract.executionMaxPerTx() @@ -405,7 +403,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { }) it('executionDailyLimit allows to set only to owner', async () => { - const newValue = web3.toBigNumber(web3.toWei(1.5, "ether")); + const newValue = ether('1.5'); const initialExecutionDailyLimit= await homeContract.executionDailyLimit() @@ -437,48 +435,45 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; const {logs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}) - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ + expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], transactionHash - }); - logs[1].event.should.be.equal("AffirmationCompleted"); - logs[1].args.should.be.deep.equal({ + }) + expectEventInLogs(logs, 'AffirmationCompleted', { recipient, value, transactionHash }) - const balanceAfter = await web3.eth.getBalance(recipient) - balanceAfter.should.be.bignumber.equal(balanceBefore.add(value)) + const balanceAfter = toBN(await web3.eth.getBalance(recipient)) + balanceAfter.should.be.bignumber.equal(toBN(balanceBefore).add(value)) - const msgHash = Web3Utils.soliditySha3(recipient, value, transactionHash); - const senderHash = Web3Utils.soliditySha3(authorities[0], msgHash) + const msgHash = web3.utils.soliditySha3(recipient, value, transactionHash); + const senderHash = web3.utils.soliditySha3(authorities[0], msgHash) true.should.be.equal(await homeBridge.affirmationsSigned(senderHash)) }) it('should allow validator to executeAffirmation with zero value', async () => { const recipient = accounts[5]; - const value = web3.toBigNumber(web3.toWei(0, "ether")); + const value = ZERO const balanceBefore = await web3.eth.getBalance(recipient) const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; const {logs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}) - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ + expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], transactionHash - }); - logs[1].event.should.be.equal("AffirmationCompleted"); - logs[1].args.should.be.deep.equal({ + }) + expectEventInLogs(logs, 'AffirmationCompleted', { recipient, value, transactionHash }) - const balanceAfter = await web3.eth.getBalance(recipient) - balanceAfter.should.be.bignumber.equal(balanceBefore.add(value)) - const msgHash = Web3Utils.soliditySha3(recipient, value, transactionHash); - const senderHash = Web3Utils.soliditySha3(authorities[0], msgHash) + const balanceAfter = toBN(await web3.eth.getBalance(recipient)) + balanceAfter.should.be.bignumber.equal(toBN(balanceBefore).add(value)) + + const msgHash = web3.utils.soliditySha3(recipient, value, transactionHash); + const senderHash = web3.utils.soliditySha3(authorities[0], msgHash) true.should.be.equal(await homeBridge.affirmationsSigned(senderHash)) }) @@ -492,32 +487,31 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const recipient = accounts[5]; const value = halfEther; const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - const balanceBefore = await web3.eth.getBalance(recipient) - const msgHash = Web3Utils.soliditySha3(recipient, value, transactionHash); + const balanceBefore = toBN(await web3.eth.getBalance(recipient)) + const msgHash = web3.utils.soliditySha3(recipient, value, transactionHash); const { logs } = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ signer: authorities[0], transactionHash }); + expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], transactionHash }) + const notProcessed = await homeBridgeWithTwoSigs.numAffirmationsSigned(msgHash); - notProcessed.should.be.bignumber.equal(1); + notProcessed.should.be.bignumber.equal('1'); await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[0]}).should.be.rejectedWith(ERROR_MSG); const secondSignature = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; - const balanceAfter = await web3.eth.getBalance(recipient) + const balanceAfter = toBN(await web3.eth.getBalance(recipient)) balanceAfter.should.be.bignumber.equal(balanceBefore.add(value)) - secondSignature.logs[1].event.should.be.equal("AffirmationCompleted"); - secondSignature.logs[1].args.should.be.deep.equal({ recipient, value, transactionHash }) + expectEventInLogs(secondSignature.logs, 'AffirmationCompleted', { recipient, value, transactionHash }) - const senderHash = Web3Utils.soliditySha3(authoritiesThreeAccs[0], msgHash) + const senderHash = web3.utils.soliditySha3(authoritiesThreeAccs[0], msgHash) true.should.be.equal(await homeBridgeWithTwoSigs.affirmationsSigned(senderHash)) - const senderHash2 = Web3Utils.soliditySha3(authoritiesThreeAccs[1], msgHash); + const senderHash2 = web3.utils.soliditySha3(authoritiesThreeAccs[1], msgHash); true.should.be.equal(await homeBridgeWithTwoSigs.affirmationsSigned(senderHash2)) const markedAsProcessed = await homeBridgeWithTwoSigs.numAffirmationsSigned(msgHash); - const processed = new web3.BigNumber(2).pow(255).add(2); + const processed = (toBN(2)).pow(toBN(255)).add(toBN(2)) markedAsProcessed.should.be.bignumber.equal(processed) }) @@ -547,21 +541,20 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const homeBridgeWithThreeSigs = await HomeBridge.new(); await homeBridgeWithThreeSigs.initialize(validatorContractWith3Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner); - const value = web3.toBigNumber(web3.toWei(0.5, "ether")); + const value = halfEther const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; const {logs} = await homeBridgeWithThreeSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesFiveAccs[0]}).should.be.fulfilled; - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ + + expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], transactionHash - }); + }) await homeBridgeWithThreeSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesFiveAccs[1]}).should.be.fulfilled; const thirdSignature = await homeBridgeWithThreeSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesFiveAccs[2]}).should.be.fulfilled; - thirdSignature.logs[1].event.should.be.equal("AffirmationCompleted"); - thirdSignature.logs[1].args.should.be.deep.equal({ + expectEventInLogs(thirdSignature.logs, 'AffirmationCompleted', { recipient, value, transactionHash @@ -573,12 +566,11 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; const {logs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.fulfilled; - logs[0].event.should.be.equal("AmountLimitExceeded"); - logs[0].args.should.be.deep.equal({ + expectEventInLogs(logs, 'AmountLimitExceeded', { recipient, value, transactionHash - }); + }) }) it('should fail if txHash already set as above of limits', async () => { const recipient = accounts[5]; @@ -586,12 +578,11 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; const {logs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.fulfilled; - logs[0].event.should.be.equal("AmountLimitExceeded"); - logs[0].args.should.be.deep.equal({ + expectEventInLogs(logs, 'AmountLimitExceeded', { recipient, value, transactionHash - }); + }) await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG) await homeBridge.executeAffirmation(accounts[6], value, transactionHash, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG) @@ -607,13 +598,11 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.fulfilled; - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ + expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], transactionHash - }); - logs[1].event.should.be.equal("AffirmationCompleted"); - logs[1].args.should.be.deep.equal({ + }) + expectEventInLogs(logs, 'AffirmationCompleted', { recipient, value, transactionHash @@ -622,13 +611,11 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const transactionHash2 = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; const { logs: logs2 } = await homeBridge.executeAffirmation(recipient, value, transactionHash2, {from: authorities[0]}).should.be.fulfilled; - logs2[0].event.should.be.equal("SignedForAffirmation"); - logs2[0].args.should.be.deep.equal({ + expectEventInLogs(logs2, 'SignedForAffirmation', { signer: authorities[0], transactionHash: transactionHash2 - }); - logs2[1].event.should.be.equal("AffirmationCompleted"); - logs2[1].args.should.be.deep.equal({ + }) + expectEventInLogs(logs2, 'AffirmationCompleted', { recipient, value, transactionHash: transactionHash2 @@ -637,12 +624,11 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const transactionHash3 = "0x69debd8fd1923c9cb3cd8ef6461e2740b2d037943b941729d5a47671a2bb8712"; const { logs: logs3 } = await homeBridge.executeAffirmation(recipient, value, transactionHash3, {from: authorities[0]}).should.be.fulfilled; - logs3[0].event.should.be.equal("AmountLimitExceeded"); - logs3[0].args.should.be.deep.equal({ + expectEventInLogs(logs3, 'AmountLimitExceeded', { recipient, value, transactionHash: transactionHash3 - }); + }) const outOfLimitAmount = await homeBridge.outOfLimitAmount() @@ -651,12 +637,11 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const transactionHash4 = "0xc9ffe298d85ec5c515153608924b7bdcf1835539813dcc82cdbcc071170c3196"; const { logs: logs4 } = await homeBridge.executeAffirmation(recipient, value, transactionHash4, {from: authorities[0]}).should.be.fulfilled; - logs4[0].event.should.be.equal("AmountLimitExceeded"); - logs4[0].args.should.be.deep.equal({ + expectEventInLogs(logs4, 'AmountLimitExceeded', { recipient, value, transactionHash: transactionHash4 - }); + }) const newOutOfLimitAmount = await homeBridge.outOfLimitAmount() newOutOfLimitAmount.should.be.bignumber.equal(oneEther) @@ -676,7 +661,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { it('allows a validator to submit a signature', async () => { const recipientAccount = accounts[8] - const value = web3.toBigNumber(web3.toWei(0.5, "ether")); + const value = halfEther const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); @@ -689,20 +674,20 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const messageFromContract = await homeBridgeWithTwoSigs.message(messageHash); signature.should.be.equal(signatureFromContract); messageFromContract.should.be.equal(messageFromContract); - const hashMsg = Web3Utils.soliditySha3(message); - const hashSenderMsg = Web3Utils.soliditySha3(authorities[0], hashMsg) + const hashMsg = web3.utils.soliditySha3(message); + const hashSenderMsg = web3.utils.soliditySha3(authorities[0], hashMsg) true.should.be.equal(await homeBridgeWithTwoSigs.messagesSigned(hashSenderMsg)); }) it('when enough requiredSignatures are collected, CollectedSignatures event is emitted', async () => { const recipientAccount = accounts[8] - const value = web3.toBigNumber(web3.toWei(0.5, "ether")); + const value = halfEther const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); const signature = await sign(authoritiesThreeAccs[0], message) const signature2 = await sign(authoritiesThreeAccs[1], message) - '2'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); + expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('2'); await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.rejectedWith(ERROR_MSG); @@ -722,13 +707,13 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const homeBridgeWithThreeSigs = await HomeBridge.new(); await homeBridgeWithThreeSigs.initialize(validatorContractWith3Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner); - const value = web3.toBigNumber(web3.toWei(0.5, "ether")); + const value = halfEther const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithThreeSigs.address); const signature = await sign(authoritiesFiveAccs[0], message) const signature2 = await sign(authoritiesFiveAccs[1], message) const signature3 = await sign(authoritiesFiveAccs[2], message) - '3'.should.be.bignumber.equal(await validatorContractWith3Signatures.requiredSignatures()); + expect(await validatorContractWith3Signatures.requiredSignatures()).to.be.bignumber.equal('3'); await homeBridgeWithThreeSigs.submitSignature(signature, message, {from: authoritiesFiveAccs[0]}).should.be.fulfilled; await homeBridgeWithThreeSigs.submitSignature(signature2, message, {from: authoritiesFiveAccs[1]}).should.be.fulfilled; @@ -739,13 +724,13 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { }) it('attack when increasing requiredSignatures', async () => { const recipientAccount = accounts[8] - const value = web3.toBigNumber(web3.toWei(0.5, "ether")); + const value = halfEther const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); const signature = await sign(authoritiesThreeAccs[0], message) const signature2 = await sign(authoritiesThreeAccs[1], message) const signature3 = await sign(authoritiesThreeAccs[2], message) - '2'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); + expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('2'); await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.rejectedWith(ERROR_MSG); @@ -757,22 +742,22 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesThreeAccs[1]) await validatorContractWith2Signatures.setRequiredSignatures(3).should.be.fulfilled; - '3'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); + expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('3'); await homeBridgeWithTwoSigs.submitSignature(signature3, message, {from: authoritiesThreeAccs[2]}).should.be.rejectedWith(ERROR_MSG); }) it('attack when decreasing requiredSignatures', async () => { const recipientAccount = accounts[8] - const value = web3.toBigNumber(web3.toWei(0.5, "ether")); + const value = halfEther const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); const signature = await sign(authoritiesThreeAccs[0], message) const signature2 = await sign(authoritiesThreeAccs[1], message) - '2'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); + expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('2'); await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; await validatorContractWith2Signatures.setRequiredSignatures(1).should.be.fulfilled; - '1'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); + expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('1'); const { logs } = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; logs.length.should.be.equal(2) @@ -787,13 +772,11 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { }) it('should return the required message length', async () => { - const requiredMessageLength = await homeContract.requiredMessageLength() - '104'.should.be.bignumber.equal(requiredMessageLength) + expect(await homeContract.requiredMessageLength()).to.be.bignumber.equal('104') }) }) describe('#fixAssetsAboveLimits', async () => { let homeBridge; - const zeroValue = web3.toBigNumber(web3.toWei(0, "ether")) beforeEach(async () => { const homeBridgeImpl = await HomeBridge.new(); const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; @@ -817,7 +800,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { logs.length.should.be.equal(0) const newOutOfLimitAmount = await homeBridge.outOfLimitAmount() - newOutOfLimitAmount.should.be.bignumber.equal(zeroValue) + newOutOfLimitAmount.should.be.bignumber.equal(ZERO) }) it('Should reduce outOfLimitAmount and emit UserRequestForSignature', async () => { const recipient = accounts[5]; @@ -833,14 +816,13 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const { logs } = await homeBridge.fixAssetsAboveLimits(transactionHash, true).should.be.fulfilled logs.length.should.be.equal(1) - logs[0].event.should.be.equal('UserRequestForSignature') - logs[0].args.should.be.deep.equal({ + expectEventInLogs(logs, 'UserRequestForSignature', { recipient, value }) const newOutOfLimitAmount = await homeBridge.outOfLimitAmount() - newOutOfLimitAmount.should.be.bignumber.equal(zeroValue) + newOutOfLimitAmount.should.be.bignumber.equal(ZERO) }) it('Should not be allow to be called by an already fixed txHash', async () => { const recipient = accounts[5]; @@ -863,7 +845,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { await homeBridge.fixAssetsAboveLimits(transactionHash2, false).should.be.fulfilled const updatedOutOfLimitAmount = await homeBridge.outOfLimitAmount() - updatedOutOfLimitAmount.should.be.bignumber.equal(zeroValue) + updatedOutOfLimitAmount.should.be.bignumber.equal(ZERO) await homeBridge.fixAssetsAboveLimits(transactionHash2, false).should.be.rejectedWith(ERROR_MSG) }) @@ -940,8 +922,8 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { it('should be able to set and get fees', async () => { // Given // 10% fee - const homeFee = web3.toBigNumber(web3.toWei(0.1, "ether")) - const foreignFee = web3.toBigNumber(web3.toWei(0.2, "ether")) + const homeFee = ether('0.1') + const foreignFee = ether('0.2') const feeManager = await FeeManagerErcToNative.new() await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled @@ -990,42 +972,44 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { // Given // 0.1% fee const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeInWei = ether(fee.toString()) const feeManager = await FeeManagerErcToNative.new() await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setForeignFee(feeInWei, { from: owner }).should.be.fulfilled const recipient = accounts[5]; const value = halfEther; - const balanceBefore = await web3.eth.getBalance(recipient) - const rewardAddressBalanceBefore = await web3.eth.getBalance(rewards[0]) + const valueCalc = 0.5 * (1 - fee) + const finalValue = ether(valueCalc.toString()) + const feeAmountCalc = 0.5 * fee + const feeAmount = ether(feeAmountCalc.toString()) + const balanceBefore = toBN(await web3.eth.getBalance(recipient)) + const rewardAddressBalanceBefore = toBN(await web3.eth.getBalance(rewards[0])) const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; // When const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled // Then - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ + expectEventInLogs(logs, 'SignedForAffirmation', { signer: validators[0], transactionHash - }); - logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); - logs[1].args.should.be.deep.equal({ - feeAmount: value.mul(web3.toBigNumber(fee)), + }) + expectEventInLogs(logs, 'FeeDistributedFromAffirmation', { + feeAmount, transactionHash }) - logs[2].event.should.be.equal("AffirmationCompleted"); - logs[2].args.should.be.deep.equal({ + expectEventInLogs(logs, 'AffirmationCompleted', { recipient, value, transactionHash }) - const balanceAfter = await web3.eth.getBalance(recipient) - const rewardAddressBalanceAfter = await web3.eth.getBalance(rewards[0]) - rewardAddressBalanceAfter.should.be.bignumber.equal(rewardAddressBalanceBefore.add(value.mul(web3.toBigNumber(fee)))) - balanceAfter.should.be.bignumber.equal(balanceBefore.add(value.mul(web3.toBigNumber(1 - fee)))) + const balanceAfter = toBN(await web3.eth.getBalance(recipient)) + const rewardAddressBalanceAfter = toBN(await web3.eth.getBalance(rewards[0])) + + rewardAddressBalanceAfter.should.be.bignumber.equal(rewardAddressBalanceBefore.add(feeAmount)) + balanceAfter.should.be.bignumber.equal(balanceBefore.add(finalValue)) }) it('should distribute fee to 3 validators', async () => { // Initialize @@ -1047,26 +1031,30 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { }).should.be.fulfilled // Given - const initialBlockRewardBalance = await web3.eth.getBalance(blockRewardContract.address) + const initialBlockRewardBalance = toBN(await web3.eth.getBalance(blockRewardContract.address)) initialBlockRewardBalance.should.be.bignumber.equal(halfEther) const value = halfEther; // 0.1% fee const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeInWei = ether(fee.toString()) + const valueCalc = 0.5 * (1 - fee) + const finalValue = ether(valueCalc.toString()) + const feeAmountCalc = 0.5 * fee + const feeAmount = ether(feeAmountCalc.toString()) // totalFee / 3 - const feePerValidator = web3.toBigNumber(166666666666666) - const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) + const feePerValidator = toBN(166666666666666) + const feePerValidatorPlusDiff = toBN(166666666666668) const feeManager = await FeeManagerErcToNative.new() await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setForeignFee(feeInWei, { from: owner }).should.be.fulfilled const recipient = accounts[8]; - const balanceBefore = await web3.eth.getBalance(recipient) + const balanceBefore = toBN(await web3.eth.getBalance(recipient)) - const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) - const initialBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) - const initialBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + const initialBalanceRewardAddress1 = toBN(await web3.eth.getBalance(rewards[0])) + const initialBalanceRewardAddress2 = toBN(await web3.eth.getBalance(rewards[1])) + const initialBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; @@ -1078,28 +1066,26 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { // Then logsValidator1.length.should.be.equals(1) - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ + expectEventInLogs(logs, 'SignedForAffirmation', { signer: validators[1], transactionHash - }); - logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); - logs[1].args.should.be.deep.equal({ - feeAmount: value.mul(web3.toBigNumber(fee)), + }) + expectEventInLogs(logs, 'FeeDistributedFromAffirmation', { + feeAmount, transactionHash }) - logs[2].event.should.be.equal("AffirmationCompleted"); - logs[2].args.should.be.deep.equal({ + expectEventInLogs(logs, 'AffirmationCompleted', { recipient, value, transactionHash }) - const balanceAfter = await web3.eth.getBalance(recipient) - balanceAfter.should.be.bignumber.equal(balanceBefore.add(value.mul(web3.toBigNumber(1 - fee)))) - const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) - const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) - const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + const balanceAfter = toBN(await web3.eth.getBalance(recipient)) + balanceAfter.should.be.bignumber.equal(balanceBefore.add(finalValue)) + + const updatedBalanceRewardAddress1 = toBN(await web3.eth.getBalance(rewards[0])) + const updatedBalanceRewardAddress2 = toBN(await web3.eth.getBalance(rewards[1])) + const updatedBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) expect( updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidator)) @@ -1111,8 +1097,8 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidator)) || updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidatorPlusDiff))).to.equal(true) - const blockRewardBalance = await web3.eth.getBalance(blockRewardContract.address) - blockRewardBalance.should.be.bignumber.equal('0') + const blockRewardBalance = toBN(await web3.eth.getBalance(blockRewardContract.address)) + blockRewardBalance.should.be.bignumber.equal(ZERO) }) it('should distribute fee to 5 validators', async () => { // Initialize @@ -1136,21 +1122,22 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const value = halfEther; // 0.1% fee const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) - const feeAmount = value.mul(web3.toBigNumber(fee)) - const feePerValidator = feeAmount.div(web3.toBigNumber(5)) + const feeInWei = ether(fee.toString()) + const feeAmountCalc = 0.5 * fee + const feeAmount = ether(feeAmountCalc.toString()) + const feePerValidator = feeAmount.div(toBN(5)) const feeManager = await FeeManagerErcToNative.new() await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setForeignFee(feeInWei, { from: owner }).should.be.fulfilled - const recipient = "0xf4bef13f9f4f2b203faf0c3cbbaabe1afe056955"; - const balanceBefore = await web3.eth.getBalance(recipient) + const recipient = "0xf4BEF13F9f4f2B203FAF0C3cBbaAbe1afE056955"; + const balanceBefore = toBN(await web3.eth.getBalance(recipient)) - const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) - const initialBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) - const initialBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) - const initialBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) - const initialBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) + const initialBalanceRewardAddress1 = toBN(await web3.eth.getBalance(rewards[0])) + const initialBalanceRewardAddress2 = toBN(await web3.eth.getBalance(rewards[1])) + const initialBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) + const initialBalanceRewardAddress4 = toBN(await web3.eth.getBalance(rewards[3])) + const initialBalanceRewardAddress5 = toBN(await web3.eth.getBalance(rewards[4])) const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; @@ -1165,30 +1152,28 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { // Then logsValidator1.length.should.be.equals(1) - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ + expectEventInLogs(logs, 'SignedForAffirmation', { signer: validators[4], transactionHash - }); - logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); - logs[1].args.should.be.deep.equal({ - feeAmount: value.mul(web3.toBigNumber(fee)), + }) + expectEventInLogs(logs, 'FeeDistributedFromAffirmation', { + feeAmount, transactionHash }) - logs[2].event.should.be.equal("AffirmationCompleted"); - logs[2].args.should.be.deep.equal({ + expectEventInLogs(logs, 'AffirmationCompleted', { recipient, value, transactionHash }) - const balanceAfter = await web3.eth.getBalance(recipient) + + const balanceAfter = toBN(await web3.eth.getBalance(recipient)) balanceAfter.should.be.bignumber.equal(balanceBefore.add(value.sub(feeAmount))) - const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) - const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) - const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) - const updatedBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) - const updatedBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) + const updatedBalanceRewardAddress1 = toBN(await web3.eth.getBalance(rewards[0])) + const updatedBalanceRewardAddress2 = toBN(await web3.eth.getBalance(rewards[1])) + const updatedBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) + const updatedBalanceRewardAddress4 = toBN(await web3.eth.getBalance(rewards[3])) + const updatedBalanceRewardAddress5 = toBN(await web3.eth.getBalance(rewards[4])) updatedBalanceRewardAddress1.should.be.bignumber.equal(initialBalanceRewardAddress1.add(feePerValidator)) updatedBalanceRewardAddress2.should.be.bignumber.equal(initialBalanceRewardAddress2.add(feePerValidator)) @@ -1220,7 +1205,9 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const value = halfEther const recipient = accounts[8]; const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeInWei = ether(fee.toString()) + const valueCalc = 0.5 * (1 - fee) + const finalValue = ether(valueCalc.toString()) const feeManager = await FeeManagerErcToNative.new() await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setHomeFee(feeInWei, { from: owner }).should.be.fulfilled @@ -1229,14 +1216,12 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const { logs } = await homeBridge.sendTransaction({ from: recipient, value }).should.be.fulfilled // Then - const finalValue = value.mul(web3.toBigNumber(1 - fee)) - logs[0].event.should.be.equal('UserRequestForSignature') - logs[0].args.should.be.deep.equal({ recipient: recipient, value: finalValue }) + expectEventInLogs(logs, 'UserRequestForSignature', { recipient: recipient, value: finalValue }) const currentDay = await homeBridge.getCurrentDay() value.should.be.bignumber.equal(await homeBridge.totalSpentPerDay(currentDay)) finalValue.should.be.bignumber.equal(await homeBridge.totalBurntCoins()) const homeBridgeBalance = await web3.eth.getBalance(homeBridge.address) - homeBridgeBalance.should.be.bignumber.equal(value.sub(finalValue)) + expect(toBN(homeBridgeBalance)).to.be.bignumber.equal(value.sub(finalValue)) }) }) describe('#feeManager_submitSignature', async () => { @@ -1258,25 +1243,27 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { // Given // 0.1% fee const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeInWei = ether(fee.toString()) const feeManager = await FeeManagerErcToNative.new() await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setHomeFee(feeInWei, { from: owner }).should.be.fulfilled const recipient = accounts[5]; const initialValue = halfEther - const value = halfEther.mul(web3.toBigNumber(1-fee)); - const feeAmount = initialValue.mul(web3.toBigNumber(fee)) - const rewardAddressBalanceBefore = await web3.eth.getBalance(rewards[0]) + const valueCalc = 0.5 * (1 - fee) + const value = ether(valueCalc.toString()) + const feeAmountCalc = 0.5 * fee + const feeAmount = ether(feeAmountCalc.toString()) + const rewardAddressBalanceBefore = toBN(await web3.eth.getBalance(rewards[0])) const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; const initialBridgeBalance = await web3.eth.getBalance(homeBridge.address) - initialBridgeBalance.should.be.bignumber.equal('0') + expect(toBN(initialBridgeBalance)).to.be.bignumber.equal(ZERO) // When await homeBridge.sendTransaction({ from: recipient, value: initialValue }).should.be.fulfilled - const afterTransferBridgeBalance = await web3.eth.getBalance(homeBridge.address) + const afterTransferBridgeBalance = toBN(await web3.eth.getBalance(homeBridge.address)) afterTransferBridgeBalance.should.be.bignumber.equal(feeAmount) const message = createMessage(recipient, value, transactionHash, homeBridge.address); @@ -1291,10 +1278,10 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { logs[2].event.should.be.equal('FeeDistributedFromSignatures') const finalBridgeBalance = await web3.eth.getBalance(homeBridge.address) - finalBridgeBalance.should.be.bignumber.equal('0') + expect(toBN(finalBridgeBalance)).to.be.bignumber.equal(ZERO) const rewardAddressBalanceAfter = await web3.eth.getBalance(rewards[0]) - rewardAddressBalanceAfter.should.be.bignumber.equal(rewardAddressBalanceBefore.add(feeAmount)) + expect(toBN(rewardAddressBalanceAfter)).to.be.bignumber.equal(toBN(rewardAddressBalanceBefore).add(feeAmount)) }) it('should distribute fee to 3 validators', async () => { // Initialize @@ -1314,30 +1301,32 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { // Given // 0.1% fee const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeInWei = ether(fee.toString()) const feeManager = await FeeManagerErcToNative.new() - const feePerValidator = web3.toBigNumber(166666666666666) - const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) + const feePerValidator = toBN(166666666666666) + const feePerValidatorPlusDiff = toBN(166666666666668) await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setHomeFee(feeInWei, { from: owner }).should.be.fulfilled const recipient = accounts[7]; const initialValue = halfEther - const value = halfEther.mul(web3.toBigNumber(1-fee)); - const feeAmount = initialValue.mul(web3.toBigNumber(fee)) + const valueCalc = 0.5 * (1 - fee) + const value = ether(valueCalc.toString()) + const feeAmountCalc = 0.5 * fee + const feeAmount = ether(feeAmountCalc.toString()) const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - const initialBridgeBalance = await web3.eth.getBalance(homeBridge.address) - initialBridgeBalance.should.be.bignumber.equal('0') + const initialBridgeBalance = toBN(await web3.eth.getBalance(homeBridge.address)) + initialBridgeBalance.should.be.bignumber.equal(ZERO) - const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) - const initialBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) - const initialBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + const initialBalanceRewardAddress1 = toBN(await web3.eth.getBalance(rewards[0])) + const initialBalanceRewardAddress2 = toBN(await web3.eth.getBalance(rewards[1])) + const initialBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) // When await homeBridge.sendTransaction({ from: recipient, value: initialValue }).should.be.fulfilled - const afterTransferBridgeBalance = await web3.eth.getBalance(homeBridge.address) + const afterTransferBridgeBalance = toBN(await web3.eth.getBalance(homeBridge.address)) afterTransferBridgeBalance.should.be.bignumber.equal(feeAmount) const message = createMessage(recipient, value, transactionHash, homeBridge.address); @@ -1355,12 +1344,12 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { logs[1].event.should.be.equal('CollectedSignatures') logs[2].event.should.be.equal('FeeDistributedFromSignatures') - const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) - const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) - const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + const updatedBalanceRewardAddress1 = toBN(await web3.eth.getBalance(rewards[0])) + const updatedBalanceRewardAddress2 = toBN(await web3.eth.getBalance(rewards[1])) + const updatedBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) - const bridgeBalance = await web3.eth.getBalance(homeBridge.address) - bridgeBalance.should.be.bignumber.equal('0') + const bridgeBalance = toBN(await web3.eth.getBalance(homeBridge.address)) + bridgeBalance.should.be.bignumber.equal(ZERO) expect( updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidator)) @@ -1390,31 +1379,33 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { // Given // 0.1% fee const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeInWei = ether(fee.toString()) const feeManager = await FeeManagerErcToNative.new() await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setHomeFee(feeInWei, { from: owner }).should.be.fulfilled const recipient = accounts[0]; const initialValue = halfEther - const value = halfEther.mul(web3.toBigNumber(1-fee)); - const feeAmount = initialValue.mul(web3.toBigNumber(fee)) - const feePerValidator = feeAmount.div(web3.toBigNumber(5)) + const valueCalc = 0.5 * (1 - fee) + const value = ether(valueCalc.toString()) + const feeAmountCalc = 0.5 * fee + const feeAmount = ether(feeAmountCalc.toString()) + const feePerValidator = feeAmount.div(toBN(5)) const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - const initialBridgeBalance = await web3.eth.getBalance(homeBridge.address) - initialBridgeBalance.should.be.bignumber.equal('0') + const initialBridgeBalance = toBN(await web3.eth.getBalance(homeBridge.address)) + initialBridgeBalance.should.be.bignumber.equal(ZERO) - const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) - const initialBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) - const initialBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) - const initialBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) - const initialBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) + const initialBalanceRewardAddress1 = toBN(await web3.eth.getBalance(rewards[0])) + const initialBalanceRewardAddress2 = toBN(await web3.eth.getBalance(rewards[1])) + const initialBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) + const initialBalanceRewardAddress4 = toBN(await web3.eth.getBalance(rewards[3])) + const initialBalanceRewardAddress5 = toBN(await web3.eth.getBalance(rewards[4])) // When await homeBridge.sendTransaction({ from: recipient, value: initialValue }).should.be.fulfilled - const afterTransferBridgeBalance = await web3.eth.getBalance(homeBridge.address) + const afterTransferBridgeBalance = toBN(await web3.eth.getBalance(homeBridge.address)) afterTransferBridgeBalance.should.be.bignumber.equal(feeAmount) const message = createMessage(recipient, value, transactionHash, homeBridge.address); @@ -1436,11 +1427,11 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { logs[1].event.should.be.equal('CollectedSignatures') logs[2].event.should.be.equal('FeeDistributedFromSignatures') - const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) - const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) - const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) - const updatedBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) - const updatedBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) + const updatedBalanceRewardAddress1 = toBN(await web3.eth.getBalance(rewards[0])) + const updatedBalanceRewardAddress2 = toBN(await web3.eth.getBalance(rewards[1])) + const updatedBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) + const updatedBalanceRewardAddress4 = toBN(await web3.eth.getBalance(rewards[3])) + const updatedBalanceRewardAddress5 = toBN(await web3.eth.getBalance(rewards[4])) updatedBalanceRewardAddress1.should.be.bignumber.equal(initialBalanceRewardAddress1.add(feePerValidator)) updatedBalanceRewardAddress2.should.be.bignumber.equal(initialBalanceRewardAddress2.add(feePerValidator)) @@ -1462,8 +1453,8 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const result = await feeManager.random(3); // Then - result.should.be.bignumber.gte(0); - result.should.be.bignumber.lt(3); + expect(result).to.be.bignumber.gte(ZERO); + expect(result).to.be.bignumber.lt('3'); } }) }) @@ -1491,13 +1482,17 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { // Given // 0.1% fee const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeInWei = ether(fee.toString()) const feeManager = await FeeManagerErcToNativePOSDAO.new() await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setForeignFee(feeInWei, { from: owner }).should.be.fulfilled const recipient = accounts[5]; const value = halfEther; + const feeAmountCalc = 0.5 * fee + const feeAmount = ether(feeAmountCalc.toString()) + const valueCalc = 0.5 * (1 - fee) + const finalValue = ether(valueCalc.toString()) const balanceBefore = await web3.eth.getBalance(recipient) const rewardAddressBalanceBefore = await web3.eth.getBalance(rewards[0]) const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; @@ -1506,18 +1501,15 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled // Then - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ + expectEventInLogs(logs, 'SignedForAffirmation', { signer: validators[0], transactionHash - }); - logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); - logs[1].args.should.be.deep.equal({ - feeAmount: value.mul(web3.toBigNumber(fee)), + }) + expectEventInLogs(logs, 'FeeDistributedFromAffirmation', { + feeAmount, transactionHash }) - logs[2].event.should.be.equal("AffirmationCompleted"); - logs[2].args.should.be.deep.equal({ + expectEventInLogs(logs, 'AffirmationCompleted', { recipient, value, transactionHash @@ -1525,11 +1517,11 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const balanceAfter = await web3.eth.getBalance(recipient) const rewardAddressBalanceAfter = await web3.eth.getBalance(rewards[0]) - rewardAddressBalanceAfter.should.be.bignumber.equal(rewardAddressBalanceBefore.add(value.mul(web3.toBigNumber(fee)))) - balanceAfter.should.be.bignumber.equal(balanceBefore.add(value.mul(web3.toBigNumber(1 - fee)))) + expect(toBN(rewardAddressBalanceAfter)).to.be.bignumber.equal(toBN(rewardAddressBalanceBefore).add(feeAmount)) + expect(toBN(balanceAfter)).to.be.bignumber.equal(toBN(balanceBefore).add(finalValue)) const feeAmountBlockReward = await blockRewardContract.feeAmount() - feeAmountBlockReward.should.be.bignumber.equal(value.mul(web3.toBigNumber(fee))) + feeAmountBlockReward.should.be.bignumber.equal(feeAmount) }) it('should distribute fee to 3 validators', async () => { // Initialize @@ -1553,15 +1545,19 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { // Given const initialBlockRewardBalance = await web3.eth.getBalance(blockRewardContract.address) - initialBlockRewardBalance.should.be.bignumber.equal(halfEther) + expect(toBN(initialBlockRewardBalance)).to.be.bignumber.equal(halfEther) const value = halfEther; // 0.1% fee const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeInWei = ether(fee.toString()) + const valueCalc = 0.5 * (1 - fee) + const finalValue = ether(valueCalc.toString()) + const feeAmountCalc = 0.5 * fee + const feeAmount = ether(feeAmountCalc.toString()) // totalFee / 3 - const feePerValidator = web3.toBigNumber(166666666666666) - const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) + const feePerValidator = toBN(166666666666666) + const feePerValidatorPlusDiff = toBN(166666666666668) const feeManager = await FeeManagerErcToNativePOSDAO.new() await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setForeignFee(feeInWei, { from: owner }).should.be.fulfilled @@ -1583,44 +1579,42 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { // Then logsValidator1.length.should.be.equals(1) - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ + expectEventInLogs(logs, 'SignedForAffirmation', { signer: validators[1], transactionHash - }); - logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); - logs[1].args.should.be.deep.equal({ - feeAmount: value.mul(web3.toBigNumber(fee)), + }) + expectEventInLogs(logs, 'FeeDistributedFromAffirmation', { + feeAmount, transactionHash }) - logs[2].event.should.be.equal("AffirmationCompleted"); - logs[2].args.should.be.deep.equal({ + expectEventInLogs(logs, 'AffirmationCompleted', { recipient, value, transactionHash }) + const balanceAfter = await web3.eth.getBalance(recipient) - balanceAfter.should.be.bignumber.equal(balanceBefore.add(value.mul(web3.toBigNumber(1 - fee)))) + expect(toBN(balanceAfter)).to.be.bignumber.equal(toBN(balanceBefore).add(finalValue)) const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) expect( - updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidator)) - || updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidatorPlusDiff))).to.equal(true) + toBN(updatedBalanceRewardAddress1).eq(toBN(initialBalanceRewardAddress1).add(feePerValidator)) + || toBN(updatedBalanceRewardAddress1).eq(toBN(initialBalanceRewardAddress1).add(feePerValidatorPlusDiff))).to.equal(true) expect( - updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidator)) - || updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidatorPlusDiff))).to.equal(true) + toBN(updatedBalanceRewardAddress2).eq(toBN(initialBalanceRewardAddress2).add(feePerValidator)) + || toBN(updatedBalanceRewardAddress2).eq(toBN(initialBalanceRewardAddress2).add(feePerValidatorPlusDiff))).to.equal(true) expect( - updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidator)) - || updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidatorPlusDiff))).to.equal(true) + toBN(updatedBalanceRewardAddress3).eq(toBN(initialBalanceRewardAddress3).add(feePerValidator)) + || toBN(updatedBalanceRewardAddress3).eq(toBN(initialBalanceRewardAddress3).add(feePerValidatorPlusDiff))).to.equal(true) const feeAmountBlockReward = await blockRewardContract.feeAmount() - feeAmountBlockReward.should.be.bignumber.equal(value.mul(web3.toBigNumber(fee))) + expect(toBN(feeAmountBlockReward)).to.be.bignumber.equal(feeAmount) const blockRewardBalance = await web3.eth.getBalance(blockRewardContract.address) - blockRewardBalance.should.be.bignumber.equal('0') + expect(toBN(blockRewardBalance)).to.be.bignumber.equal(ZERO) }) it('should distribute fee to 5 validators', async () => { // Initialize @@ -1645,14 +1639,15 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const value = halfEther; // 0.1% fee const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) - const feeAmount = value.mul(web3.toBigNumber(fee)) - const feePerValidator = feeAmount.div(web3.toBigNumber(5)) + const feeInWei = ether(fee.toString()) + const feeAmountCalc = 0.5 * fee + const feeAmount = ether(feeAmountCalc.toString()) + const feePerValidator = feeAmount.div(toBN(5)) const feeManager = await FeeManagerErcToNativePOSDAO.new() await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setForeignFee(feeInWei, { from: owner }).should.be.fulfilled - const recipient = "0xf4bef13f9f4f2b203faf0c3cbbaabe1afe056955"; + const recipient = "0xf4BEF13F9f4f2B203FAF0C3cBbaAbe1afE056955"; const balanceBefore = await web3.eth.getBalance(recipient) const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) @@ -1674,24 +1669,22 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { // Then logsValidator1.length.should.be.equals(1) - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ + expectEventInLogs(logs, 'SignedForAffirmation', { signer: validators[4], transactionHash - }); - logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); - logs[1].args.should.be.deep.equal({ - feeAmount: value.mul(web3.toBigNumber(fee)), + }) + expectEventInLogs(logs, 'FeeDistributedFromAffirmation', { + feeAmount, transactionHash }) - logs[2].event.should.be.equal("AffirmationCompleted"); - logs[2].args.should.be.deep.equal({ + expectEventInLogs(logs, 'AffirmationCompleted', { recipient, value, transactionHash }) + const balanceAfter = await web3.eth.getBalance(recipient) - balanceAfter.should.be.bignumber.equal(balanceBefore.add(value.sub(feeAmount))) + expect(toBN(balanceAfter)).to.be.bignumber.equal(toBN(balanceBefore).add(value.sub(feeAmount))) const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) @@ -1699,14 +1692,14 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const updatedBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) const updatedBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) - updatedBalanceRewardAddress1.should.be.bignumber.equal(initialBalanceRewardAddress1.add(feePerValidator)) - updatedBalanceRewardAddress2.should.be.bignumber.equal(initialBalanceRewardAddress2.add(feePerValidator)) - updatedBalanceRewardAddress3.should.be.bignumber.equal(initialBalanceRewardAddress3.add(feePerValidator)) - updatedBalanceRewardAddress4.should.be.bignumber.equal(initialBalanceRewardAddress4.add(feePerValidator)) - updatedBalanceRewardAddress5.should.be.bignumber.equal(initialBalanceRewardAddress5.add(feePerValidator)) + expect(toBN(updatedBalanceRewardAddress1)).to.be.bignumber.equal(toBN(initialBalanceRewardAddress1).add(feePerValidator)) + expect(toBN(updatedBalanceRewardAddress2)).to.be.bignumber.equal(toBN(initialBalanceRewardAddress2).add(feePerValidator)) + expect(toBN(updatedBalanceRewardAddress3)).to.be.bignumber.equal(toBN(initialBalanceRewardAddress3).add(feePerValidator)) + expect(toBN(updatedBalanceRewardAddress4)).to.be.bignumber.equal(toBN(initialBalanceRewardAddress4).add(feePerValidator)) + expect(toBN(updatedBalanceRewardAddress5)).to.be.bignumber.equal(toBN(initialBalanceRewardAddress5).add(feePerValidator)) const feeAmountBlockReward = await blockRewardContract.feeAmount() - feeAmountBlockReward.should.be.bignumber.equal(value.mul(web3.toBigNumber(fee))) + expect(toBN(feeAmountBlockReward)).to.be.bignumber.equal(feeAmount) }) }) describe('#feeManager_fallback_POSDAO', function () { @@ -1732,7 +1725,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const value = halfEther const recipient = accounts[8]; const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeInWei = ether(fee.toString()) const feeManager = await FeeManagerErcToNativePOSDAO.new() await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setHomeFee(feeInWei, { from: owner }).should.be.fulfilled @@ -1741,14 +1734,14 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const { logs } = await homeBridge.sendTransaction({ from: recipient, value }).should.be.fulfilled // Then - const finalValue = value.mul(web3.toBigNumber(1 - fee)) - logs[0].event.should.be.equal('UserRequestForSignature') - logs[0].args.should.be.deep.equal({ recipient: recipient, value: finalValue }) + const valueCalc = 0.5 * (1 - fee) + const finalValue = ether(valueCalc.toString()) + expectEventInLogs(logs, 'UserRequestForSignature', { recipient: recipient, value: finalValue }) const currentDay = await homeBridge.getCurrentDay() value.should.be.bignumber.equal(await homeBridge.totalSpentPerDay(currentDay)) value.should.be.bignumber.equal(await homeBridge.totalBurntCoins()) const homeBridgeBalance = await web3.eth.getBalance(homeBridge.address) - homeBridgeBalance.should.be.bignumber.equal(0) + expect(toBN(homeBridgeBalance)).to.be.bignumber.equal(ZERO) }) }) describe('#feeManager_submitSignature_POSDAO', async () => { @@ -1771,26 +1764,28 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { // Given // 0.1% fee const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeInWei = ether(fee.toString()) const feeManager = await FeeManagerErcToNativePOSDAO.new() await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setHomeFee(feeInWei, { from: owner }).should.be.fulfilled const recipient = accounts[5]; const initialValue = halfEther - const value = halfEther.mul(web3.toBigNumber(1-fee)); - const feeAmount = initialValue.mul(web3.toBigNumber(fee)) + const valueCalc = 0.5 * (1 - fee) + const value = ether(valueCalc.toString()) + const feeAmountCalc = 0.5 * fee + const feeAmount = ether(feeAmountCalc.toString()) const rewardAddressBalanceBefore = await web3.eth.getBalance(rewards[0]) const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; const initialBridgeBalance = await web3.eth.getBalance(homeBridge.address) - initialBridgeBalance.should.be.bignumber.equal('0') + expect(toBN(initialBridgeBalance)).to.be.bignumber.equal(ZERO) // When await homeBridge.sendTransaction({ from: recipient, value: initialValue }).should.be.fulfilled const afterTransferBridgeBalance = await web3.eth.getBalance(homeBridge.address) - afterTransferBridgeBalance.should.be.bignumber.equal(0) + expect(toBN(afterTransferBridgeBalance)).to.be.bignumber.equal(ZERO) const message = createMessage(recipient, value, transactionHash, homeBridge.address); @@ -1801,20 +1796,19 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { // Then logs.length.should.be.equal(3) logs[1].event.should.be.equal('CollectedSignatures') - logs[2].event.should.be.equal("FeeDistributedFromSignatures"); - logs[2].args.should.be.deep.equal({ + expectEventInLogs(logs, 'FeeDistributedFromSignatures', { feeAmount, transactionHash }) const finalBridgeBalance = await web3.eth.getBalance(homeBridge.address) - finalBridgeBalance.should.be.bignumber.equal('0') + expect(toBN(finalBridgeBalance)).to.be.bignumber.equal(ZERO) const rewardAddressBalanceAfter = await web3.eth.getBalance(rewards[0]) - rewardAddressBalanceAfter.should.be.bignumber.equal(rewardAddressBalanceBefore.add(feeAmount)) + expect(toBN(rewardAddressBalanceAfter)).to.be.bignumber.equal(toBN(rewardAddressBalanceBefore).add(feeAmount)) const feeAmountBlockReward = await blockRewardContract.feeAmount() - feeAmountBlockReward.should.be.bignumber.equal(initialValue.mul(web3.toBigNumber(fee))) + expect(toBN(feeAmountBlockReward)).to.be.bignumber.equal(feeAmount) }) it('should distribute fee to 3 validators', async () => { // Initialize @@ -1835,21 +1829,23 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { // Given // 0.1% fee const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeInWei = ether(fee.toString()) const feeManager = await FeeManagerErcToNativePOSDAO.new() - const feePerValidator = web3.toBigNumber(166666666666666) - const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) + const feePerValidator = toBN(166666666666666) + const feePerValidatorPlusDiff = toBN(166666666666668) await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setHomeFee(feeInWei, { from: owner }).should.be.fulfilled const recipient = accounts[7]; const initialValue = halfEther - const value = halfEther.mul(web3.toBigNumber(1-fee)); - const feeAmount = initialValue.mul(web3.toBigNumber(fee)) + const valueCalc = 0.5 * (1 - fee) + const value = ether(valueCalc.toString()) + const feeAmountCalc = 0.5 * fee + const feeAmount = ether(feeAmountCalc.toString()) const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; const initialBridgeBalance = await web3.eth.getBalance(homeBridge.address) - initialBridgeBalance.should.be.bignumber.equal('0') + expect(toBN(initialBridgeBalance)).to.be.bignumber.equal(ZERO) const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) const initialBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) @@ -1859,7 +1855,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { await homeBridge.sendTransaction({ from: recipient, value: initialValue }).should.be.fulfilled const afterTransferBridgeBalance = await web3.eth.getBalance(homeBridge.address) - afterTransferBridgeBalance.should.be.bignumber.equal(0) + expect(toBN(afterTransferBridgeBalance)).to.be.bignumber.equal(ZERO) const message = createMessage(recipient, value, transactionHash, homeBridge.address); @@ -1874,32 +1870,30 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { // Then logs.length.should.be.equal(3) logs[1].event.should.be.equal('CollectedSignatures') - logs[2].event.should.be.equal("FeeDistributedFromSignatures"); - logs[2].args.should.be.deep.equal({ + expectEventInLogs(logs, 'FeeDistributedFromSignatures', { feeAmount, transactionHash }) - const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) const bridgeBalance = await web3.eth.getBalance(homeBridge.address) - bridgeBalance.should.be.bignumber.equal('0') + expect(toBN(bridgeBalance)).to.be.bignumber.equal(ZERO) expect( - updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidator)) - || updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidatorPlusDiff))).to.equal(true) + toBN(updatedBalanceRewardAddress1).eq(toBN(initialBalanceRewardAddress1).add(feePerValidator)) + || toBN(updatedBalanceRewardAddress1).eq(toBN(initialBalanceRewardAddress1).add(feePerValidatorPlusDiff))).to.equal(true) expect( - updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidator)) - || updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidatorPlusDiff))).to.equal(true) + toBN(updatedBalanceRewardAddress2).eq(toBN(initialBalanceRewardAddress2).add(feePerValidator)) + || toBN(updatedBalanceRewardAddress2).eq(toBN(initialBalanceRewardAddress2).add(feePerValidatorPlusDiff))).to.equal(true) expect( - updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidator)) - || updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidatorPlusDiff))).to.equal(true) + toBN(updatedBalanceRewardAddress3).eq(toBN(initialBalanceRewardAddress3).add(feePerValidator)) + || toBN(updatedBalanceRewardAddress3).eq(toBN(initialBalanceRewardAddress3).add(feePerValidatorPlusDiff))).to.equal(true) const feeAmountBlockReward = await blockRewardContract.feeAmount() - feeAmountBlockReward.should.be.bignumber.equal(feeAmount) + expect(toBN(feeAmountBlockReward)).to.be.bignumber.equal(feeAmount) }) it('should distribute fee to 5 validators', async () => { // Initialize @@ -1920,20 +1914,22 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { // Given // 0.1% fee const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeInWei = ether(fee.toString()) const feeManager = await FeeManagerErcToNativePOSDAO.new() await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setHomeFee(feeInWei, { from: owner }).should.be.fulfilled const recipient = accounts[0]; const initialValue = halfEther - const value = halfEther.mul(web3.toBigNumber(1-fee)); - const feeAmount = initialValue.mul(web3.toBigNumber(fee)) - const feePerValidator = feeAmount.div(web3.toBigNumber(5)) + const valueCalc = 0.5 * (1 - fee) + const value = ether(valueCalc.toString()) + const feeAmountCalc = 0.5 * fee + const feeAmount = ether(feeAmountCalc.toString()) + const feePerValidator = feeAmount.div(toBN(5)) const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; const initialBridgeBalance = await web3.eth.getBalance(homeBridge.address) - initialBridgeBalance.should.be.bignumber.equal('0') + expect(toBN(initialBridgeBalance)).to.be.bignumber.equal(ZERO) const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) const initialBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) @@ -1945,7 +1941,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { await homeBridge.sendTransaction({ from: recipient, value: initialValue }).should.be.fulfilled const afterTransferBridgeBalance = await web3.eth.getBalance(homeBridge.address) - afterTransferBridgeBalance.should.be.bignumber.equal(0) + expect(toBN(afterTransferBridgeBalance)).to.be.bignumber.equal(ZERO) const message = createMessage(recipient, value, transactionHash, homeBridge.address); @@ -1964,8 +1960,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { // Then logs.length.should.be.equal(3) logs[1].event.should.be.equal('CollectedSignatures') - logs[2].event.should.be.equal("FeeDistributedFromSignatures"); - logs[2].args.should.be.deep.equal({ + expectEventInLogs(logs, 'FeeDistributedFromSignatures', { feeAmount, transactionHash }) @@ -1977,11 +1972,11 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const updatedBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) const updatedBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) - updatedBalanceRewardAddress1.should.be.bignumber.equal(initialBalanceRewardAddress1.add(feePerValidator)) - updatedBalanceRewardAddress2.should.be.bignumber.equal(initialBalanceRewardAddress2.add(feePerValidator)) - updatedBalanceRewardAddress3.should.be.bignumber.equal(initialBalanceRewardAddress3.add(feePerValidator)) - updatedBalanceRewardAddress4.should.be.bignumber.equal(initialBalanceRewardAddress4.add(feePerValidator)) - updatedBalanceRewardAddress5.should.be.bignumber.equal(initialBalanceRewardAddress5.add(feePerValidator)) + expect(toBN(updatedBalanceRewardAddress1)).to.be.bignumber.equal(toBN(initialBalanceRewardAddress1).add(feePerValidator)) + expect(toBN(updatedBalanceRewardAddress2)).to.be.bignumber.equal(toBN(initialBalanceRewardAddress2).add(feePerValidator)) + expect(toBN(updatedBalanceRewardAddress3)).to.be.bignumber.equal(toBN(initialBalanceRewardAddress3).add(feePerValidator)) + expect(toBN(updatedBalanceRewardAddress4)).to.be.bignumber.equal(toBN(initialBalanceRewardAddress4).add(feePerValidator)) + expect(toBN(updatedBalanceRewardAddress5)).to.be.bignumber.equal(toBN(initialBalanceRewardAddress5).add(feePerValidator)) const feeAmountBlockReward = await blockRewardContract.feeAmount() feeAmountBlockReward.should.be.bignumber.equal(feeAmount) diff --git a/test/helpers/helpers.js b/test/helpers/helpers.js index c5012a8a3..155e2b5e2 100644 --- a/test/helpers/helpers.js +++ b/test/helpers/helpers.js @@ -1,8 +1,11 @@ +const { BN } = require('../setup'); +const { expect } = require('chai'); + // returns a Promise that resolves with a hex string that is the signature of // `data` signed with the key of `address` function sign(address, data) { return new Promise(function(resolve, reject) { - web3.eth.sign(address, data, function(err, result) { + web3.eth.sign(data, address, function(err, result) { if (err !== null) { return reject(err); } else { @@ -46,9 +49,6 @@ module.exports.signatureToVRS = signatureToVRS; // that is exactly 32 bytes long. // `num` must represent an unsigned integer function bigNumberToPaddedBytes32(num) { - assert(web3._extend.utils.isBigNumber(num)); - assert(num.isInteger()); - assert(!num.isNegative()); var result = strip0x(num.toString(16)); while (result.length < 64) { result = "0" + result; @@ -77,7 +77,6 @@ module.exports.getBalances = getBalances; // composed from `recipient`, `value` and `transactionHash` // that is relayed from `foreign` to `home` on withdraw function createMessage(recipient, value, transactionHash, contractAddress) { - web3._extend.utils.isBigNumber(value); recipient = strip0x(recipient); assert.equal(recipient.length, 20 * 2); @@ -112,19 +111,54 @@ function ignoreExpectedError() { } module.exports.ignoreExpectedError = ignoreExpectedError; -const getEvents = function(contract, filter) { - return new Promise((resolve, reject) => { - var event = contract[filter.event](); - event.watch(); - event.get((error, logs) => { - if(logs.length > 0){ - resolve(logs); - } else { - throw Error("Failed to find filtered event for " + filter.event); +const getEvents = (truffleInstance, filter, fromBlock = 0, toBlock = 'latest') => truffleInstance.contract.getPastEvents(filter.event, { fromBlock, toBlock }) + +module.exports.getEvents = getEvents; + +function ether (n) { + return new BN(web3.utils.toWei(n, 'ether')); +} + +module.exports.ether = ether; + +function expectEventInLogs (logs, eventName, eventArgs = {}) { + const events = logs.filter(e => e.event === eventName); + expect(events.length > 0).to.equal(true, `There is no '${eventName}'`); + + const exception = []; + const event = events.find(function (e) { + for (const [k, v] of Object.entries(eventArgs)) { + try { + contains(e.args, k, v); + } catch (error) { + exception.push(error); + return false; } - }); - event.stopWatching(); + } + return true; }); + + if (event === undefined) { + throw exception[0]; + } + + return event; } -module.exports.getEvents = getEvents; +function contains (args, key, value) { + expect(key in args).to.equal(true, `Unknown event argument '${key}'`); + + if (value === null) { + expect(args[key]).to.equal(null); + } else if (isBN(args[key])) { + expect(args[key]).to.be.bignumber.equal(value); + } else { + expect(args[key]).to.be.equal(value); + } +} + +function isBN (object) { + return BN.isBN(object) || object instanceof BN; +} + +module.exports.expectEventInLogs = expectEventInLogs; diff --git a/test/native_to_erc/foreign_bridge_test.js b/test/native_to_erc/foreign_bridge_test.js index 3ef289e70..29029b835 100644 --- a/test/native_to_erc/foreign_bridge_test.js +++ b/test/native_to_erc/foreign_bridge_test.js @@ -4,21 +4,23 @@ const BridgeValidators = artifacts.require("BridgeValidators.sol"); const EternalStorageProxy = artifacts.require("EternalStorageProxy.sol"); const FeeManagerNativeToErc = artifacts.require("FeeManagerNativeToErc.sol"); const RewardableValidators = artifacts.require("RewardableValidators.sol"); - const POA20 = artifacts.require("ERC677BridgeToken.sol"); -const {ERROR_MSG, ZERO_ADDRESS, ERROR_MSG_OPCODE} = require('../setup'); -const {createMessage, sign, signatureToVRS, strip0x, getEvents} = require('../helpers/helpers'); -const oneEther = web3.toBigNumber(web3.toWei(1, "ether")); -const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")); -const minPerTx = web3.toBigNumber(web3.toWei(0.01, "ether")); -const Web3Utils = require('web3-utils'); + +const { expect } = require('chai'); +const {ERROR_MSG, ZERO_ADDRESS, toBN} = require('../setup'); +const {createMessage, sign, signatureToVRS, getEvents, ether} = require('../helpers/helpers'); + +const oneEther = ether('1'); +const halfEther = ether('0.5'); +const minPerTx = ether('0.01'); const requireBlockConfirmations = 8; -const gasPrice = Web3Utils.toWei('1', 'gwei'); +const gasPrice = web3.utils.toWei('1', 'gwei'); const homeDailyLimit = oneEther const homeMaxPerTx = halfEther +const ZERO = toBN(0) contract('ForeignBridge', async (accounts) => { - let validatorContract, authorities, rewards, owner, token; + let validatorContract, authorities, owner, token; before(async () => { validatorContract = await BridgeValidators.new() authorities = [accounts[1], accounts[2]]; @@ -31,11 +33,12 @@ contract('ForeignBridge', async (accounts) => { token = await POA20.new("POA ERC20 Foundation", "POA20", 18); let foreignBridge = await ForeignBridge.new(); - ZERO_ADDRESS.should.be.equal(await foreignBridge.validatorContract()) - '0'.should.be.bignumber.equal(await foreignBridge.deployedAtBlock()) - '0'.should.be.bignumber.equal(await foreignBridge.dailyLimit()) - '0'.should.be.bignumber.equal(await foreignBridge.maxPerTx()) - false.should.be.equal(await foreignBridge.isInitialized()) + expect(await foreignBridge.validatorContract()).to.be.equal(ZERO_ADDRESS) + expect(await foreignBridge.deployedAtBlock()).to.be.bignumber.equal(ZERO) + expect(await foreignBridge.isInitialized()).to.be.equal(false) + expect(await foreignBridge.requiredBlockConfirmations()).to.be.bignumber.equal(ZERO) + expect(await foreignBridge.dailyLimit()).to.be.bignumber.equal(ZERO) + expect(await foreignBridge.maxPerTx()).to.be.bignumber.equal(ZERO) await foreignBridge.initialize(ZERO_ADDRESS, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); await foreignBridge.initialize(validatorContract.address, ZERO_ADDRESS, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); @@ -44,41 +47,40 @@ contract('ForeignBridge', async (accounts) => { await foreignBridge.initialize(validatorContract.address, owner, oneEther, halfEther, minPerTx, requireBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); await foreignBridge.initialize(validatorContract.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner); - true.should.be.equal(await foreignBridge.isInitialized()) - validatorContract.address.should.be.equal(await foreignBridge.validatorContract()); - (await foreignBridge.deployedAtBlock()).should.be.bignumber.above(0); - oneEther.should.be.bignumber.equal(await foreignBridge.dailyLimit()) - halfEther.should.be.bignumber.equal(await foreignBridge.maxPerTx()) - minPerTx.should.be.bignumber.equal(await foreignBridge.minPerTx()) + expect(await foreignBridge.isInitialized()).to.be.equal(true) + expect(await foreignBridge.validatorContract()).to.be.equal(validatorContract.address) + expect(await foreignBridge.deployedAtBlock()).to.be.bignumber.above(ZERO) + expect(await foreignBridge.requiredBlockConfirmations()).to.be.bignumber.equal(requireBlockConfirmations.toString()) + expect(await foreignBridge.gasPrice()).to.be.bignumber.equal(gasPrice) + expect(await foreignBridge.dailyLimit()).to.be.bignumber.equal(oneEther) + expect(await foreignBridge.maxPerTx()).to.be.bignumber.equal(halfEther) + expect(await foreignBridge.minPerTx()).to.be.bignumber.equal(minPerTx) const bridgeMode = '0x92a8d7fe' // 4 bytes of keccak256('native-to-erc-core') - const mode = await foreignBridge.getBridgeMode(); - mode.should.be.equal(bridgeMode) - const [major, minor, patch] = await foreignBridge.getBridgeInterfacesVersion() - major.should.be.bignumber.gte(0) - minor.should.be.bignumber.gte(0) - patch.should.be.bignumber.gte(0) + expect(await foreignBridge.getBridgeMode()).to.be.equal(bridgeMode) + const { major, minor, patch } = await foreignBridge.getBridgeInterfacesVersion() + expect(major).to.be.bignumber.gte(ZERO) + expect(minor).to.be.bignumber.gte(ZERO) + expect(patch).to.be.bignumber.gte(ZERO) }) }) describe('#executeSignatures', async () => { + let foreignBridge beforeEach(async () => { foreignBridge = await ForeignBridge.new() token = await POA20.new("POA ERC20 Foundation", "POA20", 18); - const oneEther = web3.toBigNumber(web3.toWei(1, "ether")); - const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")); await foreignBridge.initialize(validatorContract.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner); - oneEther.should.be.bignumber.equal(await foreignBridge.dailyLimit()); await token.transferOwnership(foreignBridge.address); }) it('should allow to deposit', async () => { - var recipientAccount = accounts[3]; + const recipientAccount = accounts[3]; const balanceBefore = await token.balanceOf(recipientAccount) const totalSupplyBefore = await token.totalSupply() - var value = web3.toBigNumber(web3.toWei(0.25, "ether")); - var transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - var message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); - var signature = await sign(authorities[0], message) - var vrs = signatureToVRS(signature); + const value = ether('0.25'); + const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; + const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); + const signature = await sign(authorities[0], message) + const vrs = signatureToVRS(signature); false.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) const {logs} = await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.fulfilled logs[0].event.should.be.equal("RelayedMessage") @@ -93,35 +95,32 @@ contract('ForeignBridge', async (accounts) => { true.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) }) it('should reject if address is not foreign address', async () => { - var recipientAccount = accounts[3]; - const balanceBefore = await token.balanceOf(recipientAccount) - const totalSupplyBefore = await token.totalSupply() - var value = web3.toBigNumber(web3.toWei(0.25, "ether")); - var transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - var message = createMessage(recipientAccount, value, transactionHash, accounts[0]); - var signature = await sign(authorities[0], message) - var vrs = signatureToVRS(signature); + const recipientAccount = accounts[3]; + const value = ether('0.25',); + const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; + const message = createMessage(recipientAccount, value, transactionHash, accounts[0]); + const signature = await sign(authorities[0], message) + const vrs = signatureToVRS(signature); false.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.rejectedWith(ERROR_MSG) }) it('should allow second deposit with different transactionHash but same recipient and value', async ()=> { - var recipientAccount = accounts[3]; + const recipientAccount = accounts[3]; const balanceBefore = await token.balanceOf(recipientAccount) // tx 1 - var value = web3.toBigNumber(web3.toWei(0.25, "ether")); - var homeGasPrice = web3.toBigNumber(0); - var transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - var message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); - var signature = await sign(authorities[0], message) - var vrs = signatureToVRS(signature); + const value = ether('0.25'); + const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; + const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); + const signature = await sign(authorities[0], message) + const vrs = signatureToVRS(signature); false.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.fulfilled // tx 2 - var transactionHash2 = "0x77a496628a776a03d58d7e6059a5937f04bebd8ba4ff89f76dd4bb8ba7e291ee"; - var message2 = createMessage(recipientAccount, value, transactionHash2, foreignBridge.address); - var signature2 = await sign(authorities[0], message2) - var vrs2 = signatureToVRS(signature2); + const transactionHash2 = "0x77a496628a776a03d58d7e6059a5937f04bebd8ba4ff89f76dd4bb8ba7e291ee"; + const message2 = createMessage(recipientAccount, value, transactionHash2, foreignBridge.address); + const signature2 = await sign(authorities[0], message2) + const vrs2 = signatureToVRS(signature2); false.should.be.equal(await foreignBridge.relayedMessages(transactionHash2)) const {logs} = await foreignBridge.executeSignatures([vrs2.v], [vrs2.r], [vrs2.s], message2).should.be.fulfilled @@ -131,35 +130,33 @@ contract('ForeignBridge', async (accounts) => { logs[0].args.transactionHash.should.be.equal(transactionHash2); const totalSupply = await token.totalSupply() const balanceAfter = await token.balanceOf(recipientAccount) - balanceAfter.should.be.bignumber.equal(balanceBefore.add(value.mul(2))) - totalSupply.should.be.bignumber.equal(value.mul(2)) + balanceAfter.should.be.bignumber.equal(balanceBefore.add(value.mul(toBN(2)))) + totalSupply.should.be.bignumber.equal(value.mul(toBN(2))) true.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) true.should.be.equal(await foreignBridge.relayedMessages(transactionHash2)) }) it('should not allow second deposit (replay attack) with same transactionHash but different recipient', async () => { - var recipientAccount = accounts[3]; - const balanceBefore = await token.balanceOf(recipientAccount) + const recipientAccount = accounts[3]; // tx 1 - var value = web3.toBigNumber(web3.toWei(0.5, "ether")); - var homeGasPrice = web3.toBigNumber(0); - var transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - var message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); - var signature = await sign(authorities[0], message) - var vrs = signatureToVRS(signature); + const value = halfEther + const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; + const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); + const signature = await sign(authorities[0], message) + const vrs = signatureToVRS(signature); false.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.fulfilled // tx 2 - var message2 = createMessage(accounts[4], value, transactionHash, foreignBridge.address); - var signature2 = await sign(authorities[0], message2) - var vrs = signatureToVRS(signature2); + const message2 = createMessage(accounts[4], value, transactionHash, foreignBridge.address); + const signature2 = await sign(authorities[0], message2) + const vrs2 = signatureToVRS(signature2); true.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) - await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message2).should.be.rejectedWith(ERROR_MSG) + await foreignBridge.executeSignatures([vrs2.v], [vrs2.r], [vrs2.s], message2).should.be.rejectedWith(ERROR_MSG) }) it('should not allow withdraw over home max tx limit', async () => { const recipientAccount = accounts[3]; - const invalidValue = web3.toBigNumber(web3.toWei(0.75, "ether")); + const invalidValue = ether('0.75'); const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; const message = createMessage(recipientAccount, invalidValue, transactionHash, foreignBridge.address); @@ -202,51 +199,42 @@ contract('ForeignBridge', async (accounts) => { token = await POA20.new("POA ERC20 Foundation", "POA20", 18); twoAuthorities = [accounts[0], accounts[1]]; ownerOfValidatorContract = accounts[3] - const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")); await multisigValidatorContract.initialize(2, twoAuthorities, ownerOfValidatorContract, {from: ownerOfValidatorContract}) foreignBridgeWithMultiSignatures = await ForeignBridge.new() - const oneEther = web3.toBigNumber(web3.toWei(1, "ether")); await foreignBridgeWithMultiSignatures.initialize(multisigValidatorContract.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, {from: ownerOfValidatorContract}); await token.transferOwnership(foreignBridgeWithMultiSignatures.address); }) it('deposit should fail if not enough signatures are provided', async () => { - var recipientAccount = accounts[4]; - const balanceBefore = await web3.eth.getBalance(recipientAccount) - const homeBalanceBefore = await web3.eth.getBalance(foreignBridgeWithMultiSignatures.address) + const recipientAccount = accounts[4]; // msg 1 - var value = web3.toBigNumber(web3.toWei(0.5, "ether")); - var homeGasPrice = web3.toBigNumber(0); - var transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - var message = createMessage(recipientAccount, value, transactionHash, foreignBridgeWithMultiSignatures.address); - var signature = await sign(twoAuthorities[0], message) - var vrs = signatureToVRS(signature); + const value = halfEther + const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; + const message = createMessage(recipientAccount, value, transactionHash, foreignBridgeWithMultiSignatures.address); + const signature = await sign(twoAuthorities[0], message) + const vrs = signatureToVRS(signature); false.should.be.equal(await foreignBridgeWithMultiSignatures.relayedMessages(transactionHash)) await foreignBridgeWithMultiSignatures.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.rejectedWith(ERROR_MSG) // msg 2 - var signature2 = await sign(twoAuthorities[1], message) - var vrs2 = signatureToVRS(signature2); + const signature2 = await sign(twoAuthorities[1], message) + const vrs2 = signatureToVRS(signature2); const {logs} = await foreignBridgeWithMultiSignatures.executeSignatures([vrs.v, vrs2.v], [vrs.r, vrs2.r], [vrs.s, vrs2.s], message).should.be.fulfilled; logs[0].event.should.be.equal("RelayedMessage") logs[0].args.recipient.should.be.equal(recipientAccount) logs[0].args.value.should.be.bignumber.equal(value) logs[0].args.transactionHash.should.be.equal(transactionHash); - const balanceAfter = await token.balanceOf(recipientAccount) true.should.be.equal(await foreignBridgeWithMultiSignatures.relayedMessages(transactionHash)) }) it('deposit should fail if duplicate signature is provided', async () => { - var recipientAccount = accounts[4]; - const balanceBefore = await web3.eth.getBalance(recipientAccount) - const homeBalanceBefore = await web3.eth.getBalance(foreignBridgeWithMultiSignatures.address) + const recipientAccount = accounts[4]; // msg 1 - var value = web3.toBigNumber(web3.toWei(0.5, "ether")); - var homeGasPrice = web3.toBigNumber(0); - var transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - var message = createMessage(recipientAccount, value, transactionHash, foreignBridgeWithMultiSignatures.address); - var signature = await sign(twoAuthorities[0], message) - var vrs = signatureToVRS(signature); + const value = halfEther + const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; + const message = createMessage(recipientAccount, value, transactionHash, foreignBridgeWithMultiSignatures.address); + const signature = await sign(twoAuthorities[0], message) + const vrs = signatureToVRS(signature); false.should.be.equal(await foreignBridgeWithMultiSignatures.relayedMessages(transactionHash)) await foreignBridgeWithMultiSignatures.executeSignatures([vrs.v, vrs.v], [vrs.r, vrs.r], [vrs.s, vrs.s], message).should.be.rejectedWith(ERROR_MSG) }) @@ -257,7 +245,7 @@ contract('ForeignBridge', async (accounts) => { const validatorContractWith3Signatures = await BridgeValidators.new() await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) const erc20Token = await POA20.new("Some ERC20", "RSZT", 18); - const value = web3.toBigNumber(web3.toWei(0.5, "ether")); + const value = halfEther const foreignBridgeWithThreeSigs = await ForeignBridge.new() await foreignBridgeWithThreeSigs.initialize(validatorContractWith3Signatures.address, erc20Token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner); @@ -292,70 +280,85 @@ contract('ForeignBridge', async (accounts) => { const owner = accounts[3] const user = accounts[4] token = await POA20.new("POA ERC20 Foundation", "POA20", 18, {from: owner}); - foreignBridge = await ForeignBridge.new(); + const foreignBridge = await ForeignBridge.new(); await foreignBridge.initialize(validatorContract.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner); await token.mint(user, halfEther, {from: owner }).should.be.fulfilled; await token.transferOwnership(foreignBridge.address, {from: owner}); await foreignBridge.onTokenTransfer(user, halfEther, '0x00', {from: owner}).should.be.rejectedWith(ERROR_MSG); await token.transferAndCall(foreignBridge.address, halfEther, '0x00', {from: user}).should.be.fulfilled; - '0'.should.be.bignumber.equal(await token.totalSupply()); - '0'.should.be.bignumber.equal(await token.balanceOf(user)); + expect(await token.totalSupply()).to.be.bignumber.equal(ZERO) + expect(await token.balanceOf(user)).to.be.bignumber.equal(ZERO) }) it('should not allow to burn more than the limit', async () => { const owner = accounts[3] const user = accounts[4] - const valueMoreThanLimit = halfEther.add(1); + const valueMoreThanLimit = halfEther.add(toBN(1)); token = await POA20.new("POA ERC20 Foundation", "POA20", 18, {from: owner}); - foreignBridge = await ForeignBridge.new(); + const foreignBridge = await ForeignBridge.new(); + await foreignBridge.initialize(validatorContract.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner); await token.mint(user, valueMoreThanLimit, {from: owner }).should.be.fulfilled; await token.transferOwnership(foreignBridge.address, {from: owner}); + await token.transferAndCall(foreignBridge.address, valueMoreThanLimit, '0x00', {from: user}).should.be.rejectedWith(ERROR_MSG); + valueMoreThanLimit.should.be.bignumber.equal(await token.totalSupply()); valueMoreThanLimit.should.be.bignumber.equal(await token.balanceOf(user)); - const {logs} = await token.transferAndCall(foreignBridge.address, halfEther, '0x00', {from: user}).should.be.fulfilled; - '1'.should.be.bignumber.equal(await token.totalSupply()); - '1'.should.be.bignumber.equal(await token.balanceOf(user)); + + await token.transferAndCall(foreignBridge.address, halfEther, '0x00', {from: user}).should.be.fulfilled; + + expect(await token.totalSupply()).to.be.bignumber.equal('1') + expect(await token.balanceOf(user)).to.be.bignumber.equal('1') + const events = await getEvents(foreignBridge, {event: 'UserRequestForAffirmation'}); - events[0].args.should.be.deep.equal({ - recipient: user, - value: halfEther - }) + expect(events[0].returnValues.recipient).to.be.equal(user) + expect(toBN(events[0].returnValues.value)).to.be.bignumber.equal(halfEther) }) it('should only let to send within maxPerTx limit', async () => { const owner = accounts[3] const user = accounts[4] - const valueMoreThanLimit = halfEther.add(1); + const valueMoreThanLimit = halfEther.add(toBN(1)); token = await POA20.new("POA ERC20 Foundation", "POA20", 18, {from: owner}); - foreignBridge = await ForeignBridge.new(); + const foreignBridge = await ForeignBridge.new(); await foreignBridge.initialize(validatorContract.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner); - await token.mint(user, oneEther.add(1), {from: owner }).should.be.fulfilled; + await token.mint(user, oneEther.add(toBN(1)), {from: owner }).should.be.fulfilled; + await token.transferOwnership(foreignBridge.address, {from: owner}); + await token.transferAndCall(foreignBridge.address, valueMoreThanLimit, '0x00', {from: user}).should.be.rejectedWith(ERROR_MSG); - oneEther.add(1).should.be.bignumber.equal(await token.totalSupply()); - oneEther.add(1).should.be.bignumber.equal(await token.balanceOf(user)); + + oneEther.add(toBN(1)).should.be.bignumber.equal(await token.totalSupply()); + oneEther.add(toBN(1)).should.be.bignumber.equal(await token.balanceOf(user)); + await token.transferAndCall(foreignBridge.address, halfEther, '0x00', {from: user}).should.be.fulfilled; + valueMoreThanLimit.should.be.bignumber.equal(await token.totalSupply()); valueMoreThanLimit.should.be.bignumber.equal(await token.balanceOf(user)); + await token.transferAndCall(foreignBridge.address, halfEther, '0x00', {from: user}).should.be.fulfilled; - '1'.should.be.bignumber.equal(await token.totalSupply()); - '1'.should.be.bignumber.equal(await token.balanceOf(user)); + + expect(await token.totalSupply()).to.be.bignumber.equal('1') + expect(await token.balanceOf(user)).to.be.bignumber.equal('1') await token.transferAndCall(foreignBridge.address, '1', '0x00', {from: user}).should.be.rejectedWith(ERROR_MSG); }) it('should not let to withdraw less than minPerTx', async () => { const owner = accounts[3] const user = accounts[4] - const valueLessThanMinPerTx = minPerTx.sub(1); + const valueLessThanMinPerTx = minPerTx.sub(toBN(1)); token = await POA20.new("POA ERC20 Foundation", "POA20", 18, {from: owner}); - foreignBridge = await ForeignBridge.new(); + const foreignBridge = await ForeignBridge.new(); await foreignBridge.initialize(validatorContract.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner); await token.mint(user, oneEther, {from: owner }).should.be.fulfilled; await token.transferOwnership(foreignBridge.address, {from: owner}); + await token.transferAndCall(foreignBridge.address, valueLessThanMinPerTx, '0x00', {from: user}).should.be.rejectedWith(ERROR_MSG); + oneEther.should.be.bignumber.equal(await token.totalSupply()); oneEther.should.be.bignumber.equal(await token.balanceOf(user)); + await token.transferAndCall(foreignBridge.address, minPerTx, '0x00', {from: user}).should.be.fulfilled; + oneEther.sub(minPerTx).should.be.bignumber.equal(await token.totalSupply()); oneEther.sub(minPerTx).should.be.bignumber.equal(await token.balanceOf(user)); }) @@ -424,28 +427,29 @@ contract('ForeignBridge', async (accounts) => { it('can be deployed via upgradeToAndCall', async () => { const tokenAddress = token.address const validatorsAddress = validatorContract.address - const FOREIGN_DAILY_LIMIT = oneEther; - const FOREIGN_MAX_AMOUNT_PER_TX = halfEther; - const FOREIGN_MIN_AMOUNT_PER_TX = minPerTx; + const FOREIGN_DAILY_LIMIT = '3'; + const FOREIGN_MAX_AMOUNT_PER_TX = '2'; + const FOREIGN_MIN_AMOUNT_PER_TX = '1'; let storageProxy = await EternalStorageProxy.new().should.be.fulfilled; let foreignBridge = await ForeignBridge.new(); - let data = foreignBridge.initialize.request( - validatorsAddress, tokenAddress, FOREIGN_DAILY_LIMIT, FOREIGN_MAX_AMOUNT_PER_TX, FOREIGN_MIN_AMOUNT_PER_TX, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner).params[0].data + let data = foreignBridge.contract.methods.initialize( + validatorsAddress, tokenAddress, FOREIGN_DAILY_LIMIT, FOREIGN_MAX_AMOUNT_PER_TX, FOREIGN_MIN_AMOUNT_PER_TX, gasPrice, requireBlockConfirmations, '3', '2', owner).encodeABI() await storageProxy.upgradeToAndCall('1', foreignBridge.address, data).should.be.fulfilled; let finalContract = await ForeignBridge.at(storageProxy.address); true.should.be.equal(await finalContract.isInitialized()); validatorsAddress.should.be.equal(await finalContract.validatorContract()) - FOREIGN_DAILY_LIMIT.should.be.bignumber.equal(await finalContract.dailyLimit()) - FOREIGN_MAX_AMOUNT_PER_TX.should.be.bignumber.equal(await finalContract.maxPerTx()) - FOREIGN_MIN_AMOUNT_PER_TX.should.be.bignumber.equal(await finalContract.minPerTx()) + + expect(await finalContract.dailyLimit()).to.be.bignumber.equal(FOREIGN_DAILY_LIMIT) + expect(await finalContract.maxPerTx()).to.be.bignumber.equal(FOREIGN_MAX_AMOUNT_PER_TX) + expect(await finalContract.minPerTx()).to.be.bignumber.equal(FOREIGN_MIN_AMOUNT_PER_TX) }) it('can transfer ownership', async () => { const token = await POA20.new("POA ERC20 Foundation", "POA20", 18); const foreignBridge = await ForeignBridge.new(); const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; - const data = foreignBridge.initialize.request( - validatorContract.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner).params[0].data + const data = foreignBridge.contract.methods.initialize( + validatorContract.address, token.address, '3', '2', '1', gasPrice, requireBlockConfirmations, '3', '2', owner).encodeABI() await storageProxy.upgradeToAndCall('1', foreignBridge.address, data).should.be.fulfilled; await storageProxy.transferProxyOwnership(owner).should.be.fulfilled }) @@ -465,15 +469,15 @@ contract('ForeignBridge', async (accounts) => { let tokenSecond = await POA20.new("Roman Token", "RST", 18); await tokenSecond.mint(accounts[0], halfEther).should.be.fulfilled; - halfEther.should.be.bignumber.equal(await tokenSecond.balanceOf(accounts[0])) + expect(await tokenSecond.balanceOf(accounts[0])).to.be.bignumber.equal(halfEther) + await tokenSecond.transfer(foreignBridge.address, halfEther); - '0'.should.be.bignumber.equal(await tokenSecond.balanceOf(accounts[0])) - halfEther.should.be.bignumber.equal(await tokenSecond.balanceOf(foreignBridge.address)) + expect(await tokenSecond.balanceOf(accounts[0])).to.be.bignumber.equal(ZERO) + expect(await tokenSecond.balanceOf(foreignBridge.address)).to.be.bignumber.equal(halfEther) await foreignBridge.claimTokens(tokenSecond.address, accounts[3], {from: owner}); - '0'.should.be.bignumber.equal(await tokenSecond.balanceOf(foreignBridge.address)) - halfEther.should.be.bignumber.equal(await tokenSecond.balanceOf(accounts[3])) - + expect(await tokenSecond.balanceOf(foreignBridge.address)).to.be.bignumber.equal(ZERO) + expect(await tokenSecond.balanceOf(accounts[3])).to.be.bignumber.equal(halfEther) }) it('also calls claimTokens on tokenAddress', async () => { const owner = accounts[0]; @@ -488,14 +492,15 @@ contract('ForeignBridge', async (accounts) => { let tokenSecond = await POA20.new("Roman Token", "RST", 18); await tokenSecond.mint(accounts[0], 150).should.be.fulfilled; - '150'.should.be.bignumber.equal(await tokenSecond.balanceOf(accounts[0])) + expect(await tokenSecond.balanceOf(accounts[0])).to.be.bignumber.equal('150') + await tokenSecond.transfer(token.address, '150'); - '0'.should.be.bignumber.equal(await tokenSecond.balanceOf(accounts[0])) - '150'.should.be.bignumber.equal(await tokenSecond.balanceOf(token.address)) + expect(await tokenSecond.balanceOf(accounts[0])).to.be.bignumber.equal(ZERO) + expect(await tokenSecond.balanceOf(token.address)).to.be.bignumber.equal('150') await foreignBridge.claimTokensFromErc677(tokenSecond.address, accounts[3], {from: owner}); - '0'.should.be.bignumber.equal(await tokenSecond.balanceOf(foreignBridge.address)) - '150'.should.be.bignumber.equal(await tokenSecond.balanceOf(accounts[3])) + expect(await tokenSecond.balanceOf(foreignBridge.address)).to.be.bignumber.equal(ZERO) + expect(await tokenSecond.balanceOf(accounts[3])).to.be.bignumber.equal('150') }) }) @@ -509,15 +514,16 @@ contract('ForeignBridge', async (accounts) => { rewardableValidators = await RewardableValidators.new() await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled foreignBridge = await ForeignBridge.new() - homeFee = web3.toBigNumber(web3.toWei(0.001, "ether")) + homeFee = ether('0.001') }) it('sets variables', async () => { const feeManager = await FeeManagerNativeToErc.new() - ZERO_ADDRESS.should.be.equal(await foreignBridge.validatorContract()) - '0'.should.be.bignumber.equal(await foreignBridge.deployedAtBlock()) - '0'.should.be.bignumber.equal(await foreignBridge.dailyLimit()) - '0'.should.be.bignumber.equal(await foreignBridge.maxPerTx()) - false.should.be.equal(await foreignBridge.isInitialized()) + expect(await foreignBridge.validatorContract()).to.be.equal(ZERO_ADDRESS) + expect(await foreignBridge.deployedAtBlock()).to.be.bignumber.equal(ZERO) + expect(await foreignBridge.isInitialized()).to.be.equal(false) + expect(await foreignBridge.requiredBlockConfirmations()).to.be.bignumber.equal(ZERO) + expect(await foreignBridge.dailyLimit()).to.be.bignumber.equal(ZERO) + expect(await foreignBridge.maxPerTx()).to.be.bignumber.equal(ZERO) await foreignBridge.rewardableInitialize(ZERO_ADDRESS, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee).should.be.rejectedWith(ERROR_MSG); await foreignBridge.rewardableInitialize(rewardableValidators.address, ZERO_ADDRESS, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee).should.be.rejectedWith(ERROR_MSG); @@ -527,24 +533,23 @@ contract('ForeignBridge', async (accounts) => { await foreignBridge.rewardableInitialize(rewardableValidators.address, owner, oneEther, halfEther, minPerTx, requireBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, owner, ZERO_ADDRESS, homeFee).should.be.rejectedWith(ERROR_MSG); await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee).should.be.fulfilled; - true.should.be.equal(await foreignBridge.isInitialized()) - rewardableValidators.address.should.be.equal(await foreignBridge.validatorContract()); - (await foreignBridge.deployedAtBlock()).should.be.bignumber.above(0); - oneEther.should.be.bignumber.equal(await foreignBridge.dailyLimit()) - halfEther.should.be.bignumber.equal(await foreignBridge.maxPerTx()) - minPerTx.should.be.bignumber.equal(await foreignBridge.minPerTx()) + expect(await foreignBridge.isInitialized()).to.be.equal(true) + expect(await foreignBridge.validatorContract()).to.be.equal(rewardableValidators.address) + expect(await foreignBridge.deployedAtBlock()).to.be.bignumber.above(ZERO) + expect(await foreignBridge.requiredBlockConfirmations()).to.be.bignumber.equal(requireBlockConfirmations.toString()) + expect(await foreignBridge.gasPrice()).to.be.bignumber.equal(gasPrice) + expect(await foreignBridge.dailyLimit()).to.be.bignumber.equal(oneEther) + expect(await foreignBridge.maxPerTx()).to.be.bignumber.equal(halfEther) + expect(await foreignBridge.minPerTx()).to.be.bignumber.equal(minPerTx) const bridgeMode = '0x92a8d7fe' // 4 bytes of keccak256('native-to-erc-core') - const mode = await foreignBridge.getBridgeMode(); - mode.should.be.equal(bridgeMode) - const [major, minor, patch] = await foreignBridge.getBridgeInterfacesVersion() - major.should.be.bignumber.gte(0) - minor.should.be.bignumber.gte(0) - patch.should.be.bignumber.gte(0) + expect(await foreignBridge.getBridgeMode()).to.be.equal(bridgeMode) + const { major, minor, patch } = await foreignBridge.getBridgeInterfacesVersion() + expect(major).to.be.bignumber.gte(ZERO) + expect(minor).to.be.bignumber.gte(ZERO) + expect(patch).to.be.bignumber.gte(ZERO) - const feeManagerContract = await foreignBridge.feeManagerContract() - feeManagerContract.should.be.equals(feeManager.address) - const bridgeHomeFee = await foreignBridge.getHomeFee() - bridgeHomeFee.should.be.bignumber.equal(homeFee) + expect(await foreignBridge.feeManagerContract()).to.be.equals(feeManager.address) + expect(await foreignBridge.getHomeFee()).to.be.bignumber.equals(homeFee) }) it('can update fee contract', async () => { @@ -558,8 +563,7 @@ contract('ForeignBridge', async (accounts) => { await foreignBridge.setFeeManagerContract(newFeeManager.address, { from: owner }).should.be.fulfilled // Then - const feeManagerContract = await foreignBridge.feeManagerContract() - feeManagerContract.should.be.equals(newFeeManager.address) + expect(await foreignBridge.feeManagerContract()).to.be.equals(newFeeManager.address) }) it('can update fee', async () => { @@ -567,14 +571,13 @@ contract('ForeignBridge', async (accounts) => { await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee).should.be.fulfilled; // Given - const newHomeFee = web3.toBigNumber(web3.toWei(0.1, "ether")) + const newHomeFee = ether('0.1') // When await foreignBridge.setHomeFee(newHomeFee, { from: owner }).should.be.fulfilled // Then - const bridgeHomeFee = await foreignBridge.getHomeFee() - bridgeHomeFee.should.be.bignumber.equal(newHomeFee) + expect(await foreignBridge.getHomeFee()).to.be.bignumber.equals(newHomeFee) }) it('should be able to get fee manager mode', async () => { @@ -586,8 +589,7 @@ contract('ForeignBridge', async (accounts) => { await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee).should.be.fulfilled; // Then - const feeManagerMode = await foreignBridge.getFeeManagerMode() - feeManagerMode.should.be.equals(oneDirectionsModeHash) + expect(await foreignBridge.getFeeManagerMode()).to.be.equals(oneDirectionsModeHash) }) }) @@ -601,10 +603,12 @@ contract('ForeignBridge', async (accounts) => { }) it('should distribute fee to validator', async () => { const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeInWei = ether(fee.toString()) const value = halfEther - const finalUserValue = value.mul(web3.toBigNumber(1-fee)); - const feeAmount = value.mul(web3.toBigNumber(fee)) + const valueCalc = 0.5 * (1 - fee) + const feeAmountCalc = 0.5 * fee + const finalUserValue = ether(valueCalc.toString()) + const feeAmount = ether(feeAmountCalc.toString()) const validators = [accounts[1]] const rewards = [accounts[2]] @@ -625,7 +629,8 @@ contract('ForeignBridge', async (accounts) => { const { logs } = await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.fulfilled logs[0].event.should.be.equal("FeeDistributedFromSignatures") - logs[0].args.should.be.deep.equal({feeAmount, transactionHash}) + logs[0].args.feeAmount.should.be.bignumber.equal(feeAmount) + logs[0].args.transactionHash.should.be.equal(transactionHash) logs[1].event.should.be.equal("RelayedMessage") logs[1].args.recipient.should.be.equal(recipientAccount) @@ -643,12 +648,14 @@ contract('ForeignBridge', async (accounts) => { it('should distribute fee to 3 validators', async () => { // Given const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) - const feePerValidator = web3.toBigNumber(166666666666666) - const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) + const feeInWei = ether(fee.toString()) + const feePerValidator = toBN(166666666666666) + const feePerValidatorPlusDiff = toBN(166666666666668) const value = halfEther - const feeAmount = value.mul(web3.toBigNumber(fee)); - const finalUserValue = value.mul(web3.toBigNumber(1-fee)); + const valueCalc = 0.5 * (1 - fee) + const feeAmountCalc = 0.5 * fee + const finalUserValue = ether(valueCalc.toString()) + const feeAmount = ether(feeAmountCalc.toString()) const validators = [accounts[1], accounts[2], accounts[3]] const rewards = [accounts[4], accounts[5], accounts[6]] @@ -679,7 +686,8 @@ contract('ForeignBridge', async (accounts) => { // Then logs[0].event.should.be.equal("FeeDistributedFromSignatures") - logs[0].args.should.be.deep.equal({feeAmount, transactionHash}) + logs[0].args.feeAmount.should.be.bignumber.equal(feeAmount) + logs[0].args.transactionHash.should.be.equal(transactionHash) logs[1].event.should.be.equal("RelayedMessage") logs[1].args.recipient.should.be.equal(recipientAccount) @@ -708,11 +716,13 @@ contract('ForeignBridge', async (accounts) => { it('should distribute fee to 5 validators', async () => { // Given const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeInWei = ether(fee.toString()) const value = halfEther - const feeAmount = value.mul(web3.toBigNumber(fee)) - const feePerValidator = feeAmount.div(web3.toBigNumber(5)) - const finalUserValue = value.mul(web3.toBigNumber(1-fee)); + const valueCalc = 0.5 * (1 - fee) + const feeAmountCalc = 0.5 * fee + const finalUserValue = ether(valueCalc.toString()) + const feeAmount = ether(feeAmountCalc.toString()) + const feePerValidator = feeAmount.div(toBN(5)) const validators = [accounts[0], accounts[1], accounts[2], accounts[3], accounts[4]] const rewards = [accounts[5], accounts[6], accounts[7], accounts[8], accounts[9]] @@ -745,7 +755,8 @@ contract('ForeignBridge', async (accounts) => { // Then logs[0].event.should.be.equal("FeeDistributedFromSignatures") - logs[0].args.should.be.deep.equal({feeAmount, transactionHash}) + logs[0].args.feeAmount.should.be.bignumber.equal(feeAmount) + logs[0].args.transactionHash.should.be.equal(transactionHash) logs[1].event.should.be.equal("RelayedMessage") logs[1].args.recipient.should.be.equal(recipientAccount) diff --git a/test/native_to_erc/home_bridge_test.js b/test/native_to_erc/home_bridge_test.js index a8d1e281b..e43d0dda0 100644 --- a/test/native_to_erc/home_bridge_test.js +++ b/test/native_to_erc/home_bridge_test.js @@ -1,4 +1,3 @@ -const Web3Utils = require('web3-utils'); const HomeBridge = artifacts.require("HomeBridgeNativeToErc.sol"); const EternalStorageProxy = artifacts.require("EternalStorageProxy.sol"); const BridgeValidators = artifacts.require("BridgeValidators.sol"); @@ -6,16 +5,20 @@ const RevertFallback = artifacts.require("RevertFallback.sol"); const FeeManagerNativeToErc = artifacts.require("FeeManagerNativeToErc.sol"); const FeeManagerNativeToErcBothDirections = artifacts.require("FeeManagerNativeToErcBothDirections.sol"); const RewardableValidators = artifacts.require("RewardableValidators.sol"); -const {ERROR_MSG, ZERO_ADDRESS} = require('../setup'); -const {createMessage, sign, signatureToVRS} = require('../helpers/helpers'); -const minPerTx = web3.toBigNumber(web3.toWei(0.01, "ether")); + +const { expect } = require('chai'); +const { ERROR_MSG, ZERO_ADDRESS, toBN } = require('../setup'); +const {createMessage, sign, ether, expectEventInLogs} = require('../helpers/helpers'); + +const minPerTx = ether('0.01'); const requireBlockConfirmations = 8; -const gasPrice = Web3Utils.toWei('1', 'gwei'); -const oneEther = web3.toBigNumber(web3.toWei(1, "ether")); -const twoEther = web3.toBigNumber(web3.toWei(2, "ether")); -const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")); +const gasPrice = web3.utils.toWei('1', 'gwei'); +const oneEther = ether('1'); +const twoEther = ether('2'); +const halfEther = ether('0.5'); const foreignDailyLimit = oneEther const foreignMaxPerTx = halfEther +const ZERO = toBN(0) contract('HomeBridge', async (accounts) => { let homeContract, validatorContract, authorities, owner; @@ -31,25 +34,27 @@ contract('HomeBridge', async (accounts) => { homeContract = await HomeBridge.new() }) it('sets variables', async () => { - ZERO_ADDRESS.should.be.equal(await homeContract.validatorContract()) - '0'.should.be.bignumber.equal(await homeContract.deployedAtBlock()) - '0'.should.be.bignumber.equal(await homeContract.dailyLimit()) - '0'.should.be.bignumber.equal(await homeContract.maxPerTx()) - false.should.be.equal(await homeContract.isInitialized()) + expect(await homeContract.validatorContract()).to.be.equal(ZERO_ADDRESS) + expect(await homeContract.deployedAtBlock()).to.be.bignumber.equal(ZERO) + expect(await homeContract.dailyLimit()).to.be.bignumber.equal(ZERO) + expect(await homeContract.maxPerTx()).to.be.bignumber.equal(ZERO) + expect(await homeContract.isInitialized()).to.be.equal(false) + await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled; - true.should.be.equal(await homeContract.isInitialized()) - validatorContract.address.should.be.equal(await homeContract.validatorContract()); - (await homeContract.deployedAtBlock()).should.be.bignumber.above(0); - '3'.should.be.bignumber.equal(await homeContract.dailyLimit()) - '2'.should.be.bignumber.equal(await homeContract.maxPerTx()) - '1'.should.be.bignumber.equal(await homeContract.minPerTx()) + + expect(await homeContract.isInitialized()).to.be.equal(true) + expect(await homeContract.validatorContract()).to.be.equal(validatorContract.address) + expect(await homeContract.deployedAtBlock()).to.be.bignumber.above(ZERO) + expect(await homeContract.dailyLimit()).to.be.bignumber.equal('3') + expect(await homeContract.maxPerTx()).to.be.bignumber.equal('2') + expect(await homeContract.minPerTx()).to.be.bignumber.equal('1') + expect(await homeContract.gasPrice()).to.be.bignumber.equal(gasPrice) const bridgeMode = '0x92a8d7fe' // 4 bytes of keccak256('native-to-erc-core') - const mode = await homeContract.getBridgeMode(); - mode.should.be.equal(bridgeMode) - const [major, minor, patch] = await homeContract.getBridgeInterfacesVersion() - major.should.be.bignumber.gte(0) - minor.should.be.bignumber.gte(0) - patch.should.be.bignumber.gte(0) + expect(await homeContract.getBridgeMode()).to.be.equal(bridgeMode) + const { major, minor, patch } = await homeContract.getBridgeInterfacesVersion() + expect(major).to.be.bignumber.gte(ZERO) + expect(minor).to.be.bignumber.gte(ZERO) + expect(patch).to.be.bignumber.gte(ZERO) }) it('cant set maxPerTx > dailyLimit', async () => { false.should.be.equal(await homeContract.isInitialized()) @@ -60,14 +65,15 @@ contract('HomeBridge', async (accounts) => { it('can be deployed via upgradeToAndCall', async () => { let storageProxy = await EternalStorageProxy.new().should.be.fulfilled; - let data = homeContract.initialize.request(validatorContract.address, "3", "2", "1", gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner).params[0].data + let data = homeContract.contract.methods.initialize(validatorContract.address, "3", "2", "1", gasPrice, requireBlockConfirmations, '3', '2', owner).encodeABI() await storageProxy.upgradeToAndCall('1', homeContract.address, data).should.be.fulfilled; let finalContract = await HomeBridge.at(storageProxy.address); - true.should.be.equal(await finalContract.isInitialized()); - validatorContract.address.should.be.equal(await finalContract.validatorContract()) - "3".should.be.bignumber.equal(await finalContract.dailyLimit()) - "2".should.be.bignumber.equal(await finalContract.maxPerTx()) - "1".should.be.bignumber.equal(await finalContract.minPerTx()) + + expect(await finalContract.isInitialized()).to.be.equal(true) + expect(await finalContract.validatorContract()).to.be.equal(validatorContract.address) + expect(await finalContract.dailyLimit()).to.be.bignumber.equal('3') + expect(await finalContract.maxPerTx()).to.be.bignumber.equal('2') + expect(await finalContract.minPerTx()).to.be.bignumber.equal('1') }) it('cant initialize with invalid arguments', async () => { false.should.be.equal(await homeContract.isInitialized()) @@ -79,7 +85,7 @@ contract('HomeBridge', async (accounts) => { }) it('can transfer ownership', async () => { let storageProxy = await EternalStorageProxy.new().should.be.fulfilled; - let data = homeContract.initialize.request(validatorContract.address, "3", "2", "1", gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner).params[0].data + const data = homeContract.contract.methods.initialize(validatorContract.address, "3", "2", "1", gasPrice, requireBlockConfirmations, '3', '2', owner).encodeABI() await storageProxy.upgradeToAndCall('1', homeContract.address, data).should.be.fulfilled; await storageProxy.transferProxyOwnership(owner).should.be.fulfilled }) @@ -90,29 +96,30 @@ contract('HomeBridge', async (accounts) => { homeContract = await HomeBridge.new() await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner) }) - it('should accept POA', async () => { + it('should accept native coins', async () => { const currentDay = await homeContract.getCurrentDay() - '0'.should.be.bignumber.equal(await homeContract.totalSpentPerDay(currentDay)) - const {logs} = await homeContract.sendTransaction({ + expect(await homeContract.totalSpentPerDay(currentDay)).to.be.bignumber.equal(ZERO) + + const { logs } = await homeContract.sendTransaction({ from: accounts[1], value: 1 }).should.be.fulfilled - '1'.should.be.bignumber.equal(await homeContract.totalSpentPerDay(currentDay)) + expect(await homeContract.totalSpentPerDay(currentDay)).to.be.bignumber.equal('1') + + expectEventInLogs(logs, 'UserRequestForSignature', { recipient: accounts[1], value: toBN(1) }) + await homeContract.sendTransaction({ from: accounts[1], value: 3 }).should.be.rejectedWith(ERROR_MSG); - logs[0].event.should.be.equal('UserRequestForSignature') - logs[0].args.should.be.deep.equal({ - recipient: accounts[1], - value: new web3.BigNumber(1) - }) + await homeContract.setDailyLimit(4).should.be.fulfilled; await homeContract.sendTransaction({ from: accounts[1], value: 1 }).should.be.fulfilled - '2'.should.be.bignumber.equal(await homeContract.totalSpentPerDay(currentDay)) + + expect(await homeContract.totalSpentPerDay(currentDay)).to.be.bignumber.equal('2') }) it('doesnt let you send more than max amount per tx', async () => { @@ -185,7 +192,7 @@ contract('HomeBridge', async (accounts) => { beforeEach(async () => { homeBridge = await HomeBridge.new(); await homeBridge.initialize(validatorContract.address, twoEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner); - const {logs} = await homeBridge.sendTransaction({ + await homeBridge.sendTransaction({ from: accounts[2], value: halfEther }).should.be.fulfilled @@ -193,53 +200,51 @@ contract('HomeBridge', async (accounts) => { it('should allow validator to executeAffirmation', async () => { const recipient = accounts[5]; const value = halfEther; - const balanceBefore = await web3.eth.getBalance(recipient) + const balanceBefore = toBN(await web3.eth.getBalance(recipient)) const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; const {logs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}) - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ + + expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], transactionHash - }); - logs[1].event.should.be.equal("AffirmationCompleted"); - logs[1].args.should.be.deep.equal({ + }) + expectEventInLogs(logs, 'AffirmationCompleted', { recipient, value, transactionHash }) - const homeBalanceAfter = await web3.eth.getBalance(homeBridge.address) - const balanceAfter = await web3.eth.getBalance(recipient) + const homeBalanceAfter = toBN(await web3.eth.getBalance(homeBridge.address)) + const balanceAfter = toBN(await web3.eth.getBalance(recipient)) balanceAfter.should.be.bignumber.equal(balanceBefore.add(value)) - homeBalanceAfter.should.be.bignumber.equal(0) + homeBalanceAfter.should.be.bignumber.equal(ZERO) - const msgHash = Web3Utils.soliditySha3(recipient, value, transactionHash); - const senderHash = Web3Utils.soliditySha3(authorities[0], msgHash) + const msgHash = web3.utils.soliditySha3(recipient, value, transactionHash); + const senderHash = web3.utils.soliditySha3(authorities[0], msgHash) true.should.be.equal(await homeBridge.affirmationsSigned(senderHash)) }) it('should allow validator to executeAffirmation with zero value', async () => { const recipient = accounts[5]; - const value = web3.toBigNumber(web3.toWei(0, "ether")); - const balanceBefore = await web3.eth.getBalance(recipient) + const value = ZERO + const balanceBefore = toBN(await web3.eth.getBalance(recipient)) const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; const {logs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}) - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ + + expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], transactionHash - }); - logs[1].event.should.be.equal("AffirmationCompleted"); - logs[1].args.should.be.deep.equal({ + }) + expectEventInLogs(logs, 'AffirmationCompleted', { recipient, value, transactionHash }) - const balanceAfter = await web3.eth.getBalance(recipient) + const balanceAfter = toBN(await web3.eth.getBalance(recipient)) balanceAfter.should.be.bignumber.equal(balanceBefore.add(value)) - const msgHash = Web3Utils.soliditySha3(recipient, value, transactionHash); - const senderHash = Web3Utils.soliditySha3(authorities[0], msgHash) + const msgHash = web3.utils.soliditySha3(recipient, value, transactionHash); + const senderHash = web3.utils.soliditySha3(authorities[0], msgHash) true.should.be.equal(await homeBridge.affirmationsSigned(senderHash)) }) @@ -255,47 +260,39 @@ contract('HomeBridge', async (accounts) => { from: accounts[2], value: halfEther }).should.be.fulfilled - const homeBalanceBefore = await web3.eth.getBalance(homeBridgeWithTwoSigs.address) + const homeBalanceBefore = toBN(await web3.eth.getBalance(homeBridgeWithTwoSigs.address)) homeBalanceBefore.should.be.bignumber.equal(halfEther) const recipient = accounts[5]; const value = halfEther; const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - const balanceBefore = await web3.eth.getBalance(recipient) - const msgHash = Web3Utils.soliditySha3(recipient, value, transactionHash); + const balanceBefore = toBN(await web3.eth.getBalance(recipient)) + const msgHash = web3.utils.soliditySha3(recipient, value, transactionHash); const {logs} = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ - signer: authorities[0], - transactionHash - }); + + expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], transactionHash }) halfEther.should.be.bignumber.equal(await web3.eth.getBalance(homeBridgeWithTwoSigs.address)) const notProcessed = await homeBridgeWithTwoSigs.numAffirmationsSigned(msgHash); - notProcessed.should.be.bignumber.equal(1); + notProcessed.should.be.bignumber.equal('1'); await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[0]}).should.be.rejectedWith(ERROR_MSG); const secondSignature = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; - const balanceAfter = await web3.eth.getBalance(recipient) + const balanceAfter = toBN(await web3.eth.getBalance(recipient)) balanceAfter.should.be.bignumber.equal(balanceBefore.add(value)) - '0'.should.be.bignumber.equal(await web3.eth.getBalance(homeBridgeWithTwoSigs.address)) + expect(toBN(await web3.eth.getBalance(homeBridgeWithTwoSigs.address))).to.be.bignumber.equal(ZERO) - secondSignature.logs[1].event.should.be.equal("AffirmationCompleted"); - secondSignature.logs[1].args.should.be.deep.equal({ - recipient, - value, - transactionHash - }) + expectEventInLogs(secondSignature.logs, 'AffirmationCompleted', { recipient, value, transactionHash }) - const senderHash = Web3Utils.soliditySha3(authoritiesThreeAccs[0], msgHash) + const senderHash = web3.utils.soliditySha3(authoritiesThreeAccs[0], msgHash) true.should.be.equal(await homeBridgeWithTwoSigs.affirmationsSigned(senderHash)) - const senderHash2 = Web3Utils.soliditySha3(authoritiesThreeAccs[1], msgHash); + const senderHash2 = web3.utils.soliditySha3(authoritiesThreeAccs[1], msgHash); true.should.be.equal(await homeBridgeWithTwoSigs.affirmationsSigned(senderHash2)) const markedAsProcessed = await homeBridgeWithTwoSigs.numAffirmationsSigned(msgHash); - const processed = new web3.BigNumber(2).pow(255).add(2); + const processed = (toBN(2)).pow(toBN(255)).add(toBN(2)) markedAsProcessed.should.be.bignumber.equal(processed) }) it('should not allow to double submit', async () => { @@ -325,49 +322,47 @@ contract('HomeBridge', async (accounts) => { from: accounts[2], value: halfEther }).should.be.fulfilled - const homeBalanceBefore = await web3.eth.getBalance(homeBridgeWithTwoSigs.address) + const homeBalanceBefore = toBN(await web3.eth.getBalance(homeBridgeWithTwoSigs.address)) homeBalanceBefore.should.be.bignumber.equal(halfEther) const recipient = accounts[5]; - const value = halfEther.div(2); + const value = halfEther.div(toBN(2)); const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - const balanceBefore = await web3.eth.getBalance(recipient) - const msgHash = Web3Utils.soliditySha3(recipient, value, transactionHash); + const balanceBefore = toBN(await web3.eth.getBalance(recipient)) await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; - balanceBefore.add(value).should.be.bignumber.equal(await web3.eth.getBalance(recipient)) + expect(toBN(await web3.eth.getBalance(recipient))).to.be.bignumber.equal(balanceBefore.add(value)) + await validatorContractWith2Signatures.setRequiredSignatures(3).should.be.fulfilled; await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[2]}).should.be.rejectedWith(ERROR_MSG); + await validatorContractWith2Signatures.setRequiredSignatures(1).should.be.fulfilled; await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[2]}).should.be.rejectedWith(ERROR_MSG); - balanceBefore.add(value).should.be.bignumber.equal(await web3.eth.getBalance(recipient)) - + expect(toBN(await web3.eth.getBalance(recipient))).to.be.bignumber.equal(balanceBefore.add(value)) }) it('force withdraw if the recepient has fallback to revert', async () => { const revertFallbackContract = await RevertFallback.new(); await revertFallbackContract.receiveEth({from: accounts[0], value: halfEther}) - await web3.eth.getBalance(revertFallbackContract.address).should.be.bignumber.equal(halfEther) + expect(toBN(await web3.eth.getBalance(revertFallbackContract.address))).to.be.bignumber.equal(halfEther) const transactionHash = "0x106335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; const {logs} = await homeBridge.executeAffirmation(revertFallbackContract.address, halfEther, transactionHash, {from: authorities[0]}) - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ + + expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], transactionHash - }); - logs[1].event.should.be.equal("AffirmationCompleted"); - logs[1].args.should.be.deep.equal({ + }) + expectEventInLogs(logs, 'AffirmationCompleted', { recipient: revertFallbackContract.address, value: halfEther, transactionHash }) - const homeBalanceAfter = await web3.eth.getBalance(homeBridge.address) - const balanceAfter = await web3.eth.getBalance(revertFallbackContract.address) + const homeBalanceAfter = toBN(await web3.eth.getBalance(homeBridge.address)) + const balanceAfter = toBN(await web3.eth.getBalance(revertFallbackContract.address)) balanceAfter.should.be.bignumber.equal(halfEther.add(halfEther)) - homeBalanceAfter.should.be.bignumber.equal(0) - + homeBalanceAfter.should.be.bignumber.equal(ZERO) }) it('works with 5 validators and 3 required signatures', async () => { const recipient = accounts[8] @@ -379,7 +374,7 @@ contract('HomeBridge', async (accounts) => { const homeBridgeWithThreeSigs = await HomeBridge.new(); await homeBridgeWithThreeSigs.initialize(validatorContractWith3Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner); - const value = web3.toBigNumber(web3.toWei(0.5, "ether")); + const value = halfEther const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; await homeBridgeWithThreeSigs.sendTransaction({ @@ -388,17 +383,15 @@ contract('HomeBridge', async (accounts) => { }).should.be.fulfilled const {logs} = await homeBridgeWithThreeSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesFiveAccs[0]}).should.be.fulfilled; - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ + expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], transactionHash - }); + }) await homeBridgeWithThreeSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesFiveAccs[1]}).should.be.fulfilled; const thirdSignature = await homeBridgeWithThreeSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesFiveAccs[2]}).should.be.fulfilled; - thirdSignature.logs[1].event.should.be.equal("AffirmationCompleted"); - thirdSignature.logs[1].args.should.be.deep.equal({ + expectEventInLogs(thirdSignature.logs, 'AffirmationCompleted', { recipient, value, transactionHash @@ -421,13 +414,11 @@ contract('HomeBridge', async (accounts) => { const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.fulfilled; - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ + expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], transactionHash - }); - logs[1].event.should.be.equal("AffirmationCompleted"); - logs[1].args.should.be.deep.equal({ + }) + expectEventInLogs(logs, 'AffirmationCompleted', { recipient, value, transactionHash @@ -436,13 +427,11 @@ contract('HomeBridge', async (accounts) => { const transactionHash2 = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; const { logs: logs2 } = await homeBridge.executeAffirmation(recipient, value, transactionHash2, {from: authorities[0]}).should.be.fulfilled; - logs2[0].event.should.be.equal("SignedForAffirmation"); - logs2[0].args.should.be.deep.equal({ + expectEventInLogs(logs2, 'SignedForAffirmation', { signer: authorities[0], transactionHash: transactionHash2 - }); - logs2[1].event.should.be.equal("AffirmationCompleted"); - logs2[1].args.should.be.deep.equal({ + }) + expectEventInLogs(logs2, 'AffirmationCompleted', { recipient, value, transactionHash: transactionHash2 @@ -455,9 +444,9 @@ contract('HomeBridge', async (accounts) => { describe('#isAlreadyProcessed', async () => { it('returns ', async () => { - homeBridge = await HomeBridge.new(); - const bn = new web3.BigNumber(2).pow(255); - const processedNumbers = [bn.add(1).toString(10), bn.add(100).toString(10)]; + const homeBridge = await HomeBridge.new(); + const bn = new toBN(2).pow(toBN(255)); + const processedNumbers = [bn.add(toBN(1)).toString(10), bn.add(toBN(100)).toString(10)]; true.should.be.equal(await homeBridge.isAlreadyProcessed(processedNumbers[0])); true.should.be.equal(await homeBridge.isAlreadyProcessed(processedNumbers[1])); false.should.be.equal(await homeBridge.isAlreadyProcessed(10)); @@ -465,7 +454,7 @@ contract('HomeBridge', async (accounts) => { }) describe('#submitSignature', async () => { - let validatorContractWith2Signatures,authoritiesThreeAccs,ownerOfValidators,tokenPOA20,homeBridgeWithTwoSigs + let validatorContractWith2Signatures,authoritiesThreeAccs,ownerOfValidators,homeBridgeWithTwoSigs beforeEach(async () => { validatorContractWith2Signatures = await BridgeValidators.new() authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]]; @@ -475,11 +464,11 @@ contract('HomeBridge', async (accounts) => { await homeBridgeWithTwoSigs.initialize(validatorContractWith2Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner); }) it('allows a validator to submit a signature', async () => { - var recipientAccount = accounts[8] - var value = web3.toBigNumber(web3.toWei(0.5, "ether")); - var transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - var message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); - var signature = await sign(authoritiesThreeAccs[0], message) + const recipientAccount = accounts[8] + const value = halfEther + const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; + const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); + const signature = await sign(authoritiesThreeAccs[0], message) const {logs} = await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authorities[0]}).should.be.fulfilled; logs[0].event.should.be.equal('SignedForUserRequest') const msgHashFromLog = logs[0].args.messageHash @@ -487,19 +476,18 @@ contract('HomeBridge', async (accounts) => { const messageFromContract = await homeBridgeWithTwoSigs.message(msgHashFromLog); signature.should.be.equal(signatureFromContract); messageFromContract.should.be.equal(messageFromContract); - const hashMsg = Web3Utils.soliditySha3(message); - const hashSenderMsg = Web3Utils.soliditySha3(authorities[0], hashMsg) + const hashMsg = web3.utils.soliditySha3(message); + const hashSenderMsg = web3.utils.soliditySha3(authorities[0], hashMsg) true.should.be.equal(await homeBridgeWithTwoSigs.messagesSigned(hashSenderMsg)); }) it('when enough requiredSignatures are collected, CollectedSignatures event is emitted', async () => { - var recipientAccount = accounts[8] - var value = web3.toBigNumber(web3.toWei(0.5, "ether")); - var homeGasPrice = web3.toBigNumber(0); - var transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - var message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); - var signature = await sign(authoritiesThreeAccs[0], message) - var signature2 = await sign(authoritiesThreeAccs[1], message) - '2'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); + const recipientAccount = accounts[8] + const value = halfEther + const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; + const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); + const signature = await sign(authoritiesThreeAccs[0], message) + const signature2 = await sign(authoritiesThreeAccs[1], message) + expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('2'); await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.rejectedWith(ERROR_MSG); await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[1]}).should.be.rejectedWith(ERROR_MSG); @@ -517,13 +505,13 @@ contract('HomeBridge', async (accounts) => { const homeBridgeWithThreeSigs = await HomeBridge.new(); await homeBridgeWithThreeSigs.initialize(validatorContractWith3Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner); - const value = web3.toBigNumber(web3.toWei(0.5, "ether")); + const value = halfEther const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithThreeSigs.address); const signature = await sign(authoritiesFiveAccs[0], message) const signature2 = await sign(authoritiesFiveAccs[1], message) const signature3 = await sign(authoritiesFiveAccs[2], message) - '3'.should.be.bignumber.equal(await validatorContractWith3Signatures.requiredSignatures()); + expect(await validatorContractWith3Signatures.requiredSignatures()).to.be.bignumber.equal('3'); await homeBridgeWithThreeSigs.submitSignature(signature, message, {from: authoritiesFiveAccs[0]}).should.be.fulfilled; await homeBridgeWithThreeSigs.submitSignature(signature2, message, {from: authoritiesFiveAccs[1]}).should.be.fulfilled; @@ -533,40 +521,43 @@ contract('HomeBridge', async (accounts) => { logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesFiveAccs[2]) }) it('attack when increasing requiredSignatures', async () => { - var recipientAccount = accounts[8] - var value = web3.toBigNumber(web3.toWei(0.5, "ether")); - var homeGasPrice = web3.toBigNumber(0); - var transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - var message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); - var signature = await sign(authoritiesThreeAccs[0], message) - var signature2 = await sign(authoritiesThreeAccs[1], message) - var signature3 = await sign(authoritiesThreeAccs[2], message) - '2'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); + const recipientAccount = accounts[8] + const value = halfEther + const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; + const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); + const signature = await sign(authoritiesThreeAccs[0], message) + const signature2 = await sign(authoritiesThreeAccs[1], message) + const signature3 = await sign(authoritiesThreeAccs[2], message) + expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('2'); + await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.rejectedWith(ERROR_MSG); await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[1]}).should.be.rejectedWith(ERROR_MSG); const {logs} = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; + logs.length.should.be.equal(2) logs[1].event.should.be.equal('CollectedSignatures') logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesThreeAccs[1]) + await validatorContractWith2Signatures.setRequiredSignatures(3).should.be.fulfilled; - '3'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); - const attackerTx = await homeBridgeWithTwoSigs.submitSignature(signature3, message, {from: authoritiesThreeAccs[2]}).should.be.rejectedWith(ERROR_MSG); + expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('3'); + + await homeBridgeWithTwoSigs.submitSignature(signature3, message, {from: authoritiesThreeAccs[2]}).should.be.rejectedWith(ERROR_MSG); }) it('attack when decreasing requiredSignatures', async () => { - var recipientAccount = accounts[8] - var value = web3.toBigNumber(web3.toWei(0.5, "ether")); - var homeGasPrice = web3.toBigNumber(0); - var transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - var message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); - var signature = await sign(authoritiesThreeAccs[0], message) - var signature2 = await sign(authoritiesThreeAccs[1], message) - var signature3 = await sign(authoritiesThreeAccs[2], message) - '2'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); + const recipientAccount = accounts[8] + const value = halfEther + const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; + const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); + const signature = await sign(authoritiesThreeAccs[0], message) + const signature2 = await sign(authoritiesThreeAccs[1], message) + expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('2'); + await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; await validatorContractWith2Signatures.setRequiredSignatures(1).should.be.fulfilled; - '1'.should.be.bignumber.equal(await validatorContractWith2Signatures.requiredSignatures()); - const {logs} = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; + expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('1'); + const { logs } = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; + logs.length.should.be.equal(2) logs[1].event.should.be.equal('CollectedSignatures') logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesThreeAccs[1]) @@ -579,8 +570,7 @@ contract('HomeBridge', async (accounts) => { }) it('should return the required message length', async () => { - const requiredMessageLength = await homeContract.requiredMessageLength() - '104'.should.be.bignumber.equal(requiredMessageLength) + expect(await homeContract.requiredMessageLength()).to.be.bignumber.equal('104') }) }) @@ -593,16 +583,16 @@ contract('HomeBridge', async (accounts) => { rewardableValidators = await RewardableValidators.new() await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled homeBridge = await HomeBridge.new() - homeFee = web3.toBigNumber(web3.toWei(0, "ether")) - foreignFee = web3.toBigNumber(web3.toWei(0.002, "ether")) + homeFee = ZERO + foreignFee = ether('0.002') }) it('sets variables', async () => { const feeManager = await FeeManagerNativeToErc.new() - ZERO_ADDRESS.should.be.equal(await homeBridge.validatorContract()) - '0'.should.be.bignumber.equal(await homeBridge.deployedAtBlock()) - '0'.should.be.bignumber.equal(await homeBridge.dailyLimit()) - '0'.should.be.bignumber.equal(await homeBridge.maxPerTx()) - false.should.be.equal(await homeBridge.isInitialized()) + expect(await homeBridge.validatorContract()).to.be.equal(ZERO_ADDRESS) + expect(await homeBridge.deployedAtBlock()).to.be.bignumber.equal(ZERO) + expect(await homeBridge.dailyLimit()).to.be.bignumber.equal(ZERO) + expect(await homeBridge.maxPerTx()).to.be.bignumber.equal(ZERO) + expect(await homeBridge.isInitialized()).to.be.equal(false) await homeBridge.rewardableInitialize(ZERO_ADDRESS, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, 0, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); @@ -610,19 +600,19 @@ contract('HomeBridge', async (accounts) => { await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, ZERO_ADDRESS, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; - true.should.be.equal(await homeBridge.isInitialized()) - rewardableValidators.address.should.be.equal(await homeBridge.validatorContract()); - (await homeBridge.deployedAtBlock()).should.be.bignumber.above(0); - oneEther.should.be.bignumber.equal(await homeBridge.dailyLimit()) - halfEther.should.be.bignumber.equal(await homeBridge.maxPerTx()) - minPerTx.should.be.bignumber.equal(await homeBridge.minPerTx()) + expect(await homeBridge.isInitialized()).to.be.equal(true) + expect(await homeBridge.validatorContract()).to.be.equal(rewardableValidators.address) + expect(await homeBridge.deployedAtBlock()).to.be.bignumber.above(ZERO) + expect(await homeBridge.dailyLimit()).to.be.bignumber.equal(oneEther) + expect(await homeBridge.maxPerTx()).to.be.bignumber.equal(halfEther) + expect(await homeBridge.minPerTx()).to.be.bignumber.equal(minPerTx) + expect(await homeBridge.gasPrice()).to.be.bignumber.equal(gasPrice) const bridgeMode = '0x92a8d7fe' // 4 bytes of keccak256('native-to-erc-core') - const mode = await homeBridge.getBridgeMode(); - mode.should.be.equal(bridgeMode) - const [major, minor, patch] = await homeBridge.getBridgeInterfacesVersion() - major.should.be.bignumber.gte(0) - minor.should.be.bignumber.gte(0) - patch.should.be.bignumber.gte(0) + expect(await homeBridge.getBridgeMode()).to.be.equal(bridgeMode) + const { major, minor, patch } = await homeBridge.getBridgeInterfacesVersion() + expect(major).to.be.bignumber.gte(ZERO) + expect(minor).to.be.bignumber.gte(ZERO) + expect(patch).to.be.bignumber.gte(ZERO) const feeManagerContract = await homeBridge.feeManagerContract() feeManagerContract.should.be.equals(feeManager.address) @@ -650,7 +640,7 @@ contract('HomeBridge', async (accounts) => { await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; // Given - const newForeignFee = web3.toBigNumber(web3.toWei(0.2, "ether")) + const newForeignFee = ether('0.2') // When await homeBridge.setForeignFee(newForeignFee, { from: owner }).should.be.fulfilled @@ -689,8 +679,8 @@ contract('HomeBridge', async (accounts) => { // Given // 0.1% fee const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) - const notUsedFee = web3.toBigNumber(web3.toWei(0, "ether")) + const feeInWei = ether(fee.toString()) + const notUsedFee = ZERO const value = halfEther; await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, notUsedFee, feeInWei).should.be.fulfilled; @@ -702,8 +692,7 @@ contract('HomeBridge', async (accounts) => { }).should.be.fulfilled // Then - logs[0].event.should.be.equal('UserRequestForSignature') - logs[0].args.should.be.deep.equal({ + expectEventInLogs(logs, 'UserRequestForSignature', { recipient: user, value: value }) @@ -726,8 +715,8 @@ contract('HomeBridge', async (accounts) => { // Given // 0.1% fee const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) - const notUsedFee = web3.toBigNumber(web3.toWei(0, "ether")) + const feeInWei = ether(fee.toString()) + const notUsedFee = ZERO const value = halfEther; const rewardAddressBalanceBefore = await web3.eth.getBalance(rewards[0]) @@ -749,10 +738,10 @@ contract('HomeBridge', async (accounts) => { logs.length.should.be.equal(2) logs[1].event.should.be.equal('CollectedSignatures') - const bridgeBalance = await web3.eth.getBalance(homeBridge.address) + const bridgeBalance = toBN(await web3.eth.getBalance(homeBridge.address)) bridgeBalance.should.be.bignumber.equal(value) - const rewardAddressBalanceAfter = await web3.eth.getBalance(rewards[0]) + const rewardAddressBalanceAfter = toBN(await web3.eth.getBalance(rewards[0])) rewardAddressBalanceAfter.should.be.bignumber.equal(rewardAddressBalanceBefore) }) }) @@ -772,11 +761,13 @@ contract('HomeBridge', async (accounts) => { // Given // 0.1% fee const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) - const notUsedFee = web3.toBigNumber(web3.toWei(0, "ether")) + const feeInWei = ether(fee.toString()) + const notUsedFee = ZERO const value = halfEther; - const finalUserValue = value.mul(web3.toBigNumber(1-fee)); - const feeAmount = value.mul(web3.toBigNumber(fee)) + const valueCalc = 0.5 * (1 - fee) + const finalUserValue = ether(valueCalc.toString()) + const feeAmountCalc = 0.5 * fee + const feeAmount = ether(feeAmountCalc.toString()) await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, notUsedFee, feeInWei).should.be.fulfilled; await homeBridge.sendTransaction({ @@ -786,32 +777,30 @@ contract('HomeBridge', async (accounts) => { const recipient = accounts[5]; - const balanceBefore = await web3.eth.getBalance(recipient) - const rewardAddressBalanceBefore = await web3.eth.getBalance(rewards[0]) + const balanceBefore = toBN(await web3.eth.getBalance(recipient)) + const rewardAddressBalanceBefore = toBN(await web3.eth.getBalance(rewards[0])) const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; // When const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled // Then - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ + expectEventInLogs(logs, 'SignedForAffirmation', { signer: validators[0], transactionHash - }); - logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); - logs[1].args.should.be.deep.equal({ - feeAmount: value.mul(web3.toBigNumber(fee)), + }) + expectEventInLogs(logs, 'FeeDistributedFromAffirmation', { + feeAmount, transactionHash }) - logs[2].event.should.be.equal("AffirmationCompleted"); - logs[2].args.should.be.deep.equal({ + expectEventInLogs(logs, 'AffirmationCompleted', { recipient, value, transactionHash }) - const balanceAfter = await web3.eth.getBalance(recipient) - const rewardAddressBalanceAfter = await web3.eth.getBalance(rewards[0]) + + const balanceAfter = toBN(await web3.eth.getBalance(recipient)) + const rewardAddressBalanceAfter = toBN(await web3.eth.getBalance(rewards[0])) rewardAddressBalanceAfter.should.be.bignumber.equal(rewardAddressBalanceBefore.add(feeAmount)) balanceAfter.should.be.bignumber.equal(balanceBefore.add(finalUserValue)) @@ -827,11 +816,14 @@ contract('HomeBridge', async (accounts) => { const value = halfEther; // 0.1% fee const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) - const notUsedFee = web3.toBigNumber(web3.toWei(0, "ether")) - const feePerValidator = web3.toBigNumber(166666666666666) - const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) - const finalUserValue = value.mul(web3.toBigNumber(1-fee)); + const feeInWei = ether(fee.toString()) + const notUsedFee = ZERO + const feePerValidator = toBN(166666666666666) + const feePerValidatorPlusDiff = toBN(166666666666668) + const valueCalc = 0.5 * (1 - fee) + const finalUserValue = ether(valueCalc.toString()) + const feeAmountCalc = 0.5 * fee + const feeAmount = ether(feeAmountCalc.toString()) const homeBridge = await HomeBridge.new() const feeManager = await FeeManagerNativeToErc.new() @@ -843,11 +835,11 @@ contract('HomeBridge', async (accounts) => { }).should.be.fulfilled const recipient = accounts[8]; - const balanceBefore = await web3.eth.getBalance(recipient) + const balanceBefore = toBN(await web3.eth.getBalance(recipient)) - const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) - const initialBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) - const initialBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + const initialBalanceRewardAddress1 = toBN(await web3.eth.getBalance(rewards[0])) + const initialBalanceRewardAddress2 = toBN(await web3.eth.getBalance(rewards[1])) + const initialBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; @@ -858,28 +850,26 @@ contract('HomeBridge', async (accounts) => { // Then logsValidator1.length.should.be.equals(1) - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ + expectEventInLogs(logs, 'SignedForAffirmation', { signer: validators[1], transactionHash - }); - logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); - logs[1].args.should.be.deep.equal({ - feeAmount: value.mul(web3.toBigNumber(fee)), + }) + expectEventInLogs(logs, 'FeeDistributedFromAffirmation', { + feeAmount, transactionHash }) - logs[2].event.should.be.equal("AffirmationCompleted"); - logs[2].args.should.be.deep.equal({ + expectEventInLogs(logs, 'AffirmationCompleted', { recipient, value, transactionHash }) - const balanceAfter = await web3.eth.getBalance(recipient) + + const balanceAfter = toBN(await web3.eth.getBalance(recipient)) balanceAfter.should.be.bignumber.equal(balanceBefore.add(finalUserValue)) - const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) - const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) - const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + const updatedBalanceRewardAddress1 = toBN(await web3.eth.getBalance(rewards[0])) + const updatedBalanceRewardAddress2 = toBN(await web3.eth.getBalance(rewards[1])) + const updatedBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) expect( updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidator)) @@ -891,8 +881,8 @@ contract('HomeBridge', async (accounts) => { updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidator)) || updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidatorPlusDiff))).to.equal(true) - const homeBridgeBalance = await web3.eth.getBalance(homeBridge.address) - homeBridgeBalance.should.be.bignumber.equal('0') + const homeBridgeBalance = toBN(await web3.eth.getBalance(homeBridge.address)) + homeBridgeBalance.should.be.bignumber.equal(ZERO) }) it('should distribute fee to 5 validators', async () => { // Given @@ -904,10 +894,11 @@ contract('HomeBridge', async (accounts) => { const value = halfEther; // 0.1% fee const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) - const notUsedFee = web3.toBigNumber(web3.toWei(0, "ether")) - const feeAmount = value.mul(web3.toBigNumber(fee)) - const feePerValidator = feeAmount.div(web3.toBigNumber(5)) + const feeInWei = ether(fee.toString()) + const notUsedFee = ZERO + const feeAmountCalc = 0.5 * fee + const feeAmount = ether(feeAmountCalc.toString()) + const feePerValidator = feeAmount.div(toBN(5)) const rewardableValidators = await RewardableValidators.new() const homeBridge = await HomeBridge.new() @@ -919,14 +910,14 @@ contract('HomeBridge', async (accounts) => { value: halfEther }).should.be.fulfilled - const recipient = "0xf4bef13f9f4f2b203faf0c3cbbaabe1afe056955"; - const balanceBefore = await web3.eth.getBalance(recipient) + const recipient = "0xf4BEF13F9f4f2B203FAF0C3cBbaAbe1afE056955"; + const balanceBefore = toBN(await web3.eth.getBalance(recipient)) - const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) - const initialBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) - const initialBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) - const initialBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) - const initialBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) + const initialBalanceRewardAddress1 = toBN(await web3.eth.getBalance(rewards[0])) + const initialBalanceRewardAddress2 = toBN(await web3.eth.getBalance(rewards[1])) + const initialBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) + const initialBalanceRewardAddress4 = toBN(await web3.eth.getBalance(rewards[3])) + const initialBalanceRewardAddress5 = toBN(await web3.eth.getBalance(rewards[4])) const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; @@ -941,30 +932,28 @@ contract('HomeBridge', async (accounts) => { // Then logsValidator1.length.should.be.equals(1) - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ + expectEventInLogs(logs, 'SignedForAffirmation', { signer: validators[4], transactionHash - }); - logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); - logs[1].args.should.be.deep.equal({ + }) + expectEventInLogs(logs, 'FeeDistributedFromAffirmation', { feeAmount, transactionHash }) - logs[2].event.should.be.equal("AffirmationCompleted"); - logs[2].args.should.be.deep.equal({ + expectEventInLogs(logs, 'AffirmationCompleted', { recipient, value, transactionHash }) - const balanceAfter = await web3.eth.getBalance(recipient) + + const balanceAfter = toBN(await web3.eth.getBalance(recipient)) balanceAfter.should.be.bignumber.equal(balanceBefore.add(value.sub(feeAmount))) - const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) - const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) - const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) - const updatedBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) - const updatedBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) + const updatedBalanceRewardAddress1 = toBN(await web3.eth.getBalance(rewards[0])) + const updatedBalanceRewardAddress2 = toBN(await web3.eth.getBalance(rewards[1])) + const updatedBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) + const updatedBalanceRewardAddress4 = toBN(await web3.eth.getBalance(rewards[3])) + const updatedBalanceRewardAddress5 = toBN(await web3.eth.getBalance(rewards[4])) updatedBalanceRewardAddress1.should.be.bignumber.equal(initialBalanceRewardAddress1.add(feePerValidator)) updatedBalanceRewardAddress2.should.be.bignumber.equal(initialBalanceRewardAddress2.add(feePerValidator)) @@ -990,7 +979,7 @@ contract('HomeBridge', async (accounts) => { // Given // 0.1% fee const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeInWei = ether(fee.toString()) const value = halfEther; await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei, feeInWei).should.be.fulfilled; @@ -1002,9 +991,9 @@ contract('HomeBridge', async (accounts) => { }).should.be.fulfilled // Then - const finalValue = value.mul(web3.toBigNumber(1 - fee)) - logs[0].event.should.be.equal('UserRequestForSignature') - logs[0].args.should.be.deep.equal({ + const valueCalc = 0.5 * (1 - fee) + const finalValue = ether(valueCalc.toString()) + expectEventInLogs(logs, 'UserRequestForSignature', { recipient: user, value: finalValue }) @@ -1027,12 +1016,14 @@ contract('HomeBridge', async (accounts) => { // Given // 0.1% fee const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeInWei = ether(fee.toString()) const initialValue = halfEther - const value = initialValue.mul(web3.toBigNumber(1-fee)); - const feeAmount = initialValue.mul(web3.toBigNumber(fee)) + const valueCalc = 0.5 * (1 - fee) + const value = ether(valueCalc.toString()) + const feeAmountCalc = 0.5 * fee + const feeAmount = ether(feeAmountCalc.toString()) - const rewardAddressBalanceBefore = await web3.eth.getBalance(rewards[0]) + const rewardAddressBalanceBefore = toBN(await web3.eth.getBalance(rewards[0])) await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei, feeInWei).should.be.fulfilled; @@ -1050,16 +1041,15 @@ contract('HomeBridge', async (accounts) => { // Then logs.length.should.be.equal(3) logs[1].event.should.be.equal('CollectedSignatures') - logs[2].event.should.be.equal("FeeDistributedFromSignatures"); - logs[2].args.should.be.deep.equal({ + expectEventInLogs(logs, 'FeeDistributedFromSignatures', { feeAmount, transactionHash }) - const bridgeBalance = await web3.eth.getBalance(homeBridge.address) + const bridgeBalance = toBN(await web3.eth.getBalance(homeBridge.address)) bridgeBalance.should.be.bignumber.equal(value) - const rewardAddressBalanceAfter = await web3.eth.getBalance(rewards[0]) + const rewardAddressBalanceAfter = toBN(await web3.eth.getBalance(rewards[0])) rewardAddressBalanceAfter.should.be.bignumber.equal(rewardAddressBalanceBefore.add(feeAmount)) }) it('should distribute fee to 3 validators', async () => { @@ -1077,11 +1067,14 @@ contract('HomeBridge', async (accounts) => { // Given // 0.1% fee const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) - const feePerValidator = web3.toBigNumber(166666666666666) - const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) + const feeInWei = ether(fee.toString()) + const feePerValidator = toBN(166666666666666) + const feePerValidatorPlusDiff = toBN(166666666666668) const initialValue = halfEther - const value = initialValue.mul(web3.toBigNumber(1-fee)); + const valueCalc = 0.5 * (1 - fee) + const value = ether(valueCalc.toString()) + const feeAmountCalc = 0.5 * fee + const feeAmount = ether(feeAmountCalc.toString()) await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei, feeInWei).should.be.fulfilled; @@ -1090,9 +1083,9 @@ contract('HomeBridge', async (accounts) => { value: initialValue }).should.be.fulfilled - const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) - const initialBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) - const initialBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + const initialBalanceRewardAddress1 = toBN(await web3.eth.getBalance(rewards[0])) + const initialBalanceRewardAddress2 = toBN(await web3.eth.getBalance(rewards[1])) + const initialBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) // When const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80" @@ -1108,15 +1101,14 @@ contract('HomeBridge', async (accounts) => { // Then logs.length.should.be.equal(3) logs[1].event.should.be.equal('CollectedSignatures') - logs[2].event.should.be.equal("FeeDistributedFromSignatures"); - logs[2].args.should.be.deep.equal({ - feeAmount: initialValue.mul(web3.toBigNumber(fee)), + expectEventInLogs(logs, 'FeeDistributedFromSignatures', { + feeAmount, transactionHash }) - const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) - const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) - const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + const updatedBalanceRewardAddress1 = toBN(await web3.eth.getBalance(rewards[0])) + const updatedBalanceRewardAddress2 = toBN(await web3.eth.getBalance(rewards[1])) + const updatedBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) expect( updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidator)) @@ -1143,11 +1135,13 @@ contract('HomeBridge', async (accounts) => { // Given // 0.1% fee const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeInWei = ether(fee.toString()) const initialValue = halfEther - const feeAmount = initialValue.mul(web3.toBigNumber(fee)) - const feePerValidator = feeAmount.div(web3.toBigNumber(5)) - const value = initialValue.mul(web3.toBigNumber(1-fee)); + const valueCalc = 0.5 * (1 - fee) + const value = ether(valueCalc.toString()) + const feeAmountCalc = 0.5 * fee + const feeAmount = ether(feeAmountCalc.toString()) + const feePerValidator = feeAmount.div(toBN(5)) await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei, feeInWei).should.be.fulfilled; @@ -1156,11 +1150,11 @@ contract('HomeBridge', async (accounts) => { value: initialValue }).should.be.fulfilled - const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) - const initialBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) - const initialBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) - const initialBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) - const initialBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) + const initialBalanceRewardAddress1 = toBN(await web3.eth.getBalance(rewards[0])) + const initialBalanceRewardAddress2 = toBN(await web3.eth.getBalance(rewards[1])) + const initialBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) + const initialBalanceRewardAddress4 = toBN(await web3.eth.getBalance(rewards[3])) + const initialBalanceRewardAddress5 = toBN(await web3.eth.getBalance(rewards[4])) // When const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80" @@ -1180,17 +1174,16 @@ contract('HomeBridge', async (accounts) => { // Then logs.length.should.be.equal(3) logs[1].event.should.be.equal('CollectedSignatures') - logs[2].event.should.be.equal("FeeDistributedFromSignatures"); - logs[2].args.should.be.deep.equal({ + expectEventInLogs(logs, 'FeeDistributedFromSignatures', { feeAmount, transactionHash }) - const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) - const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) - const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) - const updatedBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) - const updatedBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) + const updatedBalanceRewardAddress1 = toBN(await web3.eth.getBalance(rewards[0])) + const updatedBalanceRewardAddress2 = toBN(await web3.eth.getBalance(rewards[1])) + const updatedBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) + const updatedBalanceRewardAddress4 = toBN(await web3.eth.getBalance(rewards[3])) + const updatedBalanceRewardAddress5 = toBN(await web3.eth.getBalance(rewards[4])) updatedBalanceRewardAddress1.should.be.bignumber.equal(initialBalanceRewardAddress1.add(feePerValidator)) updatedBalanceRewardAddress2.should.be.bignumber.equal(initialBalanceRewardAddress2.add(feePerValidator)) @@ -1215,10 +1208,12 @@ contract('HomeBridge', async (accounts) => { // Given // 0.1% fee const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) + const feeInWei = ether(fee.toString()) const value = halfEther; - const finalUserValue = value.mul(web3.toBigNumber(1-fee)); - const feeAmount = value.mul(web3.toBigNumber(fee)) + const valueCalc = 0.5 * (1 - fee) + const finalUserValue = ether(valueCalc.toString()) + const feeAmountCalc = 0.5 * fee + const feeAmount = ether(feeAmountCalc.toString()) await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei, feeInWei).should.be.fulfilled; await homeBridge.sendTransaction({ @@ -1228,32 +1223,30 @@ contract('HomeBridge', async (accounts) => { const recipient = accounts[5]; - const balanceBefore = await web3.eth.getBalance(recipient) - const rewardAddressBalanceBefore = await web3.eth.getBalance(rewards[0]) + const balanceBefore = toBN(await web3.eth.getBalance(recipient)) + const rewardAddressBalanceBefore = toBN(await web3.eth.getBalance(rewards[0])) const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; // When const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled // Then - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ + expectEventInLogs(logs, 'SignedForAffirmation', { signer: validators[0], transactionHash - }); - logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); - logs[1].args.should.be.deep.equal({ + }) + expectEventInLogs(logs, 'FeeDistributedFromAffirmation', { feeAmount, transactionHash }) - logs[2].event.should.be.equal("AffirmationCompleted"); - logs[2].args.should.be.deep.equal({ + expectEventInLogs(logs, 'AffirmationCompleted', { recipient, value, transactionHash }) - const balanceAfter = await web3.eth.getBalance(recipient) - const rewardAddressBalanceAfter = await web3.eth.getBalance(rewards[0]) + + const balanceAfter = toBN(await web3.eth.getBalance(recipient)) + const rewardAddressBalanceAfter = toBN(await web3.eth.getBalance(rewards[0])) rewardAddressBalanceAfter.should.be.bignumber.equal(rewardAddressBalanceBefore.add(feeAmount)) balanceAfter.should.be.bignumber.equal(balanceBefore.add(finalUserValue)) @@ -1269,10 +1262,13 @@ contract('HomeBridge', async (accounts) => { const value = halfEther; // 0.1% fee const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) - const feePerValidator = web3.toBigNumber(166666666666666) - const feePerValidatorPlusDiff = web3.toBigNumber(166666666666668) - const finalUserValue = value.mul(web3.toBigNumber(1-fee)); + const feeInWei = ether(fee.toString()) + const feePerValidator = toBN(166666666666666) + const feePerValidatorPlusDiff = toBN(166666666666668) + const valueCalc = 0.5 * (1 - fee) + const finalUserValue = ether(valueCalc.toString()) + const feeAmountCalc = 0.5 * fee + const feeAmount = ether(feeAmountCalc.toString()) const homeBridge = await HomeBridge.new() const feeManager = await FeeManagerNativeToErcBothDirections.new() @@ -1284,11 +1280,11 @@ contract('HomeBridge', async (accounts) => { }).should.be.fulfilled const recipient = accounts[8]; - const balanceBefore = await web3.eth.getBalance(recipient) + const balanceBefore = toBN(await web3.eth.getBalance(recipient)) - const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) - const initialBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) - const initialBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + const initialBalanceRewardAddress1 = toBN(await web3.eth.getBalance(rewards[0])) + const initialBalanceRewardAddress2 = toBN(await web3.eth.getBalance(rewards[1])) + const initialBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; @@ -1299,28 +1295,26 @@ contract('HomeBridge', async (accounts) => { // Then logsValidator1.length.should.be.equals(1) - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ + expectEventInLogs(logs, 'SignedForAffirmation', { signer: validators[1], transactionHash - }); - logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); - logs[1].args.should.be.deep.equal({ - feeAmount: value.mul(web3.toBigNumber(fee)), + }) + expectEventInLogs(logs, 'FeeDistributedFromAffirmation', { + feeAmount, transactionHash }) - logs[2].event.should.be.equal("AffirmationCompleted"); - logs[2].args.should.be.deep.equal({ + expectEventInLogs(logs, 'AffirmationCompleted', { recipient, value, transactionHash }) - const balanceAfter = await web3.eth.getBalance(recipient) + + const balanceAfter = toBN(await web3.eth.getBalance(recipient)) balanceAfter.should.be.bignumber.equal(balanceBefore.add(finalUserValue)) - const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) - const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) - const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) + const updatedBalanceRewardAddress1 = toBN(await web3.eth.getBalance(rewards[0])) + const updatedBalanceRewardAddress2 = toBN(await web3.eth.getBalance(rewards[1])) + const updatedBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) expect( updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidator)) @@ -1332,7 +1326,7 @@ contract('HomeBridge', async (accounts) => { updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidator)) || updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidatorPlusDiff))).to.equal(true) - const homeBridgeBalance = await web3.eth.getBalance(homeBridge.address) + const homeBridgeBalance = toBN(await web3.eth.getBalance(homeBridge.address)) homeBridgeBalance.should.be.bignumber.equal('0') }) it('should distribute fee to 5 validators', async () => { @@ -1345,9 +1339,10 @@ contract('HomeBridge', async (accounts) => { const value = halfEther; // 0.1% fee const fee = 0.001 - const feeInWei = web3.toBigNumber(web3.toWei(fee, "ether")) - const feeAmount = value.mul(web3.toBigNumber(fee)) - const feePerValidator = feeAmount.div(web3.toBigNumber(5)) + const feeInWei = ether(fee.toString()) + const feeAmountCalc = 0.5 * fee + const feeAmount = ether(feeAmountCalc.toString()) + const feePerValidator = feeAmount.div(toBN(5)) const rewardableValidators = await RewardableValidators.new() const homeBridge = await HomeBridge.new() @@ -1359,14 +1354,14 @@ contract('HomeBridge', async (accounts) => { value: halfEther }).should.be.fulfilled - const recipient = "0xf4bef13f9f4f2b203faf0c3cbbaabe1afe056955"; - const balanceBefore = await web3.eth.getBalance(recipient) + const recipient = "0xf4BEF13F9f4f2B203FAF0C3cBbaAbe1afE056955"; + const balanceBefore = toBN(await web3.eth.getBalance(recipient)) - const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) - const initialBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) - const initialBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) - const initialBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) - const initialBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) + const initialBalanceRewardAddress1 = toBN(await web3.eth.getBalance(rewards[0])) + const initialBalanceRewardAddress2 = toBN(await web3.eth.getBalance(rewards[1])) + const initialBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) + const initialBalanceRewardAddress4 = toBN(await web3.eth.getBalance(rewards[3])) + const initialBalanceRewardAddress5 = toBN(await web3.eth.getBalance(rewards[4])) const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; @@ -1381,30 +1376,28 @@ contract('HomeBridge', async (accounts) => { // Then logsValidator1.length.should.be.equals(1) - logs[0].event.should.be.equal("SignedForAffirmation"); - logs[0].args.should.be.deep.equal({ + expectEventInLogs(logs, 'SignedForAffirmation', { signer: validators[4], transactionHash - }); - logs[1].event.should.be.equal("FeeDistributedFromAffirmation"); - logs[1].args.should.be.deep.equal({ - feeAmount: value.mul(web3.toBigNumber(fee)), + }) + expectEventInLogs(logs, 'FeeDistributedFromAffirmation', { + feeAmount, transactionHash }) - logs[2].event.should.be.equal("AffirmationCompleted"); - logs[2].args.should.be.deep.equal({ + expectEventInLogs(logs, 'AffirmationCompleted', { recipient, value, transactionHash }) - const balanceAfter = await web3.eth.getBalance(recipient) + + const balanceAfter = toBN(await web3.eth.getBalance(recipient)) balanceAfter.should.be.bignumber.equal(balanceBefore.add(value.sub(feeAmount))) - const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) - const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) - const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) - const updatedBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) - const updatedBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) + const updatedBalanceRewardAddress1 = toBN(await web3.eth.getBalance(rewards[0])) + const updatedBalanceRewardAddress2 = toBN(await web3.eth.getBalance(rewards[1])) + const updatedBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) + const updatedBalanceRewardAddress4 = toBN(await web3.eth.getBalance(rewards[3])) + const updatedBalanceRewardAddress5 = toBN(await web3.eth.getBalance(rewards[4])) updatedBalanceRewardAddress1.should.be.bignumber.equal(initialBalanceRewardAddress1.add(feePerValidator)) updatedBalanceRewardAddress2.should.be.bignumber.equal(initialBalanceRewardAddress2.add(feePerValidator)) diff --git a/test/poa20_test.js b/test/poa20_test.js index 95fb49904..94e04655e 100644 --- a/test/poa20_test.js +++ b/test/poa20_test.js @@ -3,18 +3,22 @@ const POA20RewardableMock = artifacts.require("./mockContracts/ERC677BridgeToken const ERC677ReceiverTest = artifacts.require("ERC677ReceiverTest.sol") const BlockRewardTest = artifacts.require("BlockReward.sol") const StakingTest = artifacts.require("Staking.sol") -const { ERROR_MSG, ZERO_ADDRESS} = require('./setup'); -const Web3Utils = require('web3-utils'); const HomeErcToErcBridge = artifacts.require("HomeBridgeErcToErc.sol"); const ForeignNativeToErcBridge = artifacts.require("ForeignBridgeNativeToErc.sol"); const BridgeValidators = artifacts.require("BridgeValidators.sol"); -const minPerTx = web3.toBigNumber(web3.toWei(0.01, "ether")); + +const { ERROR_MSG, ZERO_ADDRESS, BN } = require('./setup'); +const { ether, expectEventInLogs } = require('./helpers/helpers'); +const { expect } = require('chai'); + +const minPerTx = ether('0.01') const requireBlockConfirmations = 8; -const gasPrice = Web3Utils.toWei('1', 'gwei'); -const oneEther = web3.toBigNumber(web3.toWei(1, "ether")); -const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")); +const gasPrice = web3.utils.toWei('1', 'gwei') +const oneEther = ether('1') +const halfEther = ether('0.5') const executionDailyLimit = oneEther const executionMaxPerTx = halfEther +const ZERO = new BN(0) async function testERC677BridgeToken(accounts, rewardable) { let token @@ -25,26 +29,16 @@ async function testERC677BridgeToken(accounts, rewardable) { token = await tokenContract.new("POA ERC20 Foundation", "POA20", 18); }) it('default values', async () => { - - const symbol = await token.symbol() - assert.equal(symbol, 'POA20') - - const decimals = await token.decimals() - assert.equal(decimals, 18) - - const name = await token.name() - assert.equal(name, "POA ERC20 Foundation") - - const totalSupply = await token.totalSupply(); - assert.equal(totalSupply, 0); - - const mintingFinished = await token.mintingFinished(); - assert.equal(mintingFinished, false); - - const [major, minor, patch] = await token.getTokenInterfacesVersion() - major.should.be.bignumber.gte(0) - minor.should.be.bignumber.gte(0) - patch.should.be.bignumber.gte(0) + expect(await token.symbol()).to.be.equal('POA20') + expect(await token.decimals()).to.be.bignumber.equal('18') + expect(await token.name()).to.be.equal('POA ERC20 Foundation') + expect(await token.totalSupply()).to.be.bignumber.equal(ZERO) + expect(await token.mintingFinished()).to.be.equal(false) + + const { major, minor, patch } = await token.getTokenInterfacesVersion() + expect(major).to.be.bignumber.gte(ZERO) + expect(minor).to.be.bignumber.gte(ZERO) + expect(patch).to.be.bignumber.gte(ZERO) }) describe('#bridgeContract', async() => { @@ -158,88 +152,88 @@ async function testERC677BridgeToken(accounts, rewardable) { const user2 = accounts[2]; const user3 = accounts[3]; - assert.equal(await token.totalSupply(), 0); - (await token.balanceOf(user1)).should.be.bignumber.equal(0); - (await token.balanceOf(user2)).should.be.bignumber.equal(0); - (await token.balanceOf(user3)).should.be.bignumber.equal(0); + expect(await token.totalSupply()).to.be.bignumber.equal(ZERO); + expect(await token.balanceOf(user1)).to.be.bignumber.equal(ZERO); + expect(await token.balanceOf(user2)).to.be.bignumber.equal(ZERO); + expect(await token.balanceOf(user3)).to.be.bignumber.equal(ZERO); await token.setBlockRewardContractMock(accounts[4]).should.be.fulfilled; await token.mintReward([user1, user2, user3], [100, 200, 300], {from: accounts[4] }).should.be.fulfilled; - assert.equal(await token.totalSupply(), 600); - (await token.balanceOf(user1)).should.be.bignumber.equal(100); - (await token.balanceOf(user2)).should.be.bignumber.equal(200); - (await token.balanceOf(user3)).should.be.bignumber.equal(300); + expect(await token.totalSupply()).to.be.bignumber.equal('600'); + expect(await token.balanceOf(user1)).to.be.bignumber.equal('100'); + expect(await token.balanceOf(user2)).to.be.bignumber.equal('200'); + expect(await token.balanceOf(user3)).to.be.bignumber.equal('300'); }) }) describe('#stake', async() => { it('can only be called by Staking contract', async () => { await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled; - await token.mintReward([user], [100], {from: accounts[2] }).should.be.fulfilled; + await token.mintReward([user], ['100'], {from: accounts[2] }).should.be.fulfilled; await token.setStakingContractMock(accounts[3]).should.be.fulfilled; - await token.stake(user, 100, {from: accounts[4] }).should.be.rejectedWith(ERROR_MSG); - await token.stake(user, 100, {from: accounts[3] }).should.be.fulfilled; + await token.stake(user, '100', {from: accounts[4] }).should.be.rejectedWith(ERROR_MSG); + await token.stake(user, '100', {from: accounts[3] }).should.be.fulfilled; }) it('should revert if user doesn\'t have enough balance', async () => { await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled; - await token.mintReward([user], [99], {from: accounts[2] }).should.be.fulfilled; - (await token.balanceOf(user)).should.be.bignumber.equal(99); + await token.mintReward([user], ['99'], {from: accounts[2] }).should.be.fulfilled; + expect(await token.balanceOf(user)).to.be.bignumber.equal('99'); await token.setStakingContractMock(accounts[3]).should.be.fulfilled; - await token.stake(user, 100, {from: accounts[3] }).should.be.rejectedWith(ERROR_MSG); + await token.stake(user, '100', {from: accounts[3] }).should.be.rejectedWith(ERROR_MSG); }) it('should decrease user\'s balance and increase Staking\'s balance', async () => { await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled; - await token.mintReward([user], [100], {from: accounts[2] }).should.be.fulfilled; - (await token.balanceOf(user)).should.be.bignumber.equal(100); - (await token.balanceOf(accounts[3])).should.be.bignumber.equal(0); + await token.mintReward([user], ['100'], {from: accounts[2] }).should.be.fulfilled; + expect(await token.balanceOf(user)).to.be.bignumber.equal('100'); + expect(await token.balanceOf(accounts[3])).to.be.bignumber.equal(ZERO); await token.setStakingContractMock(accounts[3]).should.be.fulfilled; - await token.stake(user, 100, {from: accounts[3] }).should.be.fulfilled; - (await token.balanceOf(user)).should.be.bignumber.equal(0); - (await token.balanceOf(accounts[3])).should.be.bignumber.equal(100); + await token.stake(user, '100', {from: accounts[3] }).should.be.fulfilled; + expect(await token.balanceOf(user)).to.be.bignumber.equal(ZERO); + expect(await token.balanceOf(accounts[3])).to.be.bignumber.equal('100'); }) }) describe('#withdraw', async() => { it('can only be called by Staking contract', async () => { await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled; - await token.mintReward([user], [100], {from: accounts[2] }).should.be.fulfilled; + await token.mintReward([user], ['100'], {from: accounts[2] }).should.be.fulfilled; await token.setStakingContractMock(accounts[3]).should.be.fulfilled; - await token.stake(user, 100, {from: accounts[3] }).should.be.fulfilled; - await token.withdraw(user, 100, {from: accounts[4] }).should.be.rejectedWith(ERROR_MSG); - await token.withdraw(user, 100, {from: accounts[3] }).should.be.fulfilled; + await token.stake(user, '100', {from: accounts[3] }).should.be.fulfilled; + await token.withdraw(user, '100', {from: accounts[4] }).should.be.rejectedWith(ERROR_MSG); + await token.withdraw(user, '100', {from: accounts[3] }).should.be.fulfilled; }) it('should revert if Staking doesn\'t have enough balance', async () => { await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled; - await token.mintReward([user], [100], {from: accounts[2] }).should.be.fulfilled; - (await token.balanceOf(user)).should.be.bignumber.equal(100); + await token.mintReward([user], ['100'], {from: accounts[2] }).should.be.fulfilled; + expect(await token.balanceOf(user)).to.be.bignumber.equal('100'); await token.setStakingContractMock(accounts[3]).should.be.fulfilled; - await token.stake(user, 100, {from: accounts[3] }).should.be.fulfilled; - await token.withdraw(user, 101, {from: accounts[3] }).should.be.rejectedWith(ERROR_MSG); - await token.withdraw(user, 100, {from: accounts[3] }).should.be.fulfilled; + await token.stake(user, '100', {from: accounts[3] }).should.be.fulfilled; + await token.withdraw(user, '101', {from: accounts[3] }).should.be.rejectedWith(ERROR_MSG); + await token.withdraw(user, '100', {from: accounts[3] }).should.be.fulfilled; }) it('should decrease Staking\'s balance and increase user\'s balance', async () => { await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled; - await token.mintReward([user], [100], {from: accounts[2] }).should.be.fulfilled; - (await token.balanceOf(user)).should.be.bignumber.equal(100); - (await token.balanceOf(accounts[3])).should.be.bignumber.equal(0); + await token.mintReward([user], ['100'], {from: accounts[2] }).should.be.fulfilled; + expect(await token.balanceOf(user)).to.be.bignumber.equal('100'); + expect(await token.balanceOf(accounts[3])).to.be.bignumber.equal(ZERO); await token.setStakingContractMock(accounts[3]).should.be.fulfilled; - await token.stake(user, 100, {from: accounts[3] }).should.be.fulfilled; - (await token.balanceOf(user)).should.be.bignumber.equal(0); - (await token.balanceOf(accounts[3])).should.be.bignumber.equal(100); + await token.stake(user, '100', {from: accounts[3] }).should.be.fulfilled; + expect(await token.balanceOf(user)).to.be.bignumber.equal('0'); + expect(await token.balanceOf(accounts[3])).to.be.bignumber.equal('100'); await token.withdraw(user, 60, {from: accounts[3] }).should.be.fulfilled; - (await token.balanceOf(user)).should.be.bignumber.equal(60); - (await token.balanceOf(accounts[3])).should.be.bignumber.equal(40); + expect(await token.balanceOf(user)).to.be.bignumber.equal('60'); + expect(await token.balanceOf(accounts[3])).to.be.bignumber.equal('40'); }) }) } describe('#mint', async() => { it('can mint by owner', async () => { - (await token.totalSupply()).should.be.bignumber.equal(0); + expect(await token.totalSupply()).to.be.bignumber.equal(ZERO); await token.mint(user, 1, {from: owner }).should.be.fulfilled; - (await token.totalSupply()).should.be.bignumber.equal(1); - (await token.balanceOf(user)).should.be.bignumber.equal(1); + expect(await token.totalSupply()).to.be.bignumber.equal('1'); + expect(await token.balanceOf(user)).to.be.bignumber.equal('1'); }) it('no one can call finishMinting', async () => { @@ -247,10 +241,10 @@ async function testERC677BridgeToken(accounts, rewardable) { }) it('cannot mint by non-owner', async () => { - (await token.totalSupply()).should.be.bignumber.equal(0); + expect(await token.totalSupply()).to.be.bignumber.equal(ZERO); await token.mint(user, 1, {from: user }).should.be.rejectedWith(ERROR_MSG); - (await token.totalSupply()).should.be.bignumber.equal(0); - (await token.balanceOf(user)).should.be.bignumber.equal(0); + expect(await token.totalSupply()).to.be.bignumber.equal(ZERO); + expect(await token.balanceOf(user)).to.be.bignumber.equal(ZERO); }) }) @@ -266,26 +260,24 @@ async function testERC677BridgeToken(accounts, rewardable) { await foreignNativeToErcBridge.initialize(validatorContract.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, executionDailyLimit, executionMaxPerTx, owner); }) it('sends tokens to recipient', async () => { - await token.mint(user, 1, {from: owner }).should.be.fulfilled; + await token.mint(user, '1', {from: owner }).should.be.fulfilled; await token.transfer(user, 1, {from: owner}).should.be.rejectedWith(ERROR_MSG); const {logs} = await token.transfer(owner, 1, {from: user}).should.be.fulfilled; - (await token.balanceOf(owner)).should.be.bignumber.equal(1); - (await token.balanceOf(user)).should.be.bignumber.equal(0); - logs[0].event.should.be.equal("Transfer") - logs[0].args.should.be.deep.equal({ + expect(await token.balanceOf(owner)).to.be.bignumber.equal('1'); + expect(await token.balanceOf(user)).to.be.bignumber.equal(ZERO); + expectEventInLogs(logs, 'Transfer', { from: user, to: owner, - value: new web3.BigNumber(1) + value: new BN(1) }) }) it('sends tokens to bridge contract', async () => { await token.setBridgeContract(homeErcToErcContract.address).should.be.fulfilled; - await token.mint(user, web3.toWei(1, "ether"), {from: owner }).should.be.fulfilled; + await token.mint(user, oneEther, {from: owner }).should.be.fulfilled; const result = await token.transfer(homeErcToErcContract.address, minPerTx, {from: user}).should.be.fulfilled; - result.logs[0].event.should.be.equal("Transfer") - result.logs[0].args.should.be.deep.equal({ + expectEventInLogs(result.logs, 'Transfer', { from: user, to: homeErcToErcContract.address, value: minPerTx @@ -293,8 +285,7 @@ async function testERC677BridgeToken(accounts, rewardable) { await token.setBridgeContract(foreignNativeToErcBridge.address).should.be.fulfilled; const result2 = await token.transfer(foreignNativeToErcBridge.address, minPerTx, {from: user}).should.be.fulfilled; - result2.logs[0].event.should.be.equal("Transfer") - result2.logs[0].args.should.be.deep.equal({ + expectEventInLogs(result2.logs, 'Transfer', { from: user, to: foreignNativeToErcBridge.address, value: minPerTx @@ -303,17 +294,15 @@ async function testERC677BridgeToken(accounts, rewardable) { it('sends tokens to contract that does not contains onTokenTransfer method', async () => { await token.setBridgeContract(homeErcToErcContract.address).should.be.fulfilled; - await token.mint(user, web3.toWei(1, "ether"), {from: owner }).should.be.fulfilled; + await token.mint(user, oneEther, {from: owner }).should.be.fulfilled; const result = await token.transfer(validatorContract.address, minPerTx, {from: user}).should.be.fulfilled; - result.logs[0].event.should.be.equal("Transfer") - result.logs[0].args.should.be.deep.equal({ + expectEventInLogs(result.logs, 'Transfer', { from: user, to: validatorContract.address, value: minPerTx }) - result.logs[1].event.should.be.equal("ContractFallbackCallFailed") - result.logs[1].args.should.be.deep.equal({ + expectEventInLogs(result.logs, 'ContractFallbackCallFailed', { from: user, to: validatorContract.address, value: minPerTx @@ -321,8 +310,8 @@ async function testERC677BridgeToken(accounts, rewardable) { }) it('fail to send tokens to bridge contract out of limits', async () => { - const lessThanMin = web3.toBigNumber(web3.toWei(0.0001, "ether")) - await token.mint(user, web3.toWei(1, "ether"), {from: owner }).should.be.fulfilled; + const lessThanMin = ether('0.0001') + await token.mint(user, oneEther, {from: owner }).should.be.fulfilled; await token.setBridgeContract(homeErcToErcContract.address).should.be.fulfilled; await token.transfer(homeErcToErcContract.address, lessThanMin, {from: user}).should.be.rejectedWith(ERROR_MSG); @@ -333,7 +322,7 @@ async function testERC677BridgeToken(accounts, rewardable) { if (rewardable) { it('fail to send tokens to Staking contract directly', async () => { - const amount = web3.toWei(1, "ether"); + const amount = ether('1'); const stakingContractAddress = accounts[2]; const arbitraryAccountAddress = accounts[3]; await token.setStakingContractMock(stakingContractAddress, {from: owner}).should.be.fulfilled; @@ -347,7 +336,7 @@ async function testERC677BridgeToken(accounts, rewardable) { if (rewardable) { describe('#transferFrom', async() => { it('fail to send tokens to Staking contract directly', async () => { - const amount = web3.toWei(1, "ether"); + const amount = ether('1'); const user2 = accounts[2]; const stakingContractAddress = accounts[3]; const arbitraryAccountAddress = accounts[4]; @@ -365,8 +354,8 @@ async function testERC677BridgeToken(accounts, rewardable) { await token.burn(100, {from: owner}).should.be.rejectedWith(ERROR_MSG); await token.mint(user, 1, {from: owner }).should.be.fulfilled; await token.burn(1, {from: user}).should.be.fulfilled; - (await token.totalSupply()).should.be.bignumber.equal(0); - (await token.balanceOf(user)).should.be.bignumber.equal(0); + expect(await token.totalSupply()).to.be.bignumber.equal(ZERO); + expect(await token.balanceOf(user)).to.be.bignumber.equal(ZERO); }) }) @@ -383,34 +372,30 @@ async function testERC677BridgeToken(accounts, rewardable) { }) it('calls contractFallback', async () => { const receiver = await ERC677ReceiverTest.new(); - (await receiver.from()).should.be.equal('0x0000000000000000000000000000000000000000'); - (await receiver.value()).should.be.bignumber.equal('0'); - (await receiver.data()).should.be.equal('0x'); - (await receiver.someVar()).should.be.bignumber.equal('0'); - - var ERC677ReceiverTestWeb3 = web3.eth.contract(ERC677ReceiverTest.abi); - var ERC677ReceiverTestWeb3Instance = ERC677ReceiverTestWeb3.at(receiver.address); - var callDoSomething123 = ERC677ReceiverTestWeb3Instance.doSomething.getData(123); - - await token.mint(user, 1, {from: owner }).should.be.fulfilled; - await token.transferAndCall(token.address, 1, callDoSomething123, {from: user}).should.be.rejectedWith(ERROR_MSG); - await token.transferAndCall('0x0000000000000000000000000000000000000000', 1, callDoSomething123, {from: user}).should.be.rejectedWith(ERROR_MSG); - await token.transferAndCall(receiver.address, 1, callDoSomething123, {from: user}).should.be.fulfilled; - (await token.balanceOf(receiver.address)).should.be.bignumber.equal(1); - (await token.balanceOf(user)).should.be.bignumber.equal(0); - (await receiver.from()).should.be.equal(user); - (await receiver.value()).should.be.bignumber.equal(1); - (await receiver.data()).should.be.equal(callDoSomething123); - (await receiver.someVar()).should.be.bignumber.equal('123'); + expect(await receiver.from()).to.be.equal(ZERO_ADDRESS); + expect(await receiver.value()).to.be.bignumber.equal(ZERO); + expect(await receiver.data()).to.be.equal(null); + expect(await receiver.someVar()).to.be.bignumber.equal(ZERO); + + const callDoSomething123 = receiver.contract.methods.doSomething(123).encodeABI() + await token.mint(user, '1', {from: owner }).should.be.fulfilled; + await token.transferAndCall(token.address, '1', callDoSomething123, {from: user}).should.be.rejectedWith(ERROR_MSG); + await token.transferAndCall(ZERO_ADDRESS, '1', callDoSomething123, {from: user}).should.be.rejectedWith(ERROR_MSG); + await token.transferAndCall(receiver.address, '1', callDoSomething123, {from: user}).should.be.fulfilled; + expect(await token.balanceOf(receiver.address)).to.be.bignumber.equal('1'); + expect(await token.balanceOf(user)).to.be.bignumber.equal(ZERO); + expect(await receiver.from()).to.be.equal(user); + expect(await receiver.value()).to.be.bignumber.equal('1'); + expect(await receiver.data()).to.be.equal(callDoSomething123); + expect(await receiver.someVar()).to.be.bignumber.equal('123'); }) it('sends tokens to bridge contract', async () => { await token.setBridgeContract(homeErcToErcContract.address).should.be.fulfilled; - await token.mint(user, web3.toWei(1, "ether"), {from: owner }).should.be.fulfilled; + await token.mint(user, oneEther, {from: owner }).should.be.fulfilled; const result = await token.transferAndCall(homeErcToErcContract.address, minPerTx, '0x', {from: user}).should.be.fulfilled; - result.logs[0].event.should.be.equal("Transfer") - result.logs[0].args.should.be.deep.equal({ + expectEventInLogs(result.logs, 'Transfer', { from: user, to: homeErcToErcContract.address, value: minPerTx @@ -418,8 +403,7 @@ async function testERC677BridgeToken(accounts, rewardable) { await token.setBridgeContract(foreignNativeToErcBridge.address).should.be.fulfilled; const result2 = await token.transferAndCall(foreignNativeToErcBridge.address, minPerTx, '0x', {from: user}).should.be.fulfilled; - result2.logs[0].event.should.be.equal("Transfer") - result2.logs[0].args.should.be.deep.equal({ + expectEventInLogs(result2.logs, 'Transfer', { from: user, to: foreignNativeToErcBridge.address, value: minPerTx @@ -428,14 +412,14 @@ async function testERC677BridgeToken(accounts, rewardable) { it('fail to sends tokens to contract that does not contains onTokenTransfer method', async () => { await token.setBridgeContract(homeErcToErcContract.address).should.be.fulfilled; - await token.mint(user, web3.toWei(1, "ether"), {from: owner }).should.be.fulfilled; + await token.mint(user, oneEther, {from: owner }).should.be.fulfilled; await token.transferAndCall(validatorContract.address, minPerTx, '0x', {from: user}).should.be.rejectedWith(ERROR_MSG); }) it('fail to send tokens to bridge contract out of limits', async () => { - const lessThanMin = web3.toBigNumber(web3.toWei(0.0001, "ether")) - await token.mint(user, web3.toWei(1, "ether"), {from: owner }).should.be.fulfilled; + const lessThanMin = ether('0.0001') + await token.mint(user, oneEther, {from: owner }).should.be.fulfilled; await token.setBridgeContract(homeErcToErcContract.address).should.be.fulfilled; await token.transferAndCall(homeErcToErcContract.address, lessThanMin, '0x', {from: user}).should.be.rejectedWith(ERROR_MSG); @@ -447,45 +431,45 @@ async function testERC677BridgeToken(accounts, rewardable) { describe('#claimtokens', async () => { it('can take send ERC20 tokens', async ()=> { const owner = accounts[0]; - const halfEther = web3.toBigNumber(web3.toWei(0.5, "ether")); + const halfEther = ether('0.5'); let tokenSecond = await tokenContract.new("Roman Token", "RST", 18); await tokenSecond.mint(accounts[0], halfEther).should.be.fulfilled; halfEther.should.be.bignumber.equal(await tokenSecond.balanceOf(accounts[0])) await tokenSecond.transfer(token.address, halfEther); - '0'.should.be.bignumber.equal(await tokenSecond.balanceOf(accounts[0])) - halfEther.should.be.bignumber.equal(await tokenSecond.balanceOf(token.address)) + expect(await tokenSecond.balanceOf(accounts[0])).to.be.bignumber.equal(ZERO) + expect(await tokenSecond.balanceOf(token.address)).to.be.bignumber.equal(halfEther) await token.claimTokens(tokenSecond.address, accounts[3], {from: owner}); - '0'.should.be.bignumber.equal(await tokenSecond.balanceOf(token.address)) + expect(await tokenSecond.balanceOf(token.address)).to.be.bignumber.equal(ZERO) halfEther.should.be.bignumber.equal(await tokenSecond.balanceOf(accounts[3])) }) }) describe('#transfer', async () => { it('if transfer called on contract, onTokenTransfer is also invoked', async () => { const receiver = await ERC677ReceiverTest.new(); - (await receiver.from()).should.be.equal('0x0000000000000000000000000000000000000000'); - (await receiver.value()).should.be.bignumber.equal('0'); - (await receiver.data()).should.be.equal('0x'); - (await receiver.someVar()).should.be.bignumber.equal('0'); + expect(await receiver.from()).to.be.equal(ZERO_ADDRESS); + expect(await receiver.value()).to.be.bignumber.equal(ZERO); + expect(await receiver.data()).to.be.equal(null); + expect(await receiver.someVar()).to.be.bignumber.equal(ZERO); await token.mint(user, 1, {from: owner }).should.be.fulfilled; - const {logs} = await token.transfer(receiver.address, 1, {from: user}).should.be.fulfilled; - - (await token.balanceOf(receiver.address)).should.be.bignumber.equal(1); - (await token.balanceOf(user)).should.be.bignumber.equal(0); - (await receiver.from()).should.be.equal(user); - (await receiver.value()).should.be.bignumber.equal(1); - (await receiver.data()).should.be.equal('0x'); - logs[0].event.should.be.equal("Transfer") + const {logs} = await token.transfer(receiver.address, '1', {from: user}).should.be.fulfilled; + + expect(await token.balanceOf(receiver.address)).to.be.bignumber.equal('1'); + expect(await token.balanceOf(user)).to.be.bignumber.equal(ZERO); + expect(await receiver.from()).to.be.equal(user); + expect(await receiver.value()).to.be.bignumber.equal('1'); + expect(await receiver.data()).to.be.equal(null); + expect(logs[0].event).to.be.equal("Transfer") }) it('if transfer called on contract, still works even if onTokenTransfer doesnot exist', async () => { const someContract = await tokenContract.new("Some", "Token", 18); - await token.mint(user, 2, {from: owner }).should.be.fulfilled; - const tokenTransfer = await token.transfer(someContract.address, 1, {from: user}).should.be.fulfilled; - const tokenTransfer2 = await token.transfer(accounts[0], 1, {from: user}).should.be.fulfilled; - (await token.balanceOf(someContract.address)).should.be.bignumber.equal(1); - (await token.balanceOf(user)).should.be.bignumber.equal(0); + await token.mint(user, '2', {from: owner }).should.be.fulfilled; + const tokenTransfer = await token.transfer(someContract.address, '1', {from: user}).should.be.fulfilled; + const tokenTransfer2 = await token.transfer(accounts[0], '1', {from: user}).should.be.fulfilled; + expect(await token.balanceOf(someContract.address)).to.be.bignumber.equal('1'); + expect(await token.balanceOf(user)).to.be.bignumber.equal(ZERO); tokenTransfer.logs[0].event.should.be.equal("Transfer") tokenTransfer2.logs[0].event.should.be.equal("Transfer") }) diff --git a/test/rewardable_validators_test.js b/test/rewardable_validators_test.js index 27b505e02..dc85778dc 100644 --- a/test/rewardable_validators_test.js +++ b/test/rewardable_validators_test.js @@ -1,6 +1,11 @@ const BridgeValidators = artifacts.require("RewardableValidators.sol"); const EternalStorageProxy = artifacts.require("EternalStorageProxy.sol"); -const { ERROR_MSG, ZERO_ADDRESS, F_ADDRESS } = require('./setup'); + +const { ERROR_MSG, ZERO_ADDRESS, F_ADDRESS, BN } = require('./setup'); +const { expectEventInLogs } = require('./helpers/helpers'); +const { expect } = require('chai'); + +const ZERO = new BN(0) contract('RewardableValidators', async (accounts) => { let bridgeValidators @@ -12,30 +17,32 @@ contract('RewardableValidators', async (accounts) => { describe('#initialize', async () => { it('sets values', async () => { - '0x0000000000000000000000000000000000000000'.should.be.equal(await bridgeValidators.owner()) - '0'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) - false.should.be.equal(await bridgeValidators.isValidator(accounts[0])) - false.should.be.equal(await bridgeValidators.isValidator(accounts[1])) - false.should.be.equal(await bridgeValidators.isInitialized()) - '0'.should.be.bignumber.equal(await bridgeValidators.requiredSignatures()) - '0'.should.be.bignumber.equal(await bridgeValidators.deployedAtBlock()) + expect(await bridgeValidators.owner()).to.be.equal(ZERO_ADDRESS) + expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal(ZERO) + expect(await bridgeValidators.isValidator(accounts[0])).to.be.equal(false) + expect(await bridgeValidators.isValidator(accounts[1])).to.be.equal(false) + expect(await bridgeValidators.isInitialized()).to.be.equal(false) + expect(await bridgeValidators.requiredSignatures()).to.be.bignumber.equal(ZERO) + expect(await bridgeValidators.deployedAtBlock()).to.be.bignumber.equal(ZERO) + await bridgeValidators.initialize(3, accounts.slice(0, 3), accounts.slice(3, 5), accounts[2], {from: accounts[2]}).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.initialize(1, [accounts[0]], [ZERO_ADDRESS], accounts[1], { from: accounts[1] }).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.initialize(1, [ZERO_ADDRESS], [accounts[0]], accounts[1], { from: accounts[1] }).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.initialize(1, [F_ADDRESS], [accounts[0]], accounts[1], { from: accounts[1] }).should.be.rejectedWith(ERROR_MSG) await bridgeValidators.initialize(2, accounts.slice(0, 2), accounts.slice(2, 4), accounts[2], {from: accounts[2]}).should.be.fulfilled; await bridgeValidators.initialize(2, accounts.slice(0, 2), accounts.slice(2, 4), accounts[2], {from: accounts[2]}).should.be.rejectedWith(ERROR_MSG); - await bridgeValidators.initialize(1, [accounts[0]], [ZERO_ADDRESS], [accounts[1]], { from: accounts[1] }).should.be.rejectedWith(ERROR_MSG) - await bridgeValidators.initialize(1, [ZERO_ADDRESS], [accounts[0]], [accounts[1]], { from: accounts[1] }).should.be.rejectedWith(ERROR_MSG) - await bridgeValidators.initialize(1, [F_ADDRESS], [accounts[0]], [accounts[1]], { from: accounts[1] }).should.be.rejectedWith(ERROR_MSG) - true.should.be.equal(await bridgeValidators.isInitialized()) - '2'.should.be.bignumber.equal(await bridgeValidators.requiredSignatures()) - true.should.be.equal(await bridgeValidators.isValidator(accounts[0])) - true.should.be.equal(await bridgeValidators.isValidator(accounts[1])) - accounts[2].should.be.equal(await bridgeValidators.owner()) - '2'.should.be.bignumber.equal(await bridgeValidators.validatorCount()); - (await bridgeValidators.deployedAtBlock()).should.be.bignumber.above(0) - const [major, minor, patch] = await bridgeValidators.getBridgeValidatorsInterfacesVersion() - major.should.be.bignumber.gte(0) - minor.should.be.bignumber.gte(0) - patch.should.be.bignumber.gte(0) + + expect(await bridgeValidators.isInitialized()).to.be.equal(true) + expect(await bridgeValidators.requiredSignatures()).to.be.bignumber.equal('2') + expect(await bridgeValidators.isValidator(accounts[0])).to.be.equal(true) + expect(await bridgeValidators.isValidator(accounts[1])).to.be.equal(true) + expect(await bridgeValidators.owner()).to.be.equal(accounts[2]) + expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('2') + expect(await bridgeValidators.deployedAtBlock()).to.be.bignumber.above(ZERO) + const { major, minor, patch } = await bridgeValidators.getBridgeValidatorsInterfacesVersion() + expect(major).to.be.bignumber.gte(ZERO) + expect(minor).to.be.bignumber.gte(ZERO) + expect(patch).to.be.bignumber.gte(ZERO) }) }) @@ -46,7 +53,7 @@ contract('RewardableValidators', async (accounts) => { let requiredSignatures = 2; beforeEach(async () => { await bridgeValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled - '2'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) + expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('2') }) it('adds validator', async () => { let newValidator = accounts[4]; @@ -55,19 +62,18 @@ contract('RewardableValidators', async (accounts) => { false.should.be.equal(await bridgeValidators.isValidator(newValidator)) await bridgeValidators.addRewardableValidator(newValidator, newReward, {from: validators[0]}).should.be.rejectedWith(ERROR_MSG) const {logs} = await bridgeValidators.addRewardableValidator(newValidator, newReward, {from: owner}).should.be.fulfilled - true.should.be.equal(await bridgeValidators.isValidator(newValidator)) - '3'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) - logs[0].event.should.be.equal('ValidatorAdded') - logs[0].args.should.be.deep.equal({ validator: newValidator }) + expect(await bridgeValidators.isValidator(newValidator)).to.be.equal(true) + expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('3') + expectEventInLogs(logs, 'ValidatorAdded', { validator: newValidator }) const rewardAddress = await bridgeValidators.getValidatorRewardAddress(newValidator) - rewardAddress.should.be.equal(newReward) + expect(rewardAddress).to.be.equal(newReward) }) it('cannot add already existing validator', async () => { true.should.be.equal(await bridgeValidators.isValidator(validators[0])) await bridgeValidators.addRewardableValidator(validators[0], rewards[0], {from: owner}).should.be.rejectedWith(ERROR_MSG) - '2'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) + expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('2') }) it(`cannot add 0xf as validator address`, async () => { @@ -91,18 +97,17 @@ contract('RewardableValidators', async (accounts) => { let requiredSignatures = 2; beforeEach(async () => { await bridgeValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled - '3'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) + expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('3') }) it('removes validator', async () => { let toRemove = validators[0]; - true.should.be.equal(await bridgeValidators.isValidator(toRemove)) + expect(await bridgeValidators.isValidator(toRemove)).to.be.equal(true) await bridgeValidators.removeValidator(toRemove, {from: validators[0]}).should.be.rejectedWith(ERROR_MSG) const {logs} = await bridgeValidators.removeValidator(toRemove, {from: owner}).should.be.fulfilled - false.should.be.equal(await bridgeValidators.isValidator(toRemove)) - '2'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) - logs[0].event.should.be.equal('ValidatorRemoved') - logs[0].args.should.be.deep.equal({validator: toRemove}) + expect(await bridgeValidators.isValidator(toRemove)).to.be.equal(false) + expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('2') + expectEventInLogs(logs, 'ValidatorRemoved', { validator: toRemove }) }) it('cannot remove if it will break requiredSignatures', async () => { @@ -114,14 +119,14 @@ contract('RewardableValidators', async (accounts) => { await bridgeValidators.removeValidator(toRemove2, {from: owner}).should.be.rejectedWith(ERROR_MSG) false.should.be.equal(await bridgeValidators.isValidator(toRemove)) true.should.be.equal(await bridgeValidators.isValidator(toRemove2)) - '2'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) + expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('2') }) it('cannot remove non-existent validator', async () => { false.should.be.equal(await bridgeValidators.isValidator(accounts[4])) await bridgeValidators.removeValidator(accounts[4], {from: owner}).should.be.rejectedWith(ERROR_MSG) await bridgeValidators.removeValidator(ZERO_ADDRESS, {from: owner}).should.be.rejectedWith(ERROR_MSG) - '3'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) + expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('3') }) }) @@ -129,44 +134,44 @@ contract('RewardableValidators', async (accounts) => { let owner = accounts[2]; let validators = [accounts[0], accounts[1], accounts[3]]; let rewards = accounts.slice(4, 7) - let requiredSignatures = 2; + let requiredSignatures = '2'; beforeEach(async () => { await bridgeValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled - '3'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) + expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('3') }) it('sets req signatures', async () => { - let newReqSig = 3; - requiredSignatures.should.be.bignumber.equal(await bridgeValidators.requiredSignatures()); + let newReqSig = '3'; + expect(await bridgeValidators.requiredSignatures()).to.be.bignumber.equal(requiredSignatures) await bridgeValidators.setRequiredSignatures(newReqSig, {from: validators[0]}).should.be.rejectedWith(ERROR_MSG) await bridgeValidators.setRequiredSignatures(newReqSig, {from: owner}).should.be.fulfilled - newReqSig.should.be.bignumber.equal(await bridgeValidators.requiredSignatures()); + expect(await bridgeValidators.requiredSignatures()).to.be.bignumber.equal(newReqSig) }) it('cannot set more than validators count', async () => { - let newReqSig = 4; - requiredSignatures.should.be.bignumber.equal(await bridgeValidators.requiredSignatures()); + let newReqSig = '4'; + expect(await bridgeValidators.requiredSignatures()).to.be.bignumber.equal(requiredSignatures) await bridgeValidators.setRequiredSignatures(newReqSig, {from: owner}).should.be.rejectedWith(ERROR_MSG) - requiredSignatures.should.be.bignumber.equal(await bridgeValidators.requiredSignatures()); + expect(await bridgeValidators.requiredSignatures()).to.be.bignumber.equal(requiredSignatures) }) }) describe('#upgradable', async () => { it('can be upgraded via upgradeToAndCall', async () => { let storageProxy = await EternalStorageProxy.new().should.be.fulfilled; - let required_signatures = 2; + let required_signatures = '2'; let validators = [accounts[0], accounts[1]]; let rewards = accounts.slice(3, 5); let owner = accounts[2] - let data = bridgeValidators.initialize.request(required_signatures, validators, rewards, owner).params[0].data + const data = bridgeValidators.contract.methods.initialize(required_signatures, validators,rewards, owner).encodeABI() await storageProxy.upgradeToAndCall('1', bridgeValidators.address, data).should.be.fulfilled; let finalContract = await BridgeValidators.at(storageProxy.address); true.should.be.equal(await finalContract.isInitialized()); - required_signatures.should.be.bignumber.equal(await finalContract.requiredSignatures()) + expect(await finalContract.requiredSignatures()).to.be.bignumber.equal(required_signatures) true.should.be.equal(await finalContract.isValidator(validators[0])) true.should.be.equal(await finalContract.isValidator(validators[1])) owner.should.be.equal(await finalContract.owner()) - validators.length.should.be.bignumber.equal(await finalContract.validatorCount()) + expect(await finalContract.validatorCount()).to.be.bignumber.equal(validators.length.toString()) }) }) @@ -181,8 +186,7 @@ contract('RewardableValidators', async (accounts) => { const { logs } = await removeValidator(accounts[0], { from: owner }).should.be.fulfilled // Then - logs[0].event.should.be.equal('ValidatorRemoved') - logs[0].args.should.be.deep.equal({ validator: accounts[0] }) + expectEventInLogs(logs, 'ValidatorRemoved', { validator: accounts[0] }) }) it(`Removed validator should return zero address on nextValidator`, async () => { @@ -196,8 +200,7 @@ contract('RewardableValidators', async (accounts) => { const { logs } = await removeValidator(accounts[0], { from: owner }).should.be.fulfilled // Then - logs[0].event.should.be.equal('ValidatorRemoved') - logs[0].args.should.be.deep.equal({ validator: accounts[0] }) + expectEventInLogs(logs, 'ValidatorRemoved', { validator: accounts[0] }) const updatedNextValidator = await getNextValidator(accounts[0]) @@ -211,7 +214,7 @@ contract('RewardableValidators', async (accounts) => { const proxy = await EternalStorageProxy.new() const bridgeValidatorsImpl = await BridgeValidators.new() await proxy.upgradeTo('1', bridgeValidatorsImpl.address) - bridgeValidators = BridgeValidators.at(proxy.address) + bridgeValidators = await BridgeValidators.at(proxy.address) const { initialize, isInitialized, removeValidator } = bridgeValidators await initialize( 1, @@ -229,8 +232,7 @@ contract('RewardableValidators', async (accounts) => { ).should.be.fulfilled // Then - logs[0].event.should.be.equal('ValidatorRemoved') - logs[0].args.should.be.deep.equal({ validator }) + expectEventInLogs(logs, 'ValidatorRemoved', { validator }) }) }) }) @@ -242,12 +244,12 @@ contract('RewardableValidators', async (accounts) => { await initialize(1, accounts.slice(0, 5), accounts.slice(5), owner, { from: owner }).should.be.fulfilled // When - true.should.be.equal(await isInitialized()) + expect(await isInitialized()).to.be.equal(true) // Then for (let i = 0; i < accounts.slice(0, 5).length; i++) { const validator = accounts[i] - accounts[i + 5].should.be.equal(await getValidatorRewardAddress(validator)) + expect(await getValidatorRewardAddress(validator)).to.be.equal(accounts[i + 5]) } }) }) @@ -256,13 +258,12 @@ contract('RewardableValidators', async (accounts) => { // Given const validators = accounts.slice(0, 5) const { initialize, validatorList } = bridgeValidators - await initialize(1, validators, accounts.slice(5), owner, { from: owner }).should.be.fulfilled // When - const returnedList = await validatorList() + await initialize(1, validators, accounts.slice(5), owner, { from: owner }).should.be.fulfilled // Then - returnedList.should.be.eql(validators) + expect(await validatorList()).to.be.eql(validators) }) }) }) diff --git a/test/setup.js b/test/setup.js index 3ede476e6..c770d7918 100644 --- a/test/setup.js +++ b/test/setup.js @@ -7,6 +7,7 @@ require('chai') require('chai/register-should'); exports.BN = BN +exports.toBN = web3.utils.toBN exports.ERROR_MSG = 'VM Exception while processing transaction: revert'; exports.ERROR_MSG_OPCODE = 'VM Exception while processing transaction: invalid opcode'; exports.ZERO_ADDRESS = '0x0000000000000000000000000000000000000000' diff --git a/test/validators_test.js b/test/validators_test.js index e2d7517eb..50628d641 100644 --- a/test/validators_test.js +++ b/test/validators_test.js @@ -1,6 +1,11 @@ const BridgeValidators = artifacts.require("BridgeValidators.sol"); const EternalStorageProxy = artifacts.require("EternalStorageProxy.sol"); -const { ERROR_MSG, ZERO_ADDRESS, F_ADDRESS } = require('./setup'); + +const { ERROR_MSG, ZERO_ADDRESS, F_ADDRESS, BN } = require('./setup'); +const { expectEventInLogs } = require('./helpers/helpers'); +const { expect } = require('chai'); + +const ZERO = new BN(0) contract('BridgeValidators', async (accounts) => { let bridgeValidators @@ -12,28 +17,30 @@ contract('BridgeValidators', async (accounts) => { describe('#initialize', async () => { it('sets values', async () => { - '0x0000000000000000000000000000000000000000'.should.be.equal(await bridgeValidators.owner()) - '0'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) - false.should.be.equal(await bridgeValidators.isValidator(accounts[0])) - false.should.be.equal(await bridgeValidators.isValidator(accounts[1])) - false.should.be.equal(await bridgeValidators.isInitialized()) - '0'.should.be.bignumber.equal(await bridgeValidators.requiredSignatures()) - '0'.should.be.bignumber.equal(await bridgeValidators.deployedAtBlock()) - await bridgeValidators.initialize(1, [ZERO_ADDRESS], [accounts[1]], { from: accounts[1] }).should.be.rejectedWith(ERROR_MSG) - await bridgeValidators.initialize(1, [F_ADDRESS], [accounts[1]], { from: accounts[1] }).should.be.rejectedWith(ERROR_MSG) + expect(await bridgeValidators.owner()).to.be.equal(ZERO_ADDRESS) + expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal(ZERO) + expect(await bridgeValidators.isValidator(accounts[0])).to.be.equal(false) + expect(await bridgeValidators.isValidator(accounts[1])).to.be.equal(false) + expect(await bridgeValidators.isInitialized()).to.be.equal(false) + expect(await bridgeValidators.requiredSignatures()).to.be.bignumber.equal(ZERO) + expect(await bridgeValidators.deployedAtBlock()).to.be.bignumber.equal(ZERO) + + await bridgeValidators.initialize(1, [ZERO_ADDRESS], accounts[1], { from: accounts[1] }).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.initialize(1, [F_ADDRESS], accounts[1], { from: accounts[1] }).should.be.rejectedWith(ERROR_MSG) await bridgeValidators.initialize(2, accounts.slice(0, 2), accounts[2], {from: accounts[2]}).should.be.fulfilled; - await bridgeValidators.initialize(2, accounts.slice(0, 2), accounts[2], {from: accounts[2]}).should.be.rejectedWith(ERROR_MSG); - true.should.be.equal(await bridgeValidators.isInitialized()) - '2'.should.be.bignumber.equal(await bridgeValidators.requiredSignatures()) - true.should.be.equal(await bridgeValidators.isValidator(accounts[0])) - true.should.be.equal(await bridgeValidators.isValidator(accounts[1])) - accounts[2].should.be.equal(await bridgeValidators.owner()) - '2'.should.be.bignumber.equal(await bridgeValidators.validatorCount()); - (await bridgeValidators.deployedAtBlock()).should.be.bignumber.above(0) - const [major, minor, patch] = await bridgeValidators.getBridgeValidatorsInterfacesVersion() - major.should.be.bignumber.gte(0) - minor.should.be.bignumber.gte(0) - patch.should.be.bignumber.gte(0) + await bridgeValidators.initialize(2, accounts.slice(0, 2), accounts[2], {from: accounts[2]}).should.be.rejectedWith(ERROR_MSG) + + expect(await bridgeValidators.isInitialized()).to.be.equal(true) + expect(await bridgeValidators.requiredSignatures()).to.be.bignumber.equal('2') + expect(await bridgeValidators.isValidator(accounts[0])).to.be.equal(true) + expect(await bridgeValidators.isValidator(accounts[1])).to.be.equal(true) + expect(await bridgeValidators.owner()).to.be.equal(accounts[2]) + expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('2') + expect(await bridgeValidators.deployedAtBlock()).to.be.bignumber.above(ZERO) + const { major, minor, patch } = await bridgeValidators.getBridgeValidatorsInterfacesVersion() + expect(major).to.be.bignumber.gte(ZERO) + expect(minor).to.be.bignumber.gte(ZERO) + expect(patch).to.be.bignumber.gte(ZERO) }) }) @@ -43,7 +50,7 @@ contract('BridgeValidators', async (accounts) => { let requiredSignatures = 2; beforeEach(async () => { await bridgeValidators.initialize(requiredSignatures, validators, owner, {from: owner}).should.be.fulfilled - '2'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) + expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('2') }) it('adds validator', async () => { let newValidator = accounts[4]; @@ -51,16 +58,15 @@ contract('BridgeValidators', async (accounts) => { false.should.be.equal(await bridgeValidators.isValidator(newValidator)) await bridgeValidators.addValidator(newValidator, {from: validators[0]}).should.be.rejectedWith(ERROR_MSG) const {logs} = await bridgeValidators.addValidator(newValidator, {from: owner}).should.be.fulfilled - true.should.be.equal(await bridgeValidators.isValidator(newValidator)) - '3'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) - logs[0].event.should.be.equal('ValidatorAdded') - logs[0].args.should.be.deep.equal({validator: newValidator}) + expect(await bridgeValidators.isValidator(newValidator)).to.be.equal(true) + expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('3') + expectEventInLogs(logs, 'ValidatorAdded', { validator: newValidator }) }) it('cannot add already existing validator', async () => { true.should.be.equal(await bridgeValidators.isValidator(validators[0])) await bridgeValidators.addValidator(validators[0], {from: owner}).should.be.rejectedWith(ERROR_MSG) - '2'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) + expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('2') }) it(`cannot add 0xf as validator address`, async () => { @@ -79,18 +85,17 @@ contract('BridgeValidators', async (accounts) => { let requiredSignatures = 2; beforeEach(async () => { await bridgeValidators.initialize(requiredSignatures, validators, owner, {from: owner}).should.be.fulfilled - '3'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) + expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('3') }) it('removes validator', async () => { let toRemove = validators[0]; - true.should.be.equal(await bridgeValidators.isValidator(toRemove)) + expect(await bridgeValidators.isValidator(toRemove)).to.be.equal(true) await bridgeValidators.removeValidator(toRemove, {from: validators[0]}).should.be.rejectedWith(ERROR_MSG) const {logs} = await bridgeValidators.removeValidator(toRemove, {from: owner}).should.be.fulfilled - false.should.be.equal(await bridgeValidators.isValidator(toRemove)) - '2'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) - logs[0].event.should.be.equal('ValidatorRemoved') - logs[0].args.should.be.deep.equal({validator: toRemove}) + expect(await bridgeValidators.isValidator(toRemove)).to.be.equal(false) + expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('2') + expectEventInLogs(logs, 'ValidatorRemoved', { validator: toRemove }) }) it('cannot remove if it will break requiredSignatures', async () => { @@ -102,57 +107,57 @@ contract('BridgeValidators', async (accounts) => { await bridgeValidators.removeValidator(toRemove2, {from: owner}).should.be.rejectedWith(ERROR_MSG) false.should.be.equal(await bridgeValidators.isValidator(toRemove)) true.should.be.equal(await bridgeValidators.isValidator(toRemove2)) - '2'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) + expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('2') }) it('cannot remove non-existent validator', async () => { false.should.be.equal(await bridgeValidators.isValidator(accounts[4])) await bridgeValidators.removeValidator(accounts[4], {from: owner}).should.be.rejectedWith(ERROR_MSG) await bridgeValidators.removeValidator(ZERO_ADDRESS, {from: owner}).should.be.rejectedWith(ERROR_MSG) - '3'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) + expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('3') }) }) describe('#setRequiredSignatures', async () => { let owner = accounts[2]; let validators = [accounts[0], accounts[1], accounts[3]]; - let requiredSignatures = 2; + let requiredSignatures = '2'; beforeEach(async () => { await bridgeValidators.initialize(requiredSignatures, validators, owner, {from: owner}).should.be.fulfilled - '3'.should.be.bignumber.equal(await bridgeValidators.validatorCount()) + expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('3') }) it('sets req signatures', async () => { - let newReqSig = 3; - requiredSignatures.should.be.bignumber.equal(await bridgeValidators.requiredSignatures()); + let newReqSig = '3'; + expect(await bridgeValidators.requiredSignatures()).to.be.bignumber.equal(requiredSignatures) await bridgeValidators.setRequiredSignatures(newReqSig, {from: validators[0]}).should.be.rejectedWith(ERROR_MSG) await bridgeValidators.setRequiredSignatures(newReqSig, {from: owner}).should.be.fulfilled - newReqSig.should.be.bignumber.equal(await bridgeValidators.requiredSignatures()); + expect(await bridgeValidators.requiredSignatures()).to.be.bignumber.equal(newReqSig) }) it('cannot set more than validators count', async () => { - let newReqSig = 4; - requiredSignatures.should.be.bignumber.equal(await bridgeValidators.requiredSignatures()); + let newReqSig = '4'; + expect(await bridgeValidators.requiredSignatures()).to.be.bignumber.equal(requiredSignatures) await bridgeValidators.setRequiredSignatures(newReqSig, {from: owner}).should.be.rejectedWith(ERROR_MSG) - requiredSignatures.should.be.bignumber.equal(await bridgeValidators.requiredSignatures()); + expect(await bridgeValidators.requiredSignatures()).to.be.bignumber.equal(requiredSignatures) }) }) describe('#upgradable', async () => { it('can be upgraded via upgradeToAndCall', async () => { let storageProxy = await EternalStorageProxy.new().should.be.fulfilled; - let required_signatures = 2; + let required_signatures = '2'; let validators = [accounts[0], accounts[1]]; let owner = accounts[2] - let data = bridgeValidators.initialize.request(required_signatures, validators, owner).params[0].data + const data = bridgeValidators.contract.methods.initialize(required_signatures, validators, owner).encodeABI() await storageProxy.upgradeToAndCall('1', bridgeValidators.address, data).should.be.fulfilled; let finalContract = await BridgeValidators.at(storageProxy.address); true.should.be.equal(await finalContract.isInitialized()); - required_signatures.should.be.bignumber.equal(await finalContract.requiredSignatures()) + expect(await finalContract.requiredSignatures()).to.be.bignumber.equal(required_signatures) true.should.be.equal(await finalContract.isValidator(validators[0])) true.should.be.equal(await finalContract.isValidator(validators[1])) owner.should.be.equal(await finalContract.owner()) - validators.length.should.be.bignumber.equal(await finalContract.validatorCount()) + expect(await finalContract.validatorCount()).to.be.bignumber.equal(validators.length.toString()) }) }) @@ -167,8 +172,7 @@ contract('BridgeValidators', async (accounts) => { const { logs } = await removeValidator(accounts[0], { from: owner }).should.be.fulfilled // Then - logs[0].event.should.be.equal('ValidatorRemoved') - logs[0].args.should.be.deep.equal({ validator: accounts[0] }) + expectEventInLogs(logs, 'ValidatorRemoved', { validator: accounts[0] }) }) it(`Removed validator should return zero address on nextValidator`, async () => { @@ -182,8 +186,7 @@ contract('BridgeValidators', async (accounts) => { const { logs } = await removeValidator(accounts[0], { from: owner }).should.be.fulfilled // Then - logs[0].event.should.be.equal('ValidatorRemoved') - logs[0].args.should.be.deep.equal({ validator: accounts[0] }) + expectEventInLogs(logs, 'ValidatorRemoved', { validator: accounts[0] }) const updatedNextValidator = await getNextValidator(accounts[0]) @@ -197,7 +200,7 @@ contract('BridgeValidators', async (accounts) => { const proxy = await EternalStorageProxy.new() const bridgeValidatorsImpl = await BridgeValidators.new() await proxy.upgradeTo('1', bridgeValidatorsImpl.address) - bridgeValidators = BridgeValidators.at(proxy.address) + bridgeValidators = await BridgeValidators.at(proxy.address) const { initialize, isInitialized, removeValidator } = bridgeValidators await initialize( 1, @@ -214,8 +217,7 @@ contract('BridgeValidators', async (accounts) => { ).should.be.fulfilled // Then - logs[0].event.should.be.equal('ValidatorRemoved') - logs[0].args.should.be.deep.equal({ validator }) + expectEventInLogs(logs, 'ValidatorRemoved', { validator }) }) }) }) From 34d48efad70411ae8e0e79ff2064ff48268bd1c5 Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 14 May 2019 12:36:34 -0300 Subject: [PATCH 185/187] Add linter for unit tests --- .eslintignore | 2 + .eslintrc | 27 + .prettierrc | 5 + .travis.yml | 1 + package-lock.json | 1036 ++++++++++++- package.json | 9 + test/erc_to_erc/foreign_bridge.test.js | 603 +++++--- test/erc_to_erc/home_bridge.test.js | 1214 +++++++++++---- test/erc_to_native/foreign_bridge.test.js | 441 ++++-- test/erc_to_native/home_bridge.test.js | 1655 +++++++++++++++------ test/helpers/helpers.js | 168 +-- test/native_to_erc/foreign_bridge_test.js | 1072 +++++++++---- test/native_to_erc/home_bridge_test.js | 1234 +++++++++++---- test/poa20_test.js | 594 ++++---- test/rewardable_validators_test.js | 171 ++- test/setup.js | 8 +- test/validators_test.js | 122 +- truffle-config.js | 27 +- 18 files changed, 6141 insertions(+), 2248 deletions(-) create mode 100644 .eslintignore create mode 100644 .eslintrc create mode 100644 .prettierrc diff --git a/.eslintignore b/.eslintignore new file mode 100644 index 000000000..4b4280a4c --- /dev/null +++ b/.eslintignore @@ -0,0 +1,2 @@ +node_modules +deploy diff --git a/.eslintrc b/.eslintrc new file mode 100644 index 000000000..8d19e2f80 --- /dev/null +++ b/.eslintrc @@ -0,0 +1,27 @@ +{ + "extends": [ + "plugin:node/recommended", + "airbnb-base", + "plugin:prettier/recommended" + ], + "plugins": ["node"], + "env": { + "node" : true, + "mocha" : true + }, + "globals" : { + "artifacts": false, + "contract": false, + "assert": false, + "web3": false + }, + "rules": { + "no-plusplus": "off", + "no-await-in-loop": "off", + "no-shadow": "off", + "prefer-destructuring": "off", + "no-use-before-define": ["error", { "functions": false }], + "no-restricted-syntax": "off", + "node/no-unpublished-require": "off" + } +} diff --git a/.prettierrc b/.prettierrc new file mode 100644 index 000000000..31ba22d84 --- /dev/null +++ b/.prettierrc @@ -0,0 +1,5 @@ +{ + "semi": false, + "singleQuote": true, + "printWidth": 120 +} diff --git a/.travis.yml b/.travis.yml index 77ff5d04b..a90db0b6c 100644 --- a/.travis.yml +++ b/.travis.yml @@ -14,4 +14,5 @@ matrix: allow_failures: - env: SOLIDITY_COVERAGE=true script: + - yarn lint:js - yarn test diff --git a/package-lock.json b/package-lock.json index fdb49d629..c48820c95 100644 --- a/package-lock.json +++ b/package-lock.json @@ -4,6 +4,26 @@ "lockfileVersion": 1, "requires": true, "dependencies": { + "@babel/code-frame": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/@babel/code-frame/-/code-frame-7.0.0.tgz", + "integrity": "sha512-OfC2uemaknXr87bdLUkWog7nYuliM9Ij5HUcajsVcMCpQrcLmtxRbVFTIqmcSkSeYRBFBRxs2FiUqFJDLdiebA==", + "dev": true, + "requires": { + "@babel/highlight": "^7.0.0" + } + }, + "@babel/highlight": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/@babel/highlight/-/highlight-7.0.0.tgz", + "integrity": "sha512-UFMC4ZeFC48Tpvj7C8UgLvtkaUuovQX+5xNWrsIoMG8o2z+XFKjKaN9iVmS84dPwVN00W4wPmqvYoZF3EGAsfw==", + "dev": true, + "requires": { + "chalk": "^2.0.0", + "esutils": "^2.0.2", + "js-tokens": "^4.0.0" + } + }, "@resolver-engine/core": { "version": "0.2.1", "resolved": "https://registry.npmjs.org/@resolver-engine/core/-/core-0.2.1.tgz", @@ -91,6 +111,18 @@ "web3": "^0.18.4" } }, + "acorn": { + "version": "6.1.1", + "resolved": "https://registry.npmjs.org/acorn/-/acorn-6.1.1.tgz", + "integrity": "sha512-jPTiwtOxaHNaAPg/dmrJ/beuzLRnXtB0kQPQ8JpotKJgTB6rX6c8mlf315941pyjBSaPg8NHXS9fhP4u17DpGA==", + "dev": true + }, + "acorn-jsx": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-5.0.1.tgz", + "integrity": "sha512-HJ7CfNHrfJLlNTzIEUTj43LNWGkqpRLxm3YjAlcD0ACydk9XynzYsCBHxut+iqt+1aBXkx9UP/w/ZqMr13XIzg==", + "dev": true + }, "ajv": { "version": "6.10.0", "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.10.0.tgz", @@ -152,6 +184,12 @@ } } }, + "ansi-escapes": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-3.2.0.tgz", + "integrity": "sha512-cBhpre4ma+U0T1oM5fXg7Dy1Jw7zzwv7lt/GoCpr+hDQJoYnKVPLL4dCvSEFMmQurOQvSrwT7SL/DAlhBI97RQ==", + "dev": true + }, "ansi-regex": { "version": "2.1.1", "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz", @@ -219,6 +257,16 @@ "integrity": "sha1-45sJrqne+Gao8gbiiK9jkZuuOcQ=", "dev": true }, + "array-includes": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/array-includes/-/array-includes-3.0.3.tgz", + "integrity": "sha1-GEtI9i2S10UrsxsyMWXH+L0CJm0=", + "dev": true, + "requires": { + "define-properties": "^1.1.2", + "es-abstract": "^1.7.0" + } + }, "array-unique": { "version": "0.3.2", "resolved": "https://registry.npmjs.org/array-unique/-/array-unique-0.3.2.tgz", @@ -258,6 +306,12 @@ "integrity": "sha1-WWZ/QfrdTyDMvCu5a41Pf3jsA2c=", "dev": true }, + "astral-regex": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/astral-regex/-/astral-regex-1.0.0.tgz", + "integrity": "sha512-+Ryf6g3BKoRc7jfp7ad8tM4TtMiaWvbF/1/sQcZPkkS7ag3D5nMBCe2UfOTONtAkaG0tO0ij3C5Lwmf1EiyjHg==", + "dev": true + }, "async": { "version": "1.5.2", "resolved": "https://registry.npmjs.org/async/-/async-1.5.2.tgz", @@ -512,6 +566,12 @@ "unset-value": "^1.0.0" } }, + "callsites": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/callsites/-/callsites-3.1.0.tgz", + "integrity": "sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==", + "dev": true + }, "camelcase": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-3.0.0.tgz", @@ -587,6 +647,12 @@ } } }, + "chardet": { + "version": "0.7.0", + "resolved": "https://registry.npmjs.org/chardet/-/chardet-0.7.0.tgz", + "integrity": "sha512-mT8iDcrh03qDGRRmoA2hmBJnxpllMR+0/0qlzjqZES6NdiWDcZkCNAk4rPFZ9Q85r27unkiNNg8ZOiwZXBHwcA==", + "dev": true + }, "charenc": { "version": "0.0.2", "resolved": "https://registry.npmjs.org/charenc/-/charenc-0.0.2.tgz", @@ -654,6 +720,15 @@ "integrity": "sha1-T6kXw+WclKAEzWH47lCdplFocUM=", "dev": true }, + "cli-cursor": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-2.1.0.tgz", + "integrity": "sha1-s12sN2R5+sw+lHR9QdDQ9SOP/LU=", + "dev": true, + "requires": { + "restore-cursor": "^2.0.0" + } + }, "cli-table3": { "version": "0.5.1", "resolved": "https://registry.npmjs.org/cli-table3/-/cli-table3-0.5.1.tgz", @@ -698,6 +773,12 @@ } } }, + "cli-width": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/cli-width/-/cli-width-2.2.0.tgz", + "integrity": "sha1-/xnt6Kml5XkyQUewwR8PvLq+1jk=", + "dev": true + }, "cliui": { "version": "3.2.0", "resolved": "https://registry.npmjs.org/cliui/-/cliui-3.2.0.tgz", @@ -796,6 +877,12 @@ "xdg-basedir": "^3.0.0" } }, + "contains-path": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/contains-path/-/contains-path-0.1.0.tgz", + "integrity": "sha1-/ozxhP9mcLa67wGp1IYaXL7EEgo=", + "dev": true + }, "copy-descriptor": { "version": "0.1.1", "resolved": "https://registry.npmjs.org/copy-descriptor/-/copy-descriptor-0.1.1.tgz", @@ -900,6 +987,15 @@ "integrity": "sha1-s2nW+128E+7PUk+RsHD+7cNXzzQ=", "dev": true }, + "define-properties": { + "version": "1.1.3", + "resolved": "https://registry.npmjs.org/define-properties/-/define-properties-1.1.3.tgz", + "integrity": "sha512-3MqfYKj2lLzdMSf8ZIZE/V+Zuy+BgD6f164e8K2w7dgnpKArBDerGYpM46IYYcjnkdPNMjPk9A6VFB8+3SKlXQ==", + "dev": true, + "requires": { + "object-keys": "^1.0.12" + } + }, "define-property": { "version": "2.0.2", "resolved": "https://registry.npmjs.org/define-property/-/define-property-2.0.2.tgz", @@ -952,6 +1048,15 @@ "resolved": "https://registry.npmjs.org/diff/-/diff-3.3.1.tgz", "integrity": "sha512-MKPHZDMB0o6yHyDryUOScqZibp914ksXwAMYMTHj6KO8UeKsRYNJD3oNCKjTqZon+V488P7N/HzXF8t7ZR95ww==" }, + "doctrine": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-3.0.0.tgz", + "integrity": "sha512-yS+Q5i3hBf7GBkd4KG8a7eBNNWNGLTaEwwYWUijIYM7zrlYDM0BFXHjjPWlWZ1Rg7UaddZeIDmi9jF3HmqiQ2w==", + "dev": true, + "requires": { + "esutils": "^2.0.2" + } + }, "dot-prop": { "version": "4.2.0", "resolved": "https://registry.npmjs.org/dot-prop/-/dot-prop-4.2.0.tgz", @@ -977,6 +1082,12 @@ "safer-buffer": "^2.1.0" } }, + "emoji-regex": { + "version": "7.0.3", + "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-7.0.3.tgz", + "integrity": "sha512-CwBLREIQ7LvYFB0WyRvwhq5N5qPhc6PMjD6bYggFlI5YyDgl+0vxq5VHbMOFqLg7hfWzmu8T5Z1QofhmTIhItA==", + "dev": true + }, "error-ex": { "version": "1.3.2", "resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.2.tgz", @@ -986,6 +1097,31 @@ "is-arrayish": "^0.2.1" } }, + "es-abstract": { + "version": "1.13.0", + "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.13.0.tgz", + "integrity": "sha512-vDZfg/ykNxQVwup/8E1BZhVzFfBxs9NqMzGcvIJrqg5k2/5Za2bWo40dK2J1pgLngZ7c+Shh8lwYtLGyrwPutg==", + "dev": true, + "requires": { + "es-to-primitive": "^1.2.0", + "function-bind": "^1.1.1", + "has": "^1.0.3", + "is-callable": "^1.1.4", + "is-regex": "^1.0.4", + "object-keys": "^1.0.12" + } + }, + "es-to-primitive": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/es-to-primitive/-/es-to-primitive-1.2.0.tgz", + "integrity": "sha512-qZryBOJjV//LaxLTV6UC//WewneB3LcXOL9NP++ozKVXsIIIpm/2c13UDiD9Jp2eThsecw9m3jPqDwTyobcdbg==", + "dev": true, + "requires": { + "is-callable": "^1.1.4", + "is-date-object": "^1.0.1", + "is-symbol": "^1.0.2" + } + }, "escape-string-regexp": { "version": "1.0.5", "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", @@ -1016,12 +1152,397 @@ } } }, + "eslint": { + "version": "5.16.0", + "resolved": "https://registry.npmjs.org/eslint/-/eslint-5.16.0.tgz", + "integrity": "sha512-S3Rz11i7c8AA5JPv7xAH+dOyq/Cu/VXHiHXBPOU1k/JAM5dXqQPt3qcrhpHSorXmrpu2g0gkIBVXAqCpzfoZIg==", + "dev": true, + "requires": { + "@babel/code-frame": "^7.0.0", + "ajv": "^6.9.1", + "chalk": "^2.1.0", + "cross-spawn": "^6.0.5", + "debug": "^4.0.1", + "doctrine": "^3.0.0", + "eslint-scope": "^4.0.3", + "eslint-utils": "^1.3.1", + "eslint-visitor-keys": "^1.0.0", + "espree": "^5.0.1", + "esquery": "^1.0.1", + "esutils": "^2.0.2", + "file-entry-cache": "^5.0.1", + "functional-red-black-tree": "^1.0.1", + "glob": "^7.1.2", + "globals": "^11.7.0", + "ignore": "^4.0.6", + "import-fresh": "^3.0.0", + "imurmurhash": "^0.1.4", + "inquirer": "^6.2.2", + "js-yaml": "^3.13.0", + "json-stable-stringify-without-jsonify": "^1.0.1", + "levn": "^0.3.0", + "lodash": "^4.17.11", + "minimatch": "^3.0.4", + "mkdirp": "^0.5.1", + "natural-compare": "^1.4.0", + "optionator": "^0.8.2", + "path-is-inside": "^1.0.2", + "progress": "^2.0.0", + "regexpp": "^2.0.1", + "semver": "^5.5.1", + "strip-ansi": "^4.0.0", + "strip-json-comments": "^2.0.1", + "table": "^5.2.3", + "text-table": "^0.2.0" + }, + "dependencies": { + "ansi-regex": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", + "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=", + "dev": true + }, + "cross-spawn": { + "version": "6.0.5", + "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-6.0.5.tgz", + "integrity": "sha512-eTVLrBSt7fjbDygz805pMnstIs2VTBNkRm0qxZd+M7A5XDdxVRWO5MxGBXZhjY4cqLYLdtrGqRf8mBPmzwSpWQ==", + "dev": true, + "requires": { + "nice-try": "^1.0.4", + "path-key": "^2.0.1", + "semver": "^5.5.0", + "shebang-command": "^1.2.0", + "which": "^1.2.9" + } + }, + "debug": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/debug/-/debug-4.1.1.tgz", + "integrity": "sha512-pYAIzeRo8J6KPEaJ0VWOh5Pzkbw/RetuzehGM7QRRX5he4fPHx2rdKMB256ehJCkX+XRQm16eZLqLNS8RSZXZw==", + "dev": true, + "requires": { + "ms": "^2.1.1" + } + }, + "ms": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.1.tgz", + "integrity": "sha512-tgp+dl5cGk28utYktBsrFqA7HKgrhgPsg6Z/EfhWI4gl1Hwq8B/GmY/0oXZ6nF8hDVesS/FpnYaD/kOWhYQvyg==", + "dev": true + }, + "strip-ansi": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", + "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", + "dev": true, + "requires": { + "ansi-regex": "^3.0.0" + } + } + } + }, + "eslint-config-airbnb-base": { + "version": "13.1.0", + "resolved": "https://registry.npmjs.org/eslint-config-airbnb-base/-/eslint-config-airbnb-base-13.1.0.tgz", + "integrity": "sha512-XWwQtf3U3zIoKO1BbHh6aUhJZQweOwSt4c2JrPDg9FP3Ltv3+YfEv7jIDB8275tVnO/qOHbfuYg3kzw6Je7uWw==", + "dev": true, + "requires": { + "eslint-restricted-globals": "^0.1.1", + "object.assign": "^4.1.0", + "object.entries": "^1.0.4" + } + }, + "eslint-config-prettier": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/eslint-config-prettier/-/eslint-config-prettier-4.2.0.tgz", + "integrity": "sha512-y0uWc/FRfrHhpPZCYflWC8aE0KRJRY04rdZVfl8cL3sEZmOYyaBdhdlQPjKZBnuRMyLVK+JUZr7HaZFClQiH4w==", + "dev": true, + "requires": { + "get-stdin": "^6.0.0" + } + }, + "eslint-import-resolver-node": { + "version": "0.3.2", + "resolved": "https://registry.npmjs.org/eslint-import-resolver-node/-/eslint-import-resolver-node-0.3.2.tgz", + "integrity": "sha512-sfmTqJfPSizWu4aymbPr4Iidp5yKm8yDkHp+Ir3YiTHiiDfxh69mOUsmiqW6RZ9zRXFaF64GtYmN7e+8GHBv6Q==", + "dev": true, + "requires": { + "debug": "^2.6.9", + "resolve": "^1.5.0" + }, + "dependencies": { + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, + "requires": { + "ms": "2.0.0" + } + } + } + }, + "eslint-module-utils": { + "version": "2.4.0", + "resolved": "https://registry.npmjs.org/eslint-module-utils/-/eslint-module-utils-2.4.0.tgz", + "integrity": "sha512-14tltLm38Eu3zS+mt0KvILC3q8jyIAH518MlG+HO0p+yK885Lb1UHTY/UgR91eOyGdmxAPb+OLoW4znqIT6Ndw==", + "dev": true, + "requires": { + "debug": "^2.6.8", + "pkg-dir": "^2.0.0" + }, + "dependencies": { + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, + "requires": { + "ms": "2.0.0" + } + } + } + }, + "eslint-plugin-es": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/eslint-plugin-es/-/eslint-plugin-es-1.4.0.tgz", + "integrity": "sha512-XfFmgFdIUDgvaRAlaXUkxrRg5JSADoRC8IkKLc/cISeR3yHVMefFHQZpcyXXEUUPHfy5DwviBcrfqlyqEwlQVw==", + "dev": true, + "requires": { + "eslint-utils": "^1.3.0", + "regexpp": "^2.0.1" + } + }, + "eslint-plugin-import": { + "version": "2.17.2", + "resolved": "https://registry.npmjs.org/eslint-plugin-import/-/eslint-plugin-import-2.17.2.tgz", + "integrity": "sha512-m+cSVxM7oLsIpmwNn2WXTJoReOF9f/CtLMo7qOVmKd1KntBy0hEcuNZ3erTmWjx+DxRO0Zcrm5KwAvI9wHcV5g==", + "dev": true, + "requires": { + "array-includes": "^3.0.3", + "contains-path": "^0.1.0", + "debug": "^2.6.9", + "doctrine": "1.5.0", + "eslint-import-resolver-node": "^0.3.2", + "eslint-module-utils": "^2.4.0", + "has": "^1.0.3", + "lodash": "^4.17.11", + "minimatch": "^3.0.4", + "read-pkg-up": "^2.0.0", + "resolve": "^1.10.0" + }, + "dependencies": { + "debug": { + "version": "2.6.9", + "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", + "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", + "dev": true, + "requires": { + "ms": "2.0.0" + } + }, + "doctrine": { + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-1.5.0.tgz", + "integrity": "sha1-N53Ocw9hZvds76TmcHoVmwLFpvo=", + "dev": true, + "requires": { + "esutils": "^2.0.2", + "isarray": "^1.0.0" + } + }, + "find-up": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", + "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", + "dev": true, + "requires": { + "locate-path": "^2.0.0" + } + }, + "load-json-file": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-2.0.0.tgz", + "integrity": "sha1-eUfkIUmvgNaWy/eXvKq8/h/inKg=", + "dev": true, + "requires": { + "graceful-fs": "^4.1.2", + "parse-json": "^2.2.0", + "pify": "^2.0.0", + "strip-bom": "^3.0.0" + } + }, + "path-type": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/path-type/-/path-type-2.0.0.tgz", + "integrity": "sha1-8BLMuEFbcJb8LaoQVMPXI4lZTHM=", + "dev": true, + "requires": { + "pify": "^2.0.0" + } + }, + "read-pkg": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-2.0.0.tgz", + "integrity": "sha1-jvHAYjxqbbDcZxPEv6xGMysjaPg=", + "dev": true, + "requires": { + "load-json-file": "^2.0.0", + "normalize-package-data": "^2.3.2", + "path-type": "^2.0.0" + } + }, + "read-pkg-up": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/read-pkg-up/-/read-pkg-up-2.0.0.tgz", + "integrity": "sha1-a3KoBImE4MQeeVEP1en6mbO1Sb4=", + "dev": true, + "requires": { + "find-up": "^2.0.0", + "read-pkg": "^2.0.0" + } + }, + "strip-bom": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-3.0.0.tgz", + "integrity": "sha1-IzTBjpx1n3vdVv3vfprj1YjmjtM=", + "dev": true + } + } + }, + "eslint-plugin-node": { + "version": "9.0.1", + "resolved": "https://registry.npmjs.org/eslint-plugin-node/-/eslint-plugin-node-9.0.1.tgz", + "integrity": "sha512-fljT5Uyy3lkJzuqhxrYanLSsvaILs9I7CmQ31atTtZ0DoIzRbbvInBh4cQ1CrthFHInHYBQxfPmPt6KLHXNXdw==", + "dev": true, + "requires": { + "eslint-plugin-es": "^1.4.0", + "eslint-utils": "^1.3.1", + "ignore": "^5.1.1", + "minimatch": "^3.0.4", + "resolve": "^1.10.1", + "semver": "^6.0.0" + }, + "dependencies": { + "ignore": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/ignore/-/ignore-5.1.1.tgz", + "integrity": "sha512-DWjnQIFLenVrwyRCKZT+7a7/U4Cqgar4WG8V++K3hw+lrW1hc/SIwdiGmtxKCVACmHULTuGeBbHJmbwW7/sAvA==", + "dev": true + }, + "resolve": { + "version": "1.10.1", + "resolved": "https://registry.npmjs.org/resolve/-/resolve-1.10.1.tgz", + "integrity": "sha512-KuIe4mf++td/eFb6wkaPbMDnP6kObCaEtIDuHOUED6MNUo4K670KZUHuuvYPZDxNF0WVLw49n06M2m2dXphEzA==", + "dev": true, + "requires": { + "path-parse": "^1.0.6" + } + }, + "semver": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/semver/-/semver-6.0.0.tgz", + "integrity": "sha512-0UewU+9rFapKFnlbirLi3byoOuhrSsli/z/ihNnvM24vgF+8sNBiI1LZPBSH9wJKUwaUbw+s3hToDLCXkrghrQ==", + "dev": true + } + } + }, + "eslint-plugin-prettier": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/eslint-plugin-prettier/-/eslint-plugin-prettier-3.0.1.tgz", + "integrity": "sha512-/PMttrarPAY78PLvV3xfWibMOdMDl57hmlQ2XqFeA37wd+CJ7WSxV7txqjVPHi/AAFKd2lX0ZqfsOc/i5yFCSQ==", + "dev": true, + "requires": { + "prettier-linter-helpers": "^1.0.0" + } + }, + "eslint-restricted-globals": { + "version": "0.1.1", + "resolved": "https://registry.npmjs.org/eslint-restricted-globals/-/eslint-restricted-globals-0.1.1.tgz", + "integrity": "sha1-NfDVy8ZMLj7WLpO0saevBbp+1Nc=", + "dev": true + }, + "eslint-scope": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-4.0.3.tgz", + "integrity": "sha512-p7VutNr1O/QrxysMo3E45FjYDTeXBy0iTltPFNSqKAIfjDSXC+4dj+qfyuD8bfAXrW/y6lW3O76VaYNPKfpKrg==", + "dev": true, + "requires": { + "esrecurse": "^4.1.0", + "estraverse": "^4.1.1" + }, + "dependencies": { + "estraverse": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-4.2.0.tgz", + "integrity": "sha1-De4/7TH81GlhjOc0IJn8GvoL2xM=", + "dev": true + } + } + }, + "eslint-utils": { + "version": "1.3.1", + "resolved": "https://registry.npmjs.org/eslint-utils/-/eslint-utils-1.3.1.tgz", + "integrity": "sha512-Z7YjnIldX+2XMcjr7ZkgEsOj/bREONV60qYeB/bjMAqqqZ4zxKyWX+BOUkdmRmA9riiIPVvo5x86m5elviOk0Q==", + "dev": true + }, + "eslint-visitor-keys": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/eslint-visitor-keys/-/eslint-visitor-keys-1.0.0.tgz", + "integrity": "sha512-qzm/XxIbxm/FHyH341ZrbnMUpe+5Bocte9xkmFMzPMjRaZMcXww+MpBptFvtU+79L362nqiLhekCxCxDPaUMBQ==", + "dev": true + }, + "espree": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/espree/-/espree-5.0.1.tgz", + "integrity": "sha512-qWAZcWh4XE/RwzLJejfcofscgMc9CamR6Tn1+XRXNzrvUSSbiAjGOI/fggztjIi7y9VLPqnICMIPiGyr8JaZ0A==", + "dev": true, + "requires": { + "acorn": "^6.0.7", + "acorn-jsx": "^5.0.0", + "eslint-visitor-keys": "^1.0.0" + } + }, "esprima": { "version": "2.7.3", "resolved": "https://registry.npmjs.org/esprima/-/esprima-2.7.3.tgz", "integrity": "sha1-luO3DVd59q1JzQMmc9HDEnZ7pYE=", "dev": true }, + "esquery": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/esquery/-/esquery-1.0.1.tgz", + "integrity": "sha512-SmiyZ5zIWH9VM+SRUReLS5Q8a7GxtRdxEBVZpm98rJM7Sb+A9DVCndXfkeFUd3byderg+EbDkfnevfCwynWaNA==", + "dev": true, + "requires": { + "estraverse": "^4.0.0" + }, + "dependencies": { + "estraverse": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-4.2.0.tgz", + "integrity": "sha1-De4/7TH81GlhjOc0IJn8GvoL2xM=", + "dev": true + } + } + }, + "esrecurse": { + "version": "4.2.1", + "resolved": "https://registry.npmjs.org/esrecurse/-/esrecurse-4.2.1.tgz", + "integrity": "sha512-64RBB++fIOAXPw3P9cy89qfMlvZEXZkqqJkjqqXIvzP5ezRZjW+lPWjw35UX/3EhUPFYbg5ER4JYgDw4007/DQ==", + "dev": true, + "requires": { + "estraverse": "^4.1.0" + }, + "dependencies": { + "estraverse": { + "version": "4.2.0", + "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-4.2.0.tgz", + "integrity": "sha1-De4/7TH81GlhjOc0IJn8GvoL2xM=", + "dev": true + } + } + }, "estraverse": { "version": "1.9.3", "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-1.9.3.tgz", @@ -1148,6 +1669,17 @@ } } }, + "external-editor": { + "version": "3.0.3", + "resolved": "https://registry.npmjs.org/external-editor/-/external-editor-3.0.3.tgz", + "integrity": "sha512-bn71H9+qWoOQKyZDo25mOMVpSmXROAsTJVVVYzrrtol3d4y+AsKjf4Iwl2Q+IuT0kFSQ1qo166UuIwqYq7mGnA==", + "dev": true, + "requires": { + "chardet": "^0.7.0", + "iconv-lite": "^0.4.24", + "tmp": "^0.0.33" + } + }, "extglob": { "version": "2.0.4", "resolved": "https://registry.npmjs.org/extglob/-/extglob-2.0.4.tgz", @@ -1225,6 +1757,12 @@ "integrity": "sha1-ewUhjd+WZ79/Nwv3/bLLFf3Qqkk=", "dev": true }, + "fast-diff": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/fast-diff/-/fast-diff-1.2.0.tgz", + "integrity": "sha512-xJuoT5+L99XlZ8twedaRf6Ax2TgQVxvgZOYoPKqZufmJib0tL2tegPBOZb1pVNgIhlqDlA0eO0c3wBvQcmzx4w==", + "dev": true + }, "fast-json-stable-stringify": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.0.0.tgz", @@ -1237,6 +1775,24 @@ "integrity": "sha1-PYpcZog6FqMMqGQ+hR8Zuqd5eRc=", "dev": true }, + "figures": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/figures/-/figures-2.0.0.tgz", + "integrity": "sha1-OrGi0qYsi/tDGgyUy3l6L84nyWI=", + "dev": true, + "requires": { + "escape-string-regexp": "^1.0.5" + } + }, + "file-entry-cache": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/file-entry-cache/-/file-entry-cache-5.0.1.tgz", + "integrity": "sha512-bCg29ictuBaKUwwArK4ouCaqDgLZcysCFLmM/Yn/FDoqndh/9vNuQfXRDvTuXKLxfD/JtZQGKFT8MGcJBK644g==", + "dev": true, + "requires": { + "flat-cache": "^2.0.1" + } + }, "file-uri-to-path": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/file-uri-to-path/-/file-uri-to-path-1.0.0.tgz", @@ -1275,6 +1831,23 @@ "pinkie-promise": "^2.0.0" } }, + "flat-cache": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/flat-cache/-/flat-cache-2.0.1.tgz", + "integrity": "sha512-LoQe6yDuUMDzQAEH8sgmh4Md6oZnc/7PjtwjNFSzveXqSHt6ka9fPBuso7IGf9Rz4uqnSnWiFH2B/zj24a5ReA==", + "dev": true, + "requires": { + "flatted": "^2.0.0", + "rimraf": "2.6.3", + "write": "1.0.3" + } + }, + "flatted": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/flatted/-/flatted-2.0.0.tgz", + "integrity": "sha512-R+H8IZclI8AAkSBRQJLVOsxwAoHd6WC40b4QTNWIjzAa6BXOBfQcM587MXDTVPeYaopFNWHUFLx7eNmHDSxMWg==", + "dev": true + }, "for-in": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/for-in/-/for-in-1.0.2.tgz", @@ -1365,12 +1938,14 @@ "balanced-match": { "version": "1.0.0", "bundled": true, - "dev": true + "dev": true, + "optional": true }, "brace-expansion": { "version": "1.1.11", "bundled": true, "dev": true, + "optional": true, "requires": { "balanced-match": "^1.0.0", "concat-map": "0.0.1" @@ -1385,17 +1960,20 @@ "code-point-at": { "version": "1.1.0", "bundled": true, - "dev": true + "dev": true, + "optional": true }, "concat-map": { "version": "0.0.1", "bundled": true, - "dev": true + "dev": true, + "optional": true }, "console-control-strings": { "version": "1.1.0", "bundled": true, - "dev": true + "dev": true, + "optional": true }, "core-util-is": { "version": "1.0.2", @@ -1512,7 +2090,8 @@ "inherits": { "version": "2.0.3", "bundled": true, - "dev": true + "dev": true, + "optional": true }, "ini": { "version": "1.3.5", @@ -1524,6 +2103,7 @@ "version": "1.0.0", "bundled": true, "dev": true, + "optional": true, "requires": { "number-is-nan": "^1.0.0" } @@ -1538,6 +2118,7 @@ "version": "3.0.4", "bundled": true, "dev": true, + "optional": true, "requires": { "brace-expansion": "^1.1.7" } @@ -1649,7 +2230,8 @@ "number-is-nan": { "version": "1.0.1", "bundled": true, - "dev": true + "dev": true, + "optional": true }, "object-assign": { "version": "4.1.1", @@ -1782,6 +2364,7 @@ "version": "1.0.2", "bundled": true, "dev": true, + "optional": true, "requires": { "code-point-at": "^1.0.0", "is-fullwidth-code-point": "^1.0.0", @@ -1853,6 +2436,18 @@ } } }, + "function-bind": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.1.tgz", + "integrity": "sha512-yIovAzMX49sF8Yl58fSCWJ5svSLuaibPxXQJFLmBObTuCr0Mf1KiPopGM9NiFjiYBCbfaa2Fh6breQ6ANVTI0A==", + "dev": true + }, + "functional-red-black-tree": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/functional-red-black-tree/-/functional-red-black-tree-1.0.1.tgz", + "integrity": "sha1-GwqzvVU7Kg1jmdKcDj6gslIHgyc=", + "dev": true + }, "ganache-cli": { "version": "6.4.3", "resolved": "https://registry.npmjs.org/ganache-cli/-/ganache-cli-6.4.3.tgz", @@ -2195,6 +2790,12 @@ "integrity": "sha1-3Xzn3hh8Bsi/NTeWrHHgmfCYDrw=", "dev": true }, + "get-stdin": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/get-stdin/-/get-stdin-6.0.0.tgz", + "integrity": "sha512-jp4tHawyV7+fkkSKyvjuLZswblUtz+SQKzSWnBbii16BuZksJlU1wuBYXY75r+duh/llF1ur6oNwi+2ZzjKZ7g==", + "dev": true + }, "get-stream": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-3.0.0.tgz", @@ -2258,6 +2859,12 @@ "ini": "^1.3.4" } }, + "globals": { + "version": "11.12.0", + "resolved": "https://registry.npmjs.org/globals/-/globals-11.12.0.tgz", + "integrity": "sha512-WOBp/EEGUiIsJSp7wcv/y6MO+lV9UoncWqxuFfm8eBwzWNgyfBd6Gz+IeKQ9jCmyhoH99g15M3T+QaVHFjizVA==", + "dev": true + }, "got": { "version": "6.7.1", "resolved": "https://registry.npmjs.org/got/-/got-6.7.1.tgz", @@ -2323,11 +2930,26 @@ "har-schema": "^2.0.0" } }, + "has": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/has/-/has-1.0.3.tgz", + "integrity": "sha512-f2dvO0VU6Oej7RkWJGrehjbzMAjFp5/VKPp5tTpWIV4JHHZK1/BxbFRtf/siA2SWTe09caDmVtYYzWEIbBS4zw==", + "dev": true, + "requires": { + "function-bind": "^1.1.1" + } + }, "has-flag": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-2.0.0.tgz", "integrity": "sha1-6CB68cx7MNRGzHC3NLXovhj4jVE=" }, + "has-symbols": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.0.0.tgz", + "integrity": "sha1-uhqPGvKg/DllD1yFA2dwQSIGO0Q=", + "dev": true + }, "has-value": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/has-value/-/has-value-1.0.0.tgz", @@ -2403,12 +3025,45 @@ "sshpk": "^1.7.0" } }, + "iconv-lite": { + "version": "0.4.24", + "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.24.tgz", + "integrity": "sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==", + "dev": true, + "requires": { + "safer-buffer": ">= 2.1.2 < 3" + } + }, + "ignore": { + "version": "4.0.6", + "resolved": "https://registry.npmjs.org/ignore/-/ignore-4.0.6.tgz", + "integrity": "sha512-cyFDKrqc/YdcWFniJhzI42+AzS+gNwmUzOSFcRCQYwySuBBBy/KjuxWLZ/FHEH6Moq1NizMOBWyTcv8O4OZIMg==", + "dev": true + }, "ignore-by-default": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/ignore-by-default/-/ignore-by-default-1.0.1.tgz", "integrity": "sha1-SMptcvbGo68Aqa1K5odr44ieKwk=", "dev": true }, + "import-fresh": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/import-fresh/-/import-fresh-3.0.0.tgz", + "integrity": "sha512-pOnA9tfM3Uwics+SaBLCNyZZZbK+4PTu0OPZtLlMIrv17EdBoC15S9Kn8ckJ9TZTyKb3ywNE5y1yeDxxGA7nTQ==", + "dev": true, + "requires": { + "parent-module": "^1.0.0", + "resolve-from": "^4.0.0" + }, + "dependencies": { + "resolve-from": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-4.0.0.tgz", + "integrity": "sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==", + "dev": true + } + } + }, "import-lazy": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/import-lazy/-/import-lazy-2.1.0.tgz", @@ -2441,6 +3096,79 @@ "integrity": "sha512-RZY5huIKCMRWDUqZlEi72f/lmXKMvuszcMBduliQ3nnWbx9X/ZBQO7DijMEYS9EhHBb2qacRUMtC7svLwe0lcw==", "dev": true }, + "inquirer": { + "version": "6.3.1", + "resolved": "https://registry.npmjs.org/inquirer/-/inquirer-6.3.1.tgz", + "integrity": "sha512-MmL624rfkFt4TG9y/Jvmt8vdmOo836U7Y0Hxr2aFk3RelZEGX4Igk0KabWrcaaZaTv9uzglOqWh1Vly+FAWAXA==", + "dev": true, + "requires": { + "ansi-escapes": "^3.2.0", + "chalk": "^2.4.2", + "cli-cursor": "^2.1.0", + "cli-width": "^2.0.0", + "external-editor": "^3.0.3", + "figures": "^2.0.0", + "lodash": "^4.17.11", + "mute-stream": "0.0.7", + "run-async": "^2.2.0", + "rxjs": "^6.4.0", + "string-width": "^2.1.0", + "strip-ansi": "^5.1.0", + "through": "^2.3.6" + }, + "dependencies": { + "ansi-regex": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", + "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=", + "dev": true + }, + "is-fullwidth-code-point": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", + "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=", + "dev": true + }, + "string-width": { + "version": "2.1.1", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", + "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", + "dev": true, + "requires": { + "is-fullwidth-code-point": "^2.0.0", + "strip-ansi": "^4.0.0" + }, + "dependencies": { + "strip-ansi": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", + "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", + "dev": true, + "requires": { + "ansi-regex": "^3.0.0" + } + } + } + }, + "strip-ansi": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-5.2.0.tgz", + "integrity": "sha512-DuRs1gKbBqsMKIZlrffwlug8MHkcnpjs5VPmL1PAh+mA30U0DTotfDZ0d2UUsXpPmPmMMJ6W773MaA3J+lbiWA==", + "dev": true, + "requires": { + "ansi-regex": "^4.1.0" + }, + "dependencies": { + "ansi-regex": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-4.1.0.tgz", + "integrity": "sha512-1apePfXM1UOSqw0o9IiFAovVz9M5S1Dg+4TrDwfMewQ6p/rmMueb7tWZjQ1rx4Loy1ArBggoqGpfqqdI4rondg==", + "dev": true + } + } + } + } + }, "interpret": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/interpret/-/interpret-1.2.0.tgz", @@ -2493,6 +3221,12 @@ "integrity": "sha512-NcdALwpXkTm5Zvvbk7owOUSvVvBKDgKP5/ewfXEznmQFfs4ZRmanOeKBTjRVjka3QFoN6XJ+9F3USqfHqTaU5w==", "dev": true }, + "is-callable": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/is-callable/-/is-callable-1.1.4.tgz", + "integrity": "sha512-r5p9sxJjYnArLjObpjA4xu5EKI3CuKHkJXMhT7kwbpUyIFD1n5PMAsoPvWnvtZiNz7LjkYDRZhd7FlI0eMijEA==", + "dev": true + }, "is-ci": { "version": "1.2.1", "resolved": "https://registry.npmjs.org/is-ci/-/is-ci-1.2.1.tgz", @@ -2522,6 +3256,12 @@ } } }, + "is-date-object": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-date-object/-/is-date-object-1.0.1.tgz", + "integrity": "sha1-mqIOtq7rv/d/vTPnTKAbM1gdOhY=", + "dev": true + }, "is-descriptor": { "version": "0.1.6", "resolved": "https://registry.npmjs.org/is-descriptor/-/is-descriptor-0.1.6.tgz", @@ -2630,12 +3370,27 @@ "isobject": "^3.0.1" } }, + "is-promise": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/is-promise/-/is-promise-2.1.0.tgz", + "integrity": "sha1-eaKp7OfwlugPNtKy87wWwf9L8/o=", + "dev": true + }, "is-redirect": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/is-redirect/-/is-redirect-1.0.0.tgz", "integrity": "sha1-HQPd7VO9jbDzDCbk+V02/HyH3CQ=", "dev": true }, + "is-regex": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-regex/-/is-regex-1.0.4.tgz", + "integrity": "sha1-VRdIm1RwkbCTDglWVM7SXul+lJE=", + "dev": true, + "requires": { + "has": "^1.0.1" + } + }, "is-retry-allowed": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/is-retry-allowed/-/is-retry-allowed-1.1.0.tgz", @@ -2647,6 +3402,15 @@ "resolved": "https://registry.npmjs.org/is-stream/-/is-stream-1.1.0.tgz", "integrity": "sha1-EtSj3U5o4Lec6428hBc66A2RykQ=" }, + "is-symbol": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/is-symbol/-/is-symbol-1.0.2.tgz", + "integrity": "sha512-HS8bZ9ox60yCJLH9snBpIwv9pYUAkcuLhSA1oero1UB5y9aiQpRA8y2ex945AOtCZL1lJDeIk3G5LthswI46Lw==", + "dev": true, + "requires": { + "has-symbols": "^1.0.0" + } + }, "is-typedarray": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/is-typedarray/-/is-typedarray-1.0.0.tgz", @@ -2767,6 +3531,12 @@ "integrity": "sha1-W4n3enR3Z5h39YxKB1JAk0sflcA=", "dev": true }, + "js-tokens": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-4.0.0.tgz", + "integrity": "sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==", + "dev": true + }, "js-yaml": { "version": "3.13.1", "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.13.1.tgz", @@ -2803,6 +3573,12 @@ "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", "dev": true }, + "json-stable-stringify-without-jsonify": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/json-stable-stringify-without-jsonify/-/json-stable-stringify-without-jsonify-1.0.1.tgz", + "integrity": "sha1-nbe1lJatPzz+8wp1FC0tkwrXJlE=", + "dev": true + }, "json-stringify-safe": { "version": "5.0.1", "resolved": "https://registry.npmjs.org/json-stringify-safe/-/json-stringify-safe-5.0.1.tgz", @@ -3097,6 +3873,12 @@ "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" }, + "mute-stream": { + "version": "0.0.7", + "resolved": "https://registry.npmjs.org/mute-stream/-/mute-stream-0.0.7.tgz", + "integrity": "sha1-MHXOk7whuPq0PhvE2n6BFe0ee6s=", + "dev": true + }, "nan": { "version": "2.10.0", "resolved": "https://registry.npmjs.org/nan/-/nan-2.10.0.tgz", @@ -3121,12 +3903,24 @@ "to-regex": "^3.0.1" } }, + "natural-compare": { + "version": "1.4.0", + "resolved": "https://registry.npmjs.org/natural-compare/-/natural-compare-1.4.0.tgz", + "integrity": "sha1-Sr6/7tdUHywnrPspvbvRXI1bpPc=", + "dev": true + }, "neo-async": { "version": "2.6.0", "resolved": "https://registry.npmjs.org/neo-async/-/neo-async-2.6.0.tgz", "integrity": "sha512-MFh0d/Wa7vkKO3Y3LlacqAEeHK0mckVqzDieUKTT+KGxi+zIpeVsFxymkIiRpbpDziHc290Xr9A1O4Om7otoRA==", "dev": true }, + "nice-try": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/nice-try/-/nice-try-1.0.5.tgz", + "integrity": "sha512-1nh45deeb5olNY7eX82BkPO7SSxR5SSYJiPTrTdFUVYwAl8CKMA5N9PjTYkHiRjisVcxcQ1HXdLhx2qxxJzLNQ==", + "dev": true + }, "nodemon": { "version": "1.18.10", "resolved": "https://registry.npmjs.org/nodemon/-/nodemon-1.18.10.tgz", @@ -3245,6 +4039,12 @@ } } }, + "object-keys": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/object-keys/-/object-keys-1.1.1.tgz", + "integrity": "sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==", + "dev": true + }, "object-visit": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/object-visit/-/object-visit-1.0.1.tgz", @@ -3254,6 +4054,30 @@ "isobject": "^3.0.0" } }, + "object.assign": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/object.assign/-/object.assign-4.1.0.tgz", + "integrity": "sha512-exHJeq6kBKj58mqGyTQ9DFvrZC/eR6OwxzoM9YRoGBqrXYonaFyGiFMuc9VZrXf7DarreEwMpurG3dd+CNyW5w==", + "dev": true, + "requires": { + "define-properties": "^1.1.2", + "function-bind": "^1.1.1", + "has-symbols": "^1.0.0", + "object-keys": "^1.0.11" + } + }, + "object.entries": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/object.entries/-/object.entries-1.1.0.tgz", + "integrity": "sha512-l+H6EQ8qzGRxbkHOd5I/aHRhHDKoQXQ8g0BYt4uSweQU1/J6dZUOyWh9a2Vky35YCKjzmgxOzta2hH6kf9HuXA==", + "dev": true, + "requires": { + "define-properties": "^1.1.3", + "es-abstract": "^1.12.0", + "function-bind": "^1.1.1", + "has": "^1.0.3" + } + }, "object.pick": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/object.pick/-/object.pick-1.3.0.tgz", @@ -3271,6 +4095,15 @@ "wrappy": "1" } }, + "onetime": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/onetime/-/onetime-2.0.1.tgz", + "integrity": "sha1-BnQoIw/WdEOyeUsiu6UotoZ5YtQ=", + "dev": true, + "requires": { + "mimic-fn": "^1.0.0" + } + }, "openzeppelin-solidity": { "version": "1.12.0", "resolved": "https://registry.npmjs.org/openzeppelin-solidity/-/openzeppelin-solidity-1.12.0.tgz", @@ -3322,6 +4155,12 @@ "lcid": "^1.0.0" } }, + "os-tmpdir": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/os-tmpdir/-/os-tmpdir-1.0.2.tgz", + "integrity": "sha1-u+Z0BseaqFxc/sdm/lc0VV36EnQ=", + "dev": true + }, "p-finally": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/p-finally/-/p-finally-1.0.0.tgz", @@ -3360,6 +4199,15 @@ "semver": "^5.1.0" } }, + "parent-module": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/parent-module/-/parent-module-1.0.1.tgz", + "integrity": "sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g==", + "dev": true, + "requires": { + "callsites": "^3.0.0" + } + }, "parse-cache-control": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/parse-cache-control/-/parse-cache-control-1.0.1.tgz", @@ -3468,6 +4316,26 @@ "pinkie": "^2.0.0" } }, + "pkg-dir": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/pkg-dir/-/pkg-dir-2.0.0.tgz", + "integrity": "sha1-9tXREJ4Z1j7fQo4L1X4Sd3YVM0s=", + "dev": true, + "requires": { + "find-up": "^2.1.0" + }, + "dependencies": { + "find-up": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", + "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", + "dev": true, + "requires": { + "locate-path": "^2.0.0" + } + } + } + }, "posix-character-classes": { "version": "0.1.1", "resolved": "https://registry.npmjs.org/posix-character-classes/-/posix-character-classes-0.1.1.tgz", @@ -3486,12 +4354,33 @@ "integrity": "sha1-1PRWKwzjaW5BrFLQ4ALlemNdxtw=", "dev": true }, + "prettier": { + "version": "1.17.1", + "resolved": "https://registry.npmjs.org/prettier/-/prettier-1.17.1.tgz", + "integrity": "sha512-TzGRNvuUSmPgwivDqkZ9tM/qTGW9hqDKWOE9YHiyQdixlKbv7kvEqsmDPrcHJTKwthU774TQwZXVtaQ/mMsvjg==", + "dev": true + }, + "prettier-linter-helpers": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/prettier-linter-helpers/-/prettier-linter-helpers-1.0.0.tgz", + "integrity": "sha512-GbK2cP9nraSSUF9N2XwUwqfzlAFlMNYYl+ShE/V+H8a9uNl/oUqB1w2EL54Jh0OlyRSd8RfWYJ3coVS4TROP2w==", + "dev": true, + "requires": { + "fast-diff": "^1.1.2" + } + }, "process-nextick-args": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.0.tgz", "integrity": "sha512-MtEC1TqN0EU5nephaJ4rAtThHtC86dNN9qCuEhtshvpVBkAW5ZO7BASN9REnF9eoXGcRub+pFuKEpOHE+HbEMw==", "dev": true }, + "progress": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/progress/-/progress-2.0.3.tgz", + "integrity": "sha512-7PiHtLll5LdnKIMw100I+8xJXR5gW2QwWYkT6iJva0bXitZKa/XMrSbdmg3r2Xnaidz9Qumd0VPaMrZlF9V9sA==", + "dev": true + }, "promise": { "version": "8.0.3", "resolved": "https://registry.npmjs.org/promise/-/promise-8.0.3.tgz", @@ -3616,6 +4505,12 @@ "safe-regex": "^1.1.0" } }, + "regexpp": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/regexpp/-/regexpp-2.0.1.tgz", + "integrity": "sha512-lv0M6+TkDVniA3aD1Eg0DVpfU/booSu7Eev3TDO/mZKHBfVjgCGTV4t4buppESEYDtkArYFOxTJWv6S5C+iaNw==", + "dev": true + }, "registry-auth-token": { "version": "3.4.0", "resolved": "https://registry.npmjs.org/registry-auth-token/-/registry-auth-token-3.4.0.tgz", @@ -3755,6 +4650,16 @@ "integrity": "sha1-LGN/53yJOv0qZj/iGqkIAGjiBSo=", "dev": true }, + "restore-cursor": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-2.0.0.tgz", + "integrity": "sha1-n37ih/gv0ybU/RYpI9YhKe7g368=", + "dev": true, + "requires": { + "onetime": "^2.0.0", + "signal-exit": "^3.0.2" + } + }, "ret": { "version": "0.1.15", "resolved": "https://registry.npmjs.org/ret/-/ret-0.1.15.tgz", @@ -3784,6 +4689,24 @@ } } }, + "run-async": { + "version": "2.3.0", + "resolved": "https://registry.npmjs.org/run-async/-/run-async-2.3.0.tgz", + "integrity": "sha1-A3GrSuC91yDUFm19/aZP96RFpsA=", + "dev": true, + "requires": { + "is-promise": "^2.1.0" + } + }, + "rxjs": { + "version": "6.5.2", + "resolved": "https://registry.npmjs.org/rxjs/-/rxjs-6.5.2.tgz", + "integrity": "sha512-HUb7j3kvb7p7eCUHE3FqjoDsC1xfZQ4AHFWfTKSpZ+sAhhz5X1WX0ZuUqWbzB2QhSLp3DoLUG+hMdEDKqWo2Zg==", + "dev": true, + "requires": { + "tslib": "^1.9.0" + } + }, "safe-buffer": { "version": "5.1.2", "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.2.tgz", @@ -3894,6 +4817,25 @@ "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.2.tgz", "integrity": "sha1-tf3AjxKH6hF4Yo5BXiUTK3NkbG0=" }, + "slice-ansi": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/slice-ansi/-/slice-ansi-2.1.0.tgz", + "integrity": "sha512-Qu+VC3EwYLldKa1fCxuuvULvSJOKEgk9pi8dZeCVK7TqBfUNTH4sFkk4joj8afVSfAYgJoSOetjx9QWOJ5mYoQ==", + "dev": true, + "requires": { + "ansi-styles": "^3.2.0", + "astral-regex": "^1.0.0", + "is-fullwidth-code-point": "^2.0.0" + }, + "dependencies": { + "is-fullwidth-code-point": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", + "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=", + "dev": true + } + } + }, "snapdragon": { "version": "0.8.2", "resolved": "https://registry.npmjs.org/snapdragon/-/snapdragon-0.8.2.tgz", @@ -4393,6 +5335,52 @@ "get-port": "^3.1.0" } }, + "table": { + "version": "5.3.3", + "resolved": "https://registry.npmjs.org/table/-/table-5.3.3.tgz", + "integrity": "sha512-3wUNCgdWX6PNpOe3amTTPWPuF6VGvgzjKCaO1snFj0z7Y3mUPWf5+zDtxUVGispJkDECPmR29wbzh6bVMOHbcw==", + "dev": true, + "requires": { + "ajv": "^6.9.1", + "lodash": "^4.17.11", + "slice-ansi": "^2.1.0", + "string-width": "^3.0.0" + }, + "dependencies": { + "ansi-regex": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-4.1.0.tgz", + "integrity": "sha512-1apePfXM1UOSqw0o9IiFAovVz9M5S1Dg+4TrDwfMewQ6p/rmMueb7tWZjQ1rx4Loy1ArBggoqGpfqqdI4rondg==", + "dev": true + }, + "is-fullwidth-code-point": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", + "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=", + "dev": true + }, + "string-width": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-3.1.0.tgz", + "integrity": "sha512-vafcv6KjVZKSgz06oM/H6GDBrAtz8vdhQakGjFIvNrHA6y3HCF1CInLy+QLq8dTJPQ1b+KDUqDFctkdRW44e1w==", + "dev": true, + "requires": { + "emoji-regex": "^7.0.1", + "is-fullwidth-code-point": "^2.0.0", + "strip-ansi": "^5.1.0" + } + }, + "strip-ansi": { + "version": "5.2.0", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-5.2.0.tgz", + "integrity": "sha512-DuRs1gKbBqsMKIZlrffwlug8MHkcnpjs5VPmL1PAh+mA30U0DTotfDZ0d2UUsXpPmPmMMJ6W773MaA3J+lbiWA==", + "dev": true, + "requires": { + "ansi-regex": "^4.1.0" + } + } + } + }, "term-size": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/term-size/-/term-size-1.2.0.tgz", @@ -4402,6 +5390,12 @@ "execa": "^0.7.0" } }, + "text-table": { + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/text-table/-/text-table-0.2.0.tgz", + "integrity": "sha1-f17oI66AUgfACvLfSoTsP8+lcLQ=", + "dev": true + }, "then-request": { "version": "6.0.2", "resolved": "https://registry.npmjs.org/then-request/-/then-request-6.0.2.tgz", @@ -4429,12 +5423,27 @@ } } }, + "through": { + "version": "2.3.8", + "resolved": "https://registry.npmjs.org/through/-/through-2.3.8.tgz", + "integrity": "sha1-DdTJ/6q8NXlgsbckEV1+Doai4fU=", + "dev": true + }, "timed-out": { "version": "4.0.1", "resolved": "https://registry.npmjs.org/timed-out/-/timed-out-4.0.1.tgz", "integrity": "sha1-8y6srFoXW+ol1/q1Zas+2HQe9W8=", "dev": true }, + "tmp": { + "version": "0.0.33", + "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.0.33.tgz", + "integrity": "sha512-jRCJlojKnZ3addtTOjdIqoRuPEKBvNXcGYqzO6zWZX8KfKEpnGY5jfggJQ3EjKuu8D4bJRr0y+cYJFmYbImXGw==", + "dev": true, + "requires": { + "os-tmpdir": "~1.0.2" + } + }, "to-object-path": { "version": "0.3.0", "resolved": "https://registry.npmjs.org/to-object-path/-/to-object-path-0.3.0.tgz", @@ -4551,6 +5560,12 @@ } } }, + "tslib": { + "version": "1.9.3", + "resolved": "https://registry.npmjs.org/tslib/-/tslib-1.9.3.tgz", + "integrity": "sha512-4krF8scpejhaOgqzBEcGM7yDIEfi0/8+8zDRZhNZZ2kjmHJ4hv3zCbQWxoJGz1iw5U0Jl0nma13xzHXcncMavQ==", + "dev": true + }, "tsort": { "version": "0.0.1", "resolved": "https://registry.npmjs.org/tsort/-/tsort-0.0.1.tgz", @@ -4918,6 +5933,15 @@ "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=" }, + "write": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/write/-/write-1.0.3.tgz", + "integrity": "sha512-/lg70HAjtkUgWPVZhZcm+T4hkL8Zbtp1nFNOn3lRrxnlv50SRBv7cR7RqR+GMsd3hUXy9hWBo4CHTbFTcOYwig==", + "dev": true, + "requires": { + "mkdirp": "^0.5.1" + } + }, "write-file-atomic": { "version": "2.4.2", "resolved": "https://registry.npmjs.org/write-file-atomic/-/write-file-atomic-2.4.2.tgz", diff --git a/package.json b/package.json index abde3d9fe..f8897dfe5 100644 --- a/package.json +++ b/package.json @@ -8,6 +8,8 @@ "test:gasreport": "GASREPORT=true npm run test", "compile": "truffle compile && truffle compile spuriousDragon", "flatten": "bash flatten.sh", + "lint:js": "eslint .", + "lint:js:fix": "eslint . --fix", "watch-tests": "./node_modules/.bin/nodemon ./node_modules/.bin/truffle test --network test" }, "author": "POA network", @@ -21,8 +23,15 @@ "chai": "^4.2.0", "chai-as-promised": "^7.1.1", "chai-bn": "^0.1.1", + "eslint": "^5.16.0", + "eslint-config-airbnb-base": "^13.1.0", + "eslint-config-prettier": "^4.2.0", + "eslint-plugin-import": "^2.17.2", + "eslint-plugin-node": "^9.0.1", + "eslint-plugin-prettier": "^3.0.1", "eth-gas-reporter": "^0.1.12", "nodemon": "^1.17.3", + "prettier": "^1.17.1", "solidity-coverage": "^0.5.11", "truffle-flattener": "^1.2.3" } diff --git a/test/erc_to_erc/foreign_bridge.test.js b/test/erc_to_erc/foreign_bridge.test.js index ff50ca026..7164bfcda 100644 --- a/test/erc_to_erc/foreign_bridge.test.js +++ b/test/erc_to_erc/foreign_bridge.test.js @@ -1,39 +1,41 @@ -const ForeignBridge = artifacts.require("ForeignBridgeErcToErc.sol"); -const ForeignBridgeErc677ToErc677 = artifacts.require("ForeignBridgeErc677ToErc677.sol"); -const ForeignBridgeV2 = artifacts.require("ForeignBridgeV2.sol"); -const BridgeValidators = artifacts.require("BridgeValidators.sol"); -const EternalStorageProxy = artifacts.require("EternalStorageProxy.sol"); -const ERC677BridgeToken = artifacts.require("ERC677BridgeToken.sol"); - -const { expect } = require('chai'); -const { ERROR_MSG, ZERO_ADDRESS, toBN } = require('../setup'); -const { createMessage, sign, signatureToVRS, ether, getEvents } = require('../helpers/helpers'); - -const oneEther = ether('1'); -const halfEther = ether('0.5'); -const requireBlockConfirmations = 8; +const ForeignBridge = artifacts.require('ForeignBridgeErcToErc.sol') +const ForeignBridgeErc677ToErc677 = artifacts.require('ForeignBridgeErc677ToErc677.sol') +const ForeignBridgeV2 = artifacts.require('ForeignBridgeV2.sol') +const BridgeValidators = artifacts.require('BridgeValidators.sol') +const EternalStorageProxy = artifacts.require('EternalStorageProxy.sol') +const ERC677BridgeToken = artifacts.require('ERC677BridgeToken.sol') + +const { expect } = require('chai') +const { ERROR_MSG, ZERO_ADDRESS, toBN } = require('../setup') +const { createMessage, sign, signatureToVRS, ether, getEvents } = require('../helpers/helpers') + +const oneEther = ether('1') +const halfEther = ether('0.5') +const requireBlockConfirmations = 8 const gasPrice = web3.utils.toWei('1', 'gwei') const homeDailyLimit = oneEther const homeMaxPerTx = halfEther const maxPerTx = halfEther -const minPerTx = ether('0.01'); +const minPerTx = ether('0.01') const dailyLimit = oneEther const ZERO = toBN(0) - -contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { - let validatorContract, authorities, owner, token; +contract('ForeignBridge_ERC20_to_ERC20', async accounts => { + let validatorContract + let authorities + let owner + let token before(async () => { validatorContract = await BridgeValidators.new() - authorities = [accounts[1], accounts[2]]; + authorities = [accounts[1], accounts[2]] owner = accounts[0] await validatorContract.initialize(1, authorities, owner) }) describe('#initialize', async () => { it('should initialize', async () => { - token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); - let foreignBridge = await ForeignBridge.new(); + token = await ERC677BridgeToken.new('Some ERC20', 'RSZT', 18) + const foreignBridge = await ForeignBridge.new() expect(await foreignBridge.erc20token()).to.be.equal(ZERO_ADDRESS) expect(await foreignBridge.validatorContract()).to.be.equal(ZERO_ADDRESS) @@ -41,20 +43,97 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { expect(await foreignBridge.isInitialized()).to.be.equal(false) expect(await foreignBridge.requiredBlockConfirmations()).to.be.bignumber.equal(ZERO) - await foreignBridge.initialize(ZERO_ADDRESS, token.address, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.initialize(validatorContract.address, ZERO_ADDRESS, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.initialize(validatorContract.address, owner, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.initialize(validatorContract.address, token.address, 0, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.initialize(validatorContract.address, token.address, requireBlockConfirmations, 0, maxPerTx, homeDailyLimit, homeMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.initialize(owner, token.address, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - - await foreignBridge.initialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner); + await foreignBridge + .initialize( + ZERO_ADDRESS, + token.address, + requireBlockConfirmations, + gasPrice, + maxPerTx, + homeDailyLimit, + homeMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await foreignBridge + .initialize( + validatorContract.address, + ZERO_ADDRESS, + requireBlockConfirmations, + gasPrice, + maxPerTx, + homeDailyLimit, + homeMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await foreignBridge + .initialize( + validatorContract.address, + owner, + requireBlockConfirmations, + gasPrice, + maxPerTx, + homeDailyLimit, + homeMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await foreignBridge + .initialize( + validatorContract.address, + token.address, + 0, + gasPrice, + maxPerTx, + homeDailyLimit, + homeMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await foreignBridge + .initialize( + validatorContract.address, + token.address, + requireBlockConfirmations, + 0, + maxPerTx, + homeDailyLimit, + homeMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await foreignBridge + .initialize( + owner, + token.address, + requireBlockConfirmations, + gasPrice, + maxPerTx, + homeDailyLimit, + homeMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + + await foreignBridge.initialize( + validatorContract.address, + token.address, + requireBlockConfirmations, + gasPrice, + maxPerTx, + homeDailyLimit, + homeMaxPerTx, + owner + ) expect(await foreignBridge.erc20token()).to.be.equal(token.address) expect(await foreignBridge.isInitialized()).to.be.equal(true) expect(await foreignBridge.validatorContract()).to.be.equal(validatorContract.address) expect(await foreignBridge.deployedAtBlock()).to.be.bignumber.above(ZERO) - expect(await foreignBridge.requiredBlockConfirmations()).to.be.bignumber.equal(requireBlockConfirmations.toString()) + expect(await foreignBridge.requiredBlockConfirmations()).to.be.bignumber.equal( + requireBlockConfirmations.toString() + ) expect(await foreignBridge.gasPrice()).to.be.bignumber.equal(gasPrice) const bridgeMode = '0xba4690f5' // 4 bytes of keccak256('erc-to-erc-core') expect(await foreignBridge.getBridgeMode()).to.be.equal(bridgeMode) @@ -66,54 +145,63 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { }) describe('#executeSignatures', async () => { - const value = ether('0.25'); + const value = ether('0.25') let foreignBridge beforeEach(async () => { foreignBridge = await ForeignBridge.new() - token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); - await foreignBridge.initialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner); - await token.mint(foreignBridge.address,value); + token = await ERC677BridgeToken.new('Some ERC20', 'RSZT', 18) + await foreignBridge.initialize( + validatorContract.address, + token.address, + requireBlockConfirmations, + gasPrice, + maxPerTx, + homeDailyLimit, + homeMaxPerTx, + owner + ) + await token.mint(foreignBridge.address, value) }) it('should allow to executeSignatures', async () => { - const recipientAccount = accounts[3]; + const recipientAccount = accounts[3] const balanceBefore = await token.balanceOf(recipientAccount) - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' + const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address) const signature = await sign(authorities[0], message) - const vrs = signatureToVRS(signature); + const vrs = signatureToVRS(signature) false.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) - const {logs} = await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.fulfilled - logs[0].event.should.be.equal("RelayedMessage") + const { logs } = await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.fulfilled + logs[0].event.should.be.equal('RelayedMessage') logs[0].args.recipient.should.be.equal(recipientAccount) logs[0].args.value.should.be.bignumber.equal(value) - const balanceAfter = await token.balanceOf(recipientAccount); - const balanceAfterBridge = await token.balanceOf(foreignBridge.address); + const balanceAfter = await token.balanceOf(recipientAccount) + const balanceAfterBridge = await token.balanceOf(foreignBridge.address) balanceAfter.should.be.bignumber.equal(balanceBefore.add(value)) balanceAfterBridge.should.be.bignumber.equal(ZERO) true.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) }) - it('should allow second withdrawal with different transactionHash but same recipient and value', async ()=> { - const recipientAccount = accounts[3]; + it('should allow second withdrawal with different transactionHash but same recipient and value', async () => { + const recipientAccount = accounts[3] const balanceBefore = await token.balanceOf(recipientAccount) // tx 1 - const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); + const transactionHash = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' + const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address) const signature = await sign(authorities[0], message) - const vrs = signatureToVRS(signature); + const vrs = signatureToVRS(signature) false.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.fulfilled // tx 2 - await token.mint(foreignBridge.address,value); - const transactionHash2 = "0x77a496628a776a03d58d7e6059a5937f04bebd8ba4ff89f76dd4bb8ba7e291ee"; - const message2 = createMessage(recipientAccount, value, transactionHash2, foreignBridge.address); + await token.mint(foreignBridge.address, value) + const transactionHash2 = '0x77a496628a776a03d58d7e6059a5937f04bebd8ba4ff89f76dd4bb8ba7e291ee' + const message2 = createMessage(recipientAccount, value, transactionHash2, foreignBridge.address) const signature2 = await sign(authorities[0], message2) - const vrs2 = signatureToVRS(signature2); + const vrs2 = signatureToVRS(signature2) false.should.be.equal(await foreignBridge.relayedMessages(transactionHash2)) - const {logs} = await foreignBridge.executeSignatures([vrs2.v], [vrs2.r], [vrs2.s], message2).should.be.fulfilled + const { logs } = await foreignBridge.executeSignatures([vrs2.v], [vrs2.r], [vrs2.s], message2).should.be.fulfilled - logs[0].event.should.be.equal("RelayedMessage") + logs[0].event.should.be.equal('RelayedMessage') logs[0].args.recipient.should.be.equal(recipientAccount) logs[0].args.value.should.be.bignumber.equal(value) const balanceAfter = await token.balanceOf(recipientAccount) @@ -123,104 +211,126 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { }) it('should not allow second withdraw (replay attack) with same transactionHash but different recipient', async () => { - const recipientAccount = accounts[3]; + const recipientAccount = accounts[3] // tx 1 - const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); + const transactionHash = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' + const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address) const signature = await sign(authorities[0], message) - const vrs = signatureToVRS(signature); + const vrs = signatureToVRS(signature) false.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.fulfilled // tx 2 - await token.mint(foreignBridge.address,value); - const message2 = createMessage(accounts[4], value, transactionHash, foreignBridge.address); + await token.mint(foreignBridge.address, value) + const message2 = createMessage(accounts[4], value, transactionHash, foreignBridge.address) const signature2 = await sign(authorities[0], message2) - const vrs2 = signatureToVRS(signature2); + const vrs2 = signatureToVRS(signature2) true.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) await foreignBridge.executeSignatures([vrs2.v], [vrs2.r], [vrs2.s], message2).should.be.rejectedWith(ERROR_MSG) }) it('should not allow withdraw over home max tx limit', async () => { - const recipientAccount = accounts[3]; - const invalidValue = ether('0.75'); - await token.mint(foreignBridge.address, ether('5')); + const recipientAccount = accounts[3] + const invalidValue = ether('0.75') + await token.mint(foreignBridge.address, ether('5')) - const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - const message = createMessage(recipientAccount, invalidValue, transactionHash, foreignBridge.address); + const transactionHash = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' + const message = createMessage(recipientAccount, invalidValue, transactionHash, foreignBridge.address) const signature = await sign(authorities[0], message) - const vrs = signatureToVRS(signature); + const vrs = signatureToVRS(signature) await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.rejectedWith(ERROR_MSG) }) it('should not allow withdraw over daily home limit', async () => { - const recipientAccount = accounts[3]; - await token.mint(foreignBridge.address, ether('5')); + const recipientAccount = accounts[3] + await token.mint(foreignBridge.address, ether('5')) - const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - const message = createMessage(recipientAccount, halfEther, transactionHash, foreignBridge.address); + const transactionHash = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' + const message = createMessage(recipientAccount, halfEther, transactionHash, foreignBridge.address) const signature = await sign(authorities[0], message) - const vrs = signatureToVRS(signature); + const vrs = signatureToVRS(signature) await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.fulfilled - const transactionHash2 = "0x69debd8fd1923c9cb3cd8ef6461e2740b2d037943b941729d5a47671a2bb8712"; - const message2 = createMessage(recipientAccount, halfEther, transactionHash2, foreignBridge.address); + const transactionHash2 = '0x69debd8fd1923c9cb3cd8ef6461e2740b2d037943b941729d5a47671a2bb8712' + const message2 = createMessage(recipientAccount, halfEther, transactionHash2, foreignBridge.address) const signature2 = await sign(authorities[0], message2) - const vrs2 = signatureToVRS(signature2); + const vrs2 = signatureToVRS(signature2) await foreignBridge.executeSignatures([vrs2.v], [vrs2.r], [vrs2.s], message2).should.be.fulfilled - const transactionHash3 = "0x022695428093bb292db8e48bd1417c5e1b84c0bf673bd0fff23ed0fb6495b872"; - const message3 = createMessage(recipientAccount, halfEther, transactionHash3, foreignBridge.address); + const transactionHash3 = '0x022695428093bb292db8e48bd1417c5e1b84c0bf673bd0fff23ed0fb6495b872' + const message3 = createMessage(recipientAccount, halfEther, transactionHash3, foreignBridge.address) const signature3 = await sign(authorities[0], message3) - const vrs3 = signatureToVRS(signature3); + const vrs3 = signatureToVRS(signature3) await foreignBridge.executeSignatures([vrs3.v], [vrs3.r], [vrs3.s], message3).should.be.rejectedWith(ERROR_MSG) }) }) describe('#withdraw with 2 minimum signatures', async () => { - let multisigValidatorContract, twoAuthorities, ownerOfValidatorContract, foreignBridgeWithMultiSignatures + let multisigValidatorContract + let twoAuthorities + let ownerOfValidatorContract + let foreignBridgeWithMultiSignatures const value = halfEther beforeEach(async () => { multisigValidatorContract = await BridgeValidators.new() - token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); - twoAuthorities = [accounts[0], accounts[1]]; + token = await ERC677BridgeToken.new('Some ERC20', 'RSZT', 18) + twoAuthorities = [accounts[0], accounts[1]] ownerOfValidatorContract = accounts[3] - await multisigValidatorContract.initialize(2, twoAuthorities, ownerOfValidatorContract, {from: ownerOfValidatorContract}) + await multisigValidatorContract.initialize(2, twoAuthorities, ownerOfValidatorContract, { + from: ownerOfValidatorContract + }) foreignBridgeWithMultiSignatures = await ForeignBridge.new() - await foreignBridgeWithMultiSignatures.initialize(multisigValidatorContract.address, token.address, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner, {from: ownerOfValidatorContract}); - await token.mint(foreignBridgeWithMultiSignatures.address,value); + await foreignBridgeWithMultiSignatures.initialize( + multisigValidatorContract.address, + token.address, + requireBlockConfirmations, + gasPrice, + maxPerTx, + homeDailyLimit, + homeMaxPerTx, + owner, + { from: ownerOfValidatorContract } + ) + await token.mint(foreignBridgeWithMultiSignatures.address, value) }) it('withdraw should fail if not enough signatures are provided', async () => { - - const recipientAccount = accounts[4]; + const recipientAccount = accounts[4] // msg 1 - const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - const message = createMessage(recipientAccount, value, transactionHash, foreignBridgeWithMultiSignatures.address); + const transactionHash = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' + const message = createMessage(recipientAccount, value, transactionHash, foreignBridgeWithMultiSignatures.address) const signature = await sign(twoAuthorities[0], message) - const vrs = signatureToVRS(signature); + const vrs = signatureToVRS(signature) false.should.be.equal(await foreignBridgeWithMultiSignatures.relayedMessages(transactionHash)) - await foreignBridgeWithMultiSignatures.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.rejectedWith(ERROR_MSG) + await foreignBridgeWithMultiSignatures + .executeSignatures([vrs.v], [vrs.r], [vrs.s], message) + .should.be.rejectedWith(ERROR_MSG) // msg 2 const signature2 = await sign(twoAuthorities[1], message) - const vrs2 = signatureToVRS(signature2); - const {logs} = await foreignBridgeWithMultiSignatures.executeSignatures([vrs.v, vrs2.v], [vrs.r, vrs2.r], [vrs.s, vrs2.s], message).should.be.fulfilled; - - logs[0].event.should.be.equal("RelayedMessage") + const vrs2 = signatureToVRS(signature2) + const { logs } = await foreignBridgeWithMultiSignatures.executeSignatures( + [vrs.v, vrs2.v], + [vrs.r, vrs2.r], + [vrs.s, vrs2.s], + message + ).should.be.fulfilled + + logs[0].event.should.be.equal('RelayedMessage') logs[0].args.recipient.should.be.equal(recipientAccount) logs[0].args.value.should.be.bignumber.equal(value) true.should.be.equal(await foreignBridgeWithMultiSignatures.relayedMessages(transactionHash)) - }) it('withdraw should fail if duplicate signature is provided', async () => { - const recipientAccount = accounts[4]; - const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - const message = createMessage(recipientAccount, value, transactionHash, foreignBridgeWithMultiSignatures.address); + const recipientAccount = accounts[4] + const transactionHash = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' + const message = createMessage(recipientAccount, value, transactionHash, foreignBridgeWithMultiSignatures.address) const signature = await sign(twoAuthorities[0], message) - const vrs = signatureToVRS(signature); + const vrs = signatureToVRS(signature) false.should.be.equal(await foreignBridgeWithMultiSignatures.relayedMessages(transactionHash)) - await foreignBridgeWithMultiSignatures.executeSignatures([vrs.v, vrs.v], [vrs.r, vrs.r], [vrs.s, vrs.s], message).should.be.rejectedWith(ERROR_MSG) + await foreignBridgeWithMultiSignatures + .executeSignatures([vrs.v, vrs.v], [vrs.r, vrs.r], [vrs.s, vrs.s], message) + .should.be.rejectedWith(ERROR_MSG) }) it('works with 5 validators and 3 required signatures', async () => { @@ -229,31 +339,44 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { const ownerOfValidators = accounts[0] const validatorContractWith3Signatures = await BridgeValidators.new() await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) - const erc20Token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); + const erc20Token = await ERC677BridgeToken.new('Some ERC20', 'RSZT', 18) const value = halfEther const foreignBridgeWithThreeSigs = await ForeignBridge.new() - await foreignBridgeWithThreeSigs.initialize(validatorContractWith3Signatures.address, erc20Token.address, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner); - await erc20Token.mint(foreignBridgeWithThreeSigs.address, value); - - const txHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - const message = createMessage(recipient, value, txHash, foreignBridgeWithThreeSigs.address); + await foreignBridgeWithThreeSigs.initialize( + validatorContractWith3Signatures.address, + erc20Token.address, + requireBlockConfirmations, + gasPrice, + maxPerTx, + homeDailyLimit, + homeMaxPerTx, + owner + ) + await erc20Token.mint(foreignBridgeWithThreeSigs.address, value) + + const txHash = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' + const message = createMessage(recipient, value, txHash, foreignBridgeWithThreeSigs.address) // signature 1 const signature = await sign(authoritiesFiveAccs[0], message) - const vrs = signatureToVRS(signature); + const vrs = signatureToVRS(signature) // signature 2 const signature2 = await sign(authoritiesFiveAccs[1], message) - const vrs2 = signatureToVRS(signature2); + const vrs2 = signatureToVRS(signature2) // signature 3 const signature3 = await sign(authoritiesFiveAccs[2], message) - const vrs3 = signatureToVRS(signature3); - - - const {logs} = await foreignBridgeWithThreeSigs.executeSignatures([vrs.v, vrs2.v, vrs3.v], [vrs.r, vrs2.r, vrs3.r], [vrs.s, vrs2.s, vrs3.s], message).should.be.fulfilled; - logs[0].event.should.be.equal("RelayedMessage") + const vrs3 = signatureToVRS(signature3) + + const { logs } = await foreignBridgeWithThreeSigs.executeSignatures( + [vrs.v, vrs2.v, vrs3.v], + [vrs.r, vrs2.r, vrs3.r], + [vrs.s, vrs2.s, vrs3.s], + message + ).should.be.fulfilled + logs[0].event.should.be.equal('RelayedMessage') logs[0].args.recipient.should.be.equal(recipient) logs[0].args.value.should.be.bignumber.equal(value) true.should.be.equal(await foreignBridgeWithThreeSigs.relayedMessages(txHash)) @@ -263,173 +386,241 @@ contract('ForeignBridge_ERC20_to_ERC20', async (accounts) => { it('can be upgraded', async () => { const REQUIRED_NUMBER_OF_VALIDATORS = 1 const VALIDATORS = [accounts[1]] - const PROXY_OWNER = accounts[0] + const PROXY_OWNER = accounts[0] // Validators Contract - let validatorsProxy = await EternalStorageProxy.new().should.be.fulfilled; - const validatorsContractImpl = await BridgeValidators.new().should.be.fulfilled; - await validatorsProxy.upgradeTo('1', validatorsContractImpl.address).should.be.fulfilled; + let validatorsProxy = await EternalStorageProxy.new().should.be.fulfilled + const validatorsContractImpl = await BridgeValidators.new().should.be.fulfilled + await validatorsProxy.upgradeTo('1', validatorsContractImpl.address).should.be.fulfilled validatorsContractImpl.address.should.be.equal(await validatorsProxy.implementation()) - validatorsProxy = await BridgeValidators.at(validatorsProxy.address); - await validatorsProxy.initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, PROXY_OWNER).should.be.fulfilled; - let token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); + validatorsProxy = await BridgeValidators.at(validatorsProxy.address) + await validatorsProxy.initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, PROXY_OWNER).should.be.fulfilled + const token = await ERC677BridgeToken.new('Some ERC20', 'RSZT', 18) // ForeignBridge V1 Contract - let foreignBridgeProxy = await EternalStorageProxy.new().should.be.fulfilled; - const foreignBridgeImpl = await ForeignBridge.new().should.be.fulfilled; - await foreignBridgeProxy.upgradeTo('1', foreignBridgeImpl.address).should.be.fulfilled; - - foreignBridgeProxy = await ForeignBridge.at(foreignBridgeProxy.address); - await foreignBridgeProxy.initialize(validatorsProxy.address, token.address, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner) + let foreignBridgeProxy = await EternalStorageProxy.new().should.be.fulfilled + const foreignBridgeImpl = await ForeignBridge.new().should.be.fulfilled + await foreignBridgeProxy.upgradeTo('1', foreignBridgeImpl.address).should.be.fulfilled + + foreignBridgeProxy = await ForeignBridge.at(foreignBridgeProxy.address) + await foreignBridgeProxy.initialize( + validatorsProxy.address, + token.address, + requireBlockConfirmations, + gasPrice, + maxPerTx, + homeDailyLimit, + homeMaxPerTx, + owner + ) // Deploy V2 - let foreignImplV2 = await ForeignBridgeV2.new(); - let foreignBridgeProxyUpgrade = await EternalStorageProxy.at(foreignBridgeProxy.address); - await foreignBridgeProxyUpgrade.upgradeTo('2', foreignImplV2.address).should.be.fulfilled; + const foreignImplV2 = await ForeignBridgeV2.new() + const foreignBridgeProxyUpgrade = await EternalStorageProxy.at(foreignBridgeProxy.address) + await foreignBridgeProxyUpgrade.upgradeTo('2', foreignImplV2.address).should.be.fulfilled foreignImplV2.address.should.be.equal(await foreignBridgeProxyUpgrade.implementation()) - let foreignBridgeV2Proxy = await ForeignBridgeV2.at(foreignBridgeProxy.address) - await foreignBridgeV2Proxy.doSomething(accounts[2], {from: accounts[4]}).should.be.rejectedWith(ERROR_MSG) - await foreignBridgeV2Proxy.doSomething(accounts[2], {from: PROXY_OWNER}).should.be.fulfilled; - (await foreignBridgeV2Proxy.something()).should.be.equal(accounts[2]) + const foreignBridgeV2Proxy = await ForeignBridgeV2.at(foreignBridgeProxy.address) + await foreignBridgeV2Proxy.doSomething(accounts[2], { from: accounts[4] }).should.be.rejectedWith(ERROR_MSG) + await foreignBridgeV2Proxy.doSomething(accounts[2], { from: PROXY_OWNER }).should.be.fulfilled + ;(await foreignBridgeV2Proxy.something()).should.be.equal(accounts[2]) }) it('can be deployed via upgradeToAndCall', async () => { const tokenAddress = token.address const validatorsAddress = validatorContract.address - let storageProxy = await EternalStorageProxy.new().should.be.fulfilled; - let foreignBridge = await ForeignBridge.new(); - const data = foreignBridge.contract.methods.initialize( - validatorsAddress, tokenAddress, requireBlockConfirmations, gasPrice, '2', '3', '2', owner).encodeABI() - await storageProxy.upgradeToAndCall('1', foreignBridge.address, data).should.be.fulfilled; - let finalContract = await ForeignBridge.at(storageProxy.address); - true.should.be.equal(await finalContract.isInitialized()); + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled + const foreignBridge = await ForeignBridge.new() + const data = foreignBridge.contract.methods + .initialize(validatorsAddress, tokenAddress, requireBlockConfirmations, gasPrice, '2', '3', '2', owner) + .encodeABI() + await storageProxy.upgradeToAndCall('1', foreignBridge.address, data).should.be.fulfilled + const finalContract = await ForeignBridge.at(storageProxy.address) + true.should.be.equal(await finalContract.isInitialized()) validatorsAddress.should.be.equal(await finalContract.validatorContract()) }) }) describe('#claimTokens', async () => { it('can send erc20', async () => { - const owner = accounts[0]; - token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); - const foreignBridgeImpl = await ForeignBridge.new(); - const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + const owner = accounts[0] + token = await ERC677BridgeToken.new('Some ERC20', 'RSZT', 18) + const foreignBridgeImpl = await ForeignBridge.new() + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled await storageProxy.upgradeTo('1', foreignBridgeImpl.address).should.be.fulfilled - const foreignBridge = await ForeignBridge.at(storageProxy.address); - await foreignBridge.initialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner); - - let tokenSecond = await ERC677BridgeToken.new("Roman Token", "RST", 18); - - await tokenSecond.mint(accounts[0], halfEther).should.be.fulfilled; + const foreignBridge = await ForeignBridge.at(storageProxy.address) + await foreignBridge.initialize( + validatorContract.address, + token.address, + requireBlockConfirmations, + gasPrice, + maxPerTx, + homeDailyLimit, + homeMaxPerTx, + owner + ) + + const tokenSecond = await ERC677BridgeToken.new('Roman Token', 'RST', 18) + + await tokenSecond.mint(accounts[0], halfEther).should.be.fulfilled expect(await tokenSecond.balanceOf(accounts[0])).to.be.bignumber.equal(halfEther) - await tokenSecond.transfer(foreignBridge.address, halfEther); + await tokenSecond.transfer(foreignBridge.address, halfEther) expect(await tokenSecond.balanceOf(accounts[0])).to.be.bignumber.equal(ZERO) expect(await tokenSecond.balanceOf(foreignBridge.address)).to.be.bignumber.equal(halfEther) - await foreignBridge.claimTokens(tokenSecond.address, accounts[3], {from: owner}); + await foreignBridge.claimTokens(tokenSecond.address, accounts[3], { from: owner }) expect(await tokenSecond.balanceOf(foreignBridge.address)).to.be.bignumber.equal(ZERO) expect(await tokenSecond.balanceOf(accounts[3])).to.be.bignumber.equal(halfEther) }) }) describe('#ForeignBridgeErc677ToErc677_onTokenTransfer', async () => { - it('can only be called from token contract', async ()=> { + it('can only be called from token contract', async () => { const owner = accounts[3] const user = accounts[4] - token = await ERC677BridgeToken.new("TEST", "TST", 18, {from: owner}); - const foreignBridge = await ForeignBridgeErc677ToErc677.new(); - await foreignBridge.initialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, dailyLimit, maxPerTx, minPerTx, homeDailyLimit, homeMaxPerTx, owner); - - await token.mint(user, halfEther, {from: owner }).should.be.fulfilled; - await token.transferOwnership(foreignBridge.address, {from: owner}); - await foreignBridge.onTokenTransfer(user, halfEther, '0x00', {from: owner}).should.be.rejectedWith(ERROR_MSG); - - await token.transferAndCall(foreignBridge.address, halfEther, '0x00', {from: user}).should.be.fulfilled; + token = await ERC677BridgeToken.new('TEST', 'TST', 18, { from: owner }) + const foreignBridge = await ForeignBridgeErc677ToErc677.new() + await foreignBridge.initialize( + validatorContract.address, + token.address, + requireBlockConfirmations, + gasPrice, + dailyLimit, + maxPerTx, + minPerTx, + homeDailyLimit, + homeMaxPerTx, + owner + ) + + await token.mint(user, halfEther, { from: owner }).should.be.fulfilled + await token.transferOwnership(foreignBridge.address, { from: owner }) + await foreignBridge.onTokenTransfer(user, halfEther, '0x00', { from: owner }).should.be.rejectedWith(ERROR_MSG) + + await token.transferAndCall(foreignBridge.address, halfEther, '0x00', { from: user }).should.be.fulfilled expect(await token.totalSupply()).to.be.bignumber.equal(halfEther) expect(await token.balanceOf(user)).to.be.bignumber.equal(ZERO) expect(await token.balanceOf(foreignBridge.address)).to.be.bignumber.equal(halfEther) - const events = await getEvents(foreignBridge, {event: 'UserRequestForAffirmation'}); + const events = await getEvents(foreignBridge, { event: 'UserRequestForAffirmation' }) expect(events[0].returnValues.recipient).to.be.equal(user) expect(toBN(events[0].returnValues.value)).to.be.bignumber.equal(halfEther) }) it('should not allow to transfer more than maxPerTx limit', async () => { const owner = accounts[3] const user = accounts[4] - const valueMoreThanLimit = halfEther.add(toBN(1)); - token = await ERC677BridgeToken.new("TEST", "TST", 18, {from: owner}); - const foreignBridge = await ForeignBridgeErc677ToErc677.new(); - await foreignBridge.initialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, dailyLimit, maxPerTx, minPerTx, homeDailyLimit, homeMaxPerTx, owner); - - await token.mint(user, valueMoreThanLimit, {from: owner }).should.be.fulfilled; - await token.transferOwnership(foreignBridge.address, {from: owner}); - - await token.transferAndCall(foreignBridge.address, valueMoreThanLimit, '0x00', {from: user}).should.be.rejectedWith(ERROR_MSG); - valueMoreThanLimit.should.be.bignumber.equal(await token.totalSupply()); - valueMoreThanLimit.should.be.bignumber.equal(await token.balanceOf(user)); - - await token.transferAndCall(foreignBridge.address, halfEther, '0x00', {from: user}).should.be.fulfilled; + const valueMoreThanLimit = halfEther.add(toBN(1)) + token = await ERC677BridgeToken.new('TEST', 'TST', 18, { from: owner }) + const foreignBridge = await ForeignBridgeErc677ToErc677.new() + await foreignBridge.initialize( + validatorContract.address, + token.address, + requireBlockConfirmations, + gasPrice, + dailyLimit, + maxPerTx, + minPerTx, + homeDailyLimit, + homeMaxPerTx, + owner + ) + + await token.mint(user, valueMoreThanLimit, { from: owner }).should.be.fulfilled + await token.transferOwnership(foreignBridge.address, { from: owner }) + + await token + .transferAndCall(foreignBridge.address, valueMoreThanLimit, '0x00', { from: user }) + .should.be.rejectedWith(ERROR_MSG) + valueMoreThanLimit.should.be.bignumber.equal(await token.totalSupply()) + valueMoreThanLimit.should.be.bignumber.equal(await token.balanceOf(user)) + + await token.transferAndCall(foreignBridge.address, halfEther, '0x00', { from: user }).should.be.fulfilled expect(await token.totalSupply()).to.be.bignumber.equal(valueMoreThanLimit) expect(await token.balanceOf(user)).to.be.bignumber.equal('1') expect(await token.balanceOf(foreignBridge.address)).to.be.bignumber.equal(halfEther) - const events = await getEvents(foreignBridge, {event: 'UserRequestForAffirmation'}); + const events = await getEvents(foreignBridge, { event: 'UserRequestForAffirmation' }) expect(events[0].returnValues.recipient).to.be.equal(user) expect(toBN(events[0].returnValues.value)).to.be.bignumber.equal(halfEther) }) it('should only let to transfer within daily limit', async () => { const owner = accounts[3] const user = accounts[4] - const valueMoreThanLimit = halfEther.add(toBN(1)); - token = await ERC677BridgeToken.new("TEST", "TST", 18, {from: owner}); - const foreignBridge = await ForeignBridgeErc677ToErc677.new(); - await foreignBridge.initialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, dailyLimit, maxPerTx, minPerTx, homeDailyLimit, homeMaxPerTx, owner); - - await token.mint(user, oneEther.add(toBN(1)), {from: owner }).should.be.fulfilled; - await token.transferOwnership(foreignBridge.address, {from: owner}); - - await token.transferAndCall(foreignBridge.address, valueMoreThanLimit, '0x00', {from: user}).should.be.rejectedWith(ERROR_MSG); - oneEther.add(toBN(1)).should.be.bignumber.equal(await token.totalSupply()); - oneEther.add(toBN(1)).should.be.bignumber.equal(await token.balanceOf(user)); - - await token.transferAndCall(foreignBridge.address, halfEther, '0x00', {from: user}).should.be.fulfilled; - oneEther.add(toBN(1)).should.be.bignumber.equal(await token.totalSupply()); - valueMoreThanLimit.should.be.bignumber.equal(await token.balanceOf(user)); - const events = await getEvents(foreignBridge, {event: 'UserRequestForAffirmation'}); + const valueMoreThanLimit = halfEther.add(toBN(1)) + token = await ERC677BridgeToken.new('TEST', 'TST', 18, { from: owner }) + const foreignBridge = await ForeignBridgeErc677ToErc677.new() + await foreignBridge.initialize( + validatorContract.address, + token.address, + requireBlockConfirmations, + gasPrice, + dailyLimit, + maxPerTx, + minPerTx, + homeDailyLimit, + homeMaxPerTx, + owner + ) + + await token.mint(user, oneEther.add(toBN(1)), { from: owner }).should.be.fulfilled + await token.transferOwnership(foreignBridge.address, { from: owner }) + + await token + .transferAndCall(foreignBridge.address, valueMoreThanLimit, '0x00', { from: user }) + .should.be.rejectedWith(ERROR_MSG) + oneEther.add(toBN(1)).should.be.bignumber.equal(await token.totalSupply()) + oneEther.add(toBN(1)).should.be.bignumber.equal(await token.balanceOf(user)) + + await token.transferAndCall(foreignBridge.address, halfEther, '0x00', { from: user }).should.be.fulfilled + oneEther.add(toBN(1)).should.be.bignumber.equal(await token.totalSupply()) + valueMoreThanLimit.should.be.bignumber.equal(await token.balanceOf(user)) + const events = await getEvents(foreignBridge, { event: 'UserRequestForAffirmation' }) expect(events[0].returnValues.recipient).to.be.equal(user) expect(toBN(events[0].returnValues.value)).to.be.bignumber.equal(halfEther) - - await token.transferAndCall(foreignBridge.address, halfEther, '0x00', {from: user}).should.be.fulfilled; + await token.transferAndCall(foreignBridge.address, halfEther, '0x00', { from: user }).should.be.fulfilled expect(await token.totalSupply()).to.be.bignumber.equal(oneEther.add(toBN(1))) expect(await token.balanceOf(user)).to.be.bignumber.equal('1') expect(await token.balanceOf(foreignBridge.address)).to.be.bignumber.equal(oneEther) - await token.transferAndCall(foreignBridge.address, '1', '0x00', {from: user}).should.be.rejectedWith(ERROR_MSG); + await token.transferAndCall(foreignBridge.address, '1', '0x00', { from: user }).should.be.rejectedWith(ERROR_MSG) }) it('should not let to transfer less than minPerTx', async () => { const owner = accounts[3] const user = accounts[4] - const valueLessThanMinPerTx = minPerTx.sub(toBN(1)); - token = await ERC677BridgeToken.new("TEST", "TST", 18, {from: owner}); - const foreignBridge = await ForeignBridgeErc677ToErc677.new(); - await foreignBridge.initialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, dailyLimit, maxPerTx, minPerTx, homeDailyLimit, homeMaxPerTx, owner); - - await token.mint(user, oneEther, {from: owner }).should.be.fulfilled; - await token.transferOwnership(foreignBridge.address, {from: owner}); - - await token.transferAndCall(foreignBridge.address, valueLessThanMinPerTx, '0x00', {from: user}).should.be.rejectedWith(ERROR_MSG); + const valueLessThanMinPerTx = minPerTx.sub(toBN(1)) + token = await ERC677BridgeToken.new('TEST', 'TST', 18, { from: owner }) + const foreignBridge = await ForeignBridgeErc677ToErc677.new() + await foreignBridge.initialize( + validatorContract.address, + token.address, + requireBlockConfirmations, + gasPrice, + dailyLimit, + maxPerTx, + minPerTx, + homeDailyLimit, + homeMaxPerTx, + owner + ) + + await token.mint(user, oneEther, { from: owner }).should.be.fulfilled + await token.transferOwnership(foreignBridge.address, { from: owner }) + + await token + .transferAndCall(foreignBridge.address, valueLessThanMinPerTx, '0x00', { from: user }) + .should.be.rejectedWith(ERROR_MSG) expect(await token.totalSupply()).to.be.bignumber.equal(oneEther) expect(await token.balanceOf(user)).to.be.bignumber.equal(oneEther) - await token.transferAndCall(foreignBridge.address, minPerTx, '0x00', {from: user}).should.be.fulfilled; + await token.transferAndCall(foreignBridge.address, minPerTx, '0x00', { from: user }).should.be.fulfilled expect(await token.totalSupply()).to.be.bignumber.equal(oneEther) expect(await token.balanceOf(user)).to.be.bignumber.equal(oneEther.sub(minPerTx)) expect(await token.balanceOf(foreignBridge.address)).to.be.bignumber.equal(minPerTx) - const events = await getEvents(foreignBridge, {event: 'UserRequestForAffirmation'}); + const events = await getEvents(foreignBridge, { event: 'UserRequestForAffirmation' }) expect(events[0].returnValues.recipient).to.be.equal(user) expect(toBN(events[0].returnValues.value)).to.be.bignumber.equal(minPerTx) }) diff --git a/test/erc_to_erc/home_bridge.test.js b/test/erc_to_erc/home_bridge.test.js index f608ff394..c26509e66 100644 --- a/test/erc_to_erc/home_bridge.test.js +++ b/test/erc_to_erc/home_bridge.test.js @@ -1,40 +1,45 @@ -const HomeBridge = artifacts.require("HomeBridgeErcToErc.sol"); -const POSDAOHomeBridge = artifacts.require("POSDAOHomeBridgeErcToErc.sol"); -const EternalStorageProxy = artifacts.require("EternalStorageProxy.sol"); -const BridgeValidators = artifacts.require("BridgeValidators.sol"); -const ERC677BridgeToken = artifacts.require("ERC677BridgeToken.sol"); -const ERC677BridgeTokenRewardable = artifacts.require("ERC677BridgeTokenRewardable.sol"); -const FeeManagerErcToErcPOSDAO = artifacts.require("FeeManagerErcToErcPOSDAO.sol"); -const RewardableValidators = artifacts.require("RewardableValidators.sol"); +const HomeBridge = artifacts.require('HomeBridgeErcToErc.sol') +const POSDAOHomeBridge = artifacts.require('POSDAOHomeBridgeErcToErc.sol') +const EternalStorageProxy = artifacts.require('EternalStorageProxy.sol') +const BridgeValidators = artifacts.require('BridgeValidators.sol') +const ERC677BridgeToken = artifacts.require('ERC677BridgeToken.sol') +const ERC677BridgeTokenRewardable = artifacts.require('ERC677BridgeTokenRewardable.sol') +const FeeManagerErcToErcPOSDAO = artifacts.require('FeeManagerErcToErcPOSDAO.sol') +const RewardableValidators = artifacts.require('RewardableValidators.sol') const BlockReward = artifacts.require('BlockReward') -const { expect } = require('chai'); -const { ERROR_MSG, ZERO_ADDRESS, toBN } = require('../setup'); -const { createMessage, sign, getEvents, ether, expectEventInLogs } = require('../helpers/helpers'); +const { expect } = require('chai') +const { ERROR_MSG, ZERO_ADDRESS, toBN } = require('../setup') +const { createMessage, sign, getEvents, ether, expectEventInLogs } = require('../helpers/helpers') -const minPerTx = ether('0.01'); -const requireBlockConfirmations = 8; -const gasPrice = web3.utils.toWei('1', 'gwei'); -const oneEther = ether('1'); -const halfEther = ether('0.5'); +const minPerTx = ether('0.01') +const requireBlockConfirmations = 8 +const gasPrice = web3.utils.toWei('1', 'gwei') +const oneEther = ether('1') +const halfEther = ether('0.5') const foreignDailyLimit = oneEther const foreignMaxPerTx = halfEther const ZERO = toBN(0) -const markedAsProcessed = (toBN(2)).pow(toBN(255)).add(toBN(1)) - - -contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { - let homeContract, validatorContract, authorities, owner, token; +const markedAsProcessed = toBN(2) + .pow(toBN(255)) + .add(toBN(1)) + +contract('HomeBridge_ERC20_to_ERC20', async accounts => { + let homeContract + let validatorContract + let authorities + let owner + let token before(async () => { validatorContract = await BridgeValidators.new() - authorities = [accounts[1]]; + authorities = [accounts[1]] owner = accounts[0] await validatorContract.initialize(1, authorities, owner) }) - describe('#initialize', async() => { + describe('#initialize', async () => { beforeEach(async () => { homeContract = await HomeBridge.new() - token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); + token = await ERC677BridgeToken.new('Some ERC20', 'RSZT', 18) }) it('sets variables', async () => { expect(await homeContract.validatorContract()).to.be.equal(ZERO_ADDRESS) @@ -43,7 +48,18 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { expect(await homeContract.maxPerTx()).to.be.bignumber.equal(ZERO) expect(await homeContract.isInitialized()).to.be.equal(false) - await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled; + await homeContract.initialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + token.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ).should.be.fulfilled expect(await homeContract.isInitialized()).to.be.equal(true) expect(await homeContract.validatorContract()).to.be.equal(validatorContract.address) @@ -61,17 +77,56 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { it('cant set maxPerTx > dailyLimit', async () => { expect(await homeContract.isInitialized()).to.be.equal(false) - await homeContract.initialize(validatorContract.address, '1', '2', '1', gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await homeContract.initialize(validatorContract.address, '3', '2', '2', gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); + await homeContract + .initialize( + validatorContract.address, + '1', + '2', + '1', + gasPrice, + requireBlockConfirmations, + token.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await homeContract + .initialize( + validatorContract.address, + '3', + '2', + '2', + gasPrice, + requireBlockConfirmations, + token.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) expect(await homeContract.isInitialized()).to.be.equal(false) }) it('can be deployed via upgradeToAndCall', async () => { - let storageProxy = await EternalStorageProxy.new().should.be.fulfilled; - const data = homeContract.contract.methods.initialize(validatorContract.address, "3", "2", "1", gasPrice, requireBlockConfirmations, token.address, '3', '2', owner).encodeABI() - await storageProxy.upgradeToAndCall('1', homeContract.address, data).should.be.fulfilled; - let finalContract = await HomeBridge.at(storageProxy.address); + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled + const data = homeContract.contract.methods + .initialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + token.address, + '3', + '2', + owner + ) + .encodeABI() + await storageProxy.upgradeToAndCall('1', homeContract.address, data).should.be.fulfilled + const finalContract = await HomeBridge.at(storageProxy.address) expect(await finalContract.isInitialized()).to.be.equal(true) expect(await finalContract.validatorContract()).to.be.equal(validatorContract.address) @@ -83,14 +138,116 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { it('cant initialize with invalid arguments', async () => { expect(await homeContract.isInitialized()).to.be.equal(false) - await homeContract.initialize(validatorContract.address, '3', '2', '1', 0, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, 0, token.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await homeContract.initialize(owner, '3', '2', '1', gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await homeContract.initialize(ZERO_ADDRESS, '3', '2', '1', gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, ZERO_ADDRESS, foreignDailyLimit, foreignMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, owner, foreignDailyLimit, foreignMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, token.address, halfEther, oneEther, owner).should.be.rejectedWith(ERROR_MSG); - await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled; + await homeContract + .initialize( + validatorContract.address, + '3', + '2', + '1', + 0, + requireBlockConfirmations, + token.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await homeContract + .initialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + 0, + token.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await homeContract + .initialize( + owner, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + token.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await homeContract + .initialize( + ZERO_ADDRESS, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + token.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await homeContract + .initialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + ZERO_ADDRESS, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await homeContract + .initialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + owner, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await homeContract + .initialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + token.address, + halfEther, + oneEther, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await homeContract.initialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + token.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ).should.be.fulfilled expect(await homeContract.isInitialized()).to.be.equal(true) }) @@ -99,53 +256,90 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { describe('#fallback', async () => { beforeEach(async () => { homeContract = await HomeBridge.new() - token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); - await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner) + token = await ERC677BridgeToken.new('Some ERC20', 'RSZT', 18) + await homeContract.initialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + token.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) }) it('reverts', async () => { - await homeContract.sendTransaction({ - from: accounts[1], - value: 1 - }).should.be.rejectedWith(ERROR_MSG) + await homeContract + .sendTransaction({ + from: accounts[1], + value: 1 + }) + .should.be.rejectedWith(ERROR_MSG) }) }) describe('#setting limits', async () => { - let homeContract; + let homeContract beforeEach(async () => { homeContract = await HomeBridge.new() - token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); - await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner) + token = await ERC677BridgeToken.new('Some ERC20', 'RSZT', 18) + await homeContract.initialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + token.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) }) it('#setMaxPerTx allows to set only to owner and cannot be more than daily limit', async () => { - await homeContract.setMaxPerTx(2, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG); - await homeContract.setMaxPerTx(2, {from: owner}).should.be.fulfilled; + await homeContract.setMaxPerTx(2, { from: authorities[0] }).should.be.rejectedWith(ERROR_MSG) + await homeContract.setMaxPerTx(2, { from: owner }).should.be.fulfilled - await homeContract.setMaxPerTx(3, {from: owner}).should.be.rejectedWith(ERROR_MSG); + await homeContract.setMaxPerTx(3, { from: owner }).should.be.rejectedWith(ERROR_MSG) }) it('#setMinPerTx allows to set only to owner and cannot be more than daily limit and should be less than maxPerTx', async () => { - await homeContract.setMinPerTx(1, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG); - await homeContract.setMinPerTx(1, {from: owner}).should.be.fulfilled; + await homeContract.setMinPerTx(1, { from: authorities[0] }).should.be.rejectedWith(ERROR_MSG) + await homeContract.setMinPerTx(1, { from: owner }).should.be.fulfilled - await homeContract.setMinPerTx(2, {from: owner}).should.be.rejectedWith(ERROR_MSG); + await homeContract.setMinPerTx(2, { from: owner }).should.be.rejectedWith(ERROR_MSG) }) }) describe('#executeAffirmation', async () => { - let homeBridge; + let homeBridge beforeEach(async () => { - homeBridge = await HomeBridge.new(); - token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); - await homeBridge.initialize(validatorContract.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner); - await token.transferOwnership(homeBridge.address); + homeBridge = await HomeBridge.new() + token = await ERC677BridgeToken.new('Some ERC20', 'RSZT', 18) + await homeBridge.initialize( + validatorContract.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + token.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) + await token.transferOwnership(homeBridge.address) }) it('should allow validator to withdraw', async () => { - const recipient = accounts[5]; - const value = halfEther; + const recipient = accounts[5] + const value = halfEther const balanceBefore = await token.balanceOf(recipient) - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - const {logs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}) + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: authorities[0] + }) expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], transactionHash @@ -161,20 +355,24 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { balanceAfter.should.be.bignumber.equal(balanceBefore.add(value)) totalSupply.should.be.bignumber.equal(value) - const msgHash = web3.utils.soliditySha3(recipient, value, transactionHash); + const msgHash = web3.utils.soliditySha3(recipient, value, transactionHash) const senderHash = web3.utils.soliditySha3(authorities[0], msgHash) true.should.be.equal(await homeBridge.affirmationsSigned(senderHash)) - markedAsProcessed.should.be.bignumber.equal(await homeBridge.numAffirmationsSigned(msgHash)); - await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG) + markedAsProcessed.should.be.bignumber.equal(await homeBridge.numAffirmationsSigned(msgHash)) + await homeBridge + .executeAffirmation(recipient, value, transactionHash, { from: authorities[0] }) + .should.be.rejectedWith(ERROR_MSG) }) it('should allow validator to withdraw with zero value', async () => { - const recipient = accounts[5]; + const recipient = accounts[5] const value = ZERO const balanceBefore = await token.balanceOf(recipient) - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' - const {logs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}) + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: authorities[0] + }) expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], @@ -191,29 +389,44 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { balanceAfter.should.be.bignumber.equal(balanceBefore.add(value)) totalSupply.should.be.bignumber.equal(value) - const msgHash = web3.utils.soliditySha3(recipient, value, transactionHash); + const msgHash = web3.utils.soliditySha3(recipient, value, transactionHash) const senderHash = web3.utils.soliditySha3(authorities[0], msgHash) true.should.be.equal(await homeBridge.affirmationsSigned(senderHash)) - markedAsProcessed.should.be.bignumber.equal(await homeBridge.numAffirmationsSigned(msgHash)); - await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG) + markedAsProcessed.should.be.bignumber.equal(await homeBridge.numAffirmationsSigned(msgHash)) + await homeBridge + .executeAffirmation(recipient, value, transactionHash, { from: authorities[0] }) + .should.be.rejectedWith(ERROR_MSG) }) it('test with 2 signatures required', async () => { - let token2sig = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); - let validatorContractWith2Signatures = await BridgeValidators.new() - let authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]]; - let ownerOfValidators = accounts[0] + const token2sig = await ERC677BridgeToken.new('Some ERC20', 'RSZT', 18) + const validatorContractWith2Signatures = await BridgeValidators.new() + const authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]] + const ownerOfValidators = accounts[0] await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, ownerOfValidators) - let homeBridgeWithTwoSigs = await HomeBridge.new(); - await homeBridgeWithTwoSigs.initialize(validatorContractWith2Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token2sig.address, foreignDailyLimit, foreignMaxPerTx, owner); - await token2sig.transferOwnership(homeBridgeWithTwoSigs.address); - const recipient = accounts[5]; - const value = halfEther; - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const homeBridgeWithTwoSigs = await HomeBridge.new() + await homeBridgeWithTwoSigs.initialize( + validatorContractWith2Signatures.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + token2sig.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) + await token2sig.transferOwnership(homeBridgeWithTwoSigs.address) + const recipient = accounts[5] + const value = halfEther + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' const balanceBefore = await token2sig.balanceOf(recipient) - const msgHash = web3.utils.soliditySha3(recipient, value, transactionHash); + const msgHash = web3.utils.soliditySha3(recipient, value, transactionHash) - const {logs} = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; + const { logs } = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, { + from: authoritiesThreeAccs[0] + }).should.be.fulfilled expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], @@ -221,11 +434,15 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { }) expect(await token2sig.totalSupply()).to.be.bignumber.equal(ZERO) - const notProcessed = await homeBridgeWithTwoSigs.numAffirmationsSigned(msgHash); - notProcessed.should.be.bignumber.equal('1'); + const notProcessed = await homeBridgeWithTwoSigs.numAffirmationsSigned(msgHash) + notProcessed.should.be.bignumber.equal('1') - await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[0]}).should.be.rejectedWith(ERROR_MSG); - const secondSignature = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; + await homeBridgeWithTwoSigs + .executeAffirmation(recipient, value, transactionHash, { from: authoritiesThreeAccs[0] }) + .should.be.rejectedWith(ERROR_MSG) + const secondSignature = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, { + from: authoritiesThreeAccs[1] + }).should.be.fulfilled const balanceAfter = await token2sig.balanceOf(recipient) balanceAfter.should.be.bignumber.equal(balanceBefore.add(value)) @@ -239,74 +456,117 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const senderHash = web3.utils.soliditySha3(authoritiesThreeAccs[0], msgHash) true.should.be.equal(await homeBridgeWithTwoSigs.affirmationsSigned(senderHash)) - const senderHash2 = web3.utils.soliditySha3(authoritiesThreeAccs[1], msgHash); + const senderHash2 = web3.utils.soliditySha3(authoritiesThreeAccs[1], msgHash) true.should.be.equal(await homeBridgeWithTwoSigs.affirmationsSigned(senderHash2)) - const processed = toBN(2).pow(toBN(255)).add(toBN(2)); + const processed = toBN(2) + .pow(toBN(255)) + .add(toBN(2)) expect(await homeBridgeWithTwoSigs.numAffirmationsSigned(msgHash)).to.be.bignumber.equal(processed) }) it('should not allow to double submit', async () => { - const recipient = accounts[5]; - const value = '1'; - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.fulfilled; - await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG); + const recipient = accounts[5] + const value = '1' + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: authorities[0] + }).should.be.fulfilled + await homeBridge + .executeAffirmation(recipient, value, transactionHash, { from: authorities[0] }) + .should.be.rejectedWith(ERROR_MSG) }) it('should not allow non-authorities to execute deposit', async () => { - const recipient = accounts[5]; - const value = oneEther; - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: accounts[7]}).should.be.rejectedWith(ERROR_MSG); + const recipient = accounts[5] + const value = oneEther + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + await homeBridge + .executeAffirmation(recipient, value, transactionHash, { from: accounts[7] }) + .should.be.rejectedWith(ERROR_MSG) }) it('doesnt allow to deposit if requiredSignatures has changed', async () => { - let token2sig = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); - let validatorContractWith2Signatures = await BridgeValidators.new() - let authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]]; - let ownerOfValidators = accounts[0] + const token2sig = await ERC677BridgeToken.new('Some ERC20', 'RSZT', 18) + const validatorContractWith2Signatures = await BridgeValidators.new() + const authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]] + const ownerOfValidators = accounts[0] await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, ownerOfValidators) - let homeBridgeWithTwoSigs = await HomeBridge.new(); - await homeBridgeWithTwoSigs.initialize(validatorContractWith2Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token2sig.address, foreignDailyLimit, foreignMaxPerTx, owner); - await token2sig.transferOwnership(homeBridgeWithTwoSigs.address); - const recipient = accounts[5]; - const value = halfEther.div(toBN(2)); - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const homeBridgeWithTwoSigs = await HomeBridge.new() + await homeBridgeWithTwoSigs.initialize( + validatorContractWith2Signatures.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + token2sig.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) + await token2sig.transferOwnership(homeBridgeWithTwoSigs.address) + const recipient = accounts[5] + const value = halfEther.div(toBN(2)) + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' const balanceBefore = await token.balanceOf(recipient) - await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; - await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, { + from: authoritiesThreeAccs[0] + }).should.be.fulfilled + await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, { + from: authoritiesThreeAccs[1] + }).should.be.fulfilled balanceBefore.add(value).should.be.bignumber.equal(await token2sig.balanceOf(recipient)) - await validatorContractWith2Signatures.setRequiredSignatures(3).should.be.fulfilled; - await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[2]}).should.be.rejectedWith(ERROR_MSG); - await validatorContractWith2Signatures.setRequiredSignatures(1).should.be.fulfilled; - await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[2]}).should.be.rejectedWith(ERROR_MSG); + await validatorContractWith2Signatures.setRequiredSignatures(3).should.be.fulfilled + await homeBridgeWithTwoSigs + .executeAffirmation(recipient, value, transactionHash, { from: authoritiesThreeAccs[2] }) + .should.be.rejectedWith(ERROR_MSG) + await validatorContractWith2Signatures.setRequiredSignatures(1).should.be.fulfilled + await homeBridgeWithTwoSigs + .executeAffirmation(recipient, value, transactionHash, { from: authoritiesThreeAccs[2] }) + .should.be.rejectedWith(ERROR_MSG) balanceBefore.add(value).should.be.bignumber.equal(await token2sig.balanceOf(recipient)) - }) it('works with 5 validators and 3 required signatures', async () => { const recipient = accounts[8] const authoritiesFiveAccs = [accounts[1], accounts[2], accounts[3], accounts[4], accounts[5]] - let ownerOfValidators = accounts[0] + const ownerOfValidators = accounts[0] const validatorContractWith3Signatures = await BridgeValidators.new() await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) - const token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); - - const homeBridgeWithThreeSigs = await HomeBridge.new(); - await homeBridgeWithThreeSigs.initialize(validatorContractWith3Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner); - await token.transferOwnership(homeBridgeWithThreeSigs.address); - - const value = ether('0.5'); - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - - const {logs} = await homeBridgeWithThreeSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesFiveAccs[0]}).should.be.fulfilled; + const token = await ERC677BridgeToken.new('Some ERC20', 'RSZT', 18) + + const homeBridgeWithThreeSigs = await HomeBridge.new() + await homeBridgeWithThreeSigs.initialize( + validatorContractWith3Signatures.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + token.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) + await token.transferOwnership(homeBridgeWithThreeSigs.address) + + const value = ether('0.5') + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + + const { logs } = await homeBridgeWithThreeSigs.executeAffirmation(recipient, value, transactionHash, { + from: authoritiesFiveAccs[0] + }).should.be.fulfilled expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], transactionHash }) - await homeBridgeWithThreeSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesFiveAccs[1]}).should.be.fulfilled; - const thirdSignature = await homeBridgeWithThreeSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesFiveAccs[2]}).should.be.fulfilled; + await homeBridgeWithThreeSigs.executeAffirmation(recipient, value, transactionHash, { + from: authoritiesFiveAccs[1] + }).should.be.fulfilled + const thirdSignature = await homeBridgeWithThreeSigs.executeAffirmation(recipient, value, transactionHash, { + from: authoritiesFiveAccs[2] + }).should.be.fulfilled expectEventInLogs(thirdSignature.logs, 'AffirmationCompleted', { recipient, @@ -315,10 +575,12 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { }) }) it('should not allow execute affirmation over foreign max tx limit', async () => { - const recipient = accounts[5]; - const value = oneEther; - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - const {logs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.fulfilled; + const recipient = accounts[5] + const value = oneEther + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: authorities[0] + }).should.be.fulfilled expectEventInLogs(logs, 'AmountLimitExceeded', { recipient, @@ -327,10 +589,12 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { }) }) it('should fail if txHash already set as above of limits', async () => { - const recipient = accounts[5]; - const value = oneEther; - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - const {logs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.fulfilled; + const recipient = accounts[5] + const value = oneEther + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: authorities[0] + }).should.be.fulfilled expectEventInLogs(logs, 'AmountLimitExceeded', { recipient, @@ -338,14 +602,20 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { transactionHash }) - await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG) - await homeBridge.executeAffirmation(accounts[6], value, transactionHash, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG) + await homeBridge + .executeAffirmation(recipient, value, transactionHash, { from: authorities[0] }) + .should.be.rejectedWith(ERROR_MSG) + await homeBridge + .executeAffirmation(accounts[6], value, transactionHash, { from: authorities[0] }) + .should.be.rejectedWith(ERROR_MSG) }) it('should not allow execute affirmation over daily foreign limit', async () => { - const recipient = accounts[5]; - const value = halfEther; - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.fulfilled; + const recipient = accounts[5] + const value = halfEther + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: authorities[0] + }).should.be.fulfilled expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], @@ -357,8 +627,10 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { transactionHash }) - const transactionHash2 = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - const { logs: logs2 } = await homeBridge.executeAffirmation(recipient, value, transactionHash2, {from: authorities[0]}).should.be.fulfilled; + const transactionHash2 = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' + const { logs: logs2 } = await homeBridge.executeAffirmation(recipient, value, transactionHash2, { + from: authorities[0] + }).should.be.fulfilled expectEventInLogs(logs2, 'SignedForAffirmation', { signer: authorities[0], @@ -370,8 +642,10 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { transactionHash: transactionHash2 }) - const transactionHash3 = "0x69debd8fd1923c9cb3cd8ef6461e2740b2d037943b941729d5a47671a2bb8712"; - const { logs: logs3 } = await homeBridge.executeAffirmation(recipient, value, transactionHash3, {from: authorities[0]}).should.be.fulfilled; + const transactionHash3 = '0x69debd8fd1923c9cb3cd8ef6461e2740b2d037943b941729d5a47671a2bb8712' + const { logs: logs3 } = await homeBridge.executeAffirmation(recipient, value, transactionHash3, { + from: authorities[0] + }).should.be.fulfilled expectEventInLogs(logs3, 'AmountLimitExceeded', { recipient, @@ -383,8 +657,10 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { outOfLimitAmount.should.be.bignumber.equal(halfEther) - const transactionHash4 = "0xc9ffe298d85ec5c515153608924b7bdcf1835539813dcc82cdbcc071170c3196"; - const { logs: logs4 } = await homeBridge.executeAffirmation(recipient, value, transactionHash4, {from: authorities[0]}).should.be.fulfilled; + const transactionHash4 = '0xc9ffe298d85ec5c515153608924b7bdcf1835539813dcc82cdbcc071170c3196' + const { logs: logs4 } = await homeBridge.executeAffirmation(recipient, value, transactionHash4, { + from: authorities[0] + }).should.be.fulfilled expectEventInLogs(logs4, 'AmountLimitExceeded', { recipient, @@ -397,63 +673,89 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { }) describe('#isAlreadyProcessed', async () => { it('returns ', async () => { - homeBridge = await HomeBridge.new(); - const bn = toBN(2).pow(toBN(255)); - const processedNumbers = [bn.add(toBN(1)).toString(10), bn.add(toBN(100)).toString(10)]; - true.should.be.equal(await homeBridge.isAlreadyProcessed(processedNumbers[0])); - true.should.be.equal(await homeBridge.isAlreadyProcessed(processedNumbers[1])); - false.should.be.equal(await homeBridge.isAlreadyProcessed(10)); + const homeBridge = await HomeBridge.new() + const bn = toBN(2).pow(toBN(255)) + const processedNumbers = [bn.add(toBN(1)).toString(10), bn.add(toBN(100)).toString(10)] + true.should.be.equal(await homeBridge.isAlreadyProcessed(processedNumbers[0])) + true.should.be.equal(await homeBridge.isAlreadyProcessed(processedNumbers[1])) + false.should.be.equal(await homeBridge.isAlreadyProcessed(10)) }) }) describe('#submitSignature', async () => { - let validatorContractWith2Signatures,authoritiesThreeAccs,ownerOfValidators,homeBridgeWithTwoSigs + let validatorContractWith2Signatures + let authoritiesThreeAccs + let ownerOfValidators + let homeBridgeWithTwoSigs beforeEach(async () => { - let token2sig = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); + const token2sig = await ERC677BridgeToken.new('Some ERC20', 'RSZT', 18) validatorContractWith2Signatures = await BridgeValidators.new() - authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]]; + authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]] ownerOfValidators = accounts[0] await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, ownerOfValidators) - homeBridgeWithTwoSigs = await HomeBridge.new(); - await homeBridgeWithTwoSigs.initialize(validatorContractWith2Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token2sig.address, foreignDailyLimit, foreignMaxPerTx, owner); - await token2sig.transferOwnership(homeBridgeWithTwoSigs.address); + homeBridgeWithTwoSigs = await HomeBridge.new() + await homeBridgeWithTwoSigs.initialize( + validatorContractWith2Signatures.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + token2sig.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) + await token2sig.transferOwnership(homeBridgeWithTwoSigs.address) }) it('allows a validator to submit a signature', async () => { const recipientAccount = accounts[8] - const value = ether('0.5'); - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); + const value = ether('0.5') + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' + const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address) const signature = await sign(authoritiesThreeAccs[0], message) - const {logs} = await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authorities[0]}).should.be.fulfilled; + const { logs } = await homeBridgeWithTwoSigs.submitSignature(signature, message, { + from: authorities[0] + }).should.be.fulfilled logs[0].event.should.be.equal('SignedForUserRequest') const msgHashFromLog = logs[0].args.messageHash - const signatureFromContract = await homeBridgeWithTwoSigs.signature(msgHashFromLog, 0); - const messageFromContract = await homeBridgeWithTwoSigs.message(msgHashFromLog); + const signatureFromContract = await homeBridgeWithTwoSigs.signature(msgHashFromLog, 0) + const messageFromContract = await homeBridgeWithTwoSigs.message(msgHashFromLog) - signature.should.be.equal(signatureFromContract); - messageFromContract.should.be.equal(messageFromContract); - const hashMsg = web3.utils.soliditySha3(message); + signature.should.be.equal(signatureFromContract) + messageFromContract.should.be.equal(messageFromContract) + const hashMsg = web3.utils.soliditySha3(message) expect(await homeBridgeWithTwoSigs.numMessagesSigned(hashMsg)).to.be.bignumber.equal('1') const hashSenderMsg = web3.utils.soliditySha3(authorities[0], hashMsg) - true.should.be.equal(await homeBridgeWithTwoSigs.messagesSigned(hashSenderMsg)); + true.should.be.equal(await homeBridgeWithTwoSigs.messagesSigned(hashSenderMsg)) }) it('when enough requiredSignatures are collected, CollectedSignatures event is emitted', async () => { const recipientAccount = accounts[8] - const value = ether('0.5'); - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); - const hashMsg = web3.utils.soliditySha3(message); + const value = ether('0.5') + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' + const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address) + const hashMsg = web3.utils.soliditySha3(message) const signature = await sign(authoritiesThreeAccs[0], message) const signature2 = await sign(authoritiesThreeAccs[1], message) expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('2') - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.rejectedWith(ERROR_MSG); - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[1]}).should.be.rejectedWith(ERROR_MSG); - const {logs} = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.submitSignature(signature, message, { + from: authoritiesThreeAccs[0] + }).should.be.fulfilled + await homeBridgeWithTwoSigs + .submitSignature(signature, message, { from: authoritiesThreeAccs[0] }) + .should.be.rejectedWith(ERROR_MSG) + await homeBridgeWithTwoSigs + .submitSignature(signature, message, { from: authoritiesThreeAccs[1] }) + .should.be.rejectedWith(ERROR_MSG) + const { logs } = await homeBridgeWithTwoSigs.submitSignature(signature2, message, { + from: authoritiesThreeAccs[1] + }).should.be.fulfilled logs.length.should.be.equal(2) logs[1].event.should.be.equal('CollectedSignatures') logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesThreeAccs[1]) - const markedAsProcessed = toBN(2).pow(toBN(255)).add(toBN(2)); + const markedAsProcessed = toBN(2) + .pow(toBN(255)) + .add(toBN(2)) markedAsProcessed.should.be.bignumber.equal(await homeBridgeWithTwoSigs.numMessagesSigned(hashMsg)) }) it('works with 5 validators and 3 required signatures', async () => { @@ -461,63 +763,94 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const authoritiesFiveAccs = [accounts[1], accounts[2], accounts[3], accounts[4], accounts[5]] const validatorContractWith3Signatures = await BridgeValidators.new() await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) - const token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); - - const homeBridgeWithThreeSigs = await HomeBridge.new(); - await homeBridgeWithThreeSigs.initialize(validatorContractWith3Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner); - - const value = ether('0.5'); - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithThreeSigs.address); + const token = await ERC677BridgeToken.new('Some ERC20', 'RSZT', 18) + + const homeBridgeWithThreeSigs = await HomeBridge.new() + await homeBridgeWithThreeSigs.initialize( + validatorContractWith3Signatures.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + token.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) + + const value = ether('0.5') + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' + const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithThreeSigs.address) const signature = await sign(authoritiesFiveAccs[0], message) const signature2 = await sign(authoritiesFiveAccs[1], message) const signature3 = await sign(authoritiesFiveAccs[2], message) expect(await validatorContractWith3Signatures.requiredSignatures()).to.be.bignumber.equal('3') - await homeBridgeWithThreeSigs.submitSignature(signature, message, {from: authoritiesFiveAccs[0]}).should.be.fulfilled; - await homeBridgeWithThreeSigs.submitSignature(signature2, message, {from: authoritiesFiveAccs[1]}).should.be.fulfilled; - const {logs} = await homeBridgeWithThreeSigs.submitSignature(signature3, message, {from: authoritiesFiveAccs[2]}).should.be.fulfilled; + await homeBridgeWithThreeSigs.submitSignature(signature, message, { + from: authoritiesFiveAccs[0] + }).should.be.fulfilled + await homeBridgeWithThreeSigs.submitSignature(signature2, message, { + from: authoritiesFiveAccs[1] + }).should.be.fulfilled + const { logs } = await homeBridgeWithThreeSigs.submitSignature(signature3, message, { + from: authoritiesFiveAccs[2] + }).should.be.fulfilled logs.length.should.be.equal(2) logs[1].event.should.be.equal('CollectedSignatures') logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesFiveAccs[2]) }) it('attack when increasing requiredSignatures', async () => { const recipientAccount = accounts[8] - const value = ether('0.5'); - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); + const value = ether('0.5') + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' + const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address) const signature = await sign(authoritiesThreeAccs[0], message) const signature2 = await sign(authoritiesThreeAccs[1], message) const signature3 = await sign(authoritiesThreeAccs[2], message) expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('2') - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.rejectedWith(ERROR_MSG); - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[1]}).should.be.rejectedWith(ERROR_MSG); - const {logs} = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.submitSignature(signature, message, { + from: authoritiesThreeAccs[0] + }).should.be.fulfilled + await homeBridgeWithTwoSigs + .submitSignature(signature, message, { from: authoritiesThreeAccs[0] }) + .should.be.rejectedWith(ERROR_MSG) + await homeBridgeWithTwoSigs + .submitSignature(signature, message, { from: authoritiesThreeAccs[1] }) + .should.be.rejectedWith(ERROR_MSG) + const { logs } = await homeBridgeWithTwoSigs.submitSignature(signature2, message, { + from: authoritiesThreeAccs[1] + }).should.be.fulfilled logs.length.should.be.equal(2) logs[1].event.should.be.equal('CollectedSignatures') logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesThreeAccs[1]) - await validatorContractWith2Signatures.setRequiredSignatures(3).should.be.fulfilled; + await validatorContractWith2Signatures.setRequiredSignatures(3).should.be.fulfilled expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('3') - await homeBridgeWithTwoSigs.submitSignature(signature3, message, {from: authoritiesThreeAccs[2]}).should.be.rejectedWith(ERROR_MSG); + await homeBridgeWithTwoSigs + .submitSignature(signature3, message, { from: authoritiesThreeAccs[2] }) + .should.be.rejectedWith(ERROR_MSG) }) it('attack when decreasing requiredSignatures', async () => { const recipientAccount = accounts[8] - const value = ether('0.5'); - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); + const value = ether('0.5') + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' + const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address) const signature = await sign(authoritiesThreeAccs[0], message) const signature2 = await sign(authoritiesThreeAccs[1], message) expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('2') - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; - await validatorContractWith2Signatures.setRequiredSignatures(1).should.be.fulfilled; + await homeBridgeWithTwoSigs.submitSignature(signature, message, { + from: authoritiesThreeAccs[0] + }).should.be.fulfilled + await validatorContractWith2Signatures.setRequiredSignatures(1).should.be.fulfilled expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('1') - const {logs} = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; + const { logs } = await homeBridgeWithTwoSigs.submitSignature(signature2, message, { + from: authoritiesThreeAccs[1] + }).should.be.fulfilled logs.length.should.be.equal(2) logs[1].event.should.be.equal('CollectedSignatures') logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesThreeAccs[1]) @@ -536,21 +869,34 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { }) describe('#fixAssetsAboveLimits', async () => { - let homeBridge; + let homeBridge beforeEach(async () => { - const homeBridgeImpl = await HomeBridge.new(); - const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + const homeBridgeImpl = await HomeBridge.new() + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled - homeBridge = await HomeBridge.at(storageProxy.address); - await homeBridge.initialize(validatorContract.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + homeBridge = await HomeBridge.at(storageProxy.address) + await homeBridge.initialize( + validatorContract.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + token.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ).should.be.fulfilled }) it('Should reduce outOfLimitAmount and not emit any event', async () => { - const recipient = accounts[5]; - const value = oneEther; - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - const {logs: affirmationLogs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.fulfilled + const recipient = accounts[5] + const value = oneEther + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + const { logs: affirmationLogs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: authorities[0] + }).should.be.fulfilled - affirmationLogs[0].event.should.be.equal("AmountLimitExceeded"); + affirmationLogs[0].event.should.be.equal('AmountLimitExceeded') const outOfLimitAmount = await homeBridge.outOfLimitAmount() outOfLimitAmount.should.be.bignumber.equal(value) @@ -563,12 +909,14 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { newOutOfLimitAmount.should.be.bignumber.equal(ZERO) }) it('Should reduce outOfLimitAmount and emit UserRequestForSignature', async () => { - const recipient = accounts[5]; - const value = oneEther; - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - const {logs: affirmationLogs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.fulfilled + const recipient = accounts[5] + const value = oneEther + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + const { logs: affirmationLogs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: authorities[0] + }).should.be.fulfilled - affirmationLogs[0].event.should.be.equal("AmountLimitExceeded"); + affirmationLogs[0].event.should.be.equal('AmountLimitExceeded') const outOfLimitAmount = await homeBridge.outOfLimitAmount() outOfLimitAmount.should.be.bignumber.equal(value) @@ -585,13 +933,17 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { newOutOfLimitAmount.should.be.bignumber.equal(ZERO) }) it('Should not be allow to be called by an already fixed txHash', async () => { - const recipient = accounts[5]; - const value = oneEther; - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - const transactionHash2 = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - - await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.fulfilled - await homeBridge.executeAffirmation(recipient, value, transactionHash2, {from: authorities[0]}).should.be.fulfilled + const recipient = accounts[5] + const value = oneEther + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + const transactionHash2 = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' + + await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: authorities[0] + }).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, value, transactionHash2, { + from: authorities[0] + }).should.be.fulfilled const outOfLimitAmount = await homeBridge.outOfLimitAmount() outOfLimitAmount.should.be.bignumber.equal(value.add(value)) @@ -610,37 +962,42 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { await homeBridge.fixAssetsAboveLimits(transactionHash2, false).should.be.rejectedWith(ERROR_MSG) }) it('Should fail if txHash didnt increase out of limit amount', async () => { - const recipient = accounts[5]; - const value = oneEther; - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - const invalidTxHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; + const recipient = accounts[5] + const value = oneEther + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + const invalidTxHash = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' - const {logs: affirmationLogs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.fulfilled + const { logs: affirmationLogs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: authorities[0] + }).should.be.fulfilled - affirmationLogs[0].event.should.be.equal("AmountLimitExceeded"); + affirmationLogs[0].event.should.be.equal('AmountLimitExceeded') await homeBridge.fixAssetsAboveLimits(invalidTxHash, true).should.be.rejectedWith(ERROR_MSG) }) it('Should fail if not called by proxyOwner', async () => { - const recipient = accounts[5]; - const value = oneEther; - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const recipient = accounts[5] + const value = oneEther + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' - const {logs: affirmationLogs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.fulfilled + const { logs: affirmationLogs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: authorities[0] + }).should.be.fulfilled - affirmationLogs[0].event.should.be.equal("AmountLimitExceeded"); + affirmationLogs[0].event.should.be.equal('AmountLimitExceeded') - await homeBridge.fixAssetsAboveLimits(transactionHash, true, { from: recipient}).should.be.rejectedWith(ERROR_MSG) - await homeBridge.fixAssetsAboveLimits(transactionHash, true, { from: owner}).should.be.fulfilled + await homeBridge + .fixAssetsAboveLimits(transactionHash, true, { from: recipient }) + .should.be.rejectedWith(ERROR_MSG) + await homeBridge.fixAssetsAboveLimits(transactionHash, true, { from: owner }).should.be.fulfilled }) }) describe('#OwnedUpgradeability', async () => { - it('upgradeabilityAdmin should return the proxy owner', async () => { - const homeBridgeImpl = await HomeBridge.new(); - const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + const homeBridgeImpl = await HomeBridge.new() + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled - const homeBridge = await HomeBridge.at(storageProxy.address); + const homeBridge = await HomeBridge.at(storageProxy.address) const proxyOwner = await storageProxy.proxyOwner() const upgradeabilityAdmin = await homeBridge.upgradeabilityAdmin() @@ -650,12 +1007,16 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { }) describe('#rewardableInitialize', async () => { - let homeFee, foreignFee, homeBridge, rewardableValidators, blockRewardContract - let validators = [accounts[1]] - let rewards = [accounts[2]] - let requiredSignatures = 1 + let homeFee + let foreignFee + let homeBridge + let rewardableValidators + let blockRewardContract + const validators = [accounts[1]] + const rewards = [accounts[2]] + const requiredSignatures = 1 beforeEach(async () => { - token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); + token = await ERC677BridgeToken.new('Some ERC20', 'RSZT', 18) rewardableValidators = await RewardableValidators.new() await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled homeBridge = await POSDAOHomeBridge.new() @@ -671,11 +1032,86 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { expect(await homeBridge.maxPerTx()).to.be.bignumber.equal(ZERO) expect(await homeBridge.isInitialized()).to.be.equal(false) - await homeBridge.rewardableInitialize(ZERO_ADDRESS, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.rejected; - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, 0, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.rejected; - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, 0, foreignDailyLimit, token.address, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.rejected; - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, ZERO_ADDRESS, homeFee, foreignFee, blockRewardContract.address).should.be.rejected; - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.fulfilled; + await homeBridge.rewardableInitialize( + ZERO_ADDRESS, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + token.address, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + homeFee, + foreignFee, + blockRewardContract.address + ).should.be.rejected + await homeBridge.rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + 0, + requireBlockConfirmations, + token.address, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + homeFee, + foreignFee, + blockRewardContract.address + ).should.be.rejected + await homeBridge.rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + 0, + foreignDailyLimit, + token.address, + foreignMaxPerTx, + owner, + feeManager.address, + homeFee, + foreignFee, + blockRewardContract.address + ).should.be.rejected + await homeBridge.rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + token.address, + foreignDailyLimit, + foreignMaxPerTx, + owner, + ZERO_ADDRESS, + homeFee, + foreignFee, + blockRewardContract.address + ).should.be.rejected + await homeBridge.rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + token.address, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + homeFee, + foreignFee, + blockRewardContract.address + ).should.be.fulfilled expect(await homeBridge.isInitialized()).to.be.equal(true) expect(await homeBridge.validatorContract()).to.be.equal(rewardableValidators.address) @@ -701,13 +1137,28 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { }) it('can update fee contract', async () => { const feeManager = await FeeManagerErcToErcPOSDAO.new() - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.fulfilled; + await homeBridge.rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + token.address, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + homeFee, + foreignFee, + blockRewardContract.address + ).should.be.fulfilled // Given const newFeeManager = await FeeManagerErcToErcPOSDAO.new() // When - await homeBridge.setFeeManagerContract(newFeeManager.address, {from: owner}).should.be.fulfilled + await homeBridge.setFeeManagerContract(newFeeManager.address, { from: owner }).should.be.fulfilled // Then const feeManagerContract = await homeBridge.feeManagerContract() @@ -715,15 +1166,30 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { }) it('can update fee', async () => { const feeManager = await FeeManagerErcToErcPOSDAO.new() - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.fulfilled; + await homeBridge.rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + token.address, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + homeFee, + foreignFee, + blockRewardContract.address + ).should.be.fulfilled // Given const newHomeFee = ether('0.1') const newForeignFee = ether('0.4') // When - await homeBridge.setHomeFee(newHomeFee, {from: owner}).should.be.fulfilled - await homeBridge.setForeignFee(newForeignFee, {from: owner}).should.be.fulfilled + await homeBridge.setHomeFee(newHomeFee, { from: owner }).should.be.fulfilled + await homeBridge.setForeignFee(newForeignFee, { from: owner }).should.be.fulfilled // Then const bridgeHomeFee = await homeBridge.getHomeFee() @@ -737,7 +1203,22 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const bothDirectionsModeHash = '0xd7de965f' // When - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.fulfilled; + await homeBridge.rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + token.address, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + homeFee, + foreignFee, + blockRewardContract.address + ).should.be.fulfilled // Then const feeManagerMode = await homeBridge.getFeeManagerMode() @@ -747,7 +1228,22 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { // Given const feeManager = await FeeManagerErcToErcPOSDAO.new() - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.fulfilled; + await homeBridge.rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + token.address, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + homeFee, + foreignFee, + blockRewardContract.address + ).should.be.fulfilled const blockReward = await homeBridge.blockRewardContract() blockReward.should.be.equals(blockRewardContract.address) @@ -765,21 +1261,32 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { let homeBridge beforeEach(async () => { homeBridge = await HomeBridge.new() - token = await ERC677BridgeToken.new("Some ERC20", "TEST", 18); + token = await ERC677BridgeToken.new('Some ERC20', 'TEST', 18) }) it('should trigger UserRequestForSignature with transfer value', async () => { // Given const owner = accounts[0] const user = accounts[4] - await homeBridge.initialize(validatorContract.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled; + await homeBridge.initialize( + validatorContract.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + token.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ).should.be.fulfilled const value = halfEther - await token.mint(user, value, {from: owner}).should.be.fulfilled; + await token.mint(user, value, { from: owner }).should.be.fulfilled // When - await token.transferAndCall(homeBridge.address, value, '0x00', {from: user}).should.be.fulfilled; + await token.transferAndCall(homeBridge.address, value, '0x00', { from: user }).should.be.fulfilled // Then - const events = await getEvents(homeBridge, {event: 'UserRequestForSignature'}); + const events = await getEvents(homeBridge, { event: 'UserRequestForSignature' }) expect(events[0].returnValues.recipient).to.be.equal(user) expect(toBN(events[0].returnValues.value)).to.be.bignumber.equal(value) }) @@ -799,25 +1306,46 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const homeFee = ether('0.001') const foreignFee = ether('0.001') - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.fulfilled; + await homeBridge.rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + token.address, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + homeFee, + foreignFee, + blockRewardContract.address + ).should.be.fulfilled const value = halfEther const finalValueCalc = 0.5 * (1 - fee) const finalValue = ether(finalValueCalc.toString()) - await token.mint(user, value, {from: owner}).should.be.fulfilled; + await token.mint(user, value, { from: owner }).should.be.fulfilled // When - await token.transferAndCall(homeBridge.address, value, '0x00', {from: user}).should.be.fulfilled; + await token.transferAndCall(homeBridge.address, value, '0x00', { from: user }).should.be.fulfilled // Then - const events = await getEvents(homeBridge, {event: 'UserRequestForSignature'}); + const events = await getEvents(homeBridge, { event: 'UserRequestForSignature' }) expect(events[0].returnValues.recipient).to.be.equal(user) expect(toBN(events[0].returnValues.value)).to.be.bignumber.equal(finalValue) }) }) describe('#rewardable_submitSignatures', () => { - let fee, homeFee, foreignFee, homeBridge, rewardableValidators, blockRewardContract, feeManager + let fee + let homeFee + let foreignFee + let homeBridge + let rewardableValidators + let blockRewardContract + let feeManager beforeEach(async () => { - token = await ERC677BridgeTokenRewardable.new("Some ERC20", "RSZT", 18); + token = await ERC677BridgeTokenRewardable.new('Some ERC20', 'RSZT', 18) rewardableValidators = await RewardableValidators.new() feeManager = await FeeManagerErcToErcPOSDAO.new() homeBridge = await POSDAOHomeBridge.new() @@ -825,11 +1353,26 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { homeFee = ether(fee.toString()) foreignFee = ether(fee.toString()) blockRewardContract = await BlockReward.new() - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.fulfilled; + await homeBridge.rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + token.address, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + homeFee, + foreignFee, + blockRewardContract.address + ).should.be.fulfilled }) it('should distribute fee to one validator', async () => { // Given - const recipient = accounts[9]; + const recipient = accounts[9] const owner = accounts[0] const validators = [accounts[1]] const rewards = [accounts[2]] @@ -837,22 +1380,22 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled await blockRewardContract.setValidatorsRewards(rewards) await blockRewardContract.setToken(token.address) - await token.setBlockRewardContract(blockRewardContract.address, {from: owner}) - await token.transferOwnership(homeBridge.address, {from: owner}) + await token.setBlockRewardContract(blockRewardContract.address, { from: owner }) + await token.transferOwnership(homeBridge.address, { from: owner }) const valueCalc = 0.5 * (1 - fee) const value = ether(valueCalc.toString()) const feeAmountCalc = 0.5 * fee const feeAmount = ether(feeAmountCalc.toString()) - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - const message = createMessage(recipient, value, transactionHash, homeBridge.address); + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' + const message = createMessage(recipient, value, transactionHash, homeBridge.address) const signature = await sign(validators[0], message) const rewardAddressBalanceBefore = await token.balanceOf(rewards[0]) rewardAddressBalanceBefore.should.be.bignumber.equal('0') // When - const { logs } = await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled; + const { logs } = await homeBridge.submitSignature(signature, message, { from: validators[0] }).should.be.fulfilled // Then logs.length.should.be.equal(3) @@ -873,7 +1416,7 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { }) it('should distribute fee to 3 validators', async () => { // Given - const recipient = accounts[8]; + const recipient = accounts[8] const owner = accounts[9] const validators = [accounts[1], accounts[2], accounts[3]] const rewards = [accounts[4], accounts[5], accounts[6]] @@ -884,20 +1427,22 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { await token.setBlockRewardContract(blockRewardContract.address) await token.transferOwnership(homeBridge.address) - const calcValue = 0.5 * (1- fee) + const calcValue = 0.5 * (1 - fee) const value = ether(calcValue.toString()) const calcFeeAmount = 0.5 * fee const feeAmount = ether(calcFeeAmount.toString()) const feePerValidator = toBN(166666666666666) const feePerValidatorPlusDiff = toBN(166666666666668) - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - const message = createMessage(recipient, value, transactionHash, homeBridge.address); + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' + const message = createMessage(recipient, value, transactionHash, homeBridge.address) const signature = await sign(validators[0], message) const signature2 = await sign(validators[1], message) // When - await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled; - const { logs } = await homeBridge.submitSignature(signature2, message, {from: validators[1]}).should.be.fulfilled; + await homeBridge.submitSignature(signature, message, { from: validators[0] }).should.be.fulfilled + const { logs } = await homeBridge.submitSignature(signature2, message, { + from: validators[1] + }).should.be.fulfilled // Then logs.length.should.be.equal(3) @@ -917,13 +1462,19 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const balanceRewardAddress2 = await token.balanceOf(rewards[1]) const balanceRewardAddress3 = await token.balanceOf(rewards[2]) - expect(balanceRewardAddress1.eq(feePerValidator) || balanceRewardAddress1.eq(feePerValidatorPlusDiff)).to.equal(true) - expect(balanceRewardAddress2.eq(feePerValidator) || balanceRewardAddress2.eq(feePerValidatorPlusDiff)).to.equal(true) - expect(balanceRewardAddress3.eq(feePerValidator) || balanceRewardAddress3.eq(feePerValidatorPlusDiff)).to.equal(true) + expect(balanceRewardAddress1.eq(feePerValidator) || balanceRewardAddress1.eq(feePerValidatorPlusDiff)).to.equal( + true + ) + expect(balanceRewardAddress2.eq(feePerValidator) || balanceRewardAddress2.eq(feePerValidatorPlusDiff)).to.equal( + true + ) + expect(balanceRewardAddress3.eq(feePerValidator) || balanceRewardAddress3.eq(feePerValidatorPlusDiff)).to.equal( + true + ) }) it('should distribute fee to 5 validators', async () => { // Given - const recipient = accounts[0]; + const recipient = accounts[0] const owner = accounts[0] const validators = [accounts[0], accounts[1], accounts[2], accounts[3], accounts[4]] const rewards = [accounts[5], accounts[6], accounts[7], accounts[8], accounts[9]] @@ -939,16 +1490,18 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const feeAmountCalc = 0.5 * fee const feeAmount = ether(feeAmountCalc.toString()) const feePerValidator = feeAmount.div(toBN(5)) - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - const message = createMessage(recipient, value, transactionHash, homeBridge.address); + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' + const message = createMessage(recipient, value, transactionHash, homeBridge.address) const signature = await sign(validators[0], message) const signature2 = await sign(validators[1], message) const signature3 = await sign(validators[2], message) // When - await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled; - await homeBridge.submitSignature(signature2, message, {from: validators[1]}).should.be.fulfilled; - const { logs } = await homeBridge.submitSignature(signature3, message, {from: validators[2]}).should.be.fulfilled; + await homeBridge.submitSignature(signature, message, { from: validators[0] }).should.be.fulfilled + await homeBridge.submitSignature(signature2, message, { from: validators[1] }).should.be.fulfilled + const { logs } = await homeBridge.submitSignature(signature3, message, { + from: validators[2] + }).should.be.fulfilled // Then logs.length.should.be.equal(3) @@ -978,9 +1531,15 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { }) }) describe('#rewardable_executeAffirmation', () => { - let fee, homeFee, foreignFee, homeBridge, rewardableValidators, blockRewardContract, feeManager + let fee + let homeFee + let foreignFee + let homeBridge + let rewardableValidators + let blockRewardContract + let feeManager beforeEach(async () => { - token = await ERC677BridgeTokenRewardable.new("Some ERC20", "RSZT", 18); + token = await ERC677BridgeTokenRewardable.new('Some ERC20', 'RSZT', 18) rewardableValidators = await RewardableValidators.new() feeManager = await FeeManagerErcToErcPOSDAO.new() homeBridge = await POSDAOHomeBridge.new() @@ -988,11 +1547,26 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { homeFee = ether(fee.toString()) foreignFee = ether(fee.toString()) blockRewardContract = await BlockReward.new() - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee, blockRewardContract.address).should.be.fulfilled; + await homeBridge.rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + token.address, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + homeFee, + foreignFee, + blockRewardContract.address + ).should.be.fulfilled }) it('should distribute fee to one validator', async () => { // Given - const recipient = accounts[9]; + const recipient = accounts[9] const owner = accounts[0] const validators = [accounts[1]] const rewards = [accounts[2]] @@ -1008,13 +1582,15 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const value = ether(valueCalc.toString()) const feeAmountCalc = 0.5 * fee const feeAmount = ether(feeAmountCalc.toString()) - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' const rewardAddressBalanceBefore = await token.balanceOf(rewards[0]) rewardAddressBalanceBefore.should.be.bignumber.equal('0') // When - const { logs } = await homeBridge.executeAffirmation(recipient, initialValue, transactionHash, {from: validators[0]}).should.be.fulfilled; + const { logs } = await homeBridge.executeAffirmation(recipient, initialValue, transactionHash, { + from: validators[0] + }).should.be.fulfilled // Then expectEventInLogs(logs, 'FeeDistributedFromAffirmation', { @@ -1057,14 +1633,18 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const feeAmount = ether(feeAmountCalc.toString()) const feePerValidator = toBN(166666666666666) const feePerValidatorPlusDiff = toBN(166666666666668) - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80" + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' const rewardAddressBalanceBefore = await token.balanceOf(rewards[0]) rewardAddressBalanceBefore.should.be.bignumber.equal('0') // When - await homeBridge.executeAffirmation(recipient, initialValue, transactionHash, {from: validators[0]}).should.be.fulfilled - const { logs } = await homeBridge.executeAffirmation(recipient, initialValue, transactionHash, {from: validators[1]}).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, initialValue, transactionHash, { + from: validators[0] + }).should.be.fulfilled + const { logs } = await homeBridge.executeAffirmation(recipient, initialValue, transactionHash, { + from: validators[1] + }).should.be.fulfilled // Then expectEventInLogs(logs, 'FeeDistributedFromAffirmation', { @@ -1088,9 +1668,15 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const balanceRewardAddress2 = await token.balanceOf(rewards[1]) const balanceRewardAddress3 = await token.balanceOf(rewards[2]) - expect(balanceRewardAddress1.eq(feePerValidator) || balanceRewardAddress1.eq(feePerValidatorPlusDiff)).to.equal(true) - expect(balanceRewardAddress2.eq(feePerValidator) || balanceRewardAddress2.eq(feePerValidatorPlusDiff)).to.equal(true) - expect(balanceRewardAddress3.eq(feePerValidator) || balanceRewardAddress3.eq(feePerValidatorPlusDiff)).to.equal(true) + expect(balanceRewardAddress1.eq(feePerValidator) || balanceRewardAddress1.eq(feePerValidatorPlusDiff)).to.equal( + true + ) + expect(balanceRewardAddress2.eq(feePerValidator) || balanceRewardAddress2.eq(feePerValidatorPlusDiff)).to.equal( + true + ) + expect(balanceRewardAddress3.eq(feePerValidator) || balanceRewardAddress3.eq(feePerValidatorPlusDiff)).to.equal( + true + ) }) it('should distribute fee to 5 validators', async () => { // Given @@ -1111,15 +1697,21 @@ contract('HomeBridge_ERC20_to_ERC20', async (accounts) => { const feeAmountCalc = 0.5 * fee const feeAmount = ether(feeAmountCalc.toString()) const feePerValidator = feeAmount.div(toBN(5)) - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80" + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' const rewardAddressBalanceBefore = await token.balanceOf(rewards[0]) rewardAddressBalanceBefore.should.be.bignumber.equal('0') // When - await homeBridge.executeAffirmation(recipient, initialValue, transactionHash, {from: validators[0]}).should.be.fulfilled - await homeBridge.executeAffirmation(recipient, initialValue, transactionHash, {from: validators[1]}).should.be.fulfilled - const { logs } = await homeBridge.executeAffirmation(recipient, initialValue, transactionHash, {from: validators[2]}).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, initialValue, transactionHash, { + from: validators[0] + }).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, initialValue, transactionHash, { + from: validators[1] + }).should.be.fulfilled + const { logs } = await homeBridge.executeAffirmation(recipient, initialValue, transactionHash, { + from: validators[2] + }).should.be.fulfilled // Then expectEventInLogs(logs, 'FeeDistributedFromAffirmation', { diff --git a/test/erc_to_native/foreign_bridge.test.js b/test/erc_to_native/foreign_bridge.test.js index f6708c74f..fb40411f0 100644 --- a/test/erc_to_native/foreign_bridge.test.js +++ b/test/erc_to_native/foreign_bridge.test.js @@ -1,35 +1,38 @@ -const ForeignBridge = artifacts.require("ForeignBridgeErcToNative.sol"); -const ForeignBridgeV2 = artifacts.require("ForeignBridgeV2.sol"); -const BridgeValidators = artifacts.require("BridgeValidators.sol"); -const EternalStorageProxy = artifacts.require("EternalStorageProxy.sol"); -const ERC677BridgeToken = artifacts.require("ERC677BridgeToken.sol"); - -const { expect } = require('chai'); -const { ERROR_MSG, ZERO_ADDRESS, toBN } = require('../setup'); -const { createMessage, sign, signatureToVRS, ether } = require('../helpers/helpers'); - -const halfEther = ether('0.5'); -const requireBlockConfirmations = 8; -const gasPrice = web3.utils.toWei('1', 'gwei'); -const oneEther = ether('1'); +const ForeignBridge = artifacts.require('ForeignBridgeErcToNative.sol') +const ForeignBridgeV2 = artifacts.require('ForeignBridgeV2.sol') +const BridgeValidators = artifacts.require('BridgeValidators.sol') +const EternalStorageProxy = artifacts.require('EternalStorageProxy.sol') +const ERC677BridgeToken = artifacts.require('ERC677BridgeToken.sol') + +const { expect } = require('chai') +const { ERROR_MSG, ZERO_ADDRESS, toBN } = require('../setup') +const { createMessage, sign, signatureToVRS, ether } = require('../helpers/helpers') + +const halfEther = ether('0.5') +const requireBlockConfirmations = 8 +const gasPrice = web3.utils.toWei('1', 'gwei') +const oneEther = ether('1') const homeDailyLimit = oneEther const homeMaxPerTx = halfEther const maxPerTx = halfEther const ZERO = toBN(0) -contract('ForeignBridge_ERC20_to_Native', async (accounts) => { - let validatorContract, authorities, owner, token; +contract('ForeignBridge_ERC20_to_Native', async accounts => { + let validatorContract + let authorities + let owner + let token before(async () => { validatorContract = await BridgeValidators.new() - authorities = [accounts[1], accounts[2]]; + authorities = [accounts[1], accounts[2]] owner = accounts[0] await validatorContract.initialize(1, authorities, owner) }) describe('#initialize', async () => { it('should initialize', async () => { - token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); - let foreignBridge = await ForeignBridge.new(); + token = await ERC677BridgeToken.new('Some ERC20', 'RSZT', 18) + const foreignBridge = await ForeignBridge.new() expect(await foreignBridge.erc20token()).to.be.equal(ZERO_ADDRESS) expect(await foreignBridge.validatorContract()).to.be.equal(ZERO_ADDRESS) @@ -37,21 +40,109 @@ contract('ForeignBridge_ERC20_to_Native', async (accounts) => { expect(await foreignBridge.isInitialized()).to.be.equal(false) expect(await foreignBridge.requiredBlockConfirmations()).to.be.bignumber.equal(ZERO) - await foreignBridge.initialize(ZERO_ADDRESS, token.address, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.initialize(validatorContract.address, ZERO_ADDRESS, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.initialize(validatorContract.address, token.address, 0, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.initialize(validatorContract.address, token.address, requireBlockConfirmations, 0, maxPerTx, homeDailyLimit, homeMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.initialize(validatorContract.address, owner, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.initialize(owner, token.address, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.initialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, maxPerTx, halfEther, homeMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - - await foreignBridge.initialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner); + await foreignBridge + .initialize( + ZERO_ADDRESS, + token.address, + requireBlockConfirmations, + gasPrice, + maxPerTx, + homeDailyLimit, + homeMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await foreignBridge + .initialize( + validatorContract.address, + ZERO_ADDRESS, + requireBlockConfirmations, + gasPrice, + maxPerTx, + homeDailyLimit, + homeMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await foreignBridge + .initialize( + validatorContract.address, + token.address, + 0, + gasPrice, + maxPerTx, + homeDailyLimit, + homeMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await foreignBridge + .initialize( + validatorContract.address, + token.address, + requireBlockConfirmations, + 0, + maxPerTx, + homeDailyLimit, + homeMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await foreignBridge + .initialize( + validatorContract.address, + owner, + requireBlockConfirmations, + gasPrice, + maxPerTx, + homeDailyLimit, + homeMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await foreignBridge + .initialize( + owner, + token.address, + requireBlockConfirmations, + gasPrice, + maxPerTx, + homeDailyLimit, + homeMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await foreignBridge + .initialize( + validatorContract.address, + token.address, + requireBlockConfirmations, + gasPrice, + maxPerTx, + halfEther, + homeMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + + await foreignBridge.initialize( + validatorContract.address, + token.address, + requireBlockConfirmations, + gasPrice, + maxPerTx, + homeDailyLimit, + homeMaxPerTx, + owner + ) expect(await foreignBridge.erc20token()).to.be.equal(token.address) expect(await foreignBridge.isInitialized()).to.be.equal(true) expect(await foreignBridge.validatorContract()).to.be.equal(validatorContract.address) expect(await foreignBridge.deployedAtBlock()).to.be.bignumber.above(ZERO) - expect(await foreignBridge.requiredBlockConfirmations()).to.be.bignumber.equal(requireBlockConfirmations.toString()) + expect(await foreignBridge.requiredBlockConfirmations()).to.be.bignumber.equal( + requireBlockConfirmations.toString() + ) expect(await foreignBridge.gasPrice()).to.be.bignumber.equal(gasPrice) const bridgeMode = '0x18762d46' // 4 bytes of keccak256('erc-to-native-core') expect(await foreignBridge.getBridgeMode()).to.be.equal(bridgeMode) @@ -63,62 +154,71 @@ contract('ForeignBridge_ERC20_to_Native', async (accounts) => { }) describe('#executeSignatures', async () => { - const value = ether('0.25'); + const value = ether('0.25') let foreignBridge beforeEach(async () => { foreignBridge = await ForeignBridge.new() - token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); - await foreignBridge.initialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner); - await token.mint(foreignBridge.address,value); + token = await ERC677BridgeToken.new('Some ERC20', 'RSZT', 18) + await foreignBridge.initialize( + validatorContract.address, + token.address, + requireBlockConfirmations, + gasPrice, + maxPerTx, + homeDailyLimit, + homeMaxPerTx, + owner + ) + await token.mint(foreignBridge.address, value) }) it('should allow to executeSignatures', async () => { - const recipientAccount = accounts[3]; + const recipientAccount = accounts[3] const balanceBefore = await token.balanceOf(recipientAccount) - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' + const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address) const signature = await sign(authorities[0], message) - const vrs = signatureToVRS(signature); + const vrs = signatureToVRS(signature) false.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) const { logs } = await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.fulfilled - logs[0].event.should.be.equal("RelayedMessage") + logs[0].event.should.be.equal('RelayedMessage') logs[0].args.recipient.should.be.equal(recipientAccount) logs[0].args.value.should.be.bignumber.equal(value) - const balanceAfter = await token.balanceOf(recipientAccount); - const balanceAfterBridge = await token.balanceOf(foreignBridge.address); + const balanceAfter = await token.balanceOf(recipientAccount) + const balanceAfterBridge = await token.balanceOf(foreignBridge.address) balanceAfter.should.be.bignumber.equal(balanceBefore.add(value)) balanceAfterBridge.should.be.bignumber.equal(ZERO) true.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) }) - it('should allow second withdrawal with different transactionHash but same recipient and value', async ()=> { - const recipientAccount = accounts[3]; + it('should allow second withdrawal with different transactionHash but same recipient and value', async () => { + const recipientAccount = accounts[3] const balanceBefore = await token.balanceOf(recipientAccount) // tx 1 - const value = ether('0.25'); - const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); + const value = ether('0.25') + const transactionHash = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' + const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address) const signature = await sign(authorities[0], message) - const vrs = signatureToVRS(signature); + const vrs = signatureToVRS(signature) false.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.fulfilled // tx 2 - await token.mint(foreignBridge.address,value); - const transactionHash2 = "0x77a496628a776a03d58d7e6059a5937f04bebd8ba4ff89f76dd4bb8ba7e291ee"; - const message2 = createMessage(recipientAccount, value, transactionHash2, foreignBridge.address); + await token.mint(foreignBridge.address, value) + const transactionHash2 = '0x77a496628a776a03d58d7e6059a5937f04bebd8ba4ff89f76dd4bb8ba7e291ee' + const message2 = createMessage(recipientAccount, value, transactionHash2, foreignBridge.address) const signature2 = await sign(authorities[0], message2) - const vrs2 = signatureToVRS(signature2); + const vrs2 = signatureToVRS(signature2) false.should.be.equal(await foreignBridge.relayedMessages(transactionHash2)) - const {logs} = await foreignBridge.executeSignatures([vrs2.v], [vrs2.r], [vrs2.s], message2).should.be.fulfilled + const { logs } = await foreignBridge.executeSignatures([vrs2.v], [vrs2.r], [vrs2.s], message2).should.be.fulfilled - logs[0].event.should.be.equal("RelayedMessage") + logs[0].event.should.be.equal('RelayedMessage') logs[0].args.recipient.should.be.equal(recipientAccount) logs[0].args.value.should.be.bignumber.equal(value) const balanceAfter = await token.balanceOf(recipientAccount) @@ -128,114 +228,138 @@ contract('ForeignBridge_ERC20_to_Native', async (accounts) => { }) it('should not allow second withdraw (replay attack) with same transactionHash but different recipient', async () => { - const recipientAccount = accounts[3]; + const recipientAccount = accounts[3] // tx 1 - const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); + const transactionHash = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' + const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address) const signature = await sign(authorities[0], message) - const vrs = signatureToVRS(signature); + const vrs = signatureToVRS(signature) false.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.fulfilled // tx 2 - await token.mint(foreignBridge.address,value); - const message2 = createMessage(accounts[4], value, transactionHash, foreignBridge.address); + await token.mint(foreignBridge.address, value) + const message2 = createMessage(accounts[4], value, transactionHash, foreignBridge.address) const signature2 = await sign(authorities[0], message2) - const vrs2 = signatureToVRS(signature2); + const vrs2 = signatureToVRS(signature2) true.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) await foreignBridge.executeSignatures([vrs2.v], [vrs2.r], [vrs2.s], message2).should.be.rejectedWith(ERROR_MSG) }) it('should not allow withdraw over home max tx limit', async () => { - const recipientAccount = accounts[3]; - const invalidValue = ether('0.75'); - await token.mint(foreignBridge.address, ether('5')); + const recipientAccount = accounts[3] + const invalidValue = ether('0.75') + await token.mint(foreignBridge.address, ether('5')) - const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - const message = createMessage(recipientAccount, invalidValue, transactionHash, foreignBridge.address); + const transactionHash = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' + const message = createMessage(recipientAccount, invalidValue, transactionHash, foreignBridge.address) const signature = await sign(authorities[0], message) - const vrs = signatureToVRS(signature); + const vrs = signatureToVRS(signature) await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.rejectedWith(ERROR_MSG) }) it('should not allow withdraw over daily home limit', async () => { - const recipientAccount = accounts[3]; - await token.mint(foreignBridge.address, ether('5')); + const recipientAccount = accounts[3] + await token.mint(foreignBridge.address, ether('5')) - const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - const message = createMessage(recipientAccount, halfEther, transactionHash, foreignBridge.address); + const transactionHash = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' + const message = createMessage(recipientAccount, halfEther, transactionHash, foreignBridge.address) const signature = await sign(authorities[0], message) - const vrs = signatureToVRS(signature); + const vrs = signatureToVRS(signature) await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.fulfilled - const transactionHash2 = "0x69debd8fd1923c9cb3cd8ef6461e2740b2d037943b941729d5a47671a2bb8712"; - const message2 = createMessage(recipientAccount, halfEther, transactionHash2, foreignBridge.address); + const transactionHash2 = '0x69debd8fd1923c9cb3cd8ef6461e2740b2d037943b941729d5a47671a2bb8712' + const message2 = createMessage(recipientAccount, halfEther, transactionHash2, foreignBridge.address) const signature2 = await sign(authorities[0], message2) - const vrs2 = signatureToVRS(signature2); + const vrs2 = signatureToVRS(signature2) await foreignBridge.executeSignatures([vrs2.v], [vrs2.r], [vrs2.s], message2).should.be.fulfilled - const transactionHash3 = "0x022695428093bb292db8e48bd1417c5e1b84c0bf673bd0fff23ed0fb6495b872"; - const message3 = createMessage(recipientAccount, halfEther, transactionHash3, foreignBridge.address); + const transactionHash3 = '0x022695428093bb292db8e48bd1417c5e1b84c0bf673bd0fff23ed0fb6495b872' + const message3 = createMessage(recipientAccount, halfEther, transactionHash3, foreignBridge.address) const signature3 = await sign(authorities[0], message3) - const vrs3 = signatureToVRS(signature3); + const vrs3 = signatureToVRS(signature3) await foreignBridge.executeSignatures([vrs3.v], [vrs3.r], [vrs3.s], message3).should.be.rejectedWith(ERROR_MSG) }) }) describe('#withdraw with 2 minimum signatures', async () => { - let multisigValidatorContract, twoAuthorities, ownerOfValidatorContract, foreignBridgeWithMultiSignatures + let multisigValidatorContract + let twoAuthorities + let ownerOfValidatorContract + let foreignBridgeWithMultiSignatures const value = halfEther beforeEach(async () => { multisigValidatorContract = await BridgeValidators.new() - token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); - twoAuthorities = [accounts[0], accounts[1]]; + token = await ERC677BridgeToken.new('Some ERC20', 'RSZT', 18) + twoAuthorities = [accounts[0], accounts[1]] ownerOfValidatorContract = accounts[3] - await multisigValidatorContract.initialize(2, twoAuthorities, ownerOfValidatorContract, {from: ownerOfValidatorContract}) + await multisigValidatorContract.initialize(2, twoAuthorities, ownerOfValidatorContract, { + from: ownerOfValidatorContract + }) foreignBridgeWithMultiSignatures = await ForeignBridge.new() - await foreignBridgeWithMultiSignatures.initialize(multisigValidatorContract.address, token.address, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner, {from: ownerOfValidatorContract}); - await token.mint(foreignBridgeWithMultiSignatures.address,value); + await foreignBridgeWithMultiSignatures.initialize( + multisigValidatorContract.address, + token.address, + requireBlockConfirmations, + gasPrice, + maxPerTx, + homeDailyLimit, + homeMaxPerTx, + owner, + { from: ownerOfValidatorContract } + ) + await token.mint(foreignBridgeWithMultiSignatures.address, value) }) it('withdraw should fail if not enough signatures are provided', async () => { - const recipientAccount = accounts[4]; + const recipientAccount = accounts[4] // msg 1 - const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - const message = createMessage(recipientAccount, value, transactionHash, foreignBridgeWithMultiSignatures.address); + const transactionHash = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' + const message = createMessage(recipientAccount, value, transactionHash, foreignBridgeWithMultiSignatures.address) const signature = await sign(twoAuthorities[0], message) - const vrs = signatureToVRS(signature); + const vrs = signatureToVRS(signature) false.should.be.equal(await foreignBridgeWithMultiSignatures.relayedMessages(transactionHash)) - await foreignBridgeWithMultiSignatures.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.rejectedWith(ERROR_MSG) + await foreignBridgeWithMultiSignatures + .executeSignatures([vrs.v], [vrs.r], [vrs.s], message) + .should.be.rejectedWith(ERROR_MSG) // msg 2 const signature2 = await sign(twoAuthorities[1], message) - const vrs2 = signatureToVRS(signature2); + const vrs2 = signatureToVRS(signature2) - const {logs} = await foreignBridgeWithMultiSignatures.executeSignatures([vrs.v, vrs2.v], [vrs.r, vrs2.r], [vrs.s, vrs2.s], message).should.be.fulfilled; + const { logs } = await foreignBridgeWithMultiSignatures.executeSignatures( + [vrs.v, vrs2.v], + [vrs.r, vrs2.r], + [vrs.s, vrs2.s], + message + ).should.be.fulfilled - logs[0].event.should.be.equal("RelayedMessage") + logs[0].event.should.be.equal('RelayedMessage') logs[0].args.recipient.should.be.equal(recipientAccount) logs[0].args.value.should.be.bignumber.equal(value) true.should.be.equal(await foreignBridgeWithMultiSignatures.relayedMessages(transactionHash)) }) it('withdraw should fail if duplicate signature is provided', async () => { - const recipientAccount = accounts[4]; - const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - const message = createMessage(recipientAccount, value, transactionHash, foreignBridgeWithMultiSignatures.address); + const recipientAccount = accounts[4] + const transactionHash = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' + const message = createMessage(recipientAccount, value, transactionHash, foreignBridgeWithMultiSignatures.address) const signature = await sign(twoAuthorities[0], message) - const vrs = signatureToVRS(signature); + const vrs = signatureToVRS(signature) false.should.be.equal(await foreignBridgeWithMultiSignatures.relayedMessages(transactionHash)) - await foreignBridgeWithMultiSignatures.executeSignatures([vrs.v, vrs.v], [vrs.r, vrs.r], [vrs.s, vrs.s], message).should.be.rejectedWith(ERROR_MSG) + await foreignBridgeWithMultiSignatures + .executeSignatures([vrs.v, vrs.v], [vrs.r, vrs.r], [vrs.s, vrs.s], message) + .should.be.rejectedWith(ERROR_MSG) }) it('works with 5 validators and 3 required signatures', async () => { const recipient = accounts[8] @@ -243,31 +367,44 @@ contract('ForeignBridge_ERC20_to_Native', async (accounts) => { const ownerOfValidators = accounts[0] const validatorContractWith3Signatures = await BridgeValidators.new() await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) - const erc20Token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); + const erc20Token = await ERC677BridgeToken.new('Some ERC20', 'RSZT', 18) const value = halfEther const foreignBridgeWithThreeSigs = await ForeignBridge.new() - await foreignBridgeWithThreeSigs.initialize(validatorContractWith3Signatures.address, erc20Token.address, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner); - await erc20Token.mint(foreignBridgeWithThreeSigs.address, value); - - const txHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - const message = createMessage(recipient, value, txHash, foreignBridgeWithThreeSigs.address); + await foreignBridgeWithThreeSigs.initialize( + validatorContractWith3Signatures.address, + erc20Token.address, + requireBlockConfirmations, + gasPrice, + maxPerTx, + homeDailyLimit, + homeMaxPerTx, + owner + ) + await erc20Token.mint(foreignBridgeWithThreeSigs.address, value) + + const txHash = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' + const message = createMessage(recipient, value, txHash, foreignBridgeWithThreeSigs.address) // signature 1 const signature = await sign(authoritiesFiveAccs[0], message) - const vrs = signatureToVRS(signature); + const vrs = signatureToVRS(signature) // signature 2 const signature2 = await sign(authoritiesFiveAccs[1], message) - const vrs2 = signatureToVRS(signature2); + const vrs2 = signatureToVRS(signature2) // signature 3 const signature3 = await sign(authoritiesFiveAccs[2], message) - const vrs3 = signatureToVRS(signature3); - - - const {logs} = await foreignBridgeWithThreeSigs.executeSignatures([vrs.v, vrs2.v, vrs3.v], [vrs.r, vrs2.r, vrs3.r], [vrs.s, vrs2.s, vrs3.s], message).should.be.fulfilled; - logs[0].event.should.be.equal("RelayedMessage") + const vrs3 = signatureToVRS(signature3) + + const { logs } = await foreignBridgeWithThreeSigs.executeSignatures( + [vrs.v, vrs2.v, vrs3.v], + [vrs.r, vrs2.r, vrs3.r], + [vrs.s, vrs2.s, vrs3.s], + message + ).should.be.fulfilled + logs[0].event.should.be.equal('RelayedMessage') logs[0].args.recipient.should.be.equal(recipient) logs[0].args.value.should.be.bignumber.equal(value) true.should.be.equal(await foreignBridgeWithThreeSigs.relayedMessages(txHash)) @@ -278,30 +415,39 @@ contract('ForeignBridge_ERC20_to_Native', async (accounts) => { it('can be upgraded', async () => { const REQUIRED_NUMBER_OF_VALIDATORS = 1 const VALIDATORS = [accounts[1]] - const PROXY_OWNER = accounts[0] + const PROXY_OWNER = accounts[0] // Validators Contract - let validatorsProxy = await EternalStorageProxy.new().should.be.fulfilled; - const validatorsContractImpl = await BridgeValidators.new().should.be.fulfilled; - await validatorsProxy.upgradeTo('1', validatorsContractImpl.address).should.be.fulfilled; + let validatorsProxy = await EternalStorageProxy.new().should.be.fulfilled + const validatorsContractImpl = await BridgeValidators.new().should.be.fulfilled + await validatorsProxy.upgradeTo('1', validatorsContractImpl.address).should.be.fulfilled validatorsContractImpl.address.should.be.equal(await validatorsProxy.implementation()) - validatorsProxy = await BridgeValidators.at(validatorsProxy.address); - await validatorsProxy.initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, PROXY_OWNER).should.be.fulfilled; - let token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); + validatorsProxy = await BridgeValidators.at(validatorsProxy.address) + await validatorsProxy.initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, PROXY_OWNER).should.be.fulfilled + const token = await ERC677BridgeToken.new('Some ERC20', 'RSZT', 18) // ForeignBridge V1 Contract - let foreignBridgeProxy = await EternalStorageProxy.new().should.be.fulfilled; - const foreignBridgeImpl = await ForeignBridge.new().should.be.fulfilled; - await foreignBridgeProxy.upgradeTo('1', foreignBridgeImpl.address).should.be.fulfilled; - - foreignBridgeProxy = await ForeignBridge.at(foreignBridgeProxy.address); - await foreignBridgeProxy.initialize(validatorsProxy.address, token.address, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner) + let foreignBridgeProxy = await EternalStorageProxy.new().should.be.fulfilled + const foreignBridgeImpl = await ForeignBridge.new().should.be.fulfilled + await foreignBridgeProxy.upgradeTo('1', foreignBridgeImpl.address).should.be.fulfilled + + foreignBridgeProxy = await ForeignBridge.at(foreignBridgeProxy.address) + await foreignBridgeProxy.initialize( + validatorsProxy.address, + token.address, + requireBlockConfirmations, + gasPrice, + maxPerTx, + homeDailyLimit, + homeMaxPerTx, + owner + ) // Deploy V2 - let foreignImplV2 = await ForeignBridgeV2.new(); - let foreignBridgeProxyUpgrade = await EternalStorageProxy.at(foreignBridgeProxy.address); - await foreignBridgeProxyUpgrade.upgradeTo('2', foreignImplV2.address).should.be.fulfilled; + const foreignImplV2 = await ForeignBridgeV2.new() + const foreignBridgeProxyUpgrade = await EternalStorageProxy.at(foreignBridgeProxy.address) + await foreignBridgeProxyUpgrade.upgradeTo('2', foreignImplV2.address).should.be.fulfilled foreignImplV2.address.should.be.equal(await foreignBridgeProxyUpgrade.implementation()) }) @@ -309,38 +455,49 @@ contract('ForeignBridge_ERC20_to_Native', async (accounts) => { const tokenAddress = token.address const validatorsAddress = validatorContract.address - const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; - const foreignBridge = await ForeignBridge.new(); - const data = foreignBridge.contract.methods.initialize(validatorsAddress, tokenAddress, requireBlockConfirmations, gasPrice, '2', '3', '2', owner).encodeABI() + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled + const foreignBridge = await ForeignBridge.new() + const data = foreignBridge.contract.methods + .initialize(validatorsAddress, tokenAddress, requireBlockConfirmations, gasPrice, '2', '3', '2', owner) + .encodeABI() - await storageProxy.upgradeToAndCall('1', foreignBridge.address, data).should.be.fulfilled; + await storageProxy.upgradeToAndCall('1', foreignBridge.address, data).should.be.fulfilled - let finalContract = await ForeignBridge.at(storageProxy.address); - true.should.be.equal(await finalContract.isInitialized()); + const finalContract = await ForeignBridge.at(storageProxy.address) + true.should.be.equal(await finalContract.isInitialized()) validatorsAddress.should.be.equal(await finalContract.validatorContract()) }) }) describe('#claimTokens', async () => { it('can send erc20', async () => { - const owner = accounts[0]; - token = await ERC677BridgeToken.new("Some ERC20", "RSZT", 18); - const foreignBridgeImpl = await ForeignBridge.new(); - const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + const owner = accounts[0] + token = await ERC677BridgeToken.new('Some ERC20', 'RSZT', 18) + const foreignBridgeImpl = await ForeignBridge.new() + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled await storageProxy.upgradeTo('1', foreignBridgeImpl.address).should.be.fulfilled - const foreignBridge = await ForeignBridge.at(storageProxy.address); - - await foreignBridge.initialize(validatorContract.address, token.address, requireBlockConfirmations, gasPrice, maxPerTx, homeDailyLimit, homeMaxPerTx, owner); - const tokenSecond = await ERC677BridgeToken.new("Roman Token", "RST", 18); - - await tokenSecond.mint(accounts[0], halfEther).should.be.fulfilled; + const foreignBridge = await ForeignBridge.at(storageProxy.address) + + await foreignBridge.initialize( + validatorContract.address, + token.address, + requireBlockConfirmations, + gasPrice, + maxPerTx, + homeDailyLimit, + homeMaxPerTx, + owner + ) + const tokenSecond = await ERC677BridgeToken.new('Roman Token', 'RST', 18) + + await tokenSecond.mint(accounts[0], halfEther).should.be.fulfilled expect(await tokenSecond.balanceOf(accounts[0])).to.be.bignumber.equal(halfEther) - await tokenSecond.transfer(foreignBridge.address, halfEther); + await tokenSecond.transfer(foreignBridge.address, halfEther) expect(await tokenSecond.balanceOf(accounts[0])).to.be.bignumber.equal(ZERO) expect(await tokenSecond.balanceOf(foreignBridge.address)).to.be.bignumber.equal(halfEther) - await foreignBridge.claimTokens(tokenSecond.address, accounts[3], {from: owner}); + await foreignBridge.claimTokens(tokenSecond.address, accounts[3], { from: owner }) expect(await tokenSecond.balanceOf(foreignBridge.address)).to.be.bignumber.equal(ZERO) expect(await tokenSecond.balanceOf(accounts[3])).to.be.bignumber.equal(halfEther) }) diff --git a/test/erc_to_native/home_bridge.test.js b/test/erc_to_native/home_bridge.test.js index 55d3c803a..25b59bc76 100644 --- a/test/erc_to_native/home_bridge.test.js +++ b/test/erc_to_native/home_bridge.test.js @@ -2,26 +2,29 @@ const HomeBridge = artifacts.require('HomeBridgeErcToNative.sol') const EternalStorageProxy = artifacts.require('EternalStorageProxy.sol') const BridgeValidators = artifacts.require('BridgeValidators.sol') const BlockReward = artifacts.require('BlockReward') -const RewardableValidators = artifacts.require("RewardableValidators.sol"); -const FeeManagerErcToNative = artifacts.require("FeeManagerErcToNative.sol"); -const FeeManagerErcToNativePOSDAO = artifacts.require("FeeManagerErcToNativePOSDAO"); - -const { expect } = require('chai'); -const { ERROR_MSG, ZERO_ADDRESS, toBN } = require('../setup'); -const {createMessage, sign, ether, expectEventInLogs } = require('../helpers/helpers'); - -const minPerTx = ether('0.01'); -const requireBlockConfirmations = 8; -const gasPrice = web3.utils.toWei('1', 'gwei'); -const oneEther = ether('1'); -const halfEther = ether('0.5'); +const RewardableValidators = artifacts.require('RewardableValidators.sol') +const FeeManagerErcToNative = artifacts.require('FeeManagerErcToNative.sol') +const FeeManagerErcToNativePOSDAO = artifacts.require('FeeManagerErcToNativePOSDAO') + +const { expect } = require('chai') +const { ERROR_MSG, ZERO_ADDRESS, toBN } = require('../setup') +const { createMessage, sign, ether, expectEventInLogs } = require('../helpers/helpers') + +const minPerTx = ether('0.01') +const requireBlockConfirmations = 8 +const gasPrice = web3.utils.toWei('1', 'gwei') +const oneEther = ether('1') +const halfEther = ether('0.5') const foreignDailyLimit = oneEther const foreignMaxPerTx = halfEther const ZERO = toBN(0) - -contract('HomeBridge_ERC20_to_Native', async (accounts) => { - let homeContract, validatorContract, blockRewardContract, authorities, owner; +contract('HomeBridge_ERC20_to_Native', async accounts => { + let homeContract + let validatorContract + let blockRewardContract + let authorities + let owner before(async () => { validatorContract = await BridgeValidators.new() blockRewardContract = await BlockReward.new() @@ -30,7 +33,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { await validatorContract.initialize(1, authorities, owner) }) - describe('#initialize', async() => { + describe('#initialize', async () => { beforeEach(async () => { homeContract = await HomeBridge.new() }) @@ -42,7 +45,18 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { expect(await homeContract.isInitialized()).to.be.equal(false) expect(await homeContract.blockRewardContract()).to.be.equal(ZERO_ADDRESS) - await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + await homeContract.initialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ).should.be.fulfilled expect(await homeContract.isInitialized()).to.be.equal(true) expect(await homeContract.validatorContract()).to.be.equal(validatorContract.address) @@ -63,7 +77,18 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { it('can update block reward contract', async () => { ZERO_ADDRESS.should.be.equal(await homeContract.blockRewardContract()) - await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + await homeContract.initialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ).should.be.fulfilled blockRewardContract.address.should.be.equal(await homeContract.blockRewardContract()) @@ -72,7 +97,9 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { secondBlockRewardContract.address.should.be.equal(await homeContract.blockRewardContract()) const thirdBlockRewardContract = await BlockReward.new() - await homeContract.setBlockRewardContract(thirdBlockRewardContract.address, {from: accounts[4]}).should.be.rejectedWith(ERROR_MSG) + await homeContract + .setBlockRewardContract(thirdBlockRewardContract.address, { from: accounts[4] }) + .should.be.rejectedWith(ERROR_MSG) secondBlockRewardContract.address.should.be.equal(await homeContract.blockRewardContract()) const notAContract = accounts[5] @@ -86,18 +113,57 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { it('cant set maxPerTx > dailyLimit', async () => { false.should.be.equal(await homeContract.isInitialized()) - await homeContract.initialize(validatorContract.address, '1', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG) - await homeContract.initialize(validatorContract.address, '3', '2', '2', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG) + await homeContract + .initialize( + validatorContract.address, + '1', + '2', + '1', + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await homeContract + .initialize( + validatorContract.address, + '3', + '2', + '2', + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) false.should.be.equal(await homeContract.isInitialized()) }) it('can be deployed via upgradeToAndCall', async () => { - let storageProxy = await EternalStorageProxy.new().should.be.fulfilled; - let data = homeContract.contract.methods.initialize(validatorContract.address, "3", "2", "1", gasPrice, requireBlockConfirmations, blockRewardContract.address, '3', '2', owner).encodeABI() + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled + const data = homeContract.contract.methods + .initialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + '3', + '2', + owner + ) + .encodeABI() await storageProxy.upgradeToAndCall('1', homeContract.address, data).should.be.fulfilled - let finalContract = await HomeBridge.at(storageProxy.address); + const finalContract = await HomeBridge.at(storageProxy.address) expect(await finalContract.isInitialized()).to.be.equal(true) expect(await finalContract.validatorContract()).to.be.equal(validatorContract.address) @@ -108,12 +174,25 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { }) it('can be upgraded keeping the state', async () => { const homeOwner = accounts[8] - const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled const proxyOwner = await storageProxy.proxyOwner() - const data = homeContract.contract.methods.initialize(validatorContract.address, "3", "2", "1", gasPrice, requireBlockConfirmations, blockRewardContract.address, '3', '2', homeOwner).encodeABI() + const data = homeContract.contract.methods + .initialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + '3', + '2', + homeOwner + ) + .encodeABI() await storageProxy.upgradeToAndCall('1', homeContract.address, data).should.be.fulfilled - const finalContract = await HomeBridge.at(storageProxy.address); + const finalContract = await HomeBridge.at(storageProxy.address) expect(await finalContract.isInitialized()).to.be.equal(true) expect(await finalContract.validatorContract()).to.be.equal(validatorContract.address) @@ -125,7 +204,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const homeContractV2 = await HomeBridge.new() await storageProxy.upgradeTo('2', homeContractV2.address).should.be.fulfilled - const finalContractV2 = await HomeBridge.at(storageProxy.address); + const finalContractV2 = await HomeBridge.at(storageProxy.address) expect(await finalContractV2.isInitialized()).to.be.equal(true) expect(await finalContractV2.validatorContract()).to.be.equal(validatorContract.address) @@ -137,18 +216,96 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { }) it('cant initialize with invalid arguments', async () => { false.should.be.equal(await homeContract.isInitialized()) - await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, 0, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await homeContract.initialize(owner, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await homeContract.initialize(ZERO_ADDRESS, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, owner, foreignDailyLimit, foreignMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, halfEther, oneEther, owner).should.be.rejectedWith(ERROR_MSG); - await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled; + await homeContract + .initialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + 0, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await homeContract + .initialize( + owner, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await homeContract + .initialize( + ZERO_ADDRESS, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await homeContract + .initialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + owner, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await homeContract + .initialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + halfEther, + oneEther, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await homeContract.initialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ).should.be.fulfilled true.should.be.equal(await homeContract.isInitialized()) }) }) - describe('#rewardableInitialize', async() => { - let feeManager, homeFee, foreignFee + describe('#rewardableInitialize', async () => { + let feeManager + let homeFee + let foreignFee beforeEach(async () => { feeManager = await FeeManagerErcToNative.new() homeContract = await HomeBridge.new() @@ -163,7 +320,21 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { expect(await homeContract.isInitialized()).to.be.equal(false) expect(await homeContract.blockRewardContract()).to.be.equal(ZERO_ADDRESS) - await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled + await homeContract.rewardableInitialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + homeFee, + foreignFee + ).should.be.fulfilled expect(await homeContract.isInitialized()).to.be.equal(true) expect(await homeContract.validatorContract()).to.be.equal(validatorContract.address) @@ -190,18 +361,142 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { it('cant initialize with invalid arguments', async () => { false.should.be.equal(await homeContract.isInitialized()) - await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, 0, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); - await homeContract.rewardableInitialize(owner, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); - await homeContract.rewardableInitialize(ZERO_ADDRESS, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); - await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, owner, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); - await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, halfEther, oneEther, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); - await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, ZERO_ADDRESS, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); - await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + await homeContract + .rewardableInitialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + 0, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + homeFee, + foreignFee + ) + .should.be.rejectedWith(ERROR_MSG) + await homeContract + .rewardableInitialize( + owner, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + homeFee, + foreignFee + ) + .should.be.rejectedWith(ERROR_MSG) + await homeContract + .rewardableInitialize( + ZERO_ADDRESS, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + homeFee, + foreignFee + ) + .should.be.rejectedWith(ERROR_MSG) + await homeContract + .rewardableInitialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + owner, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + homeFee, + foreignFee + ) + .should.be.rejectedWith(ERROR_MSG) + await homeContract + .rewardableInitialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + halfEther, + oneEther, + owner, + feeManager.address, + homeFee, + foreignFee + ) + .should.be.rejectedWith(ERROR_MSG) + await homeContract + .rewardableInitialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner, + ZERO_ADDRESS, + homeFee, + foreignFee + ) + .should.be.rejectedWith(ERROR_MSG) + await homeContract.rewardableInitialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + homeFee, + foreignFee + ).should.be.fulfilled true.should.be.equal(await homeContract.isInitialized()) }) it('can update fee contract', async () => { - await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + await homeContract.rewardableInitialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + homeFee, + foreignFee + ).should.be.fulfilled // Given const newFeeManager = await FeeManagerErcToNative.new() @@ -215,7 +510,21 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { }) it('can update fee', async () => { - await homeContract.rewardableInitialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + await homeContract.rewardableInitialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + homeFee, + foreignFee + ).should.be.fulfilled // Given const newHomeFee = ether('0.1') @@ -236,7 +545,18 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { describe('#fallback', async () => { beforeEach(async () => { homeContract = await HomeBridge.new() - await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner) + await homeContract.initialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) }) it('should accept native coins', async () => { @@ -247,7 +567,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const minted = await blockRewardContract.mintedTotallyByBridge(homeContract.address) minted.should.be.bignumber.equal('10') - const {logs} = await homeContract.sendTransaction({ from: accounts[1], value: 1 }).should.be.fulfilled + const { logs } = await homeContract.sendTransaction({ from: accounts[1], value: 1 }).should.be.fulfilled expectEventInLogs(logs, 'UserRequestForSignature', { recipient: accounts[1], value: toBN(1) }) expect(await homeContract.totalSpentPerDay(currentDay)).to.be.bignumber.equal('1') @@ -287,13 +607,13 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { expect(await homeContract.totalSpentPerDay(currentDay)).to.be.bignumber.equal('1') expect(await homeContract.totalBurntCoins()).to.be.bignumber.equal('1') - await homeContract.sendTransaction({ from: accounts[1], value: 1 }).should.be.fulfilled; + await homeContract.sendTransaction({ from: accounts[1], value: 1 }).should.be.fulfilled expect(await homeContract.totalSpentPerDay(currentDay)).to.be.bignumber.equal('2') - await homeContract.sendTransaction({ from: accounts[1], value: 2 }).should.be.rejectedWith(ERROR_MSG); + await homeContract.sendTransaction({ from: accounts[1], value: 2 }).should.be.rejectedWith(ERROR_MSG) - await homeContract.setDailyLimit(4).should.be.fulfilled; - await homeContract.sendTransaction({ from: accounts[1], value: 2 }).should.be.fulfilled; + await homeContract.setDailyLimit(4).should.be.fulfilled + await homeContract.sendTransaction({ from: accounts[1], value: 2 }).should.be.fulfilled expect(await homeContract.totalSpentPerDay(currentDay)).to.be.bignumber.equal('4') expect(await homeContract.totalBurntCoins()).to.be.bignumber.equal('4') }) @@ -305,43 +625,47 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { from: accounts[1], value: 1 }).should.be.fulfilled - await homeContract.sendTransaction({ - from: accounts[1], - value: 3 - }).should.be.rejectedWith(ERROR_MSG) - await homeContract.setMaxPerTx(100).should.be.rejectedWith(ERROR_MSG); - await homeContract.setDailyLimit(100).should.be.fulfilled; - await homeContract.setMaxPerTx(99).should.be.fulfilled; - //meets max per tx and daily limit + await homeContract + .sendTransaction({ + from: accounts[1], + value: 3 + }) + .should.be.rejectedWith(ERROR_MSG) + await homeContract.setMaxPerTx(100).should.be.rejectedWith(ERROR_MSG) + await homeContract.setDailyLimit(100).should.be.fulfilled + await homeContract.setMaxPerTx(99).should.be.fulfilled + // meets max per tx and daily limit await homeContract.sendTransaction({ from: accounts[1], value: 99 }).should.be.fulfilled - //above daily limit - await homeContract.sendTransaction({ - from: accounts[1], - value: 1 - }).should.be.rejectedWith(ERROR_MSG) - + // above daily limit + await homeContract + .sendTransaction({ + from: accounts[1], + value: 1 + }) + .should.be.rejectedWith(ERROR_MSG) }) it('should not let to deposit less than minPerTx', async () => { - const newDailyLimit = 100; - const newMaxPerTx = 50; - const newMinPerTx = 20; + const newDailyLimit = 100 + const newMaxPerTx = 50 + const newMinPerTx = 20 await blockRewardContract.addMintedTotallyByBridge(200, homeContract.address) - await homeContract.setDailyLimit(newDailyLimit).should.be.fulfilled; - await homeContract.setMaxPerTx(newMaxPerTx).should.be.fulfilled; - await homeContract.setMinPerTx(newMinPerTx).should.be.fulfilled; + await homeContract.setDailyLimit(newDailyLimit).should.be.fulfilled + await homeContract.setMaxPerTx(newMaxPerTx).should.be.fulfilled + await homeContract.setMinPerTx(newMinPerTx).should.be.fulfilled await homeContract.sendTransaction({ from: accounts[1], value: newMinPerTx }).should.be.fulfilled - await homeContract.sendTransaction({ from: accounts[1], value: newMinPerTx - 1 }).should.be.rejectedWith(ERROR_MSG) + await homeContract + .sendTransaction({ from: accounts[1], value: newMinPerTx - 1 }) + .should.be.rejectedWith(ERROR_MSG) }) it('should fail if not enough bridged tokens', async () => { - const initiallyMinted = await blockRewardContract.mintedTotallyByBridge(homeContract.address) initiallyMinted.should.be.bignumber.equal(ZERO) @@ -364,53 +688,64 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { }) describe('#setting limits', async () => { - let homeContract; + let homeContract beforeEach(async () => { homeContract = await HomeBridge.new() - await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner) + await homeContract.initialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) }) it('setMaxPerTx allows to set only to owner and cannot be more than daily limit', async () => { - await homeContract.setMaxPerTx(2, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG); - await homeContract.setMaxPerTx(2, {from: owner}).should.be.fulfilled; + await homeContract.setMaxPerTx(2, { from: authorities[0] }).should.be.rejectedWith(ERROR_MSG) + await homeContract.setMaxPerTx(2, { from: owner }).should.be.fulfilled - await homeContract.setMaxPerTx(3, {from: owner}).should.be.rejectedWith(ERROR_MSG); + await homeContract.setMaxPerTx(3, { from: owner }).should.be.rejectedWith(ERROR_MSG) const maxPerTx = await homeContract.maxPerTx() maxPerTx.should.be.bignumber.equal(toBN(2)) }) it('setMinPerTx allows to set only to owner and cannot be more than daily limit and should be less than maxPerTx', async () => { - await homeContract.setMinPerTx(1, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG); - await homeContract.setMinPerTx(1, {from: owner}).should.be.fulfilled; + await homeContract.setMinPerTx(1, { from: authorities[0] }).should.be.rejectedWith(ERROR_MSG) + await homeContract.setMinPerTx(1, { from: owner }).should.be.fulfilled - await homeContract.setMinPerTx(2, {from: owner}).should.be.rejectedWith(ERROR_MSG); + await homeContract.setMinPerTx(2, { from: owner }).should.be.rejectedWith(ERROR_MSG) const minPerTx = await homeContract.minPerTx() minPerTx.should.be.bignumber.equal(toBN(1)) }) it('setExecutionMaxPerTx allows to set only to owner and cannot be more than execution daily limit', async () => { - const newValue = ether('0.3'); + const newValue = ether('0.3') const initialExecutionMaxPerTx = await homeContract.executionMaxPerTx() initialExecutionMaxPerTx.should.be.bignumber.not.equal(newValue) - await homeContract.setExecutionMaxPerTx(newValue, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG); - await homeContract.setExecutionMaxPerTx(newValue, {from: owner}).should.be.fulfilled; + await homeContract.setExecutionMaxPerTx(newValue, { from: authorities[0] }).should.be.rejectedWith(ERROR_MSG) + await homeContract.setExecutionMaxPerTx(newValue, { from: owner }).should.be.fulfilled - await homeContract.setExecutionMaxPerTx(oneEther, {from: owner}).should.be.rejectedWith(ERROR_MSG); + await homeContract.setExecutionMaxPerTx(oneEther, { from: owner }).should.be.rejectedWith(ERROR_MSG) const executionMaxPerTx = await homeContract.executionMaxPerTx() executionMaxPerTx.should.be.bignumber.equal(newValue) }) it('executionDailyLimit allows to set only to owner', async () => { - const newValue = ether('1.5'); + const newValue = ether('1.5') - const initialExecutionDailyLimit= await homeContract.executionDailyLimit() + const initialExecutionDailyLimit = await homeContract.executionDailyLimit() initialExecutionDailyLimit.should.be.bignumber.not.equal(newValue) - await homeContract.setExecutionDailyLimit(newValue, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG); - await homeContract.setExecutionDailyLimit(newValue, {from: owner}).should.be.fulfilled; + await homeContract.setExecutionDailyLimit(newValue, { from: authorities[0] }).should.be.rejectedWith(ERROR_MSG) + await homeContract.setExecutionDailyLimit(newValue, { from: owner }).should.be.fulfilled const executionDailyLimit = await homeContract.executionDailyLimit() executionDailyLimit.should.be.bignumber.equal(newValue) @@ -418,10 +753,21 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { }) describe('#executeAffirmation', async () => { - let homeBridge; + let homeBridge beforeEach(async () => { - homeBridge = await HomeBridge.new(); - await homeBridge.initialize(validatorContract.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner); + homeBridge = await HomeBridge.new() + await homeBridge.initialize( + validatorContract.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) await blockRewardContract.sendTransaction({ from: accounts[2], value: oneEther @@ -429,11 +775,13 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { }) it('should allow validator to executeAffirmation', async () => { - const recipient = accounts[5]; - const value = halfEther; + const recipient = accounts[5] + const value = halfEther const balanceBefore = await web3.eth.getBalance(recipient) - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - const {logs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}) + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: authorities[0] + }) expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], @@ -447,17 +795,19 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const balanceAfter = toBN(await web3.eth.getBalance(recipient)) balanceAfter.should.be.bignumber.equal(toBN(balanceBefore).add(value)) - const msgHash = web3.utils.soliditySha3(recipient, value, transactionHash); + const msgHash = web3.utils.soliditySha3(recipient, value, transactionHash) const senderHash = web3.utils.soliditySha3(authorities[0], msgHash) true.should.be.equal(await homeBridge.affirmationsSigned(senderHash)) }) it('should allow validator to executeAffirmation with zero value', async () => { - const recipient = accounts[5]; + const recipient = accounts[5] const value = ZERO const balanceBefore = await web3.eth.getBalance(recipient) - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - const {logs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}) + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: authorities[0] + }) expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], @@ -472,87 +822,142 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const balanceAfter = toBN(await web3.eth.getBalance(recipient)) balanceAfter.should.be.bignumber.equal(toBN(balanceBefore).add(value)) - const msgHash = web3.utils.soliditySha3(recipient, value, transactionHash); + const msgHash = web3.utils.soliditySha3(recipient, value, transactionHash) const senderHash = web3.utils.soliditySha3(authorities[0], msgHash) true.should.be.equal(await homeBridge.affirmationsSigned(senderHash)) }) it('test with 2 signatures required', async () => { const validatorContractWith2Signatures = await BridgeValidators.new() - const authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]]; + const authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]] const ownerOfValidators = accounts[0] await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, ownerOfValidators) - const homeBridgeWithTwoSigs = await HomeBridge.new(); - await homeBridgeWithTwoSigs.initialize(validatorContractWith2Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner); - const recipient = accounts[5]; - const value = halfEther; - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const homeBridgeWithTwoSigs = await HomeBridge.new() + await homeBridgeWithTwoSigs.initialize( + validatorContractWith2Signatures.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) + const recipient = accounts[5] + const value = halfEther + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' const balanceBefore = toBN(await web3.eth.getBalance(recipient)) - const msgHash = web3.utils.soliditySha3(recipient, value, transactionHash); + const msgHash = web3.utils.soliditySha3(recipient, value, transactionHash) - const { logs } = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; + const { logs } = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, { + from: authoritiesThreeAccs[0] + }).should.be.fulfilled expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], transactionHash }) - const notProcessed = await homeBridgeWithTwoSigs.numAffirmationsSigned(msgHash); - notProcessed.should.be.bignumber.equal('1'); + const notProcessed = await homeBridgeWithTwoSigs.numAffirmationsSigned(msgHash) + notProcessed.should.be.bignumber.equal('1') - await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[0]}).should.be.rejectedWith(ERROR_MSG); - const secondSignature = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; + await homeBridgeWithTwoSigs + .executeAffirmation(recipient, value, transactionHash, { from: authoritiesThreeAccs[0] }) + .should.be.rejectedWith(ERROR_MSG) + const secondSignature = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, { + from: authoritiesThreeAccs[1] + }).should.be.fulfilled const balanceAfter = toBN(await web3.eth.getBalance(recipient)) balanceAfter.should.be.bignumber.equal(balanceBefore.add(value)) - expectEventInLogs(secondSignature.logs, 'AffirmationCompleted', { recipient, value, transactionHash }) + expectEventInLogs(secondSignature.logs, 'AffirmationCompleted', { + recipient, + value, + transactionHash + }) const senderHash = web3.utils.soliditySha3(authoritiesThreeAccs[0], msgHash) true.should.be.equal(await homeBridgeWithTwoSigs.affirmationsSigned(senderHash)) - const senderHash2 = web3.utils.soliditySha3(authoritiesThreeAccs[1], msgHash); + const senderHash2 = web3.utils.soliditySha3(authoritiesThreeAccs[1], msgHash) true.should.be.equal(await homeBridgeWithTwoSigs.affirmationsSigned(senderHash2)) - const markedAsProcessed = await homeBridgeWithTwoSigs.numAffirmationsSigned(msgHash); - const processed = (toBN(2)).pow(toBN(255)).add(toBN(2)) + const markedAsProcessed = await homeBridgeWithTwoSigs.numAffirmationsSigned(msgHash) + const processed = toBN(2) + .pow(toBN(255)) + .add(toBN(2)) markedAsProcessed.should.be.bignumber.equal(processed) }) it('should not allow non-validator to execute affirmation', async () => { - const recipient = accounts[5]; - const value = oneEther; - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: accounts[7]}).should.be.rejectedWith(ERROR_MSG); + const recipient = accounts[5] + const value = oneEther + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + await homeBridge + .executeAffirmation(recipient, value, transactionHash, { from: accounts[7] }) + .should.be.rejectedWith(ERROR_MSG) }) it('should fail if the block reward contract is not set', async () => { - homeBridge = await HomeBridge.new(); - await homeBridge.initialize(validatorContract.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, ZERO_ADDRESS, foreignDailyLimit, foreignMaxPerTx, owner); - - const recipient = accounts[5]; - const value = halfEther; - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG) + homeBridge = await HomeBridge.new() + await homeBridge.initialize( + validatorContract.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + ZERO_ADDRESS, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) + + const recipient = accounts[5] + const value = halfEther + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + await homeBridge + .executeAffirmation(recipient, value, transactionHash, { from: authorities[0] }) + .should.be.rejectedWith(ERROR_MSG) }) it('works with 5 validators and 3 required signatures', async () => { const recipient = accounts[8] const authoritiesFiveAccs = [accounts[1], accounts[2], accounts[3], accounts[4], accounts[5]] - let ownerOfValidators = accounts[0] + const ownerOfValidators = accounts[0] const validatorContractWith3Signatures = await BridgeValidators.new() await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) - const homeBridgeWithThreeSigs = await HomeBridge.new(); - await homeBridgeWithThreeSigs.initialize(validatorContractWith3Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner); + const homeBridgeWithThreeSigs = await HomeBridge.new() + await homeBridgeWithThreeSigs.initialize( + validatorContractWith3Signatures.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) const value = halfEther - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' - const {logs} = await homeBridgeWithThreeSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesFiveAccs[0]}).should.be.fulfilled; + const { logs } = await homeBridgeWithThreeSigs.executeAffirmation(recipient, value, transactionHash, { + from: authoritiesFiveAccs[0] + }).should.be.fulfilled expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], transactionHash }) - await homeBridgeWithThreeSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesFiveAccs[1]}).should.be.fulfilled; - const thirdSignature = await homeBridgeWithThreeSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesFiveAccs[2]}).should.be.fulfilled; + await homeBridgeWithThreeSigs.executeAffirmation(recipient, value, transactionHash, { + from: authoritiesFiveAccs[1] + }).should.be.fulfilled + const thirdSignature = await homeBridgeWithThreeSigs.executeAffirmation(recipient, value, transactionHash, { + from: authoritiesFiveAccs[2] + }).should.be.fulfilled expectEventInLogs(thirdSignature.logs, 'AffirmationCompleted', { recipient, @@ -561,10 +966,12 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { }) }) it('should not allow execute affirmation over foreign max tx limit', async () => { - const recipient = accounts[5]; - const value = oneEther; - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - const {logs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.fulfilled; + const recipient = accounts[5] + const value = oneEther + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: authorities[0] + }).should.be.fulfilled expectEventInLogs(logs, 'AmountLimitExceeded', { recipient, @@ -573,10 +980,12 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { }) }) it('should fail if txHash already set as above of limits', async () => { - const recipient = accounts[5]; - const value = oneEther; - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - const {logs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.fulfilled; + const recipient = accounts[5] + const value = oneEther + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: authorities[0] + }).should.be.fulfilled expectEventInLogs(logs, 'AmountLimitExceeded', { recipient, @@ -584,8 +993,12 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { transactionHash }) - await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG) - await homeBridge.executeAffirmation(accounts[6], value, transactionHash, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG) + await homeBridge + .executeAffirmation(recipient, value, transactionHash, { from: authorities[0] }) + .should.be.rejectedWith(ERROR_MSG) + await homeBridge + .executeAffirmation(accounts[6], value, transactionHash, { from: authorities[0] }) + .should.be.rejectedWith(ERROR_MSG) }) it('should not allow execute affirmation over daily foreign limit', async () => { await blockRewardContract.sendTransaction({ @@ -593,10 +1006,12 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { value: oneEther }).should.be.fulfilled - const recipient = accounts[5]; - const value = halfEther; - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.fulfilled; + const recipient = accounts[5] + const value = halfEther + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: authorities[0] + }).should.be.fulfilled expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], @@ -608,8 +1023,10 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { transactionHash }) - const transactionHash2 = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - const { logs: logs2 } = await homeBridge.executeAffirmation(recipient, value, transactionHash2, {from: authorities[0]}).should.be.fulfilled; + const transactionHash2 = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' + const { logs: logs2 } = await homeBridge.executeAffirmation(recipient, value, transactionHash2, { + from: authorities[0] + }).should.be.fulfilled expectEventInLogs(logs2, 'SignedForAffirmation', { signer: authorities[0], @@ -621,8 +1038,10 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { transactionHash: transactionHash2 }) - const transactionHash3 = "0x69debd8fd1923c9cb3cd8ef6461e2740b2d037943b941729d5a47671a2bb8712"; - const { logs: logs3 } = await homeBridge.executeAffirmation(recipient, value, transactionHash3, {from: authorities[0]}).should.be.fulfilled; + const transactionHash3 = '0x69debd8fd1923c9cb3cd8ef6461e2740b2d037943b941729d5a47671a2bb8712' + const { logs: logs3 } = await homeBridge.executeAffirmation(recipient, value, transactionHash3, { + from: authorities[0] + }).should.be.fulfilled expectEventInLogs(logs3, 'AmountLimitExceeded', { recipient, @@ -634,8 +1053,10 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { outOfLimitAmount.should.be.bignumber.equal(halfEther) - const transactionHash4 = "0xc9ffe298d85ec5c515153608924b7bdcf1835539813dcc82cdbcc071170c3196"; - const { logs: logs4 } = await homeBridge.executeAffirmation(recipient, value, transactionHash4, {from: authorities[0]}).should.be.fulfilled; + const transactionHash4 = '0xc9ffe298d85ec5c515153608924b7bdcf1835539813dcc82cdbcc071170c3196' + const { logs: logs4 } = await homeBridge.executeAffirmation(recipient, value, transactionHash4, { + from: authorities[0] + }).should.be.fulfilled expectEventInLogs(logs4, 'AmountLimitExceeded', { recipient, @@ -649,50 +1070,74 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { }) describe('#submitSignature', async () => { - let validatorContractWith2Signatures,authoritiesThreeAccs,ownerOfValidators,homeBridgeWithTwoSigs + let validatorContractWith2Signatures + let authoritiesThreeAccs + let ownerOfValidators + let homeBridgeWithTwoSigs beforeEach(async () => { validatorContractWith2Signatures = await BridgeValidators.new() - authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]]; + authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]] ownerOfValidators = accounts[0] await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, ownerOfValidators) - homeBridgeWithTwoSigs = await HomeBridge.new(); - await homeBridgeWithTwoSigs.initialize(validatorContractWith2Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner); + homeBridgeWithTwoSigs = await HomeBridge.new() + await homeBridgeWithTwoSigs.initialize( + validatorContractWith2Signatures.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) }) it('allows a validator to submit a signature', async () => { const recipientAccount = accounts[8] const value = halfEther - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' + const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address) const signature = await sign(authoritiesThreeAccs[0], message) - const { logs } = await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authorities[0]}).should.be.fulfilled; + const { logs } = await homeBridgeWithTwoSigs.submitSignature(signature, message, { + from: authorities[0] + }).should.be.fulfilled logs[0].event.should.be.equal('SignedForUserRequest') const { messageHash } = logs[0].args - const signatureFromContract = await homeBridgeWithTwoSigs.signature(messageHash, 0); - const messageFromContract = await homeBridgeWithTwoSigs.message(messageHash); - signature.should.be.equal(signatureFromContract); - messageFromContract.should.be.equal(messageFromContract); - const hashMsg = web3.utils.soliditySha3(message); + const signatureFromContract = await homeBridgeWithTwoSigs.signature(messageHash, 0) + const messageFromContract = await homeBridgeWithTwoSigs.message(messageHash) + signature.should.be.equal(signatureFromContract) + messageFromContract.should.be.equal(messageFromContract) + const hashMsg = web3.utils.soliditySha3(message) const hashSenderMsg = web3.utils.soliditySha3(authorities[0], hashMsg) - true.should.be.equal(await homeBridgeWithTwoSigs.messagesSigned(hashSenderMsg)); + true.should.be.equal(await homeBridgeWithTwoSigs.messagesSigned(hashSenderMsg)) }) it('when enough requiredSignatures are collected, CollectedSignatures event is emitted', async () => { const recipientAccount = accounts[8] const value = halfEther - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' + const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address) const signature = await sign(authoritiesThreeAccs[0], message) const signature2 = await sign(authoritiesThreeAccs[1], message) - expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('2'); + expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('2') - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.rejectedWith(ERROR_MSG); - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[1]}).should.be.rejectedWith(ERROR_MSG); - const { logs } = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.submitSignature(signature, message, { + from: authoritiesThreeAccs[0] + }).should.be.fulfilled + await homeBridgeWithTwoSigs + .submitSignature(signature, message, { from: authoritiesThreeAccs[0] }) + .should.be.rejectedWith(ERROR_MSG) + await homeBridgeWithTwoSigs + .submitSignature(signature, message, { from: authoritiesThreeAccs[1] }) + .should.be.rejectedWith(ERROR_MSG) + const { logs } = await homeBridgeWithTwoSigs.submitSignature(signature2, message, { + from: authoritiesThreeAccs[1] + }).should.be.fulfilled logs.length.should.be.equal(2) logs[1].event.should.be.equal('CollectedSignatures') @@ -704,20 +1149,37 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const validatorContractWith3Signatures = await BridgeValidators.new() await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) - const homeBridgeWithThreeSigs = await HomeBridge.new(); - await homeBridgeWithThreeSigs.initialize(validatorContractWith3Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner); + const homeBridgeWithThreeSigs = await HomeBridge.new() + await homeBridgeWithThreeSigs.initialize( + validatorContractWith3Signatures.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) const value = halfEther - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithThreeSigs.address); + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' + const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithThreeSigs.address) const signature = await sign(authoritiesFiveAccs[0], message) const signature2 = await sign(authoritiesFiveAccs[1], message) const signature3 = await sign(authoritiesFiveAccs[2], message) - expect(await validatorContractWith3Signatures.requiredSignatures()).to.be.bignumber.equal('3'); + expect(await validatorContractWith3Signatures.requiredSignatures()).to.be.bignumber.equal('3') - await homeBridgeWithThreeSigs.submitSignature(signature, message, {from: authoritiesFiveAccs[0]}).should.be.fulfilled; - await homeBridgeWithThreeSigs.submitSignature(signature2, message, {from: authoritiesFiveAccs[1]}).should.be.fulfilled; - const {logs} = await homeBridgeWithThreeSigs.submitSignature(signature3, message, {from: authoritiesFiveAccs[2]}).should.be.fulfilled; + await homeBridgeWithThreeSigs.submitSignature(signature, message, { + from: authoritiesFiveAccs[0] + }).should.be.fulfilled + await homeBridgeWithThreeSigs.submitSignature(signature2, message, { + from: authoritiesFiveAccs[1] + }).should.be.fulfilled + const { logs } = await homeBridgeWithThreeSigs.submitSignature(signature3, message, { + from: authoritiesFiveAccs[2] + }).should.be.fulfilled logs.length.should.be.equal(2) logs[1].event.should.be.equal('CollectedSignatures') logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesFiveAccs[2]) @@ -725,40 +1187,54 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { it('attack when increasing requiredSignatures', async () => { const recipientAccount = accounts[8] const value = halfEther - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' + const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address) const signature = await sign(authoritiesThreeAccs[0], message) const signature2 = await sign(authoritiesThreeAccs[1], message) const signature3 = await sign(authoritiesThreeAccs[2], message) - expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('2'); + expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('2') - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.rejectedWith(ERROR_MSG); - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[1]}).should.be.rejectedWith(ERROR_MSG); - const { logs } = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.submitSignature(signature, message, { + from: authoritiesThreeAccs[0] + }).should.be.fulfilled + await homeBridgeWithTwoSigs + .submitSignature(signature, message, { from: authoritiesThreeAccs[0] }) + .should.be.rejectedWith(ERROR_MSG) + await homeBridgeWithTwoSigs + .submitSignature(signature, message, { from: authoritiesThreeAccs[1] }) + .should.be.rejectedWith(ERROR_MSG) + const { logs } = await homeBridgeWithTwoSigs.submitSignature(signature2, message, { + from: authoritiesThreeAccs[1] + }).should.be.fulfilled logs.length.should.be.equal(2) logs[1].event.should.be.equal('CollectedSignatures') logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesThreeAccs[1]) - await validatorContractWith2Signatures.setRequiredSignatures(3).should.be.fulfilled; - expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('3'); - await homeBridgeWithTwoSigs.submitSignature(signature3, message, {from: authoritiesThreeAccs[2]}).should.be.rejectedWith(ERROR_MSG); + await validatorContractWith2Signatures.setRequiredSignatures(3).should.be.fulfilled + expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('3') + await homeBridgeWithTwoSigs + .submitSignature(signature3, message, { from: authoritiesThreeAccs[2] }) + .should.be.rejectedWith(ERROR_MSG) }) it('attack when decreasing requiredSignatures', async () => { const recipientAccount = accounts[8] const value = halfEther - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' + const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address) const signature = await sign(authoritiesThreeAccs[0], message) const signature2 = await sign(authoritiesThreeAccs[1], message) - expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('2'); + expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('2') - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; - await validatorContractWith2Signatures.setRequiredSignatures(1).should.be.fulfilled; - expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('1'); - const { logs } = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.submitSignature(signature, message, { + from: authoritiesThreeAccs[0] + }).should.be.fulfilled + await validatorContractWith2Signatures.setRequiredSignatures(1).should.be.fulfilled + expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('1') + const { logs } = await homeBridgeWithTwoSigs.submitSignature(signature2, message, { + from: authoritiesThreeAccs[1] + }).should.be.fulfilled logs.length.should.be.equal(2) logs[1].event.should.be.equal('CollectedSignatures') @@ -776,21 +1252,34 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { }) }) describe('#fixAssetsAboveLimits', async () => { - let homeBridge; + let homeBridge beforeEach(async () => { - const homeBridgeImpl = await HomeBridge.new(); - const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + const homeBridgeImpl = await HomeBridge.new() + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled - homeBridge = await HomeBridge.at(storageProxy.address); - await homeBridge.initialize(validatorContract.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner); + homeBridge = await HomeBridge.at(storageProxy.address) + await homeBridge.initialize( + validatorContract.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) }) it('Should reduce outOfLimitAmount and not emit any event', async () => { - const recipient = accounts[5]; - const value = oneEther; - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - const {logs: affirmationLogs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.fulfilled + const recipient = accounts[5] + const value = oneEther + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + const { logs: affirmationLogs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: authorities[0] + }).should.be.fulfilled - affirmationLogs[0].event.should.be.equal("AmountLimitExceeded"); + affirmationLogs[0].event.should.be.equal('AmountLimitExceeded') const outOfLimitAmount = await homeBridge.outOfLimitAmount() outOfLimitAmount.should.be.bignumber.equal(value) @@ -803,12 +1292,14 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { newOutOfLimitAmount.should.be.bignumber.equal(ZERO) }) it('Should reduce outOfLimitAmount and emit UserRequestForSignature', async () => { - const recipient = accounts[5]; - const value = oneEther; - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - const {logs: affirmationLogs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.fulfilled + const recipient = accounts[5] + const value = oneEther + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + const { logs: affirmationLogs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: authorities[0] + }).should.be.fulfilled - affirmationLogs[0].event.should.be.equal("AmountLimitExceeded"); + affirmationLogs[0].event.should.be.equal('AmountLimitExceeded') const outOfLimitAmount = await homeBridge.outOfLimitAmount() outOfLimitAmount.should.be.bignumber.equal(value) @@ -825,13 +1316,17 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { newOutOfLimitAmount.should.be.bignumber.equal(ZERO) }) it('Should not be allow to be called by an already fixed txHash', async () => { - const recipient = accounts[5]; - const value = oneEther; - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - const transactionHash2 = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; + const recipient = accounts[5] + const value = oneEther + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + const transactionHash2 = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' - await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.fulfilled - await homeBridge.executeAffirmation(recipient, value, transactionHash2, {from: authorities[0]}).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: authorities[0] + }).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, value, transactionHash2, { + from: authorities[0] + }).should.be.fulfilled const outOfLimitAmount = await homeBridge.outOfLimitAmount() outOfLimitAmount.should.be.bignumber.equal(value.add(value)) @@ -850,37 +1345,42 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { await homeBridge.fixAssetsAboveLimits(transactionHash2, false).should.be.rejectedWith(ERROR_MSG) }) it('Should fail if txHash didnt increase out of limit amount', async () => { - const recipient = accounts[5]; - const value = oneEther; - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - const invalidTxHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; + const recipient = accounts[5] + const value = oneEther + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + const invalidTxHash = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' - const {logs: affirmationLogs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.fulfilled + const { logs: affirmationLogs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: authorities[0] + }).should.be.fulfilled - affirmationLogs[0].event.should.be.equal("AmountLimitExceeded"); + affirmationLogs[0].event.should.be.equal('AmountLimitExceeded') await homeBridge.fixAssetsAboveLimits(invalidTxHash, true).should.be.rejectedWith(ERROR_MSG) }) it('Should fail if not called by proxyOwner', async () => { - const recipient = accounts[5]; - const value = oneEther; - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const recipient = accounts[5] + const value = oneEther + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' - const {logs: affirmationLogs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.fulfilled + const { logs: affirmationLogs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: authorities[0] + }).should.be.fulfilled - affirmationLogs[0].event.should.be.equal("AmountLimitExceeded"); + affirmationLogs[0].event.should.be.equal('AmountLimitExceeded') - await homeBridge.fixAssetsAboveLimits(transactionHash, true, { from: recipient}).should.be.rejectedWith(ERROR_MSG) - await homeBridge.fixAssetsAboveLimits(transactionHash, true, { from: owner}).should.be.fulfilled + await homeBridge + .fixAssetsAboveLimits(transactionHash, true, { from: recipient }) + .should.be.rejectedWith(ERROR_MSG) + await homeBridge.fixAssetsAboveLimits(transactionHash, true, { from: owner }).should.be.fulfilled }) }) describe('#OwnedUpgradeability', async () => { - it('upgradeabilityAdmin should return the proxy owner', async () => { - const homeBridgeImpl = await HomeBridge.new(); - const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + const homeBridgeImpl = await HomeBridge.new() + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled - const homeBridge = await HomeBridge.at(storageProxy.address); + const homeBridge = await HomeBridge.at(storageProxy.address) const proxyOwner = await storageProxy.proxyOwner() const upgradeabilityAdmin = await homeBridge.upgradeabilityAdmin() @@ -890,19 +1390,31 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { }) describe('#feeManager', async () => { - let homeBridge, rewardableValidators - let owner = accounts[9] - let validators = [accounts[1]] - let rewards = [accounts[2]] - let requiredSignatures = 1 + let homeBridge + let rewardableValidators + const owner = accounts[9] + const validators = [accounts[1]] + const rewards = [accounts[2]] + const requiredSignatures = 1 beforeEach(async () => { rewardableValidators = await RewardableValidators.new() await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled - const homeBridgeImpl = await HomeBridge.new(); - const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + const homeBridgeImpl = await HomeBridge.new() + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled - homeBridge = await HomeBridge.at(storageProxy.address); - await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + homeBridge = await HomeBridge.at(storageProxy.address) + await homeBridge.initialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ).should.be.fulfilled await blockRewardContract.sendTransaction({ from: accounts[2], value: oneEther @@ -958,12 +1470,25 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const rewards = [accounts[2]] const requiredSignatures = 1 const rewardableValidators = await RewardableValidators.new() - const homeBridgeImpl = await HomeBridge.new(); - const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + const homeBridgeImpl = await HomeBridge.new() + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled - const homeBridge = await HomeBridge.at(storageProxy.address); - await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled - await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + const homeBridge = await HomeBridge.at(storageProxy.address) + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, { + from: owner + }).should.be.fulfilled + await homeBridge.initialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ).should.be.fulfilled await blockRewardContract.sendTransaction({ from: accounts[2], value: oneEther @@ -977,18 +1502,20 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setForeignFee(feeInWei, { from: owner }).should.be.fulfilled - const recipient = accounts[5]; - const value = halfEther; + const recipient = accounts[5] + const value = halfEther const valueCalc = 0.5 * (1 - fee) const finalValue = ether(valueCalc.toString()) const feeAmountCalc = 0.5 * fee const feeAmount = ether(feeAmountCalc.toString()) const balanceBefore = toBN(await web3.eth.getBalance(recipient)) const rewardAddressBalanceBefore = toBN(await web3.eth.getBalance(rewards[0])) - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' // When - const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[0] + }).should.be.fulfilled // Then expectEventInLogs(logs, 'SignedForAffirmation', { @@ -1018,13 +1545,26 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const rewards = [accounts[4], accounts[5], accounts[6]] const requiredSignatures = 2 const rewardableValidators = await RewardableValidators.new() - const homeBridgeImpl = await HomeBridge.new(); + const homeBridgeImpl = await HomeBridge.new() const blockRewardContract = await BlockReward.new() - const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled - const homeBridge = await HomeBridge.at(storageProxy.address); - await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled - await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + const homeBridge = await HomeBridge.at(storageProxy.address) + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, { + from: owner + }).should.be.fulfilled + await homeBridge.initialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ).should.be.fulfilled await blockRewardContract.sendTransaction({ from: accounts[0], value: halfEther @@ -1034,7 +1574,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const initialBlockRewardBalance = toBN(await web3.eth.getBalance(blockRewardContract.address)) initialBlockRewardBalance.should.be.bignumber.equal(halfEther) - const value = halfEther; + const value = halfEther // 0.1% fee const fee = 0.001 const feeInWei = ether(fee.toString()) @@ -1049,19 +1589,22 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setForeignFee(feeInWei, { from: owner }).should.be.fulfilled - const recipient = accounts[8]; + const recipient = accounts[8] const balanceBefore = toBN(await web3.eth.getBalance(recipient)) const initialBalanceRewardAddress1 = toBN(await web3.eth.getBalance(rewards[0])) const initialBalanceRewardAddress2 = toBN(await web3.eth.getBalance(rewards[1])) const initialBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) - - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' // When - const { logs: logsValidator1 } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled - const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[1]}).should.be.fulfilled + const { logs: logsValidator1 } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[0] + }).should.be.fulfilled + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[1] + }).should.be.fulfilled // Then logsValidator1.length.should.be.equals(1) @@ -1088,14 +1631,17 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const updatedBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) expect( - updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidator)) - || updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidatorPlusDiff))).to.equal(true) + updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidator)) || + updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidatorPlusDiff)) + ).to.equal(true) expect( - updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidator)) - || updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidatorPlusDiff))).to.equal(true) + updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidator)) || + updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidatorPlusDiff)) + ).to.equal(true) expect( - updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidator)) - || updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidatorPlusDiff))).to.equal(true) + updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidator)) || + updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidatorPlusDiff)) + ).to.equal(true) const blockRewardBalance = toBN(await web3.eth.getBalance(blockRewardContract.address)) blockRewardBalance.should.be.bignumber.equal(ZERO) @@ -1107,19 +1653,32 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const rewards = [accounts[5], accounts[6], accounts[7], accounts[8], accounts[9]] const requiredSignatures = 5 const rewardableValidators = await RewardableValidators.new() - const homeBridgeImpl = await HomeBridge.new(); - const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + const homeBridgeImpl = await HomeBridge.new() + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled - const homeBridge = await HomeBridge.at(storageProxy.address); - await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled - await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + const homeBridge = await HomeBridge.at(storageProxy.address) + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, { + from: owner + }).should.be.fulfilled + await homeBridge.initialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ).should.be.fulfilled await blockRewardContract.sendTransaction({ from: accounts[0], value: oneEther }).should.be.fulfilled // Given - const value = halfEther; + const value = halfEther // 0.1% fee const fee = 0.001 const feeInWei = ether(fee.toString()) @@ -1130,7 +1689,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setForeignFee(feeInWei, { from: owner }).should.be.fulfilled - const recipient = "0xf4BEF13F9f4f2B203FAF0C3cBbaAbe1afE056955"; + const recipient = '0xf4BEF13F9f4f2B203FAF0C3cBbaAbe1afE056955' const balanceBefore = toBN(await web3.eth.getBalance(recipient)) const initialBalanceRewardAddress1 = toBN(await web3.eth.getBalance(rewards[0])) @@ -1139,15 +1698,24 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const initialBalanceRewardAddress4 = toBN(await web3.eth.getBalance(rewards[3])) const initialBalanceRewardAddress5 = toBN(await web3.eth.getBalance(rewards[4])) - - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' // When - const { logs: logsValidator1 } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled - await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[1]}).should.be.fulfilled - await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[2]}).should.be.fulfilled - await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[3]}).should.be.fulfilled - const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[4]}).should.be.fulfilled + const { logs: logsValidator1 } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[0] + }).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[1] + }).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[2] + }).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[3] + }).should.be.fulfilled + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[4] + }).should.be.fulfilled // Then logsValidator1.length.should.be.equals(1) @@ -1182,20 +1750,32 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { updatedBalanceRewardAddress5.should.be.bignumber.equal(initialBalanceRewardAddress5.add(feePerValidator)) }) }) - describe('#feeManager_fallback', function () { - let homeBridge, rewardableValidators - let owner = accounts[9] - let validators = [accounts[1]] - let rewards = [accounts[2]] - let requiredSignatures = 1 + describe('#feeManager_fallback', async () => { + let homeBridge + let rewardableValidators + const owner = accounts[9] + const validators = [accounts[1]] + const rewards = [accounts[2]] + const requiredSignatures = 1 beforeEach(async () => { rewardableValidators = await RewardableValidators.new() await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled - const homeBridgeImpl = await HomeBridge.new(); - const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + const homeBridgeImpl = await HomeBridge.new() + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled - homeBridge = await HomeBridge.at(storageProxy.address); - await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + homeBridge = await HomeBridge.at(storageProxy.address) + await homeBridge.initialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ).should.be.fulfilled await blockRewardContract.addMintedTotallyByBridge(oneEther, homeBridge.address) }) @@ -1203,7 +1783,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { // Given // 0.1% fee const value = halfEther - const recipient = accounts[8]; + const recipient = accounts[8] const fee = 0.001 const feeInWei = ether(fee.toString()) const valueCalc = 0.5 * (1 - fee) @@ -1216,7 +1796,10 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const { logs } = await homeBridge.sendTransaction({ from: recipient, value }).should.be.fulfilled // Then - expectEventInLogs(logs, 'UserRequestForSignature', { recipient: recipient, value: finalValue }) + expectEventInLogs(logs, 'UserRequestForSignature', { + recipient, + value: finalValue + }) const currentDay = await homeBridge.getCurrentDay() value.should.be.bignumber.equal(await homeBridge.totalSpentPerDay(currentDay)) finalValue.should.be.bignumber.equal(await homeBridge.totalBurntCoins()) @@ -1232,12 +1815,25 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const rewards = [accounts[2]] const requiredSignatures = 1 const rewardableValidators = await RewardableValidators.new() - const homeBridgeImpl = await HomeBridge.new(); - const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + const homeBridgeImpl = await HomeBridge.new() + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled - const homeBridge = await HomeBridge.at(storageProxy.address); - await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled - await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + const homeBridge = await HomeBridge.at(storageProxy.address) + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, { + from: owner + }).should.be.fulfilled + await homeBridge.initialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ).should.be.fulfilled await blockRewardContract.addMintedTotallyByBridge(oneEther, homeBridge.address) // Given @@ -1248,14 +1844,14 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setHomeFee(feeInWei, { from: owner }).should.be.fulfilled - const recipient = accounts[5]; + const recipient = accounts[5] const initialValue = halfEther const valueCalc = 0.5 * (1 - fee) const value = ether(valueCalc.toString()) const feeAmountCalc = 0.5 * fee const feeAmount = ether(feeAmountCalc.toString()) const rewardAddressBalanceBefore = toBN(await web3.eth.getBalance(rewards[0])) - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' const initialBridgeBalance = await web3.eth.getBalance(homeBridge.address) expect(toBN(initialBridgeBalance)).to.be.bignumber.equal(ZERO) @@ -1266,11 +1862,11 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const afterTransferBridgeBalance = toBN(await web3.eth.getBalance(homeBridge.address)) afterTransferBridgeBalance.should.be.bignumber.equal(feeAmount) - const message = createMessage(recipient, value, transactionHash, homeBridge.address); + const message = createMessage(recipient, value, transactionHash, homeBridge.address) const signature = await sign(validators[0], message) - const { logs } = await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled; + const { logs } = await homeBridge.submitSignature(signature, message, { from: validators[0] }).should.be.fulfilled // Then logs.length.should.be.equal(3) @@ -1290,12 +1886,25 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const rewards = [accounts[4], accounts[5], accounts[6]] const requiredSignatures = 3 const rewardableValidators = await RewardableValidators.new() - const homeBridgeImpl = await HomeBridge.new(); - const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + const homeBridgeImpl = await HomeBridge.new() + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled - const homeBridge = await HomeBridge.at(storageProxy.address); - await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled - await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + const homeBridge = await HomeBridge.at(storageProxy.address) + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, { + from: owner + }).should.be.fulfilled + await homeBridge.initialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ).should.be.fulfilled await blockRewardContract.addMintedTotallyByBridge(oneEther, homeBridge.address) // Given @@ -1308,13 +1917,13 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setHomeFee(feeInWei, { from: owner }).should.be.fulfilled - const recipient = accounts[7]; + const recipient = accounts[7] const initialValue = halfEther const valueCalc = 0.5 * (1 - fee) const value = ether(valueCalc.toString()) const feeAmountCalc = 0.5 * fee const feeAmount = ether(feeAmountCalc.toString()) - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' const initialBridgeBalance = toBN(await web3.eth.getBalance(homeBridge.address)) initialBridgeBalance.should.be.bignumber.equal(ZERO) @@ -1329,15 +1938,17 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const afterTransferBridgeBalance = toBN(await web3.eth.getBalance(homeBridge.address)) afterTransferBridgeBalance.should.be.bignumber.equal(feeAmount) - const message = createMessage(recipient, value, transactionHash, homeBridge.address); + const message = createMessage(recipient, value, transactionHash, homeBridge.address) const signature = await sign(validators[0], message) const signature2 = await sign(validators[1], message) const signature3 = await sign(validators[2], message) - await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled; - await homeBridge.submitSignature(signature2, message, {from: validators[1]}).should.be.fulfilled; - const { logs } = await homeBridge.submitSignature(signature3, message, {from: validators[2]}).should.be.fulfilled; + await homeBridge.submitSignature(signature, message, { from: validators[0] }).should.be.fulfilled + await homeBridge.submitSignature(signature2, message, { from: validators[1] }).should.be.fulfilled + const { logs } = await homeBridge.submitSignature(signature3, message, { + from: validators[2] + }).should.be.fulfilled // Then logs.length.should.be.equal(3) @@ -1352,14 +1963,17 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { bridgeBalance.should.be.bignumber.equal(ZERO) expect( - updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidator)) - || updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidatorPlusDiff))).to.equal(true) + updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidator)) || + updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidatorPlusDiff)) + ).to.equal(true) expect( - updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidator)) - || updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidatorPlusDiff))).to.equal(true) + updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidator)) || + updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidatorPlusDiff)) + ).to.equal(true) expect( - updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidator)) - || updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidatorPlusDiff))).to.equal(true) + updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidator)) || + updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidatorPlusDiff)) + ).to.equal(true) }) it('should distribute fee to 5 validators', async () => { // Initialize @@ -1368,12 +1982,25 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const rewards = [accounts[5], accounts[6], accounts[7], accounts[8], accounts[9]] const requiredSignatures = 5 const rewardableValidators = await RewardableValidators.new() - const homeBridgeImpl = await HomeBridge.new(); - const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + const homeBridgeImpl = await HomeBridge.new() + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled - const homeBridge = await HomeBridge.at(storageProxy.address); - await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled - await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + const homeBridge = await HomeBridge.at(storageProxy.address) + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, { + from: owner + }).should.be.fulfilled + await homeBridge.initialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ).should.be.fulfilled await blockRewardContract.addMintedTotallyByBridge(oneEther, homeBridge.address) // Given @@ -1384,14 +2011,14 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setHomeFee(feeInWei, { from: owner }).should.be.fulfilled - const recipient = accounts[0]; + const recipient = accounts[0] const initialValue = halfEther const valueCalc = 0.5 * (1 - fee) const value = ether(valueCalc.toString()) const feeAmountCalc = 0.5 * fee const feeAmount = ether(feeAmountCalc.toString()) const feePerValidator = feeAmount.div(toBN(5)) - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' const initialBridgeBalance = toBN(await web3.eth.getBalance(homeBridge.address)) initialBridgeBalance.should.be.bignumber.equal(ZERO) @@ -1408,7 +2035,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const afterTransferBridgeBalance = toBN(await web3.eth.getBalance(homeBridge.address)) afterTransferBridgeBalance.should.be.bignumber.equal(feeAmount) - const message = createMessage(recipient, value, transactionHash, homeBridge.address); + const message = createMessage(recipient, value, transactionHash, homeBridge.address) const signature = await sign(validators[0], message) const signature2 = await sign(validators[1], message) @@ -1416,11 +2043,13 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const signature4 = await sign(validators[3], message) const signature5 = await sign(validators[4], message) - await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled; - await homeBridge.submitSignature(signature2, message, {from: validators[1]}).should.be.fulfilled; - await homeBridge.submitSignature(signature3, message, {from: validators[2]}).should.be.fulfilled; - await homeBridge.submitSignature(signature4, message, {from: validators[3]}).should.be.fulfilled; - const { logs } = await homeBridge.submitSignature(signature5, message, {from: validators[4]}).should.be.fulfilled; + await homeBridge.submitSignature(signature, message, { from: validators[0] }).should.be.fulfilled + await homeBridge.submitSignature(signature2, message, { from: validators[1] }).should.be.fulfilled + await homeBridge.submitSignature(signature3, message, { from: validators[2] }).should.be.fulfilled + await homeBridge.submitSignature(signature4, message, { from: validators[3] }).should.be.fulfilled + const { logs } = await homeBridge.submitSignature(signature5, message, { + from: validators[4] + }).should.be.fulfilled // Then logs.length.should.be.equal(3) @@ -1450,11 +2079,11 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { await feeManager.setHomeFee(0).should.be.fulfilled // When - const result = await feeManager.random(3); + const result = await feeManager.random(3) // Then - expect(result).to.be.bignumber.gte(ZERO); - expect(result).to.be.bignumber.lt('3'); + expect(result).to.be.bignumber.gte(ZERO) + expect(result).to.be.bignumber.lt('3') } }) }) @@ -1466,14 +2095,27 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const rewards = [accounts[2]] const requiredSignatures = 1 const rewardableValidators = await RewardableValidators.new() - const homeBridgeImpl = await HomeBridge.new(); - const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + const homeBridgeImpl = await HomeBridge.new() + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled - const homeBridge = await HomeBridge.at(storageProxy.address); - await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + const homeBridge = await HomeBridge.at(storageProxy.address) + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, { + from: owner + }).should.be.fulfilled await blockRewardContract.setValidatorsRewards(rewards) - await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + await homeBridge.initialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ).should.be.fulfilled await blockRewardContract.sendTransaction({ from: accounts[2], value: oneEther @@ -1487,18 +2129,20 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setForeignFee(feeInWei, { from: owner }).should.be.fulfilled - const recipient = accounts[5]; - const value = halfEther; + const recipient = accounts[5] + const value = halfEther const feeAmountCalc = 0.5 * fee const feeAmount = ether(feeAmountCalc.toString()) const valueCalc = 0.5 * (1 - fee) const finalValue = ether(valueCalc.toString()) const balanceBefore = await web3.eth.getBalance(recipient) const rewardAddressBalanceBefore = await web3.eth.getBalance(rewards[0]) - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' // When - const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[0] + }).should.be.fulfilled // Then expectEventInLogs(logs, 'SignedForAffirmation', { @@ -1530,14 +2174,27 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const rewards = [accounts[4], accounts[5], accounts[6]] const requiredSignatures = 2 const rewardableValidators = await RewardableValidators.new() - const homeBridgeImpl = await HomeBridge.new(); + const homeBridgeImpl = await HomeBridge.new() const blockRewardContract = await BlockReward.new() - const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled - const homeBridge = await HomeBridge.at(storageProxy.address); - await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + const homeBridge = await HomeBridge.at(storageProxy.address) + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, { + from: owner + }).should.be.fulfilled await blockRewardContract.setValidatorsRewards(rewards) - await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + await homeBridge.initialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ).should.be.fulfilled await blockRewardContract.sendTransaction({ from: accounts[0], value: halfEther @@ -1547,7 +2204,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const initialBlockRewardBalance = await web3.eth.getBalance(blockRewardContract.address) expect(toBN(initialBlockRewardBalance)).to.be.bignumber.equal(halfEther) - const value = halfEther; + const value = halfEther // 0.1% fee const fee = 0.001 const feeInWei = ether(fee.toString()) @@ -1562,19 +2219,22 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setForeignFee(feeInWei, { from: owner }).should.be.fulfilled - const recipient = accounts[8]; + const recipient = accounts[8] const balanceBefore = await web3.eth.getBalance(recipient) const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) const initialBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) const initialBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) - - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' // When - const { logs: logsValidator1 } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled - const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[1]}).should.be.fulfilled + const { logs: logsValidator1 } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[0] + }).should.be.fulfilled + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[1] + }).should.be.fulfilled // Then logsValidator1.length.should.be.equals(1) @@ -1601,14 +2261,17 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) expect( - toBN(updatedBalanceRewardAddress1).eq(toBN(initialBalanceRewardAddress1).add(feePerValidator)) - || toBN(updatedBalanceRewardAddress1).eq(toBN(initialBalanceRewardAddress1).add(feePerValidatorPlusDiff))).to.equal(true) + toBN(updatedBalanceRewardAddress1).eq(toBN(initialBalanceRewardAddress1).add(feePerValidator)) || + toBN(updatedBalanceRewardAddress1).eq(toBN(initialBalanceRewardAddress1).add(feePerValidatorPlusDiff)) + ).to.equal(true) expect( - toBN(updatedBalanceRewardAddress2).eq(toBN(initialBalanceRewardAddress2).add(feePerValidator)) - || toBN(updatedBalanceRewardAddress2).eq(toBN(initialBalanceRewardAddress2).add(feePerValidatorPlusDiff))).to.equal(true) + toBN(updatedBalanceRewardAddress2).eq(toBN(initialBalanceRewardAddress2).add(feePerValidator)) || + toBN(updatedBalanceRewardAddress2).eq(toBN(initialBalanceRewardAddress2).add(feePerValidatorPlusDiff)) + ).to.equal(true) expect( - toBN(updatedBalanceRewardAddress3).eq(toBN(initialBalanceRewardAddress3).add(feePerValidator)) - || toBN(updatedBalanceRewardAddress3).eq(toBN(initialBalanceRewardAddress3).add(feePerValidatorPlusDiff))).to.equal(true) + toBN(updatedBalanceRewardAddress3).eq(toBN(initialBalanceRewardAddress3).add(feePerValidator)) || + toBN(updatedBalanceRewardAddress3).eq(toBN(initialBalanceRewardAddress3).add(feePerValidatorPlusDiff)) + ).to.equal(true) const feeAmountBlockReward = await blockRewardContract.feeAmount() expect(toBN(feeAmountBlockReward)).to.be.bignumber.equal(feeAmount) @@ -1623,20 +2286,33 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const rewards = [accounts[5], accounts[6], accounts[7], accounts[8], accounts[9]] const requiredSignatures = 5 const rewardableValidators = await RewardableValidators.new() - const homeBridgeImpl = await HomeBridge.new(); - const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + const homeBridgeImpl = await HomeBridge.new() + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled - const homeBridge = await HomeBridge.at(storageProxy.address); - await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + const homeBridge = await HomeBridge.at(storageProxy.address) + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, { + from: owner + }).should.be.fulfilled await blockRewardContract.setValidatorsRewards(rewards) - await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + await homeBridge.initialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ).should.be.fulfilled await blockRewardContract.sendTransaction({ from: accounts[0], value: oneEther }).should.be.fulfilled // Given - const value = halfEther; + const value = halfEther // 0.1% fee const fee = 0.001 const feeInWei = ether(fee.toString()) @@ -1647,7 +2323,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setForeignFee(feeInWei, { from: owner }).should.be.fulfilled - const recipient = "0xf4BEF13F9f4f2B203FAF0C3cBbaAbe1afE056955"; + const recipient = '0xf4BEF13F9f4f2B203FAF0C3cBbaAbe1afE056955' const balanceBefore = await web3.eth.getBalance(recipient) const initialBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) @@ -1656,15 +2332,24 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const initialBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) const initialBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) - - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' // When - const { logs: logsValidator1 } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled - await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[1]}).should.be.fulfilled - await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[2]}).should.be.fulfilled - await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[3]}).should.be.fulfilled - const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[4]}).should.be.fulfilled + const { logs: logsValidator1 } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[0] + }).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[1] + }).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[2] + }).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[3] + }).should.be.fulfilled + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[4] + }).should.be.fulfilled // Then logsValidator1.length.should.be.equals(1) @@ -1692,30 +2377,52 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const updatedBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) const updatedBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) - expect(toBN(updatedBalanceRewardAddress1)).to.be.bignumber.equal(toBN(initialBalanceRewardAddress1).add(feePerValidator)) - expect(toBN(updatedBalanceRewardAddress2)).to.be.bignumber.equal(toBN(initialBalanceRewardAddress2).add(feePerValidator)) - expect(toBN(updatedBalanceRewardAddress3)).to.be.bignumber.equal(toBN(initialBalanceRewardAddress3).add(feePerValidator)) - expect(toBN(updatedBalanceRewardAddress4)).to.be.bignumber.equal(toBN(initialBalanceRewardAddress4).add(feePerValidator)) - expect(toBN(updatedBalanceRewardAddress5)).to.be.bignumber.equal(toBN(initialBalanceRewardAddress5).add(feePerValidator)) + expect(toBN(updatedBalanceRewardAddress1)).to.be.bignumber.equal( + toBN(initialBalanceRewardAddress1).add(feePerValidator) + ) + expect(toBN(updatedBalanceRewardAddress2)).to.be.bignumber.equal( + toBN(initialBalanceRewardAddress2).add(feePerValidator) + ) + expect(toBN(updatedBalanceRewardAddress3)).to.be.bignumber.equal( + toBN(initialBalanceRewardAddress3).add(feePerValidator) + ) + expect(toBN(updatedBalanceRewardAddress4)).to.be.bignumber.equal( + toBN(initialBalanceRewardAddress4).add(feePerValidator) + ) + expect(toBN(updatedBalanceRewardAddress5)).to.be.bignumber.equal( + toBN(initialBalanceRewardAddress5).add(feePerValidator) + ) const feeAmountBlockReward = await blockRewardContract.feeAmount() expect(toBN(feeAmountBlockReward)).to.be.bignumber.equal(feeAmount) }) }) - describe('#feeManager_fallback_POSDAO', function () { - let homeBridge, rewardableValidators - let owner = accounts[9] - let validators = [accounts[1]] - let rewards = [accounts[2]] - let requiredSignatures = 1 + describe('#feeManager_fallback_POSDAO', async () => { + let homeBridge + let rewardableValidators + const owner = accounts[9] + const validators = [accounts[1]] + const rewards = [accounts[2]] + const requiredSignatures = 1 beforeEach(async () => { rewardableValidators = await RewardableValidators.new() await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled - const homeBridgeImpl = await HomeBridge.new(); - const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + const homeBridgeImpl = await HomeBridge.new() + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled - homeBridge = await HomeBridge.at(storageProxy.address); - await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + homeBridge = await HomeBridge.at(storageProxy.address) + await homeBridge.initialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ).should.be.fulfilled await blockRewardContract.addMintedTotallyByBridge(oneEther, homeBridge.address) }) @@ -1723,7 +2430,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { // Given // 0.1% fee const value = halfEther - const recipient = accounts[8]; + const recipient = accounts[8] const fee = 0.001 const feeInWei = ether(fee.toString()) const feeManager = await FeeManagerErcToNativePOSDAO.new() @@ -1736,7 +2443,10 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { // Then const valueCalc = 0.5 * (1 - fee) const finalValue = ether(valueCalc.toString()) - expectEventInLogs(logs, 'UserRequestForSignature', { recipient: recipient, value: finalValue }) + expectEventInLogs(logs, 'UserRequestForSignature', { + recipient, + value: finalValue + }) const currentDay = await homeBridge.getCurrentDay() value.should.be.bignumber.equal(await homeBridge.totalSpentPerDay(currentDay)) value.should.be.bignumber.equal(await homeBridge.totalBurntCoins()) @@ -1752,13 +2462,26 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const rewards = [accounts[2]] const requiredSignatures = 1 const rewardableValidators = await RewardableValidators.new() - const homeBridgeImpl = await HomeBridge.new(); - const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + const homeBridgeImpl = await HomeBridge.new() + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled - const homeBridge = await HomeBridge.at(storageProxy.address); - await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + const homeBridge = await HomeBridge.at(storageProxy.address) + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, { + from: owner + }).should.be.fulfilled await blockRewardContract.setValidatorsRewards(rewards) - await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + await homeBridge.initialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ).should.be.fulfilled await blockRewardContract.addMintedTotallyByBridge(oneEther, homeBridge.address) // Given @@ -1769,14 +2492,14 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setHomeFee(feeInWei, { from: owner }).should.be.fulfilled - const recipient = accounts[5]; + const recipient = accounts[5] const initialValue = halfEther const valueCalc = 0.5 * (1 - fee) const value = ether(valueCalc.toString()) const feeAmountCalc = 0.5 * fee const feeAmount = ether(feeAmountCalc.toString()) const rewardAddressBalanceBefore = await web3.eth.getBalance(rewards[0]) - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' const initialBridgeBalance = await web3.eth.getBalance(homeBridge.address) expect(toBN(initialBridgeBalance)).to.be.bignumber.equal(ZERO) @@ -1787,11 +2510,11 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const afterTransferBridgeBalance = await web3.eth.getBalance(homeBridge.address) expect(toBN(afterTransferBridgeBalance)).to.be.bignumber.equal(ZERO) - const message = createMessage(recipient, value, transactionHash, homeBridge.address); + const message = createMessage(recipient, value, transactionHash, homeBridge.address) const signature = await sign(validators[0], message) - const { logs } = await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled; + const { logs } = await homeBridge.submitSignature(signature, message, { from: validators[0] }).should.be.fulfilled // Then logs.length.should.be.equal(3) @@ -1817,13 +2540,26 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const rewards = [accounts[4], accounts[5], accounts[6]] const requiredSignatures = 3 const rewardableValidators = await RewardableValidators.new() - const homeBridgeImpl = await HomeBridge.new(); - const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + const homeBridgeImpl = await HomeBridge.new() + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled - const homeBridge = await HomeBridge.at(storageProxy.address); - await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + const homeBridge = await HomeBridge.at(storageProxy.address) + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, { + from: owner + }).should.be.fulfilled await blockRewardContract.setValidatorsRewards(rewards) - await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + await homeBridge.initialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ).should.be.fulfilled await blockRewardContract.addMintedTotallyByBridge(oneEther, homeBridge.address) // Given @@ -1836,13 +2572,13 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setHomeFee(feeInWei, { from: owner }).should.be.fulfilled - const recipient = accounts[7]; + const recipient = accounts[7] const initialValue = halfEther const valueCalc = 0.5 * (1 - fee) const value = ether(valueCalc.toString()) const feeAmountCalc = 0.5 * fee const feeAmount = ether(feeAmountCalc.toString()) - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' const initialBridgeBalance = await web3.eth.getBalance(homeBridge.address) expect(toBN(initialBridgeBalance)).to.be.bignumber.equal(ZERO) @@ -1857,15 +2593,17 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const afterTransferBridgeBalance = await web3.eth.getBalance(homeBridge.address) expect(toBN(afterTransferBridgeBalance)).to.be.bignumber.equal(ZERO) - const message = createMessage(recipient, value, transactionHash, homeBridge.address); + const message = createMessage(recipient, value, transactionHash, homeBridge.address) const signature = await sign(validators[0], message) const signature2 = await sign(validators[1], message) const signature3 = await sign(validators[2], message) - await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled; - await homeBridge.submitSignature(signature2, message, {from: validators[1]}).should.be.fulfilled; - const { logs } = await homeBridge.submitSignature(signature3, message, {from: validators[2]}).should.be.fulfilled; + await homeBridge.submitSignature(signature, message, { from: validators[0] }).should.be.fulfilled + await homeBridge.submitSignature(signature2, message, { from: validators[1] }).should.be.fulfilled + const { logs } = await homeBridge.submitSignature(signature3, message, { + from: validators[2] + }).should.be.fulfilled // Then logs.length.should.be.equal(3) @@ -1883,14 +2621,17 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { expect(toBN(bridgeBalance)).to.be.bignumber.equal(ZERO) expect( - toBN(updatedBalanceRewardAddress1).eq(toBN(initialBalanceRewardAddress1).add(feePerValidator)) - || toBN(updatedBalanceRewardAddress1).eq(toBN(initialBalanceRewardAddress1).add(feePerValidatorPlusDiff))).to.equal(true) + toBN(updatedBalanceRewardAddress1).eq(toBN(initialBalanceRewardAddress1).add(feePerValidator)) || + toBN(updatedBalanceRewardAddress1).eq(toBN(initialBalanceRewardAddress1).add(feePerValidatorPlusDiff)) + ).to.equal(true) expect( - toBN(updatedBalanceRewardAddress2).eq(toBN(initialBalanceRewardAddress2).add(feePerValidator)) - || toBN(updatedBalanceRewardAddress2).eq(toBN(initialBalanceRewardAddress2).add(feePerValidatorPlusDiff))).to.equal(true) + toBN(updatedBalanceRewardAddress2).eq(toBN(initialBalanceRewardAddress2).add(feePerValidator)) || + toBN(updatedBalanceRewardAddress2).eq(toBN(initialBalanceRewardAddress2).add(feePerValidatorPlusDiff)) + ).to.equal(true) expect( - toBN(updatedBalanceRewardAddress3).eq(toBN(initialBalanceRewardAddress3).add(feePerValidator)) - || toBN(updatedBalanceRewardAddress3).eq(toBN(initialBalanceRewardAddress3).add(feePerValidatorPlusDiff))).to.equal(true) + toBN(updatedBalanceRewardAddress3).eq(toBN(initialBalanceRewardAddress3).add(feePerValidator)) || + toBN(updatedBalanceRewardAddress3).eq(toBN(initialBalanceRewardAddress3).add(feePerValidatorPlusDiff)) + ).to.equal(true) const feeAmountBlockReward = await blockRewardContract.feeAmount() expect(toBN(feeAmountBlockReward)).to.be.bignumber.equal(feeAmount) @@ -1902,13 +2643,26 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const rewards = [accounts[5], accounts[6], accounts[7], accounts[8], accounts[9]] const requiredSignatures = 5 const rewardableValidators = await RewardableValidators.new() - const homeBridgeImpl = await HomeBridge.new(); - const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + const homeBridgeImpl = await HomeBridge.new() + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled await storageProxy.upgradeTo('1', homeBridgeImpl.address).should.be.fulfilled - const homeBridge = await HomeBridge.at(storageProxy.address); - await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + const homeBridge = await HomeBridge.at(storageProxy.address) + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, { + from: owner + }).should.be.fulfilled await blockRewardContract.setValidatorsRewards(rewards) - await homeBridge.initialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, blockRewardContract.address, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled + await homeBridge.initialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + blockRewardContract.address, + foreignDailyLimit, + foreignMaxPerTx, + owner + ).should.be.fulfilled await blockRewardContract.addMintedTotallyByBridge(oneEther, homeBridge.address) // Given @@ -1919,14 +2673,14 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { await homeBridge.setFeeManagerContract(feeManager.address, { from: owner }).should.be.fulfilled await homeBridge.setHomeFee(feeInWei, { from: owner }).should.be.fulfilled - const recipient = accounts[0]; + const recipient = accounts[0] const initialValue = halfEther const valueCalc = 0.5 * (1 - fee) const value = ether(valueCalc.toString()) const feeAmountCalc = 0.5 * fee const feeAmount = ether(feeAmountCalc.toString()) const feePerValidator = feeAmount.div(toBN(5)) - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' const initialBridgeBalance = await web3.eth.getBalance(homeBridge.address) expect(toBN(initialBridgeBalance)).to.be.bignumber.equal(ZERO) @@ -1943,7 +2697,7 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const afterTransferBridgeBalance = await web3.eth.getBalance(homeBridge.address) expect(toBN(afterTransferBridgeBalance)).to.be.bignumber.equal(ZERO) - const message = createMessage(recipient, value, transactionHash, homeBridge.address); + const message = createMessage(recipient, value, transactionHash, homeBridge.address) const signature = await sign(validators[0], message) const signature2 = await sign(validators[1], message) @@ -1951,11 +2705,13 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { const signature4 = await sign(validators[3], message) const signature5 = await sign(validators[4], message) - await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled; - await homeBridge.submitSignature(signature2, message, {from: validators[1]}).should.be.fulfilled; - await homeBridge.submitSignature(signature3, message, {from: validators[2]}).should.be.fulfilled; - await homeBridge.submitSignature(signature4, message, {from: validators[3]}).should.be.fulfilled; - const { logs } = await homeBridge.submitSignature(signature5, message, {from: validators[4]}).should.be.fulfilled; + await homeBridge.submitSignature(signature, message, { from: validators[0] }).should.be.fulfilled + await homeBridge.submitSignature(signature2, message, { from: validators[1] }).should.be.fulfilled + await homeBridge.submitSignature(signature3, message, { from: validators[2] }).should.be.fulfilled + await homeBridge.submitSignature(signature4, message, { from: validators[3] }).should.be.fulfilled + const { logs } = await homeBridge.submitSignature(signature5, message, { + from: validators[4] + }).should.be.fulfilled // Then logs.length.should.be.equal(3) @@ -1965,18 +2721,27 @@ contract('HomeBridge_ERC20_to_Native', async (accounts) => { transactionHash }) - const updatedBalanceRewardAddress1 = await web3.eth.getBalance(rewards[0]) const updatedBalanceRewardAddress2 = await web3.eth.getBalance(rewards[1]) const updatedBalanceRewardAddress3 = await web3.eth.getBalance(rewards[2]) const updatedBalanceRewardAddress4 = await web3.eth.getBalance(rewards[3]) const updatedBalanceRewardAddress5 = await web3.eth.getBalance(rewards[4]) - expect(toBN(updatedBalanceRewardAddress1)).to.be.bignumber.equal(toBN(initialBalanceRewardAddress1).add(feePerValidator)) - expect(toBN(updatedBalanceRewardAddress2)).to.be.bignumber.equal(toBN(initialBalanceRewardAddress2).add(feePerValidator)) - expect(toBN(updatedBalanceRewardAddress3)).to.be.bignumber.equal(toBN(initialBalanceRewardAddress3).add(feePerValidator)) - expect(toBN(updatedBalanceRewardAddress4)).to.be.bignumber.equal(toBN(initialBalanceRewardAddress4).add(feePerValidator)) - expect(toBN(updatedBalanceRewardAddress5)).to.be.bignumber.equal(toBN(initialBalanceRewardAddress5).add(feePerValidator)) + expect(toBN(updatedBalanceRewardAddress1)).to.be.bignumber.equal( + toBN(initialBalanceRewardAddress1).add(feePerValidator) + ) + expect(toBN(updatedBalanceRewardAddress2)).to.be.bignumber.equal( + toBN(initialBalanceRewardAddress2).add(feePerValidator) + ) + expect(toBN(updatedBalanceRewardAddress3)).to.be.bignumber.equal( + toBN(initialBalanceRewardAddress3).add(feePerValidator) + ) + expect(toBN(updatedBalanceRewardAddress4)).to.be.bignumber.equal( + toBN(initialBalanceRewardAddress4).add(feePerValidator) + ) + expect(toBN(updatedBalanceRewardAddress5)).to.be.bignumber.equal( + toBN(initialBalanceRewardAddress5).add(feePerValidator) + ) const feeAmountBlockReward = await blockRewardContract.feeAmount() feeAmountBlockReward.should.be.bignumber.equal(feeAmount) diff --git a/test/helpers/helpers.js b/test/helpers/helpers.js index 155e2b5e2..41e10bfcb 100644 --- a/test/helpers/helpers.js +++ b/test/helpers/helpers.js @@ -1,164 +1,164 @@ -const { BN } = require('../setup'); -const { expect } = require('chai'); +const { expect } = require('chai') +const { BN } = require('../setup') // returns a Promise that resolves with a hex string that is the signature of // `data` signed with the key of `address` function sign(address, data) { - return new Promise(function(resolve, reject) { - web3.eth.sign(data, address, function(err, result) { + return new Promise((resolve, reject) => { + web3.eth.sign(data, address, (err, result) => { if (err !== null) { - return reject(err); - } else { - return resolve(normalizeSignature(result)); - //return resolve(result); + return reject(err) } + return resolve(normalizeSignature(result)) + // return resolve(result); }) }) } -module.exports.sign = sign; +module.exports.sign = sign // geth && testrpc has different output of eth_sign than parity // https://github.com/ethereumjs/testrpc/issues/243#issuecomment-326750236 -function normalizeSignature(signature) { - signature = strip0x(signature); +function normalizeSignature(rawSignature) { + const signature = strip0x(rawSignature) // increase v by 27... - return "0x" + signature.substr(0, 128) + (parseInt(signature.substr(128), 16) + 27).toString(16); + return `0x${signature.substr(0, 128)}${(parseInt(signature.substr(128), 16) + 27).toString(16)}` } -module.exports.normalizeSignature = normalizeSignature; +module.exports.normalizeSignature = normalizeSignature // strips leading "0x" if present function strip0x(input) { - return input.replace(/^0x/, ""); + return input.replace(/^0x/, '') } -module.exports.strip0x = strip0x; +module.exports.strip0x = strip0x // extracts and returns the `v`, `r` and `s` values from a `signature`. // all inputs and outputs are hex strings with leading '0x'. -function signatureToVRS(signature) { - assert.equal(signature.length, 2 + 32 * 2 + 32 * 2 + 2); - signature = strip0x(signature); - var v = parseInt(signature.substr(64 * 2), 16); - var r = "0x" + signature.substr(0, 32 * 2); - var s = "0x" + signature.substr(32 * 2, 32 * 2); - return {v: v, r: r, s: s}; +function signatureToVRS(rawSignature) { + assert.equal(rawSignature.length, 2 + 32 * 2 + 32 * 2 + 2) + const signature = strip0x(rawSignature) + const v = parseInt(signature.substr(64 * 2), 16) + const r = `0x${signature.substr(0, 32 * 2)}` + const s = `0x${signature.substr(32 * 2, 32 * 2)}` + return { v, r, s } } -module.exports.signatureToVRS = signatureToVRS; +module.exports.signatureToVRS = signatureToVRS // returns BigNumber `num` converted to a little endian hex string // that is exactly 32 bytes long. // `num` must represent an unsigned integer function bigNumberToPaddedBytes32(num) { - var result = strip0x(num.toString(16)); + let result = strip0x(num.toString(16)) while (result.length < 64) { - result = "0" + result; + result = `0${result}` } - return "0x" + result; + return `0x${result}` } -module.exports.bigNumberToPaddedBytes32 = bigNumberToPaddedBytes32; +module.exports.bigNumberToPaddedBytes32 = bigNumberToPaddedBytes32 // returns an promise that resolves to an object // that maps `addresses` to their current balances function getBalances(addresses) { - return Promise.all(addresses.map(function(address) { - return web3.eth.getBalance(address); - })).then(function(balancesArray) { - let addressToBalance = {}; - addresses.forEach(function(address, index) { - addressToBalance[address] = balancesArray[index]; - }); - return addressToBalance; + return Promise.all( + addresses.map(address => { + return web3.eth.getBalance(address) + }) + ).then(balancesArray => { + const addressToBalance = {} + addresses.forEach((address, index) => { + addressToBalance[address] = balancesArray[index] + }) + return addressToBalance }) } -module.exports.getBalances = getBalances; - +module.exports.getBalances = getBalances // returns hex string of the bytes of the message // composed from `recipient`, `value` and `transactionHash` // that is relayed from `foreign` to `home` on withdraw -function createMessage(recipient, value, transactionHash, contractAddress) { - recipient = strip0x(recipient); - assert.equal(recipient.length, 20 * 2); +function createMessage(rawRecipient, rawValue, rawTransactionHash, rawContractAddress) { + const recipient = strip0x(rawRecipient) + assert.equal(recipient.length, 20 * 2) - var value = strip0x(bigNumberToPaddedBytes32(value)); - assert.equal(value.length, 64); + const value = strip0x(bigNumberToPaddedBytes32(rawValue)) + assert.equal(value.length, 64) - transactionHash = strip0x(transactionHash); - assert.equal(transactionHash.length, 32 * 2); + const transactionHash = strip0x(rawTransactionHash) + assert.equal(transactionHash.length, 32 * 2) - contractAddress = strip0x(contractAddress); - assert.equal(contractAddress.length, 20 * 2); + const contractAddress = strip0x(rawContractAddress) + assert.equal(contractAddress.length, 20 * 2) - var message = "0x" + recipient + value + transactionHash + contractAddress; - var expectedMessageLength = (20 + 32 + 32 + 20) * 2 + 2; - assert.equal(message.length, expectedMessageLength); - return message; + const message = `0x${recipient}${value}${transactionHash}${contractAddress}` + const expectedMessageLength = (20 + 32 + 32 + 20) * 2 + 2 + assert.equal(message.length, expectedMessageLength) + return message } -module.exports.createMessage = createMessage; +module.exports.createMessage = createMessage // returns array of integers progressing from `start` up to, but not including, `end` function range(start, end) { - var result = []; - for (var i = start; i < end; i++) { - result.push(i); + const result = [] + for (let i = start; i < end; i++) { + result.push(i) } - return result; + return result } -module.exports.range = range; +module.exports.range = range // just used to signal/document that we're explicitely ignoring/expecting an error -function ignoreExpectedError() { -} -module.exports.ignoreExpectedError = ignoreExpectedError; +function ignoreExpectedError() {} +module.exports.ignoreExpectedError = ignoreExpectedError -const getEvents = (truffleInstance, filter, fromBlock = 0, toBlock = 'latest') => truffleInstance.contract.getPastEvents(filter.event, { fromBlock, toBlock }) +const getEvents = (truffleInstance, filter, fromBlock = 0, toBlock = 'latest') => + truffleInstance.contract.getPastEvents(filter.event, { fromBlock, toBlock }) -module.exports.getEvents = getEvents; +module.exports.getEvents = getEvents -function ether (n) { - return new BN(web3.utils.toWei(n, 'ether')); +function ether(n) { + return new BN(web3.utils.toWei(n, 'ether')) } -module.exports.ether = ether; +module.exports.ether = ether -function expectEventInLogs (logs, eventName, eventArgs = {}) { - const events = logs.filter(e => e.event === eventName); - expect(events.length > 0).to.equal(true, `There is no '${eventName}'`); +function expectEventInLogs(logs, eventName, eventArgs = {}) { + const events = logs.filter(e => e.event === eventName) + expect(events.length > 0).to.equal(true, `There is no '${eventName}'`) - const exception = []; - const event = events.find(function (e) { + const exception = [] + const event = events.find(e => { for (const [k, v] of Object.entries(eventArgs)) { try { - contains(e.args, k, v); + contains(e.args, k, v) } catch (error) { - exception.push(error); - return false; + exception.push(error) + return false } } - return true; - }); + return true + }) if (event === undefined) { - throw exception[0]; + throw exception[0] } - return event; + return event } -function contains (args, key, value) { - expect(key in args).to.equal(true, `Unknown event argument '${key}'`); +function contains(args, key, value) { + expect(key in args).to.equal(true, `Unknown event argument '${key}'`) if (value === null) { - expect(args[key]).to.equal(null); + expect(args[key]).to.equal(null) } else if (isBN(args[key])) { - expect(args[key]).to.be.bignumber.equal(value); + expect(args[key]).to.be.bignumber.equal(value) } else { - expect(args[key]).to.be.equal(value); + expect(args[key]).to.be.equal(value) } } -function isBN (object) { - return BN.isBN(object) || object instanceof BN; +function isBN(object) { + return BN.isBN(object) || object instanceof BN } -module.exports.expectEventInLogs = expectEventInLogs; +module.exports.expectEventInLogs = expectEventInLogs diff --git a/test/native_to_erc/foreign_bridge_test.js b/test/native_to_erc/foreign_bridge_test.js index 29029b835..3e43832a2 100644 --- a/test/native_to_erc/foreign_bridge_test.js +++ b/test/native_to_erc/foreign_bridge_test.js @@ -1,37 +1,40 @@ -const ForeignBridge = artifacts.require("ForeignBridgeNativeToErc.sol"); -const ForeignBridgeV2 = artifacts.require("ForeignBridgeV2.sol"); -const BridgeValidators = artifacts.require("BridgeValidators.sol"); -const EternalStorageProxy = artifacts.require("EternalStorageProxy.sol"); -const FeeManagerNativeToErc = artifacts.require("FeeManagerNativeToErc.sol"); -const RewardableValidators = artifacts.require("RewardableValidators.sol"); -const POA20 = artifacts.require("ERC677BridgeToken.sol"); - -const { expect } = require('chai'); -const {ERROR_MSG, ZERO_ADDRESS, toBN} = require('../setup'); -const {createMessage, sign, signatureToVRS, getEvents, ether} = require('../helpers/helpers'); - -const oneEther = ether('1'); -const halfEther = ether('0.5'); -const minPerTx = ether('0.01'); -const requireBlockConfirmations = 8; -const gasPrice = web3.utils.toWei('1', 'gwei'); +const ForeignBridge = artifacts.require('ForeignBridgeNativeToErc.sol') +const ForeignBridgeV2 = artifacts.require('ForeignBridgeV2.sol') +const BridgeValidators = artifacts.require('BridgeValidators.sol') +const EternalStorageProxy = artifacts.require('EternalStorageProxy.sol') +const FeeManagerNativeToErc = artifacts.require('FeeManagerNativeToErc.sol') +const RewardableValidators = artifacts.require('RewardableValidators.sol') +const POA20 = artifacts.require('ERC677BridgeToken.sol') + +const { expect } = require('chai') +const { ERROR_MSG, ZERO_ADDRESS, toBN } = require('../setup') +const { createMessage, sign, signatureToVRS, getEvents, ether } = require('../helpers/helpers') + +const oneEther = ether('1') +const halfEther = ether('0.5') +const minPerTx = ether('0.01') +const requireBlockConfirmations = 8 +const gasPrice = web3.utils.toWei('1', 'gwei') const homeDailyLimit = oneEther const homeMaxPerTx = halfEther const ZERO = toBN(0) -contract('ForeignBridge', async (accounts) => { - let validatorContract, authorities, owner, token; +contract('ForeignBridge', async accounts => { + let validatorContract + let authorities + let owner + let token before(async () => { validatorContract = await BridgeValidators.new() - authorities = [accounts[1], accounts[2]]; + authorities = [accounts[1], accounts[2]] owner = accounts[0] await validatorContract.initialize(1, authorities, owner) }) describe('#initialize', async () => { it('should initialize', async () => { - token = await POA20.new("POA ERC20 Foundation", "POA20", 18); - let foreignBridge = await ForeignBridge.new(); + token = await POA20.new('POA ERC20 Foundation', 'POA20', 18) + const foreignBridge = await ForeignBridge.new() expect(await foreignBridge.validatorContract()).to.be.equal(ZERO_ADDRESS) expect(await foreignBridge.deployedAtBlock()).to.be.bignumber.equal(ZERO) @@ -40,17 +43,95 @@ contract('ForeignBridge', async (accounts) => { expect(await foreignBridge.dailyLimit()).to.be.bignumber.equal(ZERO) expect(await foreignBridge.maxPerTx()).to.be.bignumber.equal(ZERO) - await foreignBridge.initialize(ZERO_ADDRESS, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.initialize(validatorContract.address, ZERO_ADDRESS, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.initialize(validatorContract.address, token.address, oneEther, halfEther, minPerTx, 0, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.initialize(owner, token.address, oneEther, halfEther, minPerTx, requireBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.initialize(validatorContract.address, owner, oneEther, halfEther, minPerTx, requireBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.initialize(validatorContract.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner); + await foreignBridge + .initialize( + ZERO_ADDRESS, + token.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + homeDailyLimit, + homeMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await foreignBridge + .initialize( + validatorContract.address, + ZERO_ADDRESS, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + homeDailyLimit, + homeMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await foreignBridge + .initialize( + validatorContract.address, + token.address, + oneEther, + halfEther, + minPerTx, + 0, + requireBlockConfirmations, + homeDailyLimit, + homeMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await foreignBridge + .initialize( + owner, + token.address, + oneEther, + halfEther, + minPerTx, + requireBlockConfirmations, + gasPrice, + homeDailyLimit, + homeMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await foreignBridge + .initialize( + validatorContract.address, + owner, + oneEther, + halfEther, + minPerTx, + requireBlockConfirmations, + gasPrice, + homeDailyLimit, + homeMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await foreignBridge.initialize( + validatorContract.address, + token.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + homeDailyLimit, + homeMaxPerTx, + owner + ) expect(await foreignBridge.isInitialized()).to.be.equal(true) expect(await foreignBridge.validatorContract()).to.be.equal(validatorContract.address) expect(await foreignBridge.deployedAtBlock()).to.be.bignumber.above(ZERO) - expect(await foreignBridge.requiredBlockConfirmations()).to.be.bignumber.equal(requireBlockConfirmations.toString()) + expect(await foreignBridge.requiredBlockConfirmations()).to.be.bignumber.equal( + requireBlockConfirmations.toString() + ) expect(await foreignBridge.gasPrice()).to.be.bignumber.equal(gasPrice) expect(await foreignBridge.dailyLimit()).to.be.bignumber.equal(oneEther) expect(await foreignBridge.maxPerTx()).to.be.bignumber.equal(halfEther) @@ -68,66 +149,76 @@ contract('ForeignBridge', async (accounts) => { let foreignBridge beforeEach(async () => { foreignBridge = await ForeignBridge.new() - token = await POA20.new("POA ERC20 Foundation", "POA20", 18); - await foreignBridge.initialize(validatorContract.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner); - await token.transferOwnership(foreignBridge.address); + token = await POA20.new('POA ERC20 Foundation', 'POA20', 18) + await foreignBridge.initialize( + validatorContract.address, + token.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + homeDailyLimit, + homeMaxPerTx, + owner + ) + await token.transferOwnership(foreignBridge.address) }) it('should allow to deposit', async () => { - const recipientAccount = accounts[3]; + const recipientAccount = accounts[3] const balanceBefore = await token.balanceOf(recipientAccount) const totalSupplyBefore = await token.totalSupply() - const value = ether('0.25'); - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); + const value = ether('0.25') + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' + const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address) const signature = await sign(authorities[0], message) - const vrs = signatureToVRS(signature); + const vrs = signatureToVRS(signature) false.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) - const {logs} = await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.fulfilled - logs[0].event.should.be.equal("RelayedMessage") + const { logs } = await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.fulfilled + logs[0].event.should.be.equal('RelayedMessage') logs[0].args.recipient.should.be.equal(recipientAccount) logs[0].args.value.should.be.bignumber.equal(value) - logs[0].args.transactionHash.should.be.equal(transactionHash); + logs[0].args.transactionHash.should.be.equal(transactionHash) - const balanceAfter = await token.balanceOf(recipientAccount); - const totalSupplyAfter = await token.totalSupply(); + const balanceAfter = await token.balanceOf(recipientAccount) + const totalSupplyAfter = await token.totalSupply() balanceAfter.should.be.bignumber.equal(balanceBefore.add(value)) totalSupplyAfter.should.be.bignumber.equal(totalSupplyBefore.add(value)) true.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) }) it('should reject if address is not foreign address', async () => { - const recipientAccount = accounts[3]; - const value = ether('0.25',); - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - const message = createMessage(recipientAccount, value, transactionHash, accounts[0]); + const recipientAccount = accounts[3] + const value = ether('0.25') + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' + const message = createMessage(recipientAccount, value, transactionHash, accounts[0]) const signature = await sign(authorities[0], message) - const vrs = signatureToVRS(signature); + const vrs = signatureToVRS(signature) false.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.rejectedWith(ERROR_MSG) - }) - it('should allow second deposit with different transactionHash but same recipient and value', async ()=> { - const recipientAccount = accounts[3]; + it('should allow second deposit with different transactionHash but same recipient and value', async () => { + const recipientAccount = accounts[3] const balanceBefore = await token.balanceOf(recipientAccount) // tx 1 - const value = ether('0.25'); - const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); + const value = ether('0.25') + const transactionHash = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' + const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address) const signature = await sign(authorities[0], message) - const vrs = signatureToVRS(signature); + const vrs = signatureToVRS(signature) false.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.fulfilled // tx 2 - const transactionHash2 = "0x77a496628a776a03d58d7e6059a5937f04bebd8ba4ff89f76dd4bb8ba7e291ee"; - const message2 = createMessage(recipientAccount, value, transactionHash2, foreignBridge.address); + const transactionHash2 = '0x77a496628a776a03d58d7e6059a5937f04bebd8ba4ff89f76dd4bb8ba7e291ee' + const message2 = createMessage(recipientAccount, value, transactionHash2, foreignBridge.address) const signature2 = await sign(authorities[0], message2) - const vrs2 = signatureToVRS(signature2); + const vrs2 = signatureToVRS(signature2) false.should.be.equal(await foreignBridge.relayedMessages(transactionHash2)) - const {logs} = await foreignBridge.executeSignatures([vrs2.v], [vrs2.r], [vrs2.s], message2).should.be.fulfilled + const { logs } = await foreignBridge.executeSignatures([vrs2.v], [vrs2.r], [vrs2.s], message2).should.be.fulfilled - logs[0].event.should.be.equal("RelayedMessage") + logs[0].event.should.be.equal('RelayedMessage') logs[0].args.recipient.should.be.equal(recipientAccount) logs[0].args.value.should.be.bignumber.equal(value) - logs[0].args.transactionHash.should.be.equal(transactionHash2); + logs[0].args.transactionHash.should.be.equal(transactionHash2) const totalSupply = await token.totalSupply() const balanceAfter = await token.balanceOf(recipientAccount) balanceAfter.should.be.bignumber.equal(balanceBefore.add(value.mul(toBN(2)))) @@ -137,106 +228,130 @@ contract('ForeignBridge', async (accounts) => { }) it('should not allow second deposit (replay attack) with same transactionHash but different recipient', async () => { - const recipientAccount = accounts[3]; + const recipientAccount = accounts[3] // tx 1 const value = halfEther - const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); + const transactionHash = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' + const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address) const signature = await sign(authorities[0], message) - const vrs = signatureToVRS(signature); + const vrs = signatureToVRS(signature) false.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.fulfilled // tx 2 - const message2 = createMessage(accounts[4], value, transactionHash, foreignBridge.address); + const message2 = createMessage(accounts[4], value, transactionHash, foreignBridge.address) const signature2 = await sign(authorities[0], message2) - const vrs2 = signatureToVRS(signature2); + const vrs2 = signatureToVRS(signature2) true.should.be.equal(await foreignBridge.relayedMessages(transactionHash)) await foreignBridge.executeSignatures([vrs2.v], [vrs2.r], [vrs2.s], message2).should.be.rejectedWith(ERROR_MSG) }) it('should not allow withdraw over home max tx limit', async () => { - const recipientAccount = accounts[3]; - const invalidValue = ether('0.75'); + const recipientAccount = accounts[3] + const invalidValue = ether('0.75') - const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - const message = createMessage(recipientAccount, invalidValue, transactionHash, foreignBridge.address); + const transactionHash = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' + const message = createMessage(recipientAccount, invalidValue, transactionHash, foreignBridge.address) const signature = await sign(authorities[0], message) - const vrs = signatureToVRS(signature); + const vrs = signatureToVRS(signature) await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.rejectedWith(ERROR_MSG) }) it('should not allow withdraw over daily home limit', async () => { - const recipientAccount = accounts[3]; + const recipientAccount = accounts[3] - const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - const message = createMessage(recipientAccount, halfEther, transactionHash, foreignBridge.address); + const transactionHash = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' + const message = createMessage(recipientAccount, halfEther, transactionHash, foreignBridge.address) const signature = await sign(authorities[0], message) - const vrs = signatureToVRS(signature); + const vrs = signatureToVRS(signature) await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.fulfilled - const transactionHash2 = "0x69debd8fd1923c9cb3cd8ef6461e2740b2d037943b941729d5a47671a2bb8712"; - const message2 = createMessage(recipientAccount, halfEther, transactionHash2, foreignBridge.address); + const transactionHash2 = '0x69debd8fd1923c9cb3cd8ef6461e2740b2d037943b941729d5a47671a2bb8712' + const message2 = createMessage(recipientAccount, halfEther, transactionHash2, foreignBridge.address) const signature2 = await sign(authorities[0], message2) - const vrs2 = signatureToVRS(signature2); + const vrs2 = signatureToVRS(signature2) await foreignBridge.executeSignatures([vrs2.v], [vrs2.r], [vrs2.s], message2).should.be.fulfilled - const transactionHash3 = "0x022695428093bb292db8e48bd1417c5e1b84c0bf673bd0fff23ed0fb6495b872"; - const message3 = createMessage(recipientAccount, halfEther, transactionHash3, foreignBridge.address); + const transactionHash3 = '0x022695428093bb292db8e48bd1417c5e1b84c0bf673bd0fff23ed0fb6495b872' + const message3 = createMessage(recipientAccount, halfEther, transactionHash3, foreignBridge.address) const signature3 = await sign(authorities[0], message3) - const vrs3 = signatureToVRS(signature3); + const vrs3 = signatureToVRS(signature3) await foreignBridge.executeSignatures([vrs3.v], [vrs3.r], [vrs3.s], message3).should.be.rejectedWith(ERROR_MSG) }) }) describe('#executeSignatures with 2 minimum signatures', async () => { - let multisigValidatorContract, twoAuthorities, ownerOfValidatorContract, foreignBridgeWithMultiSignatures + let multisigValidatorContract + let twoAuthorities + let ownerOfValidatorContract + let foreignBridgeWithMultiSignatures beforeEach(async () => { multisigValidatorContract = await BridgeValidators.new() - token = await POA20.new("POA ERC20 Foundation", "POA20", 18); - twoAuthorities = [accounts[0], accounts[1]]; + token = await POA20.new('POA ERC20 Foundation', 'POA20', 18) + twoAuthorities = [accounts[0], accounts[1]] ownerOfValidatorContract = accounts[3] - await multisigValidatorContract.initialize(2, twoAuthorities, ownerOfValidatorContract, {from: ownerOfValidatorContract}) + await multisigValidatorContract.initialize(2, twoAuthorities, ownerOfValidatorContract, { + from: ownerOfValidatorContract + }) foreignBridgeWithMultiSignatures = await ForeignBridge.new() - await foreignBridgeWithMultiSignatures.initialize(multisigValidatorContract.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, {from: ownerOfValidatorContract}); - await token.transferOwnership(foreignBridgeWithMultiSignatures.address); + await foreignBridgeWithMultiSignatures.initialize( + multisigValidatorContract.address, + token.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + homeDailyLimit, + homeMaxPerTx, + owner, + { from: ownerOfValidatorContract } + ) + await token.transferOwnership(foreignBridgeWithMultiSignatures.address) }) it('deposit should fail if not enough signatures are provided', async () => { - - const recipientAccount = accounts[4]; + const recipientAccount = accounts[4] // msg 1 const value = halfEther - const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - const message = createMessage(recipientAccount, value, transactionHash, foreignBridgeWithMultiSignatures.address); + const transactionHash = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' + const message = createMessage(recipientAccount, value, transactionHash, foreignBridgeWithMultiSignatures.address) const signature = await sign(twoAuthorities[0], message) - const vrs = signatureToVRS(signature); + const vrs = signatureToVRS(signature) false.should.be.equal(await foreignBridgeWithMultiSignatures.relayedMessages(transactionHash)) - await foreignBridgeWithMultiSignatures.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.rejectedWith(ERROR_MSG) + await foreignBridgeWithMultiSignatures + .executeSignatures([vrs.v], [vrs.r], [vrs.s], message) + .should.be.rejectedWith(ERROR_MSG) // msg 2 const signature2 = await sign(twoAuthorities[1], message) - const vrs2 = signatureToVRS(signature2); - const {logs} = await foreignBridgeWithMultiSignatures.executeSignatures([vrs.v, vrs2.v], [vrs.r, vrs2.r], [vrs.s, vrs2.s], message).should.be.fulfilled; - - logs[0].event.should.be.equal("RelayedMessage") + const vrs2 = signatureToVRS(signature2) + const { logs } = await foreignBridgeWithMultiSignatures.executeSignatures( + [vrs.v, vrs2.v], + [vrs.r, vrs2.r], + [vrs.s, vrs2.s], + message + ).should.be.fulfilled + + logs[0].event.should.be.equal('RelayedMessage') logs[0].args.recipient.should.be.equal(recipientAccount) logs[0].args.value.should.be.bignumber.equal(value) - logs[0].args.transactionHash.should.be.equal(transactionHash); + logs[0].args.transactionHash.should.be.equal(transactionHash) true.should.be.equal(await foreignBridgeWithMultiSignatures.relayedMessages(transactionHash)) - }) it('deposit should fail if duplicate signature is provided', async () => { - const recipientAccount = accounts[4]; + const recipientAccount = accounts[4] // msg 1 const value = halfEther - const transactionHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - const message = createMessage(recipientAccount, value, transactionHash, foreignBridgeWithMultiSignatures.address); + const transactionHash = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' + const message = createMessage(recipientAccount, value, transactionHash, foreignBridgeWithMultiSignatures.address) const signature = await sign(twoAuthorities[0], message) - const vrs = signatureToVRS(signature); + const vrs = signatureToVRS(signature) false.should.be.equal(await foreignBridgeWithMultiSignatures.relayedMessages(transactionHash)) - await foreignBridgeWithMultiSignatures.executeSignatures([vrs.v, vrs.v], [vrs.r, vrs.r], [vrs.s, vrs.s], message).should.be.rejectedWith(ERROR_MSG) + await foreignBridgeWithMultiSignatures + .executeSignatures([vrs.v, vrs.v], [vrs.r, vrs.r], [vrs.s, vrs.s], message) + .should.be.rejectedWith(ERROR_MSG) }) it('works with 5 validators and 3 required signatures', async () => { const recipient = accounts[8] @@ -244,31 +359,46 @@ contract('ForeignBridge', async (accounts) => { const ownerOfValidators = accounts[0] const validatorContractWith3Signatures = await BridgeValidators.new() await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) - const erc20Token = await POA20.new("Some ERC20", "RSZT", 18); + const erc20Token = await POA20.new('Some ERC20', 'RSZT', 18) const value = halfEther const foreignBridgeWithThreeSigs = await ForeignBridge.new() - await foreignBridgeWithThreeSigs.initialize(validatorContractWith3Signatures.address, erc20Token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner); - await erc20Token.transferOwnership(foreignBridgeWithThreeSigs.address); - - const txHash = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - const message = createMessage(recipient, value, txHash, foreignBridgeWithThreeSigs.address); + await foreignBridgeWithThreeSigs.initialize( + validatorContractWith3Signatures.address, + erc20Token.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + homeDailyLimit, + homeMaxPerTx, + owner + ) + await erc20Token.transferOwnership(foreignBridgeWithThreeSigs.address) + + const txHash = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' + const message = createMessage(recipient, value, txHash, foreignBridgeWithThreeSigs.address) // signature 1 const signature = await sign(authoritiesFiveAccs[0], message) - const vrs = signatureToVRS(signature); + const vrs = signatureToVRS(signature) // signature 2 const signature2 = await sign(authoritiesFiveAccs[1], message) - const vrs2 = signatureToVRS(signature2); + const vrs2 = signatureToVRS(signature2) // signature 3 const signature3 = await sign(authoritiesFiveAccs[2], message) - const vrs3 = signatureToVRS(signature3); - - - const {logs} = await foreignBridgeWithThreeSigs.executeSignatures([vrs.v, vrs2.v, vrs3.v], [vrs.r, vrs2.r, vrs3.r], [vrs.s, vrs2.s, vrs3.s], message).should.be.fulfilled; - logs[0].event.should.be.equal("RelayedMessage") + const vrs3 = signatureToVRS(signature3) + + const { logs } = await foreignBridgeWithThreeSigs.executeSignatures( + [vrs.v, vrs2.v, vrs3.v], + [vrs.r, vrs2.r, vrs3.r], + [vrs.s, vrs2.s, vrs3.s], + message + ).should.be.fulfilled + logs[0].event.should.be.equal('RelayedMessage') logs[0].args.recipient.should.be.equal(recipient) logs[0].args.value.should.be.bignumber.equal(value) true.should.be.equal(await foreignBridgeWithThreeSigs.relayedMessages(txHash)) @@ -276,114 +406,175 @@ contract('ForeignBridge', async (accounts) => { }) describe('#onTokenTransfer', async () => { - it('can only be called from token contract', async ()=> { + it('can only be called from token contract', async () => { const owner = accounts[3] const user = accounts[4] - token = await POA20.new("POA ERC20 Foundation", "POA20", 18, {from: owner}); - const foreignBridge = await ForeignBridge.new(); - await foreignBridge.initialize(validatorContract.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner); - await token.mint(user, halfEther, {from: owner }).should.be.fulfilled; - await token.transferOwnership(foreignBridge.address, {from: owner}); - await foreignBridge.onTokenTransfer(user, halfEther, '0x00', {from: owner}).should.be.rejectedWith(ERROR_MSG); - await token.transferAndCall(foreignBridge.address, halfEther, '0x00', {from: user}).should.be.fulfilled; + token = await POA20.new('POA ERC20 Foundation', 'POA20', 18, { from: owner }) + const foreignBridge = await ForeignBridge.new() + await foreignBridge.initialize( + validatorContract.address, + token.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + homeDailyLimit, + homeMaxPerTx, + owner + ) + await token.mint(user, halfEther, { from: owner }).should.be.fulfilled + await token.transferOwnership(foreignBridge.address, { from: owner }) + await foreignBridge.onTokenTransfer(user, halfEther, '0x00', { from: owner }).should.be.rejectedWith(ERROR_MSG) + await token.transferAndCall(foreignBridge.address, halfEther, '0x00', { from: user }).should.be.fulfilled expect(await token.totalSupply()).to.be.bignumber.equal(ZERO) expect(await token.balanceOf(user)).to.be.bignumber.equal(ZERO) }) it('should not allow to burn more than the limit', async () => { const owner = accounts[3] const user = accounts[4] - const valueMoreThanLimit = halfEther.add(toBN(1)); - token = await POA20.new("POA ERC20 Foundation", "POA20", 18, {from: owner}); - const foreignBridge = await ForeignBridge.new(); - - await foreignBridge.initialize(validatorContract.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner); - await token.mint(user, valueMoreThanLimit, {from: owner }).should.be.fulfilled; - await token.transferOwnership(foreignBridge.address, {from: owner}); - - await token.transferAndCall(foreignBridge.address, valueMoreThanLimit, '0x00', {from: user}).should.be.rejectedWith(ERROR_MSG); - - valueMoreThanLimit.should.be.bignumber.equal(await token.totalSupply()); - valueMoreThanLimit.should.be.bignumber.equal(await token.balanceOf(user)); - - await token.transferAndCall(foreignBridge.address, halfEther, '0x00', {from: user}).should.be.fulfilled; + const valueMoreThanLimit = halfEther.add(toBN(1)) + token = await POA20.new('POA ERC20 Foundation', 'POA20', 18, { from: owner }) + const foreignBridge = await ForeignBridge.new() + + await foreignBridge.initialize( + validatorContract.address, + token.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + homeDailyLimit, + homeMaxPerTx, + owner + ) + await token.mint(user, valueMoreThanLimit, { from: owner }).should.be.fulfilled + await token.transferOwnership(foreignBridge.address, { from: owner }) + + await token + .transferAndCall(foreignBridge.address, valueMoreThanLimit, '0x00', { from: user }) + .should.be.rejectedWith(ERROR_MSG) + + valueMoreThanLimit.should.be.bignumber.equal(await token.totalSupply()) + valueMoreThanLimit.should.be.bignumber.equal(await token.balanceOf(user)) + + await token.transferAndCall(foreignBridge.address, halfEther, '0x00', { from: user }).should.be.fulfilled expect(await token.totalSupply()).to.be.bignumber.equal('1') expect(await token.balanceOf(user)).to.be.bignumber.equal('1') - const events = await getEvents(foreignBridge, {event: 'UserRequestForAffirmation'}); + const events = await getEvents(foreignBridge, { event: 'UserRequestForAffirmation' }) expect(events[0].returnValues.recipient).to.be.equal(user) expect(toBN(events[0].returnValues.value)).to.be.bignumber.equal(halfEther) }) it('should only let to send within maxPerTx limit', async () => { const owner = accounts[3] const user = accounts[4] - const valueMoreThanLimit = halfEther.add(toBN(1)); - token = await POA20.new("POA ERC20 Foundation", "POA20", 18, {from: owner}); - const foreignBridge = await ForeignBridge.new(); - await foreignBridge.initialize(validatorContract.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner); - await token.mint(user, oneEther.add(toBN(1)), {from: owner }).should.be.fulfilled; - - await token.transferOwnership(foreignBridge.address, {from: owner}); - - await token.transferAndCall(foreignBridge.address, valueMoreThanLimit, '0x00', {from: user}).should.be.rejectedWith(ERROR_MSG); - - oneEther.add(toBN(1)).should.be.bignumber.equal(await token.totalSupply()); - oneEther.add(toBN(1)).should.be.bignumber.equal(await token.balanceOf(user)); - - await token.transferAndCall(foreignBridge.address, halfEther, '0x00', {from: user}).should.be.fulfilled; - - valueMoreThanLimit.should.be.bignumber.equal(await token.totalSupply()); - valueMoreThanLimit.should.be.bignumber.equal(await token.balanceOf(user)); - - await token.transferAndCall(foreignBridge.address, halfEther, '0x00', {from: user}).should.be.fulfilled; + const valueMoreThanLimit = halfEther.add(toBN(1)) + token = await POA20.new('POA ERC20 Foundation', 'POA20', 18, { from: owner }) + const foreignBridge = await ForeignBridge.new() + await foreignBridge.initialize( + validatorContract.address, + token.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + homeDailyLimit, + homeMaxPerTx, + owner + ) + await token.mint(user, oneEther.add(toBN(1)), { from: owner }).should.be.fulfilled + + await token.transferOwnership(foreignBridge.address, { from: owner }) + + await token + .transferAndCall(foreignBridge.address, valueMoreThanLimit, '0x00', { from: user }) + .should.be.rejectedWith(ERROR_MSG) + + oneEther.add(toBN(1)).should.be.bignumber.equal(await token.totalSupply()) + oneEther.add(toBN(1)).should.be.bignumber.equal(await token.balanceOf(user)) + + await token.transferAndCall(foreignBridge.address, halfEther, '0x00', { from: user }).should.be.fulfilled + + valueMoreThanLimit.should.be.bignumber.equal(await token.totalSupply()) + valueMoreThanLimit.should.be.bignumber.equal(await token.balanceOf(user)) + + await token.transferAndCall(foreignBridge.address, halfEther, '0x00', { from: user }).should.be.fulfilled expect(await token.totalSupply()).to.be.bignumber.equal('1') expect(await token.balanceOf(user)).to.be.bignumber.equal('1') - await token.transferAndCall(foreignBridge.address, '1', '0x00', {from: user}).should.be.rejectedWith(ERROR_MSG); + await token.transferAndCall(foreignBridge.address, '1', '0x00', { from: user }).should.be.rejectedWith(ERROR_MSG) }) it('should not let to withdraw less than minPerTx', async () => { const owner = accounts[3] const user = accounts[4] - const valueLessThanMinPerTx = minPerTx.sub(toBN(1)); - token = await POA20.new("POA ERC20 Foundation", "POA20", 18, {from: owner}); - const foreignBridge = await ForeignBridge.new(); - await foreignBridge.initialize(validatorContract.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner); - await token.mint(user, oneEther, {from: owner }).should.be.fulfilled; - await token.transferOwnership(foreignBridge.address, {from: owner}); - - await token.transferAndCall(foreignBridge.address, valueLessThanMinPerTx, '0x00', {from: user}).should.be.rejectedWith(ERROR_MSG); - - oneEther.should.be.bignumber.equal(await token.totalSupply()); - oneEther.should.be.bignumber.equal(await token.balanceOf(user)); - - await token.transferAndCall(foreignBridge.address, minPerTx, '0x00', {from: user}).should.be.fulfilled; - - oneEther.sub(minPerTx).should.be.bignumber.equal(await token.totalSupply()); - oneEther.sub(minPerTx).should.be.bignumber.equal(await token.balanceOf(user)); + const valueLessThanMinPerTx = minPerTx.sub(toBN(1)) + token = await POA20.new('POA ERC20 Foundation', 'POA20', 18, { from: owner }) + const foreignBridge = await ForeignBridge.new() + await foreignBridge.initialize( + validatorContract.address, + token.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + homeDailyLimit, + homeMaxPerTx, + owner + ) + await token.mint(user, oneEther, { from: owner }).should.be.fulfilled + await token.transferOwnership(foreignBridge.address, { from: owner }) + + await token + .transferAndCall(foreignBridge.address, valueLessThanMinPerTx, '0x00', { from: user }) + .should.be.rejectedWith(ERROR_MSG) + + oneEther.should.be.bignumber.equal(await token.totalSupply()) + oneEther.should.be.bignumber.equal(await token.balanceOf(user)) + + await token.transferAndCall(foreignBridge.address, minPerTx, '0x00', { from: user }).should.be.fulfilled + + oneEther.sub(minPerTx).should.be.bignumber.equal(await token.totalSupply()) + oneEther.sub(minPerTx).should.be.bignumber.equal(await token.balanceOf(user)) }) }) describe('#setting limits', async () => { - let foreignBridge; + let foreignBridge beforeEach(async () => { - token = await POA20.new("POA ERC20 Foundation", "POA20", 18); - foreignBridge = await ForeignBridge.new(); - await foreignBridge.initialize(validatorContract.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner); + token = await POA20.new('POA ERC20 Foundation', 'POA20', 18) + foreignBridge = await ForeignBridge.new() + await foreignBridge.initialize( + validatorContract.address, + token.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + homeDailyLimit, + homeMaxPerTx, + owner + ) await token.transferOwnership(foreignBridge.address) }) it('#setMaxPerTx allows to set only to owner and cannot be more than daily limit', async () => { - await foreignBridge.setMaxPerTx(halfEther, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.setMaxPerTx(halfEther, {from: owner}).should.be.fulfilled; + await foreignBridge.setMaxPerTx(halfEther, { from: authorities[0] }).should.be.rejectedWith(ERROR_MSG) + await foreignBridge.setMaxPerTx(halfEther, { from: owner }).should.be.fulfilled - await foreignBridge.setMaxPerTx(oneEther, {from: owner}).should.be.rejectedWith(ERROR_MSG); + await foreignBridge.setMaxPerTx(oneEther, { from: owner }).should.be.rejectedWith(ERROR_MSG) }) it('#setMinPerTx allows to set only to owner and cannot be more than daily limit and should be less than maxPerTx', async () => { - await foreignBridge.setMinPerTx(minPerTx, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.setMinPerTx(minPerTx, {from: owner}).should.be.fulfilled; + await foreignBridge.setMinPerTx(minPerTx, { from: authorities[0] }).should.be.rejectedWith(ERROR_MSG) + await foreignBridge.setMinPerTx(minPerTx, { from: owner }).should.be.fulfilled - await foreignBridge.setMinPerTx(oneEther, {from: owner}).should.be.rejectedWith(ERROR_MSG); + await foreignBridge.setMinPerTx(oneEther, { from: owner }).should.be.rejectedWith(ERROR_MSG) }) }) @@ -391,53 +582,76 @@ contract('ForeignBridge', async (accounts) => { it('can be upgraded', async () => { const REQUIRED_NUMBER_OF_VALIDATORS = 1 const VALIDATORS = [accounts[1]] - const PROXY_OWNER = accounts[0] - const FOREIGN_DAILY_LIMIT = oneEther; - const FOREIGN_MAX_AMOUNT_PER_TX = halfEther; - const FOREIGN_MIN_AMOUNT_PER_TX = minPerTx; + const PROXY_OWNER = accounts[0] + const FOREIGN_DAILY_LIMIT = oneEther + const FOREIGN_MAX_AMOUNT_PER_TX = halfEther + const FOREIGN_MIN_AMOUNT_PER_TX = minPerTx // Validators Contract - let validatorsProxy = await EternalStorageProxy.new().should.be.fulfilled; - const validatorsContractImpl = await BridgeValidators.new().should.be.fulfilled; - await validatorsProxy.upgradeTo('1', validatorsContractImpl.address).should.be.fulfilled; + let validatorsProxy = await EternalStorageProxy.new().should.be.fulfilled + const validatorsContractImpl = await BridgeValidators.new().should.be.fulfilled + await validatorsProxy.upgradeTo('1', validatorsContractImpl.address).should.be.fulfilled validatorsContractImpl.address.should.be.equal(await validatorsProxy.implementation()) - validatorsProxy = await BridgeValidators.at(validatorsProxy.address); - await validatorsProxy.initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, PROXY_OWNER).should.be.fulfilled; + validatorsProxy = await BridgeValidators.at(validatorsProxy.address) + await validatorsProxy.initialize(REQUIRED_NUMBER_OF_VALIDATORS, VALIDATORS, PROXY_OWNER).should.be.fulfilled // POA20 - let token = await POA20.new("POA ERC20 Foundation", "POA20", 18); + const token = await POA20.new('POA ERC20 Foundation', 'POA20', 18) // ForeignBridge V1 Contract - let foreignBridgeProxy = await EternalStorageProxy.new().should.be.fulfilled; - const foreignBridgeImpl = await ForeignBridge.new().should.be.fulfilled; - await foreignBridgeProxy.upgradeTo('1', foreignBridgeImpl.address).should.be.fulfilled; - - foreignBridgeProxy = await ForeignBridge.at(foreignBridgeProxy.address); - await foreignBridgeProxy.initialize(validatorsProxy.address, token.address, FOREIGN_DAILY_LIMIT, FOREIGN_MAX_AMOUNT_PER_TX, FOREIGN_MIN_AMOUNT_PER_TX, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner) - await token.transferOwnership(foreignBridgeProxy.address).should.be.fulfilled; - - foreignBridgeProxy.address.should.be.equal(await token.owner()); + let foreignBridgeProxy = await EternalStorageProxy.new().should.be.fulfilled + const foreignBridgeImpl = await ForeignBridge.new().should.be.fulfilled + await foreignBridgeProxy.upgradeTo('1', foreignBridgeImpl.address).should.be.fulfilled + + foreignBridgeProxy = await ForeignBridge.at(foreignBridgeProxy.address) + await foreignBridgeProxy.initialize( + validatorsProxy.address, + token.address, + FOREIGN_DAILY_LIMIT, + FOREIGN_MAX_AMOUNT_PER_TX, + FOREIGN_MIN_AMOUNT_PER_TX, + gasPrice, + requireBlockConfirmations, + homeDailyLimit, + homeMaxPerTx, + owner + ) + await token.transferOwnership(foreignBridgeProxy.address).should.be.fulfilled + + foreignBridgeProxy.address.should.be.equal(await token.owner()) // Deploy V2 - let foreignImplV2 = await ForeignBridgeV2.new(); - let foreignBridgeProxyUpgrade = await EternalStorageProxy.at(foreignBridgeProxy.address); - await foreignBridgeProxyUpgrade.upgradeTo('2', foreignImplV2.address).should.be.fulfilled; + const foreignImplV2 = await ForeignBridgeV2.new() + const foreignBridgeProxyUpgrade = await EternalStorageProxy.at(foreignBridgeProxy.address) + await foreignBridgeProxyUpgrade.upgradeTo('2', foreignImplV2.address).should.be.fulfilled foreignImplV2.address.should.be.equal(await foreignBridgeProxyUpgrade.implementation()) }) it('can be deployed via upgradeToAndCall', async () => { const tokenAddress = token.address const validatorsAddress = validatorContract.address - const FOREIGN_DAILY_LIMIT = '3'; - const FOREIGN_MAX_AMOUNT_PER_TX = '2'; - const FOREIGN_MIN_AMOUNT_PER_TX = '1'; - - let storageProxy = await EternalStorageProxy.new().should.be.fulfilled; - let foreignBridge = await ForeignBridge.new(); - let data = foreignBridge.contract.methods.initialize( - validatorsAddress, tokenAddress, FOREIGN_DAILY_LIMIT, FOREIGN_MAX_AMOUNT_PER_TX, FOREIGN_MIN_AMOUNT_PER_TX, gasPrice, requireBlockConfirmations, '3', '2', owner).encodeABI() - await storageProxy.upgradeToAndCall('1', foreignBridge.address, data).should.be.fulfilled; - let finalContract = await ForeignBridge.at(storageProxy.address); - true.should.be.equal(await finalContract.isInitialized()); + const FOREIGN_DAILY_LIMIT = '3' + const FOREIGN_MAX_AMOUNT_PER_TX = '2' + const FOREIGN_MIN_AMOUNT_PER_TX = '1' + + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled + const foreignBridge = await ForeignBridge.new() + const data = foreignBridge.contract.methods + .initialize( + validatorsAddress, + tokenAddress, + FOREIGN_DAILY_LIMIT, + FOREIGN_MAX_AMOUNT_PER_TX, + FOREIGN_MIN_AMOUNT_PER_TX, + gasPrice, + requireBlockConfirmations, + '3', + '2', + owner + ) + .encodeABI() + await storageProxy.upgradeToAndCall('1', foreignBridge.address, data).should.be.fulfilled + const finalContract = await ForeignBridge.at(storageProxy.address) + true.should.be.equal(await finalContract.isInitialized()) validatorsAddress.should.be.equal(await finalContract.validatorContract()) expect(await finalContract.dailyLimit()).to.be.bignumber.equal(FOREIGN_DAILY_LIMIT) @@ -445,75 +659,112 @@ contract('ForeignBridge', async (accounts) => { expect(await finalContract.minPerTx()).to.be.bignumber.equal(FOREIGN_MIN_AMOUNT_PER_TX) }) it('can transfer ownership', async () => { - const token = await POA20.new("POA ERC20 Foundation", "POA20", 18); - const foreignBridge = await ForeignBridge.new(); - const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; - const data = foreignBridge.contract.methods.initialize( - validatorContract.address, token.address, '3', '2', '1', gasPrice, requireBlockConfirmations, '3', '2', owner).encodeABI() - await storageProxy.upgradeToAndCall('1', foreignBridge.address, data).should.be.fulfilled; + const token = await POA20.new('POA ERC20 Foundation', 'POA20', 18) + const foreignBridge = await ForeignBridge.new() + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled + const data = foreignBridge.contract.methods + .initialize( + validatorContract.address, + token.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + '3', + '2', + owner + ) + .encodeABI() + await storageProxy.upgradeToAndCall('1', foreignBridge.address, data).should.be.fulfilled await storageProxy.transferProxyOwnership(owner).should.be.fulfilled }) }) describe('#claimTokens', async () => { it('can send erc20', async () => { - const owner = accounts[0]; - token = await POA20.new("POA ERC20 Foundation", "POA20", 18); - const foreignBridgeImpl = await ForeignBridge.new(); - const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + const owner = accounts[0] + token = await POA20.new('POA ERC20 Foundation', 'POA20', 18) + const foreignBridgeImpl = await ForeignBridge.new() + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled await storageProxy.upgradeTo('1', foreignBridgeImpl.address).should.be.fulfilled - const foreignBridge = await ForeignBridge.at(storageProxy.address); - await foreignBridge.initialize(validatorContract.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner); + const foreignBridge = await ForeignBridge.at(storageProxy.address) + await foreignBridge.initialize( + validatorContract.address, + token.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + homeDailyLimit, + homeMaxPerTx, + owner + ) await token.transferOwnership(foreignBridge.address) - let tokenSecond = await POA20.new("Roman Token", "RST", 18); + const tokenSecond = await POA20.new('Roman Token', 'RST', 18) - await tokenSecond.mint(accounts[0], halfEther).should.be.fulfilled; + await tokenSecond.mint(accounts[0], halfEther).should.be.fulfilled expect(await tokenSecond.balanceOf(accounts[0])).to.be.bignumber.equal(halfEther) - await tokenSecond.transfer(foreignBridge.address, halfEther); + await tokenSecond.transfer(foreignBridge.address, halfEther) expect(await tokenSecond.balanceOf(accounts[0])).to.be.bignumber.equal(ZERO) expect(await tokenSecond.balanceOf(foreignBridge.address)).to.be.bignumber.equal(halfEther) - await foreignBridge.claimTokens(tokenSecond.address, accounts[3], {from: owner}); + await foreignBridge.claimTokens(tokenSecond.address, accounts[3], { from: owner }) expect(await tokenSecond.balanceOf(foreignBridge.address)).to.be.bignumber.equal(ZERO) expect(await tokenSecond.balanceOf(accounts[3])).to.be.bignumber.equal(halfEther) }) it('also calls claimTokens on tokenAddress', async () => { - const owner = accounts[0]; - token = await POA20.new("POA ERC20 Foundation", "POA20", 18); - const foreignBridgeImpl = await ForeignBridge.new(); - const storageProxy = await EternalStorageProxy.new().should.be.fulfilled; + const owner = accounts[0] + token = await POA20.new('POA ERC20 Foundation', 'POA20', 18) + const foreignBridgeImpl = await ForeignBridge.new() + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled await storageProxy.upgradeTo('1', foreignBridgeImpl.address).should.be.fulfilled - const foreignBridge = await ForeignBridge.at(storageProxy.address); - await foreignBridge.initialize(validatorContract.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner); + const foreignBridge = await ForeignBridge.at(storageProxy.address) + await foreignBridge.initialize( + validatorContract.address, + token.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + homeDailyLimit, + homeMaxPerTx, + owner + ) await token.transferOwnership(foreignBridge.address) - let tokenSecond = await POA20.new("Roman Token", "RST", 18); + const tokenSecond = await POA20.new('Roman Token', 'RST', 18) - await tokenSecond.mint(accounts[0], 150).should.be.fulfilled; + await tokenSecond.mint(accounts[0], 150).should.be.fulfilled expect(await tokenSecond.balanceOf(accounts[0])).to.be.bignumber.equal('150') - await tokenSecond.transfer(token.address, '150'); + await tokenSecond.transfer(token.address, '150') expect(await tokenSecond.balanceOf(accounts[0])).to.be.bignumber.equal(ZERO) expect(await tokenSecond.balanceOf(token.address)).to.be.bignumber.equal('150') - await foreignBridge.claimTokensFromErc677(tokenSecond.address, accounts[3], {from: owner}); + await foreignBridge.claimTokensFromErc677(tokenSecond.address, accounts[3], { from: owner }) expect(await tokenSecond.balanceOf(foreignBridge.address)).to.be.bignumber.equal(ZERO) expect(await tokenSecond.balanceOf(accounts[3])).to.be.bignumber.equal('150') }) }) - describe('#rewardableInitialize', async() => { - let homeFee, foreignBridge, token, rewardableValidators - let validators = [accounts[1]] - let rewards = [accounts[2]] - let requiredSignatures = 1 + describe('#rewardableInitialize', async () => { + let homeFee + let foreignBridge + let token + let rewardableValidators + const validators = [accounts[1]] + const rewards = [accounts[2]] + const requiredSignatures = 1 beforeEach(async () => { - token = await POA20.new("POA ERC20 Foundation", "POA20", 18) + token = await POA20.new('POA ERC20 Foundation', 'POA20', 18) rewardableValidators = await RewardableValidators.new() await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled - foreignBridge = await ForeignBridge.new() + foreignBridge = await ForeignBridge.new() homeFee = ether('0.001') }) it('sets variables', async () => { @@ -525,18 +776,123 @@ contract('ForeignBridge', async (accounts) => { expect(await foreignBridge.dailyLimit()).to.be.bignumber.equal(ZERO) expect(await foreignBridge.maxPerTx()).to.be.bignumber.equal(ZERO) - await foreignBridge.rewardableInitialize(ZERO_ADDRESS, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.rewardableInitialize(rewardableValidators.address, ZERO_ADDRESS, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, 0, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.rewardableInitialize(owner, token.address, oneEther, halfEther, minPerTx, requireBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.rewardableInitialize(rewardableValidators.address, owner, oneEther, halfEther, minPerTx, requireBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.rewardableInitialize(rewardableValidators.address, owner, oneEther, halfEther, minPerTx, requireBlockConfirmations, gasPrice, homeDailyLimit, homeMaxPerTx, owner, ZERO_ADDRESS, homeFee).should.be.rejectedWith(ERROR_MSG); - await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee).should.be.fulfilled; + await foreignBridge + .rewardableInitialize( + ZERO_ADDRESS, + token.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + homeDailyLimit, + homeMaxPerTx, + owner, + feeManager.address, + homeFee + ) + .should.be.rejectedWith(ERROR_MSG) + await foreignBridge + .rewardableInitialize( + rewardableValidators.address, + ZERO_ADDRESS, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + homeDailyLimit, + homeMaxPerTx, + owner, + feeManager.address, + homeFee + ) + .should.be.rejectedWith(ERROR_MSG) + await foreignBridge + .rewardableInitialize( + rewardableValidators.address, + token.address, + oneEther, + halfEther, + minPerTx, + 0, + requireBlockConfirmations, + homeDailyLimit, + homeMaxPerTx, + owner, + feeManager.address, + homeFee + ) + .should.be.rejectedWith(ERROR_MSG) + await foreignBridge + .rewardableInitialize( + owner, + token.address, + oneEther, + halfEther, + minPerTx, + requireBlockConfirmations, + gasPrice, + homeDailyLimit, + homeMaxPerTx, + owner, + feeManager.address, + homeFee + ) + .should.be.rejectedWith(ERROR_MSG) + await foreignBridge + .rewardableInitialize( + rewardableValidators.address, + owner, + oneEther, + halfEther, + minPerTx, + requireBlockConfirmations, + gasPrice, + homeDailyLimit, + homeMaxPerTx, + owner, + feeManager.address, + homeFee + ) + .should.be.rejectedWith(ERROR_MSG) + await foreignBridge + .rewardableInitialize( + rewardableValidators.address, + owner, + oneEther, + halfEther, + minPerTx, + requireBlockConfirmations, + gasPrice, + homeDailyLimit, + homeMaxPerTx, + owner, + ZERO_ADDRESS, + homeFee + ) + .should.be.rejectedWith(ERROR_MSG) + await foreignBridge.rewardableInitialize( + rewardableValidators.address, + token.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + homeDailyLimit, + homeMaxPerTx, + owner, + feeManager.address, + homeFee + ).should.be.fulfilled expect(await foreignBridge.isInitialized()).to.be.equal(true) expect(await foreignBridge.validatorContract()).to.be.equal(rewardableValidators.address) expect(await foreignBridge.deployedAtBlock()).to.be.bignumber.above(ZERO) - expect(await foreignBridge.requiredBlockConfirmations()).to.be.bignumber.equal(requireBlockConfirmations.toString()) + expect(await foreignBridge.requiredBlockConfirmations()).to.be.bignumber.equal( + requireBlockConfirmations.toString() + ) expect(await foreignBridge.gasPrice()).to.be.bignumber.equal(gasPrice) expect(await foreignBridge.dailyLimit()).to.be.bignumber.equal(oneEther) expect(await foreignBridge.maxPerTx()).to.be.bignumber.equal(halfEther) @@ -554,7 +910,20 @@ contract('ForeignBridge', async (accounts) => { it('can update fee contract', async () => { const feeManager = await FeeManagerNativeToErc.new() - await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee).should.be.fulfilled; + await foreignBridge.rewardableInitialize( + rewardableValidators.address, + token.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + homeDailyLimit, + homeMaxPerTx, + owner, + feeManager.address, + homeFee + ).should.be.fulfilled // Given const newFeeManager = await FeeManagerNativeToErc.new() @@ -568,7 +937,20 @@ contract('ForeignBridge', async (accounts) => { it('can update fee', async () => { const feeManager = await FeeManagerNativeToErc.new() - await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee).should.be.fulfilled; + await foreignBridge.rewardableInitialize( + rewardableValidators.address, + token.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + homeDailyLimit, + homeMaxPerTx, + owner, + feeManager.address, + homeFee + ).should.be.fulfilled // Given const newHomeFee = ether('0.1') @@ -586,7 +968,20 @@ contract('ForeignBridge', async (accounts) => { const oneDirectionsModeHash = '0xf2aed8f7' // When - await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, homeFee).should.be.fulfilled; + await foreignBridge.rewardableInitialize( + rewardableValidators.address, + token.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + homeDailyLimit, + homeMaxPerTx, + owner, + feeManager.address, + homeFee + ).should.be.fulfilled // Then expect(await foreignBridge.getFeeManagerMode()).to.be.equals(oneDirectionsModeHash) @@ -594,12 +989,15 @@ contract('ForeignBridge', async (accounts) => { }) describe('#RewardableBridge_executeSignatures', async () => { - let feeManager, foreignBridge, token, rewardableValidators + let feeManager + let foreignBridge + let token + let rewardableValidators beforeEach(async () => { feeManager = await FeeManagerNativeToErc.new() - token = await POA20.new("POA ERC20 Foundation", "POA20", 18) + token = await POA20.new('POA ERC20 Foundation', 'POA20', 18) rewardableValidators = await RewardableValidators.new() - foreignBridge = await ForeignBridge.new() + foreignBridge = await ForeignBridge.new() }) it('should distribute fee to validator', async () => { const fee = 0.001 @@ -614,31 +1012,44 @@ contract('ForeignBridge', async (accounts) => { const rewards = [accounts[2]] const requiredSignatures = 1 await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled - await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, feeInWei).should.be.fulfilled; - await token.transferOwnership(foreignBridge.address); + await foreignBridge.rewardableInitialize( + rewardableValidators.address, + token.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + homeDailyLimit, + homeMaxPerTx, + owner, + feeManager.address, + feeInWei + ).should.be.fulfilled + await token.transferOwnership(foreignBridge.address) - const recipientAccount = accounts[3]; + const recipientAccount = accounts[3] const balanceBefore = await token.balanceOf(recipientAccount) const initialBalanceRewardAddress = await token.balanceOf(rewards[0]) const totalSupplyBefore = await token.totalSupply() - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' + const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address) const signature = await sign(validators[0], message) - const vrs = signatureToVRS(signature); + const vrs = signatureToVRS(signature) const { logs } = await foreignBridge.executeSignatures([vrs.v], [vrs.r], [vrs.s], message).should.be.fulfilled - logs[0].event.should.be.equal("FeeDistributedFromSignatures") + logs[0].event.should.be.equal('FeeDistributedFromSignatures') logs[0].args.feeAmount.should.be.bignumber.equal(feeAmount) logs[0].args.transactionHash.should.be.equal(transactionHash) - logs[1].event.should.be.equal("RelayedMessage") + logs[1].event.should.be.equal('RelayedMessage') logs[1].args.recipient.should.be.equal(recipientAccount) logs[1].args.value.should.be.bignumber.equal(value) - logs[1].args.transactionHash.should.be.equal(transactionHash); + logs[1].args.transactionHash.should.be.equal(transactionHash) - const balanceAfter = await token.balanceOf(recipientAccount); - const totalSupplyAfter = await token.totalSupply(); + const balanceAfter = await token.balanceOf(recipientAccount) + const totalSupplyAfter = await token.totalSupply() balanceAfter.should.be.bignumber.equal(balanceBefore.add(finalUserValue)) totalSupplyAfter.should.be.bignumber.equal(totalSupplyBefore.add(value)) @@ -661,10 +1072,23 @@ contract('ForeignBridge', async (accounts) => { const rewards = [accounts[4], accounts[5], accounts[6]] const requiredSignatures = 3 await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled - await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, feeInWei).should.be.fulfilled; - await token.transferOwnership(foreignBridge.address); + await foreignBridge.rewardableInitialize( + rewardableValidators.address, + token.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + homeDailyLimit, + homeMaxPerTx, + owner, + feeManager.address, + feeInWei + ).should.be.fulfilled + await token.transferOwnership(foreignBridge.address) - const recipientAccount = accounts[7]; + const recipientAccount = accounts[7] const balanceBefore = await token.balanceOf(recipientAccount) const totalSupplyBefore = await token.totalSupply() @@ -672,30 +1096,35 @@ contract('ForeignBridge', async (accounts) => { const initialBalanceRewardAddress2 = await token.balanceOf(rewards[1]) const initialBalanceRewardAddress3 = await token.balanceOf(rewards[2]) - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' + const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address) const signature1 = await sign(validators[0], message) const signature2 = await sign(validators[1], message) const signature3 = await sign(validators[2], message) - const vrs = signatureToVRS(signature1); - const vrs2 = signatureToVRS(signature2); - const vrs3 = signatureToVRS(signature3); + const vrs = signatureToVRS(signature1) + const vrs2 = signatureToVRS(signature2) + const vrs3 = signatureToVRS(signature3) // When - const { logs } = await foreignBridge.executeSignatures([vrs.v, vrs2.v, vrs3.v], [vrs.r, vrs2.r, vrs3.r], [vrs.s, vrs2.s, vrs3.s], message).should.be.fulfilled + const { logs } = await foreignBridge.executeSignatures( + [vrs.v, vrs2.v, vrs3.v], + [vrs.r, vrs2.r, vrs3.r], + [vrs.s, vrs2.s, vrs3.s], + message + ).should.be.fulfilled // Then - logs[0].event.should.be.equal("FeeDistributedFromSignatures") + logs[0].event.should.be.equal('FeeDistributedFromSignatures') logs[0].args.feeAmount.should.be.bignumber.equal(feeAmount) logs[0].args.transactionHash.should.be.equal(transactionHash) - logs[1].event.should.be.equal("RelayedMessage") + logs[1].event.should.be.equal('RelayedMessage') logs[1].args.recipient.should.be.equal(recipientAccount) logs[1].args.value.should.be.bignumber.equal(value) - logs[1].args.transactionHash.should.be.equal(transactionHash); + logs[1].args.transactionHash.should.be.equal(transactionHash) - const balanceAfter = await token.balanceOf(recipientAccount); - const totalSupplyAfter = await token.totalSupply(); + const balanceAfter = await token.balanceOf(recipientAccount) + const totalSupplyAfter = await token.totalSupply() balanceAfter.should.be.bignumber.equal(balanceBefore.add(finalUserValue)) totalSupplyAfter.should.be.bignumber.equal(totalSupplyBefore.add(value)) @@ -704,14 +1133,17 @@ contract('ForeignBridge', async (accounts) => { const updatedBalanceRewardAddress3 = await token.balanceOf(rewards[2]) expect( - updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidator)) - || updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidatorPlusDiff))).to.equal(true) + updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidator)) || + updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidatorPlusDiff)) + ).to.equal(true) expect( - updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidator)) - || updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidatorPlusDiff))).to.equal(true) + updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidator)) || + updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidatorPlusDiff)) + ).to.equal(true) expect( - updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidator)) - || updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidatorPlusDiff))).to.equal(true) + updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidator)) || + updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidatorPlusDiff)) + ).to.equal(true) }) it('should distribute fee to 5 validators', async () => { // Given @@ -728,10 +1160,23 @@ contract('ForeignBridge', async (accounts) => { const rewards = [accounts[5], accounts[6], accounts[7], accounts[8], accounts[9]] const requiredSignatures = 3 await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled - await foreignBridge.rewardableInitialize(rewardableValidators.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, homeDailyLimit, homeMaxPerTx, owner, feeManager.address, feeInWei).should.be.fulfilled; - await token.transferOwnership(foreignBridge.address); + await foreignBridge.rewardableInitialize( + rewardableValidators.address, + token.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + homeDailyLimit, + homeMaxPerTx, + owner, + feeManager.address, + feeInWei + ).should.be.fulfilled + await token.transferOwnership(foreignBridge.address) - const recipientAccount = accounts[0]; + const recipientAccount = accounts[0] const balanceBefore = await token.balanceOf(recipientAccount) const totalSupplyBefore = await token.totalSupply() @@ -741,30 +1186,35 @@ contract('ForeignBridge', async (accounts) => { const initialBalanceRewardAddress4 = await token.balanceOf(rewards[3]) const initialBalanceRewardAddress5 = await token.balanceOf(rewards[4]) - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address); + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' + const message = createMessage(recipientAccount, value, transactionHash, foreignBridge.address) const signature1 = await sign(validators[0], message) const signature2 = await sign(validators[1], message) const signature3 = await sign(validators[2], message) - const vrs = signatureToVRS(signature1); - const vrs2 = signatureToVRS(signature2); - const vrs3 = signatureToVRS(signature3); + const vrs = signatureToVRS(signature1) + const vrs2 = signatureToVRS(signature2) + const vrs3 = signatureToVRS(signature3) // When - const { logs } = await foreignBridge.executeSignatures([vrs.v, vrs2.v, vrs3.v], [vrs.r, vrs2.r, vrs3.r], [vrs.s, vrs2.s, vrs3.s], message).should.be.fulfilled + const { logs } = await foreignBridge.executeSignatures( + [vrs.v, vrs2.v, vrs3.v], + [vrs.r, vrs2.r, vrs3.r], + [vrs.s, vrs2.s, vrs3.s], + message + ).should.be.fulfilled // Then - logs[0].event.should.be.equal("FeeDistributedFromSignatures") + logs[0].event.should.be.equal('FeeDistributedFromSignatures') logs[0].args.feeAmount.should.be.bignumber.equal(feeAmount) logs[0].args.transactionHash.should.be.equal(transactionHash) - logs[1].event.should.be.equal("RelayedMessage") + logs[1].event.should.be.equal('RelayedMessage') logs[1].args.recipient.should.be.equal(recipientAccount) logs[1].args.value.should.be.bignumber.equal(value) - logs[1].args.transactionHash.should.be.equal(transactionHash); + logs[1].args.transactionHash.should.be.equal(transactionHash) - const balanceAfter = await token.balanceOf(recipientAccount); - const totalSupplyAfter = await token.totalSupply(); + const balanceAfter = await token.balanceOf(recipientAccount) + const totalSupplyAfter = await token.totalSupply() balanceAfter.should.be.bignumber.equal(balanceBefore.add(finalUserValue)) totalSupplyAfter.should.be.bignumber.equal(totalSupplyBefore.add(value)) diff --git a/test/native_to_erc/home_bridge_test.js b/test/native_to_erc/home_bridge_test.js index e43d0dda0..8fb3d78a7 100644 --- a/test/native_to_erc/home_bridge_test.js +++ b/test/native_to_erc/home_bridge_test.js @@ -1,35 +1,38 @@ -const HomeBridge = artifacts.require("HomeBridgeNativeToErc.sol"); -const EternalStorageProxy = artifacts.require("EternalStorageProxy.sol"); -const BridgeValidators = artifacts.require("BridgeValidators.sol"); -const RevertFallback = artifacts.require("RevertFallback.sol"); -const FeeManagerNativeToErc = artifacts.require("FeeManagerNativeToErc.sol"); -const FeeManagerNativeToErcBothDirections = artifacts.require("FeeManagerNativeToErcBothDirections.sol"); -const RewardableValidators = artifacts.require("RewardableValidators.sol"); - -const { expect } = require('chai'); -const { ERROR_MSG, ZERO_ADDRESS, toBN } = require('../setup'); -const {createMessage, sign, ether, expectEventInLogs} = require('../helpers/helpers'); - -const minPerTx = ether('0.01'); -const requireBlockConfirmations = 8; -const gasPrice = web3.utils.toWei('1', 'gwei'); -const oneEther = ether('1'); -const twoEther = ether('2'); -const halfEther = ether('0.5'); +const HomeBridge = artifacts.require('HomeBridgeNativeToErc.sol') +const EternalStorageProxy = artifacts.require('EternalStorageProxy.sol') +const BridgeValidators = artifacts.require('BridgeValidators.sol') +const RevertFallback = artifacts.require('RevertFallback.sol') +const FeeManagerNativeToErc = artifacts.require('FeeManagerNativeToErc.sol') +const FeeManagerNativeToErcBothDirections = artifacts.require('FeeManagerNativeToErcBothDirections.sol') +const RewardableValidators = artifacts.require('RewardableValidators.sol') + +const { expect } = require('chai') +const { ERROR_MSG, ZERO_ADDRESS, toBN } = require('../setup') +const { createMessage, sign, ether, expectEventInLogs } = require('../helpers/helpers') + +const minPerTx = ether('0.01') +const requireBlockConfirmations = 8 +const gasPrice = web3.utils.toWei('1', 'gwei') +const oneEther = ether('1') +const twoEther = ether('2') +const halfEther = ether('0.5') const foreignDailyLimit = oneEther const foreignMaxPerTx = halfEther const ZERO = toBN(0) -contract('HomeBridge', async (accounts) => { - let homeContract, validatorContract, authorities, owner; +contract('HomeBridge', async accounts => { + let homeContract + let validatorContract + let authorities + let owner before(async () => { validatorContract = await BridgeValidators.new() - authorities = [accounts[1]]; + authorities = [accounts[1]] owner = accounts[0] await validatorContract.initialize(1, authorities, owner) }) - describe('#initialize', async() => { + describe('#initialize', async () => { beforeEach(async () => { homeContract = await HomeBridge.new() }) @@ -40,7 +43,17 @@ contract('HomeBridge', async (accounts) => { expect(await homeContract.maxPerTx()).to.be.bignumber.equal(ZERO) expect(await homeContract.isInitialized()).to.be.equal(false) - await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled; + await homeContract.initialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner + ).should.be.fulfilled expect(await homeContract.isInitialized()).to.be.equal(true) expect(await homeContract.validatorContract()).to.be.equal(validatorContract.address) @@ -58,16 +71,42 @@ contract('HomeBridge', async (accounts) => { }) it('cant set maxPerTx > dailyLimit', async () => { false.should.be.equal(await homeContract.isInitialized()) - await homeContract.initialize(validatorContract.address, '1', '2', '1', gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await homeContract.initialize(validatorContract.address, '3', '2', '2', gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); + await homeContract + .initialize( + validatorContract.address, + '1', + '2', + '1', + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await homeContract + .initialize( + validatorContract.address, + '3', + '2', + '2', + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) false.should.be.equal(await homeContract.isInitialized()) }) it('can be deployed via upgradeToAndCall', async () => { - let storageProxy = await EternalStorageProxy.new().should.be.fulfilled; - let data = homeContract.contract.methods.initialize(validatorContract.address, "3", "2", "1", gasPrice, requireBlockConfirmations, '3', '2', owner).encodeABI() - await storageProxy.upgradeToAndCall('1', homeContract.address, data).should.be.fulfilled; - let finalContract = await HomeBridge.at(storageProxy.address); + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled + const data = homeContract.contract.methods + .initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, '3', '2', owner) + .encodeABI() + await storageProxy.upgradeToAndCall('1', homeContract.address, data).should.be.fulfilled + const finalContract = await HomeBridge.at(storageProxy.address) expect(await finalContract.isInitialized()).to.be.equal(true) expect(await finalContract.validatorContract()).to.be.equal(validatorContract.address) @@ -77,16 +116,54 @@ contract('HomeBridge', async (accounts) => { }) it('cant initialize with invalid arguments', async () => { false.should.be.equal(await homeContract.isInitialized()) - await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, 0, foreignDailyLimit, foreignMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await homeContract.initialize(owner, '3', '2', '1', gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await homeContract.initialize(ZERO_ADDRESS, '3', '2', '1', gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner).should.be.rejectedWith(ERROR_MSG); - await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner).should.be.fulfilled; + await homeContract + .initialize(validatorContract.address, '3', '2', '1', gasPrice, 0, foreignDailyLimit, foreignMaxPerTx, owner) + .should.be.rejectedWith(ERROR_MSG) + await homeContract + .initialize( + owner, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await homeContract + .initialize( + ZERO_ADDRESS, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) + .should.be.rejectedWith(ERROR_MSG) + await homeContract.initialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner + ).should.be.fulfilled true.should.be.equal(await homeContract.isInitialized()) }) it('can transfer ownership', async () => { - let storageProxy = await EternalStorageProxy.new().should.be.fulfilled; - const data = homeContract.contract.methods.initialize(validatorContract.address, "3", "2", "1", gasPrice, requireBlockConfirmations, '3', '2', owner).encodeABI() - await storageProxy.upgradeToAndCall('1', homeContract.address, data).should.be.fulfilled; + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled + const data = homeContract.contract.methods + .initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, '3', '2', owner) + .encodeABI() + await storageProxy.upgradeToAndCall('1', homeContract.address, data).should.be.fulfilled await storageProxy.transferProxyOwnership(owner).should.be.fulfilled }) }) @@ -94,7 +171,17 @@ contract('HomeBridge', async (accounts) => { describe('#fallback', async () => { beforeEach(async () => { homeContract = await HomeBridge.new() - await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner) + await homeContract.initialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) }) it('should accept native coins', async () => { const currentDay = await homeContract.getCurrentDay() @@ -108,12 +195,14 @@ contract('HomeBridge', async (accounts) => { expectEventInLogs(logs, 'UserRequestForSignature', { recipient: accounts[1], value: toBN(1) }) - await homeContract.sendTransaction({ - from: accounts[1], - value: 3 - }).should.be.rejectedWith(ERROR_MSG); + await homeContract + .sendTransaction({ + from: accounts[1], + value: 3 + }) + .should.be.rejectedWith(ERROR_MSG) - await homeContract.setDailyLimit(4).should.be.fulfilled; + await homeContract.setDailyLimit(4).should.be.fulfilled await homeContract.sendTransaction({ from: accounts[1], value: 1 @@ -127,82 +216,109 @@ contract('HomeBridge', async (accounts) => { from: accounts[1], value: 1 }).should.be.fulfilled - await homeContract.sendTransaction({ - from: accounts[1], - value: 3 - }).should.be.rejectedWith(ERROR_MSG) - await homeContract.setMaxPerTx(100).should.be.rejectedWith(ERROR_MSG); - await homeContract.setDailyLimit(100).should.be.fulfilled; - await homeContract.setMaxPerTx(99).should.be.fulfilled; - //meets max per tx and daily limit + await homeContract + .sendTransaction({ + from: accounts[1], + value: 3 + }) + .should.be.rejectedWith(ERROR_MSG) + await homeContract.setMaxPerTx(100).should.be.rejectedWith(ERROR_MSG) + await homeContract.setDailyLimit(100).should.be.fulfilled + await homeContract.setMaxPerTx(99).should.be.fulfilled + // meets max per tx and daily limit await homeContract.sendTransaction({ from: accounts[1], value: 99 }).should.be.fulfilled - //above daily limit - await homeContract.sendTransaction({ - from: accounts[1], - value: 1 - }).should.be.rejectedWith(ERROR_MSG) - + // above daily limit + await homeContract + .sendTransaction({ + from: accounts[1], + value: 1 + }) + .should.be.rejectedWith(ERROR_MSG) }) it('should not let to deposit less than minPerTx', async () => { - const newDailyLimit = 100; - const newMaxPerTx = 50; - const newMinPerTx = 20; - await homeContract.setDailyLimit(newDailyLimit).should.be.fulfilled; - await homeContract.setMaxPerTx(newMaxPerTx).should.be.fulfilled; - await homeContract.setMinPerTx(newMinPerTx).should.be.fulfilled; + const newDailyLimit = 100 + const newMaxPerTx = 50 + const newMinPerTx = 20 + await homeContract.setDailyLimit(newDailyLimit).should.be.fulfilled + await homeContract.setMaxPerTx(newMaxPerTx).should.be.fulfilled + await homeContract.setMinPerTx(newMinPerTx).should.be.fulfilled await homeContract.sendTransaction({ from: accounts[1], value: newMinPerTx }).should.be.fulfilled - await homeContract.sendTransaction({ - from: accounts[1], - value: newMinPerTx - 1 - }).should.be.rejectedWith(ERROR_MSG) + await homeContract + .sendTransaction({ + from: accounts[1], + value: newMinPerTx - 1 + }) + .should.be.rejectedWith(ERROR_MSG) }) }) describe('#setting limits', async () => { - let homeContract; + let homeContract beforeEach(async () => { homeContract = await HomeBridge.new() - await homeContract.initialize(validatorContract.address, '3', '2', '1', gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner) + await homeContract.initialize( + validatorContract.address, + '3', + '2', + '1', + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) }) it('#setMaxPerTx allows to set only to owner and cannot be more than daily limit', async () => { - await homeContract.setMaxPerTx(2, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG); - await homeContract.setMaxPerTx(2, {from: owner}).should.be.fulfilled; + await homeContract.setMaxPerTx(2, { from: authorities[0] }).should.be.rejectedWith(ERROR_MSG) + await homeContract.setMaxPerTx(2, { from: owner }).should.be.fulfilled - await homeContract.setMaxPerTx(3, {from: owner}).should.be.rejectedWith(ERROR_MSG); + await homeContract.setMaxPerTx(3, { from: owner }).should.be.rejectedWith(ERROR_MSG) }) it('#setMinPerTx allows to set only to owner and cannot be more than daily limit and should be less than maxPerTx', async () => { - await homeContract.setMinPerTx(1, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG); - await homeContract.setMinPerTx(1, {from: owner}).should.be.fulfilled; + await homeContract.setMinPerTx(1, { from: authorities[0] }).should.be.rejectedWith(ERROR_MSG) + await homeContract.setMinPerTx(1, { from: owner }).should.be.fulfilled - await homeContract.setMinPerTx(2, {from: owner}).should.be.rejectedWith(ERROR_MSG); + await homeContract.setMinPerTx(2, { from: owner }).should.be.rejectedWith(ERROR_MSG) }) }) describe('#executeAffirmation', async () => { - let homeBridge; + let homeBridge beforeEach(async () => { - homeBridge = await HomeBridge.new(); - await homeBridge.initialize(validatorContract.address, twoEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner); + homeBridge = await HomeBridge.new() + await homeBridge.initialize( + validatorContract.address, + twoEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) await homeBridge.sendTransaction({ from: accounts[2], value: halfEther }).should.be.fulfilled }) it('should allow validator to executeAffirmation', async () => { - const recipient = accounts[5]; - const value = halfEther; + const recipient = accounts[5] + const value = halfEther const balanceBefore = toBN(await web3.eth.getBalance(recipient)) - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - const {logs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}) + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: authorities[0] + }) expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], @@ -218,17 +334,19 @@ contract('HomeBridge', async (accounts) => { balanceAfter.should.be.bignumber.equal(balanceBefore.add(value)) homeBalanceAfter.should.be.bignumber.equal(ZERO) - const msgHash = web3.utils.soliditySha3(recipient, value, transactionHash); + const msgHash = web3.utils.soliditySha3(recipient, value, transactionHash) const senderHash = web3.utils.soliditySha3(authorities[0], msgHash) true.should.be.equal(await homeBridge.affirmationsSigned(senderHash)) }) it('should allow validator to executeAffirmation with zero value', async () => { - const recipient = accounts[5]; + const recipient = accounts[5] const value = ZERO const balanceBefore = toBN(await web3.eth.getBalance(recipient)) - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - const {logs} = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}) + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: authorities[0] + }) expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], @@ -243,18 +361,28 @@ contract('HomeBridge', async (accounts) => { const balanceAfter = toBN(await web3.eth.getBalance(recipient)) balanceAfter.should.be.bignumber.equal(balanceBefore.add(value)) - const msgHash = web3.utils.soliditySha3(recipient, value, transactionHash); + const msgHash = web3.utils.soliditySha3(recipient, value, transactionHash) const senderHash = web3.utils.soliditySha3(authorities[0], msgHash) true.should.be.equal(await homeBridge.affirmationsSigned(senderHash)) }) it('test with 2 signatures required', async () => { - let validatorContractWith2Signatures = await BridgeValidators.new() - let authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]]; - let ownerOfValidators = accounts[0] + const validatorContractWith2Signatures = await BridgeValidators.new() + const authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]] + const ownerOfValidators = accounts[0] await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, ownerOfValidators) - let homeBridgeWithTwoSigs = await HomeBridge.new(); - await homeBridgeWithTwoSigs.initialize(validatorContractWith2Signatures.address, twoEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner); + const homeBridgeWithTwoSigs = await HomeBridge.new() + await homeBridgeWithTwoSigs.initialize( + validatorContractWith2Signatures.address, + twoEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) await homeBridgeWithTwoSigs.sendTransaction({ from: accounts[2], @@ -263,60 +391,88 @@ contract('HomeBridge', async (accounts) => { const homeBalanceBefore = toBN(await web3.eth.getBalance(homeBridgeWithTwoSigs.address)) homeBalanceBefore.should.be.bignumber.equal(halfEther) - const recipient = accounts[5]; - const value = halfEther; - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const recipient = accounts[5] + const value = halfEther + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' const balanceBefore = toBN(await web3.eth.getBalance(recipient)) - const msgHash = web3.utils.soliditySha3(recipient, value, transactionHash); + const msgHash = web3.utils.soliditySha3(recipient, value, transactionHash) - const {logs} = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; + const { logs } = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, { + from: authoritiesThreeAccs[0] + }).should.be.fulfilled expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], transactionHash }) halfEther.should.be.bignumber.equal(await web3.eth.getBalance(homeBridgeWithTwoSigs.address)) - const notProcessed = await homeBridgeWithTwoSigs.numAffirmationsSigned(msgHash); - notProcessed.should.be.bignumber.equal('1'); - - await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[0]}).should.be.rejectedWith(ERROR_MSG); - const secondSignature = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; + const notProcessed = await homeBridgeWithTwoSigs.numAffirmationsSigned(msgHash) + notProcessed.should.be.bignumber.equal('1') + + await homeBridgeWithTwoSigs + .executeAffirmation(recipient, value, transactionHash, { from: authoritiesThreeAccs[0] }) + .should.be.rejectedWith(ERROR_MSG) + const secondSignature = await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, { + from: authoritiesThreeAccs[1] + }).should.be.fulfilled const balanceAfter = toBN(await web3.eth.getBalance(recipient)) balanceAfter.should.be.bignumber.equal(balanceBefore.add(value)) expect(toBN(await web3.eth.getBalance(homeBridgeWithTwoSigs.address))).to.be.bignumber.equal(ZERO) - expectEventInLogs(secondSignature.logs, 'AffirmationCompleted', { recipient, value, transactionHash }) + expectEventInLogs(secondSignature.logs, 'AffirmationCompleted', { + recipient, + value, + transactionHash + }) const senderHash = web3.utils.soliditySha3(authoritiesThreeAccs[0], msgHash) true.should.be.equal(await homeBridgeWithTwoSigs.affirmationsSigned(senderHash)) - const senderHash2 = web3.utils.soliditySha3(authoritiesThreeAccs[1], msgHash); + const senderHash2 = web3.utils.soliditySha3(authoritiesThreeAccs[1], msgHash) true.should.be.equal(await homeBridgeWithTwoSigs.affirmationsSigned(senderHash2)) - const markedAsProcessed = await homeBridgeWithTwoSigs.numAffirmationsSigned(msgHash); - const processed = (toBN(2)).pow(toBN(255)).add(toBN(2)) + const markedAsProcessed = await homeBridgeWithTwoSigs.numAffirmationsSigned(msgHash) + const processed = toBN(2) + .pow(toBN(255)) + .add(toBN(2)) markedAsProcessed.should.be.bignumber.equal(processed) }) it('should not allow to double submit', async () => { - const recipient = accounts[5]; - const value = '1'; - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.fulfilled; - await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG); + const recipient = accounts[5] + const value = '1' + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: authorities[0] + }).should.be.fulfilled + await homeBridge + .executeAffirmation(recipient, value, transactionHash, { from: authorities[0] }) + .should.be.rejectedWith(ERROR_MSG) }) it('should not allow non-authorities to execute withdraw', async () => { - const recipient = accounts[5]; - const value = oneEther; - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: accounts[7]}).should.be.rejectedWith(ERROR_MSG); + const recipient = accounts[5] + const value = oneEther + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + await homeBridge + .executeAffirmation(recipient, value, transactionHash, { from: accounts[7] }) + .should.be.rejectedWith(ERROR_MSG) }) it('doesnt allow to withdraw if requiredSignatures has changed', async () => { - let validatorContractWith2Signatures = await BridgeValidators.new() - let authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]]; - let ownerOfValidators = accounts[0] + const validatorContractWith2Signatures = await BridgeValidators.new() + const authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]] + const ownerOfValidators = accounts[0] await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, ownerOfValidators) - let homeBridgeWithTwoSigs = await HomeBridge.new(); - await homeBridgeWithTwoSigs.initialize(validatorContractWith2Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner); + const homeBridgeWithTwoSigs = await HomeBridge.new() + await homeBridgeWithTwoSigs.initialize( + validatorContractWith2Signatures.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) await homeBridgeWithTwoSigs.sendTransaction({ from: accounts[2], @@ -325,30 +481,40 @@ contract('HomeBridge', async (accounts) => { const homeBalanceBefore = toBN(await web3.eth.getBalance(homeBridgeWithTwoSigs.address)) homeBalanceBefore.should.be.bignumber.equal(halfEther) - const recipient = accounts[5]; - const value = halfEther.div(toBN(2)); - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const recipient = accounts[5] + const value = halfEther.div(toBN(2)) + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' const balanceBefore = toBN(await web3.eth.getBalance(recipient)) - await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; - await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, { + from: authoritiesThreeAccs[0] + }).should.be.fulfilled + await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, { + from: authoritiesThreeAccs[1] + }).should.be.fulfilled expect(toBN(await web3.eth.getBalance(recipient))).to.be.bignumber.equal(balanceBefore.add(value)) - await validatorContractWith2Signatures.setRequiredSignatures(3).should.be.fulfilled; - await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[2]}).should.be.rejectedWith(ERROR_MSG); + await validatorContractWith2Signatures.setRequiredSignatures(3).should.be.fulfilled + await homeBridgeWithTwoSigs + .executeAffirmation(recipient, value, transactionHash, { from: authoritiesThreeAccs[2] }) + .should.be.rejectedWith(ERROR_MSG) - await validatorContractWith2Signatures.setRequiredSignatures(1).should.be.fulfilled; - await homeBridgeWithTwoSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesThreeAccs[2]}).should.be.rejectedWith(ERROR_MSG); + await validatorContractWith2Signatures.setRequiredSignatures(1).should.be.fulfilled + await homeBridgeWithTwoSigs + .executeAffirmation(recipient, value, transactionHash, { from: authoritiesThreeAccs[2] }) + .should.be.rejectedWith(ERROR_MSG) expect(toBN(await web3.eth.getBalance(recipient))).to.be.bignumber.equal(balanceBefore.add(value)) }) it('force withdraw if the recepient has fallback to revert', async () => { - const revertFallbackContract = await RevertFallback.new(); - await revertFallbackContract.receiveEth({from: accounts[0], value: halfEther}) + const revertFallbackContract = await RevertFallback.new() + await revertFallbackContract.receiveEth({ from: accounts[0], value: halfEther }) expect(toBN(await web3.eth.getBalance(revertFallbackContract.address))).to.be.bignumber.equal(halfEther) - const transactionHash = "0x106335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - const {logs} = await homeBridge.executeAffirmation(revertFallbackContract.address, halfEther, transactionHash, {from: authorities[0]}) + const transactionHash = '0x106335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + const { logs } = await homeBridge.executeAffirmation(revertFallbackContract.address, halfEther, transactionHash, { + from: authorities[0] + }) expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], @@ -367,29 +533,45 @@ contract('HomeBridge', async (accounts) => { it('works with 5 validators and 3 required signatures', async () => { const recipient = accounts[8] const authoritiesFiveAccs = [accounts[1], accounts[2], accounts[3], accounts[4], accounts[5]] - let ownerOfValidators = accounts[0] + const ownerOfValidators = accounts[0] const validatorContractWith3Signatures = await BridgeValidators.new() await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) - const homeBridgeWithThreeSigs = await HomeBridge.new(); - await homeBridgeWithThreeSigs.initialize(validatorContractWith3Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner); + const homeBridgeWithThreeSigs = await HomeBridge.new() + await homeBridgeWithThreeSigs.initialize( + validatorContractWith3Signatures.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) const value = halfEther - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' await homeBridgeWithThreeSigs.sendTransaction({ from: recipient, value: halfEther }).should.be.fulfilled - const {logs} = await homeBridgeWithThreeSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesFiveAccs[0]}).should.be.fulfilled; + const { logs } = await homeBridgeWithThreeSigs.executeAffirmation(recipient, value, transactionHash, { + from: authoritiesFiveAccs[0] + }).should.be.fulfilled expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], transactionHash }) - await homeBridgeWithThreeSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesFiveAccs[1]}).should.be.fulfilled; - const thirdSignature = await homeBridgeWithThreeSigs.executeAffirmation(recipient, value, transactionHash, {from: authoritiesFiveAccs[2]}).should.be.fulfilled; + await homeBridgeWithThreeSigs.executeAffirmation(recipient, value, transactionHash, { + from: authoritiesFiveAccs[1] + }).should.be.fulfilled + const thirdSignature = await homeBridgeWithThreeSigs.executeAffirmation(recipient, value, transactionHash, { + from: authoritiesFiveAccs[2] + }).should.be.fulfilled expectEventInLogs(thirdSignature.logs, 'AffirmationCompleted', { recipient, @@ -398,21 +580,24 @@ contract('HomeBridge', async (accounts) => { }) }) it('should not allow execute affirmation over foreign max tx limit', async () => { - const recipient = accounts[5]; - const value = oneEther; - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const recipient = accounts[5] + const value = oneEther + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' - await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG); + await homeBridge + .executeAffirmation(recipient, value, transactionHash, { from: authorities[0] }) + .should.be.rejectedWith(ERROR_MSG) }) it('should not allow execute affirmation over daily foreign limit', async () => { + await homeBridge.sendTransaction({ from: accounts[2], value: halfEther }).should.be.fulfilled + await homeBridge.sendTransaction({ from: accounts[2], value: halfEther }).should.be.fulfilled - await homeBridge.sendTransaction({ from: accounts[2], value: halfEther }).should.be.fulfilled; - await homeBridge.sendTransaction({ from: accounts[2], value: halfEther }).should.be.fulfilled; - - const recipient = accounts[5]; - const value = halfEther; - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; - const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: authorities[0]}).should.be.fulfilled; + const recipient = accounts[5] + const value = halfEther + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: authorities[0] + }).should.be.fulfilled expectEventInLogs(logs, 'SignedForAffirmation', { signer: authorities[0], @@ -424,8 +609,10 @@ contract('HomeBridge', async (accounts) => { transactionHash }) - const transactionHash2 = "0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121"; - const { logs: logs2 } = await homeBridge.executeAffirmation(recipient, value, transactionHash2, {from: authorities[0]}).should.be.fulfilled; + const transactionHash2 = '0x35d3818e50234655f6aebb2a1cfbf30f59568d8a4ec72066fac5a25dbe7b8121' + const { logs: logs2 } = await homeBridge.executeAffirmation(recipient, value, transactionHash2, { + from: authorities[0] + }).should.be.fulfilled expectEventInLogs(logs2, 'SignedForAffirmation', { signer: authorities[0], @@ -437,61 +624,86 @@ contract('HomeBridge', async (accounts) => { transactionHash: transactionHash2 }) - const transactionHash3 = "0x69debd8fd1923c9cb3cd8ef6461e2740b2d037943b941729d5a47671a2bb8712"; - await homeBridge.executeAffirmation(recipient, value, transactionHash3, {from: authorities[0]}).should.be.rejectedWith(ERROR_MSG); + const transactionHash3 = '0x69debd8fd1923c9cb3cd8ef6461e2740b2d037943b941729d5a47671a2bb8712' + await homeBridge + .executeAffirmation(recipient, value, transactionHash3, { from: authorities[0] }) + .should.be.rejectedWith(ERROR_MSG) }) }) describe('#isAlreadyProcessed', async () => { it('returns ', async () => { - const homeBridge = await HomeBridge.new(); - const bn = new toBN(2).pow(toBN(255)); - const processedNumbers = [bn.add(toBN(1)).toString(10), bn.add(toBN(100)).toString(10)]; - true.should.be.equal(await homeBridge.isAlreadyProcessed(processedNumbers[0])); - true.should.be.equal(await homeBridge.isAlreadyProcessed(processedNumbers[1])); - false.should.be.equal(await homeBridge.isAlreadyProcessed(10)); + const homeBridge = await HomeBridge.new() + const bn = toBN(2).pow(toBN(255)) + const processedNumbers = [bn.add(toBN(1)).toString(10), bn.add(toBN(100)).toString(10)] + true.should.be.equal(await homeBridge.isAlreadyProcessed(processedNumbers[0])) + true.should.be.equal(await homeBridge.isAlreadyProcessed(processedNumbers[1])) + false.should.be.equal(await homeBridge.isAlreadyProcessed(10)) }) }) describe('#submitSignature', async () => { - let validatorContractWith2Signatures,authoritiesThreeAccs,ownerOfValidators,homeBridgeWithTwoSigs + let validatorContractWith2Signatures + let authoritiesThreeAccs + let ownerOfValidators + let homeBridgeWithTwoSigs beforeEach(async () => { validatorContractWith2Signatures = await BridgeValidators.new() - authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]]; + authoritiesThreeAccs = [accounts[1], accounts[2], accounts[3]] ownerOfValidators = accounts[0] await validatorContractWith2Signatures.initialize(2, authoritiesThreeAccs, ownerOfValidators) - homeBridgeWithTwoSigs = await HomeBridge.new(); - await homeBridgeWithTwoSigs.initialize(validatorContractWith2Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner); + homeBridgeWithTwoSigs = await HomeBridge.new() + await homeBridgeWithTwoSigs.initialize( + validatorContractWith2Signatures.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) }) it('allows a validator to submit a signature', async () => { const recipientAccount = accounts[8] const value = halfEther - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' + const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address) const signature = await sign(authoritiesThreeAccs[0], message) - const {logs} = await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authorities[0]}).should.be.fulfilled; + const { logs } = await homeBridgeWithTwoSigs.submitSignature(signature, message, { + from: authorities[0] + }).should.be.fulfilled logs[0].event.should.be.equal('SignedForUserRequest') const msgHashFromLog = logs[0].args.messageHash - const signatureFromContract = await homeBridgeWithTwoSigs.signature(msgHashFromLog, 0); - const messageFromContract = await homeBridgeWithTwoSigs.message(msgHashFromLog); - signature.should.be.equal(signatureFromContract); - messageFromContract.should.be.equal(messageFromContract); - const hashMsg = web3.utils.soliditySha3(message); + const signatureFromContract = await homeBridgeWithTwoSigs.signature(msgHashFromLog, 0) + const messageFromContract = await homeBridgeWithTwoSigs.message(msgHashFromLog) + signature.should.be.equal(signatureFromContract) + messageFromContract.should.be.equal(messageFromContract) + const hashMsg = web3.utils.soliditySha3(message) const hashSenderMsg = web3.utils.soliditySha3(authorities[0], hashMsg) - true.should.be.equal(await homeBridgeWithTwoSigs.messagesSigned(hashSenderMsg)); + true.should.be.equal(await homeBridgeWithTwoSigs.messagesSigned(hashSenderMsg)) }) it('when enough requiredSignatures are collected, CollectedSignatures event is emitted', async () => { const recipientAccount = accounts[8] const value = halfEther - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' + const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address) const signature = await sign(authoritiesThreeAccs[0], message) const signature2 = await sign(authoritiesThreeAccs[1], message) - expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('2'); - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.rejectedWith(ERROR_MSG); - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[1]}).should.be.rejectedWith(ERROR_MSG); - const {logs} = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; + expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('2') + await homeBridgeWithTwoSigs.submitSignature(signature, message, { + from: authoritiesThreeAccs[0] + }).should.be.fulfilled + await homeBridgeWithTwoSigs + .submitSignature(signature, message, { from: authoritiesThreeAccs[0] }) + .should.be.rejectedWith(ERROR_MSG) + await homeBridgeWithTwoSigs + .submitSignature(signature, message, { from: authoritiesThreeAccs[1] }) + .should.be.rejectedWith(ERROR_MSG) + const { logs } = await homeBridgeWithTwoSigs.submitSignature(signature2, message, { + from: authoritiesThreeAccs[1] + }).should.be.fulfilled logs.length.should.be.equal(2) logs[1].event.should.be.equal('CollectedSignatures') logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesThreeAccs[1]) @@ -502,20 +714,36 @@ contract('HomeBridge', async (accounts) => { const validatorContractWith3Signatures = await BridgeValidators.new() await validatorContractWith3Signatures.initialize(3, authoritiesFiveAccs, ownerOfValidators) - const homeBridgeWithThreeSigs = await HomeBridge.new(); - await homeBridgeWithThreeSigs.initialize(validatorContractWith3Signatures.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner); + const homeBridgeWithThreeSigs = await HomeBridge.new() + await homeBridgeWithThreeSigs.initialize( + validatorContractWith3Signatures.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner + ) const value = halfEther - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithThreeSigs.address); + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' + const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithThreeSigs.address) const signature = await sign(authoritiesFiveAccs[0], message) const signature2 = await sign(authoritiesFiveAccs[1], message) const signature3 = await sign(authoritiesFiveAccs[2], message) - expect(await validatorContractWith3Signatures.requiredSignatures()).to.be.bignumber.equal('3'); + expect(await validatorContractWith3Signatures.requiredSignatures()).to.be.bignumber.equal('3') - await homeBridgeWithThreeSigs.submitSignature(signature, message, {from: authoritiesFiveAccs[0]}).should.be.fulfilled; - await homeBridgeWithThreeSigs.submitSignature(signature2, message, {from: authoritiesFiveAccs[1]}).should.be.fulfilled; - const {logs} = await homeBridgeWithThreeSigs.submitSignature(signature3, message, {from: authoritiesFiveAccs[2]}).should.be.fulfilled; + await homeBridgeWithThreeSigs.submitSignature(signature, message, { + from: authoritiesFiveAccs[0] + }).should.be.fulfilled + await homeBridgeWithThreeSigs.submitSignature(signature2, message, { + from: authoritiesFiveAccs[1] + }).should.be.fulfilled + const { logs } = await homeBridgeWithThreeSigs.submitSignature(signature3, message, { + from: authoritiesFiveAccs[2] + }).should.be.fulfilled logs.length.should.be.equal(2) logs[1].event.should.be.equal('CollectedSignatures') logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesFiveAccs[2]) @@ -523,40 +751,54 @@ contract('HomeBridge', async (accounts) => { it('attack when increasing requiredSignatures', async () => { const recipientAccount = accounts[8] const value = halfEther - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' + const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address) const signature = await sign(authoritiesThreeAccs[0], message) const signature2 = await sign(authoritiesThreeAccs[1], message) const signature3 = await sign(authoritiesThreeAccs[2], message) - expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('2'); + expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('2') - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.rejectedWith(ERROR_MSG); - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[1]}).should.be.rejectedWith(ERROR_MSG); - const {logs} = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.submitSignature(signature, message, { + from: authoritiesThreeAccs[0] + }).should.be.fulfilled + await homeBridgeWithTwoSigs + .submitSignature(signature, message, { from: authoritiesThreeAccs[0] }) + .should.be.rejectedWith(ERROR_MSG) + await homeBridgeWithTwoSigs + .submitSignature(signature, message, { from: authoritiesThreeAccs[1] }) + .should.be.rejectedWith(ERROR_MSG) + const { logs } = await homeBridgeWithTwoSigs.submitSignature(signature2, message, { + from: authoritiesThreeAccs[1] + }).should.be.fulfilled logs.length.should.be.equal(2) logs[1].event.should.be.equal('CollectedSignatures') logs[1].args.authorityResponsibleForRelay.should.be.equal(authoritiesThreeAccs[1]) - await validatorContractWith2Signatures.setRequiredSignatures(3).should.be.fulfilled; - expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('3'); + await validatorContractWith2Signatures.setRequiredSignatures(3).should.be.fulfilled + expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('3') - await homeBridgeWithTwoSigs.submitSignature(signature3, message, {from: authoritiesThreeAccs[2]}).should.be.rejectedWith(ERROR_MSG); + await homeBridgeWithTwoSigs + .submitSignature(signature3, message, { from: authoritiesThreeAccs[2] }) + .should.be.rejectedWith(ERROR_MSG) }) it('attack when decreasing requiredSignatures', async () => { const recipientAccount = accounts[8] const value = halfEther - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80"; - const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address); + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' + const message = createMessage(recipientAccount, value, transactionHash, homeBridgeWithTwoSigs.address) const signature = await sign(authoritiesThreeAccs[0], message) const signature2 = await sign(authoritiesThreeAccs[1], message) - expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('2'); + expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('2') - await homeBridgeWithTwoSigs.submitSignature(signature, message, {from: authoritiesThreeAccs[0]}).should.be.fulfilled; - await validatorContractWith2Signatures.setRequiredSignatures(1).should.be.fulfilled; - expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('1'); - const { logs } = await homeBridgeWithTwoSigs.submitSignature(signature2, message, {from: authoritiesThreeAccs[1]}).should.be.fulfilled; + await homeBridgeWithTwoSigs.submitSignature(signature, message, { + from: authoritiesThreeAccs[0] + }).should.be.fulfilled + await validatorContractWith2Signatures.setRequiredSignatures(1).should.be.fulfilled + expect(await validatorContractWith2Signatures.requiredSignatures()).to.be.bignumber.equal('1') + const { logs } = await homeBridgeWithTwoSigs.submitSignature(signature2, message, { + from: authoritiesThreeAccs[1] + }).should.be.fulfilled logs.length.should.be.equal(2) logs[1].event.should.be.equal('CollectedSignatures') @@ -574,15 +816,18 @@ contract('HomeBridge', async (accounts) => { }) }) - describe('#rewardableInitialize', async() => { - let homeFee, foreignFee, homeBridge, rewardableValidators - let validators = [accounts[1]] - let rewards = [accounts[2]] - let requiredSignatures = 1 + describe('#rewardableInitialize', async () => { + let homeFee + let foreignFee + let homeBridge + let rewardableValidators + const validators = [accounts[1]] + const rewards = [accounts[2]] + const requiredSignatures = 1 beforeEach(async () => { rewardableValidators = await RewardableValidators.new() await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner).should.be.fulfilled - homeBridge = await HomeBridge.new() + homeBridge = await HomeBridge.new() homeFee = ZERO foreignFee = ether('0.002') }) @@ -594,11 +839,84 @@ contract('HomeBridge', async (accounts) => { expect(await homeBridge.maxPerTx()).to.be.bignumber.equal(ZERO) expect(await homeBridge.isInitialized()).to.be.equal(false) - await homeBridge.rewardableInitialize(ZERO_ADDRESS, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, 0, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, 0, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, ZERO_ADDRESS, homeFee, foreignFee).should.be.rejectedWith(ERROR_MSG); - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + await homeBridge + .rewardableInitialize( + ZERO_ADDRESS, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + homeFee, + foreignFee + ) + .should.be.rejectedWith(ERROR_MSG) + await homeBridge + .rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + 0, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + homeFee, + foreignFee + ) + .should.be.rejectedWith(ERROR_MSG) + await homeBridge + .rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + 0, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + homeFee, + foreignFee + ) + .should.be.rejectedWith(ERROR_MSG) + await homeBridge + .rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner, + ZERO_ADDRESS, + homeFee, + foreignFee + ) + .should.be.rejectedWith(ERROR_MSG) + await homeBridge.rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + homeFee, + foreignFee + ).should.be.fulfilled expect(await homeBridge.isInitialized()).to.be.equal(true) expect(await homeBridge.validatorContract()).to.be.equal(rewardableValidators.address) @@ -622,7 +940,20 @@ contract('HomeBridge', async (accounts) => { it('can update fee contract', async () => { const feeManager = await FeeManagerNativeToErc.new() - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + await homeBridge.rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + homeFee, + foreignFee + ).should.be.fulfilled // Given const newFeeManager = await FeeManagerNativeToErc.new() @@ -637,7 +968,20 @@ contract('HomeBridge', async (accounts) => { it('can update fee', async () => { const feeManager = await FeeManagerNativeToErc.new() - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + await homeBridge.rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + homeFee, + foreignFee + ).should.be.fulfilled // Given const newForeignFee = ether('0.2') @@ -655,7 +999,20 @@ contract('HomeBridge', async (accounts) => { const oneDirectionsModeHash = '0xf2aed8f7' // When - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, homeFee, foreignFee).should.be.fulfilled; + await homeBridge.rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + homeFee, + foreignFee + ).should.be.fulfilled // Then const feeManagerMode = await homeBridge.getFeeManagerMode() @@ -672,8 +1029,10 @@ contract('HomeBridge', async (accounts) => { const rewards = [accounts[2]] const requiredSignatures = 1 const rewardableValidators = await RewardableValidators.new() - const homeBridge = await HomeBridge.new(); - await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + const homeBridge = await HomeBridge.new() + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, { + from: owner + }).should.be.fulfilled const feeManager = await FeeManagerNativeToErc.new() // Given @@ -681,20 +1040,33 @@ contract('HomeBridge', async (accounts) => { const fee = 0.001 const feeInWei = ether(fee.toString()) const notUsedFee = ZERO - const value = halfEther; + const value = halfEther - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, notUsedFee, feeInWei).should.be.fulfilled; + await homeBridge.rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + notUsedFee, + feeInWei + ).should.be.fulfilled // When const { logs } = await homeBridge.sendTransaction({ from: user, - value: value + value }).should.be.fulfilled // Then expectEventInLogs(logs, 'UserRequestForSignature', { recipient: user, - value: value + value }) }) }) @@ -708,8 +1080,10 @@ contract('HomeBridge', async (accounts) => { const rewards = [accounts[2]] const requiredSignatures = 1 const rewardableValidators = await RewardableValidators.new() - const homeBridge = await HomeBridge.new(); - await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + const homeBridge = await HomeBridge.new() + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, { + from: owner + }).should.be.fulfilled const feeManager = await FeeManagerNativeToErc.new() // Given @@ -717,22 +1091,35 @@ contract('HomeBridge', async (accounts) => { const fee = 0.001 const feeInWei = ether(fee.toString()) const notUsedFee = ZERO - const value = halfEther; + const value = halfEther const rewardAddressBalanceBefore = await web3.eth.getBalance(rewards[0]) - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, notUsedFee, feeInWei).should.be.fulfilled; + await homeBridge.rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + notUsedFee, + feeInWei + ).should.be.fulfilled await homeBridge.sendTransaction({ from: user, - value: value + value }).should.be.fulfilled // When - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80" + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' const message = createMessage(user, value, transactionHash, homeBridge.address) const signature = await sign(validators[0], message) - const { logs } = await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled + const { logs } = await homeBridge.submitSignature(signature, message, { from: validators[0] }).should.be.fulfilled // Then logs.length.should.be.equal(2) @@ -754,8 +1141,10 @@ contract('HomeBridge', async (accounts) => { const rewards = [accounts[2]] const requiredSignatures = 1 const rewardableValidators = await RewardableValidators.new() - const homeBridge = await HomeBridge.new(); - await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + const homeBridge = await HomeBridge.new() + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, { + from: owner + }).should.be.fulfilled const feeManager = await FeeManagerNativeToErc.new() // Given @@ -763,26 +1152,40 @@ contract('HomeBridge', async (accounts) => { const fee = 0.001 const feeInWei = ether(fee.toString()) const notUsedFee = ZERO - const value = halfEther; + const value = halfEther const valueCalc = 0.5 * (1 - fee) const finalUserValue = ether(valueCalc.toString()) const feeAmountCalc = 0.5 * fee const feeAmount = ether(feeAmountCalc.toString()) - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, notUsedFee, feeInWei).should.be.fulfilled; + await homeBridge.rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + notUsedFee, + feeInWei + ).should.be.fulfilled await homeBridge.sendTransaction({ from: accounts[0], value: halfEther }).should.be.fulfilled - - const recipient = accounts[5]; + const recipient = accounts[5] const balanceBefore = toBN(await web3.eth.getBalance(recipient)) const rewardAddressBalanceBefore = toBN(await web3.eth.getBalance(rewards[0])) - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' // When - const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[0] + }).should.be.fulfilled // Then expectEventInLogs(logs, 'SignedForAffirmation', { @@ -813,7 +1216,7 @@ contract('HomeBridge', async (accounts) => { const requiredSignatures = 2 const rewardableValidators = await RewardableValidators.new() - const value = halfEther; + const value = halfEther // 0.1% fee const fee = 0.001 const feeInWei = ether(fee.toString()) @@ -827,25 +1230,44 @@ contract('HomeBridge', async (accounts) => { const homeBridge = await HomeBridge.new() const feeManager = await FeeManagerNativeToErc.new() - await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, notUsedFee, feeInWei).should.be.fulfilled; + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, { + from: owner + }).should.be.fulfilled + await homeBridge.rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + notUsedFee, + feeInWei + ).should.be.fulfilled await homeBridge.sendTransaction({ from: accounts[0], value: halfEther }).should.be.fulfilled - const recipient = accounts[8]; + const recipient = accounts[8] const balanceBefore = toBN(await web3.eth.getBalance(recipient)) const initialBalanceRewardAddress1 = toBN(await web3.eth.getBalance(rewards[0])) const initialBalanceRewardAddress2 = toBN(await web3.eth.getBalance(rewards[1])) const initialBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' // When - const { logs: logsValidator1 } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled - const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[1]}).should.be.fulfilled + const { logs: logsValidator1 } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[0] + }).should.be.fulfilled + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[1] + }).should.be.fulfilled // Then logsValidator1.length.should.be.equals(1) @@ -872,14 +1294,17 @@ contract('HomeBridge', async (accounts) => { const updatedBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) expect( - updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidator)) - || updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidatorPlusDiff))).to.equal(true) + updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidator)) || + updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidatorPlusDiff)) + ).to.equal(true) expect( - updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidator)) - || updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidatorPlusDiff))).to.equal(true) + updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidator)) || + updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidatorPlusDiff)) + ).to.equal(true) expect( - updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidator)) - || updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidatorPlusDiff))).to.equal(true) + updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidator)) || + updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidatorPlusDiff)) + ).to.equal(true) const homeBridgeBalance = toBN(await web3.eth.getBalance(homeBridge.address)) homeBridgeBalance.should.be.bignumber.equal(ZERO) @@ -891,7 +1316,7 @@ contract('HomeBridge', async (accounts) => { const rewards = [accounts[5], accounts[6], accounts[7], accounts[8], accounts[9]] const requiredSignatures = 5 - const value = halfEther; + const value = halfEther // 0.1% fee const fee = 0.001 const feeInWei = ether(fee.toString()) @@ -903,14 +1328,29 @@ contract('HomeBridge', async (accounts) => { const rewardableValidators = await RewardableValidators.new() const homeBridge = await HomeBridge.new() const feeManager = await FeeManagerNativeToErc.new() - await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, notUsedFee, feeInWei).should.be.fulfilled; + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, { + from: owner + }).should.be.fulfilled + await homeBridge.rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + notUsedFee, + feeInWei + ).should.be.fulfilled await homeBridge.sendTransaction({ from: accounts[0], value: halfEther }).should.be.fulfilled - const recipient = "0xf4BEF13F9f4f2B203FAF0C3cBbaAbe1afE056955"; + const recipient = '0xf4BEF13F9f4f2B203FAF0C3cBbaAbe1afE056955' const balanceBefore = toBN(await web3.eth.getBalance(recipient)) const initialBalanceRewardAddress1 = toBN(await web3.eth.getBalance(rewards[0])) @@ -919,15 +1359,24 @@ contract('HomeBridge', async (accounts) => { const initialBalanceRewardAddress4 = toBN(await web3.eth.getBalance(rewards[3])) const initialBalanceRewardAddress5 = toBN(await web3.eth.getBalance(rewards[4])) - - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' // When - const { logs: logsValidator1 } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled - await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[1]}).should.be.fulfilled - await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[2]}).should.be.fulfilled - await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[3]}).should.be.fulfilled - const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[4]}).should.be.fulfilled + const { logs: logsValidator1 } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[0] + }).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[1] + }).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[2] + }).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[3] + }).should.be.fulfilled + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[4] + }).should.be.fulfilled // Then logsValidator1.length.should.be.equals(1) @@ -972,22 +1421,37 @@ contract('HomeBridge', async (accounts) => { const rewards = [accounts[2]] const requiredSignatures = 1 const rewardableValidators = await RewardableValidators.new() - const homeBridge = await HomeBridge.new(); - await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + const homeBridge = await HomeBridge.new() + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, { + from: owner + }).should.be.fulfilled const feeManager = await FeeManagerNativeToErcBothDirections.new() // Given // 0.1% fee const fee = 0.001 const feeInWei = ether(fee.toString()) - const value = halfEther; + const value = halfEther - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei, feeInWei).should.be.fulfilled; + await homeBridge.rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + feeInWei, + feeInWei + ).should.be.fulfilled // When const { logs } = await homeBridge.sendTransaction({ from: user, - value: value + value }).should.be.fulfilled // Then @@ -1009,8 +1473,10 @@ contract('HomeBridge', async (accounts) => { const rewards = [accounts[2]] const requiredSignatures = 1 const rewardableValidators = await RewardableValidators.new() - const homeBridge = await HomeBridge.new(); - await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + const homeBridge = await HomeBridge.new() + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, { + from: owner + }).should.be.fulfilled const feeManager = await FeeManagerNativeToErcBothDirections.new() // Given @@ -1025,7 +1491,20 @@ contract('HomeBridge', async (accounts) => { const rewardAddressBalanceBefore = toBN(await web3.eth.getBalance(rewards[0])) - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei, feeInWei).should.be.fulfilled; + await homeBridge.rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + feeInWei, + feeInWei + ).should.be.fulfilled await homeBridge.sendTransaction({ from: user, @@ -1033,10 +1512,10 @@ contract('HomeBridge', async (accounts) => { }).should.be.fulfilled // When - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80" + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' const message = createMessage(user, value, transactionHash, homeBridge.address) const signature = await sign(validators[0], message) - const { logs } = await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled + const { logs } = await homeBridge.submitSignature(signature, message, { from: validators[0] }).should.be.fulfilled // Then logs.length.should.be.equal(3) @@ -1060,8 +1539,10 @@ contract('HomeBridge', async (accounts) => { const rewards = [accounts[4], accounts[5], accounts[6]] const requiredSignatures = 3 const rewardableValidators = await RewardableValidators.new() - const homeBridge = await HomeBridge.new(); - await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + const homeBridge = await HomeBridge.new() + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, { + from: owner + }).should.be.fulfilled const feeManager = await FeeManagerNativeToErcBothDirections.new() // Given @@ -1076,7 +1557,20 @@ contract('HomeBridge', async (accounts) => { const feeAmountCalc = 0.5 * fee const feeAmount = ether(feeAmountCalc.toString()) - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei, feeInWei).should.be.fulfilled; + await homeBridge.rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + feeInWei, + feeInWei + ).should.be.fulfilled await homeBridge.sendTransaction({ from: user, @@ -1088,15 +1582,17 @@ contract('HomeBridge', async (accounts) => { const initialBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) // When - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80" + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' const message = createMessage(user, value, transactionHash, homeBridge.address) const signature = await sign(validators[0], message) const signature2 = await sign(validators[1], message) const signature3 = await sign(validators[2], message) - await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled; - await homeBridge.submitSignature(signature2, message, {from: validators[1]}).should.be.fulfilled; - const { logs } = await homeBridge.submitSignature(signature3, message, {from: validators[2]}).should.be.fulfilled; + await homeBridge.submitSignature(signature, message, { from: validators[0] }).should.be.fulfilled + await homeBridge.submitSignature(signature2, message, { from: validators[1] }).should.be.fulfilled + const { logs } = await homeBridge.submitSignature(signature3, message, { + from: validators[2] + }).should.be.fulfilled // Then logs.length.should.be.equal(3) @@ -1111,14 +1607,17 @@ contract('HomeBridge', async (accounts) => { const updatedBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) expect( - updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidator)) - || updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidatorPlusDiff))).to.equal(true) + updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidator)) || + updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidatorPlusDiff)) + ).to.equal(true) expect( - updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidator)) - || updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidatorPlusDiff))).to.equal(true) + updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidator)) || + updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidatorPlusDiff)) + ).to.equal(true) expect( - updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidator)) - || updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidatorPlusDiff))).to.equal(true) + updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidator)) || + updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidatorPlusDiff)) + ).to.equal(true) }) it('should distribute fee to 5 validators', async () => { // Initialize @@ -1128,8 +1627,10 @@ contract('HomeBridge', async (accounts) => { const rewards = [accounts[5], accounts[6], accounts[7], accounts[8], accounts[9]] const requiredSignatures = 5 const rewardableValidators = await RewardableValidators.new() - const homeBridge = await HomeBridge.new(); - await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + const homeBridge = await HomeBridge.new() + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, { + from: owner + }).should.be.fulfilled const feeManager = await FeeManagerNativeToErcBothDirections.new() // Given @@ -1143,7 +1644,20 @@ contract('HomeBridge', async (accounts) => { const feeAmount = ether(feeAmountCalc.toString()) const feePerValidator = feeAmount.div(toBN(5)) - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei, feeInWei).should.be.fulfilled; + await homeBridge.rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + feeInWei, + feeInWei + ).should.be.fulfilled await homeBridge.sendTransaction({ from: user, @@ -1157,7 +1671,7 @@ contract('HomeBridge', async (accounts) => { const initialBalanceRewardAddress5 = toBN(await web3.eth.getBalance(rewards[4])) // When - const transactionHash = "0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80" + const transactionHash = '0x1045bfe274b88120a6b1e5d01b5ec00ab5d01098346e90e7c7a3c9b8f0181c80' const message = createMessage(user, value, transactionHash, homeBridge.address) const signature = await sign(validators[0], message) const signature2 = await sign(validators[1], message) @@ -1165,11 +1679,13 @@ contract('HomeBridge', async (accounts) => { const signature4 = await sign(validators[3], message) const signature5 = await sign(validators[4], message) - await homeBridge.submitSignature(signature, message, {from: validators[0]}).should.be.fulfilled; - await homeBridge.submitSignature(signature2, message, {from: validators[1]}).should.be.fulfilled; - await homeBridge.submitSignature(signature3, message, {from: validators[2]}).should.be.fulfilled; - await homeBridge.submitSignature(signature4, message, {from: validators[3]}).should.be.fulfilled; - const { logs } = await homeBridge.submitSignature(signature5, message, {from: validators[4]}).should.be.fulfilled; + await homeBridge.submitSignature(signature, message, { from: validators[0] }).should.be.fulfilled + await homeBridge.submitSignature(signature2, message, { from: validators[1] }).should.be.fulfilled + await homeBridge.submitSignature(signature3, message, { from: validators[2] }).should.be.fulfilled + await homeBridge.submitSignature(signature4, message, { from: validators[3] }).should.be.fulfilled + const { logs } = await homeBridge.submitSignature(signature5, message, { + from: validators[4] + }).should.be.fulfilled // Then logs.length.should.be.equal(3) @@ -1201,34 +1717,50 @@ contract('HomeBridge', async (accounts) => { const rewards = [accounts[2]] const requiredSignatures = 1 const rewardableValidators = await RewardableValidators.new() - const homeBridge = await HomeBridge.new(); - await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + const homeBridge = await HomeBridge.new() + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, { + from: owner + }).should.be.fulfilled const feeManager = await FeeManagerNativeToErcBothDirections.new() // Given // 0.1% fee const fee = 0.001 const feeInWei = ether(fee.toString()) - const value = halfEther; + const value = halfEther const valueCalc = 0.5 * (1 - fee) const finalUserValue = ether(valueCalc.toString()) const feeAmountCalc = 0.5 * fee const feeAmount = ether(feeAmountCalc.toString()) - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei, feeInWei).should.be.fulfilled; + await homeBridge.rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + feeInWei, + feeInWei + ).should.be.fulfilled await homeBridge.sendTransaction({ from: accounts[0], value: halfEther }).should.be.fulfilled - - const recipient = accounts[5]; + const recipient = accounts[5] const balanceBefore = toBN(await web3.eth.getBalance(recipient)) const rewardAddressBalanceBefore = toBN(await web3.eth.getBalance(rewards[0])) - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' // When - const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[0] + }).should.be.fulfilled // Then expectEventInLogs(logs, 'SignedForAffirmation', { @@ -1259,7 +1791,7 @@ contract('HomeBridge', async (accounts) => { const requiredSignatures = 2 const rewardableValidators = await RewardableValidators.new() - const value = halfEther; + const value = halfEther // 0.1% fee const fee = 0.001 const feeInWei = ether(fee.toString()) @@ -1272,25 +1804,44 @@ contract('HomeBridge', async (accounts) => { const homeBridge = await HomeBridge.new() const feeManager = await FeeManagerNativeToErcBothDirections.new() - await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei, feeInWei).should.be.fulfilled; + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, { + from: owner + }).should.be.fulfilled + await homeBridge.rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + feeInWei, + feeInWei + ).should.be.fulfilled await homeBridge.sendTransaction({ from: accounts[0], value: halfEther }).should.be.fulfilled - const recipient = accounts[8]; + const recipient = accounts[8] const balanceBefore = toBN(await web3.eth.getBalance(recipient)) const initialBalanceRewardAddress1 = toBN(await web3.eth.getBalance(rewards[0])) const initialBalanceRewardAddress2 = toBN(await web3.eth.getBalance(rewards[1])) const initialBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' // When - const { logs: logsValidator1 } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled - const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[1]}).should.be.fulfilled + const { logs: logsValidator1 } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[0] + }).should.be.fulfilled + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[1] + }).should.be.fulfilled // Then logsValidator1.length.should.be.equals(1) @@ -1317,14 +1868,17 @@ contract('HomeBridge', async (accounts) => { const updatedBalanceRewardAddress3 = toBN(await web3.eth.getBalance(rewards[2])) expect( - updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidator)) - || updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidatorPlusDiff))).to.equal(true) + updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidator)) || + updatedBalanceRewardAddress1.eq(initialBalanceRewardAddress1.add(feePerValidatorPlusDiff)) + ).to.equal(true) expect( - updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidator)) - || updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidatorPlusDiff))).to.equal(true) + updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidator)) || + updatedBalanceRewardAddress2.eq(initialBalanceRewardAddress2.add(feePerValidatorPlusDiff)) + ).to.equal(true) expect( - updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidator)) - || updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidatorPlusDiff))).to.equal(true) + updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidator)) || + updatedBalanceRewardAddress3.eq(initialBalanceRewardAddress3.add(feePerValidatorPlusDiff)) + ).to.equal(true) const homeBridgeBalance = toBN(await web3.eth.getBalance(homeBridge.address)) homeBridgeBalance.should.be.bignumber.equal('0') @@ -1336,7 +1890,7 @@ contract('HomeBridge', async (accounts) => { const rewards = [accounts[5], accounts[6], accounts[7], accounts[8], accounts[9]] const requiredSignatures = 5 - const value = halfEther; + const value = halfEther // 0.1% fee const fee = 0.001 const feeInWei = ether(fee.toString()) @@ -1347,14 +1901,29 @@ contract('HomeBridge', async (accounts) => { const rewardableValidators = await RewardableValidators.new() const homeBridge = await HomeBridge.new() const feeManager = await FeeManagerNativeToErcBothDirections.new() - await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled - await homeBridge.rewardableInitialize(rewardableValidators.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, foreignDailyLimit, foreignMaxPerTx, owner, feeManager.address, feeInWei, feeInWei).should.be.fulfilled; + await rewardableValidators.initialize(requiredSignatures, validators, rewards, owner, { + from: owner + }).should.be.fulfilled + await homeBridge.rewardableInitialize( + rewardableValidators.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + foreignDailyLimit, + foreignMaxPerTx, + owner, + feeManager.address, + feeInWei, + feeInWei + ).should.be.fulfilled await homeBridge.sendTransaction({ from: accounts[0], value: halfEther }).should.be.fulfilled - const recipient = "0xf4BEF13F9f4f2B203FAF0C3cBbaAbe1afE056955"; + const recipient = '0xf4BEF13F9f4f2B203FAF0C3cBbaAbe1afE056955' const balanceBefore = toBN(await web3.eth.getBalance(recipient)) const initialBalanceRewardAddress1 = toBN(await web3.eth.getBalance(rewards[0])) @@ -1363,15 +1932,24 @@ contract('HomeBridge', async (accounts) => { const initialBalanceRewardAddress4 = toBN(await web3.eth.getBalance(rewards[3])) const initialBalanceRewardAddress5 = toBN(await web3.eth.getBalance(rewards[4])) - - const transactionHash = "0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415"; + const transactionHash = '0x806335163828a8eda675cff9c84fa6e6c7cf06bb44cc6ec832e42fe789d01415' // When - const { logs: logsValidator1 } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[0]}).should.be.fulfilled - await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[1]}).should.be.fulfilled - await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[2]}).should.be.fulfilled - await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[3]}).should.be.fulfilled - const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, {from: validators[4]}).should.be.fulfilled + const { logs: logsValidator1 } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[0] + }).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[1] + }).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[2] + }).should.be.fulfilled + await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[3] + }).should.be.fulfilled + const { logs } = await homeBridge.executeAffirmation(recipient, value, transactionHash, { + from: validators[4] + }).should.be.fulfilled // Then logsValidator1.length.should.be.equals(1) diff --git a/test/poa20_test.js b/test/poa20_test.js index 94e04655e..55e1d33d4 100644 --- a/test/poa20_test.js +++ b/test/poa20_test.js @@ -1,18 +1,18 @@ -const POA20 = artifacts.require("ERC677BridgeToken.sol"); -const POA20RewardableMock = artifacts.require("./mockContracts/ERC677BridgeTokenRewardableMock"); -const ERC677ReceiverTest = artifacts.require("ERC677ReceiverTest.sol") -const BlockRewardTest = artifacts.require("BlockReward.sol") -const StakingTest = artifacts.require("Staking.sol") -const HomeErcToErcBridge = artifacts.require("HomeBridgeErcToErc.sol"); -const ForeignNativeToErcBridge = artifacts.require("ForeignBridgeNativeToErc.sol"); -const BridgeValidators = artifacts.require("BridgeValidators.sol"); - -const { ERROR_MSG, ZERO_ADDRESS, BN } = require('./setup'); -const { ether, expectEventInLogs } = require('./helpers/helpers'); -const { expect } = require('chai'); +const POA20 = artifacts.require('ERC677BridgeToken.sol') +const POA20RewardableMock = artifacts.require('./mockContracts/ERC677BridgeTokenRewardableMock') +const ERC677ReceiverTest = artifacts.require('ERC677ReceiverTest.sol') +const BlockRewardTest = artifacts.require('BlockReward.sol') +const StakingTest = artifacts.require('Staking.sol') +const HomeErcToErcBridge = artifacts.require('HomeBridgeErcToErc.sol') +const ForeignNativeToErcBridge = artifacts.require('ForeignBridgeNativeToErc.sol') +const BridgeValidators = artifacts.require('BridgeValidators.sol') + +const { expect } = require('chai') +const { ERROR_MSG, ZERO_ADDRESS, BN } = require('./setup') +const { ether, expectEventInLogs } = require('./helpers/helpers') const minPerTx = ether('0.01') -const requireBlockConfirmations = 8; +const requireBlockConfirmations = 8 const gasPrice = web3.utils.toWei('1', 'gwei') const oneEther = ether('1') const halfEther = ether('0.5') @@ -22,11 +22,11 @@ const ZERO = new BN(0) async function testERC677BridgeToken(accounts, rewardable) { let token - let owner = accounts[0] - const user = accounts[1]; - const tokenContract = rewardable ? POA20RewardableMock : POA20; + const owner = accounts[0] + const user = accounts[1] + const tokenContract = rewardable ? POA20RewardableMock : POA20 beforeEach(async () => { - token = await tokenContract.new("POA ERC20 Foundation", "POA20", 18); + token = await tokenContract.new('POA ERC20 Foundation', 'POA20', 18) }) it('default values', async () => { expect(await token.symbol()).to.be.equal('POA20') @@ -41,199 +41,198 @@ async function testERC677BridgeToken(accounts, rewardable) { expect(patch).to.be.bignumber.gte(ZERO) }) - describe('#bridgeContract', async() => { + describe('#bridgeContract', async () => { it('can set bridge contract', async () => { - const homeErcToErcContract = await HomeErcToErcBridge.new(); - (await token.bridgeContract()).should.be.equal(ZERO_ADDRESS); + const homeErcToErcContract = await HomeErcToErcBridge.new() + ;(await token.bridgeContract()).should.be.equal(ZERO_ADDRESS) - await token.setBridgeContract(homeErcToErcContract.address).should.be.fulfilled; - - (await token.bridgeContract()).should.be.equal(homeErcToErcContract.address); + await token.setBridgeContract(homeErcToErcContract.address).should.be.fulfilled + ;(await token.bridgeContract()).should.be.equal(homeErcToErcContract.address) }) it('only owner can set bridge contract', async () => { - const homeErcToErcContract = await HomeErcToErcBridge.new(); - (await token.bridgeContract()).should.be.equal(ZERO_ADDRESS); + const homeErcToErcContract = await HomeErcToErcBridge.new() + ;(await token.bridgeContract()).should.be.equal(ZERO_ADDRESS) - await token.setBridgeContract(homeErcToErcContract.address, {from: user }).should.be.rejectedWith(ERROR_MSG); - (await token.bridgeContract()).should.be.equal(ZERO_ADDRESS); + await token.setBridgeContract(homeErcToErcContract.address, { from: user }).should.be.rejectedWith(ERROR_MSG) + ;(await token.bridgeContract()).should.be.equal(ZERO_ADDRESS) - await token.setBridgeContract(homeErcToErcContract.address, {from: owner }).should.be.fulfilled; - (await token.bridgeContract()).should.be.equal(homeErcToErcContract.address); + await token.setBridgeContract(homeErcToErcContract.address, { from: owner }).should.be.fulfilled + ;(await token.bridgeContract()).should.be.equal(homeErcToErcContract.address) }) it('fail to set invalid bridge contract address', async () => { - const invalidContractAddress = '0xaaB52d66283F7A1D5978bcFcB55721ACB467384b'; - (await token.bridgeContract()).should.be.equal(ZERO_ADDRESS); + const invalidContractAddress = '0xaaB52d66283F7A1D5978bcFcB55721ACB467384b' + ;(await token.bridgeContract()).should.be.equal(ZERO_ADDRESS) - await token.setBridgeContract(invalidContractAddress).should.be.rejectedWith(ERROR_MSG); - (await token.bridgeContract()).should.be.equal(ZERO_ADDRESS); + await token.setBridgeContract(invalidContractAddress).should.be.rejectedWith(ERROR_MSG) + ;(await token.bridgeContract()).should.be.equal(ZERO_ADDRESS) - await token.setBridgeContract(ZERO_ADDRESS).should.be.rejectedWith(ERROR_MSG); - (await token.bridgeContract()).should.be.equal(ZERO_ADDRESS); + await token.setBridgeContract(ZERO_ADDRESS).should.be.rejectedWith(ERROR_MSG) + ;(await token.bridgeContract()).should.be.equal(ZERO_ADDRESS) }) }) if (rewardable) { - describe('#blockRewardContract', async() => { + describe('#blockRewardContract', async () => { it('can set BlockReward contract', async () => { - const blockRewardContract = await BlockRewardTest.new(); - (await token.blockRewardContract()).should.be.equal(ZERO_ADDRESS); - - await token.setBlockRewardContract(blockRewardContract.address).should.be.fulfilled; + const blockRewardContract = await BlockRewardTest.new() + ;(await token.blockRewardContract()).should.be.equal(ZERO_ADDRESS) - (await token.blockRewardContract()).should.be.equal(blockRewardContract.address); + await token.setBlockRewardContract(blockRewardContract.address).should.be.fulfilled + ;(await token.blockRewardContract()).should.be.equal(blockRewardContract.address) }) it('only owner can set BlockReward contract', async () => { - const blockRewardContract = await BlockRewardTest.new(); - (await token.blockRewardContract()).should.be.equal(ZERO_ADDRESS); + const blockRewardContract = await BlockRewardTest.new() + ;(await token.blockRewardContract()).should.be.equal(ZERO_ADDRESS) - await token.setBlockRewardContract(blockRewardContract.address, {from: user }).should.be.rejectedWith(ERROR_MSG); - (await token.blockRewardContract()).should.be.equal(ZERO_ADDRESS); + await token + .setBlockRewardContract(blockRewardContract.address, { from: user }) + .should.be.rejectedWith(ERROR_MSG) + ;(await token.blockRewardContract()).should.be.equal(ZERO_ADDRESS) - await token.setBlockRewardContract(blockRewardContract.address, {from: owner }).should.be.fulfilled; - (await token.blockRewardContract()).should.be.equal(blockRewardContract.address); + await token.setBlockRewardContract(blockRewardContract.address, { from: owner }).should.be.fulfilled + ;(await token.blockRewardContract()).should.be.equal(blockRewardContract.address) }) it('fail to set invalid BlockReward contract address', async () => { - const invalidContractAddress = '0xaaB52d66283F7A1D5978bcFcB55721ACB467384b'; - (await token.blockRewardContract()).should.be.equal(ZERO_ADDRESS); + const invalidContractAddress = '0xaaB52d66283F7A1D5978bcFcB55721ACB467384b' + ;(await token.blockRewardContract()).should.be.equal(ZERO_ADDRESS) - await token.setBlockRewardContract(invalidContractAddress).should.be.rejectedWith(ERROR_MSG); - (await token.blockRewardContract()).should.be.equal(ZERO_ADDRESS); + await token.setBlockRewardContract(invalidContractAddress).should.be.rejectedWith(ERROR_MSG) + ;(await token.blockRewardContract()).should.be.equal(ZERO_ADDRESS) - await token.setBlockRewardContract(ZERO_ADDRESS).should.be.rejectedWith(ERROR_MSG); - (await token.blockRewardContract()).should.be.equal(ZERO_ADDRESS); + await token.setBlockRewardContract(ZERO_ADDRESS).should.be.rejectedWith(ERROR_MSG) + ;(await token.blockRewardContract()).should.be.equal(ZERO_ADDRESS) }) }) - describe('#stakingContract', async() => { + describe('#stakingContract', async () => { it('can set Staking contract', async () => { - const stakingContract = await StakingTest.new(); - (await token.stakingContract()).should.be.equal(ZERO_ADDRESS); + const stakingContract = await StakingTest.new() + ;(await token.stakingContract()).should.be.equal(ZERO_ADDRESS) - await token.setStakingContract(stakingContract.address).should.be.fulfilled; - - (await token.stakingContract()).should.be.equal(stakingContract.address); + await token.setStakingContract(stakingContract.address).should.be.fulfilled + ;(await token.stakingContract()).should.be.equal(stakingContract.address) }) it('only owner can set Staking contract', async () => { - const stakingContract = await StakingTest.new(); - (await token.stakingContract()).should.be.equal(ZERO_ADDRESS); + const stakingContract = await StakingTest.new() + ;(await token.stakingContract()).should.be.equal(ZERO_ADDRESS) - await token.setStakingContract(stakingContract.address, {from: user }).should.be.rejectedWith(ERROR_MSG); - (await token.stakingContract()).should.be.equal(ZERO_ADDRESS); + await token.setStakingContract(stakingContract.address, { from: user }).should.be.rejectedWith(ERROR_MSG) + ;(await token.stakingContract()).should.be.equal(ZERO_ADDRESS) - await token.setStakingContract(stakingContract.address, {from: owner }).should.be.fulfilled; - (await token.stakingContract()).should.be.equal(stakingContract.address); + await token.setStakingContract(stakingContract.address, { from: owner }).should.be.fulfilled + ;(await token.stakingContract()).should.be.equal(stakingContract.address) }) it('fail to set invalid Staking contract address', async () => { - const invalidContractAddress = '0xaaB52d66283F7A1D5978bcFcB55721ACB467384b'; - (await token.stakingContract()).should.be.equal(ZERO_ADDRESS); + const invalidContractAddress = '0xaaB52d66283F7A1D5978bcFcB55721ACB467384b' + ;(await token.stakingContract()).should.be.equal(ZERO_ADDRESS) - await token.setStakingContract(invalidContractAddress).should.be.rejectedWith(ERROR_MSG); - (await token.stakingContract()).should.be.equal(ZERO_ADDRESS); + await token.setStakingContract(invalidContractAddress).should.be.rejectedWith(ERROR_MSG) + ;(await token.stakingContract()).should.be.equal(ZERO_ADDRESS) - await token.setStakingContract(ZERO_ADDRESS).should.be.rejectedWith(ERROR_MSG); - (await token.stakingContract()).should.be.equal(ZERO_ADDRESS); + await token.setStakingContract(ZERO_ADDRESS).should.be.rejectedWith(ERROR_MSG) + ;(await token.stakingContract()).should.be.equal(ZERO_ADDRESS) }) }) - describe('#mintReward', async() => { + describe('#mintReward', async () => { it('can only be called by BlockReward contract', async () => { - await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled; - await token.mintReward([], [], {from: user }).should.be.rejectedWith(ERROR_MSG); - await token.mintReward([], [], {from: accounts[2] }).should.be.fulfilled; + await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled + await token.mintReward([], [], { from: user }).should.be.rejectedWith(ERROR_MSG) + await token.mintReward([], [], { from: accounts[2] }).should.be.fulfilled }) it('should increase totalSupply and balances', async () => { - const user1 = accounts[1]; - const user2 = accounts[2]; - const user3 = accounts[3]; - - expect(await token.totalSupply()).to.be.bignumber.equal(ZERO); - expect(await token.balanceOf(user1)).to.be.bignumber.equal(ZERO); - expect(await token.balanceOf(user2)).to.be.bignumber.equal(ZERO); - expect(await token.balanceOf(user3)).to.be.bignumber.equal(ZERO); - - await token.setBlockRewardContractMock(accounts[4]).should.be.fulfilled; - await token.mintReward([user1, user2, user3], [100, 200, 300], {from: accounts[4] }).should.be.fulfilled; - - expect(await token.totalSupply()).to.be.bignumber.equal('600'); - expect(await token.balanceOf(user1)).to.be.bignumber.equal('100'); - expect(await token.balanceOf(user2)).to.be.bignumber.equal('200'); - expect(await token.balanceOf(user3)).to.be.bignumber.equal('300'); + const user1 = accounts[1] + const user2 = accounts[2] + const user3 = accounts[3] + + expect(await token.totalSupply()).to.be.bignumber.equal(ZERO) + expect(await token.balanceOf(user1)).to.be.bignumber.equal(ZERO) + expect(await token.balanceOf(user2)).to.be.bignumber.equal(ZERO) + expect(await token.balanceOf(user3)).to.be.bignumber.equal(ZERO) + + await token.setBlockRewardContractMock(accounts[4]).should.be.fulfilled + await token.mintReward([user1, user2, user3], [100, 200, 300], { from: accounts[4] }).should.be.fulfilled + + expect(await token.totalSupply()).to.be.bignumber.equal('600') + expect(await token.balanceOf(user1)).to.be.bignumber.equal('100') + expect(await token.balanceOf(user2)).to.be.bignumber.equal('200') + expect(await token.balanceOf(user3)).to.be.bignumber.equal('300') }) }) - describe('#stake', async() => { + describe('#stake', async () => { it('can only be called by Staking contract', async () => { - await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled; - await token.mintReward([user], ['100'], {from: accounts[2] }).should.be.fulfilled; - await token.setStakingContractMock(accounts[3]).should.be.fulfilled; - await token.stake(user, '100', {from: accounts[4] }).should.be.rejectedWith(ERROR_MSG); - await token.stake(user, '100', {from: accounts[3] }).should.be.fulfilled; + await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled + await token.mintReward([user], ['100'], { from: accounts[2] }).should.be.fulfilled + await token.setStakingContractMock(accounts[3]).should.be.fulfilled + await token.stake(user, '100', { from: accounts[4] }).should.be.rejectedWith(ERROR_MSG) + await token.stake(user, '100', { from: accounts[3] }).should.be.fulfilled }) - it('should revert if user doesn\'t have enough balance', async () => { - await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled; - await token.mintReward([user], ['99'], {from: accounts[2] }).should.be.fulfilled; - expect(await token.balanceOf(user)).to.be.bignumber.equal('99'); - await token.setStakingContractMock(accounts[3]).should.be.fulfilled; - await token.stake(user, '100', {from: accounts[3] }).should.be.rejectedWith(ERROR_MSG); + it("should revert if user doesn't have enough balance", async () => { + await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled + await token.mintReward([user], ['99'], { from: accounts[2] }).should.be.fulfilled + expect(await token.balanceOf(user)).to.be.bignumber.equal('99') + await token.setStakingContractMock(accounts[3]).should.be.fulfilled + await token.stake(user, '100', { from: accounts[3] }).should.be.rejectedWith(ERROR_MSG) }) - it('should decrease user\'s balance and increase Staking\'s balance', async () => { - await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled; - await token.mintReward([user], ['100'], {from: accounts[2] }).should.be.fulfilled; - expect(await token.balanceOf(user)).to.be.bignumber.equal('100'); - expect(await token.balanceOf(accounts[3])).to.be.bignumber.equal(ZERO); - await token.setStakingContractMock(accounts[3]).should.be.fulfilled; - await token.stake(user, '100', {from: accounts[3] }).should.be.fulfilled; - expect(await token.balanceOf(user)).to.be.bignumber.equal(ZERO); - expect(await token.balanceOf(accounts[3])).to.be.bignumber.equal('100'); + it("should decrease user's balance and increase Staking's balance", async () => { + await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled + await token.mintReward([user], ['100'], { from: accounts[2] }).should.be.fulfilled + expect(await token.balanceOf(user)).to.be.bignumber.equal('100') + expect(await token.balanceOf(accounts[3])).to.be.bignumber.equal(ZERO) + await token.setStakingContractMock(accounts[3]).should.be.fulfilled + await token.stake(user, '100', { from: accounts[3] }).should.be.fulfilled + expect(await token.balanceOf(user)).to.be.bignumber.equal(ZERO) + expect(await token.balanceOf(accounts[3])).to.be.bignumber.equal('100') }) }) - describe('#withdraw', async() => { + describe('#withdraw', async () => { it('can only be called by Staking contract', async () => { - await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled; - await token.mintReward([user], ['100'], {from: accounts[2] }).should.be.fulfilled; - await token.setStakingContractMock(accounts[3]).should.be.fulfilled; - await token.stake(user, '100', {from: accounts[3] }).should.be.fulfilled; - await token.withdraw(user, '100', {from: accounts[4] }).should.be.rejectedWith(ERROR_MSG); - await token.withdraw(user, '100', {from: accounts[3] }).should.be.fulfilled; + await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled + await token.mintReward([user], ['100'], { from: accounts[2] }).should.be.fulfilled + await token.setStakingContractMock(accounts[3]).should.be.fulfilled + await token.stake(user, '100', { from: accounts[3] }).should.be.fulfilled + await token.withdraw(user, '100', { from: accounts[4] }).should.be.rejectedWith(ERROR_MSG) + await token.withdraw(user, '100', { from: accounts[3] }).should.be.fulfilled }) - it('should revert if Staking doesn\'t have enough balance', async () => { - await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled; - await token.mintReward([user], ['100'], {from: accounts[2] }).should.be.fulfilled; - expect(await token.balanceOf(user)).to.be.bignumber.equal('100'); - await token.setStakingContractMock(accounts[3]).should.be.fulfilled; - await token.stake(user, '100', {from: accounts[3] }).should.be.fulfilled; - await token.withdraw(user, '101', {from: accounts[3] }).should.be.rejectedWith(ERROR_MSG); - await token.withdraw(user, '100', {from: accounts[3] }).should.be.fulfilled; + it("should revert if Staking doesn't have enough balance", async () => { + await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled + await token.mintReward([user], ['100'], { from: accounts[2] }).should.be.fulfilled + expect(await token.balanceOf(user)).to.be.bignumber.equal('100') + await token.setStakingContractMock(accounts[3]).should.be.fulfilled + await token.stake(user, '100', { from: accounts[3] }).should.be.fulfilled + await token.withdraw(user, '101', { from: accounts[3] }).should.be.rejectedWith(ERROR_MSG) + await token.withdraw(user, '100', { from: accounts[3] }).should.be.fulfilled }) - it('should decrease Staking\'s balance and increase user\'s balance', async () => { - await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled; - await token.mintReward([user], ['100'], {from: accounts[2] }).should.be.fulfilled; - expect(await token.balanceOf(user)).to.be.bignumber.equal('100'); - expect(await token.balanceOf(accounts[3])).to.be.bignumber.equal(ZERO); - await token.setStakingContractMock(accounts[3]).should.be.fulfilled; - await token.stake(user, '100', {from: accounts[3] }).should.be.fulfilled; - expect(await token.balanceOf(user)).to.be.bignumber.equal('0'); - expect(await token.balanceOf(accounts[3])).to.be.bignumber.equal('100'); - await token.withdraw(user, 60, {from: accounts[3] }).should.be.fulfilled; - expect(await token.balanceOf(user)).to.be.bignumber.equal('60'); - expect(await token.balanceOf(accounts[3])).to.be.bignumber.equal('40'); + it("should decrease Staking's balance and increase user's balance", async () => { + await token.setBlockRewardContractMock(accounts[2]).should.be.fulfilled + await token.mintReward([user], ['100'], { from: accounts[2] }).should.be.fulfilled + expect(await token.balanceOf(user)).to.be.bignumber.equal('100') + expect(await token.balanceOf(accounts[3])).to.be.bignumber.equal(ZERO) + await token.setStakingContractMock(accounts[3]).should.be.fulfilled + await token.stake(user, '100', { from: accounts[3] }).should.be.fulfilled + expect(await token.balanceOf(user)).to.be.bignumber.equal('0') + expect(await token.balanceOf(accounts[3])).to.be.bignumber.equal('100') + await token.withdraw(user, 60, { from: accounts[3] }).should.be.fulfilled + expect(await token.balanceOf(user)).to.be.bignumber.equal('60') + expect(await token.balanceOf(accounts[3])).to.be.bignumber.equal('40') }) }) } - describe('#mint', async() => { + describe('#mint', async () => { it('can mint by owner', async () => { - expect(await token.totalSupply()).to.be.bignumber.equal(ZERO); - await token.mint(user, 1, {from: owner }).should.be.fulfilled; - expect(await token.totalSupply()).to.be.bignumber.equal('1'); - expect(await token.balanceOf(user)).to.be.bignumber.equal('1'); + expect(await token.totalSupply()).to.be.bignumber.equal(ZERO) + await token.mint(user, 1, { from: owner }).should.be.fulfilled + expect(await token.totalSupply()).to.be.bignumber.equal('1') + expect(await token.balanceOf(user)).to.be.bignumber.equal('1') }) it('no one can call finishMinting', async () => { @@ -241,30 +240,54 @@ async function testERC677BridgeToken(accounts, rewardable) { }) it('cannot mint by non-owner', async () => { - expect(await token.totalSupply()).to.be.bignumber.equal(ZERO); - await token.mint(user, 1, {from: user }).should.be.rejectedWith(ERROR_MSG); - expect(await token.totalSupply()).to.be.bignumber.equal(ZERO); - expect(await token.balanceOf(user)).to.be.bignumber.equal(ZERO); + expect(await token.totalSupply()).to.be.bignumber.equal(ZERO) + await token.mint(user, 1, { from: user }).should.be.rejectedWith(ERROR_MSG) + expect(await token.totalSupply()).to.be.bignumber.equal(ZERO) + expect(await token.balanceOf(user)).to.be.bignumber.equal(ZERO) }) }) - describe('#transfer', async() => { - let homeErcToErcContract, foreignNativeToErcBridge, validatorContract + describe('#transfer', async () => { + let homeErcToErcContract + let foreignNativeToErcBridge + let validatorContract beforeEach(async () => { validatorContract = await BridgeValidators.new() - const authorities = [accounts[2]]; + const authorities = [accounts[2]] await validatorContract.initialize(1, authorities, owner) homeErcToErcContract = await HomeErcToErcBridge.new() - await homeErcToErcContract.initialize(validatorContract.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, executionDailyLimit, executionMaxPerTx, owner) + await homeErcToErcContract.initialize( + validatorContract.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + token.address, + executionDailyLimit, + executionMaxPerTx, + owner + ) foreignNativeToErcBridge = await ForeignNativeToErcBridge.new() - await foreignNativeToErcBridge.initialize(validatorContract.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, executionDailyLimit, executionMaxPerTx, owner); + await foreignNativeToErcBridge.initialize( + validatorContract.address, + token.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + executionDailyLimit, + executionMaxPerTx, + owner + ) }) it('sends tokens to recipient', async () => { - await token.mint(user, '1', {from: owner }).should.be.fulfilled; - await token.transfer(user, 1, {from: owner}).should.be.rejectedWith(ERROR_MSG); - const {logs} = await token.transfer(owner, 1, {from: user}).should.be.fulfilled; - expect(await token.balanceOf(owner)).to.be.bignumber.equal('1'); - expect(await token.balanceOf(user)).to.be.bignumber.equal(ZERO); + await token.mint(user, '1', { from: owner }).should.be.fulfilled + await token.transfer(user, 1, { from: owner }).should.be.rejectedWith(ERROR_MSG) + const { logs } = await token.transfer(owner, 1, { from: user }).should.be.fulfilled + expect(await token.balanceOf(owner)).to.be.bignumber.equal('1') + expect(await token.balanceOf(user)).to.be.bignumber.equal(ZERO) expectEventInLogs(logs, 'Transfer', { from: user, to: owner, @@ -273,18 +296,20 @@ async function testERC677BridgeToken(accounts, rewardable) { }) it('sends tokens to bridge contract', async () => { - await token.setBridgeContract(homeErcToErcContract.address).should.be.fulfilled; - await token.mint(user, oneEther, {from: owner }).should.be.fulfilled; + await token.setBridgeContract(homeErcToErcContract.address).should.be.fulfilled + await token.mint(user, oneEther, { from: owner }).should.be.fulfilled - const result = await token.transfer(homeErcToErcContract.address, minPerTx, {from: user}).should.be.fulfilled; + const result = await token.transfer(homeErcToErcContract.address, minPerTx, { from: user }).should.be.fulfilled expectEventInLogs(result.logs, 'Transfer', { from: user, to: homeErcToErcContract.address, value: minPerTx }) - await token.setBridgeContract(foreignNativeToErcBridge.address).should.be.fulfilled; - const result2 = await token.transfer(foreignNativeToErcBridge.address, minPerTx, {from: user}).should.be.fulfilled; + await token.setBridgeContract(foreignNativeToErcBridge.address).should.be.fulfilled + const result2 = await token.transfer(foreignNativeToErcBridge.address, minPerTx, { + from: user + }).should.be.fulfilled expectEventInLogs(result2.logs, 'Transfer', { from: user, to: foreignNativeToErcBridge.address, @@ -293,10 +318,10 @@ async function testERC677BridgeToken(accounts, rewardable) { }) it('sends tokens to contract that does not contains onTokenTransfer method', async () => { - await token.setBridgeContract(homeErcToErcContract.address).should.be.fulfilled; - await token.mint(user, oneEther, {from: owner }).should.be.fulfilled; + await token.setBridgeContract(homeErcToErcContract.address).should.be.fulfilled + await token.mint(user, oneEther, { from: owner }).should.be.fulfilled - const result = await token.transfer(validatorContract.address, minPerTx, {from: user}).should.be.fulfilled; + const result = await token.transfer(validatorContract.address, minPerTx, { from: user }).should.be.fulfilled expectEventInLogs(result.logs, 'Transfer', { from: user, to: validatorContract.address, @@ -311,98 +336,133 @@ async function testERC677BridgeToken(accounts, rewardable) { it('fail to send tokens to bridge contract out of limits', async () => { const lessThanMin = ether('0.0001') - await token.mint(user, oneEther, {from: owner }).should.be.fulfilled; + await token.mint(user, oneEther, { from: owner }).should.be.fulfilled - await token.setBridgeContract(homeErcToErcContract.address).should.be.fulfilled; - await token.transfer(homeErcToErcContract.address, lessThanMin, {from: user}).should.be.rejectedWith(ERROR_MSG); + await token.setBridgeContract(homeErcToErcContract.address).should.be.fulfilled + await token.transfer(homeErcToErcContract.address, lessThanMin, { from: user }).should.be.rejectedWith(ERROR_MSG) - await token.setBridgeContract(foreignNativeToErcBridge.address).should.be.fulfilled; - await token.transfer(foreignNativeToErcBridge.address, lessThanMin, {from: user}).should.be.rejectedWith(ERROR_MSG); + await token.setBridgeContract(foreignNativeToErcBridge.address).should.be.fulfilled + await token + .transfer(foreignNativeToErcBridge.address, lessThanMin, { from: user }) + .should.be.rejectedWith(ERROR_MSG) }) if (rewardable) { it('fail to send tokens to Staking contract directly', async () => { - const amount = ether('1'); - const stakingContractAddress = accounts[2]; - const arbitraryAccountAddress = accounts[3]; - await token.setStakingContractMock(stakingContractAddress, {from: owner}).should.be.fulfilled; - await token.mint(user, amount, {from: owner}).should.be.fulfilled; - await token.transfer(stakingContractAddress, amount, {from: user}).should.be.rejectedWith(ERROR_MSG); - await token.transfer(arbitraryAccountAddress, amount, {from: user}).should.be.fulfilled; - }); + const amount = ether('1') + const stakingContractAddress = accounts[2] + const arbitraryAccountAddress = accounts[3] + await token.setStakingContractMock(stakingContractAddress, { from: owner }).should.be.fulfilled + await token.mint(user, amount, { from: owner }).should.be.fulfilled + await token.transfer(stakingContractAddress, amount, { from: user }).should.be.rejectedWith(ERROR_MSG) + await token.transfer(arbitraryAccountAddress, amount, { from: user }).should.be.fulfilled + }) } }) if (rewardable) { - describe('#transferFrom', async() => { + describe('#transferFrom', async () => { it('fail to send tokens to Staking contract directly', async () => { - const amount = ether('1'); - const user2 = accounts[2]; - const stakingContractAddress = accounts[3]; - const arbitraryAccountAddress = accounts[4]; - await token.setStakingContractMock(stakingContractAddress, {from: owner}).should.be.fulfilled; - await token.mint(user, amount, {from: owner}).should.be.fulfilled; - await token.approve(user2, amount, {from: user}).should.be.fulfilled; - await token.transferFrom(user, stakingContractAddress, amount, {from: user2}).should.be.rejectedWith(ERROR_MSG); - await token.transferFrom(user, arbitraryAccountAddress, amount, {from: user2}).should.be.fulfilled; - }); - }); + const amount = ether('1') + const user2 = accounts[2] + const stakingContractAddress = accounts[3] + const arbitraryAccountAddress = accounts[4] + await token.setStakingContractMock(stakingContractAddress, { from: owner }).should.be.fulfilled + await token.mint(user, amount, { from: owner }).should.be.fulfilled + await token.approve(user2, amount, { from: user }).should.be.fulfilled + await token + .transferFrom(user, stakingContractAddress, amount, { from: user2 }) + .should.be.rejectedWith(ERROR_MSG) + await token.transferFrom(user, arbitraryAccountAddress, amount, { from: user2 }).should.be.fulfilled + }) + }) } - describe("#burn", async () => { - it('can burn', async() => { - await token.burn(100, {from: owner}).should.be.rejectedWith(ERROR_MSG); - await token.mint(user, 1, {from: owner }).should.be.fulfilled; - await token.burn(1, {from: user}).should.be.fulfilled; - expect(await token.totalSupply()).to.be.bignumber.equal(ZERO); - expect(await token.balanceOf(user)).to.be.bignumber.equal(ZERO); + describe('#burn', async () => { + it('can burn', async () => { + await token.burn(100, { from: owner }).should.be.rejectedWith(ERROR_MSG) + await token.mint(user, 1, { from: owner }).should.be.fulfilled + await token.burn(1, { from: user }).should.be.fulfilled + expect(await token.totalSupply()).to.be.bignumber.equal(ZERO) + expect(await token.balanceOf(user)).to.be.bignumber.equal(ZERO) }) }) describe('#transferAndCall', () => { - let homeErcToErcContract, foreignNativeToErcBridge, validatorContract + let homeErcToErcContract + let foreignNativeToErcBridge + let validatorContract beforeEach(async () => { validatorContract = await BridgeValidators.new() - const authorities = [accounts[2]]; + const authorities = [accounts[2]] await validatorContract.initialize(1, authorities, owner) homeErcToErcContract = await HomeErcToErcBridge.new() - await homeErcToErcContract.initialize(validatorContract.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, token.address, executionDailyLimit, executionMaxPerTx, owner) + await homeErcToErcContract.initialize( + validatorContract.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + token.address, + executionDailyLimit, + executionMaxPerTx, + owner + ) foreignNativeToErcBridge = await ForeignNativeToErcBridge.new() - await foreignNativeToErcBridge.initialize(validatorContract.address, token.address, oneEther, halfEther, minPerTx, gasPrice, requireBlockConfirmations, executionDailyLimit, executionMaxPerTx, owner); + await foreignNativeToErcBridge.initialize( + validatorContract.address, + token.address, + oneEther, + halfEther, + minPerTx, + gasPrice, + requireBlockConfirmations, + executionDailyLimit, + executionMaxPerTx, + owner + ) }) it('calls contractFallback', async () => { - const receiver = await ERC677ReceiverTest.new(); - expect(await receiver.from()).to.be.equal(ZERO_ADDRESS); - expect(await receiver.value()).to.be.bignumber.equal(ZERO); - expect(await receiver.data()).to.be.equal(null); - expect(await receiver.someVar()).to.be.bignumber.equal(ZERO); + const receiver = await ERC677ReceiverTest.new() + expect(await receiver.from()).to.be.equal(ZERO_ADDRESS) + expect(await receiver.value()).to.be.bignumber.equal(ZERO) + expect(await receiver.data()).to.be.equal(null) + expect(await receiver.someVar()).to.be.bignumber.equal(ZERO) const callDoSomething123 = receiver.contract.methods.doSomething(123).encodeABI() - await token.mint(user, '1', {from: owner }).should.be.fulfilled; - await token.transferAndCall(token.address, '1', callDoSomething123, {from: user}).should.be.rejectedWith(ERROR_MSG); - await token.transferAndCall(ZERO_ADDRESS, '1', callDoSomething123, {from: user}).should.be.rejectedWith(ERROR_MSG); - await token.transferAndCall(receiver.address, '1', callDoSomething123, {from: user}).should.be.fulfilled; - expect(await token.balanceOf(receiver.address)).to.be.bignumber.equal('1'); - expect(await token.balanceOf(user)).to.be.bignumber.equal(ZERO); - expect(await receiver.from()).to.be.equal(user); - expect(await receiver.value()).to.be.bignumber.equal('1'); - expect(await receiver.data()).to.be.equal(callDoSomething123); - expect(await receiver.someVar()).to.be.bignumber.equal('123'); + await token.mint(user, '1', { from: owner }).should.be.fulfilled + await token + .transferAndCall(token.address, '1', callDoSomething123, { from: user }) + .should.be.rejectedWith(ERROR_MSG) + await token + .transferAndCall(ZERO_ADDRESS, '1', callDoSomething123, { from: user }) + .should.be.rejectedWith(ERROR_MSG) + await token.transferAndCall(receiver.address, '1', callDoSomething123, { from: user }).should.be.fulfilled + expect(await token.balanceOf(receiver.address)).to.be.bignumber.equal('1') + expect(await token.balanceOf(user)).to.be.bignumber.equal(ZERO) + expect(await receiver.from()).to.be.equal(user) + expect(await receiver.value()).to.be.bignumber.equal('1') + expect(await receiver.data()).to.be.equal(callDoSomething123) + expect(await receiver.someVar()).to.be.bignumber.equal('123') }) it('sends tokens to bridge contract', async () => { - await token.setBridgeContract(homeErcToErcContract.address).should.be.fulfilled; - await token.mint(user, oneEther, {from: owner }).should.be.fulfilled; + await token.setBridgeContract(homeErcToErcContract.address).should.be.fulfilled + await token.mint(user, oneEther, { from: owner }).should.be.fulfilled - const result = await token.transferAndCall(homeErcToErcContract.address, minPerTx, '0x', {from: user}).should.be.fulfilled; + const result = await token.transferAndCall(homeErcToErcContract.address, minPerTx, '0x', { + from: user + }).should.be.fulfilled expectEventInLogs(result.logs, 'Transfer', { from: user, to: homeErcToErcContract.address, value: minPerTx }) - await token.setBridgeContract(foreignNativeToErcBridge.address).should.be.fulfilled; - const result2 = await token.transferAndCall(foreignNativeToErcBridge.address, minPerTx, '0x', {from: user}).should.be.fulfilled; + await token.setBridgeContract(foreignNativeToErcBridge.address).should.be.fulfilled + const result2 = await token.transferAndCall(foreignNativeToErcBridge.address, minPerTx, '0x', { from: user }) + .should.be.fulfilled expectEventInLogs(result2.logs, 'Transfer', { from: user, to: foreignNativeToErcBridge.address, @@ -411,75 +471,81 @@ async function testERC677BridgeToken(accounts, rewardable) { }) it('fail to sends tokens to contract that does not contains onTokenTransfer method', async () => { - await token.setBridgeContract(homeErcToErcContract.address).should.be.fulfilled; - await token.mint(user, oneEther, {from: owner }).should.be.fulfilled; + await token.setBridgeContract(homeErcToErcContract.address).should.be.fulfilled + await token.mint(user, oneEther, { from: owner }).should.be.fulfilled - await token.transferAndCall(validatorContract.address, minPerTx, '0x', {from: user}).should.be.rejectedWith(ERROR_MSG); + await token + .transferAndCall(validatorContract.address, minPerTx, '0x', { from: user }) + .should.be.rejectedWith(ERROR_MSG) }) it('fail to send tokens to bridge contract out of limits', async () => { const lessThanMin = ether('0.0001') - await token.mint(user, oneEther, {from: owner }).should.be.fulfilled; + await token.mint(user, oneEther, { from: owner }).should.be.fulfilled - await token.setBridgeContract(homeErcToErcContract.address).should.be.fulfilled; - await token.transferAndCall(homeErcToErcContract.address, lessThanMin, '0x', {from: user}).should.be.rejectedWith(ERROR_MSG); + await token.setBridgeContract(homeErcToErcContract.address).should.be.fulfilled + await token + .transferAndCall(homeErcToErcContract.address, lessThanMin, '0x', { from: user }) + .should.be.rejectedWith(ERROR_MSG) - await token.setBridgeContract(foreignNativeToErcBridge.address).should.be.fulfilled; - await token.transferAndCall(foreignNativeToErcBridge.address, lessThanMin, '0x', {from: user}).should.be.rejectedWith(ERROR_MSG); + await token.setBridgeContract(foreignNativeToErcBridge.address).should.be.fulfilled + await token + .transferAndCall(foreignNativeToErcBridge.address, lessThanMin, '0x', { from: user }) + .should.be.rejectedWith(ERROR_MSG) }) }) describe('#claimtokens', async () => { - it('can take send ERC20 tokens', async ()=> { - const owner = accounts[0]; - const halfEther = ether('0.5'); - let tokenSecond = await tokenContract.new("Roman Token", "RST", 18); + it('can take send ERC20 tokens', async () => { + const owner = accounts[0] + const halfEther = ether('0.5') + const tokenSecond = await tokenContract.new('Roman Token', 'RST', 18) - await tokenSecond.mint(accounts[0], halfEther).should.be.fulfilled; + await tokenSecond.mint(accounts[0], halfEther).should.be.fulfilled halfEther.should.be.bignumber.equal(await tokenSecond.balanceOf(accounts[0])) - await tokenSecond.transfer(token.address, halfEther); + await tokenSecond.transfer(token.address, halfEther) expect(await tokenSecond.balanceOf(accounts[0])).to.be.bignumber.equal(ZERO) expect(await tokenSecond.balanceOf(token.address)).to.be.bignumber.equal(halfEther) - await token.claimTokens(tokenSecond.address, accounts[3], {from: owner}); + await token.claimTokens(tokenSecond.address, accounts[3], { from: owner }) expect(await tokenSecond.balanceOf(token.address)).to.be.bignumber.equal(ZERO) halfEther.should.be.bignumber.equal(await tokenSecond.balanceOf(accounts[3])) }) }) describe('#transfer', async () => { it('if transfer called on contract, onTokenTransfer is also invoked', async () => { - const receiver = await ERC677ReceiverTest.new(); - expect(await receiver.from()).to.be.equal(ZERO_ADDRESS); - expect(await receiver.value()).to.be.bignumber.equal(ZERO); - expect(await receiver.data()).to.be.equal(null); - expect(await receiver.someVar()).to.be.bignumber.equal(ZERO); - - await token.mint(user, 1, {from: owner }).should.be.fulfilled; - const {logs} = await token.transfer(receiver.address, '1', {from: user}).should.be.fulfilled; - - expect(await token.balanceOf(receiver.address)).to.be.bignumber.equal('1'); - expect(await token.balanceOf(user)).to.be.bignumber.equal(ZERO); - expect(await receiver.from()).to.be.equal(user); - expect(await receiver.value()).to.be.bignumber.equal('1'); - expect(await receiver.data()).to.be.equal(null); - expect(logs[0].event).to.be.equal("Transfer") + const receiver = await ERC677ReceiverTest.new() + expect(await receiver.from()).to.be.equal(ZERO_ADDRESS) + expect(await receiver.value()).to.be.bignumber.equal(ZERO) + expect(await receiver.data()).to.be.equal(null) + expect(await receiver.someVar()).to.be.bignumber.equal(ZERO) + + await token.mint(user, 1, { from: owner }).should.be.fulfilled + const { logs } = await token.transfer(receiver.address, '1', { from: user }).should.be.fulfilled + + expect(await token.balanceOf(receiver.address)).to.be.bignumber.equal('1') + expect(await token.balanceOf(user)).to.be.bignumber.equal(ZERO) + expect(await receiver.from()).to.be.equal(user) + expect(await receiver.value()).to.be.bignumber.equal('1') + expect(await receiver.data()).to.be.equal(null) + expect(logs[0].event).to.be.equal('Transfer') }) it('if transfer called on contract, still works even if onTokenTransfer doesnot exist', async () => { - const someContract = await tokenContract.new("Some", "Token", 18); - await token.mint(user, '2', {from: owner }).should.be.fulfilled; - const tokenTransfer = await token.transfer(someContract.address, '1', {from: user}).should.be.fulfilled; - const tokenTransfer2 = await token.transfer(accounts[0], '1', {from: user}).should.be.fulfilled; - expect(await token.balanceOf(someContract.address)).to.be.bignumber.equal('1'); - expect(await token.balanceOf(user)).to.be.bignumber.equal(ZERO); - tokenTransfer.logs[0].event.should.be.equal("Transfer") - tokenTransfer2.logs[0].event.should.be.equal("Transfer") + const someContract = await tokenContract.new('Some', 'Token', 18) + await token.mint(user, '2', { from: owner }).should.be.fulfilled + const tokenTransfer = await token.transfer(someContract.address, '1', { from: user }).should.be.fulfilled + const tokenTransfer2 = await token.transfer(accounts[0], '1', { from: user }).should.be.fulfilled + expect(await token.balanceOf(someContract.address)).to.be.bignumber.equal('1') + expect(await token.balanceOf(user)).to.be.bignumber.equal(ZERO) + tokenTransfer.logs[0].event.should.be.equal('Transfer') + tokenTransfer2.logs[0].event.should.be.equal('Transfer') }) }) } -contract('ERC677BridgeToken', async (accounts) => { - await testERC677BridgeToken(accounts, false); +contract('ERC677BridgeToken', async accounts => { + await testERC677BridgeToken(accounts, false) }) -contract('ERC677BridgeTokenRewardable', async (accounts) => { - await testERC677BridgeToken(accounts, true); +contract('ERC677BridgeTokenRewardable', async accounts => { + await testERC677BridgeToken(accounts, true) }) diff --git a/test/rewardable_validators_test.js b/test/rewardable_validators_test.js index dc85778dc..2a2055e70 100644 --- a/test/rewardable_validators_test.js +++ b/test/rewardable_validators_test.js @@ -1,18 +1,18 @@ -const BridgeValidators = artifacts.require("RewardableValidators.sol"); -const EternalStorageProxy = artifacts.require("EternalStorageProxy.sol"); +const BridgeValidators = artifacts.require('RewardableValidators.sol') +const EternalStorageProxy = artifacts.require('EternalStorageProxy.sol') -const { ERROR_MSG, ZERO_ADDRESS, F_ADDRESS, BN } = require('./setup'); -const { expectEventInLogs } = require('./helpers/helpers'); -const { expect } = require('chai'); +const { expect } = require('chai') +const { ERROR_MSG, ZERO_ADDRESS, F_ADDRESS, BN } = require('./setup') +const { expectEventInLogs } = require('./helpers/helpers') const ZERO = new BN(0) -contract('RewardableValidators', async (accounts) => { +contract('RewardableValidators', async accounts => { let bridgeValidators - let owner = accounts[0] + const owner = accounts[0] beforeEach(async () => { - bridgeValidators = await BridgeValidators.new(); + bridgeValidators = await BridgeValidators.new() }) describe('#initialize', async () => { @@ -25,12 +25,28 @@ contract('RewardableValidators', async (accounts) => { expect(await bridgeValidators.requiredSignatures()).to.be.bignumber.equal(ZERO) expect(await bridgeValidators.deployedAtBlock()).to.be.bignumber.equal(ZERO) - await bridgeValidators.initialize(3, accounts.slice(0, 3), accounts.slice(3, 5), accounts[2], {from: accounts[2]}).should.be.rejectedWith(ERROR_MSG) - await bridgeValidators.initialize(1, [accounts[0]], [ZERO_ADDRESS], accounts[1], { from: accounts[1] }).should.be.rejectedWith(ERROR_MSG) - await bridgeValidators.initialize(1, [ZERO_ADDRESS], [accounts[0]], accounts[1], { from: accounts[1] }).should.be.rejectedWith(ERROR_MSG) - await bridgeValidators.initialize(1, [F_ADDRESS], [accounts[0]], accounts[1], { from: accounts[1] }).should.be.rejectedWith(ERROR_MSG) - await bridgeValidators.initialize(2, accounts.slice(0, 2), accounts.slice(2, 4), accounts[2], {from: accounts[2]}).should.be.fulfilled; - await bridgeValidators.initialize(2, accounts.slice(0, 2), accounts.slice(2, 4), accounts[2], {from: accounts[2]}).should.be.rejectedWith(ERROR_MSG); + await bridgeValidators + .initialize(3, accounts.slice(0, 3), accounts.slice(3, 5), accounts[2], { + from: accounts[2] + }) + .should.be.rejectedWith(ERROR_MSG) + await bridgeValidators + .initialize(1, [accounts[0]], [ZERO_ADDRESS], accounts[1], { from: accounts[1] }) + .should.be.rejectedWith(ERROR_MSG) + await bridgeValidators + .initialize(1, [ZERO_ADDRESS], [accounts[0]], accounts[1], { from: accounts[1] }) + .should.be.rejectedWith(ERROR_MSG) + await bridgeValidators + .initialize(1, [F_ADDRESS], [accounts[0]], accounts[1], { from: accounts[1] }) + .should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.initialize(2, accounts.slice(0, 2), accounts.slice(2, 4), accounts[2], { + from: accounts[2] + }).should.be.fulfilled + await bridgeValidators + .initialize(2, accounts.slice(0, 2), accounts.slice(2, 4), accounts[2], { + from: accounts[2] + }) + .should.be.rejectedWith(ERROR_MSG) expect(await bridgeValidators.isInitialized()).to.be.equal(true) expect(await bridgeValidators.requiredSignatures()).to.be.bignumber.equal('2') @@ -47,21 +63,27 @@ contract('RewardableValidators', async (accounts) => { }) describe('#addValidator', async () => { - let owner = accounts[2]; - let validators = [accounts[0], accounts[1]]; - let rewards = accounts.slice(2, 4) - let requiredSignatures = 2; + const owner = accounts[2] + const validators = [accounts[0], accounts[1]] + const rewards = accounts.slice(2, 4) + const requiredSignatures = 2 beforeEach(async () => { - await bridgeValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + await bridgeValidators.initialize(requiredSignatures, validators, rewards, owner, { + from: owner + }).should.be.fulfilled expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('2') }) it('adds validator', async () => { - let newValidator = accounts[4]; - let newReward = accounts[5]; + const newValidator = accounts[4] + const newReward = accounts[5] false.should.be.equal(await bridgeValidators.isValidator(newValidator)) - await bridgeValidators.addRewardableValidator(newValidator, newReward, {from: validators[0]}).should.be.rejectedWith(ERROR_MSG) - const {logs} = await bridgeValidators.addRewardableValidator(newValidator, newReward, {from: owner}).should.be.fulfilled + await bridgeValidators + .addRewardableValidator(newValidator, newReward, { from: validators[0] }) + .should.be.rejectedWith(ERROR_MSG) + const { logs } = await bridgeValidators.addRewardableValidator(newValidator, newReward, { + from: owner + }).should.be.fulfilled expect(await bridgeValidators.isValidator(newValidator)).to.be.equal(true) expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('3') expectEventInLogs(logs, 'ValidatorAdded', { validator: newValidator }) @@ -72,51 +94,61 @@ contract('RewardableValidators', async (accounts) => { it('cannot add already existing validator', async () => { true.should.be.equal(await bridgeValidators.isValidator(validators[0])) - await bridgeValidators.addRewardableValidator(validators[0], rewards[0], {from: owner}).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators + .addRewardableValidator(validators[0], rewards[0], { from: owner }) + .should.be.rejectedWith(ERROR_MSG) expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('2') }) it(`cannot add 0xf as validator address`, async () => { // Given - await bridgeValidators.addRewardableValidator(F_ADDRESS, rewards[0], { from: owner }).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators + .addRewardableValidator(F_ADDRESS, rewards[0], { from: owner }) + .should.be.rejectedWith(ERROR_MSG) }) it(`cannot add 0x0 as validator address`, async () => { - await bridgeValidators.addRewardableValidator(ZERO_ADDRESS, rewards[0], {from: owner}).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators + .addRewardableValidator(ZERO_ADDRESS, rewards[0], { from: owner }) + .should.be.rejectedWith(ERROR_MSG) }) it(`cannot add 0x0 as reward address`, async () => { - await bridgeValidators.addRewardableValidator(accounts[4], ZERO_ADDRESS, { from: owner }).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators + .addRewardableValidator(accounts[4], ZERO_ADDRESS, { from: owner }) + .should.be.rejectedWith(ERROR_MSG) }) }) describe('#removeValidator', async () => { - let owner = accounts[2]; - let validators = [accounts[0], accounts[1], accounts[3]]; - let rewards = accounts.slice(4, 7); - let requiredSignatures = 2; + const owner = accounts[2] + const validators = [accounts[0], accounts[1], accounts[3]] + const rewards = accounts.slice(4, 7) + const requiredSignatures = 2 beforeEach(async () => { - await bridgeValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + await bridgeValidators.initialize(requiredSignatures, validators, rewards, owner, { + from: owner + }).should.be.fulfilled expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('3') }) it('removes validator', async () => { - let toRemove = validators[0]; + const toRemove = validators[0] expect(await bridgeValidators.isValidator(toRemove)).to.be.equal(true) - await bridgeValidators.removeValidator(toRemove, {from: validators[0]}).should.be.rejectedWith(ERROR_MSG) - const {logs} = await bridgeValidators.removeValidator(toRemove, {from: owner}).should.be.fulfilled + await bridgeValidators.removeValidator(toRemove, { from: validators[0] }).should.be.rejectedWith(ERROR_MSG) + const { logs } = await bridgeValidators.removeValidator(toRemove, { from: owner }).should.be.fulfilled expect(await bridgeValidators.isValidator(toRemove)).to.be.equal(false) expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('2') expectEventInLogs(logs, 'ValidatorRemoved', { validator: toRemove }) }) it('cannot remove if it will break requiredSignatures', async () => { - let toRemove = validators[0]; - let toRemove2 = validators[1]; + const toRemove = validators[0] + const toRemove2 = validators[1] true.should.be.equal(await bridgeValidators.isValidator(toRemove)) true.should.be.equal(await bridgeValidators.isValidator(toRemove)) - await bridgeValidators.removeValidator(toRemove, {from: owner}).should.be.fulfilled - await bridgeValidators.removeValidator(toRemove2, {from: owner}).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.removeValidator(toRemove, { from: owner }).should.be.fulfilled + await bridgeValidators.removeValidator(toRemove2, { from: owner }).should.be.rejectedWith(ERROR_MSG) false.should.be.equal(await bridgeValidators.isValidator(toRemove)) true.should.be.equal(await bridgeValidators.isValidator(toRemove2)) expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('2') @@ -124,49 +156,53 @@ contract('RewardableValidators', async (accounts) => { it('cannot remove non-existent validator', async () => { false.should.be.equal(await bridgeValidators.isValidator(accounts[4])) - await bridgeValidators.removeValidator(accounts[4], {from: owner}).should.be.rejectedWith(ERROR_MSG) - await bridgeValidators.removeValidator(ZERO_ADDRESS, {from: owner}).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.removeValidator(accounts[4], { from: owner }).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.removeValidator(ZERO_ADDRESS, { from: owner }).should.be.rejectedWith(ERROR_MSG) expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('3') }) }) describe('#setRequiredSignatures', async () => { - let owner = accounts[2]; - let validators = [accounts[0], accounts[1], accounts[3]]; - let rewards = accounts.slice(4, 7) - let requiredSignatures = '2'; + const owner = accounts[2] + const validators = [accounts[0], accounts[1], accounts[3]] + const rewards = accounts.slice(4, 7) + const requiredSignatures = '2' beforeEach(async () => { - await bridgeValidators.initialize(requiredSignatures, validators, rewards, owner, {from: owner}).should.be.fulfilled + await bridgeValidators.initialize(requiredSignatures, validators, rewards, owner, { + from: owner + }).should.be.fulfilled expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('3') }) it('sets req signatures', async () => { - let newReqSig = '3'; + const newReqSig = '3' expect(await bridgeValidators.requiredSignatures()).to.be.bignumber.equal(requiredSignatures) - await bridgeValidators.setRequiredSignatures(newReqSig, {from: validators[0]}).should.be.rejectedWith(ERROR_MSG) - await bridgeValidators.setRequiredSignatures(newReqSig, {from: owner}).should.be.fulfilled + await bridgeValidators.setRequiredSignatures(newReqSig, { from: validators[0] }).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.setRequiredSignatures(newReqSig, { from: owner }).should.be.fulfilled expect(await bridgeValidators.requiredSignatures()).to.be.bignumber.equal(newReqSig) }) it('cannot set more than validators count', async () => { - let newReqSig = '4'; + const newReqSig = '4' expect(await bridgeValidators.requiredSignatures()).to.be.bignumber.equal(requiredSignatures) - await bridgeValidators.setRequiredSignatures(newReqSig, {from: owner}).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.setRequiredSignatures(newReqSig, { from: owner }).should.be.rejectedWith(ERROR_MSG) expect(await bridgeValidators.requiredSignatures()).to.be.bignumber.equal(requiredSignatures) }) }) describe('#upgradable', async () => { it('can be upgraded via upgradeToAndCall', async () => { - let storageProxy = await EternalStorageProxy.new().should.be.fulfilled; - let required_signatures = '2'; - let validators = [accounts[0], accounts[1]]; - let rewards = accounts.slice(3, 5); - let owner = accounts[2] - const data = bridgeValidators.contract.methods.initialize(required_signatures, validators,rewards, owner).encodeABI() - await storageProxy.upgradeToAndCall('1', bridgeValidators.address, data).should.be.fulfilled; - let finalContract = await BridgeValidators.at(storageProxy.address); - true.should.be.equal(await finalContract.isInitialized()); - expect(await finalContract.requiredSignatures()).to.be.bignumber.equal(required_signatures) + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled + const requiredSignatures = '2' + const validators = [accounts[0], accounts[1]] + const rewards = accounts.slice(3, 5) + const owner = accounts[2] + const data = bridgeValidators.contract.methods + .initialize(requiredSignatures, validators, rewards, owner) + .encodeABI() + await storageProxy.upgradeToAndCall('1', bridgeValidators.address, data).should.be.fulfilled + const finalContract = await BridgeValidators.at(storageProxy.address) + true.should.be.equal(await finalContract.isInitialized()) + expect(await finalContract.requiredSignatures()).to.be.bignumber.equal(requiredSignatures) true.should.be.equal(await finalContract.isValidator(validators[0])) true.should.be.equal(await finalContract.isValidator(validators[1])) @@ -216,20 +252,11 @@ contract('RewardableValidators', async (accounts) => { await proxy.upgradeTo('1', bridgeValidatorsImpl.address) bridgeValidators = await BridgeValidators.at(proxy.address) const { initialize, isInitialized, removeValidator } = bridgeValidators - await initialize( - 1, - accounts.slice(0, 5), - accounts.slice(5), - owner, - { from: owner } - ).should.be.fulfilled + await initialize(1, accounts.slice(0, 5), accounts.slice(5), owner, { from: owner }).should.be.fulfilled true.should.be.equal(await isInitialized()) // When - const { logs } = await removeValidator( - validator, - { from: owner } - ).should.be.fulfilled + const { logs } = await removeValidator(validator, { from: owner }).should.be.fulfilled // Then expectEventInLogs(logs, 'ValidatorRemoved', { validator }) diff --git a/test/setup.js b/test/setup.js index c770d7918..900217a8c 100644 --- a/test/setup.js +++ b/test/setup.js @@ -1,15 +1,15 @@ -const BN = web3.utils.BN; +const { BN } = web3.utils require('chai') .use(require('chai-as-promised')) .use(require('chai-bn')(BN)) -require('chai/register-should'); +require('chai/register-should') exports.BN = BN exports.toBN = web3.utils.toBN -exports.ERROR_MSG = 'VM Exception while processing transaction: revert'; -exports.ERROR_MSG_OPCODE = 'VM Exception while processing transaction: invalid opcode'; +exports.ERROR_MSG = 'VM Exception while processing transaction: revert' +exports.ERROR_MSG_OPCODE = 'VM Exception while processing transaction: invalid opcode' exports.ZERO_ADDRESS = '0x0000000000000000000000000000000000000000' exports.F_ADDRESS = '0xFFfFfFffFFfffFFfFFfFFFFFffFFFffffFfFFFfF' exports.INVALID_ARGUMENTS = 'Invalid number of arguments to Solidity function' diff --git a/test/validators_test.js b/test/validators_test.js index 50628d641..57a62af0f 100644 --- a/test/validators_test.js +++ b/test/validators_test.js @@ -1,18 +1,18 @@ -const BridgeValidators = artifacts.require("BridgeValidators.sol"); -const EternalStorageProxy = artifacts.require("EternalStorageProxy.sol"); +const BridgeValidators = artifacts.require('BridgeValidators.sol') +const EternalStorageProxy = artifacts.require('EternalStorageProxy.sol') -const { ERROR_MSG, ZERO_ADDRESS, F_ADDRESS, BN } = require('./setup'); -const { expectEventInLogs } = require('./helpers/helpers'); -const { expect } = require('chai'); +const { expect } = require('chai') +const { ERROR_MSG, ZERO_ADDRESS, F_ADDRESS, BN } = require('./setup') +const { expectEventInLogs } = require('./helpers/helpers') const ZERO = new BN(0) -contract('BridgeValidators', async (accounts) => { +contract('BridgeValidators', async accounts => { let bridgeValidators - let owner = accounts[0] + const owner = accounts[0] beforeEach(async () => { - bridgeValidators = await BridgeValidators.new(); + bridgeValidators = await BridgeValidators.new() }) describe('#initialize', async () => { @@ -25,10 +25,16 @@ contract('BridgeValidators', async (accounts) => { expect(await bridgeValidators.requiredSignatures()).to.be.bignumber.equal(ZERO) expect(await bridgeValidators.deployedAtBlock()).to.be.bignumber.equal(ZERO) - await bridgeValidators.initialize(1, [ZERO_ADDRESS], accounts[1], { from: accounts[1] }).should.be.rejectedWith(ERROR_MSG) - await bridgeValidators.initialize(1, [F_ADDRESS], accounts[1], { from: accounts[1] }).should.be.rejectedWith(ERROR_MSG) - await bridgeValidators.initialize(2, accounts.slice(0, 2), accounts[2], {from: accounts[2]}).should.be.fulfilled; - await bridgeValidators.initialize(2, accounts.slice(0, 2), accounts[2], {from: accounts[2]}).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators + .initialize(1, [ZERO_ADDRESS], accounts[1], { from: accounts[1] }) + .should.be.rejectedWith(ERROR_MSG) + await bridgeValidators + .initialize(1, [F_ADDRESS], accounts[1], { from: accounts[1] }) + .should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.initialize(2, accounts.slice(0, 2), accounts[2], { from: accounts[2] }).should.be.fulfilled + await bridgeValidators + .initialize(2, accounts.slice(0, 2), accounts[2], { from: accounts[2] }) + .should.be.rejectedWith(ERROR_MSG) expect(await bridgeValidators.isInitialized()).to.be.equal(true) expect(await bridgeValidators.requiredSignatures()).to.be.bignumber.equal('2') @@ -45,19 +51,19 @@ contract('BridgeValidators', async (accounts) => { }) describe('#addValidator', async () => { - let owner = accounts[2]; - let validators = [accounts[0], accounts[1]]; - let requiredSignatures = 2; + const owner = accounts[2] + const validators = [accounts[0], accounts[1]] + const requiredSignatures = 2 beforeEach(async () => { - await bridgeValidators.initialize(requiredSignatures, validators, owner, {from: owner}).should.be.fulfilled + await bridgeValidators.initialize(requiredSignatures, validators, owner, { from: owner }).should.be.fulfilled expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('2') }) it('adds validator', async () => { - let newValidator = accounts[4]; + const newValidator = accounts[4] false.should.be.equal(await bridgeValidators.isValidator(newValidator)) - await bridgeValidators.addValidator(newValidator, {from: validators[0]}).should.be.rejectedWith(ERROR_MSG) - const {logs} = await bridgeValidators.addValidator(newValidator, {from: owner}).should.be.fulfilled + await bridgeValidators.addValidator(newValidator, { from: validators[0] }).should.be.rejectedWith(ERROR_MSG) + const { logs } = await bridgeValidators.addValidator(newValidator, { from: owner }).should.be.fulfilled expect(await bridgeValidators.isValidator(newValidator)).to.be.equal(true) expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('3') expectEventInLogs(logs, 'ValidatorAdded', { validator: newValidator }) @@ -65,7 +71,7 @@ contract('BridgeValidators', async (accounts) => { it('cannot add already existing validator', async () => { true.should.be.equal(await bridgeValidators.isValidator(validators[0])) - await bridgeValidators.addValidator(validators[0], {from: owner}).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.addValidator(validators[0], { from: owner }).should.be.rejectedWith(ERROR_MSG) expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('2') }) @@ -75,36 +81,36 @@ contract('BridgeValidators', async (accounts) => { }) it(`cannot add 0x0 as validator address`, async () => { - await bridgeValidators.addValidator(ZERO_ADDRESS, {from: owner}).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.addValidator(ZERO_ADDRESS, { from: owner }).should.be.rejectedWith(ERROR_MSG) }) }) describe('#removeValidator', async () => { - let owner = accounts[2]; - let validators = [accounts[0], accounts[1], accounts[3]]; - let requiredSignatures = 2; + const owner = accounts[2] + const validators = [accounts[0], accounts[1], accounts[3]] + const requiredSignatures = 2 beforeEach(async () => { - await bridgeValidators.initialize(requiredSignatures, validators, owner, {from: owner}).should.be.fulfilled + await bridgeValidators.initialize(requiredSignatures, validators, owner, { from: owner }).should.be.fulfilled expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('3') }) it('removes validator', async () => { - let toRemove = validators[0]; + const toRemove = validators[0] expect(await bridgeValidators.isValidator(toRemove)).to.be.equal(true) - await bridgeValidators.removeValidator(toRemove, {from: validators[0]}).should.be.rejectedWith(ERROR_MSG) - const {logs} = await bridgeValidators.removeValidator(toRemove, {from: owner}).should.be.fulfilled + await bridgeValidators.removeValidator(toRemove, { from: validators[0] }).should.be.rejectedWith(ERROR_MSG) + const { logs } = await bridgeValidators.removeValidator(toRemove, { from: owner }).should.be.fulfilled expect(await bridgeValidators.isValidator(toRemove)).to.be.equal(false) expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('2') expectEventInLogs(logs, 'ValidatorRemoved', { validator: toRemove }) }) it('cannot remove if it will break requiredSignatures', async () => { - let toRemove = validators[0]; - let toRemove2 = validators[1]; + const toRemove = validators[0] + const toRemove2 = validators[1] true.should.be.equal(await bridgeValidators.isValidator(toRemove)) true.should.be.equal(await bridgeValidators.isValidator(toRemove)) - await bridgeValidators.removeValidator(toRemove, {from: owner}).should.be.fulfilled - await bridgeValidators.removeValidator(toRemove2, {from: owner}).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.removeValidator(toRemove, { from: owner }).should.be.fulfilled + await bridgeValidators.removeValidator(toRemove2, { from: owner }).should.be.rejectedWith(ERROR_MSG) false.should.be.equal(await bridgeValidators.isValidator(toRemove)) true.should.be.equal(await bridgeValidators.isValidator(toRemove2)) expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('2') @@ -112,47 +118,47 @@ contract('BridgeValidators', async (accounts) => { it('cannot remove non-existent validator', async () => { false.should.be.equal(await bridgeValidators.isValidator(accounts[4])) - await bridgeValidators.removeValidator(accounts[4], {from: owner}).should.be.rejectedWith(ERROR_MSG) - await bridgeValidators.removeValidator(ZERO_ADDRESS, {from: owner}).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.removeValidator(accounts[4], { from: owner }).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.removeValidator(ZERO_ADDRESS, { from: owner }).should.be.rejectedWith(ERROR_MSG) expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('3') }) }) describe('#setRequiredSignatures', async () => { - let owner = accounts[2]; - let validators = [accounts[0], accounts[1], accounts[3]]; - let requiredSignatures = '2'; + const owner = accounts[2] + const validators = [accounts[0], accounts[1], accounts[3]] + const requiredSignatures = '2' beforeEach(async () => { - await bridgeValidators.initialize(requiredSignatures, validators, owner, {from: owner}).should.be.fulfilled + await bridgeValidators.initialize(requiredSignatures, validators, owner, { from: owner }).should.be.fulfilled expect(await bridgeValidators.validatorCount()).to.be.bignumber.equal('3') }) it('sets req signatures', async () => { - let newReqSig = '3'; + const newReqSig = '3' expect(await bridgeValidators.requiredSignatures()).to.be.bignumber.equal(requiredSignatures) - await bridgeValidators.setRequiredSignatures(newReqSig, {from: validators[0]}).should.be.rejectedWith(ERROR_MSG) - await bridgeValidators.setRequiredSignatures(newReqSig, {from: owner}).should.be.fulfilled + await bridgeValidators.setRequiredSignatures(newReqSig, { from: validators[0] }).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.setRequiredSignatures(newReqSig, { from: owner }).should.be.fulfilled expect(await bridgeValidators.requiredSignatures()).to.be.bignumber.equal(newReqSig) }) it('cannot set more than validators count', async () => { - let newReqSig = '4'; + const newReqSig = '4' expect(await bridgeValidators.requiredSignatures()).to.be.bignumber.equal(requiredSignatures) - await bridgeValidators.setRequiredSignatures(newReqSig, {from: owner}).should.be.rejectedWith(ERROR_MSG) + await bridgeValidators.setRequiredSignatures(newReqSig, { from: owner }).should.be.rejectedWith(ERROR_MSG) expect(await bridgeValidators.requiredSignatures()).to.be.bignumber.equal(requiredSignatures) }) }) describe('#upgradable', async () => { it('can be upgraded via upgradeToAndCall', async () => { - let storageProxy = await EternalStorageProxy.new().should.be.fulfilled; - let required_signatures = '2'; - let validators = [accounts[0], accounts[1]]; - let owner = accounts[2] - const data = bridgeValidators.contract.methods.initialize(required_signatures, validators, owner).encodeABI() - await storageProxy.upgradeToAndCall('1', bridgeValidators.address, data).should.be.fulfilled; - let finalContract = await BridgeValidators.at(storageProxy.address); - true.should.be.equal(await finalContract.isInitialized()); - expect(await finalContract.requiredSignatures()).to.be.bignumber.equal(required_signatures) + const storageProxy = await EternalStorageProxy.new().should.be.fulfilled + const requiredSignatures = '2' + const validators = [accounts[0], accounts[1]] + const owner = accounts[2] + const data = bridgeValidators.contract.methods.initialize(requiredSignatures, validators, owner).encodeABI() + await storageProxy.upgradeToAndCall('1', bridgeValidators.address, data).should.be.fulfilled + const finalContract = await BridgeValidators.at(storageProxy.address) + true.should.be.equal(await finalContract.isInitialized()) + expect(await finalContract.requiredSignatures()).to.be.bignumber.equal(requiredSignatures) true.should.be.equal(await finalContract.isValidator(validators[0])) true.should.be.equal(await finalContract.isValidator(validators[1])) @@ -202,19 +208,11 @@ contract('BridgeValidators', async (accounts) => { await proxy.upgradeTo('1', bridgeValidatorsImpl.address) bridgeValidators = await BridgeValidators.at(proxy.address) const { initialize, isInitialized, removeValidator } = bridgeValidators - await initialize( - 1, - accounts.slice(0, 5), - owner, - { from: owner } - ).should.be.fulfilled + await initialize(1, accounts.slice(0, 5), owner, { from: owner }).should.be.fulfilled true.should.be.equal(await isInitialized()) // When - const { logs } = await removeValidator( - validator, - { from: owner } - ).should.be.fulfilled + const { logs } = await removeValidator(validator, { from: owner }).should.be.fulfilled // Then expectEventInLogs(logs, 'ValidatorRemoved', { validator }) diff --git a/truffle-config.js b/truffle-config.js index a3c510631..33730c37c 100644 --- a/truffle-config.js +++ b/truffle-config.js @@ -1,15 +1,16 @@ const spuriousDragonVersion = process.argv[3] === 'spuriousDragon' const contractsBuildDirectory = spuriousDragonVersion ? './build/spuriousDragon' : './build/contracts' const evmVersion = spuriousDragonVersion ? 'spuriousDragon' : 'byzantium' -const mochaOptions = process.env.GASREPORT === 'true' - ? { - reporter: 'eth-gas-reporter', - reporterOptions : { - currency: 'USD', - gasPrice: 1 - } - } - : {} +const mochaOptions = + process.env.GASREPORT === 'true' + ? { + reporter: 'eth-gas-reporter', + reporterOptions: { + currency: 'USD', + gasPrice: 1 + } + } + : {} module.exports = { contracts_build_directory: contractsBuildDirectory, @@ -19,7 +20,7 @@ module.exports = { network_id: '*', // eslint-disable-line camelcase port: 8555, gas: 0xfffffffffff, - gasPrice: 0x01, + gasPrice: 0x01 }, ganache: { host: '127.0.0.1', @@ -30,15 +31,15 @@ module.exports = { }, compilers: { solc: { - version: "0.4.24", + version: '0.4.24', settings: { optimizer: { enabled: true, runs: 200 }, - evmVersion: evmVersion + evmVersion } } }, mocha: mochaOptions -}; +} From 2cdff962bb30174192d8956b1c549167db27a8dd Mon Sep 17 00:00:00 2001 From: Gerardo Nardelli Date: Tue, 14 May 2019 14:08:23 -0300 Subject: [PATCH 186/187] Fix used HomeBridgeNativeToErc contract on deploy script --- deploy/src/loadContracts.js | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/deploy/src/loadContracts.js b/deploy/src/loadContracts.js index e7c56499f..c44c55095 100644 --- a/deploy/src/loadContracts.js +++ b/deploy/src/loadContracts.js @@ -28,7 +28,9 @@ function getContracts(evmVersion) { FeeManagerNativeToErc: require(`../../build/${buildPath}/FeeManagerNativeToErc.json`), ForeignBridgeNativeToErc: require(`../../build/${buildPath}/ForeignBridgeNativeToErc.json`), FeeManagerNativeToErcBothDirections: require(`../../build/${buildPath}/FeeManagerNativeToErcBothDirections.json`), - HomeBridgeNativeToErc: require(`../../build/${buildPath}/HomeBridgeNativeToErc.json`), + HomeBridgeNativeToErc: useClassicProxy + ? require(`../../build/${buildPath}/ClassicHomeBridgeNativeToErc.json`) + : require(`../../build/${buildPath}/HomeBridgeNativeToErc.json`), BlockReward: require(`../../build/${buildPath}/BlockReward.json`) } } From a7c07521d5efa6fcda4c78ac369f0393b53f24d6 Mon Sep 17 00:00:00 2001 From: Alexander Kolotov Date: Wed, 22 May 2019 02:07:40 +0300 Subject: [PATCH 187/187] new contracts should be flatten after #181 --- flatten.sh | 2 ++ 1 file changed, 2 insertions(+) diff --git a/flatten.sh b/flatten.sh index 532f90e2d..e9ca1a049 100755 --- a/flatten.sh +++ b/flatten.sh @@ -15,6 +15,7 @@ VALIDATOR_CONTRACTS_DIR=contracts/upgradeable_contracts echo "Flattening common bridge contracts" ${FLATTENER} contracts/upgradeability/EternalStorageProxy.sol > flats/EternalStorageProxy_flat.sol +${FLATTENER} contracts/upgradeability/ClassicEternalStorageProxy.sol > flats/ClassicEternalStorageProxy_flat.sol ${FLATTENER} contracts/ERC677BridgeToken.sol > flats/ERC677BridgeToken_flat.sol ${FLATTENER} contracts/ERC677BridgeTokenRewardable.sol > flats/ERC677BridgeTokenRewardable_flat.sol @@ -25,6 +26,7 @@ ${FLATTENER} ${VALIDATOR_CONTRACTS_DIR}/RewardableValidators.sol > flats/validat echo "Flattening contracts related to native-to-erc bridge" ${FLATTENER} ${BRIDGE_CONTRACTS_DIR}/native_to_erc20/ForeignBridgeNativeToErc.sol > flats/native_to_erc20/ForeignBridgeNativeToErc_flat.sol ${FLATTENER} ${BRIDGE_CONTRACTS_DIR}/native_to_erc20/HomeBridgeNativeToErc.sol > flats/native_to_erc20/HomeBridgeNativeToErc_flat.sol +${FLATTENER} ${BRIDGE_CONTRACTS_DIR}/native_to_erc20/ClassicHomeBridgeNativeToErc.sol > flats/native_to_erc20/ClassicHomeBridgeNativeToErc_flat.sol ${FLATTENER} ${BRIDGE_CONTRACTS_DIR}/native_to_erc20/FeeManagerNativeToErc.sol > flats/native_to_erc20/FeeManagerNativeToErc_flat.sol ${FLATTENER} ${BRIDGE_CONTRACTS_DIR}/native_to_erc20/FeeManagerNativeToErcBothDirections.sol > flats/native_to_erc20/FeeManagerNativeToErcBothDirections_flat.sol