Example #1
0
        public async Task <GeneralWithdrawModel> SendToAddress(GeneralWithdrawModel model, string userId)
        {
            try
            {
                var wallet = await _walletsRepository.GetUserWalletAsync(userId, model.Currency);

                decimal?_amount = model.Amount.ConvertToDecimal();

                if (wallet != null && _amount.Value > 0 && _amount.Value <= wallet.Value)
                {
                    var result = await _balanceProvider.Withdraw(_amount.Value, wallet);

                    wallet.Value = result.ResultBalanceSender;


                    var tr = await _outcomeTransactionRepository.CreateOutcomeTransaction(
                        new OutcomeTransactionTableModel()
                    {
                        FromWalletId       = wallet.Id,
                        ToAddress          = model.Address,
                        Value              = _amount.Value,
                        PlatformCommission = result.Commission,
                        CurrencyAcronim    = "ZEC",
                        State              = (int)OutcomeTransactionStateEnum.Finished
                    });

                    // check if need to convert Amount
                    var txId = _client.MakeRequest <string>(ZecRestMethods.sendtoaddress, model.Address, model.Amount);


                    await _eventsRepository.CreateEventAsync(new EventTableModel()
                    {
                        UserId          = userId,
                        Type            = (int)EventTypeEnum.Withdraw,
                        Comment         = model.Comment,
                        Value           = _amount.Value,
                        StartBalance    = result.StartBalanceSender,
                        ResultBalance   = result.ResultBalanceSender,
                        WhenDate        = DateTime.Now,
                        CurrencyAcronim = model.Currency
                    });

                    model.Status = "Success";
                    await _walletsRepository.UpdateWalletBalanceAsync(wallet);
                }
                else
                {
                    model.Status = "Not enough coins";
                }
            }
            catch (Exception e)
            {
                model.Status = "Error";
                return(model);
            }

            return(model);
        }
        public async Task <GeneralWithdrawModel> SendToAddress(GeneralWithdrawModel model, string userId)
        {
            // оставляем запас 0.001 на комисию блокчейна, можно вынесли в константы
            decimal fixedCommicion = 0.001m;

            try
            {
                var wallet = await _walletsRepository.GetUserWalletAsync(userId, model.Currency);

                decimal?_amount = model.Amount.ConvertToDecimal();

                if (wallet != null && _amount.Value > 0 && _amount.Value + fixedCommicion <= wallet.Value)
                {
                    var resultBalance = await _balanceProvider.Withdraw(_amount.Value, wallet);

                    var tr = await _outcomeTransactionRepository.CreateOutcomeTransaction(
                        new OutcomeTransactionTableModel()
                    {
                        FromWalletId       = wallet.Id,
                        ToAddress          = model.Address,
                        Value              = _amount.Value,
                        PlatformCommission = resultBalance.Commission,
                        FixedCommission    = fixedCommicion,
                        CurrencyAcronim    = "ETH",
                        State              = (int)OutcomeTransactionStateEnum.Created,
                    });

                    var resultTr = await _ethRequestClient.ExecuteTransactionAsync(tr.Id);

                    if (resultTr.IsSuccess)
                    {
                        wallet.Value = resultBalance.ResultBalanceSender - resultTr.CommissionBlockchain.Value;
                        await _walletsRepository.UpdateWalletBalanceAsync(wallet);

                        tr.State = resultTr.OutcomeTransactionState;
                        tr.BlockchainCommission = resultTr.CommissionBlockchain;

                        await _eventsRepository.CreateEventAsync(new EventTableModel()
                        {
                            UserId          = userId,
                            Type            = (int)EventTypeEnum.Withdraw,
                            Comment         = model.Comment,
                            Value           = _amount.Value + resultTr.CommissionBlockchain.Value,
                            StartBalance    = resultBalance.StartBalanceSender,
                            ResultBalance   = resultBalance.ResultBalanceSender - resultTr.CommissionBlockchain.Value,
                            WhenDate        = DateTime.Now,
                            CurrencyAcronim = model.Currency
                        });

                        model.Status = "Success";
                    }
                    else
                    {
                        tr.State = resultTr.OutcomeTransactionState;
                        tr.BlockchainCommission = resultTr.CommissionBlockchain;
                        tr.ErrorText            = resultTr.ErrorText;

                        await _eventsRepository.CreateEventAsync(new EventTableModel()
                        {
                            UserId          = userId,
                            Type            = (int)EventTypeEnum.OutcomeTransactionError,
                            Comment         = resultTr.ErrorText + " (commission not deducted)",
                            Value           = _amount.Value,
                            StartBalance    = resultBalance.StartBalanceSender,
                            ResultBalance   = resultBalance.ResultBalanceSender,
                            WhenDate        = DateTime.Now,
                            CurrencyAcronim = model.Currency
                        });

                        model.Status = "Error, your transaction will be processed manually";
                    }
                    await _outcomeTransactionRepository.UpdateTransactionAfterExecutioAsync(tr);
                }
                else
                {
                    model.Status = "Not enough coins";
                }
            }
            catch (Exception e)
            {
                model.Status = "Error";
                return(model);
            }

            return(model);
        }
        public virtual async Task <GeneralWithdrawModel> Send(GeneralWithdrawModel model, string userId)
        {
            try
            {
                var wallet = await _walletsRepository.GetUserWalletAsync(userId, model.Currency);

                decimal?_amount = model.Amount.ConvertToDecimal();

                if (wallet != null && _amount.Value > 0 && _amount.Value <= wallet.Value)
                {
                    var coinService = _coinManager
                                      .CoinServices
                                      .FirstOrDefault(x => x.CoinShortName == model.Currency);

                    if (coinService == null)
                    {
                        model.Status = "Error";
                        return(model);
                    }

                    var result = await _balanceProvider.Withdraw(_amount.Value, wallet);

                    wallet.Value = result.ResultBalanceSender;

                    if (result.Commission.HasValue)
                    {
                        coinService.SendToAddress(model.Address, _amount.Value - result.Commission.Value, "", "", true);
                    }
                    else
                    {
                        coinService.SendToAddress(model.Address, _amount.Value, "", "", true);
                    }

                    var tr = await _outcomeTransactionRepository.CreateOutcomeTransaction(
                        new OutcomeTransactionTableModel()
                    {
                        FromWalletId    = wallet.Id,
                        ToAddress       = model.Address,
                        Value           = _amount.Value,
                        CurrencyAcronim = model.Currency,
                        State           = (int)OutcomeTransactionStateEnum.Finished
                    });

                    await _eventsRepository.CreateEventAsync(new EventTableModel()
                    {
                        UserId          = userId,
                        Type            = (int)EventTypeEnum.Withdraw,
                        Comment         = model.Comment,
                        Value           = _amount.Value,
                        StartBalance    = result.StartBalanceSender,
                        ResultBalance   = result.ResultBalanceSender,
                        WhenDate        = DateTime.Now,
                        CurrencyAcronim = model.Currency
                    });

                    model.Status = "Success";
                    await _walletsRepository.UpdateWalletBalanceAsync(wallet);
                }
                else
                {
                    model.Status = "Not enough coins";
                }
            }
            catch
            {
                model.Status = "Error";
                return(model);
            }

            return(model);
        }