1

是否可以在 Ocelot中访问DownstreamReRoute对象?DelegatingHandler我有一个DelegatingHandler实例,我想根据正在调用的下游重新路由稍微改变它的行为。我可以根据HttpRequestMessage传递给SendAsync()方法的 URL 来执行此操作,但如果可能的话,我更愿意通过下游重新路由键来执行此操作。

我查看了添加的依赖项OcelotBuilder,看看是否可以注入一些东西然后查询当前的重新路由,但这似乎不可能。

例如,如果我有一个DelegatingHandler

public class MyDelegatingHandler : DelegatingHandler
{
  protected override async Task<HttpResponseMessage> SendAsync(HttpRequestMessage request, CancellationToken cancellationToken)
  { 
    // access reRoute here?
  }
}

和配置(为简洁起见删除了必填字段)

"ReRoutes": [
{
  "DownstreamPathTemplate": "/downstream/foo",
  "UpstreamPathTemplate": "/foo",
  "Key": "FooKey",
  "DelegatingHandlers": [ "MyDelegatingHandler" ]
},
{
  "DownstreamPathTemplate": "/downstream/bar",
  "UpstreamPathTemplate": "/bar",
  "Key": "BarKey",
  "DelegatingHandlers": [ "MyDelegatingHandler" ]
}]

是否有可能知道我是从 delegatingHandler调用FooKey还是重新路由?BarKey

4

2 回答 2

1

我设法通过PreQueryStringBuilderMiddleware在配置 Ocelot 时添加一个处理程序来解决这个问题。

通过这样做,我可以在包含 reRouteKey 的 HttpContext.Items 集合中设置一个属性。然后可以由请求中的其他处理器拾取。

例如(没有空处理等)

app.UseOcelot(cfg =>
  cfg.PreQueryStringBuilderMiddleware = (ctx, next) => {
    ctx.HttpContext.Items["ReRouteKey"] = ctx.DownstreamReRoute.Key;
    return next.Invoke();
});
于 2019-11-15T13:38:17.190 回答
0

我刚刚找到了解决方案,您必须使用IHttpContextAccessor.

MyDelegatingHandler.cs

using Ocelot.Middleware;

public class MyDelegatingHandler : DelegatingHandler
{
    private IHttpContextAccessor _httpContext;
    public MyHandler(IHttpContextAccessor httpContext)
    {
        _httpContext = httpContext;
    }
    protected override async Task<HttpResponseMessage> SendAsync(HttpRequestMessage request, CancellationToken cancellationToken)
    {
        var downstreamRoute = _httpContext.HttpContext.Items?.DownstreamRouteHolder()?.Route?.DownstreamRoute?.FirstOrDefault();
        if (downstreamRoute != null)
        {
             if(downstreamRoute.Key == "FooKey")
             {
                  //Do something
             } else if (downstreamRoute.Key == "BarKey")
             {
                  //Do something else
             }
        }
    }
}

您还需要services.AddHttpContextAccessor();注册Startup.cs

注意:具体来说,我的配置是“Routes”而不是“ReRoutes”。我相信它也适用于“ReRoutes”配置。

于 2020-10-08T10:10:13.723 回答