From 9bf60d41e068dd22b81782f9b24287d30d6287f8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Halil=20=C4=B0brahim=20Kalkan?= Date: Mon, 5 Mar 2018 15:12:54 +0300 Subject: [PATCH] Handle multiple roles. --- Volo.Abp.sln | 7 +++ .../AbpClaimActionCollectionExtensions.cs | 12 ++++- .../OAuth/Claims/MultipleClaimAction.cs | 40 ++++++++++++++++ ...pNetCore.Authentication.OAuth.Tests.csproj | 24 ++++++++++ .../Authentication/OAuth/Claims/Class1.cs | 46 +++++++++++++++++++ 5 files changed, 127 insertions(+), 2 deletions(-) create mode 100644 src/Volo.Abp.AspNetCore.Authentication.OAuth/Volo/Abp/AspNetCore/Authentication/OAuth/Claims/MultipleClaimAction.cs create mode 100644 test/Volo.Abp.AspNetCore.Authentication.OAuth.Tests/Volo.Abp.AspNetCore.Authentication.OAuth.Tests.csproj create mode 100644 test/Volo.Abp.AspNetCore.Authentication.OAuth.Tests/Volo/Abp/AspNetCore/Authentication/OAuth/Claims/Class1.cs diff --git a/Volo.Abp.sln b/Volo.Abp.sln index 6e882feeb4..d2aeef620b 100644 --- a/Volo.Abp.sln +++ b/Volo.Abp.sln @@ -304,6 +304,8 @@ Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MicroserviceDemo.ConsoleCli EndProject Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Volo.Abp.AspNetCore.Authentication.OAuth", "src\Volo.Abp.AspNetCore.Authentication.OAuth\Volo.Abp.AspNetCore.Authentication.OAuth.csproj", "{A1C792B7-0DBF-460D-9158-A1A68A2D9C1A}" EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Volo.Abp.AspNetCore.Authentication.OAuth.Tests", "test\Volo.Abp.AspNetCore.Authentication.OAuth.Tests\Volo.Abp.AspNetCore.Authentication.OAuth.Tests.csproj", "{627B88DB-BDCF-4D92-8454-EFE95F4AFB7A}" +EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution Debug|Any CPU = Debug|Any CPU @@ -802,6 +804,10 @@ Global {A1C792B7-0DBF-460D-9158-A1A68A2D9C1A}.Debug|Any CPU.Build.0 = Debug|Any CPU {A1C792B7-0DBF-460D-9158-A1A68A2D9C1A}.Release|Any CPU.ActiveCfg = Release|Any CPU {A1C792B7-0DBF-460D-9158-A1A68A2D9C1A}.Release|Any CPU.Build.0 = Release|Any CPU + {627B88DB-BDCF-4D92-8454-EFE95F4AFB7A}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {627B88DB-BDCF-4D92-8454-EFE95F4AFB7A}.Debug|Any CPU.Build.0 = Debug|Any CPU + {627B88DB-BDCF-4D92-8454-EFE95F4AFB7A}.Release|Any CPU.ActiveCfg = Release|Any CPU + {627B88DB-BDCF-4D92-8454-EFE95F4AFB7A}.Release|Any CPU.Build.0 = Release|Any CPU EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE @@ -950,6 +956,7 @@ Global {E4AB8A4F-BB59-4BDB-B915-877CE97D8113} = {DB012309-74FD-4D5A-B843-DD77BF053BF4} {CD4E755D-D47C-45B1-AFB3-3444FF2E2E39} = {3510E248-DC9F-4A07-8134-02E7F5CC5783} {A1C792B7-0DBF-460D-9158-A1A68A2D9C1A} = {C4C6961D-01CC-49A5-8B96-2A36E71CF01F} + {627B88DB-BDCF-4D92-8454-EFE95F4AFB7A} = {37087D1B-3693-4E96-983D-A69F210BDE53} EndGlobalSection GlobalSection(ExtensibilityGlobals) = postSolution SolutionGuid = {BB97ECF4-9A84-433F-A80B-2A3285BDD1D5} diff --git a/src/Volo.Abp.AspNetCore.Authentication.OAuth/Microsoft/AspNetCore/Authentication/OAuth/Claims/AbpClaimActionCollectionExtensions.cs b/src/Volo.Abp.AspNetCore.Authentication.OAuth/Microsoft/AspNetCore/Authentication/OAuth/Claims/AbpClaimActionCollectionExtensions.cs index a5fec0f255..dbaacb6949 100644 --- a/src/Volo.Abp.AspNetCore.Authentication.OAuth/Microsoft/AspNetCore/Authentication/OAuth/Claims/AbpClaimActionCollectionExtensions.cs +++ b/src/Volo.Abp.AspNetCore.Authentication.OAuth/Microsoft/AspNetCore/Authentication/OAuth/Claims/AbpClaimActionCollectionExtensions.cs @@ -1,4 +1,5 @@ -using Volo.Abp.Security.Claims; +using Volo.Abp.AspNetCore.Authentication.OAuth.Claims; +using Volo.Abp.Security.Claims; namespace Microsoft.AspNetCore.Authentication.OAuth.Claims { @@ -6,14 +7,21 @@ namespace Microsoft.AspNetCore.Authentication.OAuth.Claims { public static void MapAbpClaimTypes(this ClaimActionCollection claimActions) { - claimActions.MapJsonKey(AbpClaimTypes.Role, "role"); claimActions.MapJsonKey(AbpClaimTypes.Email, "email"); claimActions.MapJsonKey(AbpClaimTypes.UserName, "name"); claimActions.MapJsonKey(AbpClaimTypes.EmailVerified, "email_verified"); claimActions.MapJsonKey(AbpClaimTypes.PhoneNumber, "phone_number"); claimActions.MapJsonKey(AbpClaimTypes.PhoneNumberVerified, "phone_number_verified"); + + claimActions.MapJsonKeyMultiple(AbpClaimTypes.Role, "role"); + claimActions.DeleteClaim("name"); claimActions.DeleteClaim("email"); } + + public static void MapJsonKeyMultiple(this ClaimActionCollection claimActions, string claimType, string jsonKey) + { + claimActions.Add(new MultipleClaimAction(claimType, jsonKey)); + } } } diff --git a/src/Volo.Abp.AspNetCore.Authentication.OAuth/Volo/Abp/AspNetCore/Authentication/OAuth/Claims/MultipleClaimAction.cs b/src/Volo.Abp.AspNetCore.Authentication.OAuth/Volo/Abp/AspNetCore/Authentication/OAuth/Claims/MultipleClaimAction.cs new file mode 100644 index 0000000000..742f91d057 --- /dev/null +++ b/src/Volo.Abp.AspNetCore.Authentication.OAuth/Volo/Abp/AspNetCore/Authentication/OAuth/Claims/MultipleClaimAction.cs @@ -0,0 +1,40 @@ +using System.Security.Claims; +using Microsoft.AspNetCore.Authentication.OAuth.Claims; +using Newtonsoft.Json.Linq; + +namespace Volo.Abp.AspNetCore.Authentication.OAuth.Claims +{ + public class MultipleClaimAction : ClaimAction + { + public MultipleClaimAction(string claimType, string jsonKey) + : base(claimType, jsonKey) + { + } + + public override void Run(JObject userData, ClaimsIdentity identity, string issuer) + { + var prop = userData?.Property(ValueType); + if (prop == null) + { + return; + } + + var propValue = prop.Value; + + switch (propValue.Type) + { + case JTokenType.String: + identity.AddClaim(new Claim(ClaimType, propValue.Value(), ValueType, issuer)); + break; + case JTokenType.Array: + foreach (var innterValue in propValue.Values()) + { + identity.AddClaim(new Claim(ClaimType, innterValue, ValueType, issuer)); + } + break; + default: + throw new AbpException("Unhandled JTokenType: " + propValue.Type); + } + } + } +} \ No newline at end of file diff --git a/test/Volo.Abp.AspNetCore.Authentication.OAuth.Tests/Volo.Abp.AspNetCore.Authentication.OAuth.Tests.csproj b/test/Volo.Abp.AspNetCore.Authentication.OAuth.Tests/Volo.Abp.AspNetCore.Authentication.OAuth.Tests.csproj new file mode 100644 index 0000000000..e8441e1690 --- /dev/null +++ b/test/Volo.Abp.AspNetCore.Authentication.OAuth.Tests/Volo.Abp.AspNetCore.Authentication.OAuth.Tests.csproj @@ -0,0 +1,24 @@ + + + + netcoreapp2.0 + latest + Volo.Abp.AspNetCore.Authentication.OAuth.Tests + Volo.Abp.AspNetCore.Authentication.OAuth.Tests + true + false + false + false + + + + + + + + + + + + + diff --git a/test/Volo.Abp.AspNetCore.Authentication.OAuth.Tests/Volo/Abp/AspNetCore/Authentication/OAuth/Claims/Class1.cs b/test/Volo.Abp.AspNetCore.Authentication.OAuth.Tests/Volo/Abp/AspNetCore/Authentication/OAuth/Claims/Class1.cs new file mode 100644 index 0000000000..fac9e33e29 --- /dev/null +++ b/test/Volo.Abp.AspNetCore.Authentication.OAuth.Tests/Volo/Abp/AspNetCore/Authentication/OAuth/Claims/Class1.cs @@ -0,0 +1,46 @@ +using System.Linq; +using System.Security.Claims; +using Newtonsoft.Json.Linq; +using Shouldly; +using Volo.Abp.Security.Claims; +using Xunit; + +namespace Volo.Abp.AspNetCore.Authentication.OAuth.Claims +{ + public class MultipleClaimAction_Tests + { + [Fact] + public void Should_Set_Single_Value() + { + var jObject = JObject.Parse(@"{ + ""sub"": ""71054539-0e48-af28-5e7a-39e4e42d8ea5"", + ""role"": ""admin"" +}"); + + var claimsIdentity = new ClaimsIdentity(); + new MultipleClaimAction(AbpClaimTypes.Role, "role").Run(jObject, claimsIdentity, null); + var claims = claimsIdentity.FindAll(AbpClaimTypes.Role).ToList(); + claims.Count.ShouldBe(1); + claims[0].Value.ShouldBe("admin"); + } + + [Fact] + public void Should_Set_Multiple_Values() + { + var jObject = JObject.Parse(@"{ + ""sub"": ""71054539-0e48-af28-5e7a-39e4e42d8ea5"", + ""role"": [ + ""admin"", + ""moderator"" + ] +}"); + + var claimsIdentity = new ClaimsIdentity(); + new MultipleClaimAction(AbpClaimTypes.Role, "role").Run(jObject, claimsIdentity, null); + var claims = claimsIdentity.FindAll(AbpClaimTypes.Role).ToList(); + claims.Count.ShouldBe(2); + claims[0].Value.ShouldBe("admin"); + claims[1].Value.ShouldBe("moderator"); + } + } +}