如果我们需要对下游API进行认证以及鉴权服务的,则首先Ocelot 网关这里需要添加认证服务。这和我们给一个单独的API或者ASP.NET Core Mvc添加认证服务没有什么区别。
public void ConfigureServices(IServiceCollection services) { var authenticationProviderKey = "TestKey"; services.AddAuthentication() .AddJwtBearer(authenticationProviderKey, x => { }); }然后在ReRoutes的路由模板中的AuthenticationOptions进行配置,只需要我们的AuthenticationProviderKey一致即可。
"ReRoutes": [{ "DownstreamHostAndPorts": [ { "Host": "localhost", "Port": 51876, } ], "DownstreamPathTemplate": "http://www.likecs.com/", "UpstreamPathTemplate": "http://www.likecs.com/", "UpstreamHttpMethod": ["Post"], "ReRouteIsCaseSensitive": false, "DownstreamScheme": "http", "AuthenticationOptions": { "AuthenticationProviderKey": "TestKey", "AllowedScopes": [] } }]JWT Tokens
要让网关支持JWT 的认证其实和让API支持JWT Token的认证是一样的
public void ConfigureServices(IServiceCollection services) { var authenticationProviderKey = "TestKey"; services.AddAuthentication() .AddJwtBearer(authenticationProviderKey, x => { x.Authority = "test"; x.Audience = "test"; }); services.AddOcelot(); }Identity Server Bearer Tokens
添加Identity Server的认证也是一样
public void ConfigureServices(IServiceCollection services) { var authenticationProviderKey = "TestKey"; var options = o => { o.Authority = "https://whereyouridentityserverlives.com"; o.ApiName = "api"; o.SupportedTokens = SupportedTokens.Both; o.ApiSecret = "secret"; }; services.AddAuthentication() .AddIdentityServerAuthentication(authenticationProviderKey, options); services.AddOcelot(); }Allowed Scopes
这里的Scopes将从当前 token 中的 claims中来获取,我们的鉴权服务将依靠于它来实现 。当前路由的下游API需要某个权限时,我们需要在这里声明 。和oAuth2中的 scope意义一致。
鉴权我们通过认证中的AllowedScopes 拿到claims之后,如果要进行权限的鉴别需要添加以下配置
"RouteClaimsRequirement": { "UserType": "registered" }当前请求上下文的token中所带的claims如果没有 name=”UserType” 并且 value=”registered” 的话将无法访问下游服务。
请求头转化请求头转发分两种:转化之后传给下游和从下游接收转化之后传给客户端。在Ocelot的配置里面叫做Pre Downstream Request和Post Downstream Request。目前的转化只支持查找和替换。我们用到的配置主要是 UpstreamHeaderTransform 和 DownstreamHeaderTransform
Pre Downstream Request
"Test": "http://www.bbc.co.uk/, "比如我们将客户端传过来的Header中的 Test 值改为 之后再传给下游
"UpstreamHeaderTransform": { "Test": "http://www.bbc.co.uk/, " },Post Downstream Request
而我们同样可以将下游Header中的Test再转为 之后再转给客户端。
"DownstreamHeaderTransform": { "Test": "http://www.bbc.co.uk/, " },变量
在请求头转化这里Ocelot为我们提供了两个变量:BaseUrl和DownstreamBaseUrl。BaseUrl就是我们在GlobalConfiguration里面配置的BaseUrl,后者是下游服务的Url。这里用301跳转做一个示例如何使用这两个变量。
默认的301跳转,我们会返回一个Location的头,于是我们希望将 替换为 ,后者者网关对外的域名。
"DownstreamHeaderTransform": { "Location": "http://www.bbc.co.uk/, " }, "HttpHandlerOptions": { "AllowAutoRedirect": false, },我们通过DownstreamHeaderTranfrom将下游返回的请求头中的Location替换为了网关的域名,而不是下游服务的域名。所以在这里我们也可以使用BaseUrl来做为变量替换。
"DownstreamHeaderTransform": { "Location": "http://localhost:6773, {BaseUrl}" }, "HttpHandlerOptions": { "AllowAutoRedirect": false, },