ocelot允许您指定聚合多个普通reroutes的aggregate reroutes(聚合路由),并将其响应映射到一个对象中。一般用于当您有一个客户端向服务器发出多个请求,而这些请求可以合并成一个的时候。此功能允许您通过ocelot实现前端类型结构的后端。

此功能是问题 79的一部分,并且作为问题 298的一部分进行了进一步改进。

为了设置它,你必须在ocelot.json中做如下的事情。 这里我们已经指定了两个普通的reroutes,每一个都有一个key属性。 然后,我们使用reroutekeys列表中的键指定组成两个reroutes的聚合,然后设置upstreampathtemplate,它的工作方式与普通的reroute相似。 很明显,您不能在reroutes和aggregates之间复制upstreampathtemplates。 除requestidkey之外,您可以使用普通reroute所有的选项(在下面的陷阱中进行了解释)。

高级应用-注册你自己的聚合器

ocelot只是基本的请求聚合,然后我们添加了一个更高级的方法,让用户从下游服务中获取响应,然后将它们聚合到响应对象中。

ocelot.json的设置与基本聚合方法几乎相同,只需额外添加一个aggregator属性,如下所示。

{
    "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": "/",
            "aggregator": "fakedefinedaggregator"
        }
    ]
}

这里我们添加了一个叫fakedefinedaggregator的聚合器。当ocelot尝试聚合这个reroute的时候,会去查看这个聚合器。

为了使这个聚合器可用,我们必须像下面这样把fakedefinedaggregator添加到ocelotbuilder。

services
    .addocelot()
    .addsingletondefinedaggregator<fakedefinedaggregator>();

现在,当ocelot尝试聚合上述reroute时,它会在容器中找到fakedefinedaggregator并使用它来聚合reroute。 由于fakedefinedaggregator是在容器中注册,因此您可以将它需要的任何依赖项都添加到容器中,如下所示。

services.addsingleton<foodependency>();

services
    .addocelot()
    .addsingletondefinedaggregator<fooaggregator>();

在这个例子中fooaggregator依赖foodependency,将会被容器解析。

除此之外,ocelot还允许您添加如下所示的瞬态聚合器。(参考.net core依赖注入,译者注)

services
    .addocelot()
    .addtransientdefinedaggregator<fakedefinedaggregator>();

为了实现一个聚合器,你必须实现这个接口。

public interface idefinedaggregator
{
    task<downstreamresponse> aggregate(list<downstreamresponse> responses);
}

使用此功能,您几乎可以做任何您想做的事情,因为downstreamresponse包含内容,头和状态代码。 如果需要,我们可以添加额外的东西,只需在github上提出这个问题。请注意,如果在向聚合中的reroute发出请求时httpclient抛出异常,那么您将不会获得其downstreamresponse,但您会获得其他请求成功的downstreamresponse。 如果某个请求抛出异常,则会被记录。

基本演示

{
    "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": "/"
        }
    ]
}

你也可以设置aggregate的upstreamhost和rerouteiscasesensitive,和其他reroutes的作用是一样的。

如何路由/tom返回 {“age”: 19},路由/laura返回{“age”: 25},那么聚合之后的相应就如下所示。

{"tom":{"age": 19},"laura":{"age": 25}}

目前的聚合功能非常简单。 ocelot只是从你的下游服务获得响应,并将其复制到json字典中,如上所示。将reroute键作为字典的关键字,下游服务的响应体作为值。你可以看到这个对象就是没有任何缩进空格的json。

来自下游服务相应的所有头部都会丢失。

ocelot将总是将聚合请求的内容类型返回application/json。

如果下游服务返回404,那么聚合将为该下游服务返回空内容。 即使所有下游都返回404,它也不会是聚合响应为404。

疑难杂症 / 更多信息

您不能将reroutes与特定的requestidkeys一起使用,因为这将使跟踪非常的复杂。

聚合仅支持get http动词。

原作者:小水 原文链接:https://www.cnblogs.com/loogn/p/9007768.html