Files
ROLAC/API/ROLAC.API/Data/AppDbContext.cs
T
Chris Chen 34344cbf83 feat: add Member/FamilyUnit DbSets, audit interceptor registration, EF migration
Registers AuditSaveChangesInterceptor in DI and wires it into AppDbContext.
Adds Members and FamilyUnits DbSets with full column/index configuration and
applies the AddMemberAndFamilyUnit migration to the ChurchCRM database.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-27 13:52:58 -07:00

94 lines
4.8 KiB
C#

using Microsoft.AspNetCore.Identity.EntityFrameworkCore;
using Microsoft.EntityFrameworkCore;
using ROLAC.API.Entities;
namespace ROLAC.API.Data;
public class AppDbContext : IdentityDbContext<AppUser, AppRole, string>
{
public AppDbContext(DbContextOptions<AppDbContext> options) : base(options) { }
public DbSet<RefreshToken> RefreshTokens => Set<RefreshToken>();
public DbSet<Member> Members => Set<Member>();
public DbSet<FamilyUnit> FamilyUnits => Set<FamilyUnit>();
protected override void OnModelCreating(ModelBuilder builder)
{
base.OnModelCreating(builder);
// ── RefreshToken (unchanged) ────────────────────────────────────────
builder.Entity<RefreshToken>(entity =>
{
entity.HasKey(e => e.Id);
entity.HasIndex(e => e.TokenHash).IsUnique();
entity.Property(e => e.TokenHash).HasMaxLength(64).IsRequired();
entity.Property(e => e.UserId).HasMaxLength(450).IsRequired();
entity.Property(e => e.DeviceInfo).HasMaxLength(200);
entity.Property(e => e.IpAddress).HasMaxLength(45);
entity.Property(e => e.ReplacedByHash).HasMaxLength(64);
entity.HasOne(e => e.User).WithMany(u => u.RefreshTokens)
.HasForeignKey(e => e.UserId).OnDelete(DeleteBehavior.Cascade);
entity.Ignore(e => e.IsExpired);
entity.Ignore(e => e.IsRevoked);
entity.Ignore(e => e.IsActive);
});
// ── AppUser (unchanged + new unique index on MemberId) ──────────────
builder.Entity<AppUser>(entity =>
{
entity.Property(e => e.LanguagePreference).HasMaxLength(10).HasDefaultValue("en");
// Nullable unique: one member ↔ one user account, but member can have no account
entity.HasIndex(e => e.MemberId).IsUnique()
.HasFilter("\"MemberId\" IS NOT NULL");
});
// ── AppRole (unchanged) ─────────────────────────────────────────────
builder.Entity<AppRole>(entity =>
{
entity.Property(e => e.Description).HasMaxLength(500);
});
// ── FamilyUnit ──────────────────────────────────────────────────────
builder.Entity<FamilyUnit>(entity =>
{
entity.Property(e => e.FamilyName_en).HasMaxLength(200);
entity.Property(e => e.FamilyName_zh).HasMaxLength(200);
});
// ── Member ──────────────────────────────────────────────────────────
builder.Entity<Member>(entity =>
{
entity.HasQueryFilter(m => !m.IsDeleted);
entity.Property(e => e.FirstName_en).HasMaxLength(100).IsRequired();
entity.Property(e => e.LastName_en).HasMaxLength(100).IsRequired();
entity.Property(e => e.NickName).HasMaxLength(100);
entity.Property(e => e.FirstName_zh).HasMaxLength(100);
entity.Property(e => e.LastName_zh).HasMaxLength(100);
entity.Property(e => e.Gender).HasMaxLength(10);
entity.Property(e => e.BaptismChurch).HasMaxLength(200);
entity.Property(e => e.Email).HasMaxLength(200);
entity.Property(e => e.PhoneCell).HasMaxLength(30);
entity.Property(e => e.PhoneHome).HasMaxLength(30);
entity.Property(e => e.Address).HasMaxLength(500);
entity.Property(e => e.City).HasMaxLength(100);
entity.Property(e => e.State).HasMaxLength(50);
entity.Property(e => e.ZipCode).HasMaxLength(20);
entity.Property(e => e.Country).HasMaxLength(100).HasDefaultValue("USA");
entity.Property(e => e.PhotoBlobPath).HasMaxLength(500);
entity.Property(e => e.Status).HasMaxLength(20).HasDefaultValue("Member");
entity.Property(e => e.LanguagePreference).HasMaxLength(10).HasDefaultValue("en");
entity.Property(e => e.CreatedBy).HasMaxLength(450);
entity.Property(e => e.UpdatedBy).HasMaxLength(450);
entity.Property(e => e.DeletedBy).HasMaxLength(450);
entity.HasIndex(e => e.Status).HasFilter("\"IsDeleted\" = false");
entity.HasIndex(e => e.Email).HasFilter("\"Email\" IS NOT NULL");
entity.HasIndex(e => e.FamilyUnitId);
entity.HasOne(e => e.FamilyUnit).WithMany()
.HasForeignKey(e => e.FamilyUnitId).OnDelete(DeleteBehavior.SetNull);
});
}
}