using System.Security.Claims; using FoodsharingSiegen.Contracts; using FoodsharingSiegen.Contracts.Entity; using FoodsharingSiegen.Server.Data; using FoodsharingSiegen.Server.Service; using FoodsharingSiegen.Shared.Helper; using Microsoft.AspNetCore.Components.Authorization; using Microsoft.EntityFrameworkCore; namespace FoodsharingSiegen.Server.Auth { /// /// The token auth state provider class (a. beging, 02.04.2022) /// /// public class TokenAuthStateProvider : AuthenticationStateProvider { private FsContext Context { get; } #region Private Fields /// LocalStorageService private readonly LocalStorageService _localStorageService; #endregion #region Setup/Teardown /// /// Constructor /// /// /// public TokenAuthStateProvider(LocalStorageService localStorageService, FsContext context) { Context = context; _localStorageService = localStorageService; } #endregion #region Override GetAuthenticationStateAsync //////////////////////////////////////////////////////////////////////////////////////////////////// /// Get the current authenticationstate /// A. Beging, 02.02.2022. //////////////////////////////////////////////////////////////////////////////////////////////////// public override async Task GetAuthenticationStateAsync() { var token = await _localStorageService.GetItem(StorageKeys.TokenKey); var tokenValid = AuthHelper.ValidateToken(token, out var user); var checkR = await CheckForceLogout(user); if (checkR.Success && checkR.Data) tokenValid = false; var identity = new ClaimsIdentity(); if (tokenValid) identity = new ClaimsIdentity(new[] { new Claim(ClaimTypes.Name, "user") }, "TODO"); var claimsPrincipal = new ClaimsPrincipal(identity); return new AuthenticationState(claimsPrincipal); } #endregion #region Public Method MarkUserAsAuthenticated //////////////////////////////////////////////////////////////////////////////////////////////////// /// Mark user as authenticated. /// A. Beging, 02.02.2022. //////////////////////////////////////////////////////////////////////////////////////////////////// public void MarkUserAsAuthenticated() => NotifyAuthenticationStateChanged(GetAuthenticationStateAsync()); #endregion #region Public Method CheckForceLogout /// /// Checks the force logout using the specified user (a. beging, 11.04.2022) /// /// The user /// A task containing an operation result of bool public async Task> CheckForceLogout(User? user) { try { if (user == null) return new OperationResult(new Exception()); var anyR = await Context.Users!.AnyAsync(x => x.Id == user.Id && x.ForceLogout); return new OperationResult(anyR); } catch (Exception e) { return new OperationResult(e); } } #endregion #region Public Method MarkUserAsLoggedOut /// /// Marks the user as logged out (a. beging, 02.04.2022) /// public void MarkUserAsLoggedOut() { var anonymousUser = new ClaimsPrincipal(new ClaimsIdentity()); var authState = Task.FromResult(new AuthenticationState(anonymousUser)); NotifyAuthenticationStateChanged(authState); } #endregion } }