using Dapper; using SIGCM2.Application.Audit; using SIGCM2.Infrastructure.Persistence; namespace SIGCM2.Infrastructure.Audit; public sealed class SecurityEventRepository : ISecurityEventRepository { private readonly SqlConnectionFactory _factory; public SecurityEventRepository(SqlConnectionFactory factory) { _factory = factory; } public async Task InsertAsync( DateTime occurredAt, int? actorUserId, string? attemptedUsername, Guid? sessionId, string action, string result, string? failureReason, string? ipAddress, string? userAgent, string? metadata, CancellationToken ct = default) { const string sql = """ INSERT INTO dbo.SecurityEvent (OccurredAt, ActorUserId, AttemptedUsername, SessionId, Action, Result, FailureReason, IpAddress, UserAgent, Metadata) OUTPUT INSERTED.Id VALUES (@OccurredAt, @ActorUserId, @AttemptedUsername, @SessionId, @Action, @Result, @FailureReason, @IpAddress, @UserAgent, @Metadata); """; await using var conn = _factory.CreateConnection(); await conn.OpenAsync(ct); var cmd = new CommandDefinition(sql, new { OccurredAt = occurredAt, ActorUserId = actorUserId, AttemptedUsername = attemptedUsername, SessionId = sessionId, Action = action, Result = result, FailureReason = failureReason, IpAddress = ipAddress, UserAgent = userAgent, Metadata = metadata, }, cancellationToken: ct); return await conn.ExecuteScalarAsync(cmd); } }