|  |  | 1 |  | using System.Security.Claims; | 
|  |  | 2 |  | using LGDXRobotCloud.API.Exceptions; | 
|  |  | 3 |  | using LGDXRobotCloud.Data.DbContexts; | 
|  |  | 4 |  | using LGDXRobotCloud.Data.Entities; | 
|  |  | 5 |  | using LGDXRobotCloud.Data.Models.Business.Administration; | 
|  |  | 6 |  | using LGDXRobotCloud.Data.Models.RabbitMQ; | 
|  |  | 7 |  | using LGDXRobotCloud.Utilities.Helpers; | 
|  |  | 8 |  | using Microsoft.EntityFrameworkCore; | 
|  |  | 9 |  | using Wolverine; | 
|  |  | 10 |  |  | 
|  |  | 11 |  | namespace LGDXRobotCloud.API.Services.Administration; | 
|  |  | 12 |  |  | 
|  |  | 13 |  | public interface IActivityLogService | 
|  |  | 14 |  | { | 
|  |  | 15 |  |   Task<(IEnumerable<ActivityLogListBusinessModel>, PaginationHelper)> GetActivityLogsAsync(string? entityName, string? e | 
|  |  | 16 |  |   Task<ActivityLogBusinessModel> GetActivityLogAsync(int id); | 
|  |  | 17 |  |   Task CreateActivityLogAsync(ActivityLogCreateBusinessModel activityLogCreateBusinessMode); | 
|  |  | 18 |  | } | 
|  |  | 19 |  |  | 
|  | 0 | 20 |  | public class ActivityLogService( | 
|  | 0 | 21 |  |     LgdxLogsContext LgdxLogsContext, | 
|  | 0 | 22 |  |     IMessageBus bus, | 
|  | 0 | 23 |  |     IHttpContextAccessor httpContextAccessor, | 
|  | 0 | 24 |  |     LgdxContext lgdxContext | 
|  | 0 | 25 |  |   ) : IActivityLogService | 
|  |  | 26 |  | { | 
|  | 0 | 27 |  |   private readonly LgdxLogsContext _lgdxLogsContext = LgdxLogsContext ?? throw new ArgumentNullException(nameof(LgdxLogs | 
|  | 0 | 28 |  |   private readonly IMessageBus _bus = bus ?? throw new ArgumentNullException(nameof(bus)); | 
|  | 0 | 29 |  |   private readonly IHttpContextAccessor _httpContextAccessor = httpContextAccessor ?? throw new ArgumentNullException(na | 
|  | 0 | 30 |  |   private readonly LgdxContext _lgdxContext = lgdxContext ?? throw new ArgumentNullException(nameof(lgdxContext)); | 
|  |  | 31 |  |  | 
|  |  | 32 |  |   public async Task<(IEnumerable<ActivityLogListBusinessModel>, PaginationHelper)> GetActivityLogsAsync(string? entityNa | 
|  | 0 | 33 |  |   { | 
|  | 0 | 34 |  |     var query = _lgdxLogsContext.ActivityLogs as IQueryable<ActivityLog>; | 
|  | 0 | 35 |  |     if (!string.IsNullOrWhiteSpace(entityName)) | 
|  | 0 | 36 |  |     { | 
|  | 0 | 37 |  |       entityName = entityName.Trim(); | 
|  | 0 | 38 |  |       query = query.Where(t => t.EntityName.ToLower().Contains(entityName.ToLower())); | 
|  | 0 | 39 |  |     } | 
|  | 0 | 40 |  |     if (!string.IsNullOrWhiteSpace(entityId)) | 
|  | 0 | 41 |  |     { | 
|  | 0 | 42 |  |       entityId = entityId.Trim(); | 
|  | 0 | 43 |  |       query = query.Where(t => t.EntityId.ToLower().Contains(entityId.ToLower())); | 
|  | 0 | 44 |  |     } | 
|  | 0 | 45 |  |     var itemCount = await query.CountAsync(); | 
|  | 0 | 46 |  |     var PaginationHelper = new PaginationHelper(itemCount, pageNumber, pageSize); | 
|  | 0 | 47 |  |     var activityLogs = await query.AsNoTracking() | 
|  | 0 | 48 |  |       .OrderBy(t => t.Id) | 
|  | 0 | 49 |  |       .Skip(pageSize * (pageNumber - 1)) | 
|  | 0 | 50 |  |       .Take(pageSize) | 
|  | 0 | 51 |  |       .Select(t => new ActivityLogListBusinessModel | 
|  | 0 | 52 |  |       { | 
|  | 0 | 53 |  |         Id = t.Id, | 
|  | 0 | 54 |  |         EntityName = t.EntityName, | 
|  | 0 | 55 |  |         EntityId = t.EntityId, | 
|  | 0 | 56 |  |         Action = (Utilities.Enums.ActivityAction)t.Action, | 
|  | 0 | 57 |  |         UserId = t.UserId, | 
|  | 0 | 58 |  |         CreatedAt = t.CreatedAt, | 
|  | 0 | 59 |  |       }) | 
|  | 0 | 60 |  |       .ToListAsync(); | 
|  |  | 61 |  |  | 
|  |  | 62 |  |     // Get UserName | 
|  | 0 | 63 |  |     HashSet<string> userIds = activityLogs.Where(t => t.UserId != null) | 
|  | 0 | 64 |  |       .Select(t => t.UserId!.Value.ToString()) | 
|  | 0 | 65 |  |       .ToHashSet(); | 
|  |  | 66 |  |  | 
|  | 0 | 67 |  |     Dictionary<string, string?> userNames = await _lgdxContext.Users | 
|  | 0 | 68 |  |       .Where(t => userIds.Contains(t.Id)) | 
|  | 0 | 69 |  |       .Select(t => new { t.Id, t.UserName }) | 
|  | 0 | 70 |  |       .ToDictionaryAsync(t => t.Id, t => t.UserName); | 
|  |  | 71 |  |  | 
|  | 0 | 72 |  |     foreach (var activityLog in activityLogs) | 
|  | 0 | 73 |  |     { | 
|  | 0 | 74 |  |       if (activityLog.UserId != null) | 
|  | 0 | 75 |  |       { | 
|  | 0 | 76 |  |         activityLog.UserName = userNames[activityLog.UserId.ToString()!]; | 
|  | 0 | 77 |  |       } | 
|  | 0 | 78 |  |     } | 
|  |  | 79 |  |  | 
|  | 0 | 80 |  |     return (activityLogs, PaginationHelper); | 
|  | 0 | 81 |  |   } | 
|  |  | 82 |  |  | 
|  |  | 83 |  |   public async Task<ActivityLogBusinessModel> GetActivityLogAsync(int id) | 
|  | 0 | 84 |  |   { | 
|  | 0 | 85 |  |     var activityLog = await _lgdxLogsContext.ActivityLogs.AsNoTracking() | 
|  | 0 | 86 |  |       .Where(t => t.Id == id) | 
|  | 0 | 87 |  |       .Select(t => new ActivityLogBusinessModel | 
|  | 0 | 88 |  |       { | 
|  | 0 | 89 |  |         Id = t.Id, | 
|  | 0 | 90 |  |         EntityName = t.EntityName, | 
|  | 0 | 91 |  |         EntityId = t.EntityId, | 
|  | 0 | 92 |  |         Action = (Utilities.Enums.ActivityAction)t.Action, | 
|  | 0 | 93 |  |         UserId = t.UserId, | 
|  | 0 | 94 |  |         ApiKeyId = t.ApiKeyId, | 
|  | 0 | 95 |  |         Note = t.Note, | 
|  | 0 | 96 |  |         CreatedAt = t.CreatedAt, | 
|  | 0 | 97 |  |       }) | 
|  | 0 | 98 |  |       .SingleOrDefaultAsync() ?? throw new LgdxNotFound404Exception(); | 
|  |  | 99 |  |  | 
|  |  | 100 |  |     // Get UserName | 
|  | 0 | 101 |  |     if (activityLog.UserId != null) | 
|  | 0 | 102 |  |     { | 
|  | 0 | 103 |  |       activityLog.UserName = await _lgdxContext.Users | 
|  | 0 | 104 |  |         .Where(t => t.Id == activityLog.UserId.ToString()) | 
|  | 0 | 105 |  |         .Select(t => t.UserName) | 
|  | 0 | 106 |  |         .FirstOrDefaultAsync(); | 
|  | 0 | 107 |  |     } | 
|  |  | 108 |  |  | 
|  |  | 109 |  |     // Get ApiKeyName | 
|  | 0 | 110 |  |     if (activityLog.ApiKeyId != null) | 
|  | 0 | 111 |  |     { | 
|  | 0 | 112 |  |       activityLog.ApiKeyName = await _lgdxContext.ApiKeys | 
|  | 0 | 113 |  |         .Where(t => t.Id == activityLog.ApiKeyId) | 
|  | 0 | 114 |  |         .Select(t => t.Name) | 
|  | 0 | 115 |  |         .FirstOrDefaultAsync(); | 
|  | 0 | 116 |  |     } | 
|  |  | 117 |  |  | 
|  | 0 | 118 |  |     return activityLog; | 
|  | 0 | 119 |  |   } | 
|  |  | 120 |  |  | 
|  |  | 121 |  |   public async Task CreateActivityLogAsync(ActivityLogCreateBusinessModel activityLogCreateBusinessModel) | 
|  | 0 | 122 |  |   { | 
|  | 0 | 123 |  |     var httpContext = _httpContextAccessor.HttpContext; | 
|  | 0 | 124 |  |     var userId = httpContext?.User.FindFirst(ClaimTypes.NameIdentifier)?.Value; | 
|  | 0 | 125 |  |     var apiKeyId = httpContext?.Items["ApiKeyId"] as int?; | 
|  | 0 | 126 |  |     await _bus.PublishAsync(new ActivityLogContract | 
|  | 0 | 127 |  |     { | 
|  | 0 | 128 |  |       EntityName = activityLogCreateBusinessModel.EntityName, | 
|  | 0 | 129 |  |       EntityId = activityLogCreateBusinessModel.EntityId, | 
|  | 0 | 130 |  |       Action = activityLogCreateBusinessModel.Action, | 
|  | 0 | 131 |  |       UserId = userId != null ? Guid.Parse(userId) : null, | 
|  | 0 | 132 |  |       ApiKeyId = apiKeyId, | 
|  | 0 | 133 |  |       Note = activityLogCreateBusinessModel.Note, | 
|  | 0 | 134 |  |     }); | 
|  | 0 | 135 |  |   } | 
|  |  | 136 |  | } |