using Microsoft.EntityFrameworkCore; using Microsoft.EntityFrameworkCore.Metadata.Builders; using Tiku.Domain.Learning; using Tiku.Domain.Tenancy; namespace Tiku.Infrastructure.Persistence.Configurations; internal sealed class LearningOutboxMessageConfiguration : IEntityTypeConfiguration { public void Configure(EntityTypeBuilder builder) { builder.ToTable("learning_outbox_messages"); builder.HasKey(entity => new { entity.OccurredAt, entity.Id }); builder.Property(entity => entity.Id).HasDefaultValueSql("gen_random_uuid()"); builder.HasAlternateKey(entity => new { entity.TenantId, entity.OccurredAt, entity.Id }); builder.HasOne().WithMany() .HasForeignKey(entity => entity.TenantId) .OnDelete(DeleteBehavior.Cascade); builder.Property(entity => entity.EventType).HasMaxLength(100); builder.Property(entity => entity.Payload).IsJson("{}"); builder.Property(entity => entity.OccurredAt).HasDefaultValueSql("now()"); builder.Property(entity => entity.AvailableAt).HasDefaultValueSql("now()"); builder.Property(entity => entity.LockedBy).HasMaxLength(200); builder.Property(entity => entity.LastError).HasMaxLength(2000); builder.HasIndex(entity => new { entity.TenantId, entity.EventType, entity.AggregateId, entity.OccurredAt }).IsUnique(); builder.HasIndex(entity => new { entity.AvailableAt, entity.LockExpiresAt, entity.OccurredAt, entity.Id }) .HasDatabaseName("ix_learning_outbox_pending") .HasFilter("processed_at IS NULL AND dead_lettered_at IS NULL"); builder.ToTable(table => table.HasCheckConstraint( "ck_learning_outbox_messages_attempt_count", "attempt_count >= 0")); } } internal sealed class LearningProjectionReceiptConfiguration : IEntityTypeConfiguration { public void Configure(EntityTypeBuilder builder) { builder.ConfigureTenantEntity("learning_projection_receipts"); builder.Property(entity => entity.ProjectionName).HasMaxLength(100); builder.Property(entity => entity.ProcessedAt).HasDefaultValueSql("now()"); builder.HasIndex(entity => new { entity.TenantId, entity.OutboxMessageId, entity.ProjectionName }).IsUnique(); } }