如何使用 Keycloak 和 jwt 令牌对 ASP.NET Framework Web API 进行身份验证?

问题描述 投票:0回答:1

当我在互联网上搜索 .NET 的 Keycloak 身份验证时,我得到了数百个 .NET Core Web API 的示例,但对于 .NET Framework Web API,我还没有获得完整的文章。我希望为 .net Framework Web API 实现客户端凭据授予,因为它是程序到程序的通信,无需用户参与。我是 OAuth、OpenID Connect 和 OWin 的新手。我正在寻找详细的分步指导。您能给我提供一个或给我指出一些好的链接吗? Keycloak 是我们公司选择的 OAuth 服务器,必须使用 Keycloak 来满足所有身份验证需求。

我为我的项目创建了一个 Owin Startup 类并添加了以下配置:

       app.UseJwtBearerAuthentication(
       new JwtBearerAuthenticationOptions
       {
             AuthenticationMode = AuthenticationMode.Active,
             Realm = "https://staging.com/auth/realms/drugdev",
             TokenValidationParameters = new TokenValidationParameters()
             {
                   ValidateIssuer = true,
                   ValidateAudience = true,
                   ValidateIssuerSigningKey = true,
                   ValidIssuer = "https://staging.com/auth/realms/drugdev", //some string,  
                   ValidAudience = "irt-api",
       
              }
           });

当我尝试调用任何用 [Authorize] 属性修饰的 Web API 时,我总是收到 HTTP 401 响应。

asp.net keycloak
1个回答
0
投票

我找到了一种无需在中间件中处理它的方法。

我们可以在项目中创建一个KeycloakAuthentication.cs文件,如下所示

KeycloakAuthentication.cs 使用系统;使用 System.Collections.Generic;使用系统配置;使用 System.Linq;使用 System.Security.Claims;使用系统.Web;使用系统;使用 System.IdentityModel.Tokens.Jwt;使用 System.Security.Claims;使用 Microsoft.IdentityModel.Tokens;使用 System.Security.Cryptography;使用 Org.BouncyCastle.Crypto.Parameters;使用 Org.BouncyCastle.OpenSsl;命名空间 Namespace.API.Common { 公共类 KeycloakAuthentication { 私有静态只读字符串颁发者 = ConfigurationManager.AppSettings["颁发者"];私有静态只读字符串受众 = ConfigurationManager.AppSettings["audience"]; //私有静态只读字符串secretKey = ConfigurationManager.AppSettings["secret"]; // 如果需要,您可能需要从 Keycloak 获取密钥。私有静态只读字符串secretKey = @“-----开始公钥-----”+ConfigurationManager.AppSettings[“秘密”]+“-----结束公钥-----”; public static ClaimsPrincipal ValidateToken(string token) { var validationParameters = new TokenValidationParameters { ValidateIssuer = true, ValidIssuer = Issuer, // 您的 Keycloak 领域 URL ValidateAudience = true, ValidAudiences = new[] { "realm-management", "broker", " account", Audience }, // 列出所有有效受众 ValidateIssuerSigningKey = false, IssuerSigningKey = GetRsaSecurityKeyFromKeycloakPublicKey(secretKey), ValidateLifetime = true, ClockSkew = TimeSpan.Zero }; var handler = new JwtSecurityTokenHandler();尝试 { SecurityToken validToken;返回处理程序.ValidateToken(令牌,validationParameters,out validatedToken); } catch (Exception ex) { // 处理令牌验证错误 Console.WriteLine(ex.Message);返回空值; } } 公共静态 RsaSecurityKey GetRsaSecurityKeyFromKeycloakPublicKey(string publicKey) { 尝试 { var rsaKeyParameters = (RsaKeyParameters)new PemReader(new System.IO.StringReader(publicKey)).ReadObject(); var rsaParameters = new RSAParameters { Modulus = rsaKeyParameters.Modulus.ToByteArrayUnsigned(), Exponent = rsaKeyParameters.Exponent.ToByteArrayUnsigned() }; var rsa = new RSACryptoServiceProvider(); rsa.ImportParameters(rsaParameters);返回新的 RsaSecurityKey(rsa); } catch (Exception ex) { Console.WriteLine($"创建 RSA 密钥时发生错误:{ex.Message}");扔; } } } }

之后您可以在控制器方法中添加代码,如下所示

[System.Web.Http.HttpGet] [System.Web.Http.Route("api/values/apiname/{param}")] 公共异步任务 apiname(string param){ try { bool IsOkForResponse = true;字符串标记=“”; if (ConfigurationManager.AppSettings["ISKEYCLOAKENABLED"] == "true") { HttpRequestMessage request1 = this.Request; token = request1.Headers.GetValues("授权").FirstOrDefault().Split(' ')[1]; var 主体 = KeycloakAuthentication.ValidateToken(token); IsOkForResponse = (主体!= null && 主体.Identity.IsAuthenticated) ?真假; } 如果 (IsOkForResponse) { //你的api功能。 }else{ 返回 Unauthorized() } }catch{ 返回 Unauthorized() }

如果您的访问令牌无效,则会导致您未经授权。 请根据配置在 web.config 文件中正确设置所有内容。

© www.soinside.com 2019 - 2024. All rights reserved.