using Knoks.Core.Data.Interfaces;
using Knoks.Core.Entities;
using Knoks.Core.Entities.Args;
using Knoks.Core.Logic.Interfaces;
using Newtonsoft.Json.Linq;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;

namespace Knoks.Core.Logic.Managers
{
    public class BackofficeManager : IBackofficeManager
    {
        private readonly IBackofficeDao _backofficeDao;
        private readonly ISystemConfigurationManager _systemConfigurationManager;

        public BackofficeManager(IBackofficeDao backofficeDao, 
            ISystemConfigurationManager systemConfigurationManager)
        {
            _backofficeDao = backofficeDao;
            _systemConfigurationManager = systemConfigurationManager;
        }

        public async Task<AccountTransaction> FreeTokensCredit(AddAccountTransactionArgs args)
        {
            return await _backofficeDao.AddAccountTransaction(args, AccoutTransactionTypeIdentity.FreeTokensCredit);
        }

        public async Task<AccountTransaction> Deposit(AddAccountTransactionArgs args)
        {
            return await _backofficeDao.AddAccountTransaction(args, AccoutTransactionTypeIdentity.Deposit);
        }
        public async Task<AccountTransaction> Withdraw(AddAccountTransactionArgs args)
        {
            return await _backofficeDao.AddAccountTransaction(args, AccoutTransactionTypeIdentity.Withdraw);
        }
        
        public async Task<AccountTransaction> PublishKnok(AddAccountTransactionArgs args)
        {
            return await _backofficeDao.AddAccountTransaction(args, AccoutTransactionTypeIdentity.PublishKnok);
        }
        
        public async Task<AccountTransaction> KnokerWinsToken(AddAccountTransactionArgs args)
        {
            return await _backofficeDao.AddAccountTransaction(args, AccoutTransactionTypeIdentity.KnokerWinsToken);
        }
        
        public async Task<AccountTransaction> PlatformWinsToken(AddAccountTransactionArgs args)
        {
            return await _backofficeDao.AddAccountTransaction(args, AccoutTransactionTypeIdentity.PlatformWinsToken);
        }
        
        public async Task<AccountTransaction> UserBuyExposure(AddAccountTransactionArgs args)
        {
            return await _backofficeDao.AddAccountTransaction(args, AccoutTransactionTypeIdentity.UserBuyExposure);
        }
        
        public async Task<AccountTransaction> UserBuyKnok(AddAccountTransactionArgs args)
        {
            return await _backofficeDao.AddAccountTransaction(args, AccoutTransactionTypeIdentity.UserBuyKnok);
        }
        
        public async Task<AccountTransaction> UserRefundToken(AddAccountTransactionArgs args)
        {
            return await _backofficeDao.AddAccountTransaction(args, AccoutTransactionTypeIdentity.UserRefundToken);
        }
        
        public async Task<AccountTransaction> UserBuySideBet(AddAccountTransactionArgs args)
        {
            return await _backofficeDao.AddAccountTransaction(args, AccoutTransactionTypeIdentity.UserBuySideBet);
        }
        
        public async Task<AccountTransaction> UserWinsSideBet(AddAccountTransactionArgs args)
        {
            return await _backofficeDao.AddAccountTransaction(args, AccoutTransactionTypeIdentity.UserWinsSideBet);
        }
        
        public async Task<AccountTransaction> PlatformLooseSideBet(AddAccountTransactionArgs args)
        {
            return await _backofficeDao.AddAccountTransaction(args, AccoutTransactionTypeIdentity.PlatformLooseSideBet);
        }
        
        public async Task<AccountTransaction> UserReceiveToken(AddAccountTransactionArgs args)
        {
            return await _backofficeDao.AddAccountTransaction(args, AccoutTransactionTypeIdentity.UserReceiveToken);
        }
        
        public async Task<AccountTransaction> UserUpgradeToGold(AddAccountTransactionArgs args)
        {
            return await _backofficeDao.AddAccountTransaction(args, AccoutTransactionTypeIdentity.UserUpgradeToGold);
        }
        
        public async Task<AccountTransaction> AffiliateCommision(AddAccountTransactionArgs args)
        {
            return await _backofficeDao.AddAccountTransaction(args, AccoutTransactionTypeIdentity.AffiliateCommision);
        }
        
        public async Task<AccountTransaction> FreeTokensReturn(AddAccountTransactionArgs args)
        {
            return await _backofficeDao.AddAccountTransaction(args, AccoutTransactionTypeIdentity.FreeTokensReturn);
        }

    //public async Task<BoBorrower> GetBorrowerCard(int operatorId, long userId, long? loanRequestId)
    //{
    //    return await _backofficeDao.GetBorrowerCard(operatorId, userId, loanRequestId);
    //}

    //public async Task<IEnumerable<BoBorrowerActivity>> GetBorrowerActivities(int operatorId, long userId, long? loanRequestId, long? loanId)
    //{
    //    return await _backofficeDao.GetBorrowerActivities(operatorId, userId, loanRequestId, loanId);
    //}

    //public async Task<IEnumerable<BoDisbursementMethod>> GetDisbursementMethods(int operatorId, long loanRequestId)
    //{
    //    return await _backofficeDao.GetDisbursementMethods(operatorId, loanRequestId);
    //}

    //public async Task<BorrowerPreDisclosureCard> GetBorrowerPreDisclosureCard(int operatorId, long userId, long? loanRequestId)
    //{
    //    return await _backofficeDao.GetBorrowerPreDisclosureCard(operatorId, userId, loanRequestId);
    //}

    //public async Task<IEnumerable<BoLoanVerification>> GetBorrowerVerifications(int operatorId, long userId, long loanRequestId)
    //{
    //    return await _backofficeDao.GetBorrowerVerifications(operatorId, userId, loanRequestId);
    //}

    //public async Task<UnderwritingCard> GetUnderwritingCard(int operatorId, long userId, long? loanRequestId)
    //{
    //    var result = await _backofficeDao.GetBorrowerPreDisclosureCard(operatorId, userId, loanRequestId);
    //    var propertyCollection = result.BoLoanRequest.Properties.ToPropertyCollection();
    //    var currentInterest = result.BoLoanRequest.ApprovedInterest.HasValue ? 
    //        result.BoLoanRequest.ApprovedInterest.Value : result.BoLoanRequest.InitialInterest.Value;

    //    var contextPropertiesConfig = await _propertiesManager.GetPropertyConfigsByContext(result.BoLoanRequest.ContextId);

    //    var income = await _propertiesManager.FormatLoanRequestProperties(result.BoLoanRequest.Properties, result.BoLoanRequest.ContextId, PropertyType.Income);
    //    var assets = await _propertiesManager.FormatLoanRequestProperties(result.BoLoanRequest.Properties, result.BoLoanRequest.ContextId, PropertyType.Assets);
    //    var liabilities = await _propertiesManager.FormatLoanRequestProperties(result.BoLoanRequest.Properties, result.BoLoanRequest.ContextId, PropertyType.Liabilities);

    //    return new UnderwritingCard
    //    {
    //        BorrowerPreDisclosureCard = result,
    //        Assets = assets,
    //        Income = income,
    //        Liabilities = liabilities,
    //        LoanToValueRatio = _loanLogic.GetLoanToValueRatio(0, 1)//TODO - get appraised value
    //    };
    //}

    //public async Task<BoBucketFillCard> GetBucketFillCard(int operatorId, long userId, long loanRequestId)
    //{
    //    return await _backofficeDao.GetBucketFillCard(operatorId, userId, loanRequestId);
    //}

    //public async Task<BoLoanRequestsResult> LoadBoLoanRequests(GetBoLoanRequestsArgs args)
    //{
    //    var loanRequestsResult = await _backofficeDao.LoadBoLoanRequests(args);
    //    var loanRequests = loanRequestsResult.Items.ToList();

    //    foreach (var loanRequest in loanRequests)
    //    {
    //        var propertyContext = (await _propertiesManager.GetPropertyContexts(loanRequest.ContextId)).Single();
    //        var propertyContextCommissionFeeConfigs = propertyContext.CommissionFeeConfigs;
    //        var annualInterest = loanRequest.ApprovedAnnualInterestRate ?? loanRequest.InitialAnnualInterestRate;
    //        var loanRequestScore = loanRequest.LoanRequestCurrentScore ?? loanRequest.LoanRequestOriginalScore.Value;
    //        var loanAmount = loanRequest.LoanApprovedAmount ?? loanRequest.LoanRequestAmount;
    //        var firstPaymentDate = loanRequest.PlannedFirstReturnDate ?? _systemConfigurationManager.SystemDateTime;
    //        var lastPaymentDate = _loanLogic.GetLastPaymentDate(firstPaymentDate, loanRequest.LoanRequestPeriodTypeId, loanRequest.Period.Value);
    //        annualInterest = annualInterest.HasValue ? annualInterest.Value : propertyContext.GetAnnualInterestRate(loanRequestScore);
    //        loanRequest.CommissionFeeSummary = _loanLogic.GetLoanCommissionFeeSummary(loanRequest.LoanApprovedAmount ?? loanRequest.LoanRequestAmount, propertyContextCommissionFeeConfigs);
    //        loanRequest.TotalAmountToReturn = _loanLogic.GetLoanAmountToReturn(annualInterest.Value, loanAmount, loanRequest.CommissionFeeSummary.TotalActualCommissionFees, firstPaymentDate, lastPaymentDate);
    //        loanRequest.PropertiesFormated = await _propertiesManager.FormatLoanRequestProperties(loanRequest.Properties, loanRequest.ContextId);
    //    }

    //    loanRequestsResult.Items = loanRequests;
    //    return loanRequestsResult;
    //}
    //public async Task<BoLoanRequestsCountsResult> LoadBoLoanRequestsCount(GetBoLoanRequestsCountArgs args)
    //{
    //    return await _backofficeDao.LoadBoLoanRequestsCount(args);
    //}

    //public async Task<BoLoansResult> LoadBoLoans(GetBoLoansArgs args)
    //{
    //    return await _backofficeDao.LoadBoLoans(args);
    //}
    //public async Task<BoLoansCountResult> LoadBoLoansCount(GetBoLoansCountArgs args)
    //{
    //    return await _backofficeDao.LoadBoLoansCount(args);
    //}
    //public async Task<BoMenuCountsResult> LoadBoMenuCounts(GetBoMenuCountsArgs args)
    //{
    //    return await _backofficeDao.LoadBoMenuCounts(args);
    //}
}
}
