10. Server Scheduling (服务器调度)
对于 HTTP 服务器来说,尽早发送所有响应通常是有益的。然而,当在单个连接上服务多个请求时,请求之间可能会竞争资源,例如连接带宽。本节描述了当存在这种竞争时,服务器如何调度竞争响应的发送顺序的考虑。
服务器调度是基于许多输入的优先级排序过程,优先级信号只是输入的一种形式。实现选择或部署环境等因素也起作用。任何给定的连接都可能有许多动态排列。由于这些原因,不可能描述通用的调度算法。本文档提供了一些基本的、非详尽的建议,说明服务器如何对优先级参数采取行动。它没有详细描述服务器如何将优先级信号与其他因素相结合。端点不能依赖基于优先级信号的特定处理。表达优先级只是一个建议。
建议 (RECOMMENDED) 服务器在可能的情况下尊重 urgency 参数(第 4.1 节),在低紧急度响应之前发送高紧急度响应。
incremental 参数指示客户端如何处理到达的响应字节。建议 (RECOMMENDED) 服务器在可能的情况下尊重 incremental 参数(第 4.2 节)。
相同紧急度的非增量响应应该 (SHOULD) 通过按流 ID 升序分配带宽来提供服务,这对应于客户端发出请求的顺序。这样做可确保客户端可以使用请求顺序来影响响应顺序。
相同紧急度的增量响应应该 (SHOULD) 通过在它们之间共享带宽来提供服务。增量响应的消息内容在接收到部分或块时使用。客户端可能从接收所有这些资源的一部分而不是单个资源的全部中受益更多。提高性能所需的资源部分的大小各不相同。某些资源类型将关键元素放在前面;其他资源可以逐步使用信息。此方案没有明确规定服务器应如何使用大小、类型或任何其他输入来决定如何确定优先级。
可能存在服务器需要在相同紧急度级别调度多个增量和非增量响应的场景。严格遵守基于紧急度和请求生成顺序的调度指导可能会导致客户端出现次优结果,因为早期的非增量响应可能会阻止提供稍后发出的增量响应。以下是此类挑战的示例:
-
在相同紧急度级别,对大型资源的非增量请求后跟对小型资源的增量请求。
-
在相同紧急度级别,不确定长度的增量请求后跟非增量大型资源。
建议 (RECOMMENDED) 服务器在可能的情况下避免此类饥饿。这样做的方法是实现决策。例如,服务器可能会根据内容大小等其他信息抢先发送特定增量类型的响应。
服务器推送的最佳调度很困难,尤其是当推送的资源与活动的并发请求竞争时。服务器在调度时可以考虑许多因素,例如正在推送的资源的类型或大小、触发推送的请求的优先级、活动并发响应的计数、其他活动并发响应的优先级等。没有关于应用这些的最佳方式的一般指导。过于简单的服务器可能会以过高的优先级推送并阻塞客户端请求,或者以过低的优先级推送并延迟响应,从而否定服务器推送的预期目标。
优先级信号是服务器推送调度的一个因素。参数值默认值的概念适用略有不同,因为没有明确的客户端信号初始优先级。服务器可以应用源响应中提供的优先级信号;参见第 8 节中给出的合并指导。在没有源信号的情况下,应用默认参数值可能是次优的。无论服务器决定如何调度推送的响应,它都可以通过在 PUSH_PROMISE 或 HEADERS 帧中包含 Priority 字段来向客户端发送预期优先级的信号。
10.1. Intermediaries with Multiple Backend Connections (具有多个后端连接的中介)
服务 HTTP 连接的中介可能会将请求分散到多个后端连接上。当它严格应用优先级排序规则时,低优先级请求在具有更高优先级的请求正在进行时无法取得进展。此阻塞可以传播到后端连接,对等方可能将其解释为连接停滞。端点通常实施针对停滞的保护,例如在一定时间段后突然关闭连接。为了减少发生这种情况的可能性,中介可以避免严格遵循优先级排序,而是为它们转发的所有请求分配少量带宽,以便每个请求都可以随着时间的推移取得一些进展。
类似地,服务器应该 (SHOULD) 为充当隧道的流分配一定量的带宽。