微服务--API网关
API網關
- API網關
- 什么是API網關
- 什么是API
- 什么是網關
- 為什么要使用微服務網關
- 如何在項目中使用API網關
- API網關類型
- 如何在項目中使用Ocelot
- Ocelot是什么
- Ocelot內部概念
- 上游
- 下游
- 主要功能
- Ocelot文檔地址
- Ocelot如何使用
- Ocelot如何使用路由
- 一個路由完整配置
- 路由基本使用
- 路由負載均衡
- 路由Consul負載均衡
- 多個路由配置(多項目)
- 路由聚合請求
- 路由限流
- 路由服務質量與熔斷
- 路由緩存
- 路由認證(Identity Server4)
- 路由鑒權
- 路由請求頭轉化
API網關
概念------為什么------如何使用oclet-----內部概念(上游和下游)、路由-----ocelot內部運行原理-----如何做步驟-----ocelot配置文件介紹----路由基本使用----路由負載均衡------路由consul支持-----路由多個服務操作-----路由多個服務聚合----路由限流----路由熔斷----路由緩存----路由身份驗證。
什么是API網關
就是用來限制客戶端訪問服務端api一到門檻,在圖例中已經進行了展示
什么是API
API是Application Programming Interface縮寫,翻譯成中文就是應用程序接口。在實際微服務中可以理解一個個功能方法。就比如你一個用戶服務的微服務,可以對外提供 API 接口為,查找用戶,創建用戶等。
什么是網關
網關, wiki 上定義。
在計算機網絡中,網關(英語:Gateway)是轉發其他服務器通信數據的服務器,接收從客戶端發送來的請求時,它就像自己擁有資源的源服務器一樣對請求進行處理
為什么要使用微服務網關
大概有4四種情況
1、聚合微服務增多,導致客戶端不好維護
2、聚合微服務進行集群
? 2.1 增加和修改聚合微服務集群,都要修改客戶端,導致客戶端不穩定
? 2.2 服務集群,無法解決復雜均衡的問題
3、客戶端訪問多個聚合微服務
? 3.1 如果需要對客戶端身份驗證和授權,會導致每個服務都進行授權
? 3.2 如何客戶端訪問過大,無法限制客戶端流量,導致系統宕機
? 3.3 如果客戶端訪問微服務系統,每個微服務之間進行調用。會導致耗時操作很難統計。
? 3.4 如果客戶端訪問微服務系統,如何統計客戶端的調用日志
總結
1、路由
2、負載均衡
3、限流
4、認證
5、授權
6、鏈路監控
7、熔斷降級
8、Service Fabric
如何在項目中使用API網關
API網關類型
1、Netflix Zuul +java實現
2、Kong nginx +lua腳本實現
3、Tyk go語言開發,收費版本
4、Ocelot aspnetcore開發的
如何在項目中使用Ocelot
Ocelot是什么
簡單的來說Ocelot是一堆的asp.net core middleware組成的一個管道。當它拿到請求之后會用一個request builder來構造一個HttpRequestMessage發到下游的真實服務器,等下游的服務返回response之后再由一個middleware將它返回的HttpResponseMessage映射到HttpResponse上。
Ocelot內部概念
上游
? Ocelot為上游:Upstream
下游
? Ocelot下面映射的服務為下游:Downstream
主要功能
1、路由
? 1.1 接受客戶端請求
? 1.2 獎客戶端請求轉換成下游地址
? 1.3 調用下游服務,并返回結果
? 1.4 將下游服務返回的結果返回到前端
2、認證
3、授權
4、負載均衡
5、鏈路監控
6、限流
7、熔斷降級
8、請求聚合
9、Service Fabric
等其他功能
Ocelot文檔地址
中文文檔:http://www.jessetalk.cn/2018/03/19/net-core-apigateway-ocelot-docs/
英文文檔:https://ocelot.readthedocs.io/en/latest/introduction/gettingstarted.html
Ocelot如何使用
條件
1、aspnetcore3.1
2、Ocelot
3、團隊微服務
4、ocelot.json文件
步驟
1、創建一個空的aspnetcore3.1項目
2、通過nuget安裝Ocelot
3、創建Ocelot配置文件ocelot.json
{"ReRoutes": [],"GlobalConfiguration": {"BaseUrl": "https://api.mybusiness.com"} }要特別注意一下BaseUrl是我們外部暴露的Url,比如我們的Ocelot運行在http://123.111.1.1的一個地址上,但是前面有一個 nginx綁定了域名http://api.jessetalk.cn,那這里我們的BaseUrl就是 http://api.jessetalk.cn。
4、加載ocelot.json配置文件
public static IHostBuilder CreateHostBuilder(string[] args) =>Host.CreateDefaultBuilder(args).ConfigureWebHostDefaults(webBuilder =>{webBuilder.UseStartup<Startup>();webBuilder.ConfigureAppConfiguration((hostingContext, config) =>{// 1、加載ocelot配置文件config.AddJsonFile("ocelot.aggregate.json");});});5、配置Ocelot依賴注入并加載配置文件
public void ConfigureServices(IServiceCollection services) {services.AddOcelot() }6、配置Ocelot中間件
public void Configure(IApplicationBuilder app, IHostingEnvironment env) { if (env.IsDevelopment()) { app.UseDeveloperExceptionPage(); } app.UseOcelot().Wait(); }Ocelot如何使用路由
一個路由完整配置
{"DownstreamPathTemplate": "/","UpstreamPathTemplate": "/","UpstreamHttpMethod": ["Get"],"AddHeadersToRequest": {},"AddClaimsToRequest": {},"RouteClaimsRequirement": {},"AddQueriesToRequest": {},"RequestIdKey": "","FileCacheOptions": {"TtlSeconds": 0,"Region": ""},"ReRouteIsCaseSensitive": false,"ServiceName": "","DownstreamScheme": "http","DownstreamHostAndPorts": [{"Host": "localhost","Port": 51876,}],"QoSOptions": {"ExceptionsAllowedBeforeBreaking": 0,"DurationOfBreak": 0,"TimeoutValue": 0},"LoadBalancer": "","RateLimitOptions": {"ClientWhitelist": [],"EnableRateLimiting": false,"Period": "","PeriodTimespan": 0,"Limit": 0},"AuthenticationOptions": {"AuthenticationProviderKey": "","AllowedScopes": []},"HttpHandlerOptions": {"AllowAutoRedirect": true,"UseCookieContainer": true,"UseTracing": true},"UseServiceDiscovery": false }- Downstream是下游服務配置
- UpStream是上游服務配置
- Aggregates 服務聚合配置
- ServiceName, LoadBalancer, UseServiceDiscovery 配置服務發現
- AuthenticationOptions 配置服務認證
- RouteClaimsRequirement 配置Claims鑒權
- RateLimitOptions為限流配置
- FileCacheOptions 緩存配置
- QosOptions 服務質量與熔斷
- DownstreamHeaderTransform頭信息轉發
路由基本使用
{ "DownstreamPathTemplate": "/api/post/{postId}", "DownstreamScheme": "https", "DownstreamHostAndPorts": [ { "Host": "localhost", "Port": 80, } ], "UpstreamPathTemplate": "/post/{postId}", "UpstreamHttpMethod": [ "Get"] }- DownstreamPathTemplate:下游路徑模板
- DownstreamScheme:下游服務http schema
- DownstreamHostAndPorts:下游服務的地址,如果使用LoadBalancer的話這里可以填多項
- UpstreamPathTemplate: 上游也就是用戶輸入的請求Url模板
- UpstreamHttpMethod: 上游請求http方法,可使用數組
路由負載均衡
{"DownstreamPathTemplate": "/api/posts/{postId}","DownstreamScheme": "https","DownstreamHostAndPorts": [{"Host": "10.0.1.10","Port": 5000,},{"Host": "10.0.1.11","Port": 5000,}],"UpstreamPathTemplate": "/posts/{postId}","LoadBalancerOptions": {"Type": "LeastConnection"},"UpstreamHttpMethod": [ "Put", "Delete" ] }LoadBalancer將決定負載均衡的算法
- LeastConnection – 將請求發往最空閑的那個服務器
- RoundRobin – 輪流發送
- NoLoadBalance – 總是發往第一個請求或者是服務發現
路由Consul負載均衡
條件:
1、Ocelot.Provider.Consul
2、Consul
3、Ocelot
步驟
1、通過nuget下載Ocelot.Provider.Consul
2、添加consul依賴注入
public void ConfigureServices(IServiceCollection services){// 1、添加網關Ocelot到ioc容器services.AddOcelot().AddConsul();}3、路由consul配置
{"DownstreamPathTemplate": "/api/posts/{postId}","DownstreamScheme": "https","UpstreamPathTemplate": "/posts/{postId}","UpstreamHttpMethod": [ "Put" ],"ServiceName": "product","LoadBalancerOptions": {"Type": "LeastConnection"}, }多個路由配置(多項目)
條件
1、TeamService,MemberService
2、ocelot.team.json,ocelot.member.json
步驟
1、創建ocelot.team.json,ocelot.member.json文件
2、配置動態加載ocelot.json配置文件
webBuilder.ConfigureAppConfiguration((hostingContext, config) =>{config// .SetBasePath(hostingContext.HostingEnvironment.ContentRootPath)// .AddJsonFile("appsettings.json", true, true)// .AddJsonFile($"appsettings.{hostingContext.HostingEnvironment.EnvironmentName}.json", true, true).AddOcelot(hostingContext.HostingEnvironment);// .AddEnvironmentVariables();});會自動的加載配置文件,然后進行合并,主要用于大項目配置
3、ocelot依賴注入配置
public void ConfigureServices(IServiceCollection services){// 1、添加網關Ocelot到ioc容器services.AddOcelot();}路由聚合請求
{"ReRoutes": [{"DownstreamPathTemplate": "/","UpstreamPathTemplate": "/laura","UpstreamHttpMethod": ["Get"],"DownstreamScheme": "http","DownstreamHostAndPorts": [{"Host": "localhost","Port": 51881}],"Key": "Laura"},{"DownstreamPathTemplate": "/","UpstreamPathTemplate": "/tom","UpstreamHttpMethod": ["Get"],"DownstreamScheme": "http","DownstreamHostAndPorts": [{"Host": "localhost","Port": 51882}],"Key": "Tom"}],"Aggregates": [{"ReRouteKeys": ["Tom","Laura"],"UpstreamPathTemplate": "/"}] }當我們請求/的時候,會將/tom和/laura兩個結果合并到一個response返回
{"Tom":{"Age": 19},"Laura":{"Age": 25}}需要注意的是:
- 聚合服務目前只支持返回json
- 目前只支持Get方式請求下游服務
- 任何下游的response header并會被丟棄
- 如果下游服務返回404,聚合服務只是這個key的value為空,它不會返回404
有一些其它的功能會在將來實現
- 下游服務很慢的處理
- 做一些像 GraphQL的處理對下游服務返回結果進行處理
- 404的處理
路由限流
"RateLimitOptions": {"ClientWhitelist": [],"EnableRateLimiting": true,"Period": "5m","PeriodTimespan": 1,"Limit": 1 }-
ClientWihteList 白名單
-
EnableRateLimiting 是否啟用限流
-
Period 統計時間段:1s, 5m, 1h, 1d
-
PeroidTimeSpan 多少秒之后客戶端可以重試
-
Limit 在統計時間段內允許的最大請求數量
在 GlobalConfiguration下我們還可以進行以下配置
- Http頭 X-Rate-Limit 和 Retry-After 是否禁用
- QuotaExceedMessage 當請求過載被截斷時返回的消息
- HttpStatusCode 當請求過載被截斷時返回的http status
- ClientIdHeader 用來識別客戶端的請求頭,默認是 ClientId
路由服務質量與熔斷
條件
1、Ocelot.Provider.Polly
步驟
1、在ocelot上添加熔斷
public void ConfigureServices(IServiceCollection services){// 1、添加網關Ocelot到ioc容器services.AddOcelot(new ConfigurationBuilder().AddJsonFile("ocelot.aggregate.json").Build()).AddConsul().AddPolly();}2、添加熔斷配置
熔斷的意思是停止將請求轉發到下游服務。當下游服務已經出現故障的時候再請求也是功而返,并且增加下游服務器和API網關的負擔。這個功能是用的Pollly來實現的,我們只需要為路由做一些簡單配置即可
"QoSOptions": {"ExceptionsAllowedBeforeBreaking":3,"DurationOfBreak":5,"TimeoutValue":5000 }- ExceptionsAllowedBeforeBreaking 允許多少個異常請求
- DurationOfBreak 熔斷的時間,單位為秒
- TimeoutValue 如果下游請求的處理時間超過多少則自動將請求設置為超時
路由緩存
Ocelot可以對下游請求結果進行緩存 ,目前緩存的功能還不是很強大。它主要是依賴于CacheManager 來實現的,我們只需要在路由下添加以下配置即可
"FileCacheOptions": { "TtlSeconds": 15, "Region": "somename" }Region是對緩存進行的一個分區,我們可以調用Ocelot的 administration API來移除某個區下面的緩存 。
路由認證(Identity Server4)
條件
1、
2、
3、
步驟
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/, http://ocelot.com/"比如我們將客戶端傳過來的Header中的 Test 值改為 http://ocelot.com/之后再傳給下游
"UpstreamHeaderTransform": {"Test": "http://www.bbc.co.uk/, http://ocelot.com/" },Post Downstream Request
而我們同樣可以將下游Header中的Test再轉為 http://www.bbc.co.uk/之后再轉給客戶端。
"DownstreamHeaderTransform": {"Test": "http://www.bbc.co.uk/, http://ocelot.com/" },總結
以上是生活随笔為你收集整理的微服务--API网关的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: java日期 13,如何将此格式的日期(
- 下一篇: flutter友盟分享_flutter友