| RFC 10008 | HTTP QUERY 方法 | 2026 年 6 月 |
| Reschke 等 | 标准跟踪 | [页码] |
本规范定义了 HTTP 的 QUERY 方法。 QUERY 请求要求请求目标以安全且幂等的方式处理其中包含的 内容,然后以该处理的结果进行响应。这类似于 POST 请求,但 QUERY 请求 可以自动重复或重新启动,而无需担心 部分状态更改。¶
这是一份互联网标准跟踪文档。¶
本文档是互联网工程任务组 (IETF) 的成果。它代表了 IETF 社区的共识。本文档已经 过公开评审,并已获互联网工程指导组 (IESG) 批准发布。有关 互联网标准的更多信息,请参阅 RFC 7841 第 2 节。¶
有关本文档当前状态、任何 勘误以及如何提供反馈的信息,可在 https://www.rfc-editor.org/info/rfc10008 获取。¶
Copyright (c) 2026 IETF Trust and the persons identified as the document authors. All rights reserved.¶
This document is subject to BCP 78 and the IETF Trust's Legal Provisions Relating to IETF Documents (https://trustee.ietf.org/license-info) in effect on the date of publication of this document. Please review these documents carefully, as they describe your rights and restrictions with respect to this document. Code Components extracted from this document must include Revised BSD License text as described in Section 4.e of the Trust Legal Provisions and are provided without warranty as described in the Revised BSD License.¶
本规范定义了 HTTP QUERY 请求方法,作为一种 发出安全、幂等请求([HTTP] 的 第 9.2 节)的方式,该请求 包含一个表示形式,用于描述目标资源应如何处理该请求。¶
一种常见的查询模式是:¶
但是,当所传递的数据量太大,无法编码到请求的 URI 中时, 这种模式就会出现问题:¶
作为使用 GET 的替代方案,许多实现会使用 HTTP POST 方法来执行查询,如下面的示例 所示。在这种情况下,查询操作的输入 作为请求内容传递,而不是使用 请求 URI 的查询组件。¶
使用 HTTP POST 请求查询的一种典型方式是:¶
然而,在这种变体中,如果不了解该请求所发送到的 资源和服务器的具体信息,就无法轻易看出正在执行的是一个安全、 幂等的查询。¶
QUERY 方法提供了一种跨越 GET 和 POST 使用方式之间差距的解决方案,上面的 示例可以表示为:¶
与 POST 一样,查询操作的输入作为请求内容传递, 而不是作为请求 URI 的一部分。但是,与 POST 不同,该方法明确是安全且 幂等的,因此可以使用缓存和自动重试等功能。¶
鉴于任何重要资源都应当由 URI 标识这一设计原则,本规范描述了服务器如何为查询本身或 特定查询结果分配 URI,以便以后在 GET 请求中使用。¶
总结如下:¶
| GET | QUERY | POST | |
|---|---|---|---|
| 安全 | 是 | 是 | 可能不是 |
| 幂等 | 是 | 是 | 可能不是 |
| 查询本身的 URI | 是(按定义) | 可选(Location 响应字段) | 否 |
| 查询结果的 URI | 可选(Content-Location 响应字段) | 可选(Content-Location 响应字段) | 可选(Content-Location 响应字段) |
| 可缓存 | 是 | 是 | 是,但仅用于未来的 GET 或 HEAD 请求 |
| 内容(正文) | “没有定义的语义” | 预期存在(语义由目标资源定义) | 预期存在(语义由目标资源定义) |
QUERY 方法用于发起服务器端查询。与 GET 方法不同,GET 方法请求由目标 URI 标识的资源的 表示形式 (如 [HTTP] 的 第 7.1 节所定义),QUERY 方法用于请求目标资源在 该目标资源的范围内执行查询操作。¶
请求的内容及其媒体类型定义查询。 源服务器根据目标资源确定操作的范围。¶
如果 Content-Type 请求字段 ([HTTP],第 8.3 节) 缺失或与请求内容不一致,服务器必须使请求失败。¶
与所有 HTTP 方法一样,目标 URI 的查询部分 参与标识被查询的资源。它是否以及如何 直接影响查询结果由资源本身决定, 不属于本规范的范围。¶
QUERY 请求对于目标资源而言是安全的 ([HTTP],第 9.2.1 节); 也就是说,客户端不会请求或期望对 目标资源的状态作任何更改。这并不妨碍服务器 创建额外的 HTTP 资源,通过这些资源可以检索额外 信息(参见第 2.3 节和第 2.4 节)。¶
此外,QUERY 请求是幂等的 ([HTTP],第 9.2.2 节); 它们可以在需要时重试或重复,例如在 连接失败之后。¶
根据 [HTTP] 的 第 15.3 节,2xx(成功)响应代码表示 请求已被成功接收、理解并接受。¶
特别是,200(OK)响应表示查询 已被成功处理,并且该处理的结果 包含在响应内容中。¶
QUERY 请求的语义同时取决于请求内容和相关的 元数据,例如媒体类型([HTTP],第 8.3.1 节)。 一般而言,任何内容与元数据不一致的请求问题都必须 使用 4xx(客户端错误)响应拒绝([HTTP],第 15.5 节)。¶
下面的列表描述了各种失败情况,并建议了具体的状态代码:¶
对于任何给定的 QUERY 请求,其等效资源是这样一种资源: 它响应 GET 请求,表示该 QUERY 请求及其目标,并同时考虑 消息内容和元数据([HTTP] 的 第 6 节)。 特别是,这包括表示形式元数据([HTTP] 的 第 8 节), 例如内容的媒体类型。¶
换句话说,等效资源是通过纳入请求内容, 从实现 QUERY 的资源派生出来的。¶
术语等效资源用于定义 其他 HTTP 方面的行为,例如所选择的表示形式。服务器可以 为这些资源分配 URI,但并非必须如此(参见 [URI] 的 第 1.1 节)。如果这样做,这些资源将 可通过 GET 请求访问。¶
成功响应(2xx,[HTTP] 的 第 15.3 节) 可以包含一个 Content-Location 标头字段,其中包含一个与 操作结果相对应的资源标识符;详情参见 [HTTP] 的 第 8.7 节。 这表示服务器声称客户端可以向 指示的 URI 发送 GET 请求,以检索刚刚执行的查询 操作的结果。所指示的资源可能是临时的。¶
服务器可以为 QUERY 请求的等效资源(第 2.2 节) 分配 URI。如果服务器这样做,该资源的 URI 可以包含在 2xx 响应的 Location 标头字段中(参见 [HTTP] 的 第 10.2.2 节)。这表示服务器声称客户端可以 向所指示的 URI 发送 GET 请求,以重复刚刚 执行的查询操作,而无需重新发送查询内容。该资源的 URI 可能是 临时的;如果未来的请求失败,客户端可以使用 原始 QUERY 请求目标和先前提交的内容重试。¶
在某些情况下,服务器可以选择通过将用户代理重定向到不同的 URI, 以间接方式响应 QUERY 请求(参见 [HTTP] 的 第 15.4 节)。¶
状态代码为 301(永久移动,[HTTP],第 15.4.2 节)或 308(永久重定向,[HTTP],第 15.4.9 节) 的响应表示目标资源已经永久移动到由 Location 响应字段引用的另一个 URI([HTTP],第 10.2.2 节)。 同样,状态代码为 302(已找到,[HTTP],第 15.4.3 节)或 307(临时重定向,[HTTP],第 15.4.8 节) 的响应表示目标资源已临时移动。在所有这四种情况下,服务器都在 建议用户代理可以通过向 Location 引用的新目标 URI 发送一个 类似的 QUERY 请求来完成其原始 QUERY 请求。¶
请注意,在 301 或 302 响应后将 POST 重定向为 GET 请求的例外 不适用于 QUERY 请求。¶
对 QUERY 的状态代码 303(参见其他,[HTTP] 的 第 15.4.4 节) 响应表示原始查询可以通过对 Location 响应字段所引用的 URI 发出普通检索请求来完成 ([HTTP],第 10.2.2 节)。 对于 HTTP,这意味着向新的目标 URI 发送 GET 请求,如 附录 A.4.3中的示例所示。¶
QUERY 请求的所选择表示形式([HTTP] 的 第 3.2 节) 与向该 QUERY 请求的等效资源 (第 2.2 节)发送 GET 请求时相同。¶
条件 QUERY 请求要求仅在 条件标头字段所描述的情况下,才在响应中 返回所选择的表示形式 (即经过任何内容协商后的查询结果),如 [HTTP] 的 第 13 节所定义。¶
QUERY 方法的响应是可缓存的;缓存可以按照 [HTTP-CACHING] 的 第 4 节使用它来 满足后续 QUERY 请求。¶
QUERY 请求的缓存键([HTTP-CACHING] 的 第 2 节)必须 纳入请求内容([HTTP-CACHING] 的 第 6 节)以及相关的 元数据([HTTP] 的 第 8 节)。¶
为了提高缓存效率,缓存可以先从请求内容和相关元数据中移除 语义上无关紧要的差异。例如,可以:¶
请注意,任何此类转换都仅用于生成缓存键; 它 不会改变请求本身。¶
客户端可以使用“no-transform”缓存指令([HTTP-CACHING] 的 第 5.2.1.6 节) 表明它们希望不发生此类转换(但请注意,该指令仅具有 建议性质)。¶
请注意,缓存 QUERY 方法响应本质上比缓存 GET 响应更复杂,因为需要完整读取请求内容才能确定 缓存键。如果 QUERY 响应提供 Location 响应字段(第 2.4 节) 来指示等效资源(第 2.2 节)的 URI,客户端 可以在后续请求中切换到 GET,从而简化处理。¶
资源可以使用“Accept-Query”响应标头字段 直接表示对 QUERY 方法的支持,同时标识 可以使用的具体查询格式媒体类型。¶
Accept-Query 包含一个媒体范围列表([HTTP] 的 第 12.5.1 节), 使用“结构化字段”语法 [STRUCTURED-FIELDS]。 媒体范围由 Token 或 String 组成的 List 结构化标头字段表示,其中包含不带参数的媒体范围值。¶
媒体类型参数(如果有)映射到 String 或 Token 类型的结构化字段参数。选择 Token 还是 String 在语义上没有区别。也就是说,接收方可以 将 Token 转换为 String,但不得根据接收到的类型 对它们进行不同处理。¶
媒体类型并不能完全映射到 Token;例如,它们 允许以数字开头。在此类情况下,需要 使用 String 格式。¶
通配符唯一受支持的用法是“*/*”(匹配任何类型) 或“xxxx/*”(匹配所指示类型的任何子类型)。¶
字段值中所列类型的顺序无关紧要。¶
Accept-Query 字段的值适用于服务器上共享相同路径的每个 URI;换言之, 查询组件会被忽略。如果对同一资源的请求返回 不同的 Accept-Query 值,则使用最近收到的仍然新鲜的值(按照 [HTTP-CACHING] 的 第 4.2 节)。¶
例如:¶
Accept-Query: "application/jsonpath", application/sql;charset="UTF-8"¶
尽管该字段的语法看起来与其他 字段(例如“Accept”([HTTP] 的 第 12.5.1 节))相似, 但它是一个结构化字段,因此必须按照 [STRUCTURED-FIELDS] 的 第 4 节中的规定进行处理。¶
QUERY 方法与所有 HTTP 方法一样,受到 [HTTP] 中所述的一般安全 注意事项约束。¶
它可以作为在 URI 中传递请求 信息(例如在查询组件中)的替代方案。在某些 情况下,这是首选方式,因为与请求内容相比,URI 更可能被 中间设备记录或以其他方式处理。在其他情况下,当查询 包含敏感信息时,URI 可能被记录这一点可能 促使使用 QUERY 而不是 GET。¶
如果服务器创建临时资源来表示 QUERY 请求的结果(例如用于 Location 或 Content-Location 字段),为该资源分配 URI, 并且请求包含不能被记录的敏感信息, 那么该 URI应该选择为不包含原始请求内容的任何敏感 部分。¶
如果缓存以不正确的方式规范化 QUERY 内容,或者其方式与 资源处理内容的方式存在显著差异, 那么当规范化导致误判时,可能会返回错误响应。¶
实现跨源资源共享(CORS)的用户代理所发出的 QUERY 请求 将需要“预检”请求, 因为 QUERY 不属于 CORS 安全列出的方法集合 (参见 [FETCH])。¶
IANA 已将 QUERY 方法添加到位于 <http://www.iana.org/assignments/http-methods> 的“超文本传输协议(HTTP)方法注册表” (参见 [HTTP] 的 第 16.3.1 节)。¶
| 方法名称 | 安全 | 幂等 | 规范 |
|---|---|---|---|
| QUERY | 是 | 是 | RFC 10008 的第 2 节 |
IANA 已将 Accept-Query 字段添加到“超文本传输协议(HTTP)字段名称 注册表”, 地址为 <https://www.iana.org/assignments/http-fields> (参见 [HTTP] 的 第 16.1.1 节)。¶
| 字段名称 | 状态 | 结构化类型 | 参考 | 注释 |
|---|---|---|---|---|
| Accept-Query | 永久 | List | RFC 10008 的第 3 节 |
下面的示例仅用于说明;如果确实需要 发送这么短的查询,那么使用 GET 可能更合适。¶
大多数示例中使用的媒体类型是“application/x-www-form-urlencoded” (如浏览器用户客户端的 POST 请求所使用,并在 [URL] 中的 “application/x-www-form-urlencoded” 中定义)。 为简洁起见,省略了 Content-Length 字段。¶
OPTIONS ([HTTP] 的 第 9.3.7 节)方法提供了一种发现 QUERY 支持的简单方式:¶
响应:¶
Allow 响应字段([HTTP] 的 第 10.2.1 节)表示指定资源上 支持的方法集合。¶
除使用 OPTIONS 外,还有其他替代方式。例如,可以在 事先不知道服务器是否支持的情况下尝试 QUERY 请求。服务器随后 要么处理该请求,要么可以返回 4xx 状态,例如 405(方法不 允许, [HTTP] 的 第 15.5.6 节),并包含 Allow 响应字段。¶
可以通过 Accept-Query 响应字段(第 3 节)发现 QUERY 支持的媒体类型:¶
响应:¶
哪些请求方法的响应会包含 Accept-Query,取决于 正在访问的资源。¶
检查 Accept-Query 的另一种方式是发出 QUERY 请求,然后 ——如果返回 4xx 状态,例如 415 响应(不支持的媒体类型,[HTTP] 的 第 15.5.16 节)—— 检查 Accept 响应字段([HTTP] 的 第 12.5.1 节):¶
如第 2.3 节和第 2.4 节所述,成功响应中的 Content-Location 和 Location 响应字段 (2xx,[HTTP] 的 第 15.3 节)提供了一种 标识替代资源的方式, 这些资源会响应 GET 请求,既可以用于获取已收到的请求结果,也可以用于未来 执行相同操作的请求。回到附录 A.1中的示例:¶
响应:¶
上面收到的 Content-Location 响应字段标识了一个保存 其所在 QUERY 响应结果的资源:¶
响应:¶
请注意,无法保证服务器会无限期地实现此资源, 因此,在收到错误响应后,客户端需要重新发出 原始 QUERY 请求,以获得新的替代位置。¶
Location 响应字段标识一个资源,该资源会响应 GET, 返回与原始 QUERY 请求相同过程和参数的当前结果。¶
在此示例中,一条记录于 2024-11-17T16:12:01Z 被移除(如 Last-Modified 字段所示),因此响应只包含两条记录:¶
假设服务器仍然公开该资源,并且查询结果没有变化, 则随后带有以下内容的条件 GET 请求:¶
将产生 304(未修改)响应([HTTP] 的 第 15.4.5 节)。¶
考虑一个实现 QUERY 的资源,它支持“application/sql”和 “application/xslt+xml” [XSLT] 作为请求 媒体类型,并且 可以生成“text/csv”响应。被查询的数据集包含 RFC 文档 信息,并且查询返回按十年分组的信息:¶
响应:¶
此处,服务器已将路径“/stored-queries/4815162342”分配给等效 资源(第 2.4 节),以便随后 与 GET 一起使用。¶
稍后,客户端重复该查询,但指定只有当结果 发生变化时才返回:¶
被查询的数据没有变化,因此服务器响应:¶
由于服务器为等效资源标识了 URI,因此可以 使用 GET 访问该资源。特别是,这避免了重新发送查询请求的 内容:¶
此处,数据集的状态确实发生了变化,因此返回新内容:¶
(请注意本十年对应行中的变化。)¶
下面的图示说明了条件请求的使用方式,以及当为等效资源分配 URI 时 (以及客户端利用该 URI 时)它们可能有何不同。 虚构的字段名称“Validator”仅用于演示。¶
“超文本传输协议(HTTP)方法注册表”(<http://www.iana.org/assignments/http-methods>) 已经包含另外三个具有“安全”和“幂等”属性的方法: “PROPFIND” [RFC4918]、“REPORT” [RFC3253] 和 “SEARCH” [RFC5323]。¶
本来可以复用其中任何一个方法,并对其进行更新,使其匹配 本规范定义的新方法“QUERY”。实际上,本规范的早期阶段 使用的是“SEARCH”。¶
最终选择方法名称“QUERY”的原因是:¶
感谢 HTTP 工作组的所有成员提供想法、评审和反馈。¶
以下人员值得特别致谢: Carsten Bormann、 Mark Nottingham、 Martin Thomson、 Michael Thornburgh、 Roberto Polli、 Roy Fielding 和 Will Hawkins。¶
Ashok Malhotra 参与了促成本 规范形成的早期讨论:¶
Asbjørn Ulsberg 在 2019 年 HTTP 研讨会上重新开启了关于该 HTTP 方法的讨论:¶