using Microsoft.EntityFrameworkCore;
using Microsoft.EntityFrameworkCore.Metadata.Builders;
using IamService.Domain.AggregatesModel.OrganizationAggregate;

namespace IamService.Infrastructure.EntityConfigurations;

/// <summary>
/// EN: Entity configuration for Organization.
/// VI: Cấu hình entity cho Organization.
/// </summary>
public class OrganizationEntityConfiguration : IEntityTypeConfiguration<Organization>
{
    public void Configure(EntityTypeBuilder<Organization> builder)
    {
        builder.ToTable("organizations");

        builder.HasKey(o => o.Id);

        builder.Property(o => o.Id)
            .HasColumnName("id")
            .ValueGeneratedNever();

        builder.Property("_name")
            .HasColumnName("name")
            .HasMaxLength(200)
            .IsRequired();

        builder.Property("_slug")
            .HasColumnName("slug")
            .HasMaxLength(100)
            .IsRequired();

        builder.HasIndex("_slug")
            .IsUnique()
            .HasDatabaseName("ix_organizations_slug");

        builder.Property("_description")
            .HasColumnName("description")
            .HasMaxLength(1000);

        builder.Property("_parentOrganizationId")
            .HasColumnName("parent_organization_id");

        builder.Property(o => o.StatusId)
            .HasColumnName("status_id")
            .IsRequired();

        builder.Property("_createdAt")
            .HasColumnName("created_at")
            .IsRequired();

        builder.Property("_updatedAt")
            .HasColumnName("updated_at");

        // EN: Configure owned entity for Settings
        // VI: Cấu hình owned entity cho Settings
        builder.OwnsOne<OrganizationSettings>("_settings", settings =>
        {
            settings.Property(s => s.AllowUserRegistration)
                .HasColumnName("settings_allow_user_registration")
                .HasDefaultValue(true);

            settings.Property(s => s.RequireEmailVerification)
                .HasColumnName("settings_require_email_verification")
                .HasDefaultValue(true);

            settings.Property(s => s.Require2FA)
                .HasColumnName("settings_require_2fa")
                .HasDefaultValue(false);

            settings.Property(s => s.MaxUsersLimit)
                .HasColumnName("settings_max_users_limit")
                .HasDefaultValue(100);

            settings.Property(s => s.CustomDomain)
                .HasColumnName("settings_custom_domain")
                .HasMaxLength(255);

            settings.Property(s => s.SessionTimeoutMinutes)
                .HasColumnName("settings_session_timeout_minutes")
                .HasDefaultValue(60);
        });

        // EN: Self-referencing relationship for hierarchy
        // VI: Quan hệ tự tham chiếu cho phân cấp
        builder.HasOne<Organization>()
            .WithMany()
            .HasForeignKey("_parentOrganizationId")
            .OnDelete(DeleteBehavior.Restrict)
            .HasConstraintName("fk_organizations_parent");

        // EN: Ignore domain events
        // VI: Bỏ qua domain events
        builder.Ignore(o => o.DomainEvents);
    }
}

/// <summary>
/// EN: Entity configuration for OrganizationStatus.
/// VI: Cấu hình entity cho OrganizationStatus.
/// </summary>
public class OrganizationStatusEntityConfiguration : IEntityTypeConfiguration<OrganizationStatus>
{
    public void Configure(EntityTypeBuilder<OrganizationStatus> builder)
    {
        builder.ToTable("organization_statuses");

        builder.HasKey(s => s.Id);

        builder.Property(s => s.Id)
            .HasColumnName("id")
            .ValueGeneratedNever();

        builder.Property(s => s.Name)
            .HasColumnName("name")
            .HasMaxLength(50)
            .IsRequired();

        // EN: Seed data
        // VI: Seed data
        builder.HasData(
            OrganizationStatus.Active,
            OrganizationStatus.Suspended,
            OrganizationStatus.PendingApproval,
            OrganizationStatus.Archived
        );
    }
}
