1. 程式人生 > 實用技巧 >Ocelot和Consul 實現閘道器API 服務註冊 負載均衡

Ocelot和Consul 實現閘道器API 服務註冊 負載均衡

Ocelot和Consul 實現閘道器API 服務註冊 負載均衡

Ocelot是一個用.NET Core實現並且開源的API閘道器,它功能強大,包括了:路由、請求聚合、服務發現、認證、鑑權、限流熔斷、並內建了負載均衡器與Service Fabric、Butterfly Tracing整合。這些功能只都只需要簡單的配置即可完成

Consul服務發現

在Ocelot已經支援簡單的負載功能,也就是當下遊服務存在多個結點的時候,Ocelot能夠承擔起負載均衡的作用。但是它不提供健康檢查,服務的註冊也只能通過手動在配置檔案裡面新增完成。這不夠靈活並且在一定程度下會有風險。這個時候我們就可以用Consul來做服務發現,它能與Ocelot完美結合。

Consul是什麼

Consul是一個服務網格(微服務間的 TCP/IP,負責服務之間的網路呼叫、限流、熔斷和監控)解決方案,它是一個一個分散式的,高度可用的系統,而且開發使用都很簡便。它提供了一個功能齊全的控制平面,主要特點是:服務發現、健康檢查、鍵值儲存、安全服務通訊、多資料中心。

安裝Consul:windos環境

https://www.consul.io/downloads.html 下載檔案

放到D盤下

開啟powershell 執行 命令啟動一個Agent的開發模式:

啟動完成:開啟localhost:8500 預設埠8500 就可以看到一個視覺化consul介面了,可以看到預設啟動了一個consul 服務

下面,使用netcore通過Ocelot搭建API閘道器 服務註冊 負載均衡

新建一個api1:nuget 新增一個consul 依賴

startup 新增程式碼

public void Configure(IApplicationBuilder app, IHostingEnvironment env, IApplicationLifetime lifetime)
       {
           if (env.IsDevelopment())
           {
               app.UseDeveloperExceptionPage();
           }
 
 
           
//註冊專案啟動的方法 lifetime.ApplicationStarted.Register(OnStart); //註冊專案關閉的方法 lifetime.ApplicationStarted.Register(OnStopped); app.UseMvc(); } //關閉的時候在consul中移除 private void OnStopped() { var client = new ConsulClient(); //根據ID在consul中移除當前服務 client.Agent.ServiceDeregister("servicename:93"); } private void OnStart() { var client = new ConsulClient(); //健康檢查 var httpCheck = new AgentServiceCheck() { //服務出錯一分鐘後 會自動移除 DeregisterCriticalServiceAfter = TimeSpan.FromMinutes(1), //每10秒傳送一次請求到 下面的這個地址 這個地址就是當前API資源的地址 Interval = TimeSpan.FromSeconds(10), HTTP = $"http://localhost:93/HealthCheck" }; var agentReg = new AgentServiceRegistration() { //這臺資源服務的唯一ID ID = "servicename:93", Check = httpCheck, Address = "localhsot", Name = "servicename", Port = 93 }; client.Agent.ServiceRegister(agentReg).ConfigureAwait(false); }

新增一個健康檢查介面

[Route("HealthCheck")]
   [ApiController]
   public class HealthCheckController : ControllerBase
   {
       // GET: api/HealthCheck
       [HttpGet]
       [HttpHead]
       public IActionResult Ping()
       {
           return Ok();
       }
 
   }

 修改ValuesController

[Route("api/[controller]")]
   [ApiController]
   public class ValuesController : ControllerBase
   {
       // GET api/values
       [HttpGet]
       public string Get()
       {
           return "這是1資源伺服器API";
       }
   }

然後 copy 一份api1 為api2,,我們啟用埠為92 ,細節........

新增專案Api.Gateway(Ocelot閘道器伺服器)新增Ocelot包 新增Ocelot.Json配置 Ocelot伺服器埠為91

Ocelot,Json

{
  "ReRoutes": [
    {
      //暴露出去的地址
      "UpstreamPathTemplate": "/api/{controller}",
      "UpstreamHttpMethod": [ "Get" ],
 
      //轉發到下面這個地址
      "DownstreamPathTemplate": "/api/{controller}",
      "DownstreamScheme": "http",
      //資源伺服器列表
      "DownstreamHostAndPorts": [
        {
          "host": "localhost",
          "port": 92
        },
        {
          "host": "localhost",
          "port": 93
        }
      ],
      //決定負載均衡的演算法
      "LoadBalancerOptions": {
        "Type": "LeastConnection"
      },
      "UseServiceDiscovery": true
    }
  ],
  //對外暴露的訪問地址  也就是Ocelot所在的伺服器地址
  "GlobalConfiguration": {
    "BaseUrl": "http://localhost:91"
  }
}

Startup 修改

public void ConfigureServices(IServiceCollection services)
  {
 
 
      services.AddOcelot();
      services.AddMvc().SetCompatibilityVersion(CompatibilityVersion.Version_2_2);
  }
 
  // This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
  public void Configure(IApplicationBuilder app, IHostingEnvironment env)
  {
      if (env.IsDevelopment())
      {
          app.UseDeveloperExceptionPage();
      }
      app.UseOcelot().Wait();
      app.UseMvc();
  }

Program 修改

public class Program
   {
       public static void Main(string[] args)
       {
           CreateWebHostBuilder(args).Build().Run();
       }
 
       public static IWebHostBuilder CreateWebHostBuilder(string[] args) =>
           WebHost.CreateDefaultBuilder(args)
                     .ConfigureAppConfiguration((hostingContext, builder) =>
                     {
                         builder
                         .SetBasePath(hostingContext.HostingEnvironment.ContentRootPath)
                         .AddJsonFile("Ocelot.json");
                     })
             .UseUrls("http://+:91")
             .UseStartup<Startup>();
   }

啟動 api3 和api2

再啟動Api.Gateway

執行 http://localhost:91/api/values

再執行

我們這裡負載均衡演算法是:LeastConnection

當然還可以選擇其他的:

  • RoundRobin - 輪詢,挨著來
  • LeastConnection - 最小連線數,誰的任務最少誰來
  • NoLoadBalance - 不要負載均衡

如果api1 我們關掉 ,那麼就只會請求到api2 ,api1的服務自動斷開