using System; using System.Threading; using System.Threading.Tasks; using GB5Shared.DTO.Framework.Login; using Microsoft.Extensions.Caching.Memory; namespace GB5Shared.GOP.Qualifier { // ============================================================ // IEntityCodeResolver — bridges BaseEntityAppService's numeric // EntityId (EntityConstant.*) to the string EntityCode the GOP // qualifier engine binds against (MQUALIFIERENTITY.ENTITYCODE). // // MENTITY is global framework metadata (no TENANTID column/filter // anywhere else in the codebase) — safe to cache indefinitely per // process; nothing in the ExecuteSaveAsync pipeline writes to it. // ============================================================ public interface IEntityCodeResolver { Task ResolveAsync(int entityId, LoginDTO loginDTO, CancellationToken ct = default); } public class EntityCodeResolver : IEntityCodeResolver { private static readonly TimeSpan CacheTtl = TimeSpan.FromHours(6); private readonly IQualifierDAL _Dal; private readonly IMemoryCache _Cache; public EntityCodeResolver(IQualifierDAL dal, IMemoryCache cache) { _Dal = dal; _Cache = cache; } public async Task ResolveAsync(int entityId, LoginDTO loginDTO, CancellationToken ct = default) { var cacheKey = $"EntityCode:{entityId}"; if (_Cache.TryGetValue(cacheKey, out string? cached)) return cached; var entityCode = await _Dal.GetEntityCodeById(entityId, loginDTO, ct); _Cache.Set(cacheKey, entityCode, CacheTtl); return entityCode; } } }