using Lada.Framework.DTO;
using Lada.Framework.DTO.Models;
using Lada.Framework.DTO.Results;
using Lada.Framework.Infrastructures.Services;
using static Lada.Framework.Data.Enums.OrderFinEnum;

namespace Lada.Framework.Tests
{
    /// <summary>
    /// Test examples cho OrderFeeCalculationService
    /// Lưu ý: Đây là example code, cần thêm test framework thực tế (xUnit, NUnit, MSTest) để chạy
    /// </summary>
    public class OrderFeeCalculationServiceExamples
    {
        /// <summary>
        /// Mock implementation của IFeeService cho testing
        /// </summary>
        private class MockFeeService : IFeeService
        {
            public Task<FeeResult> GetFeeByWard(FeeByWardModel model, string apiKey)
            {
                return Task.FromResult(new FeeResult
                {
                    Result = Result.Success,
                    Fee = 50000,
                    RouteName = "Test Route"
                });
            }

            public Task<FeeResult> GetFee(FeeModel model)
            {
                return Task.FromResult(new FeeResult
                {
                    Result = Result.Success,
                    Fee = 50000,
                    RouteName = "Test Route"
                });
            }
        }

        /// <summary>
        /// Test tính toán cước với VAT
        /// </summary>
        public static async Task<bool> TestCalculateOrderFeeWithVAT()
        {
            try
            {
                var service = new OrderFeeCalculationService(new MockFeeService());

                var request = new OrderFeeCalculationRequest
                {
                    CustomerId = 1,
                    SourceWardId = 100,
                    DestWardId = 200,
                    Weight = 1000,
                    CollectAmount = 500000,
                    PickupSubFee = 10000,
                    DeliverySubFee = 15000,
                    InsuranceFee = 5000,
                    ReturnFee = 0,
                    Discount = 5000,
                    PayFeeType = PayFeeType.ConsigneePay,
                    ApiKey = "test-key"
                };

                var result = await service.CalculateOrderFeeAsync(request);

                // Kiểm tra kết quả
                if (result.Result != Result.Success) return false;
                if (result.BaseFee != 50000) return false; // Cước cơ bản
                if (result.CodFee != 5000) return false; // 1% của 500,000
                if (result.TotalFeeBeforeVat != 80000) return false; // 50000 + 5000 + 10000 + 15000 + 5000 - 5000
                if (result.VatFee != 6400) return false; // 8% của 80000
                if (result.TotalFeeAfterVat != 86400) return false; // 80000 + 6400
                if (result.SourceFee != 0) return false; // ConsigneePay
                if (result.DestFee != 86400) return false; // ConsigneePay

                return true;
            }
            catch
            {
                return false;
            }
        }

        /// <summary>
        /// Test tính toán VAT từ tổng cước đã bao gồm VAT
        /// </summary>
        public static bool TestCalculateVatFee()
        {
            try
            {
                var service = new OrderFeeCalculationService(new MockFeeService());

                // Test với tổng cước đã bao gồm VAT 8%
                var vatFee1 = service.CalculateVatFee(108000); // 108,000 đã bao gồm VAT 8%
                var vatFee2 = service.CalculateVatFee(0); // Tổng cước = 0

                return vatFee1 == 8000 && // VAT = 108,000 * 0.08 / 1.08 = 8,000
                       vatFee2 == 0;      // Tổng cước = 0
            }
            catch
            {
                return false;
            }
        }

        /// <summary>
        /// Test phân bổ cước theo PayFeeType
        /// </summary>
        public static bool TestAllocateFeeByPaymentType()
        {
            try
            {
                var service = new OrderFeeCalculationService(new MockFeeService());

                // Test SenderPay
                var result1 = service.AllocateFeeByPaymentType(100000, PayFeeType.SenderPay);
                if (result1.SourceFee != 100000 || result1.DestFee != 0) return false;

                // Test ConsigneePay
                var result2 = service.AllocateFeeByPaymentType(100000, PayFeeType.ConsigneePay);
                if (result2.SourceFee != 0 || result2.DestFee != 100000) return false;

                // Test SplitPay
                var result3 = service.AllocateFeeByPaymentType(100000, PayFeeType.SplitPay, 30000);
                if (result3.SourceFee != 30000 || result3.DestFee != 70000) return false;

                // Test COD
                var result4 = service.AllocateFeeByPaymentType(100000, PayFeeType.COD);
                if (result4.DeductCodFee != 100000) return false;

                return true;
            }
            catch
            {
                return false;
            }
        }
    }
}
