refactor(guild_chat): extract chat-user lookup to viewer repo; fix NEW-direction exclusivity

Add ChatUserProfile record and IViewerRepository.LoadChatProfilesAsync (AsNoTracking,
projects Name/EmblemId/CountryCode/Rank/DegreeId from Viewer+Info nav refs).
GuildChatController.Messages now injects IViewerRepository instead of SVSimDbContext;
calls LoadChatProfilesAsync to populate users[] (removes direct db access from controller).
GuildChatMessageRepository direction=2 (NEW): change >= start to > start (exclusive).
GuildChatPollTests updated to assert the start message is NOT returned by direction=NEW.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
gamer147
2026-06-27 14:51:44 -04:00
parent 358f43aa7a
commit a248c167e0
5 changed files with 74 additions and 29 deletions

View File

@@ -1,6 +1,5 @@
using Microsoft.AspNetCore.Mvc;
using Microsoft.EntityFrameworkCore;
using SVSim.Database;
using SVSim.Database.Repositories.Viewer;
using SVSim.Database.Services.Guild;
using SVSim.EmulatedEntrypoint.Models.Dtos.Common;
using SVSim.EmulatedEntrypoint.Models.Dtos.Common.Guild;
@@ -14,12 +13,12 @@ namespace SVSim.EmulatedEntrypoint.Controllers;
public sealed class GuildChatController : SVSimController
{
private readonly IGuildChatService _chat;
private readonly SVSimDbContext _db;
private readonly IViewerRepository _viewers;
public GuildChatController(IGuildChatService chat, SVSimDbContext db)
public GuildChatController(IGuildChatService chat, IViewerRepository viewers)
{
_chat = chat;
_db = db;
_chat = chat;
_viewers = viewers;
}
[HttpPost("messages")]
@@ -53,26 +52,19 @@ public sealed class GuildChatController : SVSimController
.Distinct()
.ToList();
var viewers = authorIds.Count == 0
? new Dictionary<long, SVSim.Database.Models.Viewer>()
: await _db.Viewers
.AsNoTracking()
.Include(v => v.Info.SelectedEmblem)
.Include(v => v.Info.SelectedDegree)
.Where(v => authorIds.Contains(v.Id))
.ToDictionaryAsync(v => v.Id, ct);
var profiles = await _viewers.LoadChatProfilesAsync(authorIds, ct);
var users = authorIds.Select(vid =>
{
viewers.TryGetValue(vid, out var v);
profiles.TryGetValue(vid, out var p);
return new ChatUserDto
{
ViewerId = vid,
Name = v?.DisplayName ?? "",
EmblemId = v?.Info?.SelectedEmblem?.Id is > 0 ? v.Info.SelectedEmblem.Id : 100_000_000L,
CountryCode = v?.Info?.CountryCode ?? "",
Rank = 1, // TODO: real rank when rank tracking lands
DegreeId = v?.Info?.SelectedDegree?.Id ?? 0,
Name = p?.Name ?? "",
EmblemId = p?.EmblemId ?? 100_000_000L,
CountryCode = p?.CountryCode ?? "",
Rank = p?.Rank ?? 1,
DegreeId = p?.DegreeId ?? 0,
};
}).ToList();