using Microsoft.EntityFrameworkCore;
using Microsoft.EntityFrameworkCore.Metadata.Builders;
using SolutionErp.Domain.Budgets;

namespace SolutionErp.Infrastructure.Persistence.Configurations;

public class BudgetConfiguration : IEntityTypeConfiguration<Budget>
{
    public void Configure(EntityTypeBuilder<Budget> b)
    {
        b.ToTable("Budgets");
        b.HasKey(x => x.Id);

        b.Property(x => x.MaNganSach).HasMaxLength(100);
        b.Property(x => x.TenNganSach).HasMaxLength(500).IsRequired();
        b.Property(x => x.Description).HasMaxLength(2000);
        b.Property(x => x.Phase).HasConversion<int>();
        b.Property(x => x.RejectedFromPhase).HasConversion<int?>();
        b.Property(x => x.TongNganSach).HasPrecision(18, 2);

        b.HasIndex(x => x.MaNganSach).IsUnique().HasFilter("[MaNganSach] IS NOT NULL");
        b.HasIndex(x => new { x.Phase, x.IsDeleted });
        b.HasIndex(x => x.ProjectId);
        b.HasIndex(x => x.NamNganSach);
        b.HasIndex(x => x.SlaDeadline);

        b.HasMany(x => x.Details).WithOne(d => d.Budget).HasForeignKey(d => d.BudgetId).OnDelete(DeleteBehavior.Cascade);
        b.HasMany(x => x.Approvals).WithOne(a => a.Budget).HasForeignKey(a => a.BudgetId).OnDelete(DeleteBehavior.Cascade);
        b.HasMany(x => x.Changelogs).WithOne(c => c.Budget).HasForeignKey(c => c.BudgetId).OnDelete(DeleteBehavior.Cascade);

        b.HasQueryFilter(x => !x.IsDeleted);
    }
}

public class BudgetDetailConfiguration : IEntityTypeConfiguration<BudgetDetail>
{
    public void Configure(EntityTypeBuilder<BudgetDetail> b)
    {
        b.ToTable("BudgetDetails");
        b.HasKey(x => x.Id);

        b.Property(x => x.GroupCode).HasMaxLength(50).IsRequired();
        b.Property(x => x.GroupName).HasMaxLength(200).IsRequired();
        b.Property(x => x.ItemCode).HasMaxLength(100);
        b.Property(x => x.NoiDung).HasMaxLength(500).IsRequired();
        b.Property(x => x.DonViTinh).HasMaxLength(50);
        b.Property(x => x.GhiChu).HasMaxLength(1000);
        b.Property(x => x.KhoiLuong).HasPrecision(18, 4);
        b.Property(x => x.DonGia).HasPrecision(18, 2);
        b.Property(x => x.ThanhTien).HasPrecision(18, 2);

        b.HasIndex(x => new { x.BudgetId, x.Order });
    }
}

public class BudgetApprovalConfiguration : IEntityTypeConfiguration<BudgetApproval>
{
    public void Configure(EntityTypeBuilder<BudgetApproval> b)
    {
        b.ToTable("BudgetApprovals");
        b.HasKey(x => x.Id);

        b.Property(x => x.FromPhase).HasConversion<int>();
        b.Property(x => x.ToPhase).HasConversion<int>();
        b.Property(x => x.Decision).HasConversion<int>();
        b.Property(x => x.Comment).HasMaxLength(1000);

        b.HasIndex(x => new { x.BudgetId, x.ApprovedAt });
    }
}

public class BudgetChangelogConfiguration : IEntityTypeConfiguration<BudgetChangelog>
{
    public void Configure(EntityTypeBuilder<BudgetChangelog> b)
    {
        b.ToTable("BudgetChangelogs");
        b.HasKey(x => x.Id);

        b.Property(x => x.EntityType).HasConversion<int>();
        b.Property(x => x.Action).HasConversion<int>();
        b.Property(x => x.PhaseAtChange).HasConversion<int>();
        b.Property(x => x.UserName).HasMaxLength(200);
        b.Property(x => x.Summary).HasMaxLength(500);
        b.Property(x => x.ContextNote).HasMaxLength(2000);
        b.Property(x => x.FieldChangesJson).HasColumnType("nvarchar(max)");

        b.HasIndex(x => new { x.BudgetId, x.CreatedAt });
        b.HasIndex(x => new { x.BudgetId, x.EntityType });
    }
}
