public async Task <ActionResult> Create(string currency, string returnUrl)
        {
            var user = await UserManager.FindValidByIdAsync(User.Identity.GetUserId());

            var currencyData = await CurrencyReader.GetCurrency(currency);

            if (currencyData == null || user == null)
            {
                ViewBag.Message = $"Currency {currency} not found.";
                return(View("Error"));
            }

            if (currencyData.Status == CurrencyStatus.Maintenance || currencyData.Status == CurrencyStatus.Offline)
            {
                ViewBag.HideSupportLink = true;
                ViewBag.SubTitle        = $"Status: {currencyData.Status}";
                ViewBag.Message         = $"Unfortunately we are unable to process your withdrawal at this time.<br /><br />Status: {currencyData.Status}<br />Reason: {(string.IsNullOrEmpty(currencyData.StatusMessage) ? "Unknown" : currencyData.StatusMessage)}";
                return(View("Error"));
            }

            if (currencyData.CurrencyId == Constant.NZDT_ID && !UserVerificationReader.IsVerified(user.VerificationLevel))
            {
                return(View("NotVerified"));
            }

            return(View(await CreateWithdrawModel(user, new WithdrawCurrencyModel
            {
                Name = currencyData.Name,
                Symbol = currencyData.Symbol,
                ReturnUrl = GetLocalReturnUrl(returnUrl)
            })));
        }
        private async Task <WithdrawCurrencyModel> CreateWithdrawModel(Cryptopia.Entity.ApplicationUser user, WithdrawCurrencyModel model)
        {
            var currencyData = await CurrencyReader.GetCurrency(model.Symbol);

            var balanceData = await BalanceReader.GetCurrencyBalance(User.Identity.GetUserId(), currencyData.CurrencyId);

            var addressBook = await AddressBookReader.GetAddressBook(User.Identity.GetUserId(), currencyData.CurrencyId);

            var verificationData = await UserVerificationReader.GetVerificationStatus(User.Identity.GetUserId());

            var estimatedCoinNzd = await BalanceEstimationService.GetNZDPerCoin(currencyData.CurrencyId);

            model                  = user.GetTwoFactorModel(TwoFactorComponent.Withdraw, model);
            model.Name             = currencyData.Name;
            model.CurrencyId       = currencyData.CurrencyId;
            model.CurrencyType     = currencyData.Type;
            model.Symbol           = balanceData.Symbol;
            model.Balance          = balanceData.Available;
            model.Fee              = currencyData.WithdrawFee;
            model.WithdrawFeeType  = currencyData.WithdrawFeeType;
            model.MinWithdraw      = currencyData.WithdrawMin;
            model.MaxWithdraw      = currencyData.WithdrawMax;
            model.AddressBookOnly  = !user.IsUnsafeWithdrawEnabled;
            model.AddressBook      = addressBook;
            model.AddressType      = currencyData.AddressType;
            model.HasWithdrawLimit = verificationData.Limit > 0;
            model.WithdrawLimit    = verificationData.Limit;
            model.WithdrawTotal    = verificationData.Current;
            model.EstimatedCoinNZD = estimatedCoinNzd;
            model.Instructions     = currencyData.WithdrawInstructions;
            model.Message          = currencyData.WithdrawMessage;
            model.MessageType      = currencyData.WithdrawMessageType.ToString().ToLower();
            model.Decimals         = currencyData.CurrencyDecimals;
            return(model);
        }
        public async Task <ActionResult> GetCompletedUserDetailsModal(int id)
        {
            var model = await UserVerificationReader.GetCompletedUserDetails(id);

            return(Json(new
            {
                html = RenderPartialViewToString("_UserDetailsPartial", model)
            }));
        }
Esempio n. 4
0
        private async Task <TransferCurrencyModel> CreateTransferModel(Cryptopia.Entity.ApplicationUser user, TransferCurrencyModel model)
        {
            var currencyData = await CurrencyReader.GetCurrency(model.Symbol);

            var balanceData = await BalanceReader.GetCurrencyBalance(User.Identity.GetUserId(), currencyData.CurrencyId);

            var verificationData = await UserVerificationReader.GetVerificationStatus(User.Identity.GetUserId());

            var estimatedCoinNzd = await BalanceEstimationService.GetNZDPerCoin(currencyData.CurrencyId);

            model                  = user.GetTwoFactorModel(TwoFactorComponent.Transfer, model);
            model.Name             = currencyData.Name;
            model.CurrencyId       = currencyData.CurrencyId;
            model.Symbol           = balanceData.Symbol;
            model.Balance          = balanceData.Available;
            model.HasWithdrawLimit = verificationData.Limit > 0;
            model.WithdrawLimit    = verificationData.Limit;
            model.WithdrawTotal    = verificationData.Current;
            model.EstimatedCoinNZD = estimatedCoinNzd;
            return(model);
        }
        public async Task <ActionResult> Create(WithdrawCurrencyModel model)
        {
            var currencyData = await CurrencyReader.GetCurrency(model.Symbol);

            var user = await UserManager.FindValidByIdAsync(User.Identity.GetUserId());

            if (currencyData == null || user == null)
            {
                ViewBag.Message = $"Currency {model.Symbol} not found.";
                return(View("Error"));
            }

            if (currencyData.CurrencyId == Constant.NZDT_ID && !UserVerificationReader.IsVerified(user.VerificationLevel))
            {
                return(View("NotVerified"));
            }

            // Verify Address
            var address = model.AddressData?.Trim();

            if (string.IsNullOrEmpty(address))
            {
                address = model.SelectedAddress;
            }
            else if (currencyData.AddressType != AddressType.Standard)
            {
                if (currencyData.AddressType == AddressType.PaymentId && !CurrencyExtensions.IsValidPaymentId(model.AddressData2?.Trim()))
                {
                    ModelState.AddModelError("AddressData2", $"Please enter a valid Cryptonote PaymentId.");
                    return(View(await CreateWithdrawModel(user, model)));
                }
                address = $"{model.AddressData?.Trim()}:{model.AddressData2?.Trim()}";
                if (currencyData.Type == CurrencyType.Fiat)
                {
                    address = address.TrimEnd(':');
                }
            }
            if (string.IsNullOrEmpty(address))
            {
                ModelState.AddModelError(user.IsUnsafeWithdrawEnabled ? "AddressData" : "AddressBookError", $"Please enter a valid {model.Symbol} address");
                return(View(await CreateWithdrawModel(user, model)));
            }

            // Verify Amount
            var withdrawAmount = decimal.Round(model.Amount, currencyData.CurrencyDecimals);

            if (withdrawAmount < currencyData.WithdrawMin || withdrawAmount >= currencyData.WithdrawMax)
            {
                ModelState.AddModelError("Amount", $"Withdrawal amount must be between {currencyData.WithdrawMin} {currencyData.Symbol} and {currencyData.WithdrawMax} {currencyData.Symbol}");
                return(View(await CreateWithdrawModel(user, model)));
            }

            // Verify Two Factor
            if (!await UserManager.VerifyUserTwoFactorCodeAsync(TwoFactorComponent.Withdraw, user.Id, model.Code1, model.Code2))
            {
                ModelState.AddModelError("TwoFactorError", "The TFA code entered was incorrect or has expired, please try again.");
                return(View(await CreateWithdrawModel(user, model)));
            }

            // Create withdraw

            var twoFactortoken = await GenerateUserTwoFactorTokenAsync(TwoFactorTokenType.WithdrawConfirm, user.Id);

            var result = await WithdrawWriter.CreateWithdraw(User.Identity.GetUserId(), new CreateWithdrawModel
            {
                Address        = address,
                Amount         = withdrawAmount,
                CurrencyId     = model.CurrencyId,
                TwoFactorToken = twoFactortoken,
                Type           = WithdrawType.Normal,
            });

            if (!result.Success)
            {
                ModelState.AddModelError("Error", result.Message);
                return(View(await CreateWithdrawModel(user, model)));
            }

            // Send Confirmation email
            if (!user.DisableWithdrawEmailConfirmation)
            {
                await SendConfirmationEmail(user, model.Symbol, withdrawAmount - model.Fee, address, result.Result, twoFactortoken, currencyData.AddressType);
            }

            return(RedirectToAction("Summary", new { withdrawId = result.Result, returnUrl = GetLocalReturnUrl(model.ReturnUrl) }));
        }
 public async Task <ActionResult> GetCompletedUserVerifications(DataTablesModel model)
 {
     return(DataTable(await UserVerificationReader.GetCompletedVerifications(model)));
 }
 public async Task <ActionResult> Index()
 {
     return(View(await UserVerificationReader.GetVerification(User.Identity.GetUserId())));
 }
Esempio n. 8
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
            });
        }