关于Claims Transformation的问题

发布时间 2023-03-25 15:08:57作者: 追夢

原文关于Claims Transformation 看的有点不明白的,可以参考这篇文章的翻译:https://www.cnblogs.com/irocker/p/Ocelot-claimstransformation.html

这里主要记录一下我遇到的过的一个坑。

 我的项目的结构如上图所示。前端调用网关,网关调用admin服务的登录接口获取token,然后调用demo服务,demo怎么获取登录后的用户ID呢?

看官网的Claims Transformation这章,有三种方式:

1、AddClaimsToRequest
2、AddHeadersToRequest
3、AddQueriesToRequest
2和3这种方式比较简单,只要在ocelot配置中配置好。第一种方式有点坑,是需要在代码处理的,开始以为也只要在ocelot.json中配置就好了。
下面说说第一种方式,
第一步:看官网说需要在ocelot.json配置添加如下图选中的配置,其实并不需要,因为他是通过第二步解析token获取sid,然后赋值给claim。有知道直接配置ocelot.json就可以在demo服务中的claim获取sid,还请赐教。

 下图是创建token时,关于Claim的部分:

第二步:在demo服务中的main方法中添加如下代码:

 builder.Services.AddAuthentication(x =>
 {
                x.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme;
                x.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme;
            }).AddJwtBearer(x =>
            {
                x.RequireHttpsMetadata = false;
                x.SaveToken = true;
                x.TokenValidationParameters = CreateTokenValidationParameters();
            });
  private static TokenValidationParameters CreateTokenValidationParameters() //we ignore token validation because gateway validates it
        {
            //参考文章:https://github.com/ThreeMammals/Ocelot/issues/396#issuecomment-579719589
            var result = new TokenValidationParameters
            {
                ValidateIssuer = false,
                ValidateAudience = false,
                ValidateIssuerSigningKey = false,
                SignatureValidator = delegate (string token, TokenValidationParameters parameters)
                {
                    var jwt = new JwtSecurityToken(token);
                    return jwt;
                },
                RequireExpirationTime = true,
                ValidateLifetime = true,
                ClockSkew = TimeSpan.Zero,
                RequireSignedTokens = false
            };
            return result;
        }

第三步:在就可以在demo服务中通过claim获取到用户ID

 

 第一种方式到此结束。接下说说第二种方式:

第一步:在ocelot.json添加如下配置:

 

 然后我们就可以demo服务中controller的action中看到sid的值。不需要第一种方式中的第二步和第三步的代码。

 

 第二种方式是不是特别简单,推荐使用这种方式,不过不推荐在公网上公开这个服务。第三种方式,就不啰嗦了。