public async Task TestTransferTokens() { var colorCoin = await _coinRepository.GetCoinByAddress(_tokenAdapterAddress); var toAddress = _settings.EthereumMainAccount; await CashinTokens(_externalTokenAddress, _clientTokenTransferAddress, new BigInteger(100), _tokenAdapterAddress, _clientA); var transferUser = await _transferContractService.GetTransferAddressUser(colorCoin.AdapterAddress, _clientTokenTransferAddress); var currentBalance = await _transferContractService.GetBalanceOnAdapter(colorCoin.AdapterAddress, _clientA); Assert.AreEqual(transferUser, _clientA.ToLower()); var guid = Guid.NewGuid(); EthUtils.GuidToBigInteger(guid); var externalSign = await _exchangeService.GetSign(guid, _tokenAdapterAddress, _clientA, toAddress, currentBalance); var transferHash = await _exchangeService.Transfer(guid, _tokenAdapterAddress, _clientA, toAddress, currentBalance, externalSign); while (await _transactionService.GetTransactionReceipt(transferHash) == null) { await Task.Delay(100); } var currentBalanceOnAdapter = await _transferContractService.GetBalanceOnAdapter(colorCoin.AdapterAddress, _clientA); var newBalance = await _transferContractService.GetBalanceOnAdapter(colorCoin.AdapterAddress, toAddress); Assert.IsTrue(await _transactionService.IsTransactionExecuted(transferHash, Constants.GasForCoinTransaction)); Assert.IsTrue(currentBalanceOnAdapter == 0); Assert.IsTrue(currentBalance <= newBalance); }
public async Task <IdCheckResult> CheckId(Guid guidToCheck) { var contract = _web3.Eth.GetContract(_settings.MainExchangeContract.Abi, _settings.MainExchangeContract.Address); var transactionsCheck = contract.GetFunction("transactions"); bool isInList = true; Guid useNext = guidToCheck; while (isInList) { var bigIntRepresentation = EthUtils.GuidToBigInteger(useNext); isInList = await transactionsCheck.CallAsync <bool>(bigIntRepresentation); if (isInList) { useNext = Guid.NewGuid(); } } return(new IdCheckResult() { IsFree = useNext == guidToCheck, ProposedId = useNext }); }
public async Task <string> CashOut(Guid id, string coinAddress, string clientAddr, string toAddr, BigInteger amount, string sign) { await ThrowOnExistingId(id); var coinAFromDb = await GetCoinWithCheck(coinAddress); if (string.IsNullOrEmpty(sign)) { sign = await GetSign(id, coinAddress, clientAddr, toAddr, amount); } ThrowOnWrongSignature(id, coinAddress, clientAddr, toAddr, amount, sign); var contract = _web3.Eth.GetContract(_settings.MainExchangeContract.Abi, _settings.MainExchangeContract.Address); var cashout = contract.GetFunction("cashout"); var convertedId = EthUtils.GuidToBigInteger(id); // function cashout(uint id, address coinAddress, address client, address to, uint amount, bytes client_sign, bytes params) onlyowner { var transactionHash = await cashout.SendTransactionAsync(Constants.AddressForRoundRobinTransactionSending, new HexBigInteger(Constants.GasForCoinTransaction), new HexBigInteger(0), convertedId, coinAFromDb.AdapterAddress, clientAddr, toAddr, amount, sign.HexToByteArray().FixByteOrder(), new byte[0]); await SaveUserHistory(coinAddress, amount.ToString(), clientAddr, toAddr, transactionHash, "CashOut"); await CreatePendingTransaction(coinAddress, clientAddr, transactionHash); return(transactionHash); }
public async Task <string> Transfer(Guid id, string coinAddress, string from, string to, BigInteger amount, string sign) { await ThrowOnExistingId(id); var coinAFromDb = await GetCoinWithCheck(coinAddress); if (string.IsNullOrEmpty(sign)) { sign = await GetSign(id, coinAddress, from, to, amount); } ThrowOnWrongSignature(id, coinAddress, from, to, amount, sign); var contract = _web3.Eth.GetContract(_settings.MainExchangeContract.Abi, _settings.MainExchangeContract.Address); var transferFunction = contract.GetFunction("transfer"); var convertedId = EthUtils.GuidToBigInteger(id); var transactionHash = await transferFunction.SendTransactionAsync(Constants.AddressForRoundRobinTransactionSending, new HexBigInteger(Constants.HalfGasLimit), new HexBigInteger(0), convertedId, coinAFromDb.AdapterAddress, from, to, amount, sign.HexToByteArray().FixByteOrder(), new byte[0]); await SaveUserHistory(coinAddress, amount.ToString(), from, to, transactionHash, "Transfer"); await CreatePendingTransaction(coinAddress, from, transactionHash); return(transactionHash); }
public async Task <OperationEstimationResult> EstimateCashoutGas(Guid id, string coinAdapterAddress, string fromAddress, string toAddress, BigInteger amount, string sign) { var blackListedAddress = await _blackListAddressesRepository.GetAsync(toAddress); var whiteListedAddress = await _whiteListAddressesRepository.GetAsync(toAddress); if (blackListedAddress != null && whiteListedAddress == null) { return(new OperationEstimationResult() { GasAmount = Constants.GasForCoinTransaction, IsAllowed = false }); } //It is ok. if (ChaosKitty.MeowButLogically()) { return(new OperationEstimationResult() { GasAmount = 50000, IsAllowed = true }); } var coinAFromDb = await GetCoinWithCheck(coinAdapterAddress); if (string.IsNullOrEmpty(sign)) { sign = await GetSign(id, coinAdapterAddress, fromAddress, toAddress, amount); } ThrowOnWrongSignature(id, coinAdapterAddress, fromAddress, toAddress, amount, sign); var contract = _web3.Eth.GetContract(_settings.MainExchangeContract.Abi, _settings.MainExchangeContract.Address); var cashout = contract.GetFunction("cashout"); var convertedId = EthUtils.GuidToBigInteger(id); //ACTION var estimatedGasForOperation = await cashout.EstimateGasAsync(_settings.EthereumMainAccount, new HexBigInteger(Constants.GasForCoinTransaction), new HexBigInteger(0), convertedId, _addressUtil.ConvertToChecksumAddress(coinAFromDb.AdapterAddress), fromAddress, toAddress, amount, sign.HexToByteArray(), new byte[0]); return(new OperationEstimationResult() { GasAmount = estimatedGasForOperation.Value, IsAllowed = estimatedGasForOperation.Value < Constants.GasForCoinTransaction }); }
private async Task ThrowOnExistingId(Guid id) { var contract = _web3.Eth.GetContract(_settings.MainExchangeContract.Abi, _settings.MainExchangeContract.Address); var transactionsCheck = contract.GetFunction("transactions"); var bigIntRepresentation = EthUtils.GuidToBigInteger(id); bool isInList = await transactionsCheck.CallAsync <bool>(bigIntRepresentation); if (isInList) { throw new ClientSideException(ExceptionType.OperationWithIdAlreadyExists, $"operation with guid {id}"); } }
public async Task <string> CashIn(Guid id, string coinAddress, string receiver, BigInteger amount) { var web3 = new Web3(_settings.EthereumUrl); await web3.Personal.UnlockAccount.SendRequestAsync(_settings.EthereumMainAccount, _settings.EthereumMainAccountPassword, 120); var coinAFromDb = await _coinRepository.GetCoinByAddress(coinAddress); if (coinAFromDb == null) { throw new Exception($"Coin with address {coinAddress} deos not exist"); } Contract contract; if (coinAFromDb.ContainsEth) { contract = web3.Eth.GetContract(_settings.EthAdapterContract.Abi, coinAFromDb.AdapterAddress); } else { contract = web3.Eth.GetContract(_settings.TokenAdapterContract.Abi, coinAFromDb.AdapterAddress); } var convertedAmountA = amount; var convertedId = EthUtils.GuidToBigInteger(id); var cashin = contract.GetFunction("cashin"); var res = await cashin.CallAsync <bool>(_settings.EthereumMainAccount, new HexBigInteger(Constants.GasForCoinTransaction), new HexBigInteger(0), receiver, convertedAmountA); string tr; if (coinAFromDb.ContainsEth) { tr = await cashin.SendTransactionAsync(_settings.EthereumMainAccount, new HexBigInteger(Constants.GasForCoinTransaction), new HexBigInteger(convertedAmountA), receiver, convertedAmountA); } else { tr = await cashin.SendTransactionAsync(_settings.EthereumMainAccount, new HexBigInteger(Constants.GasForCoinTransaction), new HexBigInteger(0), receiver, convertedAmountA); } return(tr); }
public async Task TestCheckSign_IsWrong() { var guid = Guid.NewGuid(); var amount = 50; EthUtils.GuidToBigInteger(guid); var strForHash = EthUtils.GuidToByteArray(guid).ToHex() + _ethereumAdapterAddress.HexToByteArray().ToHex() + _clientA.HexToByteArray().ToHex() + _clientA.HexToByteArray().ToHex() + EthUtils.BigIntToArrayWithPadding(new BigInteger(amount)).ToHex(); var hash = new Sha3Keccack().CalculateHash(strForHash.HexToByteArray()); var sign = Sign(hash, _privateKeyA).ToHex(); var result = _exchangeService.CheckSign(guid, _ethereumAdapterAddress, _clientA, _clientA, new BigInteger(amount - 1), sign); Assert.IsFalse(result); }
public async Task <string> CashinOverTransferContract(Guid id, string coin, string receiver, decimal amount) { var coinDb = await _coinRepository.GetCoin(coin); if (!coinDb.BlockchainDepositEnabled) { throw new ClientSideException(ExceptionType.WrongParams, "Coin must be payable"); } var contract = _web3.Eth.GetContract(_settings.TokenTransferContract.Abi, _settings.TokenTransferContract.Address); var cashin = contract.GetFunction("cashin"); var blockchainAmount = amount.ToBlockchainAmount(coinDb.Multiplier); var convertedId = EthUtils.GuidToBigInteger(id); var tr = await cashin.SendTransactionAsync(_settings.EthereumMainAccount, new HexBigInteger(Constants.GasForCoinTransaction), new HexBigInteger(0), convertedId, coinDb.AdapterAddress, receiver, blockchainAmount, Constants.GasForCoinTransaction, new byte[0]); return(tr); }
//Main Exchange contract should be migrated to use the function below in an appropriate way. public async Task <string> TransferWithoutSignCheck(Guid id, string coinAddress, string from, string to, BigInteger amount, string sign = "01") { await ThrowOnExistingId(id); var coinAFromDb = await GetCoinWithCheck(coinAddress); var contract = _web3.Eth.GetContract(_settings.MainExchangeContract.Abi, _settings.MainExchangeContract.Address); var transferFunction = contract.GetFunction("transfer"); var convertedId = EthUtils.GuidToBigInteger(id); var transactionHash = await transferFunction.SendTransactionAsync(_settings.EthereumMainAccount, new HexBigInteger(Constants.GasForCoinTransaction), new HexBigInteger(0), convertedId, coinAFromDb.AdapterAddress, from, to, amount, sign.HexToByteArray(), new byte[0]); await SaveUserHistory(coinAddress, amount.ToString(), from, to, transactionHash, "TransferWithoutSignCheck"); return(transactionHash); }
public async Task TestCheckSign_IsCorrect() { var guid = Guid.NewGuid(); var amount = 50; EthUtils.GuidToBigInteger(guid); var strForHash = EthUtils.GuidToByteArray(guid).ToHex() + _tokenAdapterAddress.HexToByteArray().ToHex() + _clientA.HexToByteArray().ToHex() + _clientA.HexToByteArray().ToHex() + EthUtils.BigIntToArrayWithPadding(new BigInteger(amount)).ToHex(); var hash = new Sha3Keccack().CalculateHash(strForHash.HexToByteArray()); var sign = Sign(hash, _privateKeyA).ToHex(); //var externalSign = await _exchangeService.GetSign(guid, _tokenAdapterAddress, ClientA, ClientA, new BigInteger(amount)); var result = _exchangeService.CheckSign(guid, _tokenAdapterAddress, _clientA, _clientA, new BigInteger(amount), sign); Assert.IsTrue(result); }
public async Task <string> TransferWithChange(Guid id, string coinAddress, string from, string to, BigInteger amount, string signFrom, BigInteger change, string signTo) { if (amount <= change) { throw new ClientSideException(ExceptionType.WrongParams, "Amount can't be less or equal than change"); } await ThrowOnExistingId(id); var coinAFromDb = await GetCoinWithCheck(coinAddress); if (string.IsNullOrEmpty(signFrom)) { signFrom = await GetSign(id, coinAddress, from, to, amount); } if (string.IsNullOrEmpty(signTo)) { signTo = await GetSign(id, coinAddress, to, from, change); } ThrowOnWrongSignature(id, coinAddress, from, to, amount, signFrom); ThrowOnWrongSignature(id, coinAddress, to, from, change, signTo); var contract = _web3.Eth.GetContract(_settings.MainExchangeContract.Abi, _settings.MainExchangeContract.Address); var transferFunction = contract.GetFunction("transferWithChange"); var convertedId = EthUtils.GuidToBigInteger(id); var transactionHash = await transferFunction.SendTransactionAsync(Constants.AddressForRoundRobinTransactionSending, new HexBigInteger(Constants.HalfGasLimit), new HexBigInteger(0), convertedId, coinAFromDb.AdapterAddress, from, to, amount, change, signFrom.HexToByteArray().FixByteOrder(), signTo.HexToByteArray().FixByteOrder(), new byte[0]); var difference = (amount - change); await SaveUserHistory(coinAddress, difference.ToString(), from, to, transactionHash, "TransferWithChange"); await CreatePendingTransaction(coinAddress, from, transactionHash); return(transactionHash); }
private async Task ThrowOnExistingId(Guid id) { //Check Old contract(Prevent old transactions from executing) var addresses = new string[] { _settings.MainExchangeContract.Address, _settings.PreviousMainExchangeContractAddress }; foreach (var address in addresses) { var contract = _web3.Eth.GetContract(_settings.MainExchangeContract.Abi, address); var transactionsCheck = contract.GetFunction("transactions"); var bigIntRepresentation = EthUtils.GuidToBigInteger(id); bool isInList = await transactionsCheck.CallAsync <bool>(bigIntRepresentation); if (isInList) { throw new ClientSideException(ExceptionType.OperationWithIdAlreadyExists, $"operation with guid {id}"); } } }
//public async Task<string> Swap(Guid id, string clientA, string clientB, string coinA, string coinB, decimal amountA, decimal amountB, string signAHex, // string signBHex) //{ // var web3 = new Web3(_settings.EthereumUrl); // await web3.Personal.UnlockAccount.SendRequestAsync(_settings.EthereumMainAccount, _settings.EthereumMainAccountPassword, new HexBigInteger(120)); // var contract = web3.Eth.GetContract(_settings.MainExchangeContract.Abi, _settings.MainExchangeContract.Address); // var coinAFromDb = await _coinRepository.GetCoin(coinA); // var coinBFromDb = await _coinRepository.GetCoin(coinB); // var convertedAmountA = amountA.ToBlockchainAmount(coinAFromDb.Multiplier); // var convertedAmountB = amountB.ToBlockchainAmount(coinBFromDb.Multiplier); // var convertedId = EthUtils.GuidToBigInteger(id); // var swap = contract.GetFunction("swap"); // var tr = await swap.SendTransactionAsync(_settings.EthereumMainAccount, new HexBigInteger(Constants.GasForCoinTransaction), new HexBigInteger(0), // convertedId, clientA, clientB, coinAFromDb.AdapterAddress, coinBFromDb.AdapterAddress, convertedAmountA, convertedAmountB, signAHex.HexToByteArray().FixByteOrder(), signBHex.HexToByteArray().FixByteOrder(), new byte[0]); // await _cointTransactionService.PutTransactionToQueue(tr); // return tr; //} public async Task <OperationEstimationResult> EstimateCashoutGas(Guid id, string coinAdapterAddress, string fromAddress, string toAddress, BigInteger amount, string sign) { var coinAFromDb = await GetCoinWithCheck(coinAdapterAddress); if (string.IsNullOrEmpty(sign)) { sign = await GetSign(id, coinAdapterAddress, fromAddress, toAddress, amount); } ThrowOnWrongSignature(id, coinAdapterAddress, fromAddress, toAddress, amount, sign); var contract = _web3.Eth.GetContract(_settings.MainExchangeContract.Abi, _settings.MainExchangeContract.Address); var cashout = contract.GetFunction("cashout"); var convertedId = EthUtils.GuidToBigInteger(id); //ACTION var estimatedGasForOperation = await cashout.EstimateGasAsync(_settings.EthereumMainAccount, new HexBigInteger(Constants.GasForCoinTransaction), new HexBigInteger(0), convertedId, coinAFromDb.AdapterAddress, fromAddress, toAddress, amount, sign.HexToByteArray().FixByteOrder(), new byte[0]); return(new OperationEstimationResult() { GasAmount = estimatedGasForOperation.Value, IsAllowed = estimatedGasForOperation.Value < Constants.GasForCoinTransaction }); }