Browse Source

Implement WebAssemblyCurrentPrincipalAccessor (temporary solution)

pull/5399/head
Halil İbrahim Kalkan 6 years ago
parent
commit
6b4bcb0054
  1. 35
      framework/src/Volo.Abp.AspNetCore.Components.WebAssembly/Volo/Abp/AspNetCore/Components/WebAssembly/WebAssemblyCachedApplicationConfigurationClient.cs
  2. 39
      framework/src/Volo.Abp.AspNetCore.Components.WebAssembly/Volo/Abp/AspNetCore/Components/WebAssembly/WebAssemblyCurrentUser.cs
  3. 6
      framework/src/Volo.Abp.AspNetCore.Mvc.Client.Common/Volo/Abp/AspNetCore/Mvc/Client/ICachedApplicationConfigurationClient.cs
  4. 4
      framework/src/Volo.Abp.AspNetCore.Mvc.Client.Common/Volo/Abp/AspNetCore/Mvc/Client/RemoteLocalizationContributor.cs
  5. 19
      framework/src/Volo.Abp.AspNetCore.Mvc.Client/Volo/Abp/AspNetCore/Mvc/Client/MvcCachedApplicationConfigurationClient.cs
  6. 30
      framework/src/Volo.Abp.Security/Volo/Abp/Security/Claims/CurrentPrincipalAccessorBase.cs
  7. 26
      framework/src/Volo.Abp.Security/Volo/Abp/Security/Claims/ThreadCurrentPrincipalAccessor.cs
  8. 9
      templates/app/aspnet-core/src/MyCompanyName.MyProjectName.Blazor/App.razor
  9. 5
      templates/app/aspnet-core/src/MyCompanyName.MyProjectName.Blazor/Pages/RoleManagement.razor

35
framework/src/Volo.Abp.AspNetCore.Components.WebAssembly/Volo/Abp/AspNetCore/Components/WebAssembly/WebAssemblyCachedApplicationConfigurationClient.cs

@ -1,36 +1,53 @@
using System.Globalization;
using System.Threading.Tasks;
using System.Threading.Tasks;
using Microsoft.Extensions.Caching.Memory;
using Volo.Abp.AspNetCore.Mvc.ApplicationConfigurations;
using Volo.Abp.AspNetCore.Mvc.Client;
using Volo.Abp.DependencyInjection;
using Volo.Abp.Http.Client.DynamicProxying;
using Volo.Abp.Users;
namespace Volo.Abp.AspNetCore.Components.WebAssembly
{
public class WebAssemblyCachedApplicationConfigurationClient : ICachedApplicationConfigurationClient, ITransientDependency
{
protected IHttpClientProxy<IAbpApplicationConfigurationAppService> Proxy { get; }
protected ICurrentUser CurrentUser { get; }
protected IMemoryCache Cache { get; }
public WebAssemblyCachedApplicationConfigurationClient(
IHttpClientProxy<IAbpApplicationConfigurationAppService> proxy,
ICurrentUser currentUser)
IMemoryCache cache)
{
Proxy = proxy;
CurrentUser = currentUser;
Cache = cache;
}
public async Task InitializeAsync()
{
await GetAsync();
}
public async Task<ApplicationConfigurationDto> GetAsync()
{
//TODO: Cache
return await Cache.GetOrCreateAsync(
CreateCacheKey(),
e => Proxy.Service.GetAsync()
);
}
public ApplicationConfigurationDto Get()
{
var cacheKey = CreateCacheKey();
if(Cache.TryGetValue(cacheKey, out ApplicationConfigurationDto value))
{
return value;
}
return await Proxy.Service.GetAsync();
throw new AbpException($"Should initialize the {nameof(ICachedApplicationConfigurationClient)} before getting the value!");
}
protected virtual string CreateCacheKey()
{
return $"ApplicationConfiguration_{CurrentUser.Id?.ToString("N") ?? "Anonymous"}_{CultureInfo.CurrentUICulture.Name}";
return $"ApplicationConfiguration";
}
}
}

39
framework/src/Volo.Abp.AspNetCore.Components.WebAssembly/Volo/Abp/AspNetCore/Components/WebAssembly/WebAssemblyCurrentUser.cs

@ -0,0 +1,39 @@
using System.Collections.Generic;
using System.Security.Claims;
using Volo.Abp.AspNetCore.Mvc.Client;
using Volo.Abp.DependencyInjection;
using Volo.Abp.Security.Claims;
namespace Volo.Abp.AspNetCore.Components.WebAssembly
{
public class WebAssemblyCurrentPrincipalAccessor : CurrentPrincipalAccessorBase, ITransientDependency
{
protected ICachedApplicationConfigurationClient ConfigurationClient { get; }
public WebAssemblyCurrentPrincipalAccessor(ICachedApplicationConfigurationClient configurationClient)
{
ConfigurationClient = configurationClient;
}
protected override ClaimsPrincipal GetClaimsPrincipal()
{
//TODO: Should be optimized! Or should be replaced?
var configuration = ConfigurationClient.Get();
var claims = new List<Claim>();
claims.Add(new Claim(AbpClaimTypes.UserName,configuration.CurrentUser.UserName));
claims.Add(new Claim(AbpClaimTypes.Email,configuration.CurrentUser.Email));
claims.Add(new Claim(AbpClaimTypes.UserId,configuration.CurrentUser.Id.ToString()));
claims.Add(new Claim(AbpClaimTypes.TenantId,configuration.CurrentUser.TenantId.ToString()));
foreach (var role in configuration.CurrentUser.Roles)
{
claims.Add(new Claim(AbpClaimTypes.Role, role));
}
return new ClaimsPrincipal(new ClaimsIdentity(claims));
}
}
}

6
framework/src/Volo.Abp.AspNetCore.Mvc.Client.Common/Volo/Abp/AspNetCore/Mvc/Client/ICachedApplicationConfigurationClient.cs

@ -5,6 +5,10 @@ namespace Volo.Abp.AspNetCore.Mvc.Client
{
public interface ICachedApplicationConfigurationClient
{
Task InitializeAsync();
Task<ApplicationConfigurationDto> GetAsync();
ApplicationConfigurationDto Get();
}
}
}

4
framework/src/Volo.Abp.AspNetCore.Mvc.Client.Common/Volo/Abp/AspNetCore/Mvc/Client/RemoteLocalizationContributor.cs

@ -55,7 +55,7 @@ namespace Volo.Abp.AspNetCore.Mvc.Client
private Dictionary<string, string> GetResourceOrNull()
{
var applicationConfigurationDto = AsyncHelper.RunSync(() => _applicationConfigurationClient.GetAsync());
var applicationConfigurationDto = _applicationConfigurationClient.Get();
var resource = applicationConfigurationDto
.Localization.Values
@ -69,4 +69,4 @@ namespace Volo.Abp.AspNetCore.Mvc.Client
return resource;
}
}
}
}

19
framework/src/Volo.Abp.AspNetCore.Mvc.Client/Volo/Abp/AspNetCore/Mvc/Client/MvcCachedApplicationConfigurationClient.cs

@ -7,6 +7,7 @@ using Volo.Abp.AspNetCore.Mvc.ApplicationConfigurations;
using Volo.Abp.Caching;
using Volo.Abp.DependencyInjection;
using Volo.Abp.Http.Client.DynamicProxying;
using Volo.Abp.Threading;
using Volo.Abp.Users;
namespace Volo.Abp.AspNetCore.Mvc.Client
@ -30,6 +31,11 @@ namespace Volo.Abp.AspNetCore.Mvc.Client
Cache = cache;
}
public async Task InitializeAsync()
{
await GetAsync();
}
public async Task<ApplicationConfigurationDto> GetAsync()
{
var cacheKey = CreateCacheKey();
@ -57,6 +63,19 @@ namespace Volo.Abp.AspNetCore.Mvc.Client
return configuration;
}
public ApplicationConfigurationDto Get()
{
var cacheKey = CreateCacheKey();
var httpContext = HttpContextAccessor?.HttpContext;
if (httpContext != null && httpContext.Items[cacheKey] is ApplicationConfigurationDto configuration)
{
return configuration;
}
return AsyncHelper.RunSync(GetAsync);
}
protected virtual string CreateCacheKey()
{
return $"ApplicationConfiguration_{CurrentUser.Id?.ToString("N") ?? "Anonymous"}_{CultureInfo.CurrentUICulture.Name}";

30
framework/src/Volo.Abp.Security/Volo/Abp/Security/Claims/CurrentPrincipalAccessorBase.cs

@ -0,0 +1,30 @@
using System;
using System.Security.Claims;
using System.Threading;
namespace Volo.Abp.Security.Claims
{
public abstract class CurrentPrincipalAccessorBase : ICurrentPrincipalAccessor
{
public ClaimsPrincipal Principal => _currentPrincipal.Value ?? GetClaimsPrincipal();
private readonly AsyncLocal<ClaimsPrincipal> _currentPrincipal = new AsyncLocal<ClaimsPrincipal>();
protected abstract ClaimsPrincipal GetClaimsPrincipal();
public virtual IDisposable Change(ClaimsPrincipal principal)
{
return SetCurrent(principal);
}
private IDisposable SetCurrent(ClaimsPrincipal principal)
{
var parent = Principal;
_currentPrincipal.Value = principal;
return new DisposeAction(() =>
{
_currentPrincipal.Value = parent;
});
}
}
}

26
framework/src/Volo.Abp.Security/Volo/Abp/Security/Claims/ThreadCurrentPrincipalAccessor.cs

@ -1,34 +1,14 @@
using System;
using System.Security.Claims;
using System.Security.Claims;
using System.Threading;
using Volo.Abp.DependencyInjection;
namespace Volo.Abp.Security.Claims
{
public class ThreadCurrentPrincipalAccessor : ICurrentPrincipalAccessor, ISingletonDependency
public class ThreadCurrentPrincipalAccessor : CurrentPrincipalAccessorBase, ISingletonDependency
{
public ClaimsPrincipal Principal => _currentPrincipal.Value ?? GetClaimsPrincipal();
private readonly AsyncLocal<ClaimsPrincipal> _currentPrincipal = new AsyncLocal<ClaimsPrincipal>();
protected virtual ClaimsPrincipal GetClaimsPrincipal()
protected override ClaimsPrincipal GetClaimsPrincipal()
{
return Thread.CurrentPrincipal as ClaimsPrincipal;
}
public virtual IDisposable Change(ClaimsPrincipal principal)
{
return SetCurrent(principal);
}
private IDisposable SetCurrent(ClaimsPrincipal principal)
{
var parent = Principal;
_currentPrincipal.Value = principal;
return new DisposeAction(() =>
{
_currentPrincipal.Value = parent;
});
}
}
}

9
templates/app/aspnet-core/src/MyCompanyName.MyProjectName.Blazor/App.razor

@ -1,3 +1,5 @@
@using Volo.Abp.AspNetCore.Mvc.Client
@inject ICachedApplicationConfigurationClient ConfigurationClient
<CascadingAuthenticationState>
<Router AppAssembly="@typeof(Program).Assembly">
<Found Context="routeData">
@ -21,3 +23,10 @@
</NotFound>
</Router>
</CascadingAuthenticationState>
@code
{
protected override async Task OnInitializedAsync()
{
await ConfigurationClient.InitializeAsync();
}
}

5
templates/app/aspnet-core/src/MyCompanyName.MyProjectName.Blazor/Pages/RoleManagement.razor

@ -2,10 +2,13 @@
@attribute [Authorize]
@using Volo.Abp.Identity
@using Microsoft.AspNetCore.Authorization
@using Microsoft.Extensions.Localization
@using Volo.Abp.Application.Dtos
@using Volo.Abp.Identity.Localization
@inject IIdentityRoleAppService RoleAppService
@inject IStringLocalizer<IdentityResource> L
<h1>Roles</h1>
<h1>@L["Roles"]</h1>
@if (_roles != null)
{

Loading…
Cancel
Save