Refactor RequestLoggingMiddleware to remove unused methods and streamline user data extraction

This commit is contained in:
Suphonchai Phoonsawat 2026-03-19 10:32:13 +07:00
parent 75718a955d
commit caa0bccd79

View file

@ -1,9 +1,7 @@
using Microsoft.AspNetCore.Http;
using Microsoft.Extensions.Configuration;
using Nest;
using Newtonsoft.Json;
using System.Diagnostics;
using System.Net.Http.Headers;
using System.Security.Claims;
using System.Text.Encodings.Web;
using System.Text.Json;
@ -19,7 +17,6 @@ namespace BMA.EHR.Recurit.Exam.Service.Core
private string Uri = "";
private string IndexFormat = "";
private string SystemName = "";
private string APIKey = "";
public RequestLoggingMiddleware(RequestDelegate next, IConfiguration configuration)
{
@ -32,66 +29,6 @@ namespace BMA.EHR.Recurit.Exam.Service.Core
SystemName = "recruiting";
}
protected async Task<string> GetExternalAPIAsync(string apiPath, string accessToken, string apiKey)
{
try
{
using (var client = new HttpClient())
{
// Set timeout to 30 seconds instead of default 100 seconds
client.Timeout = TimeSpan.FromSeconds(30);
client.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer", accessToken.Replace("Bearer ", ""));
client.DefaultRequestHeaders.Add("api_key", apiKey);
using var cts = new CancellationTokenSource(TimeSpan.FromSeconds(30));
var _res = await client.GetAsync(apiPath, cts.Token);
if (_res.IsSuccessStatusCode)
{
var _result = await _res.Content.ReadAsStringAsync();
return _result;
}
return string.Empty;
}
}
catch (TaskCanceledException)
{
// Log timeout but don't throw - return empty result instead
Console.WriteLine($"API call timed out: {apiPath}");
return string.Empty;
}
catch (Exception ex)
{
// Log other exceptions but don't throw - return empty result instead
Console.WriteLine($"API call failed: {apiPath}, Error: {ex.Message}");
return string.Empty;
}
}
public async Task<GetProfileByKeycloakIdLocal?> GetProfileByKeycloakIdAsync(Guid keycloakId, string? accessToken)
{
try
{
//var apiPath = $"{_configuration["API"]}/org/dotnet/keycloak/{keycloakId}";
var apiPath = $"{_configuration["API"]}/org/dotnet/user-logs/{keycloakId}";
var apiKey = _configuration["API_KEY"] ?? "";
var apiResult = await GetExternalAPIAsync(apiPath, accessToken ?? "", apiKey);
if (!string.IsNullOrEmpty(apiResult))
{
var raw = JsonConvert.DeserializeObject<GetProfileByKeycloakIdResultLocal>(apiResult);
if (raw != null)
return raw.Result;
}
return null;
}
catch (Exception ex)
{
// Log exception but don't throw - return null instead
Console.WriteLine($"GetProfileByKeycloakIdAsync failed for {keycloakId}: {ex.Message}");
return null;
}
}
public async Task Invoke(HttpContext context)
{
@ -157,17 +94,26 @@ namespace BMA.EHR.Recurit.Exam.Service.Core
// Extract all required data from JWT token claims
var keycloakId = context.User?.FindFirst(ClaimTypes.NameIdentifier)?.Value ?? Guid.Empty.ToString("D");
var token = context.Request.Headers["Authorization"];
var pf = await GetProfileByKeycloakIdAsync(Guid.Parse(keycloakId), token);
var _userFullname = string.Empty;
var _userName = string.Empty;
if (keycloakId != "00000000-0000-0000-0000-000000000000" && pf == null)
{
_userFullname = context.User?.FindFirst("name")?.Value;
_userName = context.User?.FindFirst("preferred_username")?.Value;
}
var prefix = context.User?.FindFirst("prefix")?.Value;
var firstName = context.User?.FindFirst("given_name")?.Value;
var lastName = context.User?.FindFirst("family_name")?.Value;
var preferredUsername = context.User?.FindFirst("preferred_username")?.Value;
var orgRootDnaId = context.User?.FindFirst("orgRootDnaId")?.Value;
var orgChild1DnaId = context.User?.FindFirst("orgChild1DnaId")?.Value;
var orgChild2DnaId = context.User?.FindFirst("orgChild2DnaId")?.Value;
var orgChild3DnaId = context.User?.FindFirst("orgChild3DnaId")?.Value;
var orgChild4DnaId = context.User?.FindFirst("orgChild4DnaId")?.Value;
// Parse Guid values safely
Guid? rootDnaId = Guid.TryParse(orgRootDnaId, out var rid) ? rid : null;
Guid? child1DnaId = Guid.TryParse(orgChild1DnaId, out var c1) ? c1 : null;
Guid? child2DnaId = Guid.TryParse(orgChild2DnaId, out var c2) ? c2 : null;
Guid? child3DnaId = Guid.TryParse(orgChild3DnaId, out var c3) ? c3 : null;
Guid? child4DnaId = Guid.TryParse(orgChild4DnaId, out var c4) ? c4 : null;
await _next(context); // ดำเนินการต่อไปยัง Middleware อื่น ๆ
@ -254,8 +200,7 @@ namespace BMA.EHR.Recurit.Exam.Service.Core
{
logType = logType,
ip = context.Connection.RemoteIpAddress?.ToString(),
//rootId = pf == null ? null : pf.RootId,
rootId = pf == null ? null : pf.RootDnaId,
rootId = rootDnaId,
systemName = SystemName,
startTimeStamp = startTime.ToString("o"),
endTimeStamp = endTime.ToString("o"),
@ -269,8 +214,8 @@ namespace BMA.EHR.Recurit.Exam.Service.Core
output = responseBodyJson,
userId = keycloakId,
userName = pf != null ? $"{pf?.Prefix ?? ""}{pf?.FirstName ?? ""} {pf?.LastName ?? ""}" : _userFullname ?? "",
user = pf != null ? pf?.CitizenId ?? "" : _userName ?? ""
userName = $"{prefix ?? ""}{firstName ?? ""} {lastName ?? ""}".Trim(),
user = preferredUsername ?? ""
};
@ -295,47 +240,4 @@ namespace BMA.EHR.Recurit.Exam.Service.Core
return body;
}
}
public class GetProfileByKeycloakIdLocal
{
public Guid Id { get; set; }
public string? Prefix { get; set; }
public string? FirstName { get; set; }
public string? LastName { get; set; }
public string? CitizenId { get; set; }
public string? Root { get; set; }
public string? Child1 { get; set; }
public string? Child2 { get; set; }
public string? Child3 { get; set; }
public string? Child4 { get; set; }
public Guid? RootId { get; set; }
public Guid? Child1Id { get; set; }
public Guid? Child2Id { get; set; }
public Guid? Child3Id { get; set; }
public Guid? Child4Id { get; set; }
public Guid? RootDnaId { get; set; }
public Guid? Child1DnaId { get; set; }
public Guid? Child2DnaId { get; set; }
public Guid? Child3DnaId { get; set; }
public Guid? Child4DnaId { get; set; }
public double? Amount { get; set; }
public double? PositionSalaryAmount { get; set; }
public string? Commander { get; set; }
public Guid? CommanderId { get; set; }
public Guid? CommanderKeycloak { get; set; }
}
public class GetProfileByKeycloakIdResultLocal
{
public string Message { get; set; } = string.Empty;
public int Status { get; set; } = -1;
public GetProfileByKeycloakIdLocal? Result { get; set; }
}
}