using Lada.Framework.Data.Repositories;
using Lada.Framework.Infrastructures.AppSettings;
using Lada.Framework.Infrastructures.Extensions;
using Lada.Framework.Infrastructures.Services;
using Ladaer.BackEnd.Infrastructures.AppSettings;
using Ladaer.BackEnd.Infrastructures.Extensions;
using Ladaer.BackEnd.Infrastructures.Services;
using Ladaer.BackEnd.Infrastructures.Services.Business;
using Ladaer.BackEnd.Infrastructures.Services.Categories;
using Ladaer.BackEnd.Infrastructures.Services.Cms;
using Ladaer.BackEnd.Infrastructures.Services.Crm;
using Ladaer.BackEnd.Infrastructures.Services.DriverApp;
using Ladaer.BackEnd.Infrastructures.Services.ErrorReports;
using Ladaer.BackEnd.Infrastructures.Services.Finance;
using Ladaer.BackEnd.Infrastructures.Services.Finances;
using Ladaer.BackEnd.Infrastructures.Services.Hr;
using Ladaer.BackEnd.Infrastructures.Services.Identity;
using Ladaer.BackEnd.Infrastructures.Services.Monitor;
using Ladaer.BackEnd.Infrastructures.Services.Orders;
using Ladaer.BackEnd.Infrastructures.Services.Orders.Exports;
using Ladaer.BackEnd.Infrastructures.Services.Report.Finance;
using Ladaer.BackEnd.Infrastructures.Services.Report.OperationReports;
using Ladaer.BackEnd.Infrastructures.Services.Report.Orders;
using Ladaer.BackEnd.Infrastructures.Services.Report.SaleReports;
using Ladaer.BackEnd.Infrastructures.Services.Settings;
using Ladaer.BackEnd.Infrastructures.Services.Trucks;
using Ladaer.BackEnd.Infrastructures.Services.Premises;
using Ladaer.BackEnd.Infrastructures.Services.OrderBusiness;

namespace Ladaer.BackEnd.Infrastructures.Startup
{
    /// <summary>
    /// Lớp tĩnh để đăng ký các phụ thuộc cho ứng dụng.
    /// </summary>
    public static partial class DependencyRegister
    {
        /// <summary>
        /// Đăng ký các phụ thuộc cho ứng dụng.
        /// </summary>
        /// <param name="services">Bộ sưu tập dịch vụ.</param>
        /// <param name="Configuration">Cấu hình ứng dụng.</param>
        public static void RegisterDependency(this IServiceCollection services, IConfiguration Configuration)
        {
            #region AppSettings
            services.Configure<AppSetting>(Configuration.GetSection("AppSetting"));
            services.Configure<MediaProcessingSettings>(options => Configuration.GetSection("MediaProcessingSettings").Bind(options));
            services.Configure<CmsSetting>(options => Configuration.GetSection("CmsSetting").Bind(options));
            #endregion

            services.AddTransient<IHttpContextAccessor, HttpContextAccessor>();

            // Sử dụng AppConfigService từ Framework (đã di chuyển)
            services.AddScoped<Lada.Framework.Infrastructures.Services.IAppConfigService, Lada.Framework.Infrastructures.Services.AppConfigService>();

            // Backward compatibility cho Backend IAppConfigService
            services.AddScoped<Services.IAppConfigService>(provider =>
            {
                var frameworkService = provider.GetRequiredService<Lada.Framework.Infrastructures.Services.IAppConfigService>();
                return new BackendAppConfigServiceAdapter(frameworkService);
            });

            // AppConfig Management Service
            services.AddScoped<Services.IAppConfigManagementService, Services.AppConfigManagementService>();


            //services.AddSingleton(new OpenAIClient(new OpenAIAuthentication(Configuration.GetSection("OpenAI:ApiKey").Get<string>())));




            #region Repositories
            services.AddScoped(typeof(IRepository<>), typeof(Repository<>));
            services.AddScoped(typeof(IUserRepository<>), typeof(UserRepository<>));
            #endregion

            #region Services
            services.AddTransient<ILocationService, LocationService>();
            services.AddTransient<ICategoryService, CategoryService>();
            services.AddTransient<IEndPointsService, EndPointsService>();
            services.AddTransient<IRouteService, RouteService>();
            services.AddTransient<IAgencyService, AgencyService>();
            services.AddTransient<IAgencyLocationService, AgencyLocationService>();
            services.AddTransient<IMenuService, MenuService>();
            services.AddTransient<IOrderService, OrderService>();
            services.AddTransient<IOrderAddressService, OrderAddressService>();
            services.AddTransient<IOrderTrackService, OrderTrackService>();
            services.AddTransient<IOrderFinService, OrderFinService>();
            services.AddTransient<IOrderPackageService, OrderPackageService>();
            services.AddTransient<IGoogleMapService, GoogleMapService>();
            services.AddTransient<IUserService, UserService>();
            services.AddTransient<IRoleService, RoleService>();
            services.AddTransient<IPermissionService, PermissionService>();
            services.AddTransient<IRoleMigrationService, RoleMigrationService>();
            services.AddTransient<ICustomerService, CustomerService>();
            services.AddTransient<ICustomerBankAccountService, CustomerBankAccountService>();
            services.AddTransient<IPriceService, PriceService>();
            services.AddTransient<IWalletService, WalletService>();
            services.AddTransient<IWalletTransferService, WalletTransferService>();
            services.AddTransient<IFeeService, FeeService>();
            services.AddTransient<IBackFeeService, BackFeeService>();
            services.AddTransient<ITruckService, TruckService>();
            services.AddTransient<IPremiseService, PremiseService>();
            services.AddTransient<IPremiseScoringService, PremiseScoringService>();
            services.AddTransient<ITruckAssetService, TruckAssetService>();
            services.AddTransient<ITruckActivityService, TruckActivityService>();
            services.AddTransient<ICustomerAddressService, CustomerAddressService>();
            services.AddTransient<IPictureService, PictureService>();
            services.AddTransient<IUrlRecordService, UrlRecordService>();
            services.AddTransient<IPostService, PostService>();
            services.AddTransient<IPostCategoryService, PostCategoryService>();
            services.AddTransient<IProductService, ProductService>();
            services.AddTransient<IProductCategoryService, ProductCategoryService>();
            services.AddTransient<ITagService, TagService>();
            services.AddTransient<IJobPostService, JobPostService>();
            services.AddTransient<ICandidateService, CandidateService>();
            services.AddTransient<ICvUploadService, CvUploadService>();
            services.AddTransient<IDeployService, DeployService>();
            services.AddTransient<IOperationService, OperationService>();

            // Media Services (Framework level) - thay thế hoàn toàn cho legacy MediaService
            services.AddMediaServicesWithBackwardCompatibility(Configuration);
            services.AddTransient<IWarehouseService, WarehouseService>();
            services.AddTransient<ICashierService, CashierService>();
            services.AddTransient<IOrderTimeTrackService, OrderTimeTrackService>();
            services.AddTransient<ITransactionService, TransactionService>();
            services.AddTransient<IReconciliationService, ReconciliationService>();
            services.AddTransient<ITransferPaymentBillService, TransferPaymentBillService>();
            services.AddTransient<ICustomerReconciliationSlipService, CustomerReconciliationSlipService>();
            services.AddTransient<IExpenseCategoryService, ExpenseCategoryService>();
            services.AddTransient<IExpenseService, ExpenseService>();
            services.AddTransient<IIncomeCategoryService, IncomeCategoryService>();
            services.AddTransient<IIncomeService, IncomeService>();
            services.AddTransient<IVatInfoService, VatInfoService>();
            services.AddTransient<ITaxInvoiceService, TaxInvoiceService>();

            // Fuel Card Management Services
            services.AddTransient<Services.FuelCards.IFuelCardService, Services.FuelCards.FuelCardService>();
            services.AddTransient<Services.FuelCards.IFuelCardTransactionService, Services.FuelCards.FuelCardTransactionService>();
            services.AddTransient<Services.FuelCards.IFuelRefillService, Services.FuelCards.FuelRefillService>();
            services.AddTransient<Services.FuelCards.IFuelRefillExcelService, Services.FuelCards.FuelRefillExcelService>();

            // VAT Invoice Management Services
            services.AddTransient<IVatInvoiceService, VatInvoiceService>();
            services.AddTransient<IVatInvoiceSyncService, VatInvoiceSyncService>();

            // Excel File Service (Framework level)
            services.AddTransient<IExcelFileService, ExcelFileService>();

            // Document Service (Framework level)
            services.AddTransient<IDocumentService, DocumentService>();

            // Finance Excel Export Services
            services.AddTransient<IReconciliationExcelService, ReconciliationExcelService>();
            services.AddTransient<ITransferPaymentBillExcelService, TransferPaymentBillExcelService>();
            services.AddTransient<ICustomerReconciliationSlipExcelService, CustomerReconciliationSlipExcelService>();

            // Order Fee Calculation Services (Framework level)
            services.AddOrderFeeCalculationService();
            services.AddTransient<Lada.Framework.Infrastructures.Services.OrderFeeCalculationHelper>();
            services.AddTransient<BankSeedService>();

            // Order Export Services (Generic)
            services.AddTransient<IOrderExportService, OrderExportService>();
            services.AddTransient<Services.Orders.Exports.Templates.FinanceOrderExportTemplate>();
            services.AddTransient<Services.Orders.Exports.Templates.BasicOrderExportTemplate>();

            // Legacy Export Service (for backward compatibility)
            services.AddTransient<IExportOrderService, ExportOrderService>();

            services.AddTransient<ILeadService, LeadService>();
            services.AddTransient<ICallLogService, CallLogService>();
            services.AddTransient<ITopicService, TopicService>();
            //services.AddTransient<IOpenAiService, OpenAiService>();
            services.AddTransient<IScriptConfigService, ScriptConfigService>();
            services.AddTransient<ICallPathService, CallPathService>();
            services.AddTransient<ICallPathVersionService, CallPathVersionService>();
            services.AddTransient<IDriverAppService, DriverAppService>();
            services.AddTransient<IDriverFinService, DriverFinService>();
            services.AddTransient<IDriverAppOrderService, DriverAppOrderService>();
            services.AddTransient<IOrderFailReasonService, OrderFailReasonService>();
            services.AddTransient<IAttendanceService, AttendanceService>();
            services.AddTransient<IErrorReportService, ErrorReportService>();

            services.AddTransient<IOrderReportService, OrderReportService>();
            services.AddTransient<IOrderFinReportService, OrderFinReportService>();
            services.AddTransient<ISaleReportService, SaleReportService>();
            services.AddTransient<IDriverReportService, DriverReportService>();
            services.AddTransient<IIncomeExpenseReportService, IncomeExpenseReportService>();
            services.AddTransient<Services.Report.FuelCards.IFuelRefillReportService, Services.Report.FuelCards.FuelRefillReportService>();
            services.AddTransient<Services.Report.FuelCards.IFuelRefillReportExcelService, Services.Report.FuelCards.FuelRefillReportExcelService>();

            // Bank Management Services
            services.AddTransient<IBankService, BankService>();
            services.AddTransient<IBankAccountService, BankAccountService>();
            services.AddTransient<IBankStatementParser, BankStatementParser>();
            services.AddTransient<IUserBankAccountService, UserBankAccountService>();

            // Monitor Services
            services.AddTransient<IOrderRiskService, OrderRiskService>();

            // Rewards & Penalties Services
            services.AddTransient<Services.Rewards.IRewardPenaltyService, Services.Rewards.RewardPenaltyService>();
            services.AddTransient<Services.Rewards.IAutoPenaltyConfigService, Services.Rewards.AutoPenaltyConfigService>();

            // Permission Management Services
            #endregion
        }
    }
}
