Identity Server 6 : The Problem is How to API Authorize in Asp.net(.Net Framework 4.8)?

258 views Asked by At

I did try this method in API Startup below And Show me the Error When I Call API through the Web MVC Project. The Error is "Response status code does not indicate success: 401 (Unauthorized)."

        app.UseJwtBearerAuthentication(new JwtBearerAuthenticationOptions
        {

            AuthenticationType = "jwt",
            AuthenticationMode = Microsoft.Owin.Security.AuthenticationMode.Active,
            TokenValidationParameters = new TokenValidationParameters
            {

                ValidIssuer = Urls.IdentityServer,
                ValidateIssuer = true,

                ValidAudience = Urls.IdentityServer + "/resources", 
                ValidateAudience = true,

                ValidateIssuerSigningKey = true,

                ValidateLifetime = true,
                IssuerSigningKeyResolver = LoadKeys,
                NameClaimType = "name",
                RoleClaimType = "role",
            },
        });

My Keyset method in Web API Startup.

internal static DiscoveryCache _discoveryCache = new DiscoveryCache(Urls.IdentityServer);

    private IEnumerable<SecurityKey> LoadKeys(string token, SecurityToken securityToken, string kid, TokenValidationParameters validationParameters)
    {
       
        var disco = _discoveryCache.GetAsync().Result;

        var keys = disco.KeySet.Keys
            .Where(x => x.N != null && x.E != null)
            .Select(x =>
            {
                var rsa = new RSAParameters
                {
                    Exponent = Base64UrlEncoder.DecodeBytes(x.E),
                    Modulus = Base64UrlEncoder.DecodeBytes(x.N),
                };

                return new RsaSecurityKey(rsa)
                {
                    KeyId = x.Kid
                };
            });

        
        return keys;
    }

policies/rules method in web identityserver. this is my " public Task GetProfileDataAsync(ProfileDataRequestContext context)" method.

    {
        var UserName = "";
      

        foreach (var data in context.Subject.Identities)
        {
            UserName = data.Name;
          
        }
        var Roless = _loginValidationService.RoleAsync(UserName).Result;

        List<Claim> customClaims = new List<Claim>();

        foreach (var item in Roless)
        {
            var role = new Claim("role", item.Name);
            customClaims.Add(role);
        }

        var RoleClaim = _loginValidationService.ClaimAsync(Roless).Result;

        foreach (var claim in RoleClaim)
        {
            var Roleclaim = new Claim( claim.ClaimType, claim.ClaimValue) ;
            customClaims.Add(Roleclaim);
        }

        var getuser = _applicationDbContext.Users.Where(x => x.UserName.Equals(UserName)).ToList();

        foreach (var user in getuser)
        {
            var Userclaims = _applicationDbContext.UserClaims.Where(x => x.UserId.Equals(user.Id)).ToList();
            foreach (var Claim in Userclaims)
            {
                var role = new Claim(Claim.ClaimType, Claim.ClaimValue);
                customClaims.Add(role);
            }
        }
        

        context.IssuedClaims.AddRange(customClaims);
        return Task.CompletedTask;
    }` 







   
1

There are 1 answers

0
Om Makwana On BEST ANSWER

Ok, i have an answer to this question. KeySet is null in my Web API startup. I did include one method for this solution. and I solved my problem with this method. The method is...

{
public class OpenIdConnectSigningKeyResolver
{
    private readonly OpenIdConnectConfiguration openIdConfig;

    public OpenIdConnectSigningKeyResolver(string authority)
    {
        var cm = new ConfigurationManager<OpenIdConnectConfiguration>($"{authority.TrimEnd('/')}/.well-known/openid-configuration", new OpenIdConnectConfigurationRetriever());
        openIdConfig = AsyncHelper.RunSync(async () => await cm.GetConfigurationAsync());
    }

    public SecurityKey[] GetSigningKey(string kid)
    {
        return new[] { openIdConfig.JsonWebKeySet.GetSigningKeys().FirstOrDefault(t => t.KeyId == kid) };
    }
}

}

And my Web API Startup is...

public class Startup
{
    public void Configuration(IAppBuilder app)
    {
        var Domain = Urls.IdentityServer;
        var KeyResolver = new OpenIdConnectSigningKeyResolver(Domain);

        app.UseJwtBearerAuthentication(new JwtBearerAuthenticationOptions
        {
            AuthenticationType = "jwt",
            AuthenticationMode = AuthenticationMode.Active,
            TokenValidationParameters = new TokenValidationParameters
            {
                ValidIssuer = Domain,
                ValidAudience = "APICore",
                IssuerSigningKeyResolver = (token, securityToken, kid, parameters) => KeyResolver.GetSigningKey(kid)
            }
        });

        HttpConfiguration config = new HttpConfiguration();
        config.Routes.MapHttpRoute(
        name: "DefaultApi",
        routeTemplate: "{controller}/{id}",
            defaults: new { id = RouteParameter.Optional });
        app.UseWebApi(config);
    }
}