小黑在哪里资料

本文主要介绍小黑在哪里资料 方法和在新技术下所面对的“挑战”,方便大家深入理解小黑在哪里资料 过程。本文也将分享小黑在哪里资料 所遇到的问题和应对策略,怎么解决怎么做的问题。
通过深入本文可以理解代码原理,进行代码文档的下载,也可以查看相应 Demo 部署效果。

前言

上一篇【.Net Core微服务入门全纪录(六)——EventBus-事件总线】中使用CAP完成了一个简单的Eventbus,实现了服务之间的解耦和异步调用,并且做到数据的最终一致性。这一篇将使用IdentityServer4来搭建一个鉴权中心,来完成授权认证相关的功能。

IdentityServer4官方文档:https://identityserver4.readthedocs.io/

鉴权中心

创建ids4项目

关于IdentityServer4的基本介绍和模板安装可以看一下我的另一篇博客【IdentityServer4 4.x版本 配置Scope的正确姿势】,下面直接从创建项目开始。

来到我的项目目录下执行:dotnet new is4inmem --name IDS4.AuthCenter

小黑在哪里

执行完成后会生成以下文件:

小黑在哪里

用vs2019打开之前的解决方案,把刚刚创建的ids项目添加进来:

小黑在哪里

将此项目设为启动项,先运行看一下效果:

小黑在哪里

小黑在哪里

项目正常运行,下面需要结合我们的业务稍微修改一下默认代码。

鉴权中心配置

修改Startup的ConfigureServices方法:

// in-memory, code config builder.AddInMemoryIdentityResources(Config.IdentityResources); builder.AddInMemoryApiScopes(Config.ApiScopes); builder.AddInMemoryApiResources(Config.ApiResources); builder.AddInMemoryClients(Config.Clients); 

Config类:

public static class Config {     public static IEnumerable<IdentityResource> IdentityResources =>         new IdentityResource[]         {             new IdentityResources.OpenId(),             new IdentityResources.Profile(),         };      public static IEnumerable<ApiResource> ApiResources =>         new ApiResource[]         {             new ApiResource("orderApi","订单服务")             {                 ApiSecrets ={ new Secret("orderApi secret".Sha256()) },                 Scopes = { "orderApiScope" }             },             new ApiResource("productApi","产品服务")             {                 ApiSecrets ={ new Secret("productApi secret".Sha256()) },                 Scopes = { "productApiScope" }             }         };      public static IEnumerable<ApiScope> ApiScopes =>         new ApiScope[]         {             new ApiScope("orderApiScope"),             new ApiScope("productApiScope"),         };      public static IEnumerable<Client> Clients =>         new Client[]         {             new Client             {                 ClientId = "web client",                 ClientName = "Web Client",                  AllowedGrantTypes = GrantTypes.Code,                 ClientSecrets = { new Secret("web client secret".Sha256()) },                  RedirectUris = { "http://localhost:5000/signin-oidc" },                 FrontChannelLogoutUri = "http://localhost:5000/signout-oidc",                 PostLogoutRedirectUris = { "http://localhost:5000/signout-callback-oidc" },                  AllowedScopes = new [] {                     IdentityServerConstants.StandardScopes.OpenId,                     IdentityServerConstants.StandardScopes.Profile,                     "orderApiScope", "productApiScope"                 },                 AllowAccessTokensViaBrowser = true,                  RequireConsent = true,//是否显示同意界面                 AllowRememberConsent = false,//是否记住同意选项             }         }; } 

Config中定义了2个api资源:orderApi,productApi。2个Scope:orderApiScope,productApiScope。1个客户端:web client,使用Code授权码模式,拥有openid,profile,orderApiScope,productApiScope 4个scope。

TestUsers类:

public class TestUsers {     public static List<TestUser> Users     {         get         {             var address = new             {                 street_address = "One Hacker Way",                 locality = "Heidelberg",                 postal_code = 69118,                 country = "Germany"             };                          return new List<TestUser>             {                 new TestUser                 {                     SubjectId = "818727",                     Username = "alice",                     Password = "alice",                     Claims =                     {                         new Claim(JwtClaimTypes.Name, "Alice Smith"),                         new Claim(JwtClaimTypes.GivenName, "Alice"),                         new Claim(JwtClaimTypes.FamilyName, "Smith"),                         new Claim(JwtClaimTypes.Email, "AliceSmith@email.com"),                         new Claim(JwtClaimTypes.EmailVerified, "true", ClaimValueTypes.Boolean),                         new Claim(JwtClaimTypes.WebSite, "http://alice.com"),                         new Claim(JwtClaimTypes.Address, JsonSerializer.Serialize(address), IdentityServerConstants.ClaimValueTypes.Json)                     }                 },                 new TestUser                 {                     SubjectId = "88421113",                     Username = "bob",                     Password = "bob",                     Claims =                     {                         new Claim(JwtClaimTypes.Name, "Bob Smith"),                         new Claim(JwtClaimTypes.GivenName, "Bob"),                         new Claim(JwtClaimTypes.FamilyName, "Smith"),                         new Claim(JwtClaimTypes.Email, "BobSmith@email.com"),                         new Claim(JwtClaimTypes.EmailVerified, "true", ClaimValueTypes.Boolean),                         new Claim(JwtClaimTypes.WebSite, "http://bob.com"),                         new Claim(JwtClaimTypes.Address, JsonSerializer.Serialize(address), IdentityServerConstants.ClaimValueTypes.Json)                     }                 }             };         }     } } 

TestUsers没有做修改,用项目模板默认生成的就行。这里定义了2个用户alice,bob,密码与用户名相同。

至此,鉴权中心的代码修改就差不多了。这个项目也不放docker了,直接用vs来启动,让他运行在9080端口。/Properties/launchSettings.json修改一下:"applicationUrl": "http://localhost:9080"

Ocelot集成ids4

Ocelot保护api资源

鉴权中心搭建完成,下面整合到之前的Ocelot.APIGateway网关项目中。

首先NuGet安装IdentityServer4.AccessTokenValidation

小黑在哪里

修改Startup:

public void ConfigureServices(IServiceCollection services) {     services.AddAuthentication(IdentityServerAuthenticationDefaults.AuthenticationScheme)         .AddIdentityServerAuthentication("orderService", options =>         {             options.Authority = "http://localhost:9080";//鉴权中心地址             options.ApiName = "orderApi";             options.SupportedTokens = SupportedTokens.Both;             options.ApiSecret = "orderApi secret";             options.RequireHttpsMetadata = false;         })         .AddIdentityServerAuthentication("productService", options =>         {             options.Authority = "http://localhost:9080";//鉴权中心地址             options.ApiName = "productApi";             options.SupportedTokens = SupportedTokens.Both;             options.ApiSecret = "productApi secret";             options.RequireHttpsMetadata = false;         });      //添加ocelot服务     services.AddOcelot()         //添加consul支持         .AddConsul()         //添加缓存         .AddCacheManager(x =>         {             x.WithDictionaryHandle();         })         //添加Polly         .AddPolly(); } 

修改ocelot.json配置文件:

{   "DownstreamPathTemplate": "/products",   "DownstreamScheme": "http",   "UpstreamPathTemplate": "/products",   "UpstreamHttpMethod": [ "Get" ],   "ServiceName": "ProductService",   ......   "AuthenticationOptions": {     "AuthenticationProviderKey": "productService",     "AllowScopes": []   } }, {   "DownstreamPathTemplate": "/orders",   "DownstreamScheme": "http",   "UpstreamPathTemplate": "/orders",   "UpstreamHttpMethod": [ "Get" ],   "ServiceName": "OrderService",   ......   "AuthenticationOptions": {     "AuthenticationProviderKey": "orderService",     "AllowScopes": []   } } 

添加了AuthenticationOptions节点,AuthenticationProviderKey对应的是上面Startup中的定义。

Ocelot代理ids4

既然网关是客户端访问api的统一入口,那么同样可以作为鉴权中心的入口。使用Ocelot来做代理,这样客户端也无需知道鉴权中心的地址,同样修改ocelot.json:

{   "DownstreamPathTemplate": "/{url}",   "DownstreamScheme": "http",   "DownstreamHostAndPorts": [     {       "Host": "localhost",       "Port": 9080     }   ],   "UpstreamPathTemplate": "/auth/{url}",   "UpstreamHttpMethod": [     "Get",     "Post"   ],   "LoadBalancerOptions": {     "Type": "RoundRobin"   } } 

添加一个鉴权中心的路由,实际中鉴权中心也可以部署多个实例,也可以集成Consul服务发现,实现方式跟前面章节讲的差不多,这里就不再赘述。

让网关服务运行在9070端口,/Properties/launchSettings.json修改一下:"applicationUrl": "http://localhost:9070"

客户端集成

首先NuGet安装Microsoft.AspNetCore.Authentication.OpenIdConnect

小黑在哪里

修改Startup:

public void ConfigureServices(IServiceCollection services) {     services.AddAuthentication(options =>         {             options.DefaultScheme = "Cookies";             options.DefaultChallengeScheme = "oidc";         })         .AddCookie("Cookies")         .AddOpenIdConnect("oidc", options =>         {             options.Authority = "http://localhost:9070/auth";//通过网关访问鉴权中心             //options.Authority = "http://localhost:9080";              options.ClientId = "web client";             options.ClientSecret = "web client secret";             options.ResponseType = "code";              options.RequireHttpsMetadata = false;              options.SaveTokens = true;              options.Scope.Add("orderApiScope");             options.Scope.Add("productApiScope");         });      services.AddControllersWithViews();          //注入IServiceHelper     //services.AddSingleton<IServiceHelper, ServiceHelper>();          //注入IServiceHelper     services.AddSingleton<IServiceHelper, GatewayServiceHelper>(); }  // This method gets called by the runtime. Use this method to configure the HTTP request pipeline. public void Configure(IApplicationBuilder app, IWebHostEnvironment env, IServiceHelper serviceHelper) {     if (env.IsDevelopment())     {         app.UseDeveloperExceptionPage();     }     else     {         app.UseExceptionHandler("/Home/Error");     }     app.UseStaticFiles();      app.UseRouting();      app.UseAuthentication();      app.UseAuthorization();      app.UseEndpoints(endpoints =>     {         endpoints.MapControllerRoute(             name: "default",             pattern: "{controller=Home}/{action=Index}/{id?}");     });      //程序启动时 获取服务列表     //serviceHelper.GetServices(); } 

修改/Helper/IServiceHelper,方法定义增加accessToken参数:

/// <summary> /// 获取产品数据 /// </summary> /// <param name="accessToken"></param> /// <returns></returns> Task<string> GetProduct(string accessToken);  /// <summary> /// 获取订单数据 /// </summary> /// <param name="accessToken"></param> /// <returns></returns> Task<string> GetOrder(string accessToken); 

修改/Helper/GatewayServiceHelper,访问接口时增加Authorization参数,传入accessToken:

public async Task<string> GetOrder(string accessToken) {     var Client = new RestClient("http://localhost:9070");     var request = new RestRequest("/orders", Method.GET);     request.AddHeader("Authorization", "Bearer " + accessToken);      var response = await Client.ExecuteAsync(request);     if (response.StatusCode != HttpStatusCode.OK)     {         return response.StatusCode + " " + response.Content;     }     return response.Content; }  public async Task<string> GetProduct(string accessToken) {     var Client = new RestClient("http://localhost:9070");     var request = new RestRequest("/products", Method.GET);     request.AddHeader("Authorization", "Bearer " + accessToken);      var response = await Client.ExecuteAsync(request);     if (response.StatusCode != HttpStatusCode.OK)     {         return response.StatusCode + " " + response.Content;     }     return response.Content; } 

最后是/Controllers/HomeController的修改。添加Authorize标记:

[Authorize] public class HomeController : Controller 

修改Index action,获取accessToken并传入:

public async Task<IActionResult> Index() {     var accessToken = await HttpContext.GetTokenAsync("access_token");      ViewBag.OrderData = await _serviceHelper.GetOrder(accessToken);     ViewBag.ProductData = await _serviceHelper.GetProduct(accessToken);      return View(); } 

至此,客户端集成也已完成。

测试

为了方便,鉴权中心、网关、web客户端这3个项目都使用vs来启动,他们的端口分别是9080,9070,5000。之前的OrderAPI和ProductAPI还是在docker中不变。

为了让vs能同时启动多个项目,需要设置一下,解决方案右键属性:

小黑在哪里

Ctor+F5启动项目。

3个项目都启动完成后,浏览器访问web客户端:http://localhost:5000/

小黑在哪里

因为我还没登录,所以请求直接被重定向到了鉴权中心的登录界面。使用alice/alice这个账户登录系统。

小黑在哪里

登录成功后,进入授权同意界面,你可以同意或者拒绝,还可以选择勾选scope权限。点击Yes,Allow按钮同意授权:

小黑在哪里

同意授权后,就能正常访问客户端界面了。下面测试一下部分授权,这里没做登出功能,只能手动清理一下浏览器Cookie,ids4登出功能也很简单,可以自行百度。

小黑在哪里

清除Cookie后,刷新页面又会转到ids4的登录界面,这次使用bob/bob登录:

小黑在哪里

这次只勾选orderApiScope,点击Yes,Allow:

小黑在哪里

这次客户端就只能访问订单服务了。当然也可以在鉴权中心去限制客户端的api权限,也可以在网关层面ocelot.json中限制,相信你已经知道该怎么做了。

总结

本文主要完成了IdentityServer4鉴权中心、Ocelot网关、web客户端之间的整合,实现了系统的统一授权认证。授权认证是几乎每个系统必备的功能,而IdentityServer4是.Net Core下优秀的授权认证方案。再次推荐一下B站@solenovex 杨老师的视频,地址:https://www.bilibili.com/video/BV16b411k7yM ,虽然视频有点老了,但还是非常受用。

需要代码的点这里:https://github.com/xiajingren/NetCoreMicroserviceDemo

小黑在哪里资料部分资料来自网络,侵权毕设源码联系删除

区块链毕设网(www.qklbishe.com)全网最靠谱的原创区块链毕设代做网站
部分资料来自网络,侵权联系删除!
资源收费仅为搬运整理打赏费用,用户自愿支付 !
qklbishe.com区块链毕设代做网专注|以太坊fabric-计算机|java|毕业设计|代做平台 » 小黑在哪里资料

提供最优质的资源集合

立即查看 了解详情