From eea596c6ecaf025a1ad86e3cc88d169af0d8ac6d Mon Sep 17 00:00:00 2001 From: gamer147 Date: Mon, 8 Jun 2026 20:33:50 -0400 Subject: [PATCH] feat(db): wire ViewerPresent into SVSimDbContext with indexes --- SVSim.Database/SVSimDbContext.cs | 20 ++++++++++++++++++++ 1 file changed, 20 insertions(+) diff --git a/SVSim.Database/SVSimDbContext.cs b/SVSim.Database/SVSimDbContext.cs index 27ee4d8..0bfc5da 100644 --- a/SVSim.Database/SVSimDbContext.cs +++ b/SVSim.Database/SVSimDbContext.cs @@ -102,6 +102,7 @@ public class SVSimDbContext : DbContext public DbSet ViewerStoryBranchUnlocks => Set(); public DbSet ViewerClaimedTutorialGifts => Set(); + public DbSet ViewerPresents => Set(); public DbSet ArenaTwoPickRewards { get; set; } = null!; public DbSet ViewerArenaTwoPickRuns { get; set; } = null!; @@ -373,6 +374,25 @@ public class SVSimDbContext : DbContext b.Property(g => g.PresentId).HasMaxLength(64); }); + modelBuilder.Entity(b => + { + b.HasKey(p => p.Id); + b.Property(p => p.PresentId).HasMaxLength(64); + b.Property(p => p.Source).HasMaxLength(64); + + b.HasOne(p => p.Viewer) + .WithMany() + .HasForeignKey(p => p.ViewerId) + .OnDelete(DeleteBehavior.Cascade); + + // Drives /gift/top — partition by status, then chronological. + b.HasIndex(p => new { p.ViewerId, p.Status, p.CreatedAt }); + + // One row per (viewer, present_id) — backstop against double-seeding and + // double-enqueue from future producers. + b.HasIndex(p => new { p.ViewerId, p.PresentId }).IsUnique(); + }); + base.OnModelCreating(modelBuilder); }