[转载]Ocelot简易教程(四)之请求聚合以及服务发现
上篇文章给大家讲解了Ocelot的一些特性并对路由进行了详细的介绍,今天呢就大家一起来学习下Ocelot的请求聚合以及服务发现功能。希望能对大家有所帮助。
作者:依乐祝
原文地址:https://www.cnblogs.com/yilezhu/p/9695639.html
请求聚合
Ocelot允许你声明聚合路由,这样你可以把多个正常的ReRoutes打包并映射到一个对象来对客户端的请求进行响应。比如,你请求订单信息,订单中又包含商品信息,这里就设计到两个微服务,一个是商品服务,一个是订单服务。如果不运用聚合路由的话,对于一个订单信息,客户端可能需要请求两次服务端。实际上这会造成服务端额外的开销。这时候有了聚合路由后,你只需要请求一次聚合路由,然后聚合路由会合并订单跟商品的结果都一个对象中,并把这个对象响应给客户端。使用Ocelot的此特性可以让你很容易的实现前后端分离的架构。
为了实现Ocelot的请求功能,你需要在ocelot.json中进行如下的配置。这里我们指定了了两个正常的ReRoutes,然后给每个ReRoute设置一个Key属性。最后我们再Aggregates节点中的ReRouteKeys属性中加入我们刚刚指定的两个Key从而组成了两个ReRoutes的聚合。当然我们还需要设置UpstreamPathTemplate匹配上游的用户请求,它的工作方式与正常的ReRoute类似。
注意:不要把Aggregates中UpstreamPathTemplate设置的跟ReRoutes中的UpstreamPathTemplate设置成一样。
下面我们先上个实例例子先!演示代码已经同步更新Github上。有兴趣的朋友可以查看源码:https://github.com/yilezhu/OcelotDemo
在开始实例前先把我们的ocelot Nuget包升级到最新的12.0.0版本,当然你也可以不进行升级。这里需要注意一下,如果你升级到12.0.0的版本的话,那么你
config.AddOcelot()
的用法会发生改变,需要传入参数config.AddOcelot(hostingContext.HostingEnvironment)
1.为了演示的需要这里我们新增一个类库项目,分别新建两个类,一个是商品Good类,一个是订单Order类(这里只是为了演示的需要,所以代码很简陋)如下所示:
public class Goods
{
public int Id { get; set; }
public string Content { get; set; }
}
public class Orders
{
public int Id { get; set; }
public string Content { get; set; }
}
接下来我们给OrderApi以及GoodApi分别新建一个控制器,并返回相应的实体。如下所示:
//GoodApi项目中
[Route("api/[controller]")]
[ApiController]
public class GoodController : ControllerBase
{
// GET api/Good/5
[HttpGet("{id}")]
public ActionResult<string> Get(int id)
{
var item = new Goods
{
Id = id,
Content = $"{id}的关联的商品明细",
};
return JsonConvert.SerializeObject(item);
}
}
//OrderApi项目中
[Route("api/[controller]")]
[ApiController]
public class OrderController : ControllerBase
{
// GET api/Order/5
[HttpGet("{id}")]
public ActionResult<string> Get(int id)
{
var item = new Orders {
Id=id,
Content=$"{id}的订单明细",
};
return JsonConvert.SerializeObject(item);
}
}接下来我们分别在ocelot.good.json以及ocelot.order.json中新增一个路由,并给出Keys.如下所示:
这里注意,跟上篇文章中的路由不同的是,这里多了一个Key属性。
//ocelot.good.json
{
"DownstreamPathTemplate": "/api/Good/{id}",
"DownstreamScheme": "http",
"DownstreamHostAndPorts": [
{
"Host": "localhost",
"Port": 1001
}
],
"UpstreamPathTemplate": "/good/{id}",
"UpstreamHttpMethod": [ "Get", "Post" ],
"Key": "Good",
"Priority": 2
}
//ocelot.order.json
{
"DownstreamPathTemplate": "/api/Order/{id}",
"DownstreamScheme": "http",
"DownstreamHostAndPorts": [
{
"Host": "localhost",
"Port": 1002
}
],
"UpstreamPathTemplate": "/order/{id}",
"UpstreamHttpMethod": [ "Get", "Post" ],
"Key": "Order",
"Priority": 2
}在ocelot.all.json中加入聚合配置,如下所示:
"Aggregates": [
{
"ReRouteKeys": [
"Good",
"Order"
],
"UpstreamPathTemplate": "/GetOrderDetail/{id}"
}
]注意:这里
Aggregates
跟ReRoutes
同级,ReRouteKeys
中填写的数组就是上面步骤3中设置的Key
属性对应的值。我们分别运行起来三个项目,然后访问接口地址:http://localhost:1000/GetOrderDetail/1 会得到如下的聚合响应内容:
格式化后代码如下:{
"Good":{
"Id":1,
"Content":"1的关联的商品明细"
},
"Order":{
"Id":1,
"Content":"1的订单明细"
}
}眼尖的朋友可能已经猜到了。聚合路由返回的内容就是json串。json串由
ReRouteKeys
组成,每个Key
的内容就是具体下游响应的内容了!实例代码已经同步更新到Github上,地址:https://github.com/yilezhu/OcelotDemoOcelot将始终使用聚合请求返回内容类型application/json。还有需要注意的是聚合请求不会返回404请求。如果两个下游都返回404状态码的话,这里聚合后的响应也不会返回404,只会返回空的json串,拿上面的实例,如果两个下游都返回404的话,那么他的响应代码类似下面这样:
{
"Good": ,
"Order":
}如果下游服务返回404,则聚合将仅为该下游服务返回任何内容。即使所有下游都返回404,它也不会将聚合响应更改为404。
服务发现
Ocelot允许您指定服务发现提供程序,并将使用它来查找Ocelot将请求转发到的下游服务的主机和端口。目前,这仅在GlobalConfiguration部分中受支持,这意味着相同的服务发现提供程序将用于为ReRoute级别指定ServiceName的所有ReRoutes。
Consul
在使用Consul前你首先要做的就是安装在Ocelot中提供Consul支持的NuGet包
Install-Package Ocelot.Provider.Consul
然后将下面的内容添加在ConfigureServices方法中
services.AddOcelot()//注入Ocelot服务
.AddConsul();
GlobalConfiguration中需要加入以下内容。如果您未指定主机和端口,则将使用Consul默认值。
"ServiceDiscoveryProvider": {
"Host": "localhost",
"Port": 8500,
"Type": "Consul"
}
注意:如果你采用
AddOcelot()
这种方式来自动加载ocelot配置文件的方式,那么你需要新建一个ocelot.global.json文件,然后加入上面的配置:如下所示:{
"GlobalConfiguration": {
"ServiceDiscoveryProvider": {
"Host": "localhost",
"Port": 8500,
"Type": "Consul"
}
}
}
然后重新运行dotnet run命令会自动合并配置信息到Ocelot.json中,生成的对应内容如下:
```C#
"ServiceDiscoveryProvider": {
"Host": "localhost",
"Port": 8500,
"Type": "Consul",
"Token": null,
"ConfigurationKey": null,
"PollingInterval": 0
}这个上篇文章中已经进行了相关的介绍。
为了告诉Ocelot ReRoute是为其主机和端口使用服务发现提供程序,您必须在下游请求时添加要使用的ServiceName和负载均衡器。目前,Ocelot可以使用RoundRobin和LeastConnection算法。如果未指定负载均衡器,则Ocelot将不会对请求进行负载均衡。
{
"DownstreamPathTemplate": "/api/posts/{postId}",
"DownstreamScheme": "https",
"UpstreamPathTemplate": "/posts/{postId}",
"UpstreamHttpMethod": [ "Put" ],
"ServiceName": "product",
"LoadBalancerOptions": {
"Type": "LeastConnection"
},
}
设置此项后,Ocelot将从服务发现提供程序中查找下游主机和端口,并跨任何可用服务进行负载平衡请求。
动态路由
作者的想法是在使用服务发现提供程序时启用动态路由。在此模式下,Ocelot将使用上游路径的第一个段来与服务发现提供程序一起查找下游服务。
例如,使用https://api.yilezhu.cn/product/products 等网址调用ocelot 。Ocelot将采用产品路径的第一部分product
,并将其用作在Consul中查找服务的Key。如果consul返回一个服务,Ocelot将使用从consul返回的主机和端口以及剩余路径段组合后的Url来进行请求的响应。,如:http:// hostfromconsul:portfromconsul/products。Ocelot将正常向下游URL转发查询字符串。即query
要启用动态路由,您需要在配置中保留0个ReRoutes。目前您无法混合动态和配置ReRoutes。除此之外,您还需要指定上面概述的Service Discovery提供程序详细信息和下游http / https方案作为DownstreamScheme。
除此之外,您还可以设置RateLimitOptions,QoSOptions,LoadBalancerOptions和HttpHandlerOptions,DownstreamScheme(您可能希望在https上调用Ocelot,但可以通过http与私有服务进行通信),这些将应用于所有动态ReRoutes。
配置可能看起来像:
{
"ReRoutes": [],
"Aggregates": [],
"GlobalConfiguration": {
"RequestIdKey": null,
"ServiceDiscoveryProvider": {
"Host": "localhost",
"Port": 8500,
"Type": "Consul",
"Token": null,
"ConfigurationKey": null
},
"RateLimitOptions": {
"ClientIdHeader": "ClientId",
"QuotaExceededMessage": null,
"RateLimitCounterPrefix": "ocelot",
"DisableRateLimitHeaders": false,
"HttpStatusCode": 429
},
"QoSOptions": {
"ExceptionsAllowedBeforeBreaking": 0,
"DurationOfBreak": 0,
"TimeoutValue": 0
},
"BaseUrl": null,
"LoadBalancerOptions": {
"Type": "LeastConnection",
"Key": null,
"Expiry": 0
},
"DownstreamScheme": "http",
"HttpHandlerOptions": {
"AllowAutoRedirect": false,
"UseCookieContainer": false,
"UseTracing": false
}
}
}
Ocelot还允许您设置DynamicReRoutes,允许您为每个下游服务设置速率限制规则。如果您有一个产品和搜索服务,并且您希望对另一个进行速率限制,则此功能非常有用。这方面的一个例子如下。
{
"DynamicReRoutes": [
{
"ServiceName": "product",
"RateLimitRule": {
"ClientWhitelist": [],
"EnableRateLimiting": true,
"Period": "1s",
"PeriodTimespan": 1000.0,
"Limit": 3
}
}
],
"GlobalConfiguration": {
"RequestIdKey": null,
"ServiceDiscoveryProvider": {
"Host": "localhost",
"Port": 8523,
"Type": "Consul"
},
"RateLimitOptions": {
"ClientIdHeader": "ClientId",
"QuotaExceededMessage": "",
"RateLimitCounterPrefix": "",
"DisableRateLimitHeaders": false,
"HttpStatusCode": 428
}
"DownstreamScheme": "http",
}
}
此配置意味着如果您在/product/上进入Ocelot请求,则动态路由将启动,并且ocelot将使用针对DynamicReRoutes部分中的产品服务的速率限制设置。
GitHub地址
https://github.com/yilezhu/OcelotDemo
总结
本文接着上篇文章进行了Ocelot请求聚合功能以及服务发现功能的介绍,并且对Ocelot动态路由功能也进行了简单的阐述。对于请求聚合这块进行了相关实例代码的演示,并已经更新到Github上面了!希望能对大家有所帮助!
作者:依乐祝
出处:https://www.cnblogs.com/yilezhu
联系:1015657114@qq.com .NET Core实战项目交流群:637326624
[转载]Ocelot简易教程(四)之请求聚合以及服务发现的更多相关文章
- Ocelot简易教程(四)之请求聚合以及服务发现
上篇文章给大家讲解了Ocelot的一些特性并对路由进行了详细的介绍,今天呢就大家一起来学习下Ocelot的请求聚合以及服务发现功能.希望能对大家有所帮助. 作者:依乐祝 原文地址:https://ww ...
- [转载]Ocelot简易教程(三)之主要特性及路由详解
上篇<Ocelot简易教程(二)之快速开始2>教大家如何快速跑起来一个ocelot实例项目,也只是简单的对Ocelot进行了配置,这篇文章会给大家详细的介绍一下Ocelot的配置信息.希望 ...
- [转载]Ocelot简易教程(一)Ocelot是什么
Ocelot简易教程(一)Ocelot是什么 简单的说Ocelot是一个用.NET Core实现并且开源的API网关技术. 可能你又要问了,什么是API网关技术呢?Ocelot又有什么特别呢?我们又该 ...
- [转载]Ocelot简易教程(五)之集成IdentityServer认证以及授权
作者:依乐祝 原文地址:https://www.cnblogs.com/yilezhu/p/9807125.html 最近比较懒,所以隔了N天才来继续更新第五篇Ocelot简易教程,本篇教程会先简单介 ...
- [转载]Ocelot简易教程(二)之快速开始2
为什么这篇的标题叫“Ocelot简易教程(二)之快速开始2”呢,因为很多朋友跟我说上一篇“ Ocelot简易教程(二)之快速开始1”内容太少了,只是简单介绍Ocelot的一些简单配置,让Ocelot能 ...
- [转载]Ocelot简易教程(六)之重写配置文件存储方式并优化响应数据
作者:依乐祝 原文地址:https://www.cnblogs.com/yilezhu/p/9807125.html 很多人都说配置文件的配置很繁琐,如果存储在数据库就方便很多,可以通过自定义UI界面 ...
- [转载]Ocelot简易教程(二)之快速开始1
Ocelot是为.net core量身定做的,目前是基于 netstandard2.0进行构建的. .NET Core 2.1中如何使用呢? 安装NuGet package 使用nuget安装Ocel ...
- Ocelot简易教程(七)之配置文件数据库存储插件源码解析
作者:依乐祝 原文地址:https://www.cnblogs.com/yilezhu/p/9852711.html 上篇文章给大家分享了如何集成我写的一个Ocelot扩展插件把Ocelot的配置存储 ...
- Ocelot简易教程(六)之重写配置文件存储方式并优化响应数据
本来这篇文章在昨天晚上就能发布的,悲剧的是写了两三千字的文章居然没保存,结果我懵逼了.今天重新来写这篇文章.今天我们就一起来探讨下如何重写Ocelot配置文件的存储方式以及获取方式. 作者:依乐祝 原 ...
随机推荐
- 1.3 Quick Start中 Step 8: Use Kafka Streams to process data官网剖析(博主推荐)
不多说,直接上干货! 一切来源于官网 http://kafka.apache.org/documentation/ Step 8: Use Kafka Streams to process data ...
- 如何修复和检测Windows系统漏洞
本文为<如何给系统打补丁(知识篇)>一文实战文章. 本文出自 "李晨光原创技术博客" 博客,谢绝转载!
- 去掉“此电脑”中的“WPS云文档”图标
平台:Win10 问题:安装了WPS2019专业版后,此电脑窗口出现了一个WPS云文档图标,无法删除,云文档设置中也无法取消. 解决:打开注册表,定位到HKEY_CURRENT_USER\Softwa ...
- 记2018/4/29 qbxt 测试
记 2018/4/29 qbxt 测试(提高基础班) 简单的 NOIP 模拟赛 竞赛时间: 2018 年 4 月 29 日 13:30-17:00 题目名称 乘法 求和 计数 输入文件名 mul.i ...
- 全球可信并且唯一免费的HTTPS(SSL)证书颁发机构:StartSSL
全球可信并且唯一免费的HTTPS(SSL)证书颁发机构:StartSSL http://blog.s135.com/startssl/ 购买权威机构的证书一年大概得七八千元,其实这是不值得的,所以一直 ...
- Iptables-主机防火墙设置
基于Iptables构建主机防火墙 Iptables优点: 数据包过滤机制,它会对数据包包头数据进行分析. 1.1.1 加载相关薄块到内核 [root@centos7 ~]# lsmod | egre ...
- Flume Channels官网剖析(博主推荐)
不多说,直接上干货! Flume Sources官网剖析(博主推荐) 一切来源于flume官网 http://flume.apache.org/FlumeUserGuide.html Flume Ch ...
- git的安装及其使用
在Windows上安装Git的快捷方式: 工具:1.Windows的console工具:ConEmu(https://conemu.github.io/)多窗口.记录log.多theme选择,操作Gi ...
- Android 使用XML隐藏ActionBar中遇错的解决的方法
今天我在使用Menifest.xml让程序隐藏标题栏是一直出错.主要内容是: You need to use a theme.AppCompat theme(descendant) with this ...
- Windows下Nginx的下载安装、启动停止和配置浏览
前言: 记录一下今天在Windows下载安装Nginx服务器的过程.因为网上关于Nginx的资料都太复杂了,大多数是在Linux下使用的方法. 1.下载 Nginx官网下载地址:http://ngin ...