public async Task TransferAllAssetsToAddress(string clientId, string srcAddress, string srcPrivateKey, string destAddress) { var transactionId = Guid.NewGuid().ToString("N"); var transfer = await _transferEventsRepository.RegisterAsync(TransferEvent.CreateNewTransferAll(clientId, transactionId, srcAddress)); var contextData = TransferContextData.Create(new TransferContextData.TransferModel { ClientId = clientId, OperationId = transfer.Id }); await _bitCoinTransactionsRepository.CreateAsync(transactionId, null, contextData); if (_baseSettings.UsePushPrivateKeyService) { await _srvBlockchainHelper.PushPrivateKey(srcPrivateKey); srcPrivateKey = null; } var assets = (await _assetsDict.Values()).ToArray(); bool needToTransferAssets = (await _srvBlockchainReader.GetBalancesForAdress(srcAddress, assets)).Any(x => x.Balance > 0); if (needToTransferAssets) { var queueMsg = await _bitCoinCommandProducer.TransferAllAssetsToAddress(transactionId, srcAddress, srcPrivateKey, destAddress); await _bitCoinTransactionsRepository.UpdateRequestAsync(transactionId, queueMsg); } }
public async Task <CommandHandlingResult> Handle(Commands.SaveTransferOperationStateCommand command, IEventPublisher eventPublisher) { var message = command.QueueMessage; var transactionId = message.Id; var transaction = await _transactionsRepository.FindByTransactionIdAsync(transactionId); if (transaction == null) { _log.Error(nameof(Commands.SaveManualOperationStateCommand), new Exception($"unknown transaction {transactionId}"), context: command); return(CommandHandlingResult.Ok()); } var amountNoFee = await _feeCalculationService.GetAmountNoFeeAsync(message); var context = await _transactionService.GetTransactionContext <TransferContextData>(transactionId) ?? TransferContextData.Create( message.FromClientId, new TransferContextData.TransferModel { ClientId = message.ToClientid }, new TransferContextData.TransferModel { ClientId = message.FromClientId }); context.Transfers[0].OperationId = Guid.NewGuid().ToString(); context.Transfers[1].OperationId = Guid.NewGuid().ToString(); var destWallet = await _walletCredentialsRepository.GetAsync(message.ToClientid); var sourceWallet = await _walletCredentialsRepository.GetAsync(message.FromClientId); var contextJson = context.ToJson(); var cmd = new TransferCommand { Amount = amountNoFee, AssetId = message.AssetId, Context = contextJson, SourceAddress = sourceWallet?.MultiSig, DestinationAddress = destWallet?.MultiSig, TransactionId = Guid.Parse(transactionId) }; await SaveState(cmd, context); eventPublisher.PublishEvent(new TransferOperationStateSavedEvent { TransactionId = transactionId, QueueMessage = message, AmountNoFee = (double)amountNoFee }); return(CommandHandlingResult.Ok()); }
public async Task GenerateTransferFromOrdinaryWallet(string clientId, string sourceAddress, string sourceKey, double amount, string assetId, TransferContextData.AdditionalActions additionalActionsDest = null) { var asset = await _assetsRepository.GetAssetAsync(assetId); if (asset == null) { return; } amount = Math.Abs(amount); var transactionId = Guid.NewGuid().ToString("N"); var clientCreds = await _walletCredentialsRepository.GetAsync(clientId); var transfer = await _transferEventsRepository.RegisterAsync(TransferEvent.CreateNew(clientId, clientCreds.MultiSig, null, assetId, amount, transactionId, sourceAddress, clientCreds.MultiSig)); var contextData = TransferContextData.Create(new TransferContextData.TransferModel { ClientId = clientId, OperationId = transfer.Id, Actions = additionalActionsDest }); if (_baseSettings.UsePushPrivateKeyService) { await _srvBlockchainHelper.PushPrivateKey(sourceKey, true); sourceKey = null; } var queueMsg = await _bitCoinCommandProducer.ProduceGenerateTransferAsync(transactionId, sourceAddress, sourceKey, clientCreds.MultiSig, amount, asset.BlockChainId); await _bitCoinTransactionsRepository.CreateAsync(transactionId, queueMsg, contextData); }
public async Task <string> GenerateTransfer(string destClientId, string sourceClientId, double amount, string assetId, bool fromBtcConvWallet = false, TransferContextData.AdditionalActions additionalActionsDest = null, TransferContextData.AdditionalActions additionalActionsSrc = null) { var asset = await _assetsRepository.GetAssetAsync(assetId); if (asset == null) { throw new ArgumentNullException(nameof(assetId)); } amount = Math.Abs(amount); var transactionId = Guid.NewGuid().ToString("N"); var destClientCredentials = await _walletCredentialsRepository.GetAsync(destClientId); var sourceWalletCred = await _walletCredentialsRepository.GetAsync(sourceClientId); var destTransfer = await _transferEventsRepository.RegisterAsync(TransferEvent.CreateNew(destClientId, destClientCredentials.MultiSig, null, assetId, amount, transactionId, destClientCredentials.Address, destClientCredentials.MultiSig)); var sourceTransfer = await _transferEventsRepository.RegisterAsync(TransferEvent.CreateNew(sourceClientId, fromBtcConvWallet ? sourceWalletCred.BtcConvertionWalletAddress : sourceWalletCred.MultiSig, null, assetId, -amount, transactionId, sourceWalletCred.Address, sourceWalletCred.MultiSig)); var contextData = TransferContextData.Create(new TransferContextData.TransferModel { ClientId = destClientId, OperationId = destTransfer.Id, Actions = additionalActionsDest }, new TransferContextData.TransferModel { ClientId = sourceClientId, OperationId = sourceTransfer.Id, Actions = additionalActionsSrc }); var pk = fromBtcConvWallet ? sourceWalletCred.BtcConvertionWalletPrivateKey : sourceWalletCred.PrivateKey; if (_baseSettings.UsePushPrivateKeyService) { await _srvBlockchainHelper.PushPrivateKey(pk, fromBtcConvWallet); } var queueMsg = await _bitCoinCommandProducer.ProduceGenerateTransferAsync(transactionId, fromBtcConvWallet?sourceWalletCred.BtcConvertionWalletAddress : sourceWalletCred.MultiSig, _baseSettings.UsePushPrivateKeyService?null : pk, destClientCredentials.MultiSig, amount, asset.BlockChainId); await _bitCoinTransactionsRepository.CreateAsync(transactionId, queueMsg, contextData); return(destTransfer.Id); }
public async Task <bool> ProcessMessage(TransferQueueMessage queueMessage) { var amount = queueMessage.Amount.ParseAnyDouble(); //Get client wallets var toWallet = await _walletCredentialsRepository.GetAsync(queueMessage.ToClientid); var fromWallet = await _walletCredentialsRepository.GetAsync(queueMessage.FromClientId); //Register transfer events var destTransfer = await _transferEventsRepository.RegisterAsync( TransferEvent.CreateNew(queueMessage.ToClientid, toWallet.MultiSig, null, queueMessage.AssetId, amount, queueMessage.Id, toWallet.Address, toWallet.MultiSig, state: TransactionStates.SettledOffchain)); var sourceTransfer = await _transferEventsRepository.RegisterAsync( TransferEvent.CreateNew(queueMessage.FromClientId, fromWallet.MultiSig, null, queueMessage.AssetId, -amount, queueMessage.Id, fromWallet.Address, fromWallet.MultiSig, state: TransactionStates.SettledOffchain)); //Craete or Update transfer context var transaction = await _bitCoinTransactionsRepository.FindByTransactionIdAsync(queueMessage.Id); if (transaction == null) { await _log.WriteWarningAsync(nameof(TransferQueue), nameof(ProcessMessage), queueMessage.ToJson(), "unkown transaction"); return(false); } var contextData = await _bitcoinTransactionService.GetTransactionContext <TransferContextData>(transaction.TransactionId); if (contextData == null) { contextData = TransferContextData .Create(queueMessage.FromClientId, new TransferContextData.TransferModel { ClientId = queueMessage.ToClientid }, new TransferContextData.TransferModel { ClientId = queueMessage.FromClientId }); } contextData.Transfers[0].OperationId = destTransfer.Id; contextData.Transfers[1].OperationId = sourceTransfer.Id; var contextJson = contextData.ToJson(); var cmd = new TransferCommand { Amount = amount, AssetId = queueMessage.AssetId, Context = contextJson, SourceAddress = fromWallet.MultiSig, DestinationAddress = toWallet.MultiSig, TransactionId = Guid.Parse(queueMessage.Id) }; await _bitCoinTransactionsRepository.UpdateAsync(transaction.TransactionId, cmd.ToJson(), null, ""); await _bitcoinTransactionService.SetTransactionContext(transaction.TransactionId, contextData); if (await _clientSettingsRepository.IsOffchainClient(queueMessage.ToClientid)) { if (!await _clientAccountsRepository.IsTrusted(queueMessage.ToClientid)) { try { await _offchainRequestService.CreateOffchainRequestAndNotify(transaction.TransactionId, queueMessage.ToClientid, queueMessage.AssetId, (decimal)amount, null, OffchainTransferType.CashinToClient); } catch (Exception) { await _log.WriteWarningAsync(nameof(TransferQueue), nameof(ProcessMessage), "", $"Transfer already exists {transaction.TransactionId}"); } } } else { await _bitcoinCommandSender.SendCommand(cmd); } return(true); }