ASP.NET Core 404 响应中的 Service Fabric 反向代理集成

Posted

技术标签:

【中文标题】ASP.NET Core 404 响应中的 Service Fabric 反向代理集成【英文标题】:Servce Fabric Reverse Proxy Integration in ASP.NET Core 404 Response 【发布时间】:2018-08-08 20:21:27 【问题描述】:

我正在研究ICommunicationClient 的实现以及用于 HTTP 协议通信的相关内容,这些内容应该与 SF 反向代理兼容。对我来说最微妙的部分是重试策略。根据 Azure docs for 404 errors,反向代理在决定是否应重试时依赖于从 Web 服务返回的 X-Service-Fabric 标头。

ASP.NET Core 提供 middleware 用于与反向代理集成,该反向代理向每个 404 响应添加 X-Service-Fabric 标头。

假设我们有这样的场景:ServicePartitionClient 为侦听端口 3001 的无状态服务缓存端点。在某些时候,该服务可能会移动到另一个节点。在第一个节点上,Service Fabric 运行时分配具有自己的终结点的不同服务,但使用相同的中间件并侦听相同的 3001 端口。

当客户端尝试在其旧(缓存)地址调用原始服务时,它将收到包含 X-Service-Fabric 标头的 404 响应。根据反向代理策略,它不应该重试,但对我来说,客户端似乎会永远保持连接到错误的服务,并且不会尝试重新解析端点。

我在文档中找不到有关此案例的任何信息,我在这里遗漏了什么吗?依赖此标准中间件并且不对带有 X-Service-Fabric: ResourceNotFound 标头的 404 错误进行重试尝试是否安全?

【问题讨论】:

您是否可能将 您的 应用程序发出的 404 与假定驻留在您迁移节点中的任何服务发出的 404 混为一谈?我假设您无法控制您的应用程序不再运行的节点 @JoshE:我无法控制服务结构如何管理服务生命周期、故障转移、端口分配等。服务可以在节点周围随机移动,最终不同的 SF 服务可能会开始监听该地址以前被其他服务使用过 对,SF 有责任确保通过结构正确路由请求。客户端有责任使自己的缓存失效,例如,当它从缓存的端点接收到 404 时。您无法控制节点迁移,但(如果您是客户端)您可以控制响应它的操作 @JoshE: 确切地说,客户端提供基于错误响应的重试机制,反向代理行为是仅在响应不包含“X-Service-Fabric: ResourceNotFound”标头时重试 404 并解析新端点,但在我描述的场景中,客户端可能会从另一个结构服务接收此标头,并认为它保持连接到正确的提供程序,对我来说,似乎唯一安全的选择是重试每个 404 响应,即我要避免的事情 【参考方案1】:

在所描述的情况下,通信客户端将因保持连接到错误的服务而失效。 recommended by Microsoft 为具有动态分配端口的服务使用唯一的 URL 前缀来处理这些场景。

在 ASP.NET Core 中,程序员可以利用 ServiceFabricMiddleware 检查 URL 前缀,如果不匹配则返回 410 Gone。然后,ICommunicationClient 的 HTTP 实现可以仅针对 410 响应使用重新解析端点重试,并且如果启用了反向代理集成,则不对带有 X-Service-Fabric: ResourceNotFound 标头的 404 响应执行任何重试。

【讨论】:

【参考方案2】:

在您给定的场景中,当您的客户端遇到 404 时,X-Service-Fabric:ResourceNotFound 标头并不是您的代码在决定是否重试某些操作时可以检查的唯一属性。

为了简单地解决您的担忧,即您的客户端将无法区分“友好”节点和“新到达”节点之间的区别,并且由于您已经在使用 http 标头,您可以添加自定义传出响应的 HTTP 标头,以标识请求来自您的应用程序。 当客户端收到 404 时,您可以简单地检查您的自定义标头是否存在,以回答它是否是“合法”重试的问题。当然,仅仅为了验证检查而添加自定义 HTTP 标头可能更像是针对本地问题的全局解决方案。 Ed:不用说,这不应该被应用程序用来做出安全决策

一个更优雅和更复杂的方法是使用 HTTP 标头和响应属性的不同组合来推断相同的结果(例如,查看是否有一些其他标头是预期的/意外的),但这也可能是问题的超本地解决方案。

【讨论】:

感谢您的回答,我正在考虑的直接解决方案是创建过滤器,在控制器处理请求后添加自定义标头,这将表明 404 与无效地址无关,并且请求命中正确的端点并由正确的服务处理,但我的问题的主要问题是为什么 ASP.NET Core 在中间件级别执行此操作而不是提供操作过滤器,这是否意味着 SF 反向代理行为在这种情况下会不正确 我认为原因是允许了解堆栈中更高层的底层基础设施问题可能会带来、允许或鼓励不希望的耦合和混合问题。您也可以考虑在中间件中设置您的标头,以保护您的应用程序逻辑免受它和重试等问题的影响

以上是关于ASP.NET Core 404 响应中的 Service Fabric 反向代理集成的主要内容,如果未能解决你的问题,请参考以下文章

ASP.NET Core API - 在 Azure 应用服务上获取 404,但在 Localhost 上工作正常

Blazor ASP.Net Core 3.1 Web API 在发布时返回 404 错误

在 Azure 的 ASP.NET Core 3.1 应用程序中获取 swagger-ui 返回 404

IIS 10 上的 ASP.NET Core 404 错误

ASP.NET Core Kestrel 随机404错误

使用 app.useSpa() 并处理 404 的 Asp.Net Core