using Microsoft.AspNetCore.Http; using Netmash.Security.Authentication.Tuitio.Abstractions; using Netmash.Security.Authentication.Tuitio.Extensions; using Newtonsoft.Json; using System; using System.Collections.Generic; using System.Linq; using System.Security.Claims; using Tuitio.PublishedLanguage.Dto; using c = Netmash.Security.Authentication.Tuitio.Constants; namespace Netmash.Security.Authentication.Tuitio.Services { internal class UserContextAccessor : IUserContextAccessor { private readonly IHttpContextAccessor _httpAccessor; public UserContextAccessor(IHttpContextAccessor httpAccessor) { _httpAccessor = httpAccessor; } public bool UserIsLoggedIn => _httpAccessor.HttpContext.User != null; public string UserId => GetUserClaim(ClaimTypes.NameIdentifier, true, true, "User id"); public string UserName => GetUserClaim(ClaimTypes.Name, true, true, "User name"); public IEnumerable<(int id, string code)> UserGroups { get { var groups = GetUserClaim>(c.ClaimTypes.UserGroups, false, false); return groups.ToTuples(); } } public IEnumerable<(int id, string code)> UserRoles { get { var roles = GetUserClaim>(c.ClaimTypes.UserRoles, false, false); return roles.ToTuples(); } } public bool IsAnonymousGuest => GetUserClaim(c.ClaimTypes.IsAnonymousGuest); private T GetUserClaim(string claimType, bool isMandatory = false, bool isPrimitiveType = true, string claimLabel = null) { var claimValue = _httpAccessor.HttpContext.User?.Claims.FirstOrDefault(z => z.Type == claimType)?.Value; if (string.IsNullOrEmpty(claimValue)) { if (isMandatory) throw new Exception($"{claimLabel ?? claimType} could not be retrieved from claims."); else return default; } try { if (isPrimitiveType) return (T)Convert.ChangeType(claimValue, typeof(T)); else return JsonConvert.DeserializeObject(claimValue); } catch (Exception ex) { throw new Exception($"Failed to convert claim {claimLabel ?? claimType} to type {typeof(T).Name}.", ex); } } } }