- ABP Framework version: v7.4.2
- UI Type: MVC(SQL)
Hi,
After we upgraded from IdentityServer to OpenIdDict there were some issues
We have an Admin application (which is working fine) and Clinic application which has an issue while redirecting to the application dashboard after signing in using OpenId
Please advise ASAP.
46 Answer(s)
-
0
hi, have you checked the sent code?
-
0
hi
Maw3idIdentityServerModule
looks no problem.I suggest you make a project that reproduces the problem. You can test your code in a new template project.
-
0
I have sent the tenant and public web modules, can you please check
-
0
hi
The problem is with the
Maw3idIdentityServerModule
project.I suggest you make a project that reproduces the problem. You can test your code in a new template project.
-
0
Hi,
After a lot of investigation, I have fixed the issue by adding some scope values.
Now there exist 2 issues
The first one is that after logging in, the CurrentUser data is filled correctly but the phone is Null !
and second when we try to request tokens using
var result = await httpClient.RequestTokenAsync(request);
the result is "unsupported grant_type",
We want to get a token using the phone number and a verification code sent to the customer. What are the changes that should be done for that? It was working normally with the identity server but it did not work after upgrading to openiddict.
-
0
hi
The first one is that after logging in, the CurrentUser data is filled correctly but the phone is Null !
Please check the value of
AbpClaimTypes.PhoneNumber
andAbpClaimTypes.PhoneNumberVerified
. And check theClaim[] GetAllClaims
ofICurrentUser
the result is "unsupported grant_type",
Please share the HTTP request and response info and logs.
Thanks.
-
0
The first one is that after logging in, the CurrentUser data is filled correctly but the phone is Null !
Please check the value of
AbpClaimTypes.PhoneNumber
it's value is "phone_number"
and
AbpClaimTypes.PhoneNumberVerified
.it's value is
"phone_number_verified"
And check the
Claim[] GetAllClaims
ofICurrentUser
the result is "unsupported grant_type",
Please share the HTTP request and response info and logs.
var disc = await httpClient.GetDiscoveryDocumentAsync(_options.CurrentValue.Authority); var request = new TokenRequest { Address = _options.CurrentValue.Authority + _options.CurrentValue.TokenEndPoint, GrantType = "PhoneNumberLogin_credentials", ClientId = _options.CurrentValue.ClientId, ClientSecret = _options.CurrentValue.ClientSecret, Parameters = { {"phonenumber", phoneNumber}, {"code", code} } }; var configManager = new ConfigurationManager<OpenIdConnectConfiguration>($"{_options.CurrentValue.Authority}/.well-known/openid-configuration", new OpenIdConnectConfigurationRetriever()); var openidconfig = await configManager.GetConfigurationAsync(); var result = await httpClient.RequestTokenAsync(request);
2024-01-28 07:49:15.031 +02:00 [DBG] The event OpenIddict.Server.OpenIddictServerEvents+ExtractTokenRequestContext was successfully processed by OpenIddict.Server.AspNetCore.OpenIddictServerAspNetCoreHandlers+ExtractPostRequest`1[[OpenIddict.Server.OpenIddictServerEvents+ExtractTokenRequestContext, OpenIddict.Server, Version=4.8.0.0, Culture=neutral, PublicKeyToken=35a561290d20de2f]]. 2024-01-28 07:49:15.040 +02:00 [DBG] The event OpenIddict.Server.OpenIddictServerEvents+ExtractTokenRequestContext was successfully processed by OpenIddict.Server.AspNetCore.OpenIddictServerAspNetCoreHandlers+ExtractBasicAuthenticationCredentials`1[[OpenIddict.Server.OpenIddictServerEvents+ExtractTokenRequestContext, OpenIddict.Server, Version=4.8.0.0, Culture=neutral, PublicKeyToken=35a561290d20de2f]]. 2024-01-28 07:49:15.042 +02:00 [INF] The token request was successfully extracted: { "phonenumber": "966511223344", "code": "[redacted]", "grant_type": "PhoneNumberLogin_credentials", "client_id": "MyApp_Public_Web_Tiered", "client_secret": "[redacted]" }. 2024-01-28 07:49:15.042 +02:00 [DBG] The event OpenIddict.Server.OpenIddictServerEvents+ProcessRequestContext was successfully processed by OpenIddict.Server.OpenIddictServerHandlers+Exchange+ExtractTokenRequest. 2024-01-28 07:49:15.057 +02:00 [INF] The token request was rejected because the 'PhoneNumberLogin_credentials' grant type is not supported. 2024-01-28 07:49:15.090 +02:00 [DBG] The event OpenIddict.Server.OpenIddictServerEvents+ValidateTokenRequestContext was successfully processed by OpenIddict.Server.OpenIddictServerHandlers+Exchange+ValidateGrantType. 2024-01-28 07:49:15.090 +02:00 [DBG] The event OpenIddict.Server.OpenIddictServerEvents+ValidateTokenRequestContext was marked as rejected by OpenIddict.Server.OpenIddictServerHandlers+Exchange+ValidateGrantType. 2024-01-28 07:49:15.092 +02:00 [DBG] The event OpenIddict.Server.OpenIddictServerEvents+ProcessRequestContext was successfully processed by OpenIddict.Server.OpenIddictServerHandlers+Exchange+ValidateTokenRequest. 2024-01-28 07:49:15.092 +02:00 [DBG] The event OpenIddict.Server.OpenIddictServerEvents+ProcessRequestContext was marked as rejected by OpenIddict.Server.OpenIddictServerHandlers+Exchange+ValidateTokenRequest. 2024-01-28 07:49:15.107 +02:00 [DBG] The event OpenIddict.Server.OpenIddictServerEvents+ProcessErrorContext was successfully processed by OpenIddict.Server.OpenIddictServerHandlers+AttachErrorParameters. 2024-01-28 07:49:15.110 +02:00 [DBG] The event OpenIddict.Server.OpenIddictServerEvents+ProcessErrorContext was successfully processed by OpenIddict.Server.OpenIddictServerHandlers+AttachCustomErrorParameters. 2024-01-28 07:49:15.170 +02:00 [DBG] The event OpenIddict.Server.OpenIddictServerEvents+ApplyTokenResponseContext was successfully processed by OpenIddict.Server.OpenIddictServerHandlers+Exchange+NormalizeErrorResponse. 2024-01-28 07:49:15.173 +02:00 [DBG] The event OpenIddict.Server.OpenIddictServerEvents+ApplyTokenResponseContext was successfully processed by OpenIddict.Server.AspNetCore.OpenIddictServerAspNetCoreHandlers+AttachHttpResponseCode`1[[OpenIddict.Server.OpenIddictServerEvents+ApplyTokenResponseContext, OpenIddict.Server, Version=4.8.0.0, Culture=neutral, PublicKeyToken=35a561290d20de2f]]. 2024-01-28 07:49:15.175 +02:00 [DBG] The event OpenIddict.Server.OpenIddictServerEvents+ApplyTokenResponseContext was successfully processed by OpenIddict.Server.AspNetCore.OpenIddictServerAspNetCoreHandlers+AttachCacheControlHeader`1[[OpenIddict.Server.OpenIddictServerEvents+ApplyTokenResponseContext, OpenIddict.Server, Version=4.8.0.0, Culture=neutral, PublicKeyToken=35a561290d20de2f]]. 2024-01-28 07:49:15.175 +02:00 [DBG] The event OpenIddict.Server.OpenIddictServerEvents+ApplyTokenResponseContext was successfully processed by OpenIddict.Server.AspNetCore.OpenIddictServerAspNetCoreHandlers+AttachWwwAuthenticateHeader`1[[OpenIddict.Server.OpenIddictServerEvents+ApplyTokenResponseContext, OpenIddict.Server, Version=4.8.0.0, Culture=neutral, PublicKeyToken=35a561290d20de2f]]. 2024-01-28 07:49:15.178 +02:00 [DBG] The event OpenIddict.Server.OpenIddictServerEvents+ApplyTokenResponseContext was successfully processed by Volo.Abp.Account.Web.ExtensionGrants.LinkLoginExtensionGrantProcessJsonResponse. 2024-01-28 07:49:15.180 +02:00 [INF] The response was successfully returned as a JSON document: { "error": "unsupported\_grant\_type", "error\_description": "The specified 'grant\_type' is not supported.", "error\_uri": "[https://documentation.openiddict.com/errors/ID2032"](https://documentation.openiddict.com/errors/ID2032%22) }. 2024-01-28 07:49:15.190 +02:00 [DBG] The event OpenIddict.Server.OpenIddictServerEvents+ApplyTokenResponseContext was successfully processed by OpenIddict.Server.AspNetCore.OpenIddictServerAspNetCoreHandlers+ProcessJsonResponse`1[[OpenIddict.Server.OpenIddictServerEvents+ApplyTokenResponseContext, OpenIddict.Server, Version=4.8.0.0, Culture=neutral, PublicKeyToken=35a561290d20de2f]].
-
0
hi
Your current identity has no
phone_number
andphone_number_verified
claims.The token request was rejected because the 'PhoneNumberLogin_credentials' grant type is not supported.
Please check this https://community.abp.io/posts/how-to-add-a-custom-grant-type-in-openiddict.-6v0df94z make sure your
PhoneNumberLogin_credentials
is added to OpenIddict correctly. -
0
hi, what is the namespace for ITokenExtensionGrant, ExtensionGrantContext, OpenIddictServerAspNetCoreDefaults, OpenIddictServerAspNetCoreConstants, please?
-
0
hi
https://github.com/abpframework/abp/blob/dev/modules/openiddict/src/Volo.Abp.OpenIddict.AspNetCore/Volo/Abp/OpenIddict/ExtensionGrantTypes/ITokenExtensionGrant.cs#L4
-
0
hi
Please check this https://community.abp.io/posts/how-to-add-a-custom-grant-type-in-openiddict.-6v0df94z
what are the usings used in MyTokenExtensionGrant class please? as i face some ambiguty and compliation errors.
-
0
Your current identity has no
phone_number
andphone_number_verified
claims.how to add them please?
-
0
hi
The framework will add it to access_token automatically. That is, if you don't change the code, it will be there.
https://github.com/abpframework/abp/blob/dev/modules/identity/src/Volo.Abp.Identity.Domain/Volo/Abp/Identity/AbpUserClaimsPrincipalFactory.cs#L61
-
0
hi,
I have added the customTokenExtensionGrant and now the result is succeed
var request = new TokenRequest { Address = _options.CurrentValue.Authority + _options.CurrentValue.TokenEndPoint, GrantType = MyApp.Identity.PhoneNumberLoginConsts.GrantType, ClientId = _options.CurrentValue.ClientId, ClientSecret = _options.CurrentValue.ClientSecret, Parameters = { {"phone_number", phoneNumber}, {"code", code} } }; var result = await httpClient.RequestTokenAsync(request);
but there is an old code (while using identity server) after the result is get
if (!result.IsError) { var TokenValidationParameters = new TokenValidationParameters() { ValidateAudience = true, ValidAudience = "Public", ValidateIssuer = true, ValidIssuers = new[] { _options.CurrentValue.Authority }, ValidateIssuerSigningKey = true, IssuerSigningKeys = openidconfig.SigningKeys, RequireExpirationTime = true, ValidateLifetime = true, RequireSignedTokens = true, }; JwtSecurityTokenHandler jwtSecurityTokenHandler = new JwtSecurityTokenHandler(); var claimsPrinciples = jwtSecurityTokenHandler.ValidateToken(result.AccessToken, TokenValidationParameters, out SecurityToken validatedToken); var AuthenticationProperties = new AuthenticationProperties(); if (_options.CurrentValue.SaveTokens) { var authTokens = new List<AuthenticationToken>(); authTokens.Add(new AuthenticationToken { Name = "access_token", Value = result.AccessToken }); if (!string.IsNullOrEmpty(result.RefreshToken)) { authTokens.Add(new AuthenticationToken { Name = "refresh_token", Value = result.RefreshToken }); } if (!string.IsNullOrEmpty(result.TokenType)) { authTokens.Add(new AuthenticationToken { Name = "token_type", Value = result.TokenType }); } if (result.ExpiresIn != 0) { var expiresAt = DateTime.UtcNow + TimeSpan.FromSeconds(result.ExpiresIn); authTokens.Add(new AuthenticationToken { Name = "expires_at", Value = expiresAt.ToString("o", CultureInfo.InvariantCulture) }); AuthenticationProperties.ExpiresUtc = expiresAt; } AuthenticationProperties.StoreTokens(authTokens); } // generate AuthenticationTicket from the Identity // and current authentication scheme var ticket = new AuthenticationTicket(claimsPrinciples,AuthenticationProperties, "Cookies"); return AuthenticateResult.Success(ticket);
bur there is an error
IDX10206: Unable to validate audience. The 'audiences' parameter is empty.
so how can i fix, or what is the replacement for that code using openIdDict not identityServer?
-
0
hi
The framework will add it to access_token automatically. That is, if you don't change the code, it will be there.
https://github.com/abpframework/abp/blob/dev/modules/identity/src/Volo.Abp.Identity.Domain/Volo/Abp/Identity/AbpUserClaimsPrincipalFactory.cs#L61
also, i have overridden the AbpUserClaimsPrincipalFactory
using System; using System.Linq; using System.Security.Claims; using System.Threading.Tasks; using Microsoft.AspNetCore.Identity; using Microsoft.Extensions.Options; using System.Security.Principal; using Volo.Abp.DependencyInjection; using Volo.Abp.Security.Claims; using Volo.Abp.Uow; using MyApp.Users; using Volo.Abp.Identity; using IdentityUser = Volo.Abp.Identity.IdentityUser; using IdentityRole = Volo.Abp.Identity.IdentityRole; namespace MyApp.Identity { /// <summary> /// </summary> [Dependency(ReplaceServices = true)] [ExposeServices(typeof(AbpUserClaimsPrincipalFactory), typeof(ExtendedUserClaimsPrincipalFactory), IncludeSelf = false, IncludeDefaults = false)] public class ExtendedUserClaimsPrincipalFactory : AbpUserClaimsPrincipalFactory, ITransientDependency { public ExtendedUserClaimsPrincipalFactory( UserManager<IdentityUser> userManager, RoleManager<IdentityRole> roleManager, IOptions<IdentityOptions> options, ICurrentPrincipalAccessor currentPrincipalAccessor, IAbpClaimsPrincipalFactory abpClaimsPrincipalFactory) : base( userManager, roleManager, options, currentPrincipalAccessor, abpClaimsPrincipalFactory) { } [UnitOfWork] public override async Task<ClaimsPrincipal> CreateAsync(IdentityUser user) { var principal = await base.CreateAsync(user); var identity = principal.Identities.First(); if (user.TenantId.HasValue) { identity.AddIfNotContains(new Claim(AbpClaimTypes.TenantId, user.TenantId.ToString())); } if (!user.Name.IsNullOrWhiteSpace()) { identity.AddIfNotContains(new Claim(AbpClaimTypes.Name, user.Name)); } if (!user.Surname.IsNullOrWhiteSpace()) { identity.AddIfNotContains(new Claim(AbpClaimTypes.SurName, user.Surname)); } if (!user.PhoneNumber.IsNullOrWhiteSpace()) { identity.AddIfNotContains(new Claim(AbpClaimTypes.PhoneNumber, user.PhoneNumber)); } identity.AddIfNotContains( new Claim(AbpClaimTypes.PhoneNumberVerified, user.PhoneNumberConfirmed.ToString())); if (!user.Email.IsNullOrWhiteSpace()) { identity.AddIfNotContains(new Claim(AbpClaimTypes.Email, user.Email)); } identity.AddIfNotContains(new Claim(AbpClaimTypes.EmailVerified, user.EmailConfirmed.ToString())); if (user.ExtraProperties.ContainsKey(AppUserConsts.UserTypePropertyName)) { var userType = user.ExtraProperties[AppUserConsts.UserTypePropertyName]?.ToString(); if (!string.IsNullOrEmpty(userType)) identity.AddIfNotContains(new Claim(AppUserConsts.UserTypePropertyName, userType)); } using (CurrentPrincipalAccessor.Change(identity)) { await AbpClaimsPrincipalFactory.CreateAsync(principal); } return principal; } } }
and configured at the domain module
PreConfigure<IdentityBuilder>(builder => { builder.AddClaimsPrincipalFactory<ExtendedUserClaimsPrincipalFactory>(); });
and the principal is filled correctly with claims values, but the phoneNumber at currentUser is still null and currentUser claims did not update with the values at the principal.
Please advise.
-
0
any update please?
-
0
hi
IDX10206: Unable to validate audience. The 'audiences' parameter is empty.
Please share a
access_token
-
0
hi
IDX10206: Unable to validate audience. The 'audiences' parameter is empty.
Please share a
access_token
do you mean a generated access_token value or what?
-
0
hi
The framework will add it to access_token automatically. That is, if you don't change the code, it will be there.
https://github.com/abpframework/abp/blob/dev/modules/identity/src/Volo.Abp.Identity.Domain/Volo/Abp/Identity/AbpUserClaimsPrincipalFactory.cs#L61
also, i have overridden the AbpUserClaimsPrincipalFactory
using System; using System.Linq; using System.Security.Claims; using System.Threading.Tasks; using Microsoft.AspNetCore.Identity; using Microsoft.Extensions.Options; using System.Security.Principal; using Volo.Abp.DependencyInjection; using Volo.Abp.Security.Claims; using Volo.Abp.Uow; using MyApp.Users; using Volo.Abp.Identity; using IdentityUser = Volo.Abp.Identity.IdentityUser; using IdentityRole = Volo.Abp.Identity.IdentityRole; namespace MyApp.Identity { /// <summary> /// </summary> [Dependency(ReplaceServices = true)] [ExposeServices(typeof(AbpUserClaimsPrincipalFactory), typeof(ExtendedUserClaimsPrincipalFactory), IncludeSelf = false, IncludeDefaults = false)] public class ExtendedUserClaimsPrincipalFactory : AbpUserClaimsPrincipalFactory, ITransientDependency { public ExtendedUserClaimsPrincipalFactory( UserManager<IdentityUser> userManager, RoleManager<IdentityRole> roleManager, IOptions<IdentityOptions> options, ICurrentPrincipalAccessor currentPrincipalAccessor, IAbpClaimsPrincipalFactory abpClaimsPrincipalFactory) : base( userManager, roleManager, options, currentPrincipalAccessor, abpClaimsPrincipalFactory) { } [UnitOfWork] public override async Task<ClaimsPrincipal> CreateAsync(IdentityUser user) { var principal = await base.CreateAsync(user); var identity = principal.Identities.First(); if (user.TenantId.HasValue) { identity.AddIfNotContains(new Claim(AbpClaimTypes.TenantId, user.TenantId.ToString())); } if (!user.Name.IsNullOrWhiteSpace()) { identity.AddIfNotContains(new Claim(AbpClaimTypes.Name, user.Name)); } if (!user.Surname.IsNullOrWhiteSpace()) { identity.AddIfNotContains(new Claim(AbpClaimTypes.SurName, user.Surname)); } if (!user.PhoneNumber.IsNullOrWhiteSpace()) { identity.AddIfNotContains(new Claim(AbpClaimTypes.PhoneNumber, user.PhoneNumber)); } identity.AddIfNotContains( new Claim(AbpClaimTypes.PhoneNumberVerified, user.PhoneNumberConfirmed.ToString())); if (!user.Email.IsNullOrWhiteSpace()) { identity.AddIfNotContains(new Claim(AbpClaimTypes.Email, user.Email)); } identity.AddIfNotContains(new Claim(AbpClaimTypes.EmailVerified, user.EmailConfirmed.ToString())); if (user.ExtraProperties.ContainsKey(AppUserConsts.UserTypePropertyName)) { var userType = user.ExtraProperties[AppUserConsts.UserTypePropertyName]?.ToString(); if (!string.IsNullOrEmpty(userType)) identity.AddIfNotContains(new Claim(AppUserConsts.UserTypePropertyName, userType)); } using (CurrentPrincipalAccessor.Change(identity)) { await AbpClaimsPrincipalFactory.CreateAsync(principal); } return principal; } } }
and configured at the domain module
PreConfigure<IdentityBuilder>(builder => { builder.AddClaimsPrincipalFactory<ExtendedUserClaimsPrincipalFactory>(); });
and the principal is filled correctly with claims values, but the phoneNumber at currentUser is still null and currentUser claims did not update with the values at the principal.
Please advise.
and what about this issue please? the claims are filled correctly at the principal but the currentUser still does not contain them.
-
0
hi
do you mean a generated access_token value or what?
a
access_token
value, liming.ma@volosoft.com -
0
and what about this issue please? the claims are filled correctly at the principal but the currentUser still does not contain them.
I can't get the reason by your code.
You can add an
IAbpClaimsPrincipalContributor
instead of override theAbpUserClaimsPrincipalFactory
https://docs.abp.io/en/abp/latest/Authorization#claims-principal-factory