Exemplo n.º 1
0
        public async Task <ApiSubmitUserWithdrawResponse> SubmitUserWithdraw(ApiSubmitUserWithdrawRequest request)
        {
            var currency = request.CurrencyId.HasValue
                                        ? await CurrencyReader.GetCurrency(request.CurrencyId.Value).ConfigureAwait(false)
                                        : await CurrencyReader.GetCurrency(request.Currency).ConfigureAwait(false);

            if (currency == null)
            {
                return new ApiSubmitUserWithdrawResponse {
                           Success = false, Error = "Currency not found."
                }
            }
            ;

            if (currency.Status == CurrencyStatus.Maintenance || currency.Status == CurrencyStatus.Offline || currency.Status == CurrencyStatus.NoConnections)
            {
                return new ApiSubmitUserWithdrawResponse {
                           Success = false, Error = $"Currency is currently not available for withdraw, Status: {currency.Status}"
                }
            }
            ;

            if (request.Amount < currency.WithdrawMin)
            {
                return new ApiSubmitUserWithdrawResponse {
                           Success = false, Error = $"Withdraw amount is below the minimum, Minimum: {currency.WithdrawMin:F8} {currency.Symbol}"
                }
            }
            ;

            if (request.Amount > currency.WithdrawMax)
            {
                return new ApiSubmitUserWithdrawResponse {
                           Success = false, Error = $"Withdraw amount is above the maximum, Maximum: {currency.WithdrawMax:F8} {currency.Symbol}"
                }
            }
            ;

            var balance = await UserBalanceReader.GetBalance(request.UserId.ToString(), currency.CurrencyId).ConfigureAwait(false);

            if (balance == null || request.Amount > balance.Available)
            {
                return new ApiSubmitUserWithdrawResponse {
                           Success = false, Error = "Insufficient funds."
                }
            }
            ;

            var user = await UserReader.GetUserById(request.UserId.ToString()).ConfigureAwait(false);

            if (user == null || !user.IsApiWithdrawEnabled)
            {
                return new ApiSubmitUserWithdrawResponse {
                           Success = false, Error = "Your API withdraw setting is currently disabled."
                }
            }
            ;

            var address = request.Address;

            if (currency.AddressType != AddressType.Standard)
            {
                address = $"{request.Address}:{request.PaymentId ?? string.Empty}";
            }
            if (currency.Type == CurrencyType.Fiat)
            {
                address = address.TrimEnd(':');
            }

            if (!user.IsApiUnsafeWithdrawEnabled)
            {
                using (var context = ExchangeDataContextFactory.CreateReadOnlyContext())
                {
                    var validAddress = await context.AddressBook
                                       .AsNoTracking()
                                       .FirstOrDefaultAsync(x => x.UserId == request.UserId && x.CurrencyId == currency.CurrencyId && x.Address == address && x.IsEnabled).ConfigureAwait(false);

                    if (validAddress == null)
                    {
                        return new ApiSubmitUserWithdrawResponse {
                                   Success = false, Error = $"Address does not exist in your secure Withdraw Address Book"
                        }
                    }
                    ;
                }
            }
            else
            {
                if (currency.CurrencyId == Constant.NZDT_ID && !UserVerificationReader.IsVerified(user.VerificationLevel))
                {
                    return(new ApiSubmitUserWithdrawResponse {
                        Success = false, Error = $"Id verification required for NZDT services."
                    });
                }

                if (!await DepositService.ValidateAddress(currency.CurrencyId, address))
                {
                    return new ApiSubmitUserWithdrawResponse {
                               Success = false, Error = $"Invalid {currency.Symbol} address."
                    }
                }
                ;
            }

            var response = await TradeService.CreateWithdraw(request.UserId.ToString(), new CreateWithdrawModel
            {
                Address        = address,
                Amount         = Math.Max(0, request.Amount),
                CurrencyId     = balance.CurrencyId,
                TwoFactorToken = string.Empty,
                Type           = WithdrawType.Normal
            }, true).ConfigureAwait(false);

            if (response.IsError)
            {
                return new ApiSubmitUserWithdrawResponse {
                           Success = false, Error = response.Error
                }
            }
            ;

            return(new ApiSubmitUserWithdrawResponse
            {
                Success = true,
                Data = response.WithdrawId
            });
        }